aboutsummaryrefslogtreecommitdiffhomepage
path: root/third_party/protobuf
diff options
context:
space:
mode:
authorGravatar Alex Humesky <ahumesky@google.com>2016-09-06 17:55:16 -0400
committerGravatar Kristina Chodorow <kchodorow@google.com>2016-09-07 10:09:20 -0400
commit211c7d00b348ec705639ada41536b6f60e9a6ed0 (patch)
treee0775b38943a3f4eed0bc17336e34c59ce644529 /third_party/protobuf
parent77062125f8787f29c9f21cd025eae8d38f712bb5 (diff)
Adds protobuf 3.0.0 to third_party
Change-Id: I91f5b85852cabff0da8b1c68bf432596d7dc341d
Diffstat (limited to 'third_party/protobuf')
-rw-r--r--third_party/protobuf/3.0.0/protobuf-java-3.0.0.jarbin0 -> 1304430 bytes
-rwxr-xr-xthird_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_32.exebin0 -> 3811164 bytes
-rwxr-xr-xthird_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_64.exebin0 -> 49067924 bytes
-rwxr-xr-xthird_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_32.exebin0 -> 4699352 bytes
-rwxr-xr-xthird_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_64.exebin0 -> 4810344 bytes
-rwxr-xr-xthird_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_32.exebin0 -> 4064256 bytes
-rwxr-xr-xthird_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_64.exebin0 -> 3987456 bytes
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/__init__.py4
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/__init__.py39
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/descriptor.py993
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/descriptor_database.py141
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/descriptor_pool.py814
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/__init__.py0
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/_parameterized.py443
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/any_test.proto42
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.cc129
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.py113
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/containers.py615
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/decoder.py854
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_database_test.py69
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test.py768
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test1.proto96
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test2.proto73
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_test.py823
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/encoder.py823
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/enum_type_wrapper.py89
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test1.proto58
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test2.proto99
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/file_options_test.proto43
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/generator_test.py348
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/__init__.py33
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/inner.proto37
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/outer.proto39
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/json_format_test.py815
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/message_factory_test.py190
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/message_listener.py78
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/message_set_extensions.proto74
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/message_test.py1856
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/missing_enum_values.proto56
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions.proto59
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions_dynamic.proto50
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/more_messages.proto52
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/packed_field_test.proto73
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/proto_builder_test.py96
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/python_message.py1550
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/reflection_test.py2984
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/service_reflection_test.py140
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/symbol_database_test.py131
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/test_bad_identifiers.proto53
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/test_util.py696
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/text_encoding_test.py72
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/text_format_test.py1359
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/type_checkers.py352
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/unknown_fields_test.py320
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types.py724
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types_test.py644
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format.py268
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format_test.py257
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/json_format.py664
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/message.py295
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/message_factory.py147
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/proto_builder.py130
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/README6
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/__init__.py4
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/cpp_message.py65
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.cc1845
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.h103
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.cc1786
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.h109
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.cc148
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.h75
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.cc631
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.h167
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.cc337
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.h137
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.cc970
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.h142
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.cc3085
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.h367
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/message_module.cc88
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/proto2_api_test.proto40
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/python.proto68
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/python_protobuf.h57
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.cc612
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.h179
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.cc812
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.h122
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/pyext/scoped_pyobject_ptr.h96
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/reflection.py114
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/service.py226
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/service_reflection.py284
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/symbol_database.py169
-rw-r--r--third_party/protobuf/3.0.0/python/google/protobuf/text_encoding.py107
-rwxr-xr-xthird_party/protobuf/3.0.0/python/google/protobuf/text_format.py1490
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/any.cc114
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/any.h107
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/any.pb.cc496
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/any.pb.h258
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/any.proto140
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/any_test.cc89
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/any_test.proto41
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/api.pb.cc2028
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/api.pb.h996
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/api.proto202
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/arena.cc314
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arena.h925
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arena_nc.cc45
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arena_nc_test.py61
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.cc50
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.h60
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arena_unittest.cc1353
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arenastring.cc53
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/arenastring.h314
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/arenastring_unittest.cc110
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.cc85
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.h176
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.cc1887
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.h394
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface_unittest.cc1849
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_bootstrap_unittest.cc159
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.cc319
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.h111
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.cc507
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.h124
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.cc210
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.h86
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.cc201
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.h229
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.cc1058
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.h164
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.cc168
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.h72
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.cc704
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.h306
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.cc437
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.h80
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.cc3819
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.h208
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.cc1055
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.h150
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_options.h69
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_plugin_unittest.cc252
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.cc458
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.h126
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.cc336
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.h118
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.cc871
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.h132
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_bad_identifiers.proto156
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_large_enum_value.proto43
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.cc2139
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.h51
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/metadata_test.cc242
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.cc114
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.h51
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.cc94
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.h63
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.cc120
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.h81
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.cc430
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.h105
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.cc118
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.h58
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator_unittest.cc70
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.cc506
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.h132
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.cc141
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.h73
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.cc528
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.h89
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.cc200
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.h90
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_names.h103
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_options.h86
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.cc218
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.h94
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.cc290
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.h71
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.cc127
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.h75
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.cc144
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.h75
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.cc125
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.h71
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.cc73
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.h70
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.cc211
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.h91
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.cc496
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.h326
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer_unittest.cc523
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.cc202
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.h112
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.cc233
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.h69
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment_unittest.cc67
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.cc397
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.h98
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.cc969
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.h160
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.cc962
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.h159
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.cc221
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.h98
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.cc174
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.h113
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.cc118
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.h76
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.cc332
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.h197
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.cc639
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.h120
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.cc202
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.h72
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.cc87
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.h101
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.cc776
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.h396
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.cc814
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.h121
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.cc723
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.h118
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.cc743
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.h80
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.cc836
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.h78
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.cc1466
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.h142
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.cc737
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.h86
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.cc179
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.h83
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.cc1296
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.h173
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.cc941
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.h157
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.cc1099
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.h92
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.cc273
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.h125
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_names.h87
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_options.h73
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_plugin_unittest.cc128
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.cc860
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.h160
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.cc914
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.h163
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.cc473
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.h135
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.cc222
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.h96
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.cc1005
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.h159
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.cc872
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.h157
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.cc143
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.h87
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.cc544
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.h126
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.cc150
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.h74
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.cc209
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.h130
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.cc263
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.h94
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.cc230
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.h72
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.cc591
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.h199
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.cc186
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.h70
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.cc676
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.h97
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.cc363
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.h121
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_params.h258
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.cc968
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.h150
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.cc3307
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.h281
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/main.cc98
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.cc255
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.h122
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.cc219
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.h73
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.cc147
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.h80
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.cc136
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.h69
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.cc477
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.h194
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.cc637
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.h102
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.cc151
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.h61
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.cc1375
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.h230
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers_unittest.cc257
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.cc180
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.h67
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.cc616
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.h99
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.cc108
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.h81
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.cc138
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.h79
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.cc192
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.h92
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/package_info.h64
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.cc2119
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.h569
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser_unittest.cc3157
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.cc194
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.h90
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.cc1605
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.h830
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.proto150
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.cc1382
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.h174
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_plugin_unittest.cc170
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code.proto67
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code_pb.rb74
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.cc501
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.h58
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator_unittest.cc109
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.cc465
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.h108
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/test_plugin.cc51
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_output_unittest.sh91
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.cc218
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.h93
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor.cc6295
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor.h1919
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.cc15680
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.h8002
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor.proto813
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.cc543
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.h369
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database_unittest.cc753
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/descriptor_unittest.cc6615
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/drop_unknown_fields_test.cc88
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.cc422
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.h176
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/duration.proto98
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.cc873
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.h152
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message_unittest.cc291
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.cc316
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.h147
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/empty.proto53
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/extension_set.cc1816
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/extension_set.h1318
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/extension_set_heavy.cc801
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/extension_set_unittest.cc1275
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.cc402
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.h206
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/field_mask.proto246
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_reflection.h88
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_util.h46
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.cc2319
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.h683
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection_unittest.cc919
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.cc84
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.h127
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.cc956
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.h1367
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_inl.h90
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_unittest.cc1385
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.cc330
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.h209
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream_unittest.sh44
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/package_info.h54
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/printer.cc346
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/printer.h353
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/printer_unittest.cc523
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.cc125
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.h55
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.cc1139
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.h411
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer_unittest.cc996
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.cc58
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.h248
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.cc474
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.h358
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.cc438
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.h410
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_unittest.cc1007
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/lite_arena_unittest.cc83
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/lite_unittest.cc718
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map.h1742
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_entry.h310
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_entry_lite.h568
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_field.cc471
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_field.h397
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_field_inl.h489
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_field_lite.h278
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_field_test.cc494
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.cc93
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.h80
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_lite_unittest.proto130
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_proto2_unittest.proto86
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_test.cc3067
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.cc1801
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.h159
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_test_util_impl.h490
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_type_handler.h743
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_unittest.proto129
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/map_unittest_proto3.proto120
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/message.cc515
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/message.h1150
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/message_lite.cc371
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/message_lite.h296
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/message_unittest.cc471
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/metadata.h163
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/no_field_presence_test.cc577
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/package_info.h64
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/preserve_unknown_enum_test.cc289
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_lite_unittest.cc164
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_unittest.cc209
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/proto3_lite_unittest.cc145
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/reflection.h600
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/reflection_internal.h378
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.cc269
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.h81
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops_unittest.cc476
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.cc102
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.h2481
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_reflection_unittest.cc706
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_unittest.cc1566
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/service.cc46
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/service.h292
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.cc394
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.h190
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/source_context.proto48
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.cc1579
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.h781
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/struct.proto96
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomic_sequence_num.h54
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops.h246
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm64_gcc.h325
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h151
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_qnx.h146
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_atomicword_compat.h122
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_generic_gcc.h137
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_macosx.h225
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_mips_gcc.h313
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_pnacl.h231
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_power.h440
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_ppc_gcc.h155
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_solaris.h188
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_tsan.h219
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.cc137
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.h293
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.cc112
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.h150
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.cc196
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.h348
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream_unittest.cc146
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/callback.h546
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/casts.h133
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.cc459
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.h225
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/common_unittest.cc358
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/fastmem.h152
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/hash.h438
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.cc201
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.h383
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128_unittest.cc513
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/logging.h237
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/macros.h168
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/map_util.h769
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.cc144
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.h279
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathutil.h162
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/mutex.h148
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.cc99
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.h167
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/once_unittest.cc255
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/platform_macros.h125
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/port.h393
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/scoped_ptr.h236
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/shared_ptr.h470
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/singleton.h68
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.cc134
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.h116
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_macros.h89
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_test.cc131
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.cc46
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.h259
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor_test.cc274
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/stl_util.h121
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.cc268
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.h483
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece_unittest.cc794
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.cc174
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.h76
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf_unittest.cc152
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid.cc588
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid_unittest.cc40
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.cc2289
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.h876
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil_unittest.cc810
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.cc134
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.h170
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util.h138
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util_unittest.cc130
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.cc365
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.h75
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/time_test.cc208
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits.h364
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits_unittest.cc631
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/test_util.cc3350
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/test_util.h215
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.cc1586
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.h101
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/bad_utf8_string1
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_messagebin0 -> 531 bytes
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_mapsbin0 -> 13619 bytes
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_oneof_implementedbin0 -> 515 bytes
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_proto3bin0 -> 248 bytes
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_packed_fields_messagebin0 -> 142 bytes
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/map_test_data.txt140
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data.txt134
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_oneof_implemented.txt129
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy.txt134
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy_oneof.txt129
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data.txt134
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data_pointy.txt134
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testing/file.cc200
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testing/file.h100
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.cc271
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.h102
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgunzip.cc80
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgzip.cc86
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/text_format.cc2007
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/text_format.h517
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/text_format_unittest.cc1493
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.cc448
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.h189
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/timestamp.proto111
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/type.pb.cc3304
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/type.pb.h1751
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/type.proto180
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest.proto880
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_arena.proto46
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_custom_options.proto430
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_drop_unknown_fields.proto58
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_embed_optimize_for.proto51
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_empty.proto38
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_enormous_descriptor.proto1048
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_import.proto73
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_lite.proto52
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_proto3.proto68
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public.proto41
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_lite.proto43
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_proto3.proto42
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite.proto407
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite_imports_nonlite.proto44
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset.proto82
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset_wire_format.proto52
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena.proto202
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_import.proto37
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_lite.proto42
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_field_presence.proto138
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_generic_services.proto54
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_optimize_for.proto67
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum.proto71
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum2.proto50
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3.proto388
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena.proto206
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena_lite.proto207
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_lite.proto206
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unittest_well_known_types.proto114
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.cc333
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.h346
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set_unittest.cc609
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.cc208
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.h259
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator_test.cc488
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.cc538
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.h193
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util_test.cc606
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/constants.h103
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.cc378
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.h204
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.cc596
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.h284
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter_test.cc189
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.cc42
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.h103
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/expecting_objectwriter.h238
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.cc225
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.h72
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.cc404
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.h91
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.cc183
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.h215
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter_test.cc313
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.cc820
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.h258
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser_test.cc819
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/location_tracker.h65
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/mock_error_listener.h63
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_location_tracker.h64
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_source.h79
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.cc92
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.h139
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.cc796
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.h345
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.cc1114
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.h302
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource_test.cc1007
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.cc1215
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.h345
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter_test.cc2394
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/structured_objectwriter.h118
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/anys.proto53
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/books.proto187
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value.proto170
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value_test.proto53
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/field_mask.proto71
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/maps.proto86
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/oneofs.proto68
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/struct.proto45
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/timestamp_duration.proto47
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/wrappers.proto100
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.cc171
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.h92
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.cc134
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.h98
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.cc365
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.h197
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/json_format_proto3.proto181
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.cc242
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.h190
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/json_util_test.cc354
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.cc1692
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.h849
-rwxr-xr-xthird_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.cc3151
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.proto74
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.cc532
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.h293
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/time_util_test.cc380
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver.h75
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.cc259
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.h52
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util_test.cc352
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/well_known_types_unittest.cc60
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wire_format.cc1133
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wire_format.h337
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.cc545
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.h724
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite_inl.h876
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wire_format_unittest.cc1289
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.cc2801
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.h1216
-rw-r--r--third_party/protobuf/3.0.0/src/google/protobuf/wrappers.proto119
657 files changed, 293815 insertions, 0 deletions
diff --git a/third_party/protobuf/3.0.0/protobuf-java-3.0.0.jar b/third_party/protobuf/3.0.0/protobuf-java-3.0.0.jar
new file mode 100644
index 0000000000..7f36b33432
--- /dev/null
+++ b/third_party/protobuf/3.0.0/protobuf-java-3.0.0.jar
Binary files differ
diff --git a/third_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_32.exe b/third_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_32.exe
new file mode 100755
index 0000000000..1765da52aa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_32.exe
Binary files differ
diff --git a/third_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_64.exe b/third_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_64.exe
new file mode 100755
index 0000000000..7c04254e48
--- /dev/null
+++ b/third_party/protobuf/3.0.0/protoc-3.0.0-linux-x86_64.exe
Binary files differ
diff --git a/third_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_32.exe b/third_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_32.exe
new file mode 100755
index 0000000000..892eec6815
--- /dev/null
+++ b/third_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_32.exe
Binary files differ
diff --git a/third_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_64.exe b/third_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_64.exe
new file mode 100755
index 0000000000..1ca8aa8f8d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/protoc-3.0.0-osx-x86_64.exe
Binary files differ
diff --git a/third_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_32.exe b/third_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_32.exe
new file mode 100755
index 0000000000..9285f90e50
--- /dev/null
+++ b/third_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_32.exe
Binary files differ
diff --git a/third_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_64.exe b/third_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_64.exe
new file mode 100755
index 0000000000..061fcc109b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/protoc-3.0.0-windows-x86_64.exe
Binary files differ
diff --git a/third_party/protobuf/3.0.0/python/google/__init__.py b/third_party/protobuf/3.0.0/python/google/__init__.py
new file mode 100755
index 0000000000..5585614122
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/__init__.py
@@ -0,0 +1,4 @@
+try:
+ __import__('pkg_resources').declare_namespace(__name__)
+except ImportError:
+ __path__ = __import__('pkgutil').extend_path(__path__, __name__)
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/__init__.py b/third_party/protobuf/3.0.0/python/google/protobuf/__init__.py
new file mode 100755
index 0000000000..6210a404b5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/__init__.py
@@ -0,0 +1,39 @@
+# 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.
+
+# Copyright 2007 Google Inc. All Rights Reserved.
+
+__version__ = '3.0.0'
+
+if __name__ != '__main__':
+ try:
+ __import__('pkg_resources').declare_namespace(__name__)
+ except ImportError:
+ __path__ = __import__('pkgutil').extend_path(__path__, __name__)
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/descriptor.py b/third_party/protobuf/3.0.0/python/google/protobuf/descriptor.py
new file mode 100755
index 0000000000..873af30646
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/descriptor.py
@@ -0,0 +1,993 @@
+# 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.
+
+"""Descriptors essentially contain exactly the information found in a .proto
+file, in types that make this information accessible in Python.
+"""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+import six
+
+from google.protobuf.internal import api_implementation
+
+_USE_C_DESCRIPTORS = False
+if api_implementation.Type() == 'cpp':
+ # Used by MakeDescriptor in cpp mode
+ import os
+ import uuid
+ from google.protobuf.pyext import _message
+ _USE_C_DESCRIPTORS = getattr(_message, '_USE_C_DESCRIPTORS', False)
+
+
+class Error(Exception):
+ """Base error for this module."""
+
+
+class TypeTransformationError(Error):
+ """Error transforming between python proto type and corresponding C++ type."""
+
+
+if _USE_C_DESCRIPTORS:
+ # This metaclass allows to override the behavior of code like
+ # isinstance(my_descriptor, FieldDescriptor)
+ # and make it return True when the descriptor is an instance of the extension
+ # type written in C++.
+ class DescriptorMetaclass(type):
+ def __instancecheck__(cls, obj):
+ if super(DescriptorMetaclass, cls).__instancecheck__(obj):
+ return True
+ if isinstance(obj, cls._C_DESCRIPTOR_CLASS):
+ return True
+ return False
+else:
+ # The standard metaclass; nothing changes.
+ DescriptorMetaclass = type
+
+
+class DescriptorBase(six.with_metaclass(DescriptorMetaclass)):
+
+ """Descriptors base class.
+
+ This class is the base of all descriptor classes. It provides common options
+ related functionality.
+
+ Attributes:
+ has_options: True if the descriptor has non-default options. Usually it
+ is not necessary to read this -- just call GetOptions() which will
+ happily return the default instance. However, it's sometimes useful
+ for efficiency, and also useful inside the protobuf implementation to
+ avoid some bootstrapping issues.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ # The class, or tuple of classes, that are considered as "virtual
+ # subclasses" of this descriptor class.
+ _C_DESCRIPTOR_CLASS = ()
+
+ def __init__(self, options, options_class_name):
+ """Initialize the descriptor given its options message and the name of the
+ class of the options message. The name of the class is required in case
+ the options message is None and has to be created.
+ """
+ self._options = options
+ self._options_class_name = options_class_name
+
+ # Does this descriptor have non-default options?
+ self.has_options = options is not None
+
+ def _SetOptions(self, options, options_class_name):
+ """Sets the descriptor's options
+
+ This function is used in generated proto2 files to update descriptor
+ options. It must not be used outside proto2.
+ """
+ self._options = options
+ self._options_class_name = options_class_name
+
+ # Does this descriptor have non-default options?
+ self.has_options = options is not None
+
+ def GetOptions(self):
+ """Retrieves descriptor options.
+
+ This method returns the options set or creates the default options for the
+ descriptor.
+ """
+ if self._options:
+ return self._options
+ from google.protobuf import descriptor_pb2
+ try:
+ options_class = getattr(descriptor_pb2, self._options_class_name)
+ except AttributeError:
+ raise RuntimeError('Unknown options class name %s!' %
+ (self._options_class_name))
+ self._options = options_class()
+ return self._options
+
+
+class _NestedDescriptorBase(DescriptorBase):
+ """Common class for descriptors that can be nested."""
+
+ def __init__(self, options, options_class_name, name, full_name,
+ file, containing_type, serialized_start=None,
+ serialized_end=None):
+ """Constructor.
+
+ Args:
+ options: Protocol message options or None
+ to use default message options.
+ options_class_name: (str) The class name of the above options.
+
+ name: (str) Name of this protocol message type.
+ full_name: (str) Fully-qualified name of this protocol message type,
+ which will include protocol "package" name and the name of any
+ enclosing types.
+ file: (FileDescriptor) Reference to file info.
+ containing_type: if provided, this is a nested descriptor, with this
+ descriptor as parent, otherwise None.
+ serialized_start: The start index (inclusive) in block in the
+ file.serialized_pb that describes this descriptor.
+ serialized_end: The end index (exclusive) in block in the
+ file.serialized_pb that describes this descriptor.
+ """
+ super(_NestedDescriptorBase, self).__init__(
+ options, options_class_name)
+
+ self.name = name
+ # TODO(falk): Add function to calculate full_name instead of having it in
+ # memory?
+ self.full_name = full_name
+ self.file = file
+ self.containing_type = containing_type
+
+ self._serialized_start = serialized_start
+ self._serialized_end = serialized_end
+
+ def GetTopLevelContainingType(self):
+ """Returns the root if this is a nested type, or itself if its the root."""
+ desc = self
+ while desc.containing_type is not None:
+ desc = desc.containing_type
+ return desc
+
+ def CopyToProto(self, proto):
+ """Copies this to the matching proto in descriptor_pb2.
+
+ Args:
+ proto: An empty proto instance from descriptor_pb2.
+
+ Raises:
+ Error: If self couldnt be serialized, due to to few constructor arguments.
+ """
+ if (self.file is not None and
+ self._serialized_start is not None and
+ self._serialized_end is not None):
+ proto.ParseFromString(self.file.serialized_pb[
+ self._serialized_start:self._serialized_end])
+ else:
+ raise Error('Descriptor does not contain serialization.')
+
+
+class Descriptor(_NestedDescriptorBase):
+
+ """Descriptor for a protocol message type.
+
+ A Descriptor instance has the following attributes:
+
+ name: (str) Name of this protocol message type.
+ full_name: (str) Fully-qualified name of this protocol message type,
+ which will include protocol "package" name and the name of any
+ enclosing types.
+
+ containing_type: (Descriptor) Reference to the descriptor of the
+ type containing us, or None if this is top-level.
+
+ fields: (list of FieldDescriptors) Field descriptors for all
+ fields in this type.
+ fields_by_number: (dict int -> FieldDescriptor) Same FieldDescriptor
+ objects as in |fields|, but indexed by "number" attribute in each
+ FieldDescriptor.
+ fields_by_name: (dict str -> FieldDescriptor) Same FieldDescriptor
+ objects as in |fields|, but indexed by "name" attribute in each
+ FieldDescriptor.
+ fields_by_camelcase_name: (dict str -> FieldDescriptor) Same
+ FieldDescriptor objects as in |fields|, but indexed by
+ "camelcase_name" attribute in each FieldDescriptor.
+
+ nested_types: (list of Descriptors) Descriptor references
+ for all protocol message types nested within this one.
+ nested_types_by_name: (dict str -> Descriptor) Same Descriptor
+ objects as in |nested_types|, but indexed by "name" attribute
+ in each Descriptor.
+
+ enum_types: (list of EnumDescriptors) EnumDescriptor references
+ for all enums contained within this type.
+ enum_types_by_name: (dict str ->EnumDescriptor) Same EnumDescriptor
+ objects as in |enum_types|, but indexed by "name" attribute
+ in each EnumDescriptor.
+ enum_values_by_name: (dict str -> EnumValueDescriptor) Dict mapping
+ from enum value name to EnumValueDescriptor for that value.
+
+ extensions: (list of FieldDescriptor) All extensions defined directly
+ within this message type (NOT within a nested type).
+ extensions_by_name: (dict, string -> FieldDescriptor) Same FieldDescriptor
+ objects as |extensions|, but indexed by "name" attribute of each
+ FieldDescriptor.
+
+ is_extendable: Does this type define any extension ranges?
+
+ oneofs: (list of OneofDescriptor) The list of descriptors for oneof fields
+ in this message.
+ oneofs_by_name: (dict str -> OneofDescriptor) Same objects as in |oneofs|,
+ but indexed by "name" attribute.
+
+ file: (FileDescriptor) Reference to file descriptor.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.Descriptor
+
+ def __new__(cls, name, full_name, filename, containing_type, fields,
+ nested_types, enum_types, extensions, options=None,
+ is_extendable=True, extension_ranges=None, oneofs=None,
+ file=None, serialized_start=None, serialized_end=None, # pylint: disable=redefined-builtin
+ syntax=None):
+ _message.Message._CheckCalledFromGeneratedFile()
+ return _message.default_pool.FindMessageTypeByName(full_name)
+
+ # NOTE(tmarek): The file argument redefining a builtin is nothing we can
+ # fix right now since we don't know how many clients already rely on the
+ # name of the argument.
+ def __init__(self, name, full_name, filename, containing_type, fields,
+ nested_types, enum_types, extensions, options=None,
+ is_extendable=True, extension_ranges=None, oneofs=None,
+ file=None, serialized_start=None, serialized_end=None, # pylint: disable=redefined-builtin
+ syntax=None):
+ """Arguments to __init__() are as described in the description
+ of Descriptor fields above.
+
+ Note that filename is an obsolete argument, that is not used anymore.
+ Please use file.name to access this as an attribute.
+ """
+ super(Descriptor, self).__init__(
+ options, 'MessageOptions', name, full_name, file,
+ containing_type, serialized_start=serialized_start,
+ serialized_end=serialized_end)
+
+ # We have fields in addition to fields_by_name and fields_by_number,
+ # so that:
+ # 1. Clients can index fields by "order in which they're listed."
+ # 2. Clients can easily iterate over all fields with the terse
+ # syntax: for f in descriptor.fields: ...
+ self.fields = fields
+ for field in self.fields:
+ field.containing_type = self
+ self.fields_by_number = dict((f.number, f) for f in fields)
+ self.fields_by_name = dict((f.name, f) for f in fields)
+ self._fields_by_camelcase_name = None
+
+ self.nested_types = nested_types
+ for nested_type in nested_types:
+ nested_type.containing_type = self
+ self.nested_types_by_name = dict((t.name, t) for t in nested_types)
+
+ self.enum_types = enum_types
+ for enum_type in self.enum_types:
+ enum_type.containing_type = self
+ self.enum_types_by_name = dict((t.name, t) for t in enum_types)
+ self.enum_values_by_name = dict(
+ (v.name, v) for t in enum_types for v in t.values)
+
+ self.extensions = extensions
+ for extension in self.extensions:
+ extension.extension_scope = self
+ self.extensions_by_name = dict((f.name, f) for f in extensions)
+ self.is_extendable = is_extendable
+ self.extension_ranges = extension_ranges
+ self.oneofs = oneofs if oneofs is not None else []
+ self.oneofs_by_name = dict((o.name, o) for o in self.oneofs)
+ for oneof in self.oneofs:
+ oneof.containing_type = self
+ self.syntax = syntax or "proto2"
+
+ @property
+ def fields_by_camelcase_name(self):
+ if self._fields_by_camelcase_name is None:
+ self._fields_by_camelcase_name = dict(
+ (f.camelcase_name, f) for f in self.fields)
+ return self._fields_by_camelcase_name
+
+ def EnumValueName(self, enum, value):
+ """Returns the string name of an enum value.
+
+ This is just a small helper method to simplify a common operation.
+
+ Args:
+ enum: string name of the Enum.
+ value: int, value of the enum.
+
+ Returns:
+ string name of the enum value.
+
+ Raises:
+ KeyError if either the Enum doesn't exist or the value is not a valid
+ value for the enum.
+ """
+ return self.enum_types_by_name[enum].values_by_number[value].name
+
+ def CopyToProto(self, proto):
+ """Copies this to a descriptor_pb2.DescriptorProto.
+
+ Args:
+ proto: An empty descriptor_pb2.DescriptorProto.
+ """
+ # This function is overridden to give a better doc comment.
+ super(Descriptor, self).CopyToProto(proto)
+
+
+# TODO(robinson): We should have aggressive checking here,
+# for example:
+# * If you specify a repeated field, you should not be allowed
+# to specify a default value.
+# * [Other examples here as needed].
+#
+# TODO(robinson): for this and other *Descriptor classes, we
+# might also want to lock things down aggressively (e.g.,
+# prevent clients from setting the attributes). Having
+# stronger invariants here in general will reduce the number
+# of runtime checks we must do in reflection.py...
+class FieldDescriptor(DescriptorBase):
+
+ """Descriptor for a single field in a .proto file.
+
+ A FieldDescriptor instance has the following attributes:
+
+ name: (str) Name of this field, exactly as it appears in .proto.
+ full_name: (str) Name of this field, including containing scope. This is
+ particularly relevant for extensions.
+ camelcase_name: (str) Camelcase name of this field.
+ index: (int) Dense, 0-indexed index giving the order that this
+ field textually appears within its message in the .proto file.
+ number: (int) Tag number declared for this field in the .proto file.
+
+ type: (One of the TYPE_* constants below) Declared type.
+ cpp_type: (One of the CPPTYPE_* constants below) C++ type used to
+ represent this field.
+
+ label: (One of the LABEL_* constants below) Tells whether this
+ field is optional, required, or repeated.
+ has_default_value: (bool) True if this field has a default value defined,
+ otherwise false.
+ default_value: (Varies) Default value of this field. Only
+ meaningful for non-repeated scalar fields. Repeated fields
+ should always set this to [], and non-repeated composite
+ fields should always set this to None.
+
+ containing_type: (Descriptor) Descriptor of the protocol message
+ type that contains this field. Set by the Descriptor constructor
+ if we're passed into one.
+ Somewhat confusingly, for extension fields, this is the
+ descriptor of the EXTENDED message, not the descriptor
+ of the message containing this field. (See is_extension and
+ extension_scope below).
+ message_type: (Descriptor) If a composite field, a descriptor
+ of the message type contained in this field. Otherwise, this is None.
+ enum_type: (EnumDescriptor) If this field contains an enum, a
+ descriptor of that enum. Otherwise, this is None.
+
+ is_extension: True iff this describes an extension field.
+ extension_scope: (Descriptor) Only meaningful if is_extension is True.
+ Gives the message that immediately contains this extension field.
+ Will be None iff we're a top-level (file-level) extension field.
+
+ options: (descriptor_pb2.FieldOptions) Protocol message field options or
+ None to use default field options.
+
+ containing_oneof: (OneofDescriptor) If the field is a member of a oneof
+ union, contains its descriptor. Otherwise, None.
+ """
+
+ # Must be consistent with C++ FieldDescriptor::Type enum in
+ # descriptor.h.
+ #
+ # TODO(robinson): Find a way to eliminate this repetition.
+ TYPE_DOUBLE = 1
+ TYPE_FLOAT = 2
+ TYPE_INT64 = 3
+ TYPE_UINT64 = 4
+ TYPE_INT32 = 5
+ TYPE_FIXED64 = 6
+ TYPE_FIXED32 = 7
+ TYPE_BOOL = 8
+ TYPE_STRING = 9
+ TYPE_GROUP = 10
+ TYPE_MESSAGE = 11
+ TYPE_BYTES = 12
+ TYPE_UINT32 = 13
+ TYPE_ENUM = 14
+ TYPE_SFIXED32 = 15
+ TYPE_SFIXED64 = 16
+ TYPE_SINT32 = 17
+ TYPE_SINT64 = 18
+ MAX_TYPE = 18
+
+ # Must be consistent with C++ FieldDescriptor::CppType enum in
+ # descriptor.h.
+ #
+ # TODO(robinson): Find a way to eliminate this repetition.
+ CPPTYPE_INT32 = 1
+ CPPTYPE_INT64 = 2
+ CPPTYPE_UINT32 = 3
+ CPPTYPE_UINT64 = 4
+ CPPTYPE_DOUBLE = 5
+ CPPTYPE_FLOAT = 6
+ CPPTYPE_BOOL = 7
+ CPPTYPE_ENUM = 8
+ CPPTYPE_STRING = 9
+ CPPTYPE_MESSAGE = 10
+ MAX_CPPTYPE = 10
+
+ _PYTHON_TO_CPP_PROTO_TYPE_MAP = {
+ TYPE_DOUBLE: CPPTYPE_DOUBLE,
+ TYPE_FLOAT: CPPTYPE_FLOAT,
+ TYPE_ENUM: CPPTYPE_ENUM,
+ TYPE_INT64: CPPTYPE_INT64,
+ TYPE_SINT64: CPPTYPE_INT64,
+ TYPE_SFIXED64: CPPTYPE_INT64,
+ TYPE_UINT64: CPPTYPE_UINT64,
+ TYPE_FIXED64: CPPTYPE_UINT64,
+ TYPE_INT32: CPPTYPE_INT32,
+ TYPE_SFIXED32: CPPTYPE_INT32,
+ TYPE_SINT32: CPPTYPE_INT32,
+ TYPE_UINT32: CPPTYPE_UINT32,
+ TYPE_FIXED32: CPPTYPE_UINT32,
+ TYPE_BYTES: CPPTYPE_STRING,
+ TYPE_STRING: CPPTYPE_STRING,
+ TYPE_BOOL: CPPTYPE_BOOL,
+ TYPE_MESSAGE: CPPTYPE_MESSAGE,
+ TYPE_GROUP: CPPTYPE_MESSAGE
+ }
+
+ # Must be consistent with C++ FieldDescriptor::Label enum in
+ # descriptor.h.
+ #
+ # TODO(robinson): Find a way to eliminate this repetition.
+ LABEL_OPTIONAL = 1
+ LABEL_REQUIRED = 2
+ LABEL_REPEATED = 3
+ MAX_LABEL = 3
+
+ # Must be consistent with C++ constants kMaxNumber, kFirstReservedNumber,
+ # and kLastReservedNumber in descriptor.h
+ MAX_FIELD_NUMBER = (1 << 29) - 1
+ FIRST_RESERVED_FIELD_NUMBER = 19000
+ LAST_RESERVED_FIELD_NUMBER = 19999
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.FieldDescriptor
+
+ def __new__(cls, name, full_name, index, number, type, cpp_type, label,
+ default_value, message_type, enum_type, containing_type,
+ is_extension, extension_scope, options=None,
+ has_default_value=True, containing_oneof=None):
+ _message.Message._CheckCalledFromGeneratedFile()
+ if is_extension:
+ return _message.default_pool.FindExtensionByName(full_name)
+ else:
+ return _message.default_pool.FindFieldByName(full_name)
+
+ def __init__(self, name, full_name, index, number, type, cpp_type, label,
+ default_value, message_type, enum_type, containing_type,
+ is_extension, extension_scope, options=None,
+ has_default_value=True, containing_oneof=None):
+ """The arguments are as described in the description of FieldDescriptor
+ attributes above.
+
+ Note that containing_type may be None, and may be set later if necessary
+ (to deal with circular references between message types, for example).
+ Likewise for extension_scope.
+ """
+ super(FieldDescriptor, self).__init__(options, 'FieldOptions')
+ self.name = name
+ self.full_name = full_name
+ self._camelcase_name = None
+ self.index = index
+ self.number = number
+ self.type = type
+ self.cpp_type = cpp_type
+ self.label = label
+ self.has_default_value = has_default_value
+ self.default_value = default_value
+ self.containing_type = containing_type
+ self.message_type = message_type
+ self.enum_type = enum_type
+ self.is_extension = is_extension
+ self.extension_scope = extension_scope
+ self.containing_oneof = containing_oneof
+ if api_implementation.Type() == 'cpp':
+ if is_extension:
+ self._cdescriptor = _message.default_pool.FindExtensionByName(full_name)
+ else:
+ self._cdescriptor = _message.default_pool.FindFieldByName(full_name)
+ else:
+ self._cdescriptor = None
+
+ @property
+ def camelcase_name(self):
+ if self._camelcase_name is None:
+ self._camelcase_name = _ToCamelCase(self.name)
+ return self._camelcase_name
+
+ @staticmethod
+ def ProtoTypeToCppProtoType(proto_type):
+ """Converts from a Python proto type to a C++ Proto Type.
+
+ The Python ProtocolBuffer classes specify both the 'Python' datatype and the
+ 'C++' datatype - and they're not the same. This helper method should
+ translate from one to another.
+
+ Args:
+ proto_type: the Python proto type (descriptor.FieldDescriptor.TYPE_*)
+ Returns:
+ descriptor.FieldDescriptor.CPPTYPE_*, the C++ type.
+ Raises:
+ TypeTransformationError: when the Python proto type isn't known.
+ """
+ try:
+ return FieldDescriptor._PYTHON_TO_CPP_PROTO_TYPE_MAP[proto_type]
+ except KeyError:
+ raise TypeTransformationError('Unknown proto_type: %s' % proto_type)
+
+
+class EnumDescriptor(_NestedDescriptorBase):
+
+ """Descriptor for an enum defined in a .proto file.
+
+ An EnumDescriptor instance has the following attributes:
+
+ name: (str) Name of the enum type.
+ full_name: (str) Full name of the type, including package name
+ and any enclosing type(s).
+
+ values: (list of EnumValueDescriptors) List of the values
+ in this enum.
+ values_by_name: (dict str -> EnumValueDescriptor) Same as |values|,
+ but indexed by the "name" field of each EnumValueDescriptor.
+ values_by_number: (dict int -> EnumValueDescriptor) Same as |values|,
+ but indexed by the "number" field of each EnumValueDescriptor.
+ containing_type: (Descriptor) Descriptor of the immediate containing
+ type of this enum, or None if this is an enum defined at the
+ top level in a .proto file. Set by Descriptor's constructor
+ if we're passed into one.
+ file: (FileDescriptor) Reference to file descriptor.
+ options: (descriptor_pb2.EnumOptions) Enum options message or
+ None to use default enum options.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.EnumDescriptor
+
+ def __new__(cls, name, full_name, filename, values,
+ containing_type=None, options=None, file=None,
+ serialized_start=None, serialized_end=None):
+ _message.Message._CheckCalledFromGeneratedFile()
+ return _message.default_pool.FindEnumTypeByName(full_name)
+
+ def __init__(self, name, full_name, filename, values,
+ containing_type=None, options=None, file=None,
+ serialized_start=None, serialized_end=None):
+ """Arguments are as described in the attribute description above.
+
+ Note that filename is an obsolete argument, that is not used anymore.
+ Please use file.name to access this as an attribute.
+ """
+ super(EnumDescriptor, self).__init__(
+ options, 'EnumOptions', name, full_name, file,
+ containing_type, serialized_start=serialized_start,
+ serialized_end=serialized_end)
+
+ self.values = values
+ for value in self.values:
+ value.type = self
+ self.values_by_name = dict((v.name, v) for v in values)
+ self.values_by_number = dict((v.number, v) for v in values)
+
+ def CopyToProto(self, proto):
+ """Copies this to a descriptor_pb2.EnumDescriptorProto.
+
+ Args:
+ proto: An empty descriptor_pb2.EnumDescriptorProto.
+ """
+ # This function is overridden to give a better doc comment.
+ super(EnumDescriptor, self).CopyToProto(proto)
+
+
+class EnumValueDescriptor(DescriptorBase):
+
+ """Descriptor for a single value within an enum.
+
+ name: (str) Name of this value.
+ index: (int) Dense, 0-indexed index giving the order that this
+ value appears textually within its enum in the .proto file.
+ number: (int) Actual number assigned to this enum value.
+ type: (EnumDescriptor) EnumDescriptor to which this value
+ belongs. Set by EnumDescriptor's constructor if we're
+ passed into one.
+ options: (descriptor_pb2.EnumValueOptions) Enum value options message or
+ None to use default enum value options options.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.EnumValueDescriptor
+
+ def __new__(cls, name, index, number, type=None, options=None):
+ _message.Message._CheckCalledFromGeneratedFile()
+ # There is no way we can build a complete EnumValueDescriptor with the
+ # given parameters (the name of the Enum is not known, for example).
+ # Fortunately generated files just pass it to the EnumDescriptor()
+ # constructor, which will ignore it, so returning None is good enough.
+ return None
+
+ def __init__(self, name, index, number, type=None, options=None):
+ """Arguments are as described in the attribute description above."""
+ super(EnumValueDescriptor, self).__init__(options, 'EnumValueOptions')
+ self.name = name
+ self.index = index
+ self.number = number
+ self.type = type
+
+
+class OneofDescriptor(DescriptorBase):
+ """Descriptor for a oneof field.
+
+ name: (str) Name of the oneof field.
+ full_name: (str) Full name of the oneof field, including package name.
+ index: (int) 0-based index giving the order of the oneof field inside
+ its containing type.
+ containing_type: (Descriptor) Descriptor of the protocol message
+ type that contains this field. Set by the Descriptor constructor
+ if we're passed into one.
+ fields: (list of FieldDescriptor) The list of field descriptors this
+ oneof can contain.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.OneofDescriptor
+
+ def __new__(
+ cls, name, full_name, index, containing_type, fields, options=None):
+ _message.Message._CheckCalledFromGeneratedFile()
+ return _message.default_pool.FindOneofByName(full_name)
+
+ def __init__(
+ self, name, full_name, index, containing_type, fields, options=None):
+ """Arguments are as described in the attribute description above."""
+ super(OneofDescriptor, self).__init__(options, 'OneofOptions')
+ self.name = name
+ self.full_name = full_name
+ self.index = index
+ self.containing_type = containing_type
+ self.fields = fields
+
+
+class ServiceDescriptor(_NestedDescriptorBase):
+
+ """Descriptor for a service.
+
+ name: (str) Name of the service.
+ full_name: (str) Full name of the service, including package name.
+ index: (int) 0-indexed index giving the order that this services
+ definition appears withing the .proto file.
+ methods: (list of MethodDescriptor) List of methods provided by this
+ service.
+ methods_by_name: (dict str -> MethodDescriptor) Same MethodDescriptor
+ objects as in |methods_by_name|, but indexed by "name" attribute in each
+ MethodDescriptor.
+ options: (descriptor_pb2.ServiceOptions) Service options message or
+ None to use default service options.
+ file: (FileDescriptor) Reference to file info.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.ServiceDescriptor
+
+ def __new__(cls, name, full_name, index, methods, options=None, file=None, # pylint: disable=redefined-builtin
+ serialized_start=None, serialized_end=None):
+ _message.Message._CheckCalledFromGeneratedFile() # pylint: disable=protected-access
+ return _message.default_pool.FindServiceByName(full_name)
+
+ def __init__(self, name, full_name, index, methods, options=None, file=None,
+ serialized_start=None, serialized_end=None):
+ super(ServiceDescriptor, self).__init__(
+ options, 'ServiceOptions', name, full_name, file,
+ None, serialized_start=serialized_start,
+ serialized_end=serialized_end)
+ self.index = index
+ self.methods = methods
+ self.methods_by_name = dict((m.name, m) for m in methods)
+ # Set the containing service for each method in this service.
+ for method in self.methods:
+ method.containing_service = self
+
+ def FindMethodByName(self, name):
+ """Searches for the specified method, and returns its descriptor."""
+ return self.methods_by_name.get(name, None)
+
+ def CopyToProto(self, proto):
+ """Copies this to a descriptor_pb2.ServiceDescriptorProto.
+
+ Args:
+ proto: An empty descriptor_pb2.ServiceDescriptorProto.
+ """
+ # This function is overridden to give a better doc comment.
+ super(ServiceDescriptor, self).CopyToProto(proto)
+
+
+class MethodDescriptor(DescriptorBase):
+
+ """Descriptor for a method in a service.
+
+ name: (str) Name of the method within the service.
+ full_name: (str) Full name of method.
+ index: (int) 0-indexed index of the method inside the service.
+ containing_service: (ServiceDescriptor) The service that contains this
+ method.
+ input_type: The descriptor of the message that this method accepts.
+ output_type: The descriptor of the message that this method returns.
+ options: (descriptor_pb2.MethodOptions) Method options message or
+ None to use default method options.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.MethodDescriptor
+
+ def __new__(cls, name, full_name, index, containing_service,
+ input_type, output_type, options=None):
+ _message.Message._CheckCalledFromGeneratedFile() # pylint: disable=protected-access
+ return _message.default_pool.FindMethodByName(full_name)
+
+ def __init__(self, name, full_name, index, containing_service,
+ input_type, output_type, options=None):
+ """The arguments are as described in the description of MethodDescriptor
+ attributes above.
+
+ Note that containing_service may be None, and may be set later if necessary.
+ """
+ super(MethodDescriptor, self).__init__(options, 'MethodOptions')
+ self.name = name
+ self.full_name = full_name
+ self.index = index
+ self.containing_service = containing_service
+ self.input_type = input_type
+ self.output_type = output_type
+
+
+class FileDescriptor(DescriptorBase):
+ """Descriptor for a file. Mimics the descriptor_pb2.FileDescriptorProto.
+
+ Note that enum_types_by_name, extensions_by_name, and dependencies
+ fields are only set by the message_factory module, and not by the
+ generated proto code.
+
+ name: name of file, relative to root of source tree.
+ package: name of the package
+ syntax: string indicating syntax of the file (can be "proto2" or "proto3")
+ serialized_pb: (str) Byte string of serialized
+ descriptor_pb2.FileDescriptorProto.
+ dependencies: List of other FileDescriptors this FileDescriptor depends on.
+ public_dependencies: A list of FileDescriptors, subset of the dependencies
+ above, which were declared as "public".
+ message_types_by_name: Dict of message names of their descriptors.
+ enum_types_by_name: Dict of enum names and their descriptors.
+ extensions_by_name: Dict of extension names and their descriptors.
+ services_by_name: Dict of services names and their descriptors.
+ pool: the DescriptorPool this descriptor belongs to. When not passed to the
+ constructor, the global default pool is used.
+ """
+
+ if _USE_C_DESCRIPTORS:
+ _C_DESCRIPTOR_CLASS = _message.FileDescriptor
+
+ def __new__(cls, name, package, options=None, serialized_pb=None,
+ dependencies=None, public_dependencies=None,
+ syntax=None, pool=None):
+ # FileDescriptor() is called from various places, not only from generated
+ # files, to register dynamic proto files and messages.
+ if serialized_pb:
+ # TODO(amauryfa): use the pool passed as argument. This will work only
+ # for C++-implemented DescriptorPools.
+ return _message.default_pool.AddSerializedFile(serialized_pb)
+ else:
+ return super(FileDescriptor, cls).__new__(cls)
+
+ def __init__(self, name, package, options=None, serialized_pb=None,
+ dependencies=None, public_dependencies=None,
+ syntax=None, pool=None):
+ """Constructor."""
+ super(FileDescriptor, self).__init__(options, 'FileOptions')
+
+ if pool is None:
+ from google.protobuf import descriptor_pool
+ pool = descriptor_pool.Default()
+ self.pool = pool
+ self.message_types_by_name = {}
+ self.name = name
+ self.package = package
+ self.syntax = syntax or "proto2"
+ self.serialized_pb = serialized_pb
+
+ self.enum_types_by_name = {}
+ self.extensions_by_name = {}
+ self.services_by_name = {}
+ self.dependencies = (dependencies or [])
+ self.public_dependencies = (public_dependencies or [])
+
+ if (api_implementation.Type() == 'cpp' and
+ self.serialized_pb is not None):
+ _message.default_pool.AddSerializedFile(self.serialized_pb)
+
+ def CopyToProto(self, proto):
+ """Copies this to a descriptor_pb2.FileDescriptorProto.
+
+ Args:
+ proto: An empty descriptor_pb2.FileDescriptorProto.
+ """
+ proto.ParseFromString(self.serialized_pb)
+
+
+def _ParseOptions(message, string):
+ """Parses serialized options.
+
+ This helper function is used to parse serialized options in generated
+ proto2 files. It must not be used outside proto2.
+ """
+ message.ParseFromString(string)
+ return message
+
+
+def _ToCamelCase(name):
+ """Converts name to camel-case and returns it."""
+ capitalize_next = False
+ result = []
+
+ for c in name:
+ if c == '_':
+ if result:
+ capitalize_next = True
+ elif capitalize_next:
+ result.append(c.upper())
+ capitalize_next = False
+ else:
+ result += c
+
+ # Lower-case the first letter.
+ if result and result[0].isupper():
+ result[0] = result[0].lower()
+ return ''.join(result)
+
+
+def MakeDescriptor(desc_proto, package='', build_file_if_cpp=True,
+ syntax=None):
+ """Make a protobuf Descriptor given a DescriptorProto protobuf.
+
+ Handles nested descriptors. Note that this is limited to the scope of defining
+ a message inside of another message. Composite fields can currently only be
+ resolved if the message is defined in the same scope as the field.
+
+ Args:
+ desc_proto: The descriptor_pb2.DescriptorProto protobuf message.
+ package: Optional package name for the new message Descriptor (string).
+ build_file_if_cpp: Update the C++ descriptor pool if api matches.
+ Set to False on recursion, so no duplicates are created.
+ syntax: The syntax/semantics that should be used. Set to "proto3" to get
+ proto3 field presence semantics.
+ Returns:
+ A Descriptor for protobuf messages.
+ """
+ if api_implementation.Type() == 'cpp' and build_file_if_cpp:
+ # The C++ implementation requires all descriptors to be backed by the same
+ # definition in the C++ descriptor pool. To do this, we build a
+ # FileDescriptorProto with the same definition as this descriptor and build
+ # it into the pool.
+ from google.protobuf import descriptor_pb2
+ file_descriptor_proto = descriptor_pb2.FileDescriptorProto()
+ file_descriptor_proto.message_type.add().MergeFrom(desc_proto)
+
+ # Generate a random name for this proto file to prevent conflicts with any
+ # imported ones. We need to specify a file name so the descriptor pool
+ # accepts our FileDescriptorProto, but it is not important what that file
+ # name is actually set to.
+ proto_name = str(uuid.uuid4())
+
+ if package:
+ file_descriptor_proto.name = os.path.join(package.replace('.', '/'),
+ proto_name + '.proto')
+ file_descriptor_proto.package = package
+ else:
+ file_descriptor_proto.name = proto_name + '.proto'
+
+ _message.default_pool.Add(file_descriptor_proto)
+ result = _message.default_pool.FindFileByName(file_descriptor_proto.name)
+
+ if _USE_C_DESCRIPTORS:
+ return result.message_types_by_name[desc_proto.name]
+
+ full_message_name = [desc_proto.name]
+ if package: full_message_name.insert(0, package)
+
+ # Create Descriptors for enum types
+ enum_types = {}
+ for enum_proto in desc_proto.enum_type:
+ full_name = '.'.join(full_message_name + [enum_proto.name])
+ enum_desc = EnumDescriptor(
+ enum_proto.name, full_name, None, [
+ EnumValueDescriptor(enum_val.name, ii, enum_val.number)
+ for ii, enum_val in enumerate(enum_proto.value)])
+ enum_types[full_name] = enum_desc
+
+ # Create Descriptors for nested types
+ nested_types = {}
+ for nested_proto in desc_proto.nested_type:
+ full_name = '.'.join(full_message_name + [nested_proto.name])
+ # Nested types are just those defined inside of the message, not all types
+ # used by fields in the message, so no loops are possible here.
+ nested_desc = MakeDescriptor(nested_proto,
+ package='.'.join(full_message_name),
+ build_file_if_cpp=False,
+ syntax=syntax)
+ nested_types[full_name] = nested_desc
+
+ fields = []
+ for field_proto in desc_proto.field:
+ full_name = '.'.join(full_message_name + [field_proto.name])
+ enum_desc = None
+ nested_desc = None
+ if field_proto.HasField('type_name'):
+ type_name = field_proto.type_name
+ full_type_name = '.'.join(full_message_name +
+ [type_name[type_name.rfind('.')+1:]])
+ if full_type_name in nested_types:
+ nested_desc = nested_types[full_type_name]
+ elif full_type_name in enum_types:
+ enum_desc = enum_types[full_type_name]
+ # Else type_name references a non-local type, which isn't implemented
+ field = FieldDescriptor(
+ field_proto.name, full_name, field_proto.number - 1,
+ field_proto.number, field_proto.type,
+ FieldDescriptor.ProtoTypeToCppProtoType(field_proto.type),
+ field_proto.label, None, nested_desc, enum_desc, None, False, None,
+ options=field_proto.options, has_default_value=False)
+ fields.append(field)
+
+ desc_name = '.'.join(full_message_name)
+ return Descriptor(desc_proto.name, desc_name, None, None, fields,
+ list(nested_types.values()), list(enum_types.values()), [],
+ options=desc_proto.options)
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/descriptor_database.py b/third_party/protobuf/3.0.0/python/google/protobuf/descriptor_database.py
new file mode 100644
index 0000000000..1333f9966e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/descriptor_database.py
@@ -0,0 +1,141 @@
+# 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.
+
+"""Provides a container for DescriptorProtos."""
+
+__author__ = 'matthewtoia@google.com (Matt Toia)'
+
+
+class Error(Exception):
+ pass
+
+
+class DescriptorDatabaseConflictingDefinitionError(Error):
+ """Raised when a proto is added with the same name & different descriptor."""
+
+
+class DescriptorDatabase(object):
+ """A container accepting FileDescriptorProtos and maps DescriptorProtos."""
+
+ def __init__(self):
+ self._file_desc_protos_by_file = {}
+ self._file_desc_protos_by_symbol = {}
+
+ def Add(self, file_desc_proto):
+ """Adds the FileDescriptorProto and its types to this database.
+
+ Args:
+ file_desc_proto: The FileDescriptorProto to add.
+ Raises:
+ DescriptorDatabaseException: if an attempt is made to add a proto
+ with the same name but different definition than an exisiting
+ proto in the database.
+ """
+ proto_name = file_desc_proto.name
+ if proto_name not in self._file_desc_protos_by_file:
+ self._file_desc_protos_by_file[proto_name] = file_desc_proto
+ elif self._file_desc_protos_by_file[proto_name] != file_desc_proto:
+ raise DescriptorDatabaseConflictingDefinitionError(
+ '%s already added, but with different descriptor.' % proto_name)
+
+ # Add the top-level Message, Enum and Extension descriptors to the index.
+ package = file_desc_proto.package
+ for message in file_desc_proto.message_type:
+ self._file_desc_protos_by_symbol.update(
+ (name, file_desc_proto) for name in _ExtractSymbols(message, package))
+ for enum in file_desc_proto.enum_type:
+ self._file_desc_protos_by_symbol[
+ '.'.join((package, enum.name))] = file_desc_proto
+ for extension in file_desc_proto.extension:
+ self._file_desc_protos_by_symbol[
+ '.'.join((package, extension.name))] = file_desc_proto
+
+ def FindFileByName(self, name):
+ """Finds the file descriptor proto by file name.
+
+ Typically the file name is a relative path ending to a .proto file. The
+ proto with the given name will have to have been added to this database
+ using the Add method or else an error will be raised.
+
+ Args:
+ name: The file name to find.
+
+ Returns:
+ The file descriptor proto matching the name.
+
+ Raises:
+ KeyError if no file by the given name was added.
+ """
+
+ return self._file_desc_protos_by_file[name]
+
+ def FindFileContainingSymbol(self, symbol):
+ """Finds the file descriptor proto containing the specified symbol.
+
+ The symbol should be a fully qualified name including the file descriptor's
+ package and any containing messages. Some examples:
+
+ 'some.package.name.Message'
+ 'some.package.name.Message.NestedEnum'
+
+ The file descriptor proto containing the specified symbol must be added to
+ this database using the Add method or else an error will be raised.
+
+ Args:
+ symbol: The fully qualified symbol name.
+
+ Returns:
+ The file descriptor proto containing the symbol.
+
+ Raises:
+ KeyError if no file contains the specified symbol.
+ """
+
+ return self._file_desc_protos_by_symbol[symbol]
+
+
+def _ExtractSymbols(desc_proto, package):
+ """Pulls out all the symbols from a descriptor proto.
+
+ Args:
+ desc_proto: The proto to extract symbols from.
+ package: The package containing the descriptor type.
+
+ Yields:
+ The fully qualified name found in the descriptor.
+ """
+
+ message_name = '.'.join((package, desc_proto.name))
+ yield message_name
+ for nested_type in desc_proto.nested_type:
+ for symbol in _ExtractSymbols(nested_type, message_name):
+ yield symbol
+ for enum_type in desc_proto.enum_type:
+ yield '.'.join((message_name, enum_type.name))
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/descriptor_pool.py b/third_party/protobuf/3.0.0/python/google/protobuf/descriptor_pool.py
new file mode 100644
index 0000000000..5c055ab9b7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/descriptor_pool.py
@@ -0,0 +1,814 @@
+# 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.
+
+"""Provides DescriptorPool to use as a container for proto2 descriptors.
+
+The DescriptorPool is used in conjection with a DescriptorDatabase to maintain
+a collection of protocol buffer descriptors for use when dynamically creating
+message types at runtime.
+
+For most applications protocol buffers should be used via modules generated by
+the protocol buffer compiler tool. This should only be used when the type of
+protocol buffers used in an application or library cannot be predetermined.
+
+Below is a straightforward example on how to use this class:
+
+ pool = DescriptorPool()
+ file_descriptor_protos = [ ... ]
+ for file_descriptor_proto in file_descriptor_protos:
+ pool.Add(file_descriptor_proto)
+ my_message_descriptor = pool.FindMessageTypeByName('some.package.MessageType')
+
+The message descriptor can be used in conjunction with the message_factory
+module in order to create a protocol buffer class that can be encoded and
+decoded.
+
+If you want to get a Python class for the specified proto, use the
+helper functions inside google.protobuf.message_factory
+directly instead of this class.
+"""
+
+__author__ = 'matthewtoia@google.com (Matt Toia)'
+
+from google.protobuf import descriptor
+from google.protobuf import descriptor_database
+from google.protobuf import text_encoding
+
+
+_USE_C_DESCRIPTORS = descriptor._USE_C_DESCRIPTORS
+
+
+def _NormalizeFullyQualifiedName(name):
+ """Remove leading period from fully-qualified type name.
+
+ Due to b/13860351 in descriptor_database.py, types in the root namespace are
+ generated with a leading period. This function removes that prefix.
+
+ Args:
+ name: A str, the fully-qualified symbol name.
+
+ Returns:
+ A str, the normalized fully-qualified symbol name.
+ """
+ return name.lstrip('.')
+
+
+class DescriptorPool(object):
+ """A collection of protobufs dynamically constructed by descriptor protos."""
+
+ if _USE_C_DESCRIPTORS:
+
+ def __new__(cls, descriptor_db=None):
+ # pylint: disable=protected-access
+ return descriptor._message.DescriptorPool(descriptor_db)
+
+ def __init__(self, descriptor_db=None):
+ """Initializes a Pool of proto buffs.
+
+ The descriptor_db argument to the constructor is provided to allow
+ specialized file descriptor proto lookup code to be triggered on demand. An
+ example would be an implementation which will read and compile a file
+ specified in a call to FindFileByName() and not require the call to Add()
+ at all. Results from this database will be cached internally here as well.
+
+ Args:
+ descriptor_db: A secondary source of file descriptors.
+ """
+
+ self._internal_db = descriptor_database.DescriptorDatabase()
+ self._descriptor_db = descriptor_db
+ self._descriptors = {}
+ self._enum_descriptors = {}
+ self._file_descriptors = {}
+
+ def Add(self, file_desc_proto):
+ """Adds the FileDescriptorProto and its types to this pool.
+
+ Args:
+ file_desc_proto: The FileDescriptorProto to add.
+ """
+
+ self._internal_db.Add(file_desc_proto)
+
+ def AddSerializedFile(self, serialized_file_desc_proto):
+ """Adds the FileDescriptorProto and its types to this pool.
+
+ Args:
+ serialized_file_desc_proto: A bytes string, serialization of the
+ FileDescriptorProto to add.
+ """
+
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf import descriptor_pb2
+ file_desc_proto = descriptor_pb2.FileDescriptorProto.FromString(
+ serialized_file_desc_proto)
+ self.Add(file_desc_proto)
+
+ def AddDescriptor(self, desc):
+ """Adds a Descriptor to the pool, non-recursively.
+
+ If the Descriptor contains nested messages or enums, the caller must
+ explicitly register them. This method also registers the FileDescriptor
+ associated with the message.
+
+ Args:
+ desc: A Descriptor.
+ """
+ if not isinstance(desc, descriptor.Descriptor):
+ raise TypeError('Expected instance of descriptor.Descriptor.')
+
+ self._descriptors[desc.full_name] = desc
+ self.AddFileDescriptor(desc.file)
+
+ def AddEnumDescriptor(self, enum_desc):
+ """Adds an EnumDescriptor to the pool.
+
+ This method also registers the FileDescriptor associated with the message.
+
+ Args:
+ enum_desc: An EnumDescriptor.
+ """
+
+ if not isinstance(enum_desc, descriptor.EnumDescriptor):
+ raise TypeError('Expected instance of descriptor.EnumDescriptor.')
+
+ self._enum_descriptors[enum_desc.full_name] = enum_desc
+ self.AddFileDescriptor(enum_desc.file)
+
+ def AddFileDescriptor(self, file_desc):
+ """Adds a FileDescriptor to the pool, non-recursively.
+
+ If the FileDescriptor contains messages or enums, the caller must explicitly
+ register them.
+
+ Args:
+ file_desc: A FileDescriptor.
+ """
+
+ if not isinstance(file_desc, descriptor.FileDescriptor):
+ raise TypeError('Expected instance of descriptor.FileDescriptor.')
+ self._file_descriptors[file_desc.name] = file_desc
+
+ def FindFileByName(self, file_name):
+ """Gets a FileDescriptor by file name.
+
+ Args:
+ file_name: The path to the file to get a descriptor for.
+
+ Returns:
+ A FileDescriptor for the named file.
+
+ Raises:
+ KeyError: if the file can not be found in the pool.
+ """
+
+ try:
+ return self._file_descriptors[file_name]
+ except KeyError:
+ pass
+
+ try:
+ file_proto = self._internal_db.FindFileByName(file_name)
+ except KeyError as error:
+ if self._descriptor_db:
+ file_proto = self._descriptor_db.FindFileByName(file_name)
+ else:
+ raise error
+ if not file_proto:
+ raise KeyError('Cannot find a file named %s' % file_name)
+ return self._ConvertFileProtoToFileDescriptor(file_proto)
+
+ def FindFileContainingSymbol(self, symbol):
+ """Gets the FileDescriptor for the file containing the specified symbol.
+
+ Args:
+ symbol: The name of the symbol to search for.
+
+ Returns:
+ A FileDescriptor that contains the specified symbol.
+
+ Raises:
+ KeyError: if the file can not be found in the pool.
+ """
+
+ symbol = _NormalizeFullyQualifiedName(symbol)
+ try:
+ return self._descriptors[symbol].file
+ except KeyError:
+ pass
+
+ try:
+ return self._enum_descriptors[symbol].file
+ except KeyError:
+ pass
+
+ try:
+ file_proto = self._internal_db.FindFileContainingSymbol(symbol)
+ except KeyError as error:
+ if self._descriptor_db:
+ file_proto = self._descriptor_db.FindFileContainingSymbol(symbol)
+ else:
+ raise error
+ if not file_proto:
+ raise KeyError('Cannot find a file containing %s' % symbol)
+ return self._ConvertFileProtoToFileDescriptor(file_proto)
+
+ def FindMessageTypeByName(self, full_name):
+ """Loads the named descriptor from the pool.
+
+ Args:
+ full_name: The full name of the descriptor to load.
+
+ Returns:
+ The descriptor for the named type.
+ """
+
+ full_name = _NormalizeFullyQualifiedName(full_name)
+ if full_name not in self._descriptors:
+ self.FindFileContainingSymbol(full_name)
+ return self._descriptors[full_name]
+
+ def FindEnumTypeByName(self, full_name):
+ """Loads the named enum descriptor from the pool.
+
+ Args:
+ full_name: The full name of the enum descriptor to load.
+
+ Returns:
+ The enum descriptor for the named type.
+ """
+
+ full_name = _NormalizeFullyQualifiedName(full_name)
+ if full_name not in self._enum_descriptors:
+ self.FindFileContainingSymbol(full_name)
+ return self._enum_descriptors[full_name]
+
+ def FindFieldByName(self, full_name):
+ """Loads the named field descriptor from the pool.
+
+ Args:
+ full_name: The full name of the field descriptor to load.
+
+ Returns:
+ The field descriptor for the named field.
+ """
+ full_name = _NormalizeFullyQualifiedName(full_name)
+ message_name, _, field_name = full_name.rpartition('.')
+ message_descriptor = self.FindMessageTypeByName(message_name)
+ return message_descriptor.fields_by_name[field_name]
+
+ def FindExtensionByName(self, full_name):
+ """Loads the named extension descriptor from the pool.
+
+ Args:
+ full_name: The full name of the extension descriptor to load.
+
+ Returns:
+ A FieldDescriptor, describing the named extension.
+ """
+ full_name = _NormalizeFullyQualifiedName(full_name)
+ message_name, _, extension_name = full_name.rpartition('.')
+ try:
+ # Most extensions are nested inside a message.
+ scope = self.FindMessageTypeByName(message_name)
+ except KeyError:
+ # Some extensions are defined at file scope.
+ scope = self.FindFileContainingSymbol(full_name)
+ return scope.extensions_by_name[extension_name]
+
+ def _ConvertFileProtoToFileDescriptor(self, file_proto):
+ """Creates a FileDescriptor from a proto or returns a cached copy.
+
+ This method also has the side effect of loading all the symbols found in
+ the file into the appropriate dictionaries in the pool.
+
+ Args:
+ file_proto: The proto to convert.
+
+ Returns:
+ A FileDescriptor matching the passed in proto.
+ """
+
+ if file_proto.name not in self._file_descriptors:
+ built_deps = list(self._GetDeps(file_proto.dependency))
+ direct_deps = [self.FindFileByName(n) for n in file_proto.dependency]
+ public_deps = [direct_deps[i] for i in file_proto.public_dependency]
+
+ file_descriptor = descriptor.FileDescriptor(
+ pool=self,
+ name=file_proto.name,
+ package=file_proto.package,
+ syntax=file_proto.syntax,
+ options=file_proto.options,
+ serialized_pb=file_proto.SerializeToString(),
+ dependencies=direct_deps,
+ public_dependencies=public_deps)
+ if _USE_C_DESCRIPTORS:
+ # When using C++ descriptors, all objects defined in the file were added
+ # to the C++ database when the FileDescriptor was built above.
+ # Just add them to this descriptor pool.
+ def _AddMessageDescriptor(message_desc):
+ self._descriptors[message_desc.full_name] = message_desc
+ for nested in message_desc.nested_types:
+ _AddMessageDescriptor(nested)
+ for enum_type in message_desc.enum_types:
+ _AddEnumDescriptor(enum_type)
+ def _AddEnumDescriptor(enum_desc):
+ self._enum_descriptors[enum_desc.full_name] = enum_desc
+ for message_type in file_descriptor.message_types_by_name.values():
+ _AddMessageDescriptor(message_type)
+ for enum_type in file_descriptor.enum_types_by_name.values():
+ _AddEnumDescriptor(enum_type)
+ else:
+ scope = {}
+
+ # This loop extracts all the message and enum types from all the
+ # dependencies of the file_proto. This is necessary to create the
+ # scope of available message types when defining the passed in
+ # file proto.
+ for dependency in built_deps:
+ scope.update(self._ExtractSymbols(
+ dependency.message_types_by_name.values()))
+ scope.update((_PrefixWithDot(enum.full_name), enum)
+ for enum in dependency.enum_types_by_name.values())
+
+ for message_type in file_proto.message_type:
+ message_desc = self._ConvertMessageDescriptor(
+ message_type, file_proto.package, file_descriptor, scope,
+ file_proto.syntax)
+ file_descriptor.message_types_by_name[message_desc.name] = (
+ message_desc)
+
+ for enum_type in file_proto.enum_type:
+ file_descriptor.enum_types_by_name[enum_type.name] = (
+ self._ConvertEnumDescriptor(enum_type, file_proto.package,
+ file_descriptor, None, scope))
+
+ for index, extension_proto in enumerate(file_proto.extension):
+ extension_desc = self._MakeFieldDescriptor(
+ extension_proto, file_proto.package, index, is_extension=True)
+ extension_desc.containing_type = self._GetTypeFromScope(
+ file_descriptor.package, extension_proto.extendee, scope)
+ self._SetFieldType(extension_proto, extension_desc,
+ file_descriptor.package, scope)
+ file_descriptor.extensions_by_name[extension_desc.name] = (
+ extension_desc)
+
+ for desc_proto in file_proto.message_type:
+ self._SetAllFieldTypes(file_proto.package, desc_proto, scope)
+
+ if file_proto.package:
+ desc_proto_prefix = _PrefixWithDot(file_proto.package)
+ else:
+ desc_proto_prefix = ''
+
+ for desc_proto in file_proto.message_type:
+ desc = self._GetTypeFromScope(
+ desc_proto_prefix, desc_proto.name, scope)
+ file_descriptor.message_types_by_name[desc_proto.name] = desc
+
+ for index, service_proto in enumerate(file_proto.service):
+ file_descriptor.services_by_name[service_proto.name] = (
+ self._MakeServiceDescriptor(service_proto, index, scope,
+ file_proto.package, file_descriptor))
+
+ self.Add(file_proto)
+ self._file_descriptors[file_proto.name] = file_descriptor
+
+ return self._file_descriptors[file_proto.name]
+
+ def _ConvertMessageDescriptor(self, desc_proto, package=None, file_desc=None,
+ scope=None, syntax=None):
+ """Adds the proto to the pool in the specified package.
+
+ Args:
+ desc_proto: The descriptor_pb2.DescriptorProto protobuf message.
+ package: The package the proto should be located in.
+ file_desc: The file containing this message.
+ scope: Dict mapping short and full symbols to message and enum types.
+
+ Returns:
+ The added descriptor.
+ """
+
+ if package:
+ desc_name = '.'.join((package, desc_proto.name))
+ else:
+ desc_name = desc_proto.name
+
+ if file_desc is None:
+ file_name = None
+ else:
+ file_name = file_desc.name
+
+ if scope is None:
+ scope = {}
+
+ nested = [
+ self._ConvertMessageDescriptor(
+ nested, desc_name, file_desc, scope, syntax)
+ for nested in desc_proto.nested_type]
+ enums = [
+ self._ConvertEnumDescriptor(enum, desc_name, file_desc, None, scope)
+ for enum in desc_proto.enum_type]
+ fields = [self._MakeFieldDescriptor(field, desc_name, index)
+ for index, field in enumerate(desc_proto.field)]
+ extensions = [
+ self._MakeFieldDescriptor(extension, desc_name, index,
+ is_extension=True)
+ for index, extension in enumerate(desc_proto.extension)]
+ oneofs = [
+ descriptor.OneofDescriptor(desc.name, '.'.join((desc_name, desc.name)),
+ index, None, [], desc.options)
+ for index, desc in enumerate(desc_proto.oneof_decl)]
+ extension_ranges = [(r.start, r.end) for r in desc_proto.extension_range]
+ if extension_ranges:
+ is_extendable = True
+ else:
+ is_extendable = False
+ desc = descriptor.Descriptor(
+ name=desc_proto.name,
+ full_name=desc_name,
+ filename=file_name,
+ containing_type=None,
+ fields=fields,
+ oneofs=oneofs,
+ nested_types=nested,
+ enum_types=enums,
+ extensions=extensions,
+ options=desc_proto.options,
+ is_extendable=is_extendable,
+ extension_ranges=extension_ranges,
+ file=file_desc,
+ serialized_start=None,
+ serialized_end=None,
+ syntax=syntax)
+ for nested in desc.nested_types:
+ nested.containing_type = desc
+ for enum in desc.enum_types:
+ enum.containing_type = desc
+ for field_index, field_desc in enumerate(desc_proto.field):
+ if field_desc.HasField('oneof_index'):
+ oneof_index = field_desc.oneof_index
+ oneofs[oneof_index].fields.append(fields[field_index])
+ fields[field_index].containing_oneof = oneofs[oneof_index]
+
+ scope[_PrefixWithDot(desc_name)] = desc
+ self._descriptors[desc_name] = desc
+ return desc
+
+ def _ConvertEnumDescriptor(self, enum_proto, package=None, file_desc=None,
+ containing_type=None, scope=None):
+ """Make a protobuf EnumDescriptor given an EnumDescriptorProto protobuf.
+
+ Args:
+ enum_proto: The descriptor_pb2.EnumDescriptorProto protobuf message.
+ package: Optional package name for the new message EnumDescriptor.
+ file_desc: The file containing the enum descriptor.
+ containing_type: The type containing this enum.
+ scope: Scope containing available types.
+
+ Returns:
+ The added descriptor
+ """
+
+ if package:
+ enum_name = '.'.join((package, enum_proto.name))
+ else:
+ enum_name = enum_proto.name
+
+ if file_desc is None:
+ file_name = None
+ else:
+ file_name = file_desc.name
+
+ values = [self._MakeEnumValueDescriptor(value, index)
+ for index, value in enumerate(enum_proto.value)]
+ desc = descriptor.EnumDescriptor(name=enum_proto.name,
+ full_name=enum_name,
+ filename=file_name,
+ file=file_desc,
+ values=values,
+ containing_type=containing_type,
+ options=enum_proto.options)
+ scope['.%s' % enum_name] = desc
+ self._enum_descriptors[enum_name] = desc
+ return desc
+
+ def _MakeFieldDescriptor(self, field_proto, message_name, index,
+ is_extension=False):
+ """Creates a field descriptor from a FieldDescriptorProto.
+
+ For message and enum type fields, this method will do a look up
+ in the pool for the appropriate descriptor for that type. If it
+ is unavailable, it will fall back to the _source function to
+ create it. If this type is still unavailable, construction will
+ fail.
+
+ Args:
+ field_proto: The proto describing the field.
+ message_name: The name of the containing message.
+ index: Index of the field
+ is_extension: Indication that this field is for an extension.
+
+ Returns:
+ An initialized FieldDescriptor object
+ """
+
+ if message_name:
+ full_name = '.'.join((message_name, field_proto.name))
+ else:
+ full_name = field_proto.name
+
+ return descriptor.FieldDescriptor(
+ name=field_proto.name,
+ full_name=full_name,
+ index=index,
+ number=field_proto.number,
+ type=field_proto.type,
+ cpp_type=None,
+ message_type=None,
+ enum_type=None,
+ containing_type=None,
+ label=field_proto.label,
+ has_default_value=False,
+ default_value=None,
+ is_extension=is_extension,
+ extension_scope=None,
+ options=field_proto.options)
+
+ def _SetAllFieldTypes(self, package, desc_proto, scope):
+ """Sets all the descriptor's fields's types.
+
+ This method also sets the containing types on any extensions.
+
+ Args:
+ package: The current package of desc_proto.
+ desc_proto: The message descriptor to update.
+ scope: Enclosing scope of available types.
+ """
+
+ package = _PrefixWithDot(package)
+
+ main_desc = self._GetTypeFromScope(package, desc_proto.name, scope)
+
+ if package == '.':
+ nested_package = _PrefixWithDot(desc_proto.name)
+ else:
+ nested_package = '.'.join([package, desc_proto.name])
+
+ for field_proto, field_desc in zip(desc_proto.field, main_desc.fields):
+ self._SetFieldType(field_proto, field_desc, nested_package, scope)
+
+ for extension_proto, extension_desc in (
+ zip(desc_proto.extension, main_desc.extensions)):
+ extension_desc.containing_type = self._GetTypeFromScope(
+ nested_package, extension_proto.extendee, scope)
+ self._SetFieldType(extension_proto, extension_desc, nested_package, scope)
+
+ for nested_type in desc_proto.nested_type:
+ self._SetAllFieldTypes(nested_package, nested_type, scope)
+
+ def _SetFieldType(self, field_proto, field_desc, package, scope):
+ """Sets the field's type, cpp_type, message_type and enum_type.
+
+ Args:
+ field_proto: Data about the field in proto format.
+ field_desc: The descriptor to modiy.
+ package: The package the field's container is in.
+ scope: Enclosing scope of available types.
+ """
+ if field_proto.type_name:
+ desc = self._GetTypeFromScope(package, field_proto.type_name, scope)
+ else:
+ desc = None
+
+ if not field_proto.HasField('type'):
+ if isinstance(desc, descriptor.Descriptor):
+ field_proto.type = descriptor.FieldDescriptor.TYPE_MESSAGE
+ else:
+ field_proto.type = descriptor.FieldDescriptor.TYPE_ENUM
+
+ field_desc.cpp_type = descriptor.FieldDescriptor.ProtoTypeToCppProtoType(
+ field_proto.type)
+
+ if (field_proto.type == descriptor.FieldDescriptor.TYPE_MESSAGE
+ or field_proto.type == descriptor.FieldDescriptor.TYPE_GROUP):
+ field_desc.message_type = desc
+
+ if field_proto.type == descriptor.FieldDescriptor.TYPE_ENUM:
+ field_desc.enum_type = desc
+
+ if field_proto.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ field_desc.has_default_value = False
+ field_desc.default_value = []
+ elif field_proto.HasField('default_value'):
+ field_desc.has_default_value = True
+ if (field_proto.type == descriptor.FieldDescriptor.TYPE_DOUBLE or
+ field_proto.type == descriptor.FieldDescriptor.TYPE_FLOAT):
+ field_desc.default_value = float(field_proto.default_value)
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_STRING:
+ field_desc.default_value = field_proto.default_value
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_BOOL:
+ field_desc.default_value = field_proto.default_value.lower() == 'true'
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_ENUM:
+ field_desc.default_value = field_desc.enum_type.values_by_name[
+ field_proto.default_value].number
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_BYTES:
+ field_desc.default_value = text_encoding.CUnescape(
+ field_proto.default_value)
+ else:
+ # All other types are of the "int" type.
+ field_desc.default_value = int(field_proto.default_value)
+ else:
+ field_desc.has_default_value = False
+ if (field_proto.type == descriptor.FieldDescriptor.TYPE_DOUBLE or
+ field_proto.type == descriptor.FieldDescriptor.TYPE_FLOAT):
+ field_desc.default_value = 0.0
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_STRING:
+ field_desc.default_value = u''
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_BOOL:
+ field_desc.default_value = False
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_ENUM:
+ field_desc.default_value = field_desc.enum_type.values[0].number
+ elif field_proto.type == descriptor.FieldDescriptor.TYPE_BYTES:
+ field_desc.default_value = b''
+ else:
+ # All other types are of the "int" type.
+ field_desc.default_value = 0
+
+ field_desc.type = field_proto.type
+
+ def _MakeEnumValueDescriptor(self, value_proto, index):
+ """Creates a enum value descriptor object from a enum value proto.
+
+ Args:
+ value_proto: The proto describing the enum value.
+ index: The index of the enum value.
+
+ Returns:
+ An initialized EnumValueDescriptor object.
+ """
+
+ return descriptor.EnumValueDescriptor(
+ name=value_proto.name,
+ index=index,
+ number=value_proto.number,
+ options=value_proto.options,
+ type=None)
+
+ def _MakeServiceDescriptor(self, service_proto, service_index, scope,
+ package, file_desc):
+ """Make a protobuf ServiceDescriptor given a ServiceDescriptorProto.
+
+ Args:
+ service_proto: The descriptor_pb2.ServiceDescriptorProto protobuf message.
+ service_index: The index of the service in the File.
+ scope: Dict mapping short and full symbols to message and enum types.
+ package: Optional package name for the new message EnumDescriptor.
+ file_desc: The file containing the service descriptor.
+
+ Returns:
+ The added descriptor.
+ """
+
+ if package:
+ service_name = '.'.join((package, service_proto.name))
+ else:
+ service_name = service_proto.name
+
+ methods = [self._MakeMethodDescriptor(method_proto, service_name, package,
+ scope, index)
+ for index, method_proto in enumerate(service_proto.method)]
+ desc = descriptor.ServiceDescriptor(name=service_proto.name,
+ full_name=service_name,
+ index=service_index,
+ methods=methods,
+ options=service_proto.options,
+ file=file_desc)
+ return desc
+
+ def _MakeMethodDescriptor(self, method_proto, service_name, package, scope,
+ index):
+ """Creates a method descriptor from a MethodDescriptorProto.
+
+ Args:
+ method_proto: The proto describing the method.
+ service_name: The name of the containing service.
+ package: Optional package name to look up for types.
+ scope: Scope containing available types.
+ index: Index of the method in the service.
+
+ Returns:
+ An initialized MethodDescriptor object.
+ """
+ full_name = '.'.join((service_name, method_proto.name))
+ input_type = self._GetTypeFromScope(
+ package, method_proto.input_type, scope)
+ output_type = self._GetTypeFromScope(
+ package, method_proto.output_type, scope)
+ return descriptor.MethodDescriptor(name=method_proto.name,
+ full_name=full_name,
+ index=index,
+ containing_service=None,
+ input_type=input_type,
+ output_type=output_type,
+ options=method_proto.options)
+
+ def _ExtractSymbols(self, descriptors):
+ """Pulls out all the symbols from descriptor protos.
+
+ Args:
+ descriptors: The messages to extract descriptors from.
+ Yields:
+ A two element tuple of the type name and descriptor object.
+ """
+
+ for desc in descriptors:
+ yield (_PrefixWithDot(desc.full_name), desc)
+ for symbol in self._ExtractSymbols(desc.nested_types):
+ yield symbol
+ for enum in desc.enum_types:
+ yield (_PrefixWithDot(enum.full_name), enum)
+
+ def _GetDeps(self, dependencies):
+ """Recursively finds dependencies for file protos.
+
+ Args:
+ dependencies: The names of the files being depended on.
+
+ Yields:
+ Each direct and indirect dependency.
+ """
+
+ for dependency in dependencies:
+ dep_desc = self.FindFileByName(dependency)
+ yield dep_desc
+ for parent_dep in dep_desc.dependencies:
+ yield parent_dep
+
+ def _GetTypeFromScope(self, package, type_name, scope):
+ """Finds a given type name in the current scope.
+
+ Args:
+ package: The package the proto should be located in.
+ type_name: The name of the type to be found in the scope.
+ scope: Dict mapping short and full symbols to message and enum types.
+
+ Returns:
+ The descriptor for the requested type.
+ """
+ if type_name not in scope:
+ components = _PrefixWithDot(package).split('.')
+ while components:
+ possible_match = '.'.join(components + [type_name])
+ if possible_match in scope:
+ type_name = possible_match
+ break
+ else:
+ components.pop(-1)
+ return scope[type_name]
+
+
+def _PrefixWithDot(name):
+ return name if name.startswith('.') else '.%s' % name
+
+
+if _USE_C_DESCRIPTORS:
+ # TODO(amauryfa): This pool could be constructed from Python code, when we
+ # support a flag like 'use_cpp_generated_pool=True'.
+ # pylint: disable=protected-access
+ _DEFAULT = descriptor._message.default_pool
+else:
+ _DEFAULT = DescriptorPool()
+
+
+def Default():
+ return _DEFAULT
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/__init__.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/__init__.py
new file mode 100755
index 0000000000..e69de29bb2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/__init__.py
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/_parameterized.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/_parameterized.py
new file mode 100755
index 0000000000..23a78f037e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/_parameterized.py
@@ -0,0 +1,443 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Adds support for parameterized tests to Python's unittest TestCase class.
+
+A parameterized test is a method in a test case that is invoked with different
+argument tuples.
+
+A simple example:
+
+ class AdditionExample(parameterized.ParameterizedTestCase):
+ @parameterized.Parameters(
+ (1, 2, 3),
+ (4, 5, 9),
+ (1, 1, 3))
+ def testAddition(self, op1, op2, result):
+ self.assertEqual(result, op1 + op2)
+
+
+Each invocation is a separate test case and properly isolated just
+like a normal test method, with its own setUp/tearDown cycle. In the
+example above, there are three separate testcases, one of which will
+fail due to an assertion error (1 + 1 != 3).
+
+Parameters for invididual test cases can be tuples (with positional parameters)
+or dictionaries (with named parameters):
+
+ class AdditionExample(parameterized.ParameterizedTestCase):
+ @parameterized.Parameters(
+ {'op1': 1, 'op2': 2, 'result': 3},
+ {'op1': 4, 'op2': 5, 'result': 9},
+ )
+ def testAddition(self, op1, op2, result):
+ self.assertEqual(result, op1 + op2)
+
+If a parameterized test fails, the error message will show the
+original test name (which is modified internally) and the arguments
+for the specific invocation, which are part of the string returned by
+the shortDescription() method on test cases.
+
+The id method of the test, used internally by the unittest framework,
+is also modified to show the arguments. To make sure that test names
+stay the same across several invocations, object representations like
+
+ >>> class Foo(object):
+ ... pass
+ >>> repr(Foo())
+ '<__main__.Foo object at 0x23d8610>'
+
+are turned into '<__main__.Foo>'. For even more descriptive names,
+especially in test logs, you can use the NamedParameters decorator. In
+this case, only tuples are supported, and the first parameters has to
+be a string (or an object that returns an apt name when converted via
+str()):
+
+ class NamedExample(parameterized.ParameterizedTestCase):
+ @parameterized.NamedParameters(
+ ('Normal', 'aa', 'aaa', True),
+ ('EmptyPrefix', '', 'abc', True),
+ ('BothEmpty', '', '', True))
+ def testStartsWith(self, prefix, string, result):
+ self.assertEqual(result, strings.startswith(prefix))
+
+Named tests also have the benefit that they can be run individually
+from the command line:
+
+ $ testmodule.py NamedExample.testStartsWithNormal
+ .
+ --------------------------------------------------------------------
+ Ran 1 test in 0.000s
+
+ OK
+
+Parameterized Classes
+=====================
+If invocation arguments are shared across test methods in a single
+ParameterizedTestCase class, instead of decorating all test methods
+individually, the class itself can be decorated:
+
+ @parameterized.Parameters(
+ (1, 2, 3)
+ (4, 5, 9))
+ class ArithmeticTest(parameterized.ParameterizedTestCase):
+ def testAdd(self, arg1, arg2, result):
+ self.assertEqual(arg1 + arg2, result)
+
+ def testSubtract(self, arg2, arg2, result):
+ self.assertEqual(result - arg1, arg2)
+
+Inputs from Iterables
+=====================
+If parameters should be shared across several test cases, or are dynamically
+created from other sources, a single non-tuple iterable can be passed into
+the decorator. This iterable will be used to obtain the test cases:
+
+ class AdditionExample(parameterized.ParameterizedTestCase):
+ @parameterized.Parameters(
+ c.op1, c.op2, c.result for c in testcases
+ )
+ def testAddition(self, op1, op2, result):
+ self.assertEqual(result, op1 + op2)
+
+
+Single-Argument Test Methods
+============================
+If a test method takes only one argument, the single argument does not need to
+be wrapped into a tuple:
+
+ class NegativeNumberExample(parameterized.ParameterizedTestCase):
+ @parameterized.Parameters(
+ -1, -3, -4, -5
+ )
+ def testIsNegative(self, arg):
+ self.assertTrue(IsNegative(arg))
+"""
+
+__author__ = 'tmarek@google.com (Torsten Marek)'
+
+import collections
+import functools
+import re
+import types
+try:
+ import unittest2 as unittest
+except ImportError:
+ import unittest
+import uuid
+
+import six
+
+ADDR_RE = re.compile(r'\<([a-zA-Z0-9_\-\.]+) object at 0x[a-fA-F0-9]+\>')
+_SEPARATOR = uuid.uuid1().hex
+_FIRST_ARG = object()
+_ARGUMENT_REPR = object()
+
+
+def _CleanRepr(obj):
+ return ADDR_RE.sub(r'<\1>', repr(obj))
+
+
+# Helper function formerly from the unittest module, removed from it in
+# Python 2.7.
+def _StrClass(cls):
+ return '%s.%s' % (cls.__module__, cls.__name__)
+
+
+def _NonStringIterable(obj):
+ return (isinstance(obj, collections.Iterable) and not
+ isinstance(obj, six.string_types))
+
+
+def _FormatParameterList(testcase_params):
+ if isinstance(testcase_params, collections.Mapping):
+ return ', '.join('%s=%s' % (argname, _CleanRepr(value))
+ for argname, value in testcase_params.items())
+ elif _NonStringIterable(testcase_params):
+ return ', '.join(map(_CleanRepr, testcase_params))
+ else:
+ return _FormatParameterList((testcase_params,))
+
+
+class _ParameterizedTestIter(object):
+ """Callable and iterable class for producing new test cases."""
+
+ def __init__(self, test_method, testcases, naming_type):
+ """Returns concrete test functions for a test and a list of parameters.
+
+ The naming_type is used to determine the name of the concrete
+ functions as reported by the unittest framework. If naming_type is
+ _FIRST_ARG, the testcases must be tuples, and the first element must
+ have a string representation that is a valid Python identifier.
+
+ Args:
+ test_method: The decorated test method.
+ testcases: (list of tuple/dict) A list of parameter
+ tuples/dicts for individual test invocations.
+ naming_type: The test naming type, either _NAMED or _ARGUMENT_REPR.
+ """
+ self._test_method = test_method
+ self.testcases = testcases
+ self._naming_type = naming_type
+
+ def __call__(self, *args, **kwargs):
+ raise RuntimeError('You appear to be running a parameterized test case '
+ 'without having inherited from parameterized.'
+ 'ParameterizedTestCase. This is bad because none of '
+ 'your test cases are actually being run.')
+
+ def __iter__(self):
+ test_method = self._test_method
+ naming_type = self._naming_type
+
+ def MakeBoundParamTest(testcase_params):
+ @functools.wraps(test_method)
+ def BoundParamTest(self):
+ if isinstance(testcase_params, collections.Mapping):
+ test_method(self, **testcase_params)
+ elif _NonStringIterable(testcase_params):
+ test_method(self, *testcase_params)
+ else:
+ test_method(self, testcase_params)
+
+ if naming_type is _FIRST_ARG:
+ # Signal the metaclass that the name of the test function is unique
+ # and descriptive.
+ BoundParamTest.__x_use_name__ = True
+ BoundParamTest.__name__ += str(testcase_params[0])
+ testcase_params = testcase_params[1:]
+ elif naming_type is _ARGUMENT_REPR:
+ # __x_extra_id__ is used to pass naming information to the __new__
+ # method of TestGeneratorMetaclass.
+ # The metaclass will make sure to create a unique, but nondescriptive
+ # name for this test.
+ BoundParamTest.__x_extra_id__ = '(%s)' % (
+ _FormatParameterList(testcase_params),)
+ else:
+ raise RuntimeError('%s is not a valid naming type.' % (naming_type,))
+
+ BoundParamTest.__doc__ = '%s(%s)' % (
+ BoundParamTest.__name__, _FormatParameterList(testcase_params))
+ if test_method.__doc__:
+ BoundParamTest.__doc__ += '\n%s' % (test_method.__doc__,)
+ return BoundParamTest
+ return (MakeBoundParamTest(c) for c in self.testcases)
+
+
+def _IsSingletonList(testcases):
+ """True iff testcases contains only a single non-tuple element."""
+ return len(testcases) == 1 and not isinstance(testcases[0], tuple)
+
+
+def _ModifyClass(class_object, testcases, naming_type):
+ assert not getattr(class_object, '_id_suffix', None), (
+ 'Cannot add parameters to %s,'
+ ' which already has parameterized methods.' % (class_object,))
+ class_object._id_suffix = id_suffix = {}
+ # We change the size of __dict__ while we iterate over it,
+ # which Python 3.x will complain about, so use copy().
+ for name, obj in class_object.__dict__.copy().items():
+ if (name.startswith(unittest.TestLoader.testMethodPrefix)
+ and isinstance(obj, types.FunctionType)):
+ delattr(class_object, name)
+ methods = {}
+ _UpdateClassDictForParamTestCase(
+ methods, id_suffix, name,
+ _ParameterizedTestIter(obj, testcases, naming_type))
+ for name, meth in methods.items():
+ setattr(class_object, name, meth)
+
+
+def _ParameterDecorator(naming_type, testcases):
+ """Implementation of the parameterization decorators.
+
+ Args:
+ naming_type: The naming type.
+ testcases: Testcase parameters.
+
+ Returns:
+ A function for modifying the decorated object.
+ """
+ def _Apply(obj):
+ if isinstance(obj, type):
+ _ModifyClass(
+ obj,
+ list(testcases) if not isinstance(testcases, collections.Sequence)
+ else testcases,
+ naming_type)
+ return obj
+ else:
+ return _ParameterizedTestIter(obj, testcases, naming_type)
+
+ if _IsSingletonList(testcases):
+ assert _NonStringIterable(testcases[0]), (
+ 'Single parameter argument must be a non-string iterable')
+ testcases = testcases[0]
+
+ return _Apply
+
+
+def Parameters(*testcases):
+ """A decorator for creating parameterized tests.
+
+ See the module docstring for a usage example.
+ Args:
+ *testcases: Parameters for the decorated method, either a single
+ iterable, or a list of tuples/dicts/objects (for tests
+ with only one argument).
+
+ Returns:
+ A test generator to be handled by TestGeneratorMetaclass.
+ """
+ return _ParameterDecorator(_ARGUMENT_REPR, testcases)
+
+
+def NamedParameters(*testcases):
+ """A decorator for creating parameterized tests.
+
+ See the module docstring for a usage example. The first element of
+ each parameter tuple should be a string and will be appended to the
+ name of the test method.
+
+ Args:
+ *testcases: Parameters for the decorated method, either a single
+ iterable, or a list of tuples.
+
+ Returns:
+ A test generator to be handled by TestGeneratorMetaclass.
+ """
+ return _ParameterDecorator(_FIRST_ARG, testcases)
+
+
+class TestGeneratorMetaclass(type):
+ """Metaclass for test cases with test generators.
+
+ A test generator is an iterable in a testcase that produces callables. These
+ callables must be single-argument methods. These methods are injected into
+ the class namespace and the original iterable is removed. If the name of the
+ iterable conforms to the test pattern, the injected methods will be picked
+ up as tests by the unittest framework.
+
+ In general, it is supposed to be used in conjunction with the
+ Parameters decorator.
+ """
+
+ def __new__(mcs, class_name, bases, dct):
+ dct['_id_suffix'] = id_suffix = {}
+ for name, obj in dct.items():
+ if (name.startswith(unittest.TestLoader.testMethodPrefix) and
+ _NonStringIterable(obj)):
+ iterator = iter(obj)
+ dct.pop(name)
+ _UpdateClassDictForParamTestCase(dct, id_suffix, name, iterator)
+
+ return type.__new__(mcs, class_name, bases, dct)
+
+
+def _UpdateClassDictForParamTestCase(dct, id_suffix, name, iterator):
+ """Adds individual test cases to a dictionary.
+
+ Args:
+ dct: The target dictionary.
+ id_suffix: The dictionary for mapping names to test IDs.
+ name: The original name of the test case.
+ iterator: The iterator generating the individual test cases.
+ """
+ for idx, func in enumerate(iterator):
+ assert callable(func), 'Test generators must yield callables, got %r' % (
+ func,)
+ if getattr(func, '__x_use_name__', False):
+ new_name = func.__name__
+ else:
+ new_name = '%s%s%d' % (name, _SEPARATOR, idx)
+ assert new_name not in dct, (
+ 'Name of parameterized test case "%s" not unique' % (new_name,))
+ dct[new_name] = func
+ id_suffix[new_name] = getattr(func, '__x_extra_id__', '')
+
+
+class ParameterizedTestCase(unittest.TestCase):
+ """Base class for test cases using the Parameters decorator."""
+ __metaclass__ = TestGeneratorMetaclass
+
+ def _OriginalName(self):
+ return self._testMethodName.split(_SEPARATOR)[0]
+
+ def __str__(self):
+ return '%s (%s)' % (self._OriginalName(), _StrClass(self.__class__))
+
+ def id(self): # pylint: disable=invalid-name
+ """Returns the descriptive ID of the test.
+
+ This is used internally by the unittesting framework to get a name
+ for the test to be used in reports.
+
+ Returns:
+ The test id.
+ """
+ return '%s.%s%s' % (_StrClass(self.__class__),
+ self._OriginalName(),
+ self._id_suffix.get(self._testMethodName, ''))
+
+
+def CoopParameterizedTestCase(other_base_class):
+ """Returns a new base class with a cooperative metaclass base.
+
+ This enables the ParameterizedTestCase to be used in combination
+ with other base classes that have custom metaclasses, such as
+ mox.MoxTestBase.
+
+ Only works with metaclasses that do not override type.__new__.
+
+ Example:
+
+ import google3
+ import mox
+
+ from google3.testing.pybase import parameterized
+
+ class ExampleTest(parameterized.CoopParameterizedTestCase(mox.MoxTestBase)):
+ ...
+
+ Args:
+ other_base_class: (class) A test case base class.
+
+ Returns:
+ A new class object.
+ """
+ metaclass = type(
+ 'CoopMetaclass',
+ (other_base_class.__metaclass__,
+ TestGeneratorMetaclass), {})
+ return metaclass(
+ 'CoopParameterizedTestCase',
+ (other_base_class, ParameterizedTestCase), {})
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/any_test.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/any_test.proto
new file mode 100644
index 0000000000..cd641ca0b8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/any_test.proto
@@ -0,0 +1,42 @@
+// 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: jieluo@google.com (Jie Luo)
+
+syntax = "proto3";
+
+package google.protobuf.internal;
+
+import "google/protobuf/any.proto";
+
+message TestAny {
+ google.protobuf.Any value = 1;
+ int32 int_value = 2;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.cc b/third_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.cc
new file mode 100644
index 0000000000..6db12e8dc6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.cc
@@ -0,0 +1,129 @@
+// 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.
+
+#include <Python.h>
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+// Version constant.
+// This is either 0 for python, 1 for CPP V1, 2 for CPP V2.
+//
+// 0 is default and is equivalent to
+// PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION=python
+//
+// 1 is set with -DPYTHON_PROTO2_CPP_IMPL_V1 and is equivalent to
+// PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION=cpp
+// and
+// PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION_VERSION=1
+//
+// 2 is set with -DPYTHON_PROTO2_CPP_IMPL_V2 and is equivalent to
+// PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION=cpp
+// and
+// PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION_VERSION=2
+#ifdef PYTHON_PROTO2_CPP_IMPL_V1
+#error "PYTHON_PROTO2_CPP_IMPL_V1 is no longer supported."
+#else
+#ifdef PYTHON_PROTO2_CPP_IMPL_V2
+static int kImplVersion = 2;
+#else
+#ifdef PYTHON_PROTO2_PYTHON_IMPL
+static int kImplVersion = 0;
+#else
+
+static int kImplVersion = -1; // -1 means "Unspecified by compiler flags".
+
+#endif // PYTHON_PROTO2_PYTHON_IMPL
+#endif // PYTHON_PROTO2_CPP_IMPL_V2
+#endif // PYTHON_PROTO2_CPP_IMPL_V1
+
+static const char* kImplVersionName = "api_version";
+
+static const char* kModuleName = "_api_implementation";
+static const char kModuleDocstring[] =
+"_api_implementation is a module that exposes compile-time constants that\n"
+"determine the default API implementation to use for Python proto2.\n"
+"\n"
+"It complements api_implementation.py by setting defaults using compile-time\n"
+"constants defined in C, such that one can set defaults at compilation\n"
+"(e.g. with blaze flag --copt=-DPYTHON_PROTO2_CPP_IMPL_V2).";
+
+#if PY_MAJOR_VERSION >= 3
+static struct PyModuleDef _module = {
+ PyModuleDef_HEAD_INIT,
+ kModuleName,
+ kModuleDocstring,
+ -1,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL
+};
+#define INITFUNC PyInit__api_implementation
+#define INITFUNC_ERRORVAL NULL
+#else
+#define INITFUNC init_api_implementation
+#define INITFUNC_ERRORVAL
+#endif
+
+extern "C" {
+ PyMODINIT_FUNC INITFUNC() {
+#if PY_MAJOR_VERSION >= 3
+ PyObject *module = PyModule_Create(&_module);
+#else
+ PyObject *module = Py_InitModule3(
+ const_cast<char*>(kModuleName),
+ NULL,
+ const_cast<char*>(kModuleDocstring));
+#endif
+ if (module == NULL) {
+ return INITFUNC_ERRORVAL;
+ }
+
+ // Adds the module variable "api_version".
+ if (PyModule_AddIntConstant(
+ module,
+ const_cast<char*>(kImplVersionName),
+ kImplVersion))
+#if PY_MAJOR_VERSION < 3
+ return;
+#else
+ { Py_DECREF(module); return NULL; }
+
+ return module;
+#endif
+ }
+}
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.py
new file mode 100755
index 0000000000..460a4a6c2c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/api_implementation.py
@@ -0,0 +1,113 @@
+# 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.
+
+"""Determine which implementation of the protobuf API is used in this process.
+"""
+
+import os
+import warnings
+import sys
+
+try:
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf.internal import _api_implementation
+ # The compile-time constants in the _api_implementation module can be used to
+ # switch to a certain implementation of the Python API at build time.
+ _api_version = _api_implementation.api_version
+ _proto_extension_modules_exist_in_build = True
+except ImportError:
+ _api_version = -1 # Unspecified by compiler flags.
+ _proto_extension_modules_exist_in_build = False
+
+if _api_version == 1:
+ raise ValueError('api_version=1 is no longer supported.')
+if _api_version < 0: # Still unspecified?
+ try:
+ # The presence of this module in a build allows the proto implementation to
+ # be upgraded merely via build deps rather than a compiler flag or the
+ # runtime environment variable.
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf import _use_fast_cpp_protos
+ # Work around a known issue in the classic bootstrap .par import hook.
+ if not _use_fast_cpp_protos:
+ raise ImportError('_use_fast_cpp_protos import succeeded but was None')
+ del _use_fast_cpp_protos
+ _api_version = 2
+ except ImportError:
+ if _proto_extension_modules_exist_in_build:
+ if sys.version_info[0] >= 3: # Python 3 defaults to C++ impl v2.
+ _api_version = 2
+ # TODO(b/17427486): Make Python 2 default to C++ impl v2.
+
+_default_implementation_type = (
+ 'python' if _api_version <= 0 else 'cpp')
+
+# This environment variable can be used to switch to a certain implementation
+# of the Python API, overriding the compile-time constants in the
+# _api_implementation module. Right now only 'python' and 'cpp' are valid
+# values. Any other value will be ignored.
+_implementation_type = os.getenv('PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION',
+ _default_implementation_type)
+
+if _implementation_type != 'python':
+ _implementation_type = 'cpp'
+
+if 'PyPy' in sys.version and _implementation_type == 'cpp':
+ warnings.warn('PyPy does not work yet with cpp protocol buffers. '
+ 'Falling back to the python implementation.')
+ _implementation_type = 'python'
+
+# This environment variable can be used to switch between the two
+# 'cpp' implementations, overriding the compile-time constants in the
+# _api_implementation module. Right now only '2' is supported. Any other
+# value will cause an error to be raised.
+_implementation_version_str = os.getenv(
+ 'PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION_VERSION', '2')
+
+if _implementation_version_str != '2':
+ raise ValueError(
+ 'unsupported PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION_VERSION: "' +
+ _implementation_version_str + '" (supported versions: 2)'
+ )
+
+_implementation_version = int(_implementation_version_str)
+
+
+# Usage of this function is discouraged. Clients shouldn't care which
+# implementation of the API is in use. Note that there is no guarantee
+# that differences between APIs will be maintained.
+# Please don't use this function if possible.
+def Type():
+ return _implementation_type
+
+
+# See comment on 'Type' above.
+def Version():
+ return _implementation_version
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/containers.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/containers.py
new file mode 100755
index 0000000000..ce46d08c9e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/containers.py
@@ -0,0 +1,615 @@
+# 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.
+
+"""Contains container classes to represent different protocol buffer types.
+
+This file defines container classes which represent categories of protocol
+buffer field types which need extra maintenance. Currently these categories
+are:
+ - Repeated scalar fields - These are all repeated fields which aren't
+ composite (e.g. they are of simple types like int32, string, etc).
+ - Repeated composite fields - Repeated fields which are composite. This
+ includes groups and nested messages.
+"""
+
+__author__ = 'petar@google.com (Petar Petrov)'
+
+import collections
+import sys
+
+if sys.version_info[0] < 3:
+ # We would use collections.MutableMapping all the time, but in Python 2 it
+ # doesn't define __slots__. This causes two significant problems:
+ #
+ # 1. we can't disallow arbitrary attribute assignment, even if our derived
+ # classes *do* define __slots__.
+ #
+ # 2. we can't safely derive a C type from it without __slots__ defined (the
+ # interpreter expects to find a dict at tp_dictoffset, which we can't
+ # robustly provide. And we don't want an instance dict anyway.
+ #
+ # So this is the Python 2.7 definition of Mapping/MutableMapping functions
+ # verbatim, except that:
+ # 1. We declare __slots__.
+ # 2. We don't declare this as a virtual base class. The classes defined
+ # in collections are the interesting base classes, not us.
+ #
+ # Note: deriving from object is critical. It is the only thing that makes
+ # this a true type, allowing us to derive from it in C++ cleanly and making
+ # __slots__ properly disallow arbitrary element assignment.
+
+ class Mapping(object):
+ __slots__ = ()
+
+ def get(self, key, default=None):
+ try:
+ return self[key]
+ except KeyError:
+ return default
+
+ def __contains__(self, key):
+ try:
+ self[key]
+ except KeyError:
+ return False
+ else:
+ return True
+
+ def iterkeys(self):
+ return iter(self)
+
+ def itervalues(self):
+ for key in self:
+ yield self[key]
+
+ def iteritems(self):
+ for key in self:
+ yield (key, self[key])
+
+ def keys(self):
+ return list(self)
+
+ def items(self):
+ return [(key, self[key]) for key in self]
+
+ def values(self):
+ return [self[key] for key in self]
+
+ # Mappings are not hashable by default, but subclasses can change this
+ __hash__ = None
+
+ def __eq__(self, other):
+ if not isinstance(other, collections.Mapping):
+ return NotImplemented
+ return dict(self.items()) == dict(other.items())
+
+ def __ne__(self, other):
+ return not (self == other)
+
+ class MutableMapping(Mapping):
+ __slots__ = ()
+
+ __marker = object()
+
+ def pop(self, key, default=__marker):
+ try:
+ value = self[key]
+ except KeyError:
+ if default is self.__marker:
+ raise
+ return default
+ else:
+ del self[key]
+ return value
+
+ def popitem(self):
+ try:
+ key = next(iter(self))
+ except StopIteration:
+ raise KeyError
+ value = self[key]
+ del self[key]
+ return key, value
+
+ def clear(self):
+ try:
+ while True:
+ self.popitem()
+ except KeyError:
+ pass
+
+ def update(*args, **kwds):
+ if len(args) > 2:
+ raise TypeError("update() takes at most 2 positional "
+ "arguments ({} given)".format(len(args)))
+ elif not args:
+ raise TypeError("update() takes at least 1 argument (0 given)")
+ self = args[0]
+ other = args[1] if len(args) >= 2 else ()
+
+ if isinstance(other, Mapping):
+ for key in other:
+ self[key] = other[key]
+ elif hasattr(other, "keys"):
+ for key in other.keys():
+ self[key] = other[key]
+ else:
+ for key, value in other:
+ self[key] = value
+ for key, value in kwds.items():
+ self[key] = value
+
+ def setdefault(self, key, default=None):
+ try:
+ return self[key]
+ except KeyError:
+ self[key] = default
+ return default
+
+ collections.Mapping.register(Mapping)
+ collections.MutableMapping.register(MutableMapping)
+
+else:
+ # In Python 3 we can just use MutableMapping directly, because it defines
+ # __slots__.
+ MutableMapping = collections.MutableMapping
+
+
+class BaseContainer(object):
+
+ """Base container class."""
+
+ # Minimizes memory usage and disallows assignment to other attributes.
+ __slots__ = ['_message_listener', '_values']
+
+ def __init__(self, message_listener):
+ """
+ Args:
+ message_listener: A MessageListener implementation.
+ The RepeatedScalarFieldContainer will call this object's
+ Modified() method when it is modified.
+ """
+ self._message_listener = message_listener
+ self._values = []
+
+ def __getitem__(self, key):
+ """Retrieves item by the specified key."""
+ return self._values[key]
+
+ def __len__(self):
+ """Returns the number of elements in the container."""
+ return len(self._values)
+
+ def __ne__(self, other):
+ """Checks if another instance isn't equal to this one."""
+ # The concrete classes should define __eq__.
+ return not self == other
+
+ def __hash__(self):
+ raise TypeError('unhashable object')
+
+ def __repr__(self):
+ return repr(self._values)
+
+ def sort(self, *args, **kwargs):
+ # Continue to support the old sort_function keyword argument.
+ # This is expected to be a rare occurrence, so use LBYL to avoid
+ # the overhead of actually catching KeyError.
+ if 'sort_function' in kwargs:
+ kwargs['cmp'] = kwargs.pop('sort_function')
+ self._values.sort(*args, **kwargs)
+
+
+class RepeatedScalarFieldContainer(BaseContainer):
+
+ """Simple, type-checked, list-like container for holding repeated scalars."""
+
+ # Disallows assignment to other attributes.
+ __slots__ = ['_type_checker']
+
+ def __init__(self, message_listener, type_checker):
+ """
+ Args:
+ message_listener: A MessageListener implementation.
+ The RepeatedScalarFieldContainer will call this object's
+ Modified() method when it is modified.
+ type_checker: A type_checkers.ValueChecker instance to run on elements
+ inserted into this container.
+ """
+ super(RepeatedScalarFieldContainer, self).__init__(message_listener)
+ self._type_checker = type_checker
+
+ def append(self, value):
+ """Appends an item to the list. Similar to list.append()."""
+ self._values.append(self._type_checker.CheckValue(value))
+ if not self._message_listener.dirty:
+ self._message_listener.Modified()
+
+ def insert(self, key, value):
+ """Inserts the item at the specified position. Similar to list.insert()."""
+ self._values.insert(key, self._type_checker.CheckValue(value))
+ if not self._message_listener.dirty:
+ self._message_listener.Modified()
+
+ def extend(self, elem_seq):
+ """Extends by appending the given iterable. Similar to list.extend()."""
+
+ if elem_seq is None:
+ return
+ try:
+ elem_seq_iter = iter(elem_seq)
+ except TypeError:
+ if not elem_seq:
+ # silently ignore falsy inputs :-/.
+ # TODO(ptucker): Deprecate this behavior. b/18413862
+ return
+ raise
+
+ new_values = [self._type_checker.CheckValue(elem) for elem in elem_seq_iter]
+ if new_values:
+ self._values.extend(new_values)
+ self._message_listener.Modified()
+
+ def MergeFrom(self, other):
+ """Appends the contents of another repeated field of the same type to this
+ one. We do not check the types of the individual fields.
+ """
+ self._values.extend(other._values)
+ self._message_listener.Modified()
+
+ def remove(self, elem):
+ """Removes an item from the list. Similar to list.remove()."""
+ self._values.remove(elem)
+ self._message_listener.Modified()
+
+ def pop(self, key=-1):
+ """Removes and returns an item at a given index. Similar to list.pop()."""
+ value = self._values[key]
+ self.__delitem__(key)
+ return value
+
+ def __setitem__(self, key, value):
+ """Sets the item on the specified position."""
+ if isinstance(key, slice): # PY3
+ if key.step is not None:
+ raise ValueError('Extended slices not supported')
+ self.__setslice__(key.start, key.stop, value)
+ else:
+ self._values[key] = self._type_checker.CheckValue(value)
+ self._message_listener.Modified()
+
+ def __getslice__(self, start, stop):
+ """Retrieves the subset of items from between the specified indices."""
+ return self._values[start:stop]
+
+ def __setslice__(self, start, stop, values):
+ """Sets the subset of items from between the specified indices."""
+ new_values = []
+ for value in values:
+ new_values.append(self._type_checker.CheckValue(value))
+ self._values[start:stop] = new_values
+ self._message_listener.Modified()
+
+ def __delitem__(self, key):
+ """Deletes the item at the specified position."""
+ del self._values[key]
+ self._message_listener.Modified()
+
+ def __delslice__(self, start, stop):
+ """Deletes the subset of items from between the specified indices."""
+ del self._values[start:stop]
+ self._message_listener.Modified()
+
+ def __eq__(self, other):
+ """Compares the current instance with another one."""
+ if self is other:
+ return True
+ # Special case for the same type which should be common and fast.
+ if isinstance(other, self.__class__):
+ return other._values == self._values
+ # We are presumably comparing against some other sequence type.
+ return other == self._values
+
+collections.MutableSequence.register(BaseContainer)
+
+
+class RepeatedCompositeFieldContainer(BaseContainer):
+
+ """Simple, list-like container for holding repeated composite fields."""
+
+ # Disallows assignment to other attributes.
+ __slots__ = ['_message_descriptor']
+
+ def __init__(self, message_listener, message_descriptor):
+ """
+ Note that we pass in a descriptor instead of the generated directly,
+ since at the time we construct a _RepeatedCompositeFieldContainer we
+ haven't yet necessarily initialized the type that will be contained in the
+ container.
+
+ Args:
+ message_listener: A MessageListener implementation.
+ The RepeatedCompositeFieldContainer will call this object's
+ Modified() method when it is modified.
+ message_descriptor: A Descriptor instance describing the protocol type
+ that should be present in this container. We'll use the
+ _concrete_class field of this descriptor when the client calls add().
+ """
+ super(RepeatedCompositeFieldContainer, self).__init__(message_listener)
+ self._message_descriptor = message_descriptor
+
+ def add(self, **kwargs):
+ """Adds a new element at the end of the list and returns it. Keyword
+ arguments may be used to initialize the element.
+ """
+ new_element = self._message_descriptor._concrete_class(**kwargs)
+ new_element._SetListener(self._message_listener)
+ self._values.append(new_element)
+ if not self._message_listener.dirty:
+ self._message_listener.Modified()
+ return new_element
+
+ def extend(self, elem_seq):
+ """Extends by appending the given sequence of elements of the same type
+ as this one, copying each individual message.
+ """
+ message_class = self._message_descriptor._concrete_class
+ listener = self._message_listener
+ values = self._values
+ for message in elem_seq:
+ new_element = message_class()
+ new_element._SetListener(listener)
+ new_element.MergeFrom(message)
+ values.append(new_element)
+ listener.Modified()
+
+ def MergeFrom(self, other):
+ """Appends the contents of another repeated field of the same type to this
+ one, copying each individual message.
+ """
+ self.extend(other._values)
+
+ def remove(self, elem):
+ """Removes an item from the list. Similar to list.remove()."""
+ self._values.remove(elem)
+ self._message_listener.Modified()
+
+ def pop(self, key=-1):
+ """Removes and returns an item at a given index. Similar to list.pop()."""
+ value = self._values[key]
+ self.__delitem__(key)
+ return value
+
+ def __getslice__(self, start, stop):
+ """Retrieves the subset of items from between the specified indices."""
+ return self._values[start:stop]
+
+ def __delitem__(self, key):
+ """Deletes the item at the specified position."""
+ del self._values[key]
+ self._message_listener.Modified()
+
+ def __delslice__(self, start, stop):
+ """Deletes the subset of items from between the specified indices."""
+ del self._values[start:stop]
+ self._message_listener.Modified()
+
+ def __eq__(self, other):
+ """Compares the current instance with another one."""
+ if self is other:
+ return True
+ if not isinstance(other, self.__class__):
+ raise TypeError('Can only compare repeated composite fields against '
+ 'other repeated composite fields.')
+ return self._values == other._values
+
+
+class ScalarMap(MutableMapping):
+
+ """Simple, type-checked, dict-like container for holding repeated scalars."""
+
+ # Disallows assignment to other attributes.
+ __slots__ = ['_key_checker', '_value_checker', '_values', '_message_listener']
+
+ def __init__(self, message_listener, key_checker, value_checker):
+ """
+ Args:
+ message_listener: A MessageListener implementation.
+ The ScalarMap will call this object's Modified() method when it
+ is modified.
+ key_checker: A type_checkers.ValueChecker instance to run on keys
+ inserted into this container.
+ value_checker: A type_checkers.ValueChecker instance to run on values
+ inserted into this container.
+ """
+ self._message_listener = message_listener
+ self._key_checker = key_checker
+ self._value_checker = value_checker
+ self._values = {}
+
+ def __getitem__(self, key):
+ try:
+ return self._values[key]
+ except KeyError:
+ key = self._key_checker.CheckValue(key)
+ val = self._value_checker.DefaultValue()
+ self._values[key] = val
+ return val
+
+ def __contains__(self, item):
+ # We check the key's type to match the strong-typing flavor of the API.
+ # Also this makes it easier to match the behavior of the C++ implementation.
+ self._key_checker.CheckValue(item)
+ return item in self._values
+
+ # We need to override this explicitly, because our defaultdict-like behavior
+ # will make the default implementation (from our base class) always insert
+ # the key.
+ def get(self, key, default=None):
+ if key in self:
+ return self[key]
+ else:
+ return default
+
+ def __setitem__(self, key, value):
+ checked_key = self._key_checker.CheckValue(key)
+ checked_value = self._value_checker.CheckValue(value)
+ self._values[checked_key] = checked_value
+ self._message_listener.Modified()
+
+ def __delitem__(self, key):
+ del self._values[key]
+ self._message_listener.Modified()
+
+ def __len__(self):
+ return len(self._values)
+
+ def __iter__(self):
+ return iter(self._values)
+
+ def __repr__(self):
+ return repr(self._values)
+
+ def MergeFrom(self, other):
+ self._values.update(other._values)
+ self._message_listener.Modified()
+
+ def InvalidateIterators(self):
+ # It appears that the only way to reliably invalidate iterators to
+ # self._values is to ensure that its size changes.
+ original = self._values
+ self._values = original.copy()
+ original[None] = None
+
+ # This is defined in the abstract base, but we can do it much more cheaply.
+ def clear(self):
+ self._values.clear()
+ self._message_listener.Modified()
+
+
+class MessageMap(MutableMapping):
+
+ """Simple, type-checked, dict-like container for with submessage values."""
+
+ # Disallows assignment to other attributes.
+ __slots__ = ['_key_checker', '_values', '_message_listener',
+ '_message_descriptor']
+
+ def __init__(self, message_listener, message_descriptor, key_checker):
+ """
+ Args:
+ message_listener: A MessageListener implementation.
+ The ScalarMap will call this object's Modified() method when it
+ is modified.
+ key_checker: A type_checkers.ValueChecker instance to run on keys
+ inserted into this container.
+ value_checker: A type_checkers.ValueChecker instance to run on values
+ inserted into this container.
+ """
+ self._message_listener = message_listener
+ self._message_descriptor = message_descriptor
+ self._key_checker = key_checker
+ self._values = {}
+
+ def __getitem__(self, key):
+ try:
+ return self._values[key]
+ except KeyError:
+ key = self._key_checker.CheckValue(key)
+ new_element = self._message_descriptor._concrete_class()
+ new_element._SetListener(self._message_listener)
+ self._values[key] = new_element
+ self._message_listener.Modified()
+
+ return new_element
+
+ def get_or_create(self, key):
+ """get_or_create() is an alias for getitem (ie. map[key]).
+
+ Args:
+ key: The key to get or create in the map.
+
+ This is useful in cases where you want to be explicit that the call is
+ mutating the map. This can avoid lint errors for statements like this
+ that otherwise would appear to be pointless statements:
+
+ msg.my_map[key]
+ """
+ return self[key]
+
+ # We need to override this explicitly, because our defaultdict-like behavior
+ # will make the default implementation (from our base class) always insert
+ # the key.
+ def get(self, key, default=None):
+ if key in self:
+ return self[key]
+ else:
+ return default
+
+ def __contains__(self, item):
+ return item in self._values
+
+ def __setitem__(self, key, value):
+ raise ValueError('May not set values directly, call my_map[key].foo = 5')
+
+ def __delitem__(self, key):
+ del self._values[key]
+ self._message_listener.Modified()
+
+ def __len__(self):
+ return len(self._values)
+
+ def __iter__(self):
+ return iter(self._values)
+
+ def __repr__(self):
+ return repr(self._values)
+
+ def MergeFrom(self, other):
+ for key in other:
+ # According to documentation: "When parsing from the wire or when merging,
+ # if there are duplicate map keys the last key seen is used".
+ if key in self:
+ del self[key]
+ self[key].CopyFrom(other[key])
+ # self._message_listener.Modified() not required here, because
+ # mutations to submessages already propagate.
+
+ def InvalidateIterators(self):
+ # It appears that the only way to reliably invalidate iterators to
+ # self._values is to ensure that its size changes.
+ original = self._values
+ self._values = original.copy()
+ original[None] = None
+
+ # This is defined in the abstract base, but we can do it much more cheaply.
+ def clear(self):
+ self._values.clear()
+ self._message_listener.Modified()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/decoder.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/decoder.py
new file mode 100755
index 0000000000..31869e4575
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/decoder.py
@@ -0,0 +1,854 @@
+# 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.
+
+"""Code for decoding protocol buffer primitives.
+
+This code is very similar to encoder.py -- read the docs for that module first.
+
+A "decoder" is a function with the signature:
+ Decode(buffer, pos, end, message, field_dict)
+The arguments are:
+ buffer: The string containing the encoded message.
+ pos: The current position in the string.
+ end: The position in the string where the current message ends. May be
+ less than len(buffer) if we're reading a sub-message.
+ message: The message object into which we're parsing.
+ field_dict: message._fields (avoids a hashtable lookup).
+The decoder reads the field and stores it into field_dict, returning the new
+buffer position. A decoder for a repeated field may proactively decode all of
+the elements of that field, if they appear consecutively.
+
+Note that decoders may throw any of the following:
+ IndexError: Indicates a truncated message.
+ struct.error: Unpacking of a fixed-width field failed.
+ message.DecodeError: Other errors.
+
+Decoders are expected to raise an exception if they are called with pos > end.
+This allows callers to be lax about bounds checking: it's fineto read past
+"end" as long as you are sure that someone else will notice and throw an
+exception later on.
+
+Something up the call stack is expected to catch IndexError and struct.error
+and convert them to message.DecodeError.
+
+Decoders are constructed using decoder constructors with the signature:
+ MakeDecoder(field_number, is_repeated, is_packed, key, new_default)
+The arguments are:
+ field_number: The field number of the field we want to decode.
+ is_repeated: Is the field a repeated field? (bool)
+ is_packed: Is the field a packed field? (bool)
+ key: The key to use when looking up the field within field_dict.
+ (This is actually the FieldDescriptor but nothing in this
+ file should depend on that.)
+ new_default: A function which takes a message object as a parameter and
+ returns a new instance of the default value for this field.
+ (This is called for repeated fields and sub-messages, when an
+ instance does not already exist.)
+
+As with encoders, we define a decoder constructor for every type of field.
+Then, for every field of every message class we construct an actual decoder.
+That decoder goes into a dict indexed by tag, so when we decode a message
+we repeatedly read a tag, look up the corresponding decoder, and invoke it.
+"""
+
+__author__ = 'kenton@google.com (Kenton Varda)'
+
+import struct
+
+import six
+
+if six.PY3:
+ long = int
+
+from google.protobuf.internal import encoder
+from google.protobuf.internal import wire_format
+from google.protobuf import message
+
+
+# This will overflow and thus become IEEE-754 "infinity". We would use
+# "float('inf')" but it doesn't work on Windows pre-Python-2.6.
+_POS_INF = 1e10000
+_NEG_INF = -_POS_INF
+_NAN = _POS_INF * 0
+
+
+# This is not for optimization, but rather to avoid conflicts with local
+# variables named "message".
+_DecodeError = message.DecodeError
+
+
+def _VarintDecoder(mask, result_type):
+ """Return an encoder for a basic varint value (does not include tag).
+
+ Decoded values will be bitwise-anded with the given mask before being
+ returned, e.g. to limit them to 32 bits. The returned decoder does not
+ take the usual "end" parameter -- the caller is expected to do bounds checking
+ after the fact (often the caller can defer such checking until later). The
+ decoder returns a (value, new_pos) pair.
+ """
+
+ def DecodeVarint(buffer, pos):
+ result = 0
+ shift = 0
+ while 1:
+ b = six.indexbytes(buffer, pos)
+ result |= ((b & 0x7f) << shift)
+ pos += 1
+ if not (b & 0x80):
+ result &= mask
+ result = result_type(result)
+ return (result, pos)
+ shift += 7
+ if shift >= 64:
+ raise _DecodeError('Too many bytes when decoding varint.')
+ return DecodeVarint
+
+
+def _SignedVarintDecoder(mask, result_type):
+ """Like _VarintDecoder() but decodes signed values."""
+
+ def DecodeVarint(buffer, pos):
+ result = 0
+ shift = 0
+ while 1:
+ b = six.indexbytes(buffer, pos)
+ result |= ((b & 0x7f) << shift)
+ pos += 1
+ if not (b & 0x80):
+ if result > 0x7fffffffffffffff:
+ result -= (1 << 64)
+ result |= ~mask
+ else:
+ result &= mask
+ result = result_type(result)
+ return (result, pos)
+ shift += 7
+ if shift >= 64:
+ raise _DecodeError('Too many bytes when decoding varint.')
+ return DecodeVarint
+
+# We force 32-bit values to int and 64-bit values to long to make
+# alternate implementations where the distinction is more significant
+# (e.g. the C++ implementation) simpler.
+
+_DecodeVarint = _VarintDecoder((1 << 64) - 1, long)
+_DecodeSignedVarint = _SignedVarintDecoder((1 << 64) - 1, long)
+
+# Use these versions for values which must be limited to 32 bits.
+_DecodeVarint32 = _VarintDecoder((1 << 32) - 1, int)
+_DecodeSignedVarint32 = _SignedVarintDecoder((1 << 32) - 1, int)
+
+
+def ReadTag(buffer, pos):
+ """Read a tag from the buffer, and return a (tag_bytes, new_pos) tuple.
+
+ We return the raw bytes of the tag rather than decoding them. The raw
+ bytes can then be used to look up the proper decoder. This effectively allows
+ us to trade some work that would be done in pure-python (decoding a varint)
+ for work that is done in C (searching for a byte string in a hash table).
+ In a low-level language it would be much cheaper to decode the varint and
+ use that, but not in Python.
+ """
+
+ start = pos
+ while six.indexbytes(buffer, pos) & 0x80:
+ pos += 1
+ pos += 1
+ return (buffer[start:pos], pos)
+
+
+# --------------------------------------------------------------------
+
+
+def _SimpleDecoder(wire_type, decode_value):
+ """Return a constructor for a decoder for fields of a particular type.
+
+ Args:
+ wire_type: The field's wire type.
+ decode_value: A function which decodes an individual value, e.g.
+ _DecodeVarint()
+ """
+
+ def SpecificDecoder(field_number, is_repeated, is_packed, key, new_default):
+ if is_packed:
+ local_DecodeVarint = _DecodeVarint
+ def DecodePackedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ (endpoint, pos) = local_DecodeVarint(buffer, pos)
+ endpoint += pos
+ if endpoint > end:
+ raise _DecodeError('Truncated message.')
+ while pos < endpoint:
+ (element, pos) = decode_value(buffer, pos)
+ value.append(element)
+ if pos > endpoint:
+ del value[-1] # Discard corrupt value.
+ raise _DecodeError('Packed element was truncated.')
+ return pos
+ return DecodePackedField
+ elif is_repeated:
+ tag_bytes = encoder.TagBytes(field_number, wire_type)
+ tag_len = len(tag_bytes)
+ def DecodeRepeatedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ while 1:
+ (element, new_pos) = decode_value(buffer, pos)
+ value.append(element)
+ # Predict that the next tag is another copy of the same repeated
+ # field.
+ pos = new_pos + tag_len
+ if buffer[new_pos:pos] != tag_bytes or new_pos >= end:
+ # Prediction failed. Return.
+ if new_pos > end:
+ raise _DecodeError('Truncated message.')
+ return new_pos
+ return DecodeRepeatedField
+ else:
+ def DecodeField(buffer, pos, end, message, field_dict):
+ (field_dict[key], pos) = decode_value(buffer, pos)
+ if pos > end:
+ del field_dict[key] # Discard corrupt value.
+ raise _DecodeError('Truncated message.')
+ return pos
+ return DecodeField
+
+ return SpecificDecoder
+
+
+def _ModifiedDecoder(wire_type, decode_value, modify_value):
+ """Like SimpleDecoder but additionally invokes modify_value on every value
+ before storing it. Usually modify_value is ZigZagDecode.
+ """
+
+ # Reusing _SimpleDecoder is slightly slower than copying a bunch of code, but
+ # not enough to make a significant difference.
+
+ def InnerDecode(buffer, pos):
+ (result, new_pos) = decode_value(buffer, pos)
+ return (modify_value(result), new_pos)
+ return _SimpleDecoder(wire_type, InnerDecode)
+
+
+def _StructPackDecoder(wire_type, format):
+ """Return a constructor for a decoder for a fixed-width field.
+
+ Args:
+ wire_type: The field's wire type.
+ format: The format string to pass to struct.unpack().
+ """
+
+ value_size = struct.calcsize(format)
+ local_unpack = struct.unpack
+
+ # Reusing _SimpleDecoder is slightly slower than copying a bunch of code, but
+ # not enough to make a significant difference.
+
+ # Note that we expect someone up-stack to catch struct.error and convert
+ # it to _DecodeError -- this way we don't have to set up exception-
+ # handling blocks every time we parse one value.
+
+ def InnerDecode(buffer, pos):
+ new_pos = pos + value_size
+ result = local_unpack(format, buffer[pos:new_pos])[0]
+ return (result, new_pos)
+ return _SimpleDecoder(wire_type, InnerDecode)
+
+
+def _FloatDecoder():
+ """Returns a decoder for a float field.
+
+ This code works around a bug in struct.unpack for non-finite 32-bit
+ floating-point values.
+ """
+
+ local_unpack = struct.unpack
+
+ def InnerDecode(buffer, pos):
+ # We expect a 32-bit value in little-endian byte order. Bit 1 is the sign
+ # bit, bits 2-9 represent the exponent, and bits 10-32 are the significand.
+ new_pos = pos + 4
+ float_bytes = buffer[pos:new_pos]
+
+ # If this value has all its exponent bits set, then it's non-finite.
+ # In Python 2.4, struct.unpack will convert it to a finite 64-bit value.
+ # To avoid that, we parse it specially.
+ if (float_bytes[3:4] in b'\x7F\xFF' and float_bytes[2:3] >= b'\x80'):
+ # If at least one significand bit is set...
+ if float_bytes[0:3] != b'\x00\x00\x80':
+ return (_NAN, new_pos)
+ # If sign bit is set...
+ if float_bytes[3:4] == b'\xFF':
+ return (_NEG_INF, new_pos)
+ return (_POS_INF, new_pos)
+
+ # Note that we expect someone up-stack to catch struct.error and convert
+ # it to _DecodeError -- this way we don't have to set up exception-
+ # handling blocks every time we parse one value.
+ result = local_unpack('<f', float_bytes)[0]
+ return (result, new_pos)
+ return _SimpleDecoder(wire_format.WIRETYPE_FIXED32, InnerDecode)
+
+
+def _DoubleDecoder():
+ """Returns a decoder for a double field.
+
+ This code works around a bug in struct.unpack for not-a-number.
+ """
+
+ local_unpack = struct.unpack
+
+ def InnerDecode(buffer, pos):
+ # We expect a 64-bit value in little-endian byte order. Bit 1 is the sign
+ # bit, bits 2-12 represent the exponent, and bits 13-64 are the significand.
+ new_pos = pos + 8
+ double_bytes = buffer[pos:new_pos]
+
+ # If this value has all its exponent bits set and at least one significand
+ # bit set, it's not a number. In Python 2.4, struct.unpack will treat it
+ # as inf or -inf. To avoid that, we treat it specially.
+ if ((double_bytes[7:8] in b'\x7F\xFF')
+ and (double_bytes[6:7] >= b'\xF0')
+ and (double_bytes[0:7] != b'\x00\x00\x00\x00\x00\x00\xF0')):
+ return (_NAN, new_pos)
+
+ # Note that we expect someone up-stack to catch struct.error and convert
+ # it to _DecodeError -- this way we don't have to set up exception-
+ # handling blocks every time we parse one value.
+ result = local_unpack('<d', double_bytes)[0]
+ return (result, new_pos)
+ return _SimpleDecoder(wire_format.WIRETYPE_FIXED64, InnerDecode)
+
+
+def EnumDecoder(field_number, is_repeated, is_packed, key, new_default):
+ enum_type = key.enum_type
+ if is_packed:
+ local_DecodeVarint = _DecodeVarint
+ def DecodePackedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ (endpoint, pos) = local_DecodeVarint(buffer, pos)
+ endpoint += pos
+ if endpoint > end:
+ raise _DecodeError('Truncated message.')
+ while pos < endpoint:
+ value_start_pos = pos
+ (element, pos) = _DecodeSignedVarint32(buffer, pos)
+ if element in enum_type.values_by_number:
+ value.append(element)
+ else:
+ if not message._unknown_fields:
+ message._unknown_fields = []
+ tag_bytes = encoder.TagBytes(field_number,
+ wire_format.WIRETYPE_VARINT)
+ message._unknown_fields.append(
+ (tag_bytes, buffer[value_start_pos:pos]))
+ if pos > endpoint:
+ if element in enum_type.values_by_number:
+ del value[-1] # Discard corrupt value.
+ else:
+ del message._unknown_fields[-1]
+ raise _DecodeError('Packed element was truncated.')
+ return pos
+ return DecodePackedField
+ elif is_repeated:
+ tag_bytes = encoder.TagBytes(field_number, wire_format.WIRETYPE_VARINT)
+ tag_len = len(tag_bytes)
+ def DecodeRepeatedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ while 1:
+ (element, new_pos) = _DecodeSignedVarint32(buffer, pos)
+ if element in enum_type.values_by_number:
+ value.append(element)
+ else:
+ if not message._unknown_fields:
+ message._unknown_fields = []
+ message._unknown_fields.append(
+ (tag_bytes, buffer[pos:new_pos]))
+ # Predict that the next tag is another copy of the same repeated
+ # field.
+ pos = new_pos + tag_len
+ if buffer[new_pos:pos] != tag_bytes or new_pos >= end:
+ # Prediction failed. Return.
+ if new_pos > end:
+ raise _DecodeError('Truncated message.')
+ return new_pos
+ return DecodeRepeatedField
+ else:
+ def DecodeField(buffer, pos, end, message, field_dict):
+ value_start_pos = pos
+ (enum_value, pos) = _DecodeSignedVarint32(buffer, pos)
+ if pos > end:
+ raise _DecodeError('Truncated message.')
+ if enum_value in enum_type.values_by_number:
+ field_dict[key] = enum_value
+ else:
+ if not message._unknown_fields:
+ message._unknown_fields = []
+ tag_bytes = encoder.TagBytes(field_number,
+ wire_format.WIRETYPE_VARINT)
+ message._unknown_fields.append(
+ (tag_bytes, buffer[value_start_pos:pos]))
+ return pos
+ return DecodeField
+
+
+# --------------------------------------------------------------------
+
+
+Int32Decoder = _SimpleDecoder(
+ wire_format.WIRETYPE_VARINT, _DecodeSignedVarint32)
+
+Int64Decoder = _SimpleDecoder(
+ wire_format.WIRETYPE_VARINT, _DecodeSignedVarint)
+
+UInt32Decoder = _SimpleDecoder(wire_format.WIRETYPE_VARINT, _DecodeVarint32)
+UInt64Decoder = _SimpleDecoder(wire_format.WIRETYPE_VARINT, _DecodeVarint)
+
+SInt32Decoder = _ModifiedDecoder(
+ wire_format.WIRETYPE_VARINT, _DecodeVarint32, wire_format.ZigZagDecode)
+SInt64Decoder = _ModifiedDecoder(
+ wire_format.WIRETYPE_VARINT, _DecodeVarint, wire_format.ZigZagDecode)
+
+# Note that Python conveniently guarantees that when using the '<' prefix on
+# formats, they will also have the same size across all platforms (as opposed
+# to without the prefix, where their sizes depend on the C compiler's basic
+# type sizes).
+Fixed32Decoder = _StructPackDecoder(wire_format.WIRETYPE_FIXED32, '<I')
+Fixed64Decoder = _StructPackDecoder(wire_format.WIRETYPE_FIXED64, '<Q')
+SFixed32Decoder = _StructPackDecoder(wire_format.WIRETYPE_FIXED32, '<i')
+SFixed64Decoder = _StructPackDecoder(wire_format.WIRETYPE_FIXED64, '<q')
+FloatDecoder = _FloatDecoder()
+DoubleDecoder = _DoubleDecoder()
+
+BoolDecoder = _ModifiedDecoder(
+ wire_format.WIRETYPE_VARINT, _DecodeVarint, bool)
+
+
+def StringDecoder(field_number, is_repeated, is_packed, key, new_default):
+ """Returns a decoder for a string field."""
+
+ local_DecodeVarint = _DecodeVarint
+ local_unicode = six.text_type
+
+ def _ConvertToUnicode(byte_str):
+ try:
+ return local_unicode(byte_str, 'utf-8')
+ except UnicodeDecodeError as e:
+ # add more information to the error message and re-raise it.
+ e.reason = '%s in field: %s' % (e, key.full_name)
+ raise
+
+ assert not is_packed
+ if is_repeated:
+ tag_bytes = encoder.TagBytes(field_number,
+ wire_format.WIRETYPE_LENGTH_DELIMITED)
+ tag_len = len(tag_bytes)
+ def DecodeRepeatedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ while 1:
+ (size, pos) = local_DecodeVarint(buffer, pos)
+ new_pos = pos + size
+ if new_pos > end:
+ raise _DecodeError('Truncated string.')
+ value.append(_ConvertToUnicode(buffer[pos:new_pos]))
+ # Predict that the next tag is another copy of the same repeated field.
+ pos = new_pos + tag_len
+ if buffer[new_pos:pos] != tag_bytes or new_pos == end:
+ # Prediction failed. Return.
+ return new_pos
+ return DecodeRepeatedField
+ else:
+ def DecodeField(buffer, pos, end, message, field_dict):
+ (size, pos) = local_DecodeVarint(buffer, pos)
+ new_pos = pos + size
+ if new_pos > end:
+ raise _DecodeError('Truncated string.')
+ field_dict[key] = _ConvertToUnicode(buffer[pos:new_pos])
+ return new_pos
+ return DecodeField
+
+
+def BytesDecoder(field_number, is_repeated, is_packed, key, new_default):
+ """Returns a decoder for a bytes field."""
+
+ local_DecodeVarint = _DecodeVarint
+
+ assert not is_packed
+ if is_repeated:
+ tag_bytes = encoder.TagBytes(field_number,
+ wire_format.WIRETYPE_LENGTH_DELIMITED)
+ tag_len = len(tag_bytes)
+ def DecodeRepeatedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ while 1:
+ (size, pos) = local_DecodeVarint(buffer, pos)
+ new_pos = pos + size
+ if new_pos > end:
+ raise _DecodeError('Truncated string.')
+ value.append(buffer[pos:new_pos])
+ # Predict that the next tag is another copy of the same repeated field.
+ pos = new_pos + tag_len
+ if buffer[new_pos:pos] != tag_bytes or new_pos == end:
+ # Prediction failed. Return.
+ return new_pos
+ return DecodeRepeatedField
+ else:
+ def DecodeField(buffer, pos, end, message, field_dict):
+ (size, pos) = local_DecodeVarint(buffer, pos)
+ new_pos = pos + size
+ if new_pos > end:
+ raise _DecodeError('Truncated string.')
+ field_dict[key] = buffer[pos:new_pos]
+ return new_pos
+ return DecodeField
+
+
+def GroupDecoder(field_number, is_repeated, is_packed, key, new_default):
+ """Returns a decoder for a group field."""
+
+ end_tag_bytes = encoder.TagBytes(field_number,
+ wire_format.WIRETYPE_END_GROUP)
+ end_tag_len = len(end_tag_bytes)
+
+ assert not is_packed
+ if is_repeated:
+ tag_bytes = encoder.TagBytes(field_number,
+ wire_format.WIRETYPE_START_GROUP)
+ tag_len = len(tag_bytes)
+ def DecodeRepeatedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ while 1:
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ # Read sub-message.
+ pos = value.add()._InternalParse(buffer, pos, end)
+ # Read end tag.
+ new_pos = pos+end_tag_len
+ if buffer[pos:new_pos] != end_tag_bytes or new_pos > end:
+ raise _DecodeError('Missing group end tag.')
+ # Predict that the next tag is another copy of the same repeated field.
+ pos = new_pos + tag_len
+ if buffer[new_pos:pos] != tag_bytes or new_pos == end:
+ # Prediction failed. Return.
+ return new_pos
+ return DecodeRepeatedField
+ else:
+ def DecodeField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ # Read sub-message.
+ pos = value._InternalParse(buffer, pos, end)
+ # Read end tag.
+ new_pos = pos+end_tag_len
+ if buffer[pos:new_pos] != end_tag_bytes or new_pos > end:
+ raise _DecodeError('Missing group end tag.')
+ return new_pos
+ return DecodeField
+
+
+def MessageDecoder(field_number, is_repeated, is_packed, key, new_default):
+ """Returns a decoder for a message field."""
+
+ local_DecodeVarint = _DecodeVarint
+
+ assert not is_packed
+ if is_repeated:
+ tag_bytes = encoder.TagBytes(field_number,
+ wire_format.WIRETYPE_LENGTH_DELIMITED)
+ tag_len = len(tag_bytes)
+ def DecodeRepeatedField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ while 1:
+ # Read length.
+ (size, pos) = local_DecodeVarint(buffer, pos)
+ new_pos = pos + size
+ if new_pos > end:
+ raise _DecodeError('Truncated message.')
+ # Read sub-message.
+ if value.add()._InternalParse(buffer, pos, new_pos) != new_pos:
+ # The only reason _InternalParse would return early is if it
+ # encountered an end-group tag.
+ raise _DecodeError('Unexpected end-group tag.')
+ # Predict that the next tag is another copy of the same repeated field.
+ pos = new_pos + tag_len
+ if buffer[new_pos:pos] != tag_bytes or new_pos == end:
+ # Prediction failed. Return.
+ return new_pos
+ return DecodeRepeatedField
+ else:
+ def DecodeField(buffer, pos, end, message, field_dict):
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ # Read length.
+ (size, pos) = local_DecodeVarint(buffer, pos)
+ new_pos = pos + size
+ if new_pos > end:
+ raise _DecodeError('Truncated message.')
+ # Read sub-message.
+ if value._InternalParse(buffer, pos, new_pos) != new_pos:
+ # The only reason _InternalParse would return early is if it encountered
+ # an end-group tag.
+ raise _DecodeError('Unexpected end-group tag.')
+ return new_pos
+ return DecodeField
+
+
+# --------------------------------------------------------------------
+
+MESSAGE_SET_ITEM_TAG = encoder.TagBytes(1, wire_format.WIRETYPE_START_GROUP)
+
+def MessageSetItemDecoder(extensions_by_number):
+ """Returns a decoder for a MessageSet item.
+
+ The parameter is the _extensions_by_number map for the message class.
+
+ The message set message looks like this:
+ message MessageSet {
+ repeated group Item = 1 {
+ required int32 type_id = 2;
+ required string message = 3;
+ }
+ }
+ """
+
+ type_id_tag_bytes = encoder.TagBytes(2, wire_format.WIRETYPE_VARINT)
+ message_tag_bytes = encoder.TagBytes(3, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ item_end_tag_bytes = encoder.TagBytes(1, wire_format.WIRETYPE_END_GROUP)
+
+ local_ReadTag = ReadTag
+ local_DecodeVarint = _DecodeVarint
+ local_SkipField = SkipField
+
+ def DecodeItem(buffer, pos, end, message, field_dict):
+ message_set_item_start = pos
+ type_id = -1
+ message_start = -1
+ message_end = -1
+
+ # Technically, type_id and message can appear in any order, so we need
+ # a little loop here.
+ while 1:
+ (tag_bytes, pos) = local_ReadTag(buffer, pos)
+ if tag_bytes == type_id_tag_bytes:
+ (type_id, pos) = local_DecodeVarint(buffer, pos)
+ elif tag_bytes == message_tag_bytes:
+ (size, message_start) = local_DecodeVarint(buffer, pos)
+ pos = message_end = message_start + size
+ elif tag_bytes == item_end_tag_bytes:
+ break
+ else:
+ pos = SkipField(buffer, pos, end, tag_bytes)
+ if pos == -1:
+ raise _DecodeError('Missing group end tag.')
+
+ if pos > end:
+ raise _DecodeError('Truncated message.')
+
+ if type_id == -1:
+ raise _DecodeError('MessageSet item missing type_id.')
+ if message_start == -1:
+ raise _DecodeError('MessageSet item missing message.')
+
+ extension = extensions_by_number.get(type_id)
+ if extension is not None:
+ value = field_dict.get(extension)
+ if value is None:
+ value = field_dict.setdefault(
+ extension, extension.message_type._concrete_class())
+ if value._InternalParse(buffer, message_start,message_end) != message_end:
+ # The only reason _InternalParse would return early is if it encountered
+ # an end-group tag.
+ raise _DecodeError('Unexpected end-group tag.')
+ else:
+ if not message._unknown_fields:
+ message._unknown_fields = []
+ message._unknown_fields.append((MESSAGE_SET_ITEM_TAG,
+ buffer[message_set_item_start:pos]))
+
+ return pos
+
+ return DecodeItem
+
+# --------------------------------------------------------------------
+
+def MapDecoder(field_descriptor, new_default, is_message_map):
+ """Returns a decoder for a map field."""
+
+ key = field_descriptor
+ tag_bytes = encoder.TagBytes(field_descriptor.number,
+ wire_format.WIRETYPE_LENGTH_DELIMITED)
+ tag_len = len(tag_bytes)
+ local_DecodeVarint = _DecodeVarint
+ # Can't read _concrete_class yet; might not be initialized.
+ message_type = field_descriptor.message_type
+
+ def DecodeMap(buffer, pos, end, message, field_dict):
+ submsg = message_type._concrete_class()
+ value = field_dict.get(key)
+ if value is None:
+ value = field_dict.setdefault(key, new_default(message))
+ while 1:
+ # Read length.
+ (size, pos) = local_DecodeVarint(buffer, pos)
+ new_pos = pos + size
+ if new_pos > end:
+ raise _DecodeError('Truncated message.')
+ # Read sub-message.
+ submsg.Clear()
+ if submsg._InternalParse(buffer, pos, new_pos) != new_pos:
+ # The only reason _InternalParse would return early is if it
+ # encountered an end-group tag.
+ raise _DecodeError('Unexpected end-group tag.')
+
+ if is_message_map:
+ value[submsg.key].MergeFrom(submsg.value)
+ else:
+ value[submsg.key] = submsg.value
+
+ # Predict that the next tag is another copy of the same repeated field.
+ pos = new_pos + tag_len
+ if buffer[new_pos:pos] != tag_bytes or new_pos == end:
+ # Prediction failed. Return.
+ return new_pos
+
+ return DecodeMap
+
+# --------------------------------------------------------------------
+# Optimization is not as heavy here because calls to SkipField() are rare,
+# except for handling end-group tags.
+
+def _SkipVarint(buffer, pos, end):
+ """Skip a varint value. Returns the new position."""
+ # Previously ord(buffer[pos]) raised IndexError when pos is out of range.
+ # With this code, ord(b'') raises TypeError. Both are handled in
+ # python_message.py to generate a 'Truncated message' error.
+ while ord(buffer[pos:pos+1]) & 0x80:
+ pos += 1
+ pos += 1
+ if pos > end:
+ raise _DecodeError('Truncated message.')
+ return pos
+
+def _SkipFixed64(buffer, pos, end):
+ """Skip a fixed64 value. Returns the new position."""
+
+ pos += 8
+ if pos > end:
+ raise _DecodeError('Truncated message.')
+ return pos
+
+def _SkipLengthDelimited(buffer, pos, end):
+ """Skip a length-delimited value. Returns the new position."""
+
+ (size, pos) = _DecodeVarint(buffer, pos)
+ pos += size
+ if pos > end:
+ raise _DecodeError('Truncated message.')
+ return pos
+
+def _SkipGroup(buffer, pos, end):
+ """Skip sub-group. Returns the new position."""
+
+ while 1:
+ (tag_bytes, pos) = ReadTag(buffer, pos)
+ new_pos = SkipField(buffer, pos, end, tag_bytes)
+ if new_pos == -1:
+ return pos
+ pos = new_pos
+
+def _EndGroup(buffer, pos, end):
+ """Skipping an END_GROUP tag returns -1 to tell the parent loop to break."""
+
+ return -1
+
+def _SkipFixed32(buffer, pos, end):
+ """Skip a fixed32 value. Returns the new position."""
+
+ pos += 4
+ if pos > end:
+ raise _DecodeError('Truncated message.')
+ return pos
+
+def _RaiseInvalidWireType(buffer, pos, end):
+ """Skip function for unknown wire types. Raises an exception."""
+
+ raise _DecodeError('Tag had invalid wire type.')
+
+def _FieldSkipper():
+ """Constructs the SkipField function."""
+
+ WIRETYPE_TO_SKIPPER = [
+ _SkipVarint,
+ _SkipFixed64,
+ _SkipLengthDelimited,
+ _SkipGroup,
+ _EndGroup,
+ _SkipFixed32,
+ _RaiseInvalidWireType,
+ _RaiseInvalidWireType,
+ ]
+
+ wiretype_mask = wire_format.TAG_TYPE_MASK
+
+ def SkipField(buffer, pos, end, tag_bytes):
+ """Skips a field with the specified tag.
+
+ |pos| should point to the byte immediately after the tag.
+
+ Returns:
+ The new position (after the tag value), or -1 if the tag is an end-group
+ tag (in which case the calling loop should break).
+ """
+
+ # The wire type is always in the first byte since varints are little-endian.
+ wire_type = ord(tag_bytes[0:1]) & wiretype_mask
+ return WIRETYPE_TO_SKIPPER[wire_type](buffer, pos, end)
+
+ return SkipField
+
+SkipField = _FieldSkipper()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_database_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_database_test.py
new file mode 100644
index 0000000000..5225a45821
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_database_test.py
@@ -0,0 +1,69 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests for google.protobuf.descriptor_database."""
+
+__author__ = 'matthewtoia@google.com (Matt Toia)'
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import descriptor_pb2
+from google.protobuf.internal import factory_test2_pb2
+from google.protobuf import descriptor_database
+
+
+class DescriptorDatabaseTest(unittest.TestCase):
+
+ def testAdd(self):
+ db = descriptor_database.DescriptorDatabase()
+ file_desc_proto = descriptor_pb2.FileDescriptorProto.FromString(
+ factory_test2_pb2.DESCRIPTOR.serialized_pb)
+ db.Add(file_desc_proto)
+
+ self.assertEqual(file_desc_proto, db.FindFileByName(
+ 'google/protobuf/internal/factory_test2.proto'))
+ self.assertEqual(file_desc_proto, db.FindFileContainingSymbol(
+ 'google.protobuf.python.internal.Factory2Message'))
+ self.assertEqual(file_desc_proto, db.FindFileContainingSymbol(
+ 'google.protobuf.python.internal.Factory2Message.NestedFactory2Message'))
+ self.assertEqual(file_desc_proto, db.FindFileContainingSymbol(
+ 'google.protobuf.python.internal.Factory2Enum'))
+ self.assertEqual(file_desc_proto, db.FindFileContainingSymbol(
+ 'google.protobuf.python.internal.Factory2Message.NestedFactory2Enum'))
+ self.assertEqual(file_desc_proto, db.FindFileContainingSymbol(
+ 'google.protobuf.python.internal.MessageWithNestedEnumOnly.NestedEnum'))
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test.py
new file mode 100644
index 0000000000..3c8c793537
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test.py
@@ -0,0 +1,768 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests for google.protobuf.descriptor_pool."""
+
+__author__ = 'matthewtoia@google.com (Matt Toia)'
+
+import os
+import sys
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import unittest_import_pb2
+from google.protobuf import unittest_import_public_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import descriptor_pb2
+from google.protobuf.internal import api_implementation
+from google.protobuf.internal import descriptor_pool_test1_pb2
+from google.protobuf.internal import descriptor_pool_test2_pb2
+from google.protobuf.internal import factory_test1_pb2
+from google.protobuf.internal import factory_test2_pb2
+from google.protobuf.internal import file_options_test_pb2
+from google.protobuf.internal import more_messages_pb2
+from google.protobuf import descriptor
+from google.protobuf import descriptor_database
+from google.protobuf import descriptor_pool
+from google.protobuf import message_factory
+from google.protobuf import symbol_database
+
+
+class DescriptorPoolTest(unittest.TestCase):
+
+ def setUp(self):
+ self.pool = descriptor_pool.DescriptorPool()
+ self.factory_test1_fd = descriptor_pb2.FileDescriptorProto.FromString(
+ factory_test1_pb2.DESCRIPTOR.serialized_pb)
+ self.factory_test2_fd = descriptor_pb2.FileDescriptorProto.FromString(
+ factory_test2_pb2.DESCRIPTOR.serialized_pb)
+ self.pool.Add(self.factory_test1_fd)
+ self.pool.Add(self.factory_test2_fd)
+
+ def testFindFileByName(self):
+ name1 = 'google/protobuf/internal/factory_test1.proto'
+ file_desc1 = self.pool.FindFileByName(name1)
+ self.assertIsInstance(file_desc1, descriptor.FileDescriptor)
+ self.assertEqual(name1, file_desc1.name)
+ self.assertEqual('google.protobuf.python.internal', file_desc1.package)
+ self.assertIn('Factory1Message', file_desc1.message_types_by_name)
+
+ name2 = 'google/protobuf/internal/factory_test2.proto'
+ file_desc2 = self.pool.FindFileByName(name2)
+ self.assertIsInstance(file_desc2, descriptor.FileDescriptor)
+ self.assertEqual(name2, file_desc2.name)
+ self.assertEqual('google.protobuf.python.internal', file_desc2.package)
+ self.assertIn('Factory2Message', file_desc2.message_types_by_name)
+
+ def testFindFileByNameFailure(self):
+ with self.assertRaises(KeyError):
+ self.pool.FindFileByName('Does not exist')
+
+ def testFindFileContainingSymbol(self):
+ file_desc1 = self.pool.FindFileContainingSymbol(
+ 'google.protobuf.python.internal.Factory1Message')
+ self.assertIsInstance(file_desc1, descriptor.FileDescriptor)
+ self.assertEqual('google/protobuf/internal/factory_test1.proto',
+ file_desc1.name)
+ self.assertEqual('google.protobuf.python.internal', file_desc1.package)
+ self.assertIn('Factory1Message', file_desc1.message_types_by_name)
+
+ file_desc2 = self.pool.FindFileContainingSymbol(
+ 'google.protobuf.python.internal.Factory2Message')
+ self.assertIsInstance(file_desc2, descriptor.FileDescriptor)
+ self.assertEqual('google/protobuf/internal/factory_test2.proto',
+ file_desc2.name)
+ self.assertEqual('google.protobuf.python.internal', file_desc2.package)
+ self.assertIn('Factory2Message', file_desc2.message_types_by_name)
+
+ def testFindFileContainingSymbolFailure(self):
+ with self.assertRaises(KeyError):
+ self.pool.FindFileContainingSymbol('Does not exist')
+
+ def testFindMessageTypeByName(self):
+ msg1 = self.pool.FindMessageTypeByName(
+ 'google.protobuf.python.internal.Factory1Message')
+ self.assertIsInstance(msg1, descriptor.Descriptor)
+ self.assertEqual('Factory1Message', msg1.name)
+ self.assertEqual('google.protobuf.python.internal.Factory1Message',
+ msg1.full_name)
+ self.assertEqual(None, msg1.containing_type)
+
+ nested_msg1 = msg1.nested_types[0]
+ self.assertEqual('NestedFactory1Message', nested_msg1.name)
+ self.assertEqual(msg1, nested_msg1.containing_type)
+
+ nested_enum1 = msg1.enum_types[0]
+ self.assertEqual('NestedFactory1Enum', nested_enum1.name)
+ self.assertEqual(msg1, nested_enum1.containing_type)
+
+ self.assertEqual(nested_msg1, msg1.fields_by_name[
+ 'nested_factory_1_message'].message_type)
+ self.assertEqual(nested_enum1, msg1.fields_by_name[
+ 'nested_factory_1_enum'].enum_type)
+
+ msg2 = self.pool.FindMessageTypeByName(
+ 'google.protobuf.python.internal.Factory2Message')
+ self.assertIsInstance(msg2, descriptor.Descriptor)
+ self.assertEqual('Factory2Message', msg2.name)
+ self.assertEqual('google.protobuf.python.internal.Factory2Message',
+ msg2.full_name)
+ self.assertIsNone(msg2.containing_type)
+
+ nested_msg2 = msg2.nested_types[0]
+ self.assertEqual('NestedFactory2Message', nested_msg2.name)
+ self.assertEqual(msg2, nested_msg2.containing_type)
+
+ nested_enum2 = msg2.enum_types[0]
+ self.assertEqual('NestedFactory2Enum', nested_enum2.name)
+ self.assertEqual(msg2, nested_enum2.containing_type)
+
+ self.assertEqual(nested_msg2, msg2.fields_by_name[
+ 'nested_factory_2_message'].message_type)
+ self.assertEqual(nested_enum2, msg2.fields_by_name[
+ 'nested_factory_2_enum'].enum_type)
+
+ self.assertTrue(msg2.fields_by_name['int_with_default'].has_default_value)
+ self.assertEqual(
+ 1776, msg2.fields_by_name['int_with_default'].default_value)
+
+ self.assertTrue(
+ msg2.fields_by_name['double_with_default'].has_default_value)
+ self.assertEqual(
+ 9.99, msg2.fields_by_name['double_with_default'].default_value)
+
+ self.assertTrue(
+ msg2.fields_by_name['string_with_default'].has_default_value)
+ self.assertEqual(
+ 'hello world', msg2.fields_by_name['string_with_default'].default_value)
+
+ self.assertTrue(msg2.fields_by_name['bool_with_default'].has_default_value)
+ self.assertFalse(msg2.fields_by_name['bool_with_default'].default_value)
+
+ self.assertTrue(msg2.fields_by_name['enum_with_default'].has_default_value)
+ self.assertEqual(
+ 1, msg2.fields_by_name['enum_with_default'].default_value)
+
+ msg3 = self.pool.FindMessageTypeByName(
+ 'google.protobuf.python.internal.Factory2Message.NestedFactory2Message')
+ self.assertEqual(nested_msg2, msg3)
+
+ self.assertTrue(msg2.fields_by_name['bytes_with_default'].has_default_value)
+ self.assertEqual(
+ b'a\xfb\x00c',
+ msg2.fields_by_name['bytes_with_default'].default_value)
+
+ self.assertEqual(1, len(msg2.oneofs))
+ self.assertEqual(1, len(msg2.oneofs_by_name))
+ self.assertEqual(2, len(msg2.oneofs[0].fields))
+ for name in ['oneof_int', 'oneof_string']:
+ self.assertEqual(msg2.oneofs[0],
+ msg2.fields_by_name[name].containing_oneof)
+ self.assertIn(msg2.fields_by_name[name], msg2.oneofs[0].fields)
+
+ def testFindMessageTypeByNameFailure(self):
+ with self.assertRaises(KeyError):
+ self.pool.FindMessageTypeByName('Does not exist')
+
+ def testFindEnumTypeByName(self):
+ enum1 = self.pool.FindEnumTypeByName(
+ 'google.protobuf.python.internal.Factory1Enum')
+ self.assertIsInstance(enum1, descriptor.EnumDescriptor)
+ self.assertEqual(0, enum1.values_by_name['FACTORY_1_VALUE_0'].number)
+ self.assertEqual(1, enum1.values_by_name['FACTORY_1_VALUE_1'].number)
+
+ nested_enum1 = self.pool.FindEnumTypeByName(
+ 'google.protobuf.python.internal.Factory1Message.NestedFactory1Enum')
+ self.assertIsInstance(nested_enum1, descriptor.EnumDescriptor)
+ self.assertEqual(
+ 0, nested_enum1.values_by_name['NESTED_FACTORY_1_VALUE_0'].number)
+ self.assertEqual(
+ 1, nested_enum1.values_by_name['NESTED_FACTORY_1_VALUE_1'].number)
+
+ enum2 = self.pool.FindEnumTypeByName(
+ 'google.protobuf.python.internal.Factory2Enum')
+ self.assertIsInstance(enum2, descriptor.EnumDescriptor)
+ self.assertEqual(0, enum2.values_by_name['FACTORY_2_VALUE_0'].number)
+ self.assertEqual(1, enum2.values_by_name['FACTORY_2_VALUE_1'].number)
+
+ nested_enum2 = self.pool.FindEnumTypeByName(
+ 'google.protobuf.python.internal.Factory2Message.NestedFactory2Enum')
+ self.assertIsInstance(nested_enum2, descriptor.EnumDescriptor)
+ self.assertEqual(
+ 0, nested_enum2.values_by_name['NESTED_FACTORY_2_VALUE_0'].number)
+ self.assertEqual(
+ 1, nested_enum2.values_by_name['NESTED_FACTORY_2_VALUE_1'].number)
+
+ def testFindEnumTypeByNameFailure(self):
+ with self.assertRaises(KeyError):
+ self.pool.FindEnumTypeByName('Does not exist')
+
+ def testFindFieldByName(self):
+ field = self.pool.FindFieldByName(
+ 'google.protobuf.python.internal.Factory1Message.list_value')
+ self.assertEqual(field.name, 'list_value')
+ self.assertEqual(field.label, field.LABEL_REPEATED)
+ with self.assertRaises(KeyError):
+ self.pool.FindFieldByName('Does not exist')
+
+ def testFindExtensionByName(self):
+ # An extension defined in a message.
+ extension = self.pool.FindExtensionByName(
+ 'google.protobuf.python.internal.Factory2Message.one_more_field')
+ self.assertEqual(extension.name, 'one_more_field')
+ # An extension defined at file scope.
+ extension = self.pool.FindExtensionByName(
+ 'google.protobuf.python.internal.another_field')
+ self.assertEqual(extension.name, 'another_field')
+ self.assertEqual(extension.number, 1002)
+ with self.assertRaises(KeyError):
+ self.pool.FindFieldByName('Does not exist')
+
+ def testExtensionsAreNotFields(self):
+ with self.assertRaises(KeyError):
+ self.pool.FindFieldByName('google.protobuf.python.internal.another_field')
+ with self.assertRaises(KeyError):
+ self.pool.FindFieldByName(
+ 'google.protobuf.python.internal.Factory2Message.one_more_field')
+ with self.assertRaises(KeyError):
+ self.pool.FindExtensionByName(
+ 'google.protobuf.python.internal.Factory1Message.list_value')
+
+ def testUserDefinedDB(self):
+ db = descriptor_database.DescriptorDatabase()
+ self.pool = descriptor_pool.DescriptorPool(db)
+ db.Add(self.factory_test1_fd)
+ db.Add(self.factory_test2_fd)
+ self.testFindMessageTypeByName()
+
+ def testAddSerializedFile(self):
+ self.pool = descriptor_pool.DescriptorPool()
+ self.pool.AddSerializedFile(self.factory_test1_fd.SerializeToString())
+ self.pool.AddSerializedFile(self.factory_test2_fd.SerializeToString())
+ self.testFindMessageTypeByName()
+
+ def testComplexNesting(self):
+ more_messages_desc = descriptor_pb2.FileDescriptorProto.FromString(
+ more_messages_pb2.DESCRIPTOR.serialized_pb)
+ test1_desc = descriptor_pb2.FileDescriptorProto.FromString(
+ descriptor_pool_test1_pb2.DESCRIPTOR.serialized_pb)
+ test2_desc = descriptor_pb2.FileDescriptorProto.FromString(
+ descriptor_pool_test2_pb2.DESCRIPTOR.serialized_pb)
+ self.pool.Add(more_messages_desc)
+ self.pool.Add(test1_desc)
+ self.pool.Add(test2_desc)
+ TEST1_FILE.CheckFile(self, self.pool)
+ TEST2_FILE.CheckFile(self, self.pool)
+
+
+ def testEnumDefaultValue(self):
+ """Test the default value of enums which don't start at zero."""
+ def _CheckDefaultValue(file_descriptor):
+ default_value = (file_descriptor
+ .message_types_by_name['DescriptorPoolTest1']
+ .fields_by_name['nested_enum']
+ .default_value)
+ self.assertEqual(default_value,
+ descriptor_pool_test1_pb2.DescriptorPoolTest1.BETA)
+ # First check what the generated descriptor contains.
+ _CheckDefaultValue(descriptor_pool_test1_pb2.DESCRIPTOR)
+ # Then check the generated pool. Normally this is the same descriptor.
+ file_descriptor = symbol_database.Default().pool.FindFileByName(
+ 'google/protobuf/internal/descriptor_pool_test1.proto')
+ self.assertIs(file_descriptor, descriptor_pool_test1_pb2.DESCRIPTOR)
+ _CheckDefaultValue(file_descriptor)
+
+ # Then check the dynamic pool and its internal DescriptorDatabase.
+ descriptor_proto = descriptor_pb2.FileDescriptorProto.FromString(
+ descriptor_pool_test1_pb2.DESCRIPTOR.serialized_pb)
+ self.pool.Add(descriptor_proto)
+ # And do the same check as above
+ file_descriptor = self.pool.FindFileByName(
+ 'google/protobuf/internal/descriptor_pool_test1.proto')
+ _CheckDefaultValue(file_descriptor)
+
+ def testDefaultValueForCustomMessages(self):
+ """Check the value returned by non-existent fields."""
+ def _CheckValueAndType(value, expected_value, expected_type):
+ self.assertEqual(value, expected_value)
+ self.assertIsInstance(value, expected_type)
+
+ def _CheckDefaultValues(msg):
+ try:
+ int64 = long
+ except NameError: # Python3
+ int64 = int
+ try:
+ unicode_type = unicode
+ except NameError: # Python3
+ unicode_type = str
+ _CheckValueAndType(msg.optional_int32, 0, int)
+ _CheckValueAndType(msg.optional_uint64, 0, (int64, int))
+ _CheckValueAndType(msg.optional_float, 0, (float, int))
+ _CheckValueAndType(msg.optional_double, 0, (float, int))
+ _CheckValueAndType(msg.optional_bool, False, bool)
+ _CheckValueAndType(msg.optional_string, u'', unicode_type)
+ _CheckValueAndType(msg.optional_bytes, b'', bytes)
+ _CheckValueAndType(msg.optional_nested_enum, msg.FOO, int)
+ # First for the generated message
+ _CheckDefaultValues(unittest_pb2.TestAllTypes())
+ # Then for a message built with from the DescriptorPool.
+ pool = descriptor_pool.DescriptorPool()
+ pool.Add(descriptor_pb2.FileDescriptorProto.FromString(
+ unittest_import_public_pb2.DESCRIPTOR.serialized_pb))
+ pool.Add(descriptor_pb2.FileDescriptorProto.FromString(
+ unittest_import_pb2.DESCRIPTOR.serialized_pb))
+ pool.Add(descriptor_pb2.FileDescriptorProto.FromString(
+ unittest_pb2.DESCRIPTOR.serialized_pb))
+ message_class = message_factory.MessageFactory(pool).GetPrototype(
+ pool.FindMessageTypeByName(
+ unittest_pb2.TestAllTypes.DESCRIPTOR.full_name))
+ _CheckDefaultValues(message_class())
+
+
+class ProtoFile(object):
+
+ def __init__(self, name, package, messages, dependencies=None,
+ public_dependencies=None):
+ self.name = name
+ self.package = package
+ self.messages = messages
+ self.dependencies = dependencies or []
+ self.public_dependencies = public_dependencies or []
+
+ def CheckFile(self, test, pool):
+ file_desc = pool.FindFileByName(self.name)
+ test.assertEqual(self.name, file_desc.name)
+ test.assertEqual(self.package, file_desc.package)
+ dependencies_names = [f.name for f in file_desc.dependencies]
+ test.assertEqual(self.dependencies, dependencies_names)
+ public_dependencies_names = [f.name for f in file_desc.public_dependencies]
+ test.assertEqual(self.public_dependencies, public_dependencies_names)
+ for name, msg_type in self.messages.items():
+ msg_type.CheckType(test, None, name, file_desc)
+
+
+class EnumType(object):
+
+ def __init__(self, values):
+ self.values = values
+
+ def CheckType(self, test, msg_desc, name, file_desc):
+ enum_desc = msg_desc.enum_types_by_name[name]
+ test.assertEqual(name, enum_desc.name)
+ expected_enum_full_name = '.'.join([msg_desc.full_name, name])
+ test.assertEqual(expected_enum_full_name, enum_desc.full_name)
+ test.assertEqual(msg_desc, enum_desc.containing_type)
+ test.assertEqual(file_desc, enum_desc.file)
+ for index, (value, number) in enumerate(self.values):
+ value_desc = enum_desc.values_by_name[value]
+ test.assertEqual(value, value_desc.name)
+ test.assertEqual(index, value_desc.index)
+ test.assertEqual(number, value_desc.number)
+ test.assertEqual(enum_desc, value_desc.type)
+ test.assertIn(value, msg_desc.enum_values_by_name)
+
+
+class MessageType(object):
+
+ def __init__(self, type_dict, field_list, is_extendable=False,
+ extensions=None):
+ self.type_dict = type_dict
+ self.field_list = field_list
+ self.is_extendable = is_extendable
+ self.extensions = extensions or []
+
+ def CheckType(self, test, containing_type_desc, name, file_desc):
+ if containing_type_desc is None:
+ desc = file_desc.message_types_by_name[name]
+ expected_full_name = '.'.join([file_desc.package, name])
+ else:
+ desc = containing_type_desc.nested_types_by_name[name]
+ expected_full_name = '.'.join([containing_type_desc.full_name, name])
+
+ test.assertEqual(name, desc.name)
+ test.assertEqual(expected_full_name, desc.full_name)
+ test.assertEqual(containing_type_desc, desc.containing_type)
+ test.assertEqual(desc.file, file_desc)
+ test.assertEqual(self.is_extendable, desc.is_extendable)
+ for name, subtype in self.type_dict.items():
+ subtype.CheckType(test, desc, name, file_desc)
+
+ for index, (name, field) in enumerate(self.field_list):
+ field.CheckField(test, desc, name, index)
+
+ for index, (name, field) in enumerate(self.extensions):
+ field.CheckField(test, desc, name, index)
+
+
+class EnumField(object):
+
+ def __init__(self, number, type_name, default_value):
+ self.number = number
+ self.type_name = type_name
+ self.default_value = default_value
+
+ def CheckField(self, test, msg_desc, name, index):
+ field_desc = msg_desc.fields_by_name[name]
+ enum_desc = msg_desc.enum_types_by_name[self.type_name]
+ test.assertEqual(name, field_desc.name)
+ expected_field_full_name = '.'.join([msg_desc.full_name, name])
+ test.assertEqual(expected_field_full_name, field_desc.full_name)
+ test.assertEqual(index, field_desc.index)
+ test.assertEqual(self.number, field_desc.number)
+ test.assertEqual(descriptor.FieldDescriptor.TYPE_ENUM, field_desc.type)
+ test.assertEqual(descriptor.FieldDescriptor.CPPTYPE_ENUM,
+ field_desc.cpp_type)
+ test.assertTrue(field_desc.has_default_value)
+ test.assertEqual(enum_desc.values_by_name[self.default_value].number,
+ field_desc.default_value)
+ test.assertEqual(msg_desc, field_desc.containing_type)
+ test.assertEqual(enum_desc, field_desc.enum_type)
+
+
+class MessageField(object):
+
+ def __init__(self, number, type_name):
+ self.number = number
+ self.type_name = type_name
+
+ def CheckField(self, test, msg_desc, name, index):
+ field_desc = msg_desc.fields_by_name[name]
+ field_type_desc = msg_desc.nested_types_by_name[self.type_name]
+ test.assertEqual(name, field_desc.name)
+ expected_field_full_name = '.'.join([msg_desc.full_name, name])
+ test.assertEqual(expected_field_full_name, field_desc.full_name)
+ test.assertEqual(index, field_desc.index)
+ test.assertEqual(self.number, field_desc.number)
+ test.assertEqual(descriptor.FieldDescriptor.TYPE_MESSAGE, field_desc.type)
+ test.assertEqual(descriptor.FieldDescriptor.CPPTYPE_MESSAGE,
+ field_desc.cpp_type)
+ test.assertFalse(field_desc.has_default_value)
+ test.assertEqual(msg_desc, field_desc.containing_type)
+ test.assertEqual(field_type_desc, field_desc.message_type)
+
+
+class StringField(object):
+
+ def __init__(self, number, default_value):
+ self.number = number
+ self.default_value = default_value
+
+ def CheckField(self, test, msg_desc, name, index):
+ field_desc = msg_desc.fields_by_name[name]
+ test.assertEqual(name, field_desc.name)
+ expected_field_full_name = '.'.join([msg_desc.full_name, name])
+ test.assertEqual(expected_field_full_name, field_desc.full_name)
+ test.assertEqual(index, field_desc.index)
+ test.assertEqual(self.number, field_desc.number)
+ test.assertEqual(descriptor.FieldDescriptor.TYPE_STRING, field_desc.type)
+ test.assertEqual(descriptor.FieldDescriptor.CPPTYPE_STRING,
+ field_desc.cpp_type)
+ test.assertTrue(field_desc.has_default_value)
+ test.assertEqual(self.default_value, field_desc.default_value)
+
+
+class ExtensionField(object):
+
+ def __init__(self, number, extended_type):
+ self.number = number
+ self.extended_type = extended_type
+
+ def CheckField(self, test, msg_desc, name, index):
+ field_desc = msg_desc.extensions_by_name[name]
+ test.assertEqual(name, field_desc.name)
+ expected_field_full_name = '.'.join([msg_desc.full_name, name])
+ test.assertEqual(expected_field_full_name, field_desc.full_name)
+ test.assertEqual(self.number, field_desc.number)
+ test.assertEqual(index, field_desc.index)
+ test.assertEqual(descriptor.FieldDescriptor.TYPE_MESSAGE, field_desc.type)
+ test.assertEqual(descriptor.FieldDescriptor.CPPTYPE_MESSAGE,
+ field_desc.cpp_type)
+ test.assertFalse(field_desc.has_default_value)
+ test.assertTrue(field_desc.is_extension)
+ test.assertEqual(msg_desc, field_desc.extension_scope)
+ test.assertEqual(msg_desc, field_desc.message_type)
+ test.assertEqual(self.extended_type, field_desc.containing_type.name)
+
+
+class AddDescriptorTest(unittest.TestCase):
+
+ def _TestMessage(self, prefix):
+ pool = descriptor_pool.DescriptorPool()
+ pool.AddDescriptor(unittest_pb2.TestAllTypes.DESCRIPTOR)
+ self.assertEqual(
+ 'protobuf_unittest.TestAllTypes',
+ pool.FindMessageTypeByName(
+ prefix + 'protobuf_unittest.TestAllTypes').full_name)
+
+ # AddDescriptor is not recursive.
+ with self.assertRaises(KeyError):
+ pool.FindMessageTypeByName(
+ prefix + 'protobuf_unittest.TestAllTypes.NestedMessage')
+
+ pool.AddDescriptor(unittest_pb2.TestAllTypes.NestedMessage.DESCRIPTOR)
+ self.assertEqual(
+ 'protobuf_unittest.TestAllTypes.NestedMessage',
+ pool.FindMessageTypeByName(
+ prefix + 'protobuf_unittest.TestAllTypes.NestedMessage').full_name)
+
+ # Files are implicitly also indexed when messages are added.
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ pool.FindFileByName(
+ 'google/protobuf/unittest.proto').name)
+
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ pool.FindFileContainingSymbol(
+ prefix + 'protobuf_unittest.TestAllTypes.NestedMessage').name)
+
+ @unittest.skipIf(api_implementation.Type() == 'cpp',
+ 'With the cpp implementation, Add() must be called first')
+ def testMessage(self):
+ self._TestMessage('')
+ self._TestMessage('.')
+
+ def _TestEnum(self, prefix):
+ pool = descriptor_pool.DescriptorPool()
+ pool.AddEnumDescriptor(unittest_pb2.ForeignEnum.DESCRIPTOR)
+ self.assertEqual(
+ 'protobuf_unittest.ForeignEnum',
+ pool.FindEnumTypeByName(
+ prefix + 'protobuf_unittest.ForeignEnum').full_name)
+
+ # AddEnumDescriptor is not recursive.
+ with self.assertRaises(KeyError):
+ pool.FindEnumTypeByName(
+ prefix + 'protobuf_unittest.ForeignEnum.NestedEnum')
+
+ pool.AddEnumDescriptor(unittest_pb2.TestAllTypes.NestedEnum.DESCRIPTOR)
+ self.assertEqual(
+ 'protobuf_unittest.TestAllTypes.NestedEnum',
+ pool.FindEnumTypeByName(
+ prefix + 'protobuf_unittest.TestAllTypes.NestedEnum').full_name)
+
+ # Files are implicitly also indexed when enums are added.
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ pool.FindFileByName(
+ 'google/protobuf/unittest.proto').name)
+
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ pool.FindFileContainingSymbol(
+ prefix + 'protobuf_unittest.TestAllTypes.NestedEnum').name)
+
+ @unittest.skipIf(api_implementation.Type() == 'cpp',
+ 'With the cpp implementation, Add() must be called first')
+ def testEnum(self):
+ self._TestEnum('')
+ self._TestEnum('.')
+
+ @unittest.skipIf(api_implementation.Type() == 'cpp',
+ 'With the cpp implementation, Add() must be called first')
+ def testFile(self):
+ pool = descriptor_pool.DescriptorPool()
+ pool.AddFileDescriptor(unittest_pb2.DESCRIPTOR)
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ pool.FindFileByName(
+ 'google/protobuf/unittest.proto').name)
+
+ # AddFileDescriptor is not recursive; messages and enums within files must
+ # be explicitly registered.
+ with self.assertRaises(KeyError):
+ pool.FindFileContainingSymbol(
+ 'protobuf_unittest.TestAllTypes')
+
+ def testEmptyDescriptorPool(self):
+ # Check that an empty DescriptorPool() contains no messages.
+ pool = descriptor_pool.DescriptorPool()
+ proto_file_name = descriptor_pb2.DESCRIPTOR.name
+ self.assertRaises(KeyError, pool.FindFileByName, proto_file_name)
+ # Add the above file to the pool
+ file_descriptor = descriptor_pb2.FileDescriptorProto()
+ descriptor_pb2.DESCRIPTOR.CopyToProto(file_descriptor)
+ pool.Add(file_descriptor)
+ # Now it exists.
+ self.assertTrue(pool.FindFileByName(proto_file_name))
+
+ def testCustomDescriptorPool(self):
+ # Create a new pool, and add a file descriptor.
+ pool = descriptor_pool.DescriptorPool()
+ file_desc = descriptor_pb2.FileDescriptorProto(
+ name='some/file.proto', package='package')
+ file_desc.message_type.add(name='Message')
+ pool.Add(file_desc)
+ self.assertEqual(pool.FindFileByName('some/file.proto').name,
+ 'some/file.proto')
+ self.assertEqual(pool.FindMessageTypeByName('package.Message').name,
+ 'Message')
+
+ def testFileDescriptorOptionsWithCustomDescriptorPool(self):
+ # Create a descriptor pool, and add a new FileDescriptorProto to it.
+ pool = descriptor_pool.DescriptorPool()
+ file_name = 'file_descriptor_options_with_custom_descriptor_pool.proto'
+ file_descriptor_proto = descriptor_pb2.FileDescriptorProto(name=file_name)
+ extension_id = file_options_test_pb2.foo_options
+ file_descriptor_proto.options.Extensions[extension_id].foo_name = 'foo'
+ pool.Add(file_descriptor_proto)
+ # The options set on the FileDescriptorProto should be available in the
+ # descriptor even if they contain extensions that cannot be deserialized
+ # using the pool.
+ file_descriptor = pool.FindFileByName(file_name)
+ options = file_descriptor.GetOptions()
+ self.assertEqual('foo', options.Extensions[extension_id].foo_name)
+ # The object returned by GetOptions() is cached.
+ self.assertIs(options, file_descriptor.GetOptions())
+
+
+@unittest.skipIf(
+ api_implementation.Type() != 'cpp',
+ 'default_pool is only supported by the C++ implementation')
+class DefaultPoolTest(unittest.TestCase):
+
+ def testFindMethods(self):
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf.pyext import _message
+ pool = _message.default_pool
+ self.assertIs(
+ pool.FindFileByName('google/protobuf/unittest.proto'),
+ unittest_pb2.DESCRIPTOR)
+ self.assertIs(
+ pool.FindMessageTypeByName('protobuf_unittest.TestAllTypes'),
+ unittest_pb2.TestAllTypes.DESCRIPTOR)
+ self.assertIs(
+ pool.FindFieldByName('protobuf_unittest.TestAllTypes.optional_int32'),
+ unittest_pb2.TestAllTypes.DESCRIPTOR.fields_by_name['optional_int32'])
+ self.assertIs(
+ pool.FindExtensionByName('protobuf_unittest.optional_int32_extension'),
+ unittest_pb2.DESCRIPTOR.extensions_by_name['optional_int32_extension'])
+ self.assertIs(
+ pool.FindEnumTypeByName('protobuf_unittest.ForeignEnum'),
+ unittest_pb2.ForeignEnum.DESCRIPTOR)
+ self.assertIs(
+ pool.FindOneofByName('protobuf_unittest.TestAllTypes.oneof_field'),
+ unittest_pb2.TestAllTypes.DESCRIPTOR.oneofs_by_name['oneof_field'])
+
+ def testAddFileDescriptor(self):
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf.pyext import _message
+ pool = _message.default_pool
+ file_desc = descriptor_pb2.FileDescriptorProto(name='some/file.proto')
+ pool.Add(file_desc)
+ pool.AddSerializedFile(file_desc.SerializeToString())
+
+
+TEST1_FILE = ProtoFile(
+ 'google/protobuf/internal/descriptor_pool_test1.proto',
+ 'google.protobuf.python.internal',
+ {
+ 'DescriptorPoolTest1': MessageType({
+ 'NestedEnum': EnumType([('ALPHA', 1), ('BETA', 2)]),
+ 'NestedMessage': MessageType({
+ 'NestedEnum': EnumType([('EPSILON', 5), ('ZETA', 6)]),
+ 'DeepNestedMessage': MessageType({
+ 'NestedEnum': EnumType([('ETA', 7), ('THETA', 8)]),
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'ETA')),
+ ('nested_field', StringField(2, 'theta')),
+ ]),
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'ZETA')),
+ ('nested_field', StringField(2, 'beta')),
+ ('deep_nested_message', MessageField(3, 'DeepNestedMessage')),
+ ])
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'BETA')),
+ ('nested_message', MessageField(2, 'NestedMessage')),
+ ], is_extendable=True),
+
+ 'DescriptorPoolTest2': MessageType({
+ 'NestedEnum': EnumType([('GAMMA', 3), ('DELTA', 4)]),
+ 'NestedMessage': MessageType({
+ 'NestedEnum': EnumType([('IOTA', 9), ('KAPPA', 10)]),
+ 'DeepNestedMessage': MessageType({
+ 'NestedEnum': EnumType([('LAMBDA', 11), ('MU', 12)]),
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'MU')),
+ ('nested_field', StringField(2, 'lambda')),
+ ]),
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'IOTA')),
+ ('nested_field', StringField(2, 'delta')),
+ ('deep_nested_message', MessageField(3, 'DeepNestedMessage')),
+ ])
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'GAMMA')),
+ ('nested_message', MessageField(2, 'NestedMessage')),
+ ]),
+ })
+
+
+TEST2_FILE = ProtoFile(
+ 'google/protobuf/internal/descriptor_pool_test2.proto',
+ 'google.protobuf.python.internal',
+ {
+ 'DescriptorPoolTest3': MessageType({
+ 'NestedEnum': EnumType([('NU', 13), ('XI', 14)]),
+ 'NestedMessage': MessageType({
+ 'NestedEnum': EnumType([('OMICRON', 15), ('PI', 16)]),
+ 'DeepNestedMessage': MessageType({
+ 'NestedEnum': EnumType([('RHO', 17), ('SIGMA', 18)]),
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'RHO')),
+ ('nested_field', StringField(2, 'sigma')),
+ ]),
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'PI')),
+ ('nested_field', StringField(2, 'nu')),
+ ('deep_nested_message', MessageField(3, 'DeepNestedMessage')),
+ ])
+ }, [
+ ('nested_enum', EnumField(1, 'NestedEnum', 'XI')),
+ ('nested_message', MessageField(2, 'NestedMessage')),
+ ], extensions=[
+ ('descriptor_pool_test',
+ ExtensionField(1001, 'DescriptorPoolTest1')),
+ ]),
+ },
+ dependencies=['google/protobuf/internal/descriptor_pool_test1.proto',
+ 'google/protobuf/internal/more_messages.proto'],
+ public_dependencies=['google/protobuf/internal/more_messages.proto'])
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test1.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test1.proto
new file mode 100644
index 0000000000..00816b78ec
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test1.proto
@@ -0,0 +1,96 @@
+// 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.
+
+syntax = "proto2";
+
+package google.protobuf.python.internal;
+
+
+message DescriptorPoolTest1 {
+ extensions 1000 to max;
+
+ enum NestedEnum {
+ ALPHA = 1;
+ BETA = 2;
+ }
+
+ optional NestedEnum nested_enum = 1 [default = BETA];
+
+ message NestedMessage {
+ enum NestedEnum {
+ EPSILON = 5;
+ ZETA = 6;
+ }
+ optional NestedEnum nested_enum = 1 [default = ZETA];
+ optional string nested_field = 2 [default = "beta"];
+ optional DeepNestedMessage deep_nested_message = 3;
+
+ message DeepNestedMessage {
+ enum NestedEnum {
+ ETA = 7;
+ THETA = 8;
+ }
+ optional NestedEnum nested_enum = 1 [default = ETA];
+ optional string nested_field = 2 [default = "theta"];
+ }
+ }
+
+ optional NestedMessage nested_message = 2;
+}
+
+message DescriptorPoolTest2 {
+ enum NestedEnum {
+ GAMMA = 3;
+ DELTA = 4;
+ }
+
+ optional NestedEnum nested_enum = 1 [default = GAMMA];
+
+ message NestedMessage {
+ enum NestedEnum {
+ IOTA = 9;
+ KAPPA = 10;
+ }
+ optional NestedEnum nested_enum = 1 [default = IOTA];
+ optional string nested_field = 2 [default = "delta"];
+ optional DeepNestedMessage deep_nested_message = 3;
+
+ message DeepNestedMessage {
+ enum NestedEnum {
+ LAMBDA = 11;
+ MU = 12;
+ }
+ optional NestedEnum nested_enum = 1 [default = MU];
+ optional string nested_field = 2 [default = "lambda"];
+ }
+ }
+
+ optional NestedMessage nested_message = 2;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test2.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test2.proto
new file mode 100644
index 0000000000..a218eccb9f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_pool_test2.proto
@@ -0,0 +1,73 @@
+// 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.
+
+syntax = "proto2";
+
+package google.protobuf.python.internal;
+
+import "google/protobuf/internal/descriptor_pool_test1.proto";
+import public "google/protobuf/internal/more_messages.proto";
+
+
+message DescriptorPoolTest3 {
+
+ extend DescriptorPoolTest1 {
+ optional DescriptorPoolTest3 descriptor_pool_test = 1001;
+ }
+
+ enum NestedEnum {
+ NU = 13;
+ XI = 14;
+ }
+
+ optional NestedEnum nested_enum = 1 [default = XI];
+
+ message NestedMessage {
+ enum NestedEnum {
+ OMICRON = 15;
+ PI = 16;
+ }
+ optional NestedEnum nested_enum = 1 [default = PI];
+ optional string nested_field = 2 [default = "nu"];
+ optional DeepNestedMessage deep_nested_message = 3;
+
+ message DeepNestedMessage {
+ enum NestedEnum {
+ RHO = 17;
+ SIGMA = 18;
+ }
+ optional NestedEnum nested_enum = 1 [default = RHO];
+ optional string nested_field = 2 [default = "sigma"];
+ }
+ }
+
+ optional NestedMessage nested_message = 2;
+}
+
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_test.py
new file mode 100755
index 0000000000..623198c8d0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/descriptor_test.py
@@ -0,0 +1,823 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Unittest for google.protobuf.internal.descriptor."""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+import sys
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import unittest_custom_options_pb2
+from google.protobuf import unittest_import_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import descriptor_pb2
+from google.protobuf.internal import api_implementation
+from google.protobuf.internal import test_util
+from google.protobuf import descriptor
+from google.protobuf import descriptor_pool
+from google.protobuf import symbol_database
+from google.protobuf import text_format
+
+
+TEST_EMPTY_MESSAGE_DESCRIPTOR_ASCII = """
+name: 'TestEmptyMessage'
+"""
+
+
+class DescriptorTest(unittest.TestCase):
+
+ def setUp(self):
+ file_proto = descriptor_pb2.FileDescriptorProto(
+ name='some/filename/some.proto',
+ package='protobuf_unittest')
+ message_proto = file_proto.message_type.add(
+ name='NestedMessage')
+ message_proto.field.add(
+ name='bb',
+ number=1,
+ type=descriptor_pb2.FieldDescriptorProto.TYPE_INT32,
+ label=descriptor_pb2.FieldDescriptorProto.LABEL_OPTIONAL)
+ enum_proto = message_proto.enum_type.add(
+ name='ForeignEnum')
+ enum_proto.value.add(name='FOREIGN_FOO', number=4)
+ enum_proto.value.add(name='FOREIGN_BAR', number=5)
+ enum_proto.value.add(name='FOREIGN_BAZ', number=6)
+
+ file_proto.message_type.add(name='ResponseMessage')
+ service_proto = file_proto.service.add(
+ name='Service')
+ method_proto = service_proto.method.add(
+ name='CallMethod',
+ input_type='.protobuf_unittest.NestedMessage',
+ output_type='.protobuf_unittest.ResponseMessage')
+
+ # Note: Calling DescriptorPool.Add() multiple times with the same file only
+ # works if the input is canonical; in particular, all type names must be
+ # fully qualified.
+ self.pool = self.GetDescriptorPool()
+ self.pool.Add(file_proto)
+ self.my_file = self.pool.FindFileByName(file_proto.name)
+ self.my_message = self.my_file.message_types_by_name[message_proto.name]
+ self.my_enum = self.my_message.enum_types_by_name[enum_proto.name]
+ self.my_service = self.my_file.services_by_name[service_proto.name]
+ self.my_method = self.my_service.methods_by_name[method_proto.name]
+
+ def GetDescriptorPool(self):
+ return symbol_database.Default().pool
+
+ def testEnumValueName(self):
+ self.assertEqual(self.my_message.EnumValueName('ForeignEnum', 4),
+ 'FOREIGN_FOO')
+
+ self.assertEqual(
+ self.my_message.enum_types_by_name[
+ 'ForeignEnum'].values_by_number[4].name,
+ self.my_message.EnumValueName('ForeignEnum', 4))
+
+ def testEnumFixups(self):
+ self.assertEqual(self.my_enum, self.my_enum.values[0].type)
+
+ def testContainingTypeFixups(self):
+ self.assertEqual(self.my_message, self.my_message.fields[0].containing_type)
+ self.assertEqual(self.my_message, self.my_enum.containing_type)
+
+ def testContainingServiceFixups(self):
+ self.assertEqual(self.my_service, self.my_method.containing_service)
+
+ def testGetOptions(self):
+ self.assertEqual(self.my_enum.GetOptions(),
+ descriptor_pb2.EnumOptions())
+ self.assertEqual(self.my_enum.values[0].GetOptions(),
+ descriptor_pb2.EnumValueOptions())
+ self.assertEqual(self.my_message.GetOptions(),
+ descriptor_pb2.MessageOptions())
+ self.assertEqual(self.my_message.fields[0].GetOptions(),
+ descriptor_pb2.FieldOptions())
+ self.assertEqual(self.my_method.GetOptions(),
+ descriptor_pb2.MethodOptions())
+ self.assertEqual(self.my_service.GetOptions(),
+ descriptor_pb2.ServiceOptions())
+
+ def testSimpleCustomOptions(self):
+ file_descriptor = unittest_custom_options_pb2.DESCRIPTOR
+ message_descriptor =\
+ unittest_custom_options_pb2.TestMessageWithCustomOptions.DESCRIPTOR
+ field_descriptor = message_descriptor.fields_by_name['field1']
+ oneof_descriptor = message_descriptor.oneofs_by_name['AnOneof']
+ enum_descriptor = message_descriptor.enum_types_by_name['AnEnum']
+ enum_value_descriptor =\
+ message_descriptor.enum_values_by_name['ANENUM_VAL2']
+ service_descriptor =\
+ unittest_custom_options_pb2.TestServiceWithCustomOptions.DESCRIPTOR
+ method_descriptor = service_descriptor.FindMethodByName('Foo')
+
+ file_options = file_descriptor.GetOptions()
+ file_opt1 = unittest_custom_options_pb2.file_opt1
+ self.assertEqual(9876543210, file_options.Extensions[file_opt1])
+ message_options = message_descriptor.GetOptions()
+ message_opt1 = unittest_custom_options_pb2.message_opt1
+ self.assertEqual(-56, message_options.Extensions[message_opt1])
+ field_options = field_descriptor.GetOptions()
+ field_opt1 = unittest_custom_options_pb2.field_opt1
+ self.assertEqual(8765432109, field_options.Extensions[field_opt1])
+ field_opt2 = unittest_custom_options_pb2.field_opt2
+ self.assertEqual(42, field_options.Extensions[field_opt2])
+ oneof_options = oneof_descriptor.GetOptions()
+ oneof_opt1 = unittest_custom_options_pb2.oneof_opt1
+ self.assertEqual(-99, oneof_options.Extensions[oneof_opt1])
+ enum_options = enum_descriptor.GetOptions()
+ enum_opt1 = unittest_custom_options_pb2.enum_opt1
+ self.assertEqual(-789, enum_options.Extensions[enum_opt1])
+ enum_value_options = enum_value_descriptor.GetOptions()
+ enum_value_opt1 = unittest_custom_options_pb2.enum_value_opt1
+ self.assertEqual(123, enum_value_options.Extensions[enum_value_opt1])
+
+ service_options = service_descriptor.GetOptions()
+ service_opt1 = unittest_custom_options_pb2.service_opt1
+ self.assertEqual(-9876543210, service_options.Extensions[service_opt1])
+ method_options = method_descriptor.GetOptions()
+ method_opt1 = unittest_custom_options_pb2.method_opt1
+ self.assertEqual(unittest_custom_options_pb2.METHODOPT1_VAL2,
+ method_options.Extensions[method_opt1])
+
+ message_descriptor = (
+ unittest_custom_options_pb2.DummyMessageContainingEnum.DESCRIPTOR)
+ self.assertTrue(file_descriptor.has_options)
+ self.assertFalse(message_descriptor.has_options)
+
+ def testDifferentCustomOptionTypes(self):
+ kint32min = -2**31
+ kint64min = -2**63
+ kint32max = 2**31 - 1
+ kint64max = 2**63 - 1
+ kuint32max = 2**32 - 1
+ kuint64max = 2**64 - 1
+
+ message_descriptor =\
+ unittest_custom_options_pb2.CustomOptionMinIntegerValues.DESCRIPTOR
+ message_options = message_descriptor.GetOptions()
+ self.assertEqual(False, message_options.Extensions[
+ unittest_custom_options_pb2.bool_opt])
+ self.assertEqual(kint32min, message_options.Extensions[
+ unittest_custom_options_pb2.int32_opt])
+ self.assertEqual(kint64min, message_options.Extensions[
+ unittest_custom_options_pb2.int64_opt])
+ self.assertEqual(0, message_options.Extensions[
+ unittest_custom_options_pb2.uint32_opt])
+ self.assertEqual(0, message_options.Extensions[
+ unittest_custom_options_pb2.uint64_opt])
+ self.assertEqual(kint32min, message_options.Extensions[
+ unittest_custom_options_pb2.sint32_opt])
+ self.assertEqual(kint64min, message_options.Extensions[
+ unittest_custom_options_pb2.sint64_opt])
+ self.assertEqual(0, message_options.Extensions[
+ unittest_custom_options_pb2.fixed32_opt])
+ self.assertEqual(0, message_options.Extensions[
+ unittest_custom_options_pb2.fixed64_opt])
+ self.assertEqual(kint32min, message_options.Extensions[
+ unittest_custom_options_pb2.sfixed32_opt])
+ self.assertEqual(kint64min, message_options.Extensions[
+ unittest_custom_options_pb2.sfixed64_opt])
+
+ message_descriptor =\
+ unittest_custom_options_pb2.CustomOptionMaxIntegerValues.DESCRIPTOR
+ message_options = message_descriptor.GetOptions()
+ self.assertEqual(True, message_options.Extensions[
+ unittest_custom_options_pb2.bool_opt])
+ self.assertEqual(kint32max, message_options.Extensions[
+ unittest_custom_options_pb2.int32_opt])
+ self.assertEqual(kint64max, message_options.Extensions[
+ unittest_custom_options_pb2.int64_opt])
+ self.assertEqual(kuint32max, message_options.Extensions[
+ unittest_custom_options_pb2.uint32_opt])
+ self.assertEqual(kuint64max, message_options.Extensions[
+ unittest_custom_options_pb2.uint64_opt])
+ self.assertEqual(kint32max, message_options.Extensions[
+ unittest_custom_options_pb2.sint32_opt])
+ self.assertEqual(kint64max, message_options.Extensions[
+ unittest_custom_options_pb2.sint64_opt])
+ self.assertEqual(kuint32max, message_options.Extensions[
+ unittest_custom_options_pb2.fixed32_opt])
+ self.assertEqual(kuint64max, message_options.Extensions[
+ unittest_custom_options_pb2.fixed64_opt])
+ self.assertEqual(kint32max, message_options.Extensions[
+ unittest_custom_options_pb2.sfixed32_opt])
+ self.assertEqual(kint64max, message_options.Extensions[
+ unittest_custom_options_pb2.sfixed64_opt])
+
+ message_descriptor =\
+ unittest_custom_options_pb2.CustomOptionOtherValues.DESCRIPTOR
+ message_options = message_descriptor.GetOptions()
+ self.assertEqual(-100, message_options.Extensions[
+ unittest_custom_options_pb2.int32_opt])
+ self.assertAlmostEqual(12.3456789, message_options.Extensions[
+ unittest_custom_options_pb2.float_opt], 6)
+ self.assertAlmostEqual(1.234567890123456789, message_options.Extensions[
+ unittest_custom_options_pb2.double_opt])
+ self.assertEqual("Hello, \"World\"", message_options.Extensions[
+ unittest_custom_options_pb2.string_opt])
+ self.assertEqual(b"Hello\0World", message_options.Extensions[
+ unittest_custom_options_pb2.bytes_opt])
+ dummy_enum = unittest_custom_options_pb2.DummyMessageContainingEnum
+ self.assertEqual(
+ dummy_enum.TEST_OPTION_ENUM_TYPE2,
+ message_options.Extensions[unittest_custom_options_pb2.enum_opt])
+
+ message_descriptor =\
+ unittest_custom_options_pb2.SettingRealsFromPositiveInts.DESCRIPTOR
+ message_options = message_descriptor.GetOptions()
+ self.assertAlmostEqual(12, message_options.Extensions[
+ unittest_custom_options_pb2.float_opt], 6)
+ self.assertAlmostEqual(154, message_options.Extensions[
+ unittest_custom_options_pb2.double_opt])
+
+ message_descriptor =\
+ unittest_custom_options_pb2.SettingRealsFromNegativeInts.DESCRIPTOR
+ message_options = message_descriptor.GetOptions()
+ self.assertAlmostEqual(-12, message_options.Extensions[
+ unittest_custom_options_pb2.float_opt], 6)
+ self.assertAlmostEqual(-154, message_options.Extensions[
+ unittest_custom_options_pb2.double_opt])
+
+ def testComplexExtensionOptions(self):
+ descriptor =\
+ unittest_custom_options_pb2.VariousComplexOptions.DESCRIPTOR
+ options = descriptor.GetOptions()
+ self.assertEqual(42, options.Extensions[
+ unittest_custom_options_pb2.complex_opt1].foo)
+ self.assertEqual(324, options.Extensions[
+ unittest_custom_options_pb2.complex_opt1].Extensions[
+ unittest_custom_options_pb2.quux])
+ self.assertEqual(876, options.Extensions[
+ unittest_custom_options_pb2.complex_opt1].Extensions[
+ unittest_custom_options_pb2.corge].qux)
+ self.assertEqual(987, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].baz)
+ self.assertEqual(654, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].Extensions[
+ unittest_custom_options_pb2.grault])
+ self.assertEqual(743, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].bar.foo)
+ self.assertEqual(1999, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].bar.Extensions[
+ unittest_custom_options_pb2.quux])
+ self.assertEqual(2008, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].bar.Extensions[
+ unittest_custom_options_pb2.corge].qux)
+ self.assertEqual(741, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].Extensions[
+ unittest_custom_options_pb2.garply].foo)
+ self.assertEqual(1998, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].Extensions[
+ unittest_custom_options_pb2.garply].Extensions[
+ unittest_custom_options_pb2.quux])
+ self.assertEqual(2121, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].Extensions[
+ unittest_custom_options_pb2.garply].Extensions[
+ unittest_custom_options_pb2.corge].qux)
+ self.assertEqual(1971, options.Extensions[
+ unittest_custom_options_pb2.ComplexOptionType2
+ .ComplexOptionType4.complex_opt4].waldo)
+ self.assertEqual(321, options.Extensions[
+ unittest_custom_options_pb2.complex_opt2].fred.waldo)
+ self.assertEqual(9, options.Extensions[
+ unittest_custom_options_pb2.complex_opt3].qux)
+ self.assertEqual(22, options.Extensions[
+ unittest_custom_options_pb2.complex_opt3].complexoptiontype5.plugh)
+ self.assertEqual(24, options.Extensions[
+ unittest_custom_options_pb2.complexopt6].xyzzy)
+
+ # Check that aggregate options were parsed and saved correctly in
+ # the appropriate descriptors.
+ def testAggregateOptions(self):
+ file_descriptor = unittest_custom_options_pb2.DESCRIPTOR
+ message_descriptor =\
+ unittest_custom_options_pb2.AggregateMessage.DESCRIPTOR
+ field_descriptor = message_descriptor.fields_by_name["fieldname"]
+ enum_descriptor = unittest_custom_options_pb2.AggregateEnum.DESCRIPTOR
+ enum_value_descriptor = enum_descriptor.values_by_name["VALUE"]
+ service_descriptor =\
+ unittest_custom_options_pb2.AggregateService.DESCRIPTOR
+ method_descriptor = service_descriptor.FindMethodByName("Method")
+
+ # Tests for the different types of data embedded in fileopt
+ file_options = file_descriptor.GetOptions().Extensions[
+ unittest_custom_options_pb2.fileopt]
+ self.assertEqual(100, file_options.i)
+ self.assertEqual("FileAnnotation", file_options.s)
+ self.assertEqual("NestedFileAnnotation", file_options.sub.s)
+ self.assertEqual("FileExtensionAnnotation", file_options.file.Extensions[
+ unittest_custom_options_pb2.fileopt].s)
+ self.assertEqual("EmbeddedMessageSetElement", file_options.mset.Extensions[
+ unittest_custom_options_pb2.AggregateMessageSetElement
+ .message_set_extension].s)
+
+ # Simple tests for all the other types of annotations
+ self.assertEqual(
+ "MessageAnnotation",
+ message_descriptor.GetOptions().Extensions[
+ unittest_custom_options_pb2.msgopt].s)
+ self.assertEqual(
+ "FieldAnnotation",
+ field_descriptor.GetOptions().Extensions[
+ unittest_custom_options_pb2.fieldopt].s)
+ self.assertEqual(
+ "EnumAnnotation",
+ enum_descriptor.GetOptions().Extensions[
+ unittest_custom_options_pb2.enumopt].s)
+ self.assertEqual(
+ "EnumValueAnnotation",
+ enum_value_descriptor.GetOptions().Extensions[
+ unittest_custom_options_pb2.enumvalopt].s)
+ self.assertEqual(
+ "ServiceAnnotation",
+ service_descriptor.GetOptions().Extensions[
+ unittest_custom_options_pb2.serviceopt].s)
+ self.assertEqual(
+ "MethodAnnotation",
+ method_descriptor.GetOptions().Extensions[
+ unittest_custom_options_pb2.methodopt].s)
+
+ def testNestedOptions(self):
+ nested_message =\
+ unittest_custom_options_pb2.NestedOptionType.NestedMessage.DESCRIPTOR
+ self.assertEqual(1001, nested_message.GetOptions().Extensions[
+ unittest_custom_options_pb2.message_opt1])
+ nested_field = nested_message.fields_by_name["nested_field"]
+ self.assertEqual(1002, nested_field.GetOptions().Extensions[
+ unittest_custom_options_pb2.field_opt1])
+ outer_message =\
+ unittest_custom_options_pb2.NestedOptionType.DESCRIPTOR
+ nested_enum = outer_message.enum_types_by_name["NestedEnum"]
+ self.assertEqual(1003, nested_enum.GetOptions().Extensions[
+ unittest_custom_options_pb2.enum_opt1])
+ nested_enum_value = outer_message.enum_values_by_name["NESTED_ENUM_VALUE"]
+ self.assertEqual(1004, nested_enum_value.GetOptions().Extensions[
+ unittest_custom_options_pb2.enum_value_opt1])
+ nested_extension = outer_message.extensions_by_name["nested_extension"]
+ self.assertEqual(1005, nested_extension.GetOptions().Extensions[
+ unittest_custom_options_pb2.field_opt2])
+
+ def testFileDescriptorReferences(self):
+ self.assertEqual(self.my_enum.file, self.my_file)
+ self.assertEqual(self.my_message.file, self.my_file)
+
+ def testFileDescriptor(self):
+ self.assertEqual(self.my_file.name, 'some/filename/some.proto')
+ self.assertEqual(self.my_file.package, 'protobuf_unittest')
+ self.assertEqual(self.my_file.pool, self.pool)
+ # Generated modules also belong to the default pool.
+ self.assertEqual(unittest_pb2.DESCRIPTOR.pool, descriptor_pool.Default())
+
+ @unittest.skipIf(
+ api_implementation.Type() != 'cpp' or api_implementation.Version() != 2,
+ 'Immutability of descriptors is only enforced in v2 implementation')
+ def testImmutableCppDescriptor(self):
+ message_descriptor = unittest_pb2.TestAllTypes.DESCRIPTOR
+ with self.assertRaises(AttributeError):
+ message_descriptor.fields_by_name = None
+ with self.assertRaises(TypeError):
+ message_descriptor.fields_by_name['Another'] = None
+ with self.assertRaises(TypeError):
+ message_descriptor.fields.append(None)
+
+
+class NewDescriptorTest(DescriptorTest):
+ """Redo the same tests as above, but with a separate DescriptorPool."""
+
+ def GetDescriptorPool(self):
+ return descriptor_pool.DescriptorPool()
+
+
+class GeneratedDescriptorTest(unittest.TestCase):
+ """Tests for the properties of descriptors in generated code."""
+
+ def CheckMessageDescriptor(self, message_descriptor):
+ # Basic properties
+ self.assertEqual(message_descriptor.name, 'TestAllTypes')
+ self.assertEqual(message_descriptor.full_name,
+ 'protobuf_unittest.TestAllTypes')
+ # Test equality and hashability
+ self.assertEqual(message_descriptor, message_descriptor)
+ self.assertEqual(message_descriptor.fields[0].containing_type,
+ message_descriptor)
+ self.assertIn(message_descriptor, [message_descriptor])
+ self.assertIn(message_descriptor, {message_descriptor: None})
+ # Test field containers
+ self.CheckDescriptorSequence(message_descriptor.fields)
+ self.CheckDescriptorMapping(message_descriptor.fields_by_name)
+ self.CheckDescriptorMapping(message_descriptor.fields_by_number)
+ self.CheckDescriptorMapping(message_descriptor.fields_by_camelcase_name)
+
+ def CheckFieldDescriptor(self, field_descriptor):
+ # Basic properties
+ self.assertEqual(field_descriptor.name, 'optional_int32')
+ self.assertEqual(field_descriptor.camelcase_name, 'optionalInt32')
+ self.assertEqual(field_descriptor.full_name,
+ 'protobuf_unittest.TestAllTypes.optional_int32')
+ self.assertEqual(field_descriptor.containing_type.name, 'TestAllTypes')
+ # Test equality and hashability
+ self.assertEqual(field_descriptor, field_descriptor)
+ self.assertEqual(
+ field_descriptor.containing_type.fields_by_name['optional_int32'],
+ field_descriptor)
+ self.assertEqual(
+ field_descriptor.containing_type.fields_by_camelcase_name[
+ 'optionalInt32'],
+ field_descriptor)
+ self.assertIn(field_descriptor, [field_descriptor])
+ self.assertIn(field_descriptor, {field_descriptor: None})
+
+ def CheckDescriptorSequence(self, sequence):
+ # Verifies that a property like 'messageDescriptor.fields' has all the
+ # properties of an immutable abc.Sequence.
+ self.assertGreater(len(sequence), 0) # Sized
+ self.assertEqual(len(sequence), len(list(sequence))) # Iterable
+ item = sequence[0]
+ self.assertEqual(item, sequence[0])
+ self.assertIn(item, sequence) # Container
+ self.assertEqual(sequence.index(item), 0)
+ self.assertEqual(sequence.count(item), 1)
+ reversed_iterator = reversed(sequence)
+ self.assertEqual(list(reversed_iterator), list(sequence)[::-1])
+ self.assertRaises(StopIteration, next, reversed_iterator)
+
+ def CheckDescriptorMapping(self, mapping):
+ # Verifies that a property like 'messageDescriptor.fields' has all the
+ # properties of an immutable abc.Mapping.
+ self.assertGreater(len(mapping), 0) # Sized
+ self.assertEqual(len(mapping), len(list(mapping))) # Iterable
+ if sys.version_info >= (3,):
+ key, item = next(iter(mapping.items()))
+ else:
+ key, item = mapping.items()[0]
+ self.assertIn(key, mapping) # Container
+ self.assertEqual(mapping.get(key), item)
+ # keys(), iterkeys() &co
+ item = (next(iter(mapping.keys())), next(iter(mapping.values())))
+ self.assertEqual(item, next(iter(mapping.items())))
+ if sys.version_info < (3,):
+ def CheckItems(seq, iterator):
+ self.assertEqual(next(iterator), seq[0])
+ self.assertEqual(list(iterator), seq[1:])
+ CheckItems(mapping.keys(), mapping.iterkeys())
+ CheckItems(mapping.values(), mapping.itervalues())
+ CheckItems(mapping.items(), mapping.iteritems())
+
+ def testDescriptor(self):
+ message_descriptor = unittest_pb2.TestAllTypes.DESCRIPTOR
+ self.CheckMessageDescriptor(message_descriptor)
+ field_descriptor = message_descriptor.fields_by_name['optional_int32']
+ self.CheckFieldDescriptor(field_descriptor)
+ field_descriptor = message_descriptor.fields_by_camelcase_name[
+ 'optionalInt32']
+ self.CheckFieldDescriptor(field_descriptor)
+
+ def testCppDescriptorContainer(self):
+ # Check that the collection is still valid even if the parent disappeared.
+ enum = unittest_pb2.TestAllTypes.DESCRIPTOR.enum_types_by_name['NestedEnum']
+ values = enum.values
+ del enum
+ self.assertEqual('FOO', values[0].name)
+
+ def testCppDescriptorContainer_Iterator(self):
+ # Same test with the iterator
+ enum = unittest_pb2.TestAllTypes.DESCRIPTOR.enum_types_by_name['NestedEnum']
+ values_iter = iter(enum.values)
+ del enum
+ self.assertEqual('FOO', next(values_iter).name)
+
+
+class DescriptorCopyToProtoTest(unittest.TestCase):
+ """Tests for CopyTo functions of Descriptor."""
+
+ def _AssertProtoEqual(self, actual_proto, expected_class, expected_ascii):
+ expected_proto = expected_class()
+ text_format.Merge(expected_ascii, expected_proto)
+
+ self.assertEqual(
+ actual_proto, expected_proto,
+ 'Not equal,\nActual:\n%s\nExpected:\n%s\n'
+ % (str(actual_proto), str(expected_proto)))
+
+ def _InternalTestCopyToProto(self, desc, expected_proto_class,
+ expected_proto_ascii):
+ actual = expected_proto_class()
+ desc.CopyToProto(actual)
+ self._AssertProtoEqual(
+ actual, expected_proto_class, expected_proto_ascii)
+
+ def testCopyToProto_EmptyMessage(self):
+ self._InternalTestCopyToProto(
+ unittest_pb2.TestEmptyMessage.DESCRIPTOR,
+ descriptor_pb2.DescriptorProto,
+ TEST_EMPTY_MESSAGE_DESCRIPTOR_ASCII)
+
+ def testCopyToProto_NestedMessage(self):
+ TEST_NESTED_MESSAGE_ASCII = """
+ name: 'NestedMessage'
+ field: <
+ name: 'bb'
+ number: 1
+ label: 1 # Optional
+ type: 5 # TYPE_INT32
+ >
+ """
+
+ self._InternalTestCopyToProto(
+ unittest_pb2.TestAllTypes.NestedMessage.DESCRIPTOR,
+ descriptor_pb2.DescriptorProto,
+ TEST_NESTED_MESSAGE_ASCII)
+
+ def testCopyToProto_ForeignNestedMessage(self):
+ TEST_FOREIGN_NESTED_ASCII = """
+ name: 'TestForeignNested'
+ field: <
+ name: 'foreign_nested'
+ number: 1
+ label: 1 # Optional
+ type: 11 # TYPE_MESSAGE
+ type_name: '.protobuf_unittest.TestAllTypes.NestedMessage'
+ >
+ """
+
+ self._InternalTestCopyToProto(
+ unittest_pb2.TestForeignNested.DESCRIPTOR,
+ descriptor_pb2.DescriptorProto,
+ TEST_FOREIGN_NESTED_ASCII)
+
+ def testCopyToProto_ForeignEnum(self):
+ TEST_FOREIGN_ENUM_ASCII = """
+ name: 'ForeignEnum'
+ value: <
+ name: 'FOREIGN_FOO'
+ number: 4
+ >
+ value: <
+ name: 'FOREIGN_BAR'
+ number: 5
+ >
+ value: <
+ name: 'FOREIGN_BAZ'
+ number: 6
+ >
+ """
+
+ self._InternalTestCopyToProto(
+ unittest_pb2.ForeignEnum.DESCRIPTOR,
+ descriptor_pb2.EnumDescriptorProto,
+ TEST_FOREIGN_ENUM_ASCII)
+
+ def testCopyToProto_Options(self):
+ TEST_DEPRECATED_FIELDS_ASCII = """
+ name: 'TestDeprecatedFields'
+ field: <
+ name: 'deprecated_int32'
+ number: 1
+ label: 1 # Optional
+ type: 5 # TYPE_INT32
+ options: <
+ deprecated: true
+ >
+ >
+ """
+
+ self._InternalTestCopyToProto(
+ unittest_pb2.TestDeprecatedFields.DESCRIPTOR,
+ descriptor_pb2.DescriptorProto,
+ TEST_DEPRECATED_FIELDS_ASCII)
+
+ def testCopyToProto_AllExtensions(self):
+ TEST_EMPTY_MESSAGE_WITH_EXTENSIONS_ASCII = """
+ name: 'TestEmptyMessageWithExtensions'
+ extension_range: <
+ start: 1
+ end: 536870912
+ >
+ """
+
+ self._InternalTestCopyToProto(
+ unittest_pb2.TestEmptyMessageWithExtensions.DESCRIPTOR,
+ descriptor_pb2.DescriptorProto,
+ TEST_EMPTY_MESSAGE_WITH_EXTENSIONS_ASCII)
+
+ def testCopyToProto_SeveralExtensions(self):
+ TEST_MESSAGE_WITH_SEVERAL_EXTENSIONS_ASCII = """
+ name: 'TestMultipleExtensionRanges'
+ extension_range: <
+ start: 42
+ end: 43
+ >
+ extension_range: <
+ start: 4143
+ end: 4244
+ >
+ extension_range: <
+ start: 65536
+ end: 536870912
+ >
+ """
+
+ self._InternalTestCopyToProto(
+ unittest_pb2.TestMultipleExtensionRanges.DESCRIPTOR,
+ descriptor_pb2.DescriptorProto,
+ TEST_MESSAGE_WITH_SEVERAL_EXTENSIONS_ASCII)
+
+ # Disable this test so we can make changes to the proto file.
+ # TODO(xiaofeng): Enable this test after cl/55530659 is submitted.
+ #
+ # def testCopyToProto_FileDescriptor(self):
+ # UNITTEST_IMPORT_FILE_DESCRIPTOR_ASCII = ("""
+ # name: 'google/protobuf/unittest_import.proto'
+ # package: 'protobuf_unittest_import'
+ # dependency: 'google/protobuf/unittest_import_public.proto'
+ # message_type: <
+ # name: 'ImportMessage'
+ # field: <
+ # name: 'd'
+ # number: 1
+ # label: 1 # Optional
+ # type: 5 # TYPE_INT32
+ # >
+ # >
+ # """ +
+ # """enum_type: <
+ # name: 'ImportEnum'
+ # value: <
+ # name: 'IMPORT_FOO'
+ # number: 7
+ # >
+ # value: <
+ # name: 'IMPORT_BAR'
+ # number: 8
+ # >
+ # value: <
+ # name: 'IMPORT_BAZ'
+ # number: 9
+ # >
+ # >
+ # options: <
+ # java_package: 'com.google.protobuf.test'
+ # optimize_for: 1 # SPEED
+ # >
+ # public_dependency: 0
+ # """)
+ # self._InternalTestCopyToProto(
+ # unittest_import_pb2.DESCRIPTOR,
+ # descriptor_pb2.FileDescriptorProto,
+ # UNITTEST_IMPORT_FILE_DESCRIPTOR_ASCII)
+
+ def testCopyToProto_ServiceDescriptor(self):
+ TEST_SERVICE_ASCII = """
+ name: 'TestService'
+ method: <
+ name: 'Foo'
+ input_type: '.protobuf_unittest.FooRequest'
+ output_type: '.protobuf_unittest.FooResponse'
+ >
+ method: <
+ name: 'Bar'
+ input_type: '.protobuf_unittest.BarRequest'
+ output_type: '.protobuf_unittest.BarResponse'
+ >
+ """
+ # TODO(rocking): enable this test after the proto descriptor change is
+ # checked in.
+ #self._InternalTestCopyToProto(
+ # unittest_pb2.TestService.DESCRIPTOR,
+ # descriptor_pb2.ServiceDescriptorProto,
+ # TEST_SERVICE_ASCII)
+
+
+class MakeDescriptorTest(unittest.TestCase):
+
+ def testMakeDescriptorWithNestedFields(self):
+ file_descriptor_proto = descriptor_pb2.FileDescriptorProto()
+ file_descriptor_proto.name = 'Foo2'
+ message_type = file_descriptor_proto.message_type.add()
+ message_type.name = file_descriptor_proto.name
+ nested_type = message_type.nested_type.add()
+ nested_type.name = 'Sub'
+ enum_type = nested_type.enum_type.add()
+ enum_type.name = 'FOO'
+ enum_type_val = enum_type.value.add()
+ enum_type_val.name = 'BAR'
+ enum_type_val.number = 3
+ field = message_type.field.add()
+ field.number = 1
+ field.name = 'uint64_field'
+ field.label = descriptor.FieldDescriptor.LABEL_REQUIRED
+ field.type = descriptor.FieldDescriptor.TYPE_UINT64
+ field = message_type.field.add()
+ field.number = 2
+ field.name = 'nested_message_field'
+ field.label = descriptor.FieldDescriptor.LABEL_REQUIRED
+ field.type = descriptor.FieldDescriptor.TYPE_MESSAGE
+ field.type_name = 'Sub'
+ enum_field = nested_type.field.add()
+ enum_field.number = 2
+ enum_field.name = 'bar_field'
+ enum_field.label = descriptor.FieldDescriptor.LABEL_REQUIRED
+ enum_field.type = descriptor.FieldDescriptor.TYPE_ENUM
+ enum_field.type_name = 'Foo2.Sub.FOO'
+
+ result = descriptor.MakeDescriptor(message_type)
+ self.assertEqual(result.fields[0].cpp_type,
+ descriptor.FieldDescriptor.CPPTYPE_UINT64)
+ self.assertEqual(result.fields[1].cpp_type,
+ descriptor.FieldDescriptor.CPPTYPE_MESSAGE)
+ self.assertEqual(result.fields[1].message_type.containing_type,
+ result)
+ self.assertEqual(result.nested_types[0].fields[0].full_name,
+ 'Foo2.Sub.bar_field')
+ self.assertEqual(result.nested_types[0].fields[0].enum_type,
+ result.nested_types[0].enum_types[0])
+
+ def testMakeDescriptorWithUnsignedIntField(self):
+ file_descriptor_proto = descriptor_pb2.FileDescriptorProto()
+ file_descriptor_proto.name = 'Foo'
+ message_type = file_descriptor_proto.message_type.add()
+ message_type.name = file_descriptor_proto.name
+ enum_type = message_type.enum_type.add()
+ enum_type.name = 'FOO'
+ enum_type_val = enum_type.value.add()
+ enum_type_val.name = 'BAR'
+ enum_type_val.number = 3
+ field = message_type.field.add()
+ field.number = 1
+ field.name = 'uint64_field'
+ field.label = descriptor.FieldDescriptor.LABEL_REQUIRED
+ field.type = descriptor.FieldDescriptor.TYPE_UINT64
+ enum_field = message_type.field.add()
+ enum_field.number = 2
+ enum_field.name = 'bar_field'
+ enum_field.label = descriptor.FieldDescriptor.LABEL_REQUIRED
+ enum_field.type = descriptor.FieldDescriptor.TYPE_ENUM
+ enum_field.type_name = 'Foo.FOO'
+
+ result = descriptor.MakeDescriptor(message_type)
+ self.assertEqual(result.fields[0].cpp_type,
+ descriptor.FieldDescriptor.CPPTYPE_UINT64)
+
+
+ def testMakeDescriptorWithOptions(self):
+ descriptor_proto = descriptor_pb2.DescriptorProto()
+ aggregate_message = unittest_custom_options_pb2.AggregateMessage
+ aggregate_message.DESCRIPTOR.CopyToProto(descriptor_proto)
+ reformed_descriptor = descriptor.MakeDescriptor(descriptor_proto)
+
+ options = reformed_descriptor.GetOptions()
+ self.assertEqual(101,
+ options.Extensions[unittest_custom_options_pb2.msgopt].i)
+
+ def testCamelcaseName(self):
+ descriptor_proto = descriptor_pb2.DescriptorProto()
+ descriptor_proto.name = 'Bar'
+ names = ['foo_foo', 'FooBar', 'fooBaz', 'fooFoo', 'foobar']
+ camelcase_names = ['fooFoo', 'fooBar', 'fooBaz', 'fooFoo', 'foobar']
+ for index in range(len(names)):
+ field = descriptor_proto.field.add()
+ field.number = index + 1
+ field.name = names[index]
+ result = descriptor.MakeDescriptor(descriptor_proto)
+ for index in range(len(camelcase_names)):
+ self.assertEqual(result.fields[index].camelcase_name,
+ camelcase_names[index])
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/encoder.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/encoder.py
new file mode 100755
index 0000000000..48ef2df31c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/encoder.py
@@ -0,0 +1,823 @@
+# 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.
+
+"""Code for encoding protocol message primitives.
+
+Contains the logic for encoding every logical protocol field type
+into one of the 5 physical wire types.
+
+This code is designed to push the Python interpreter's performance to the
+limits.
+
+The basic idea is that at startup time, for every field (i.e. every
+FieldDescriptor) we construct two functions: a "sizer" and an "encoder". The
+sizer takes a value of this field's type and computes its byte size. The
+encoder takes a writer function and a value. It encodes the value into byte
+strings and invokes the writer function to write those strings. Typically the
+writer function is the write() method of a BytesIO.
+
+We try to do as much work as possible when constructing the writer and the
+sizer rather than when calling them. In particular:
+* We copy any needed global functions to local variables, so that we do not need
+ to do costly global table lookups at runtime.
+* Similarly, we try to do any attribute lookups at startup time if possible.
+* Every field's tag is encoded to bytes at startup, since it can't change at
+ runtime.
+* Whatever component of the field size we can compute at startup, we do.
+* We *avoid* sharing code if doing so would make the code slower and not sharing
+ does not burden us too much. For example, encoders for repeated fields do
+ not just call the encoders for singular fields in a loop because this would
+ add an extra function call overhead for every loop iteration; instead, we
+ manually inline the single-value encoder into the loop.
+* If a Python function lacks a return statement, Python actually generates
+ instructions to pop the result of the last statement off the stack, push
+ None onto the stack, and then return that. If we really don't care what
+ value is returned, then we can save two instructions by returning the
+ result of the last statement. It looks funny but it helps.
+* We assume that type and bounds checking has happened at a higher level.
+"""
+
+__author__ = 'kenton@google.com (Kenton Varda)'
+
+import struct
+
+import six
+
+from google.protobuf.internal import wire_format
+
+
+# This will overflow and thus become IEEE-754 "infinity". We would use
+# "float('inf')" but it doesn't work on Windows pre-Python-2.6.
+_POS_INF = 1e10000
+_NEG_INF = -_POS_INF
+
+
+def _VarintSize(value):
+ """Compute the size of a varint value."""
+ if value <= 0x7f: return 1
+ if value <= 0x3fff: return 2
+ if value <= 0x1fffff: return 3
+ if value <= 0xfffffff: return 4
+ if value <= 0x7ffffffff: return 5
+ if value <= 0x3ffffffffff: return 6
+ if value <= 0x1ffffffffffff: return 7
+ if value <= 0xffffffffffffff: return 8
+ if value <= 0x7fffffffffffffff: return 9
+ return 10
+
+
+def _SignedVarintSize(value):
+ """Compute the size of a signed varint value."""
+ if value < 0: return 10
+ if value <= 0x7f: return 1
+ if value <= 0x3fff: return 2
+ if value <= 0x1fffff: return 3
+ if value <= 0xfffffff: return 4
+ if value <= 0x7ffffffff: return 5
+ if value <= 0x3ffffffffff: return 6
+ if value <= 0x1ffffffffffff: return 7
+ if value <= 0xffffffffffffff: return 8
+ if value <= 0x7fffffffffffffff: return 9
+ return 10
+
+
+def _TagSize(field_number):
+ """Returns the number of bytes required to serialize a tag with this field
+ number."""
+ # Just pass in type 0, since the type won't affect the tag+type size.
+ return _VarintSize(wire_format.PackTag(field_number, 0))
+
+
+# --------------------------------------------------------------------
+# In this section we define some generic sizers. Each of these functions
+# takes parameters specific to a particular field type, e.g. int32 or fixed64.
+# It returns another function which in turn takes parameters specific to a
+# particular field, e.g. the field number and whether it is repeated or packed.
+# Look at the next section to see how these are used.
+
+
+def _SimpleSizer(compute_value_size):
+ """A sizer which uses the function compute_value_size to compute the size of
+ each value. Typically compute_value_size is _VarintSize."""
+
+ def SpecificSizer(field_number, is_repeated, is_packed):
+ tag_size = _TagSize(field_number)
+ if is_packed:
+ local_VarintSize = _VarintSize
+ def PackedFieldSize(value):
+ result = 0
+ for element in value:
+ result += compute_value_size(element)
+ return result + local_VarintSize(result) + tag_size
+ return PackedFieldSize
+ elif is_repeated:
+ def RepeatedFieldSize(value):
+ result = tag_size * len(value)
+ for element in value:
+ result += compute_value_size(element)
+ return result
+ return RepeatedFieldSize
+ else:
+ def FieldSize(value):
+ return tag_size + compute_value_size(value)
+ return FieldSize
+
+ return SpecificSizer
+
+
+def _ModifiedSizer(compute_value_size, modify_value):
+ """Like SimpleSizer, but modify_value is invoked on each value before it is
+ passed to compute_value_size. modify_value is typically ZigZagEncode."""
+
+ def SpecificSizer(field_number, is_repeated, is_packed):
+ tag_size = _TagSize(field_number)
+ if is_packed:
+ local_VarintSize = _VarintSize
+ def PackedFieldSize(value):
+ result = 0
+ for element in value:
+ result += compute_value_size(modify_value(element))
+ return result + local_VarintSize(result) + tag_size
+ return PackedFieldSize
+ elif is_repeated:
+ def RepeatedFieldSize(value):
+ result = tag_size * len(value)
+ for element in value:
+ result += compute_value_size(modify_value(element))
+ return result
+ return RepeatedFieldSize
+ else:
+ def FieldSize(value):
+ return tag_size + compute_value_size(modify_value(value))
+ return FieldSize
+
+ return SpecificSizer
+
+
+def _FixedSizer(value_size):
+ """Like _SimpleSizer except for a fixed-size field. The input is the size
+ of one value."""
+
+ def SpecificSizer(field_number, is_repeated, is_packed):
+ tag_size = _TagSize(field_number)
+ if is_packed:
+ local_VarintSize = _VarintSize
+ def PackedFieldSize(value):
+ result = len(value) * value_size
+ return result + local_VarintSize(result) + tag_size
+ return PackedFieldSize
+ elif is_repeated:
+ element_size = value_size + tag_size
+ def RepeatedFieldSize(value):
+ return len(value) * element_size
+ return RepeatedFieldSize
+ else:
+ field_size = value_size + tag_size
+ def FieldSize(value):
+ return field_size
+ return FieldSize
+
+ return SpecificSizer
+
+
+# ====================================================================
+# Here we declare a sizer constructor for each field type. Each "sizer
+# constructor" is a function that takes (field_number, is_repeated, is_packed)
+# as parameters and returns a sizer, which in turn takes a field value as
+# a parameter and returns its encoded size.
+
+
+Int32Sizer = Int64Sizer = EnumSizer = _SimpleSizer(_SignedVarintSize)
+
+UInt32Sizer = UInt64Sizer = _SimpleSizer(_VarintSize)
+
+SInt32Sizer = SInt64Sizer = _ModifiedSizer(
+ _SignedVarintSize, wire_format.ZigZagEncode)
+
+Fixed32Sizer = SFixed32Sizer = FloatSizer = _FixedSizer(4)
+Fixed64Sizer = SFixed64Sizer = DoubleSizer = _FixedSizer(8)
+
+BoolSizer = _FixedSizer(1)
+
+
+def StringSizer(field_number, is_repeated, is_packed):
+ """Returns a sizer for a string field."""
+
+ tag_size = _TagSize(field_number)
+ local_VarintSize = _VarintSize
+ local_len = len
+ assert not is_packed
+ if is_repeated:
+ def RepeatedFieldSize(value):
+ result = tag_size * len(value)
+ for element in value:
+ l = local_len(element.encode('utf-8'))
+ result += local_VarintSize(l) + l
+ return result
+ return RepeatedFieldSize
+ else:
+ def FieldSize(value):
+ l = local_len(value.encode('utf-8'))
+ return tag_size + local_VarintSize(l) + l
+ return FieldSize
+
+
+def BytesSizer(field_number, is_repeated, is_packed):
+ """Returns a sizer for a bytes field."""
+
+ tag_size = _TagSize(field_number)
+ local_VarintSize = _VarintSize
+ local_len = len
+ assert not is_packed
+ if is_repeated:
+ def RepeatedFieldSize(value):
+ result = tag_size * len(value)
+ for element in value:
+ l = local_len(element)
+ result += local_VarintSize(l) + l
+ return result
+ return RepeatedFieldSize
+ else:
+ def FieldSize(value):
+ l = local_len(value)
+ return tag_size + local_VarintSize(l) + l
+ return FieldSize
+
+
+def GroupSizer(field_number, is_repeated, is_packed):
+ """Returns a sizer for a group field."""
+
+ tag_size = _TagSize(field_number) * 2
+ assert not is_packed
+ if is_repeated:
+ def RepeatedFieldSize(value):
+ result = tag_size * len(value)
+ for element in value:
+ result += element.ByteSize()
+ return result
+ return RepeatedFieldSize
+ else:
+ def FieldSize(value):
+ return tag_size + value.ByteSize()
+ return FieldSize
+
+
+def MessageSizer(field_number, is_repeated, is_packed):
+ """Returns a sizer for a message field."""
+
+ tag_size = _TagSize(field_number)
+ local_VarintSize = _VarintSize
+ assert not is_packed
+ if is_repeated:
+ def RepeatedFieldSize(value):
+ result = tag_size * len(value)
+ for element in value:
+ l = element.ByteSize()
+ result += local_VarintSize(l) + l
+ return result
+ return RepeatedFieldSize
+ else:
+ def FieldSize(value):
+ l = value.ByteSize()
+ return tag_size + local_VarintSize(l) + l
+ return FieldSize
+
+
+# --------------------------------------------------------------------
+# MessageSet is special: it needs custom logic to compute its size properly.
+
+
+def MessageSetItemSizer(field_number):
+ """Returns a sizer for extensions of MessageSet.
+
+ The message set message looks like this:
+ message MessageSet {
+ repeated group Item = 1 {
+ required int32 type_id = 2;
+ required string message = 3;
+ }
+ }
+ """
+ static_size = (_TagSize(1) * 2 + _TagSize(2) + _VarintSize(field_number) +
+ _TagSize(3))
+ local_VarintSize = _VarintSize
+
+ def FieldSize(value):
+ l = value.ByteSize()
+ return static_size + local_VarintSize(l) + l
+
+ return FieldSize
+
+
+# --------------------------------------------------------------------
+# Map is special: it needs custom logic to compute its size properly.
+
+
+def MapSizer(field_descriptor):
+ """Returns a sizer for a map field."""
+
+ # Can't look at field_descriptor.message_type._concrete_class because it may
+ # not have been initialized yet.
+ message_type = field_descriptor.message_type
+ message_sizer = MessageSizer(field_descriptor.number, False, False)
+
+ def FieldSize(map_value):
+ total = 0
+ for key in map_value:
+ value = map_value[key]
+ # It's wasteful to create the messages and throw them away one second
+ # later since we'll do the same for the actual encode. But there's not an
+ # obvious way to avoid this within the current design without tons of code
+ # duplication.
+ entry_msg = message_type._concrete_class(key=key, value=value)
+ total += message_sizer(entry_msg)
+ return total
+
+ return FieldSize
+
+# ====================================================================
+# Encoders!
+
+
+def _VarintEncoder():
+ """Return an encoder for a basic varint value (does not include tag)."""
+
+ def EncodeVarint(write, value):
+ bits = value & 0x7f
+ value >>= 7
+ while value:
+ write(six.int2byte(0x80|bits))
+ bits = value & 0x7f
+ value >>= 7
+ return write(six.int2byte(bits))
+
+ return EncodeVarint
+
+
+def _SignedVarintEncoder():
+ """Return an encoder for a basic signed varint value (does not include
+ tag)."""
+
+ def EncodeSignedVarint(write, value):
+ if value < 0:
+ value += (1 << 64)
+ bits = value & 0x7f
+ value >>= 7
+ while value:
+ write(six.int2byte(0x80|bits))
+ bits = value & 0x7f
+ value >>= 7
+ return write(six.int2byte(bits))
+
+ return EncodeSignedVarint
+
+
+_EncodeVarint = _VarintEncoder()
+_EncodeSignedVarint = _SignedVarintEncoder()
+
+
+def _VarintBytes(value):
+ """Encode the given integer as a varint and return the bytes. This is only
+ called at startup time so it doesn't need to be fast."""
+
+ pieces = []
+ _EncodeVarint(pieces.append, value)
+ return b"".join(pieces)
+
+
+def TagBytes(field_number, wire_type):
+ """Encode the given tag and return the bytes. Only called at startup."""
+
+ return _VarintBytes(wire_format.PackTag(field_number, wire_type))
+
+# --------------------------------------------------------------------
+# As with sizers (see above), we have a number of common encoder
+# implementations.
+
+
+def _SimpleEncoder(wire_type, encode_value, compute_value_size):
+ """Return a constructor for an encoder for fields of a particular type.
+
+ Args:
+ wire_type: The field's wire type, for encoding tags.
+ encode_value: A function which encodes an individual value, e.g.
+ _EncodeVarint().
+ compute_value_size: A function which computes the size of an individual
+ value, e.g. _VarintSize().
+ """
+
+ def SpecificEncoder(field_number, is_repeated, is_packed):
+ if is_packed:
+ tag_bytes = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ def EncodePackedField(write, value):
+ write(tag_bytes)
+ size = 0
+ for element in value:
+ size += compute_value_size(element)
+ local_EncodeVarint(write, size)
+ for element in value:
+ encode_value(write, element)
+ return EncodePackedField
+ elif is_repeated:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(tag_bytes)
+ encode_value(write, element)
+ return EncodeRepeatedField
+ else:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeField(write, value):
+ write(tag_bytes)
+ return encode_value(write, value)
+ return EncodeField
+
+ return SpecificEncoder
+
+
+def _ModifiedEncoder(wire_type, encode_value, compute_value_size, modify_value):
+ """Like SimpleEncoder but additionally invokes modify_value on every value
+ before passing it to encode_value. Usually modify_value is ZigZagEncode."""
+
+ def SpecificEncoder(field_number, is_repeated, is_packed):
+ if is_packed:
+ tag_bytes = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ def EncodePackedField(write, value):
+ write(tag_bytes)
+ size = 0
+ for element in value:
+ size += compute_value_size(modify_value(element))
+ local_EncodeVarint(write, size)
+ for element in value:
+ encode_value(write, modify_value(element))
+ return EncodePackedField
+ elif is_repeated:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(tag_bytes)
+ encode_value(write, modify_value(element))
+ return EncodeRepeatedField
+ else:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeField(write, value):
+ write(tag_bytes)
+ return encode_value(write, modify_value(value))
+ return EncodeField
+
+ return SpecificEncoder
+
+
+def _StructPackEncoder(wire_type, format):
+ """Return a constructor for an encoder for a fixed-width field.
+
+ Args:
+ wire_type: The field's wire type, for encoding tags.
+ format: The format string to pass to struct.pack().
+ """
+
+ value_size = struct.calcsize(format)
+
+ def SpecificEncoder(field_number, is_repeated, is_packed):
+ local_struct_pack = struct.pack
+ if is_packed:
+ tag_bytes = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ def EncodePackedField(write, value):
+ write(tag_bytes)
+ local_EncodeVarint(write, len(value) * value_size)
+ for element in value:
+ write(local_struct_pack(format, element))
+ return EncodePackedField
+ elif is_repeated:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(tag_bytes)
+ write(local_struct_pack(format, element))
+ return EncodeRepeatedField
+ else:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeField(write, value):
+ write(tag_bytes)
+ return write(local_struct_pack(format, value))
+ return EncodeField
+
+ return SpecificEncoder
+
+
+def _FloatingPointEncoder(wire_type, format):
+ """Return a constructor for an encoder for float fields.
+
+ This is like StructPackEncoder, but catches errors that may be due to
+ passing non-finite floating-point values to struct.pack, and makes a
+ second attempt to encode those values.
+
+ Args:
+ wire_type: The field's wire type, for encoding tags.
+ format: The format string to pass to struct.pack().
+ """
+
+ value_size = struct.calcsize(format)
+ if value_size == 4:
+ def EncodeNonFiniteOrRaise(write, value):
+ # Remember that the serialized form uses little-endian byte order.
+ if value == _POS_INF:
+ write(b'\x00\x00\x80\x7F')
+ elif value == _NEG_INF:
+ write(b'\x00\x00\x80\xFF')
+ elif value != value: # NaN
+ write(b'\x00\x00\xC0\x7F')
+ else:
+ raise
+ elif value_size == 8:
+ def EncodeNonFiniteOrRaise(write, value):
+ if value == _POS_INF:
+ write(b'\x00\x00\x00\x00\x00\x00\xF0\x7F')
+ elif value == _NEG_INF:
+ write(b'\x00\x00\x00\x00\x00\x00\xF0\xFF')
+ elif value != value: # NaN
+ write(b'\x00\x00\x00\x00\x00\x00\xF8\x7F')
+ else:
+ raise
+ else:
+ raise ValueError('Can\'t encode floating-point values that are '
+ '%d bytes long (only 4 or 8)' % value_size)
+
+ def SpecificEncoder(field_number, is_repeated, is_packed):
+ local_struct_pack = struct.pack
+ if is_packed:
+ tag_bytes = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ def EncodePackedField(write, value):
+ write(tag_bytes)
+ local_EncodeVarint(write, len(value) * value_size)
+ for element in value:
+ # This try/except block is going to be faster than any code that
+ # we could write to check whether element is finite.
+ try:
+ write(local_struct_pack(format, element))
+ except SystemError:
+ EncodeNonFiniteOrRaise(write, element)
+ return EncodePackedField
+ elif is_repeated:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(tag_bytes)
+ try:
+ write(local_struct_pack(format, element))
+ except SystemError:
+ EncodeNonFiniteOrRaise(write, element)
+ return EncodeRepeatedField
+ else:
+ tag_bytes = TagBytes(field_number, wire_type)
+ def EncodeField(write, value):
+ write(tag_bytes)
+ try:
+ write(local_struct_pack(format, value))
+ except SystemError:
+ EncodeNonFiniteOrRaise(write, value)
+ return EncodeField
+
+ return SpecificEncoder
+
+
+# ====================================================================
+# Here we declare an encoder constructor for each field type. These work
+# very similarly to sizer constructors, described earlier.
+
+
+Int32Encoder = Int64Encoder = EnumEncoder = _SimpleEncoder(
+ wire_format.WIRETYPE_VARINT, _EncodeSignedVarint, _SignedVarintSize)
+
+UInt32Encoder = UInt64Encoder = _SimpleEncoder(
+ wire_format.WIRETYPE_VARINT, _EncodeVarint, _VarintSize)
+
+SInt32Encoder = SInt64Encoder = _ModifiedEncoder(
+ wire_format.WIRETYPE_VARINT, _EncodeVarint, _VarintSize,
+ wire_format.ZigZagEncode)
+
+# Note that Python conveniently guarantees that when using the '<' prefix on
+# formats, they will also have the same size across all platforms (as opposed
+# to without the prefix, where their sizes depend on the C compiler's basic
+# type sizes).
+Fixed32Encoder = _StructPackEncoder(wire_format.WIRETYPE_FIXED32, '<I')
+Fixed64Encoder = _StructPackEncoder(wire_format.WIRETYPE_FIXED64, '<Q')
+SFixed32Encoder = _StructPackEncoder(wire_format.WIRETYPE_FIXED32, '<i')
+SFixed64Encoder = _StructPackEncoder(wire_format.WIRETYPE_FIXED64, '<q')
+FloatEncoder = _FloatingPointEncoder(wire_format.WIRETYPE_FIXED32, '<f')
+DoubleEncoder = _FloatingPointEncoder(wire_format.WIRETYPE_FIXED64, '<d')
+
+
+def BoolEncoder(field_number, is_repeated, is_packed):
+ """Returns an encoder for a boolean field."""
+
+ false_byte = b'\x00'
+ true_byte = b'\x01'
+ if is_packed:
+ tag_bytes = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ def EncodePackedField(write, value):
+ write(tag_bytes)
+ local_EncodeVarint(write, len(value))
+ for element in value:
+ if element:
+ write(true_byte)
+ else:
+ write(false_byte)
+ return EncodePackedField
+ elif is_repeated:
+ tag_bytes = TagBytes(field_number, wire_format.WIRETYPE_VARINT)
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(tag_bytes)
+ if element:
+ write(true_byte)
+ else:
+ write(false_byte)
+ return EncodeRepeatedField
+ else:
+ tag_bytes = TagBytes(field_number, wire_format.WIRETYPE_VARINT)
+ def EncodeField(write, value):
+ write(tag_bytes)
+ if value:
+ return write(true_byte)
+ return write(false_byte)
+ return EncodeField
+
+
+def StringEncoder(field_number, is_repeated, is_packed):
+ """Returns an encoder for a string field."""
+
+ tag = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ local_len = len
+ assert not is_packed
+ if is_repeated:
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ encoded = element.encode('utf-8')
+ write(tag)
+ local_EncodeVarint(write, local_len(encoded))
+ write(encoded)
+ return EncodeRepeatedField
+ else:
+ def EncodeField(write, value):
+ encoded = value.encode('utf-8')
+ write(tag)
+ local_EncodeVarint(write, local_len(encoded))
+ return write(encoded)
+ return EncodeField
+
+
+def BytesEncoder(field_number, is_repeated, is_packed):
+ """Returns an encoder for a bytes field."""
+
+ tag = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ local_len = len
+ assert not is_packed
+ if is_repeated:
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(tag)
+ local_EncodeVarint(write, local_len(element))
+ write(element)
+ return EncodeRepeatedField
+ else:
+ def EncodeField(write, value):
+ write(tag)
+ local_EncodeVarint(write, local_len(value))
+ return write(value)
+ return EncodeField
+
+
+def GroupEncoder(field_number, is_repeated, is_packed):
+ """Returns an encoder for a group field."""
+
+ start_tag = TagBytes(field_number, wire_format.WIRETYPE_START_GROUP)
+ end_tag = TagBytes(field_number, wire_format.WIRETYPE_END_GROUP)
+ assert not is_packed
+ if is_repeated:
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(start_tag)
+ element._InternalSerialize(write)
+ write(end_tag)
+ return EncodeRepeatedField
+ else:
+ def EncodeField(write, value):
+ write(start_tag)
+ value._InternalSerialize(write)
+ return write(end_tag)
+ return EncodeField
+
+
+def MessageEncoder(field_number, is_repeated, is_packed):
+ """Returns an encoder for a message field."""
+
+ tag = TagBytes(field_number, wire_format.WIRETYPE_LENGTH_DELIMITED)
+ local_EncodeVarint = _EncodeVarint
+ assert not is_packed
+ if is_repeated:
+ def EncodeRepeatedField(write, value):
+ for element in value:
+ write(tag)
+ local_EncodeVarint(write, element.ByteSize())
+ element._InternalSerialize(write)
+ return EncodeRepeatedField
+ else:
+ def EncodeField(write, value):
+ write(tag)
+ local_EncodeVarint(write, value.ByteSize())
+ return value._InternalSerialize(write)
+ return EncodeField
+
+
+# --------------------------------------------------------------------
+# As before, MessageSet is special.
+
+
+def MessageSetItemEncoder(field_number):
+ """Encoder for extensions of MessageSet.
+
+ The message set message looks like this:
+ message MessageSet {
+ repeated group Item = 1 {
+ required int32 type_id = 2;
+ required string message = 3;
+ }
+ }
+ """
+ start_bytes = b"".join([
+ TagBytes(1, wire_format.WIRETYPE_START_GROUP),
+ TagBytes(2, wire_format.WIRETYPE_VARINT),
+ _VarintBytes(field_number),
+ TagBytes(3, wire_format.WIRETYPE_LENGTH_DELIMITED)])
+ end_bytes = TagBytes(1, wire_format.WIRETYPE_END_GROUP)
+ local_EncodeVarint = _EncodeVarint
+
+ def EncodeField(write, value):
+ write(start_bytes)
+ local_EncodeVarint(write, value.ByteSize())
+ value._InternalSerialize(write)
+ return write(end_bytes)
+
+ return EncodeField
+
+
+# --------------------------------------------------------------------
+# As before, Map is special.
+
+
+def MapEncoder(field_descriptor):
+ """Encoder for extensions of MessageSet.
+
+ Maps always have a wire format like this:
+ message MapEntry {
+ key_type key = 1;
+ value_type value = 2;
+ }
+ repeated MapEntry map = N;
+ """
+ # Can't look at field_descriptor.message_type._concrete_class because it may
+ # not have been initialized yet.
+ message_type = field_descriptor.message_type
+ encode_message = MessageEncoder(field_descriptor.number, False, False)
+
+ def EncodeField(write, value):
+ for key in value:
+ entry_msg = message_type._concrete_class(key=key, value=value[key])
+ encode_message(write, entry_msg)
+
+ return EncodeField
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/enum_type_wrapper.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/enum_type_wrapper.py
new file mode 100644
index 0000000000..1cffe35295
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/enum_type_wrapper.py
@@ -0,0 +1,89 @@
+# 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.
+
+"""A simple wrapper around enum types to expose utility functions.
+
+Instances are created as properties with the same name as the enum they wrap
+on proto classes. For usage, see:
+ reflection_test.py
+"""
+
+__author__ = 'rabsatt@google.com (Kevin Rabsatt)'
+
+
+class EnumTypeWrapper(object):
+ """A utility for finding the names of enum values."""
+
+ DESCRIPTOR = None
+
+ def __init__(self, enum_type):
+ """Inits EnumTypeWrapper with an EnumDescriptor."""
+ self._enum_type = enum_type
+ self.DESCRIPTOR = enum_type;
+
+ def Name(self, number):
+ """Returns a string containing the name of an enum value."""
+ if number in self._enum_type.values_by_number:
+ return self._enum_type.values_by_number[number].name
+ raise ValueError('Enum %s has no name defined for value %d' % (
+ self._enum_type.name, number))
+
+ def Value(self, name):
+ """Returns the value coresponding to the given enum name."""
+ if name in self._enum_type.values_by_name:
+ return self._enum_type.values_by_name[name].number
+ raise ValueError('Enum %s has no value defined for name %s' % (
+ self._enum_type.name, name))
+
+ def keys(self):
+ """Return a list of the string names in the enum.
+
+ These are returned in the order they were defined in the .proto file.
+ """
+
+ return [value_descriptor.name
+ for value_descriptor in self._enum_type.values]
+
+ def values(self):
+ """Return a list of the integer values in the enum.
+
+ These are returned in the order they were defined in the .proto file.
+ """
+
+ return [value_descriptor.number
+ for value_descriptor in self._enum_type.values]
+
+ def items(self):
+ """Return a list of the (name, value) pairs of the enum.
+
+ These are returned in the order they were defined in the .proto file.
+ """
+ return [(value_descriptor.name, value_descriptor.number)
+ for value_descriptor in self._enum_type.values]
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test1.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test1.proto
new file mode 100644
index 0000000000..d2fbbeecf1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test1.proto
@@ -0,0 +1,58 @@
+// 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: matthewtoia@google.com (Matt Toia)
+
+syntax = "proto2";
+
+package google.protobuf.python.internal;
+
+
+enum Factory1Enum {
+ FACTORY_1_VALUE_0 = 0;
+ FACTORY_1_VALUE_1 = 1;
+}
+
+message Factory1Message {
+ optional Factory1Enum factory_1_enum = 1;
+ enum NestedFactory1Enum {
+ NESTED_FACTORY_1_VALUE_0 = 0;
+ NESTED_FACTORY_1_VALUE_1 = 1;
+ }
+ optional NestedFactory1Enum nested_factory_1_enum = 2;
+ message NestedFactory1Message {
+ optional string value = 1;
+ }
+ optional NestedFactory1Message nested_factory_1_message = 3;
+ optional int32 scalar_value = 4;
+ repeated string list_value = 5;
+
+ extensions 1000 to max;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test2.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test2.proto
new file mode 100644
index 0000000000..bb1b54ada2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/factory_test2.proto
@@ -0,0 +1,99 @@
+// 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: matthewtoia@google.com (Matt Toia)
+
+syntax = "proto2";
+
+package google.protobuf.python.internal;
+
+import "google/protobuf/internal/factory_test1.proto";
+
+
+enum Factory2Enum {
+ FACTORY_2_VALUE_0 = 0;
+ FACTORY_2_VALUE_1 = 1;
+}
+
+message Factory2Message {
+ required int32 mandatory = 1;
+ optional Factory2Enum factory_2_enum = 2;
+ enum NestedFactory2Enum {
+ NESTED_FACTORY_2_VALUE_0 = 0;
+ NESTED_FACTORY_2_VALUE_1 = 1;
+ }
+ optional NestedFactory2Enum nested_factory_2_enum = 3;
+ message NestedFactory2Message {
+ optional string value = 1;
+ }
+ optional NestedFactory2Message nested_factory_2_message = 4;
+ optional Factory1Message factory_1_message = 5;
+ optional Factory1Enum factory_1_enum = 6;
+ optional Factory1Message.NestedFactory1Enum nested_factory_1_enum = 7;
+ optional Factory1Message.NestedFactory1Message nested_factory_1_message = 8;
+ optional Factory2Message circular_message = 9;
+ optional string scalar_value = 10;
+ repeated string list_value = 11;
+ repeated group Grouped = 12 {
+ optional string part_1 = 13;
+ optional string part_2 = 14;
+ }
+ optional LoopMessage loop = 15;
+ optional int32 int_with_default = 16 [default = 1776];
+ optional double double_with_default = 17 [default = 9.99];
+ optional string string_with_default = 18 [default = "hello world"];
+ optional bool bool_with_default = 19 [default = false];
+ optional Factory2Enum enum_with_default = 20 [default = FACTORY_2_VALUE_1];
+ optional bytes bytes_with_default = 21 [default = "a\373\000c"];
+
+
+ extend Factory1Message {
+ optional string one_more_field = 1001;
+ }
+
+ oneof oneof_field {
+ int32 oneof_int = 22;
+ string oneof_string = 23;
+ }
+}
+
+message LoopMessage {
+ optional Factory2Message loop = 1;
+}
+
+message MessageWithNestedEnumOnly {
+ enum NestedEnum {
+ NESTED_MESSAGE_ENUM_0 = 0;
+ }
+}
+
+extend Factory1Message {
+ optional string another_field = 1002;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/file_options_test.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/file_options_test.proto
new file mode 100644
index 0000000000..4eceeb07f4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/file_options_test.proto
@@ -0,0 +1,43 @@
+// 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.
+
+syntax = "proto2";
+
+import "google/protobuf/descriptor.proto";
+
+package google.protobuf.python.internal;
+
+message FooOptions {
+ optional string foo_name = 1;
+}
+
+extend .google.protobuf.FileOptions {
+ optional FooOptions foo_options = 120436268;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/generator_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/generator_test.py
new file mode 100755
index 0000000000..83ea5f5094
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/generator_test.py
@@ -0,0 +1,348 @@
+#! /usr/bin/env python
+#
+# 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.
+
+# TODO(robinson): Flesh this out considerably. We focused on reflection_test.py
+# first, since it's testing the subtler code, and since it provides decent
+# indirect testing of the protocol compiler output.
+
+"""Unittest that directly tests the output of the pure-Python protocol
+compiler. See //google/protobuf/internal/reflection_test.py for a test which
+further ensures that we can use Python protocol message objects as we expect.
+"""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf.internal import test_bad_identifiers_pb2
+from google.protobuf import unittest_custom_options_pb2
+from google.protobuf import unittest_import_pb2
+from google.protobuf import unittest_import_public_pb2
+from google.protobuf import unittest_mset_pb2
+from google.protobuf import unittest_mset_wire_format_pb2
+from google.protobuf import unittest_no_generic_services_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import service
+from google.protobuf import symbol_database
+
+MAX_EXTENSION = 536870912
+
+
+class GeneratorTest(unittest.TestCase):
+
+ def testNestedMessageDescriptor(self):
+ field_name = 'optional_nested_message'
+ proto_type = unittest_pb2.TestAllTypes
+ self.assertEqual(
+ proto_type.NestedMessage.DESCRIPTOR,
+ proto_type.DESCRIPTOR.fields_by_name[field_name].message_type)
+
+ def testEnums(self):
+ # We test only module-level enums here.
+ # TODO(robinson): Examine descriptors directly to check
+ # enum descriptor output.
+ self.assertEqual(4, unittest_pb2.FOREIGN_FOO)
+ self.assertEqual(5, unittest_pb2.FOREIGN_BAR)
+ self.assertEqual(6, unittest_pb2.FOREIGN_BAZ)
+
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(1, proto.FOO)
+ self.assertEqual(1, unittest_pb2.TestAllTypes.FOO)
+ self.assertEqual(2, proto.BAR)
+ self.assertEqual(2, unittest_pb2.TestAllTypes.BAR)
+ self.assertEqual(3, proto.BAZ)
+ self.assertEqual(3, unittest_pb2.TestAllTypes.BAZ)
+
+ def testExtremeDefaultValues(self):
+ message = unittest_pb2.TestExtremeDefaultValues()
+
+ # Python pre-2.6 does not have isinf() or isnan() functions, so we have
+ # to provide our own.
+ def isnan(val):
+ # NaN is never equal to itself.
+ return val != val
+ def isinf(val):
+ # Infinity times zero equals NaN.
+ return not isnan(val) and isnan(val * 0)
+
+ self.assertTrue(isinf(message.inf_double))
+ self.assertTrue(message.inf_double > 0)
+ self.assertTrue(isinf(message.neg_inf_double))
+ self.assertTrue(message.neg_inf_double < 0)
+ self.assertTrue(isnan(message.nan_double))
+
+ self.assertTrue(isinf(message.inf_float))
+ self.assertTrue(message.inf_float > 0)
+ self.assertTrue(isinf(message.neg_inf_float))
+ self.assertTrue(message.neg_inf_float < 0)
+ self.assertTrue(isnan(message.nan_float))
+ self.assertEqual("? ? ?? ?? ??? ??/ ??-", message.cpp_trigraph)
+
+ def testHasDefaultValues(self):
+ desc = unittest_pb2.TestAllTypes.DESCRIPTOR
+
+ expected_has_default_by_name = {
+ 'optional_int32': False,
+ 'repeated_int32': False,
+ 'optional_nested_message': False,
+ 'default_int32': True,
+ }
+
+ has_default_by_name = dict(
+ [(f.name, f.has_default_value)
+ for f in desc.fields
+ if f.name in expected_has_default_by_name])
+ self.assertEqual(expected_has_default_by_name, has_default_by_name)
+
+ def testContainingTypeBehaviorForExtensions(self):
+ self.assertEqual(unittest_pb2.optional_int32_extension.containing_type,
+ unittest_pb2.TestAllExtensions.DESCRIPTOR)
+ self.assertEqual(unittest_pb2.TestRequired.single.containing_type,
+ unittest_pb2.TestAllExtensions.DESCRIPTOR)
+
+ def testExtensionScope(self):
+ self.assertEqual(unittest_pb2.optional_int32_extension.extension_scope,
+ None)
+ self.assertEqual(unittest_pb2.TestRequired.single.extension_scope,
+ unittest_pb2.TestRequired.DESCRIPTOR)
+
+ def testIsExtension(self):
+ self.assertTrue(unittest_pb2.optional_int32_extension.is_extension)
+ self.assertTrue(unittest_pb2.TestRequired.single.is_extension)
+
+ message_descriptor = unittest_pb2.TestRequired.DESCRIPTOR
+ non_extension_descriptor = message_descriptor.fields_by_name['a']
+ self.assertTrue(not non_extension_descriptor.is_extension)
+
+ def testOptions(self):
+ proto = unittest_mset_wire_format_pb2.TestMessageSet()
+ self.assertTrue(proto.DESCRIPTOR.GetOptions().message_set_wire_format)
+
+ def testMessageWithCustomOptions(self):
+ proto = unittest_custom_options_pb2.TestMessageWithCustomOptions()
+ enum_options = proto.DESCRIPTOR.enum_types_by_name['AnEnum'].GetOptions()
+ self.assertTrue(enum_options is not None)
+ # TODO(gps): We really should test for the presence of the enum_opt1
+ # extension and for its value to be set to -789.
+
+ def testNestedTypes(self):
+ self.assertEqual(
+ set(unittest_pb2.TestAllTypes.DESCRIPTOR.nested_types),
+ set([
+ unittest_pb2.TestAllTypes.NestedMessage.DESCRIPTOR,
+ unittest_pb2.TestAllTypes.OptionalGroup.DESCRIPTOR,
+ unittest_pb2.TestAllTypes.RepeatedGroup.DESCRIPTOR,
+ ]))
+ self.assertEqual(unittest_pb2.TestEmptyMessage.DESCRIPTOR.nested_types, [])
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.NestedMessage.DESCRIPTOR.nested_types, [])
+
+ def testContainingType(self):
+ self.assertTrue(
+ unittest_pb2.TestEmptyMessage.DESCRIPTOR.containing_type is None)
+ self.assertTrue(
+ unittest_pb2.TestAllTypes.DESCRIPTOR.containing_type is None)
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.NestedMessage.DESCRIPTOR.containing_type,
+ unittest_pb2.TestAllTypes.DESCRIPTOR)
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.NestedMessage.DESCRIPTOR.containing_type,
+ unittest_pb2.TestAllTypes.DESCRIPTOR)
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.RepeatedGroup.DESCRIPTOR.containing_type,
+ unittest_pb2.TestAllTypes.DESCRIPTOR)
+
+ def testContainingTypeInEnumDescriptor(self):
+ self.assertTrue(unittest_pb2._FOREIGNENUM.containing_type is None)
+ self.assertEqual(unittest_pb2._TESTALLTYPES_NESTEDENUM.containing_type,
+ unittest_pb2.TestAllTypes.DESCRIPTOR)
+
+ def testPackage(self):
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.DESCRIPTOR.file.package,
+ 'protobuf_unittest')
+ desc = unittest_pb2.TestAllTypes.NestedMessage.DESCRIPTOR
+ self.assertEqual(desc.file.package, 'protobuf_unittest')
+ self.assertEqual(
+ unittest_import_pb2.ImportMessage.DESCRIPTOR.file.package,
+ 'protobuf_unittest_import')
+
+ self.assertEqual(
+ unittest_pb2._FOREIGNENUM.file.package, 'protobuf_unittest')
+ self.assertEqual(
+ unittest_pb2._TESTALLTYPES_NESTEDENUM.file.package,
+ 'protobuf_unittest')
+ self.assertEqual(
+ unittest_import_pb2._IMPORTENUM.file.package,
+ 'protobuf_unittest_import')
+
+ def testExtensionRange(self):
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.DESCRIPTOR.extension_ranges, [])
+ self.assertEqual(
+ unittest_pb2.TestAllExtensions.DESCRIPTOR.extension_ranges,
+ [(1, MAX_EXTENSION)])
+ self.assertEqual(
+ unittest_pb2.TestMultipleExtensionRanges.DESCRIPTOR.extension_ranges,
+ [(42, 43), (4143, 4244), (65536, MAX_EXTENSION)])
+
+ def testFileDescriptor(self):
+ self.assertEqual(unittest_pb2.DESCRIPTOR.name,
+ 'google/protobuf/unittest.proto')
+ self.assertEqual(unittest_pb2.DESCRIPTOR.package, 'protobuf_unittest')
+ self.assertFalse(unittest_pb2.DESCRIPTOR.serialized_pb is None)
+ self.assertEqual(unittest_pb2.DESCRIPTOR.dependencies,
+ [unittest_import_pb2.DESCRIPTOR])
+ self.assertEqual(unittest_import_pb2.DESCRIPTOR.dependencies,
+ [unittest_import_public_pb2.DESCRIPTOR])
+
+ def testNoGenericServices(self):
+ self.assertTrue(hasattr(unittest_no_generic_services_pb2, "TestMessage"))
+ self.assertTrue(hasattr(unittest_no_generic_services_pb2, "FOO"))
+ self.assertTrue(hasattr(unittest_no_generic_services_pb2, "test_extension"))
+
+ # Make sure unittest_no_generic_services_pb2 has no services subclassing
+ # Proto2 Service class.
+ if hasattr(unittest_no_generic_services_pb2, "TestService"):
+ self.assertFalse(issubclass(unittest_no_generic_services_pb2.TestService,
+ service.Service))
+
+ def testMessageTypesByName(self):
+ file_type = unittest_pb2.DESCRIPTOR
+ self.assertEqual(
+ unittest_pb2._TESTALLTYPES,
+ file_type.message_types_by_name[unittest_pb2._TESTALLTYPES.name])
+
+ # Nested messages shouldn't be included in the message_types_by_name
+ # dictionary (like in the C++ API).
+ self.assertFalse(
+ unittest_pb2._TESTALLTYPES_NESTEDMESSAGE.name in
+ file_type.message_types_by_name)
+
+ def testEnumTypesByName(self):
+ file_type = unittest_pb2.DESCRIPTOR
+ self.assertEqual(
+ unittest_pb2._FOREIGNENUM,
+ file_type.enum_types_by_name[unittest_pb2._FOREIGNENUM.name])
+
+ def testExtensionsByName(self):
+ file_type = unittest_pb2.DESCRIPTOR
+ self.assertEqual(
+ unittest_pb2.my_extension_string,
+ file_type.extensions_by_name[unittest_pb2.my_extension_string.name])
+
+ def testPublicImports(self):
+ # Test public imports as embedded message.
+ all_type_proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(0, all_type_proto.optional_public_import_message.e)
+
+ # PublicImportMessage is actually defined in unittest_import_public_pb2
+ # module, and is public imported by unittest_import_pb2 module.
+ public_import_proto = unittest_import_pb2.PublicImportMessage()
+ self.assertEqual(0, public_import_proto.e)
+ self.assertTrue(unittest_import_public_pb2.PublicImportMessage is
+ unittest_import_pb2.PublicImportMessage)
+
+ def testBadIdentifiers(self):
+ # We're just testing that the code was imported without problems.
+ message = test_bad_identifiers_pb2.TestBadIdentifiers()
+ self.assertEqual(message.Extensions[test_bad_identifiers_pb2.message],
+ "foo")
+ self.assertEqual(message.Extensions[test_bad_identifiers_pb2.descriptor],
+ "bar")
+ self.assertEqual(message.Extensions[test_bad_identifiers_pb2.reflection],
+ "baz")
+ self.assertEqual(message.Extensions[test_bad_identifiers_pb2.service],
+ "qux")
+
+ def testOneof(self):
+ desc = unittest_pb2.TestAllTypes.DESCRIPTOR
+ self.assertEqual(1, len(desc.oneofs))
+ self.assertEqual('oneof_field', desc.oneofs[0].name)
+ self.assertEqual(0, desc.oneofs[0].index)
+ self.assertIs(desc, desc.oneofs[0].containing_type)
+ self.assertIs(desc.oneofs[0], desc.oneofs_by_name['oneof_field'])
+ nested_names = set(['oneof_uint32', 'oneof_nested_message',
+ 'oneof_string', 'oneof_bytes'])
+ self.assertEqual(
+ nested_names,
+ set([field.name for field in desc.oneofs[0].fields]))
+ for field_name, field_desc in desc.fields_by_name.items():
+ if field_name in nested_names:
+ self.assertIs(desc.oneofs[0], field_desc.containing_oneof)
+ else:
+ self.assertIsNone(field_desc.containing_oneof)
+
+
+class SymbolDatabaseRegistrationTest(unittest.TestCase):
+ """Checks that messages, enums and files are correctly registered."""
+
+ def testGetSymbol(self):
+ self.assertEqual(
+ unittest_pb2.TestAllTypes, symbol_database.Default().GetSymbol(
+ 'protobuf_unittest.TestAllTypes'))
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.NestedMessage,
+ symbol_database.Default().GetSymbol(
+ 'protobuf_unittest.TestAllTypes.NestedMessage'))
+ with self.assertRaises(KeyError):
+ symbol_database.Default().GetSymbol('protobuf_unittest.NestedMessage')
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.OptionalGroup,
+ symbol_database.Default().GetSymbol(
+ 'protobuf_unittest.TestAllTypes.OptionalGroup'))
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.RepeatedGroup,
+ symbol_database.Default().GetSymbol(
+ 'protobuf_unittest.TestAllTypes.RepeatedGroup'))
+
+ def testEnums(self):
+ self.assertEqual(
+ 'protobuf_unittest.ForeignEnum',
+ symbol_database.Default().pool.FindEnumTypeByName(
+ 'protobuf_unittest.ForeignEnum').full_name)
+ self.assertEqual(
+ 'protobuf_unittest.TestAllTypes.NestedEnum',
+ symbol_database.Default().pool.FindEnumTypeByName(
+ 'protobuf_unittest.TestAllTypes.NestedEnum').full_name)
+
+ def testFindFileByName(self):
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ symbol_database.Default().pool.FindFileByName(
+ 'google/protobuf/unittest.proto').name)
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/__init__.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/__init__.py
new file mode 100644
index 0000000000..5121dd0ec5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/__init__.py
@@ -0,0 +1,33 @@
+# 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.
+
+"""Sample module importing a nested proto from itself."""
+
+from google.protobuf.internal.import_test_package import outer_pb2 as myproto
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/inner.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/inner.proto
new file mode 100644
index 0000000000..2887c1230e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/inner.proto
@@ -0,0 +1,37 @@
+// 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.
+
+syntax = "proto2";
+
+package google.protobuf.python.internal.import_test_package;
+
+message Inner {
+ optional int32 value = 1 [default = 57];
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/outer.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/outer.proto
new file mode 100644
index 0000000000..a27fb5c8f4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/import_test_package/outer.proto
@@ -0,0 +1,39 @@
+// 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.
+
+syntax = "proto2";
+
+package google.protobuf.python.internal.import_test_package;
+
+import "google/protobuf/internal/import_test_package/inner.proto";
+
+message Outer {
+ optional Inner inner = 1;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/json_format_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/json_format_test.py
new file mode 100644
index 0000000000..a5ee8ace0e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/json_format_test.py
@@ -0,0 +1,815 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Test for google.protobuf.json_format."""
+
+__author__ = 'jieluo@google.com (Jie Luo)'
+
+import json
+import math
+import sys
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import any_pb2
+from google.protobuf import duration_pb2
+from google.protobuf import field_mask_pb2
+from google.protobuf import struct_pb2
+from google.protobuf import timestamp_pb2
+from google.protobuf import wrappers_pb2
+from google.protobuf.internal import well_known_types
+from google.protobuf import json_format
+from google.protobuf.util import json_format_proto3_pb2
+
+
+class JsonFormatBase(unittest.TestCase):
+
+ def FillAllFields(self, message):
+ message.int32_value = 20
+ message.int64_value = -20
+ message.uint32_value = 3120987654
+ message.uint64_value = 12345678900
+ message.float_value = float('-inf')
+ message.double_value = 3.1415
+ message.bool_value = True
+ message.string_value = 'foo'
+ message.bytes_value = b'bar'
+ message.message_value.value = 10
+ message.enum_value = json_format_proto3_pb2.BAR
+ # Repeated
+ message.repeated_int32_value.append(0x7FFFFFFF)
+ message.repeated_int32_value.append(-2147483648)
+ message.repeated_int64_value.append(9007199254740992)
+ message.repeated_int64_value.append(-9007199254740992)
+ message.repeated_uint32_value.append(0xFFFFFFF)
+ message.repeated_uint32_value.append(0x7FFFFFF)
+ message.repeated_uint64_value.append(9007199254740992)
+ message.repeated_uint64_value.append(9007199254740991)
+ message.repeated_float_value.append(0)
+
+ message.repeated_double_value.append(1E-15)
+ message.repeated_double_value.append(float('inf'))
+ message.repeated_bool_value.append(True)
+ message.repeated_bool_value.append(False)
+ message.repeated_string_value.append('Few symbols!#$,;')
+ message.repeated_string_value.append('bar')
+ message.repeated_bytes_value.append(b'foo')
+ message.repeated_bytes_value.append(b'bar')
+ message.repeated_message_value.add().value = 10
+ message.repeated_message_value.add().value = 11
+ message.repeated_enum_value.append(json_format_proto3_pb2.FOO)
+ message.repeated_enum_value.append(json_format_proto3_pb2.BAR)
+ self.message = message
+
+ def CheckParseBack(self, message, parsed_message):
+ json_format.Parse(json_format.MessageToJson(message),
+ parsed_message)
+ self.assertEqual(message, parsed_message)
+
+ def CheckError(self, text, error_message):
+ message = json_format_proto3_pb2.TestMessage()
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ error_message,
+ json_format.Parse, text, message)
+
+
+class JsonFormatTest(JsonFormatBase):
+
+ def testEmptyMessageToJson(self):
+ message = json_format_proto3_pb2.TestMessage()
+ self.assertEqual(json_format.MessageToJson(message),
+ '{}')
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ self.CheckParseBack(message, parsed_message)
+
+ def testPartialMessageToJson(self):
+ message = json_format_proto3_pb2.TestMessage(
+ string_value='test',
+ repeated_int32_value=[89, 4])
+ self.assertEqual(json.loads(json_format.MessageToJson(message)),
+ json.loads('{"stringValue": "test", '
+ '"repeatedInt32Value": [89, 4]}'))
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ self.CheckParseBack(message, parsed_message)
+
+ def testAllFieldsToJson(self):
+ message = json_format_proto3_pb2.TestMessage()
+ text = ('{"int32Value": 20, '
+ '"int64Value": "-20", '
+ '"uint32Value": 3120987654,'
+ '"uint64Value": "12345678900",'
+ '"floatValue": "-Infinity",'
+ '"doubleValue": 3.1415,'
+ '"boolValue": true,'
+ '"stringValue": "foo",'
+ '"bytesValue": "YmFy",'
+ '"messageValue": {"value": 10},'
+ '"enumValue": "BAR",'
+ '"repeatedInt32Value": [2147483647, -2147483648],'
+ '"repeatedInt64Value": ["9007199254740992", "-9007199254740992"],'
+ '"repeatedUint32Value": [268435455, 134217727],'
+ '"repeatedUint64Value": ["9007199254740992", "9007199254740991"],'
+ '"repeatedFloatValue": [0],'
+ '"repeatedDoubleValue": [1e-15, "Infinity"],'
+ '"repeatedBoolValue": [true, false],'
+ '"repeatedStringValue": ["Few symbols!#$,;", "bar"],'
+ '"repeatedBytesValue": ["Zm9v", "YmFy"],'
+ '"repeatedMessageValue": [{"value": 10}, {"value": 11}],'
+ '"repeatedEnumValue": ["FOO", "BAR"]'
+ '}')
+ self.FillAllFields(message)
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message)),
+ json.loads(text))
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ json_format.Parse(text, parsed_message)
+ self.assertEqual(message, parsed_message)
+
+ def testJsonEscapeString(self):
+ message = json_format_proto3_pb2.TestMessage()
+ if sys.version_info[0] < 3:
+ message.string_value = '&\n<\"\r>\b\t\f\\\001/\xe2\x80\xa8\xe2\x80\xa9'
+ else:
+ message.string_value = '&\n<\"\r>\b\t\f\\\001/'
+ message.string_value += (b'\xe2\x80\xa8\xe2\x80\xa9').decode('utf-8')
+ self.assertEqual(
+ json_format.MessageToJson(message),
+ '{\n "stringValue": '
+ '"&\\n<\\\"\\r>\\b\\t\\f\\\\\\u0001/\\u2028\\u2029"\n}')
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ self.CheckParseBack(message, parsed_message)
+ text = u'{"int32Value": "\u0031"}'
+ json_format.Parse(text, message)
+ self.assertEqual(message.int32_value, 1)
+
+ def testAlwaysSeriliaze(self):
+ message = json_format_proto3_pb2.TestMessage(
+ string_value='foo')
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads('{'
+ '"repeatedStringValue": [],'
+ '"stringValue": "foo",'
+ '"repeatedBoolValue": [],'
+ '"repeatedUint32Value": [],'
+ '"repeatedInt32Value": [],'
+ '"enumValue": "FOO",'
+ '"int32Value": 0,'
+ '"floatValue": 0,'
+ '"int64Value": "0",'
+ '"uint32Value": 0,'
+ '"repeatedBytesValue": [],'
+ '"repeatedUint64Value": [],'
+ '"repeatedDoubleValue": [],'
+ '"bytesValue": "",'
+ '"boolValue": false,'
+ '"repeatedEnumValue": [],'
+ '"uint64Value": "0",'
+ '"doubleValue": 0,'
+ '"repeatedFloatValue": [],'
+ '"repeatedInt64Value": [],'
+ '"repeatedMessageValue": []}'))
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ self.CheckParseBack(message, parsed_message)
+
+ def testMapFields(self):
+ message = json_format_proto3_pb2.TestMap()
+ message.bool_map[True] = 1
+ message.bool_map[False] = 2
+ message.int32_map[1] = 2
+ message.int32_map[2] = 3
+ message.int64_map[1] = 2
+ message.int64_map[2] = 3
+ message.uint32_map[1] = 2
+ message.uint32_map[2] = 3
+ message.uint64_map[1] = 2
+ message.uint64_map[2] = 3
+ message.string_map['1'] = 2
+ message.string_map['null'] = 3
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads('{'
+ '"boolMap": {"false": 2, "true": 1},'
+ '"int32Map": {"1": 2, "2": 3},'
+ '"int64Map": {"1": 2, "2": 3},'
+ '"uint32Map": {"1": 2, "2": 3},'
+ '"uint64Map": {"1": 2, "2": 3},'
+ '"stringMap": {"1": 2, "null": 3}'
+ '}'))
+ parsed_message = json_format_proto3_pb2.TestMap()
+ self.CheckParseBack(message, parsed_message)
+
+ def testOneofFields(self):
+ message = json_format_proto3_pb2.TestOneof()
+ # Always print does not affect oneof fields.
+ self.assertEqual(
+ json_format.MessageToJson(message, True),
+ '{}')
+ message.oneof_int32_value = 0
+ self.assertEqual(
+ json_format.MessageToJson(message, True),
+ '{\n'
+ ' "oneofInt32Value": 0\n'
+ '}')
+ parsed_message = json_format_proto3_pb2.TestOneof()
+ self.CheckParseBack(message, parsed_message)
+
+ def testSurrogates(self):
+ # Test correct surrogate handling.
+ message = json_format_proto3_pb2.TestMessage()
+ json_format.Parse('{"stringValue": "\\uD83D\\uDE01"}', message)
+ self.assertEqual(message.string_value,
+ b'\xF0\x9F\x98\x81'.decode('utf-8', 'strict'))
+
+ # Error case: unpaired high surrogate.
+ self.CheckError(
+ '{"stringValue": "\\uD83D"}',
+ r'Invalid \\uXXXX escape|Unpaired.*surrogate')
+
+ # Unpaired low surrogate.
+ self.CheckError(
+ '{"stringValue": "\\uDE01"}',
+ r'Invalid \\uXXXX escape|Unpaired.*surrogate')
+
+ def testTimestampMessage(self):
+ message = json_format_proto3_pb2.TestTimestamp()
+ message.value.seconds = 0
+ message.value.nanos = 0
+ message.repeated_value.add().seconds = 20
+ message.repeated_value[0].nanos = 1
+ message.repeated_value.add().seconds = 0
+ message.repeated_value[1].nanos = 10000
+ message.repeated_value.add().seconds = 100000000
+ message.repeated_value[2].nanos = 0
+ # Maximum time
+ message.repeated_value.add().seconds = 253402300799
+ message.repeated_value[3].nanos = 999999999
+ # Minimum time
+ message.repeated_value.add().seconds = -62135596800
+ message.repeated_value[4].nanos = 0
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads('{'
+ '"value": "1970-01-01T00:00:00Z",'
+ '"repeatedValue": ['
+ ' "1970-01-01T00:00:20.000000001Z",'
+ ' "1970-01-01T00:00:00.000010Z",'
+ ' "1973-03-03T09:46:40Z",'
+ ' "9999-12-31T23:59:59.999999999Z",'
+ ' "0001-01-01T00:00:00Z"'
+ ']'
+ '}'))
+ parsed_message = json_format_proto3_pb2.TestTimestamp()
+ self.CheckParseBack(message, parsed_message)
+ text = (r'{"value": "1970-01-01T00:00:00.01+08:00",'
+ r'"repeatedValue":['
+ r' "1970-01-01T00:00:00.01+08:30",'
+ r' "1970-01-01T00:00:00.01-01:23"]}')
+ json_format.Parse(text, parsed_message)
+ self.assertEqual(parsed_message.value.seconds, -8 * 3600)
+ self.assertEqual(parsed_message.value.nanos, 10000000)
+ self.assertEqual(parsed_message.repeated_value[0].seconds, -8.5 * 3600)
+ self.assertEqual(parsed_message.repeated_value[1].seconds, 3600 + 23 * 60)
+
+ def testDurationMessage(self):
+ message = json_format_proto3_pb2.TestDuration()
+ message.value.seconds = 1
+ message.repeated_value.add().seconds = 0
+ message.repeated_value[0].nanos = 10
+ message.repeated_value.add().seconds = -1
+ message.repeated_value[1].nanos = -1000
+ message.repeated_value.add().seconds = 10
+ message.repeated_value[2].nanos = 11000000
+ message.repeated_value.add().seconds = -315576000000
+ message.repeated_value.add().seconds = 315576000000
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads('{'
+ '"value": "1s",'
+ '"repeatedValue": ['
+ ' "0.000000010s",'
+ ' "-1.000001s",'
+ ' "10.011s",'
+ ' "-315576000000s",'
+ ' "315576000000s"'
+ ']'
+ '}'))
+ parsed_message = json_format_proto3_pb2.TestDuration()
+ self.CheckParseBack(message, parsed_message)
+
+ def testFieldMaskMessage(self):
+ message = json_format_proto3_pb2.TestFieldMask()
+ message.value.paths.append('foo.bar')
+ message.value.paths.append('bar')
+ self.assertEqual(
+ json_format.MessageToJson(message, True),
+ '{\n'
+ ' "value": "foo.bar,bar"\n'
+ '}')
+ parsed_message = json_format_proto3_pb2.TestFieldMask()
+ self.CheckParseBack(message, parsed_message)
+
+ def testWrapperMessage(self):
+ message = json_format_proto3_pb2.TestWrapper()
+ message.bool_value.value = False
+ message.int32_value.value = 0
+ message.string_value.value = ''
+ message.bytes_value.value = b''
+ message.repeated_bool_value.add().value = True
+ message.repeated_bool_value.add().value = False
+ message.repeated_int32_value.add()
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads('{\n'
+ ' "int32Value": 0,'
+ ' "boolValue": false,'
+ ' "stringValue": "",'
+ ' "bytesValue": "",'
+ ' "repeatedBoolValue": [true, false],'
+ ' "repeatedInt32Value": [0],'
+ ' "repeatedUint32Value": [],'
+ ' "repeatedFloatValue": [],'
+ ' "repeatedDoubleValue": [],'
+ ' "repeatedBytesValue": [],'
+ ' "repeatedInt64Value": [],'
+ ' "repeatedUint64Value": [],'
+ ' "repeatedStringValue": []'
+ '}'))
+ parsed_message = json_format_proto3_pb2.TestWrapper()
+ self.CheckParseBack(message, parsed_message)
+
+ def testStructMessage(self):
+ message = json_format_proto3_pb2.TestStruct()
+ message.value['name'] = 'Jim'
+ message.value['age'] = 10
+ message.value['attend'] = True
+ message.value['email'] = None
+ message.value.get_or_create_struct('address')['city'] = 'SFO'
+ message.value['address']['house_number'] = 1024
+ struct_list = message.value.get_or_create_list('list')
+ struct_list.extend([6, 'seven', True, False, None])
+ struct_list.add_struct()['subkey2'] = 9
+ message.repeated_value.add()['age'] = 11
+ message.repeated_value.add()
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, False)),
+ json.loads(
+ '{'
+ ' "value": {'
+ ' "address": {'
+ ' "city": "SFO", '
+ ' "house_number": 1024'
+ ' }, '
+ ' "age": 10, '
+ ' "name": "Jim", '
+ ' "attend": true, '
+ ' "email": null, '
+ ' "list": [6, "seven", true, false, null, {"subkey2": 9}]'
+ ' },'
+ ' "repeatedValue": [{"age": 11}, {}]'
+ '}'))
+ parsed_message = json_format_proto3_pb2.TestStruct()
+ self.CheckParseBack(message, parsed_message)
+
+ def testValueMessage(self):
+ message = json_format_proto3_pb2.TestValue()
+ message.value.string_value = 'hello'
+ message.repeated_value.add().number_value = 11.1
+ message.repeated_value.add().bool_value = False
+ message.repeated_value.add().null_value = 0
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, False)),
+ json.loads(
+ '{'
+ ' "value": "hello",'
+ ' "repeatedValue": [11.1, false, null]'
+ '}'))
+ parsed_message = json_format_proto3_pb2.TestValue()
+ self.CheckParseBack(message, parsed_message)
+ # Can't parse back if the Value message is not set.
+ message.repeated_value.add()
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, False)),
+ json.loads(
+ '{'
+ ' "value": "hello",'
+ ' "repeatedValue": [11.1, false, null, null]'
+ '}'))
+
+ def testListValueMessage(self):
+ message = json_format_proto3_pb2.TestListValue()
+ message.value.values.add().number_value = 11.1
+ message.value.values.add().null_value = 0
+ message.value.values.add().bool_value = True
+ message.value.values.add().string_value = 'hello'
+ message.value.values.add().struct_value['name'] = 'Jim'
+ message.repeated_value.add().values.add().number_value = 1
+ message.repeated_value.add()
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, False)),
+ json.loads(
+ '{"value": [11.1, null, true, "hello", {"name": "Jim"}]\n,'
+ '"repeatedValue": [[1], []]}'))
+ parsed_message = json_format_proto3_pb2.TestListValue()
+ self.CheckParseBack(message, parsed_message)
+
+ def testAnyMessage(self):
+ message = json_format_proto3_pb2.TestAny()
+ value1 = json_format_proto3_pb2.MessageType()
+ value2 = json_format_proto3_pb2.MessageType()
+ value1.value = 1234
+ value2.value = 5678
+ message.value.Pack(value1)
+ message.repeated_value.add().Pack(value1)
+ message.repeated_value.add().Pack(value2)
+ message.repeated_value.add()
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads(
+ '{\n'
+ ' "repeatedValue": [ {\n'
+ ' "@type": "type.googleapis.com/proto3.MessageType",\n'
+ ' "value": 1234\n'
+ ' }, {\n'
+ ' "@type": "type.googleapis.com/proto3.MessageType",\n'
+ ' "value": 5678\n'
+ ' },\n'
+ ' {}],\n'
+ ' "value": {\n'
+ ' "@type": "type.googleapis.com/proto3.MessageType",\n'
+ ' "value": 1234\n'
+ ' }\n'
+ '}\n'))
+ parsed_message = json_format_proto3_pb2.TestAny()
+ self.CheckParseBack(message, parsed_message)
+ # Must print @type first
+ test_message = json_format_proto3_pb2.TestMessage(
+ bool_value=True,
+ int32_value=20,
+ int64_value=-20,
+ uint32_value=20,
+ uint64_value=20,
+ double_value=3.14,
+ string_value='foo')
+ message.Clear()
+ message.value.Pack(test_message)
+ self.assertEqual(
+ json_format.MessageToJson(message, False)[0:68],
+ '{\n'
+ ' "value": {\n'
+ ' "@type": "type.googleapis.com/proto3.TestMessage"')
+
+ def testWellKnownInAnyMessage(self):
+ message = any_pb2.Any()
+ int32_value = wrappers_pb2.Int32Value()
+ int32_value.value = 1234
+ message.Pack(int32_value)
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads(
+ '{\n'
+ ' "@type": \"type.googleapis.com/google.protobuf.Int32Value\",\n'
+ ' "value": 1234\n'
+ '}\n'))
+ parsed_message = any_pb2.Any()
+ self.CheckParseBack(message, parsed_message)
+
+ timestamp = timestamp_pb2.Timestamp()
+ message.Pack(timestamp)
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads(
+ '{\n'
+ ' "@type": "type.googleapis.com/google.protobuf.Timestamp",\n'
+ ' "value": "1970-01-01T00:00:00Z"\n'
+ '}\n'))
+ self.CheckParseBack(message, parsed_message)
+
+ duration = duration_pb2.Duration()
+ duration.seconds = 1
+ message.Pack(duration)
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads(
+ '{\n'
+ ' "@type": "type.googleapis.com/google.protobuf.Duration",\n'
+ ' "value": "1s"\n'
+ '}\n'))
+ self.CheckParseBack(message, parsed_message)
+
+ field_mask = field_mask_pb2.FieldMask()
+ field_mask.paths.append('foo.bar')
+ field_mask.paths.append('bar')
+ message.Pack(field_mask)
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads(
+ '{\n'
+ ' "@type": "type.googleapis.com/google.protobuf.FieldMask",\n'
+ ' "value": "foo.bar,bar"\n'
+ '}\n'))
+ self.CheckParseBack(message, parsed_message)
+
+ struct_message = struct_pb2.Struct()
+ struct_message['name'] = 'Jim'
+ message.Pack(struct_message)
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads(
+ '{\n'
+ ' "@type": "type.googleapis.com/google.protobuf.Struct",\n'
+ ' "value": {"name": "Jim"}\n'
+ '}\n'))
+ self.CheckParseBack(message, parsed_message)
+
+ nested_any = any_pb2.Any()
+ int32_value.value = 5678
+ nested_any.Pack(int32_value)
+ message.Pack(nested_any)
+ self.assertEqual(
+ json.loads(json_format.MessageToJson(message, True)),
+ json.loads(
+ '{\n'
+ ' "@type": "type.googleapis.com/google.protobuf.Any",\n'
+ ' "value": {\n'
+ ' "@type": "type.googleapis.com/google.protobuf.Int32Value",\n'
+ ' "value": 5678\n'
+ ' }\n'
+ '}\n'))
+ self.CheckParseBack(message, parsed_message)
+
+ def testParseNull(self):
+ message = json_format_proto3_pb2.TestMessage()
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ self.FillAllFields(parsed_message)
+ json_format.Parse('{"int32Value": null, '
+ '"int64Value": null, '
+ '"uint32Value": null,'
+ '"uint64Value": null,'
+ '"floatValue": null,'
+ '"doubleValue": null,'
+ '"boolValue": null,'
+ '"stringValue": null,'
+ '"bytesValue": null,'
+ '"messageValue": null,'
+ '"enumValue": null,'
+ '"repeatedInt32Value": null,'
+ '"repeatedInt64Value": null,'
+ '"repeatedUint32Value": null,'
+ '"repeatedUint64Value": null,'
+ '"repeatedFloatValue": null,'
+ '"repeatedDoubleValue": null,'
+ '"repeatedBoolValue": null,'
+ '"repeatedStringValue": null,'
+ '"repeatedBytesValue": null,'
+ '"repeatedMessageValue": null,'
+ '"repeatedEnumValue": null'
+ '}',
+ parsed_message)
+ self.assertEqual(message, parsed_message)
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'Failed to parse repeatedInt32Value field: '
+ 'null is not allowed to be used as an element in a repeated field.',
+ json_format.Parse,
+ '{"repeatedInt32Value":[1, null]}',
+ parsed_message)
+
+ def testNanFloat(self):
+ message = json_format_proto3_pb2.TestMessage()
+ message.float_value = float('nan')
+ text = '{\n "floatValue": "NaN"\n}'
+ self.assertEqual(json_format.MessageToJson(message), text)
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ json_format.Parse(text, parsed_message)
+ self.assertTrue(math.isnan(parsed_message.float_value))
+
+ def testParseEmptyText(self):
+ self.CheckError('',
+ r'Failed to load JSON: (Expecting value)|(No JSON).')
+
+ def testParseBadEnumValue(self):
+ self.CheckError(
+ '{"enumValue": 1}',
+ 'Enum value must be a string literal with double quotes. '
+ 'Type "proto3.EnumType" has no value named 1.')
+ self.CheckError(
+ '{"enumValue": "baz"}',
+ 'Enum value must be a string literal with double quotes. '
+ 'Type "proto3.EnumType" has no value named baz.')
+
+ def testParseBadIdentifer(self):
+ self.CheckError('{int32Value: 1}',
+ (r'Failed to load JSON: Expecting property name'
+ r'( enclosed in double quotes)?: line 1'))
+ self.CheckError('{"unknownName": 1}',
+ 'Message type "proto3.TestMessage" has no field named '
+ '"unknownName".')
+
+ def testIgnoreUnknownField(self):
+ text = '{"unknownName": 1}'
+ parsed_message = json_format_proto3_pb2.TestMessage()
+ json_format.Parse(text, parsed_message, ignore_unknown_fields=True)
+ text = ('{\n'
+ ' "repeatedValue": [ {\n'
+ ' "@type": "type.googleapis.com/proto3.MessageType",\n'
+ ' "unknownName": 1\n'
+ ' }]\n'
+ '}\n')
+ parsed_message = json_format_proto3_pb2.TestAny()
+ json_format.Parse(text, parsed_message, ignore_unknown_fields=True)
+
+ def testDuplicateField(self):
+ # Duplicate key check is not supported for python2.6
+ if sys.version_info < (2, 7):
+ return
+ self.CheckError('{"int32Value": 1,\n"int32Value":2}',
+ 'Failed to load JSON: duplicate key int32Value.')
+
+ def testInvalidBoolValue(self):
+ self.CheckError('{"boolValue": 1}',
+ 'Failed to parse boolValue field: '
+ 'Expected true or false without quotes.')
+ self.CheckError('{"boolValue": "true"}',
+ 'Failed to parse boolValue field: '
+ 'Expected true or false without quotes.')
+
+ def testInvalidIntegerValue(self):
+ message = json_format_proto3_pb2.TestMessage()
+ text = '{"int32Value": 0x12345}'
+ self.assertRaises(json_format.ParseError,
+ json_format.Parse, text, message)
+ self.CheckError('{"int32Value": 012345}',
+ (r'Failed to load JSON: Expecting \'?,\'? delimiter: '
+ r'line 1.'))
+ self.CheckError('{"int32Value": 1.0}',
+ 'Failed to parse int32Value field: '
+ 'Couldn\'t parse integer: 1.0.')
+ self.CheckError('{"int32Value": " 1 "}',
+ 'Failed to parse int32Value field: '
+ 'Couldn\'t parse integer: " 1 ".')
+ self.CheckError('{"int32Value": "1 "}',
+ 'Failed to parse int32Value field: '
+ 'Couldn\'t parse integer: "1 ".')
+ self.CheckError('{"int32Value": 12345678901234567890}',
+ 'Failed to parse int32Value field: Value out of range: '
+ '12345678901234567890.')
+ self.CheckError('{"int32Value": 1e5}',
+ 'Failed to parse int32Value field: '
+ 'Couldn\'t parse integer: 100000.0.')
+ self.CheckError('{"uint32Value": -1}',
+ 'Failed to parse uint32Value field: '
+ 'Value out of range: -1.')
+
+ def testInvalidFloatValue(self):
+ self.CheckError('{"floatValue": "nan"}',
+ 'Failed to parse floatValue field: Couldn\'t '
+ 'parse float "nan", use "NaN" instead.')
+
+ def testInvalidBytesValue(self):
+ self.CheckError('{"bytesValue": "AQI"}',
+ 'Failed to parse bytesValue field: Incorrect padding.')
+ self.CheckError('{"bytesValue": "AQI*"}',
+ 'Failed to parse bytesValue field: Incorrect padding.')
+
+ def testInvalidMap(self):
+ message = json_format_proto3_pb2.TestMap()
+ text = '{"int32Map": {"null": 2, "2": 3}}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'Failed to parse int32Map field: invalid literal',
+ json_format.Parse, text, message)
+ text = '{"int32Map": {1: 2, "2": 3}}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ (r'Failed to load JSON: Expecting property name'
+ r'( enclosed in double quotes)?: line 1'),
+ json_format.Parse, text, message)
+ text = '{"boolMap": {"null": 1}}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'Failed to parse boolMap field: Expected "true" or "false", not null.',
+ json_format.Parse, text, message)
+ if sys.version_info < (2, 7):
+ return
+ text = r'{"stringMap": {"a": 3, "\u0061": 2}}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'Failed to load JSON: duplicate key a',
+ json_format.Parse, text, message)
+
+ def testInvalidTimestamp(self):
+ message = json_format_proto3_pb2.TestTimestamp()
+ text = '{"value": "10000-01-01T00:00:00.00Z"}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'time data \'10000-01-01T00:00:00\' does not match'
+ ' format \'%Y-%m-%dT%H:%M:%S\'.',
+ json_format.Parse, text, message)
+ text = '{"value": "1970-01-01T00:00:00.0123456789012Z"}'
+ self.assertRaisesRegexp(
+ well_known_types.ParseError,
+ 'nanos 0123456789012 more than 9 fractional digits.',
+ json_format.Parse, text, message)
+ text = '{"value": "1972-01-01T01:00:00.01+08"}'
+ self.assertRaisesRegexp(
+ well_known_types.ParseError,
+ (r'Invalid timezone offset value: \+08.'),
+ json_format.Parse, text, message)
+ # Time smaller than minimum time.
+ text = '{"value": "0000-01-01T00:00:00Z"}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'Failed to parse value field: year is out of range.',
+ json_format.Parse, text, message)
+ # Time bigger than maxinum time.
+ message.value.seconds = 253402300800
+ self.assertRaisesRegexp(
+ OverflowError,
+ 'date value out of range',
+ json_format.MessageToJson, message)
+
+ def testInvalidOneof(self):
+ message = json_format_proto3_pb2.TestOneof()
+ text = '{"oneofInt32Value": 1, "oneofStringValue": "2"}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'Message type "proto3.TestOneof"'
+ ' should not have multiple "oneof_value" oneof fields.',
+ json_format.Parse, text, message)
+
+ def testInvalidListValue(self):
+ message = json_format_proto3_pb2.TestListValue()
+ text = '{"value": 1234}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ r'Failed to parse value field: ListValue must be in \[\] which is 1234',
+ json_format.Parse, text, message)
+
+ def testInvalidStruct(self):
+ message = json_format_proto3_pb2.TestStruct()
+ text = '{"value": 1234}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ 'Failed to parse value field: Struct must be in a dict which is 1234',
+ json_format.Parse, text, message)
+
+ def testInvalidAny(self):
+ message = any_pb2.Any()
+ text = '{"@type": "type.googleapis.com/google.protobuf.Int32Value"}'
+ self.assertRaisesRegexp(
+ KeyError,
+ 'value',
+ json_format.Parse, text, message)
+ text = '{"value": 1234}'
+ self.assertRaisesRegexp(
+ json_format.ParseError,
+ '@type is missing when parsing any message.',
+ json_format.Parse, text, message)
+ text = '{"@type": "type.googleapis.com/MessageNotExist", "value": 1234}'
+ self.assertRaisesRegexp(
+ TypeError,
+ 'Can not find message descriptor by type_url: '
+ 'type.googleapis.com/MessageNotExist.',
+ json_format.Parse, text, message)
+ # Only last part is to be used: b/25630112
+ text = (r'{"@type": "incorrect.googleapis.com/google.protobuf.Int32Value",'
+ r'"value": 1234}')
+ json_format.Parse(text, message)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_factory_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_factory_test.py
new file mode 100644
index 0000000000..7bb7d1acec
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_factory_test.py
@@ -0,0 +1,190 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests for google.protobuf.message_factory."""
+
+__author__ = 'matthewtoia@google.com (Matt Toia)'
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import descriptor_pb2
+from google.protobuf.internal import factory_test1_pb2
+from google.protobuf.internal import factory_test2_pb2
+from google.protobuf import descriptor_database
+from google.protobuf import descriptor_pool
+from google.protobuf import message_factory
+
+
+class MessageFactoryTest(unittest.TestCase):
+
+ def setUp(self):
+ self.factory_test1_fd = descriptor_pb2.FileDescriptorProto.FromString(
+ factory_test1_pb2.DESCRIPTOR.serialized_pb)
+ self.factory_test2_fd = descriptor_pb2.FileDescriptorProto.FromString(
+ factory_test2_pb2.DESCRIPTOR.serialized_pb)
+
+ def _ExerciseDynamicClass(self, cls):
+ msg = cls()
+ msg.mandatory = 42
+ msg.nested_factory_2_enum = 0
+ msg.nested_factory_2_message.value = 'nested message value'
+ msg.factory_1_message.factory_1_enum = 1
+ msg.factory_1_message.nested_factory_1_enum = 0
+ msg.factory_1_message.nested_factory_1_message.value = (
+ 'nested message value')
+ msg.factory_1_message.scalar_value = 22
+ msg.factory_1_message.list_value.extend([u'one', u'two', u'three'])
+ msg.factory_1_message.list_value.append(u'four')
+ msg.factory_1_enum = 1
+ msg.nested_factory_1_enum = 0
+ msg.nested_factory_1_message.value = 'nested message value'
+ msg.circular_message.mandatory = 1
+ msg.circular_message.circular_message.mandatory = 2
+ msg.circular_message.scalar_value = 'one deep'
+ msg.scalar_value = 'zero deep'
+ msg.list_value.extend([u'four', u'three', u'two'])
+ msg.list_value.append(u'one')
+ msg.grouped.add()
+ msg.grouped[0].part_1 = 'hello'
+ msg.grouped[0].part_2 = 'world'
+ msg.grouped.add(part_1='testing', part_2='123')
+ msg.loop.loop.mandatory = 2
+ msg.loop.loop.loop.loop.mandatory = 4
+ serialized = msg.SerializeToString()
+ converted = factory_test2_pb2.Factory2Message.FromString(serialized)
+ reserialized = converted.SerializeToString()
+ self.assertEqual(serialized, reserialized)
+ result = cls.FromString(reserialized)
+ self.assertEqual(msg, result)
+
+ def testGetPrototype(self):
+ db = descriptor_database.DescriptorDatabase()
+ pool = descriptor_pool.DescriptorPool(db)
+ db.Add(self.factory_test1_fd)
+ db.Add(self.factory_test2_fd)
+ factory = message_factory.MessageFactory()
+ cls = factory.GetPrototype(pool.FindMessageTypeByName(
+ 'google.protobuf.python.internal.Factory2Message'))
+ self.assertFalse(cls is factory_test2_pb2.Factory2Message)
+ self._ExerciseDynamicClass(cls)
+ cls2 = factory.GetPrototype(pool.FindMessageTypeByName(
+ 'google.protobuf.python.internal.Factory2Message'))
+ self.assertTrue(cls is cls2)
+
+ def testGetMessages(self):
+ # performed twice because multiple calls with the same input must be allowed
+ for _ in range(2):
+ messages = message_factory.GetMessages([self.factory_test1_fd,
+ self.factory_test2_fd])
+ self.assertTrue(
+ set(['google.protobuf.python.internal.Factory2Message',
+ 'google.protobuf.python.internal.Factory1Message'],
+ ).issubset(set(messages.keys())))
+ self._ExerciseDynamicClass(
+ messages['google.protobuf.python.internal.Factory2Message'])
+ self.assertTrue(
+ set(['google.protobuf.python.internal.Factory2Message.one_more_field',
+ 'google.protobuf.python.internal.another_field'],
+ ).issubset(
+ set(messages['google.protobuf.python.internal.Factory1Message']
+ ._extensions_by_name.keys())))
+ factory_msg1 = messages['google.protobuf.python.internal.Factory1Message']
+ msg1 = messages['google.protobuf.python.internal.Factory1Message']()
+ ext1 = factory_msg1._extensions_by_name[
+ 'google.protobuf.python.internal.Factory2Message.one_more_field']
+ ext2 = factory_msg1._extensions_by_name[
+ 'google.protobuf.python.internal.another_field']
+ msg1.Extensions[ext1] = 'test1'
+ msg1.Extensions[ext2] = 'test2'
+ self.assertEqual('test1', msg1.Extensions[ext1])
+ self.assertEqual('test2', msg1.Extensions[ext2])
+
+ def testDuplicateExtensionNumber(self):
+ pool = descriptor_pool.DescriptorPool()
+ factory = message_factory.MessageFactory(pool=pool)
+
+ # Add Container message.
+ f = descriptor_pb2.FileDescriptorProto()
+ f.name = 'google/protobuf/internal/container.proto'
+ f.package = 'google.protobuf.python.internal'
+ msg = f.message_type.add()
+ msg.name = 'Container'
+ rng = msg.extension_range.add()
+ rng.start = 1
+ rng.end = 10
+ pool.Add(f)
+ msgs = factory.GetMessages([f.name])
+ self.assertIn('google.protobuf.python.internal.Container', msgs)
+
+ # Extend container.
+ f = descriptor_pb2.FileDescriptorProto()
+ f.name = 'google/protobuf/internal/extension.proto'
+ f.package = 'google.protobuf.python.internal'
+ f.dependency.append('google/protobuf/internal/container.proto')
+ msg = f.message_type.add()
+ msg.name = 'Extension'
+ ext = msg.extension.add()
+ ext.name = 'extension_field'
+ ext.number = 2
+ ext.label = descriptor_pb2.FieldDescriptorProto.LABEL_OPTIONAL
+ ext.type_name = 'Extension'
+ ext.extendee = 'Container'
+ pool.Add(f)
+ msgs = factory.GetMessages([f.name])
+ self.assertIn('google.protobuf.python.internal.Extension', msgs)
+
+ # Add Duplicate extending the same field number.
+ f = descriptor_pb2.FileDescriptorProto()
+ f.name = 'google/protobuf/internal/duplicate.proto'
+ f.package = 'google.protobuf.python.internal'
+ f.dependency.append('google/protobuf/internal/container.proto')
+ msg = f.message_type.add()
+ msg.name = 'Duplicate'
+ ext = msg.extension.add()
+ ext.name = 'extension_field'
+ ext.number = 2
+ ext.label = descriptor_pb2.FieldDescriptorProto.LABEL_OPTIONAL
+ ext.type_name = 'Duplicate'
+ ext.extendee = 'Container'
+ pool.Add(f)
+
+ with self.assertRaises(Exception) as cm:
+ factory.GetMessages([f.name])
+
+ self.assertIsInstance(cm.exception, (AssertionError, ValueError))
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_listener.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_listener.py
new file mode 100755
index 0000000000..0fc255a774
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_listener.py
@@ -0,0 +1,78 @@
+# 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.
+
+"""Defines a listener interface for observing certain
+state transitions on Message objects.
+
+Also defines a null implementation of this interface.
+"""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+
+class MessageListener(object):
+
+ """Listens for modifications made to a message. Meant to be registered via
+ Message._SetListener().
+
+ Attributes:
+ dirty: If True, then calling Modified() would be a no-op. This can be
+ used to avoid these calls entirely in the common case.
+ """
+
+ def Modified(self):
+ """Called every time the message is modified in such a way that the parent
+ message may need to be updated. This currently means either:
+ (a) The message was modified for the first time, so the parent message
+ should henceforth mark the message as present.
+ (b) The message's cached byte size became dirty -- i.e. the message was
+ modified for the first time after a previous call to ByteSize().
+ Therefore the parent should also mark its byte size as dirty.
+ Note that (a) implies (b), since new objects start out with a client cached
+ size (zero). However, we document (a) explicitly because it is important.
+
+ Modified() will *only* be called in response to one of these two events --
+ not every time the sub-message is modified.
+
+ Note that if the listener's |dirty| attribute is true, then calling
+ Modified at the moment would be a no-op, so it can be skipped. Performance-
+ sensitive callers should check this attribute directly before calling since
+ it will be true most of the time.
+ """
+
+ raise NotImplementedError
+
+
+class NullMessageListener(object):
+
+ """No-op MessageListener implementation."""
+
+ def Modified(self):
+ pass
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_set_extensions.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_set_extensions.proto
new file mode 100644
index 0000000000..14e5f19375
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_set_extensions.proto
@@ -0,0 +1,74 @@
+// 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.
+
+// This file contains messages that extend MessageSet.
+
+syntax = "proto2";
+package google.protobuf.internal;
+
+
+// A message with message_set_wire_format.
+message TestMessageSet {
+ option message_set_wire_format = true;
+ extensions 4 to max;
+}
+
+message TestMessageSetExtension1 {
+ extend TestMessageSet {
+ optional TestMessageSetExtension1 message_set_extension = 98418603;
+ }
+ optional int32 i = 15;
+}
+
+message TestMessageSetExtension2 {
+ extend TestMessageSet {
+ optional TestMessageSetExtension2 message_set_extension = 98418634;
+ }
+ optional string str = 25;
+}
+
+message TestMessageSetExtension3 {
+ optional string text = 35;
+}
+
+extend TestMessageSet {
+ optional TestMessageSetExtension3 message_set_extension3 = 98418655;
+}
+
+// This message was used to generate
+// //net/proto2/python/internal/testdata/message_set_message, but is commented
+// out since it must not actually exist in code, to simulate an "unknown"
+// extension.
+// message TestMessageSetUnknownExtension {
+// extend TestMessageSet {
+// optional TestMessageSetUnknownExtension message_set_extension = 56141421;
+// }
+// optional int64 a = 1;
+// }
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_test.py
new file mode 100755
index 0000000000..1e95adf9cd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/message_test.py
@@ -0,0 +1,1856 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests python protocol buffers against the golden message.
+
+Note that the golden messages exercise every known field type, thus this
+test ends up exercising and verifying nearly all of the parsing and
+serialization code in the whole library.
+
+TODO(kenton): Merge with wire_format_test? It doesn't make a whole lot of
+sense to call this a test of the "message" module, which only declares an
+abstract interface.
+"""
+
+__author__ = 'gps@google.com (Gregory P. Smith)'
+
+
+import collections
+import copy
+import math
+import operator
+import pickle
+import six
+import sys
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import map_unittest_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import unittest_proto3_arena_pb2
+from google.protobuf import descriptor_pb2
+from google.protobuf import descriptor_pool
+from google.protobuf import message_factory
+from google.protobuf import text_format
+from google.protobuf.internal import api_implementation
+from google.protobuf.internal import packed_field_test_pb2
+from google.protobuf.internal import test_util
+from google.protobuf import message
+from google.protobuf.internal import _parameterized
+
+if six.PY3:
+ long = int
+
+
+# Python pre-2.6 does not have isinf() or isnan() functions, so we have
+# to provide our own.
+def isnan(val):
+ # NaN is never equal to itself.
+ return val != val
+def isinf(val):
+ # Infinity times zero equals NaN.
+ return not isnan(val) and isnan(val * 0)
+def IsPosInf(val):
+ return isinf(val) and (val > 0)
+def IsNegInf(val):
+ return isinf(val) and (val < 0)
+
+
+@_parameterized.Parameters(
+ (unittest_pb2),
+ (unittest_proto3_arena_pb2))
+class MessageTest(unittest.TestCase):
+
+ def testBadUtf8String(self, message_module):
+ if api_implementation.Type() != 'python':
+ self.skipTest("Skipping testBadUtf8String, currently only the python "
+ "api implementation raises UnicodeDecodeError when a "
+ "string field contains bad utf-8.")
+ bad_utf8_data = test_util.GoldenFileData('bad_utf8_string')
+ with self.assertRaises(UnicodeDecodeError) as context:
+ message_module.TestAllTypes.FromString(bad_utf8_data)
+ self.assertIn('TestAllTypes.optional_string', str(context.exception))
+
+ def testGoldenMessage(self, message_module):
+ # Proto3 doesn't have the "default_foo" members or foreign enums,
+ # and doesn't preserve unknown fields, so for proto3 we use a golden
+ # message that doesn't have these fields set.
+ if message_module is unittest_pb2:
+ golden_data = test_util.GoldenFileData(
+ 'golden_message_oneof_implemented')
+ else:
+ golden_data = test_util.GoldenFileData('golden_message_proto3')
+
+ golden_message = message_module.TestAllTypes()
+ golden_message.ParseFromString(golden_data)
+ if message_module is unittest_pb2:
+ test_util.ExpectAllFieldsSet(self, golden_message)
+ self.assertEqual(golden_data, golden_message.SerializeToString())
+ golden_copy = copy.deepcopy(golden_message)
+ self.assertEqual(golden_data, golden_copy.SerializeToString())
+
+ def testGoldenPackedMessage(self, message_module):
+ golden_data = test_util.GoldenFileData('golden_packed_fields_message')
+ golden_message = message_module.TestPackedTypes()
+ golden_message.ParseFromString(golden_data)
+ all_set = message_module.TestPackedTypes()
+ test_util.SetAllPackedFields(all_set)
+ self.assertEqual(all_set, golden_message)
+ self.assertEqual(golden_data, all_set.SerializeToString())
+ golden_copy = copy.deepcopy(golden_message)
+ self.assertEqual(golden_data, golden_copy.SerializeToString())
+
+ def testPickleSupport(self, message_module):
+ golden_data = test_util.GoldenFileData('golden_message')
+ golden_message = message_module.TestAllTypes()
+ golden_message.ParseFromString(golden_data)
+ pickled_message = pickle.dumps(golden_message)
+
+ unpickled_message = pickle.loads(pickled_message)
+ self.assertEqual(unpickled_message, golden_message)
+
+ def testPositiveInfinity(self, message_module):
+ if message_module is unittest_pb2:
+ golden_data = (b'\x5D\x00\x00\x80\x7F'
+ b'\x61\x00\x00\x00\x00\x00\x00\xF0\x7F'
+ b'\xCD\x02\x00\x00\x80\x7F'
+ b'\xD1\x02\x00\x00\x00\x00\x00\x00\xF0\x7F')
+ else:
+ golden_data = (b'\x5D\x00\x00\x80\x7F'
+ b'\x61\x00\x00\x00\x00\x00\x00\xF0\x7F'
+ b'\xCA\x02\x04\x00\x00\x80\x7F'
+ b'\xD2\x02\x08\x00\x00\x00\x00\x00\x00\xF0\x7F')
+
+ golden_message = message_module.TestAllTypes()
+ golden_message.ParseFromString(golden_data)
+ self.assertTrue(IsPosInf(golden_message.optional_float))
+ self.assertTrue(IsPosInf(golden_message.optional_double))
+ self.assertTrue(IsPosInf(golden_message.repeated_float[0]))
+ self.assertTrue(IsPosInf(golden_message.repeated_double[0]))
+ self.assertEqual(golden_data, golden_message.SerializeToString())
+
+ def testNegativeInfinity(self, message_module):
+ if message_module is unittest_pb2:
+ golden_data = (b'\x5D\x00\x00\x80\xFF'
+ b'\x61\x00\x00\x00\x00\x00\x00\xF0\xFF'
+ b'\xCD\x02\x00\x00\x80\xFF'
+ b'\xD1\x02\x00\x00\x00\x00\x00\x00\xF0\xFF')
+ else:
+ golden_data = (b'\x5D\x00\x00\x80\xFF'
+ b'\x61\x00\x00\x00\x00\x00\x00\xF0\xFF'
+ b'\xCA\x02\x04\x00\x00\x80\xFF'
+ b'\xD2\x02\x08\x00\x00\x00\x00\x00\x00\xF0\xFF')
+
+ golden_message = message_module.TestAllTypes()
+ golden_message.ParseFromString(golden_data)
+ self.assertTrue(IsNegInf(golden_message.optional_float))
+ self.assertTrue(IsNegInf(golden_message.optional_double))
+ self.assertTrue(IsNegInf(golden_message.repeated_float[0]))
+ self.assertTrue(IsNegInf(golden_message.repeated_double[0]))
+ self.assertEqual(golden_data, golden_message.SerializeToString())
+
+ def testNotANumber(self, message_module):
+ golden_data = (b'\x5D\x00\x00\xC0\x7F'
+ b'\x61\x00\x00\x00\x00\x00\x00\xF8\x7F'
+ b'\xCD\x02\x00\x00\xC0\x7F'
+ b'\xD1\x02\x00\x00\x00\x00\x00\x00\xF8\x7F')
+ golden_message = message_module.TestAllTypes()
+ golden_message.ParseFromString(golden_data)
+ self.assertTrue(isnan(golden_message.optional_float))
+ self.assertTrue(isnan(golden_message.optional_double))
+ self.assertTrue(isnan(golden_message.repeated_float[0]))
+ self.assertTrue(isnan(golden_message.repeated_double[0]))
+
+ # The protocol buffer may serialize to any one of multiple different
+ # representations of a NaN. Rather than verify a specific representation,
+ # verify the serialized string can be converted into a correctly
+ # behaving protocol buffer.
+ serialized = golden_message.SerializeToString()
+ message = message_module.TestAllTypes()
+ message.ParseFromString(serialized)
+ self.assertTrue(isnan(message.optional_float))
+ self.assertTrue(isnan(message.optional_double))
+ self.assertTrue(isnan(message.repeated_float[0]))
+ self.assertTrue(isnan(message.repeated_double[0]))
+
+ def testPositiveInfinityPacked(self, message_module):
+ golden_data = (b'\xA2\x06\x04\x00\x00\x80\x7F'
+ b'\xAA\x06\x08\x00\x00\x00\x00\x00\x00\xF0\x7F')
+ golden_message = message_module.TestPackedTypes()
+ golden_message.ParseFromString(golden_data)
+ self.assertTrue(IsPosInf(golden_message.packed_float[0]))
+ self.assertTrue(IsPosInf(golden_message.packed_double[0]))
+ self.assertEqual(golden_data, golden_message.SerializeToString())
+
+ def testNegativeInfinityPacked(self, message_module):
+ golden_data = (b'\xA2\x06\x04\x00\x00\x80\xFF'
+ b'\xAA\x06\x08\x00\x00\x00\x00\x00\x00\xF0\xFF')
+ golden_message = message_module.TestPackedTypes()
+ golden_message.ParseFromString(golden_data)
+ self.assertTrue(IsNegInf(golden_message.packed_float[0]))
+ self.assertTrue(IsNegInf(golden_message.packed_double[0]))
+ self.assertEqual(golden_data, golden_message.SerializeToString())
+
+ def testNotANumberPacked(self, message_module):
+ golden_data = (b'\xA2\x06\x04\x00\x00\xC0\x7F'
+ b'\xAA\x06\x08\x00\x00\x00\x00\x00\x00\xF8\x7F')
+ golden_message = message_module.TestPackedTypes()
+ golden_message.ParseFromString(golden_data)
+ self.assertTrue(isnan(golden_message.packed_float[0]))
+ self.assertTrue(isnan(golden_message.packed_double[0]))
+
+ serialized = golden_message.SerializeToString()
+ message = message_module.TestPackedTypes()
+ message.ParseFromString(serialized)
+ self.assertTrue(isnan(message.packed_float[0]))
+ self.assertTrue(isnan(message.packed_double[0]))
+
+ def testExtremeFloatValues(self, message_module):
+ message = message_module.TestAllTypes()
+
+ # Most positive exponent, no significand bits set.
+ kMostPosExponentNoSigBits = math.pow(2, 127)
+ message.optional_float = kMostPosExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == kMostPosExponentNoSigBits)
+
+ # Most positive exponent, one significand bit set.
+ kMostPosExponentOneSigBit = 1.5 * math.pow(2, 127)
+ message.optional_float = kMostPosExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == kMostPosExponentOneSigBit)
+
+ # Repeat last two cases with values of same magnitude, but negative.
+ message.optional_float = -kMostPosExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == -kMostPosExponentNoSigBits)
+
+ message.optional_float = -kMostPosExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == -kMostPosExponentOneSigBit)
+
+ # Most negative exponent, no significand bits set.
+ kMostNegExponentNoSigBits = math.pow(2, -127)
+ message.optional_float = kMostNegExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == kMostNegExponentNoSigBits)
+
+ # Most negative exponent, one significand bit set.
+ kMostNegExponentOneSigBit = 1.5 * math.pow(2, -127)
+ message.optional_float = kMostNegExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == kMostNegExponentOneSigBit)
+
+ # Repeat last two cases with values of the same magnitude, but negative.
+ message.optional_float = -kMostNegExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == -kMostNegExponentNoSigBits)
+
+ message.optional_float = -kMostNegExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_float == -kMostNegExponentOneSigBit)
+
+ def testExtremeDoubleValues(self, message_module):
+ message = message_module.TestAllTypes()
+
+ # Most positive exponent, no significand bits set.
+ kMostPosExponentNoSigBits = math.pow(2, 1023)
+ message.optional_double = kMostPosExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == kMostPosExponentNoSigBits)
+
+ # Most positive exponent, one significand bit set.
+ kMostPosExponentOneSigBit = 1.5 * math.pow(2, 1023)
+ message.optional_double = kMostPosExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == kMostPosExponentOneSigBit)
+
+ # Repeat last two cases with values of same magnitude, but negative.
+ message.optional_double = -kMostPosExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == -kMostPosExponentNoSigBits)
+
+ message.optional_double = -kMostPosExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == -kMostPosExponentOneSigBit)
+
+ # Most negative exponent, no significand bits set.
+ kMostNegExponentNoSigBits = math.pow(2, -1023)
+ message.optional_double = kMostNegExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == kMostNegExponentNoSigBits)
+
+ # Most negative exponent, one significand bit set.
+ kMostNegExponentOneSigBit = 1.5 * math.pow(2, -1023)
+ message.optional_double = kMostNegExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == kMostNegExponentOneSigBit)
+
+ # Repeat last two cases with values of the same magnitude, but negative.
+ message.optional_double = -kMostNegExponentNoSigBits
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == -kMostNegExponentNoSigBits)
+
+ message.optional_double = -kMostNegExponentOneSigBit
+ message.ParseFromString(message.SerializeToString())
+ self.assertTrue(message.optional_double == -kMostNegExponentOneSigBit)
+
+ def testFloatPrinting(self, message_module):
+ message = message_module.TestAllTypes()
+ message.optional_float = 2.0
+ self.assertEqual(str(message), 'optional_float: 2.0\n')
+
+ def testHighPrecisionFloatPrinting(self, message_module):
+ message = message_module.TestAllTypes()
+ message.optional_double = 0.12345678912345678
+ if sys.version_info >= (3,):
+ self.assertEqual(str(message), 'optional_double: 0.12345678912345678\n')
+ else:
+ self.assertEqual(str(message), 'optional_double: 0.123456789123\n')
+
+ def testUnknownFieldPrinting(self, message_module):
+ populated = message_module.TestAllTypes()
+ test_util.SetAllNonLazyFields(populated)
+ empty = message_module.TestEmptyMessage()
+ empty.ParseFromString(populated.SerializeToString())
+ self.assertEqual(str(empty), '')
+
+ def testRepeatedNestedFieldIteration(self, message_module):
+ msg = message_module.TestAllTypes()
+ msg.repeated_nested_message.add(bb=1)
+ msg.repeated_nested_message.add(bb=2)
+ msg.repeated_nested_message.add(bb=3)
+ msg.repeated_nested_message.add(bb=4)
+
+ self.assertEqual([1, 2, 3, 4],
+ [m.bb for m in msg.repeated_nested_message])
+ self.assertEqual([4, 3, 2, 1],
+ [m.bb for m in reversed(msg.repeated_nested_message)])
+ self.assertEqual([4, 3, 2, 1],
+ [m.bb for m in msg.repeated_nested_message[::-1]])
+
+ def testSortingRepeatedScalarFieldsDefaultComparator(self, message_module):
+ """Check some different types with the default comparator."""
+ message = message_module.TestAllTypes()
+
+ # TODO(mattp): would testing more scalar types strengthen test?
+ message.repeated_int32.append(1)
+ message.repeated_int32.append(3)
+ message.repeated_int32.append(2)
+ message.repeated_int32.sort()
+ self.assertEqual(message.repeated_int32[0], 1)
+ self.assertEqual(message.repeated_int32[1], 2)
+ self.assertEqual(message.repeated_int32[2], 3)
+
+ message.repeated_float.append(1.1)
+ message.repeated_float.append(1.3)
+ message.repeated_float.append(1.2)
+ message.repeated_float.sort()
+ self.assertAlmostEqual(message.repeated_float[0], 1.1)
+ self.assertAlmostEqual(message.repeated_float[1], 1.2)
+ self.assertAlmostEqual(message.repeated_float[2], 1.3)
+
+ message.repeated_string.append('a')
+ message.repeated_string.append('c')
+ message.repeated_string.append('b')
+ message.repeated_string.sort()
+ self.assertEqual(message.repeated_string[0], 'a')
+ self.assertEqual(message.repeated_string[1], 'b')
+ self.assertEqual(message.repeated_string[2], 'c')
+
+ message.repeated_bytes.append(b'a')
+ message.repeated_bytes.append(b'c')
+ message.repeated_bytes.append(b'b')
+ message.repeated_bytes.sort()
+ self.assertEqual(message.repeated_bytes[0], b'a')
+ self.assertEqual(message.repeated_bytes[1], b'b')
+ self.assertEqual(message.repeated_bytes[2], b'c')
+
+ def testSortingRepeatedScalarFieldsCustomComparator(self, message_module):
+ """Check some different types with custom comparator."""
+ message = message_module.TestAllTypes()
+
+ message.repeated_int32.append(-3)
+ message.repeated_int32.append(-2)
+ message.repeated_int32.append(-1)
+ message.repeated_int32.sort(key=abs)
+ self.assertEqual(message.repeated_int32[0], -1)
+ self.assertEqual(message.repeated_int32[1], -2)
+ self.assertEqual(message.repeated_int32[2], -3)
+
+ message.repeated_string.append('aaa')
+ message.repeated_string.append('bb')
+ message.repeated_string.append('c')
+ message.repeated_string.sort(key=len)
+ self.assertEqual(message.repeated_string[0], 'c')
+ self.assertEqual(message.repeated_string[1], 'bb')
+ self.assertEqual(message.repeated_string[2], 'aaa')
+
+ def testSortingRepeatedCompositeFieldsCustomComparator(self, message_module):
+ """Check passing a custom comparator to sort a repeated composite field."""
+ message = message_module.TestAllTypes()
+
+ message.repeated_nested_message.add().bb = 1
+ message.repeated_nested_message.add().bb = 3
+ message.repeated_nested_message.add().bb = 2
+ message.repeated_nested_message.add().bb = 6
+ message.repeated_nested_message.add().bb = 5
+ message.repeated_nested_message.add().bb = 4
+ message.repeated_nested_message.sort(key=operator.attrgetter('bb'))
+ self.assertEqual(message.repeated_nested_message[0].bb, 1)
+ self.assertEqual(message.repeated_nested_message[1].bb, 2)
+ self.assertEqual(message.repeated_nested_message[2].bb, 3)
+ self.assertEqual(message.repeated_nested_message[3].bb, 4)
+ self.assertEqual(message.repeated_nested_message[4].bb, 5)
+ self.assertEqual(message.repeated_nested_message[5].bb, 6)
+
+ def testSortingRepeatedCompositeFieldsStable(self, message_module):
+ """Check passing a custom comparator to sort a repeated composite field."""
+ message = message_module.TestAllTypes()
+
+ message.repeated_nested_message.add().bb = 21
+ message.repeated_nested_message.add().bb = 20
+ message.repeated_nested_message.add().bb = 13
+ message.repeated_nested_message.add().bb = 33
+ message.repeated_nested_message.add().bb = 11
+ message.repeated_nested_message.add().bb = 24
+ message.repeated_nested_message.add().bb = 10
+ message.repeated_nested_message.sort(key=lambda z: z.bb // 10)
+ self.assertEqual(
+ [13, 11, 10, 21, 20, 24, 33],
+ [n.bb for n in message.repeated_nested_message])
+
+ # Make sure that for the C++ implementation, the underlying fields
+ # are actually reordered.
+ pb = message.SerializeToString()
+ message.Clear()
+ message.MergeFromString(pb)
+ self.assertEqual(
+ [13, 11, 10, 21, 20, 24, 33],
+ [n.bb for n in message.repeated_nested_message])
+
+ def testRepeatedCompositeFieldSortArguments(self, message_module):
+ """Check sorting a repeated composite field using list.sort() arguments."""
+ message = message_module.TestAllTypes()
+
+ get_bb = operator.attrgetter('bb')
+ cmp_bb = lambda a, b: cmp(a.bb, b.bb)
+ message.repeated_nested_message.add().bb = 1
+ message.repeated_nested_message.add().bb = 3
+ message.repeated_nested_message.add().bb = 2
+ message.repeated_nested_message.add().bb = 6
+ message.repeated_nested_message.add().bb = 5
+ message.repeated_nested_message.add().bb = 4
+ message.repeated_nested_message.sort(key=get_bb)
+ self.assertEqual([k.bb for k in message.repeated_nested_message],
+ [1, 2, 3, 4, 5, 6])
+ message.repeated_nested_message.sort(key=get_bb, reverse=True)
+ self.assertEqual([k.bb for k in message.repeated_nested_message],
+ [6, 5, 4, 3, 2, 1])
+ if sys.version_info >= (3,): return # No cmp sorting in PY3.
+ message.repeated_nested_message.sort(sort_function=cmp_bb)
+ self.assertEqual([k.bb for k in message.repeated_nested_message],
+ [1, 2, 3, 4, 5, 6])
+ message.repeated_nested_message.sort(cmp=cmp_bb, reverse=True)
+ self.assertEqual([k.bb for k in message.repeated_nested_message],
+ [6, 5, 4, 3, 2, 1])
+
+ def testRepeatedScalarFieldSortArguments(self, message_module):
+ """Check sorting a scalar field using list.sort() arguments."""
+ message = message_module.TestAllTypes()
+
+ message.repeated_int32.append(-3)
+ message.repeated_int32.append(-2)
+ message.repeated_int32.append(-1)
+ message.repeated_int32.sort(key=abs)
+ self.assertEqual(list(message.repeated_int32), [-1, -2, -3])
+ message.repeated_int32.sort(key=abs, reverse=True)
+ self.assertEqual(list(message.repeated_int32), [-3, -2, -1])
+ if sys.version_info < (3,): # No cmp sorting in PY3.
+ abs_cmp = lambda a, b: cmp(abs(a), abs(b))
+ message.repeated_int32.sort(sort_function=abs_cmp)
+ self.assertEqual(list(message.repeated_int32), [-1, -2, -3])
+ message.repeated_int32.sort(cmp=abs_cmp, reverse=True)
+ self.assertEqual(list(message.repeated_int32), [-3, -2, -1])
+
+ message.repeated_string.append('aaa')
+ message.repeated_string.append('bb')
+ message.repeated_string.append('c')
+ message.repeated_string.sort(key=len)
+ self.assertEqual(list(message.repeated_string), ['c', 'bb', 'aaa'])
+ message.repeated_string.sort(key=len, reverse=True)
+ self.assertEqual(list(message.repeated_string), ['aaa', 'bb', 'c'])
+ if sys.version_info < (3,): # No cmp sorting in PY3.
+ len_cmp = lambda a, b: cmp(len(a), len(b))
+ message.repeated_string.sort(sort_function=len_cmp)
+ self.assertEqual(list(message.repeated_string), ['c', 'bb', 'aaa'])
+ message.repeated_string.sort(cmp=len_cmp, reverse=True)
+ self.assertEqual(list(message.repeated_string), ['aaa', 'bb', 'c'])
+
+ def testRepeatedFieldsComparable(self, message_module):
+ m1 = message_module.TestAllTypes()
+ m2 = message_module.TestAllTypes()
+ m1.repeated_int32.append(0)
+ m1.repeated_int32.append(1)
+ m1.repeated_int32.append(2)
+ m2.repeated_int32.append(0)
+ m2.repeated_int32.append(1)
+ m2.repeated_int32.append(2)
+ m1.repeated_nested_message.add().bb = 1
+ m1.repeated_nested_message.add().bb = 2
+ m1.repeated_nested_message.add().bb = 3
+ m2.repeated_nested_message.add().bb = 1
+ m2.repeated_nested_message.add().bb = 2
+ m2.repeated_nested_message.add().bb = 3
+
+ if sys.version_info >= (3,): return # No cmp() in PY3.
+
+ # These comparisons should not raise errors.
+ _ = m1 < m2
+ _ = m1.repeated_nested_message < m2.repeated_nested_message
+
+ # Make sure cmp always works. If it wasn't defined, these would be
+ # id() comparisons and would all fail.
+ self.assertEqual(cmp(m1, m2), 0)
+ self.assertEqual(cmp(m1.repeated_int32, m2.repeated_int32), 0)
+ self.assertEqual(cmp(m1.repeated_int32, [0, 1, 2]), 0)
+ self.assertEqual(cmp(m1.repeated_nested_message,
+ m2.repeated_nested_message), 0)
+ with self.assertRaises(TypeError):
+ # Can't compare repeated composite containers to lists.
+ cmp(m1.repeated_nested_message, m2.repeated_nested_message[:])
+
+ # TODO(anuraag): Implement extensiondict comparison in C++ and then add test
+
+ def testRepeatedFieldsAreSequences(self, message_module):
+ m = message_module.TestAllTypes()
+ self.assertIsInstance(m.repeated_int32, collections.MutableSequence)
+ self.assertIsInstance(m.repeated_nested_message,
+ collections.MutableSequence)
+
+ def ensureNestedMessageExists(self, msg, attribute):
+ """Make sure that a nested message object exists.
+
+ As soon as a nested message attribute is accessed, it will be present in the
+ _fields dict, without being marked as actually being set.
+ """
+ getattr(msg, attribute)
+ self.assertFalse(msg.HasField(attribute))
+
+ def testOneofGetCaseNonexistingField(self, message_module):
+ m = message_module.TestAllTypes()
+ self.assertRaises(ValueError, m.WhichOneof, 'no_such_oneof_field')
+
+ def testOneofDefaultValues(self, message_module):
+ m = message_module.TestAllTypes()
+ self.assertIs(None, m.WhichOneof('oneof_field'))
+ self.assertFalse(m.HasField('oneof_uint32'))
+
+ # Oneof is set even when setting it to a default value.
+ m.oneof_uint32 = 0
+ self.assertEqual('oneof_uint32', m.WhichOneof('oneof_field'))
+ self.assertTrue(m.HasField('oneof_uint32'))
+ self.assertFalse(m.HasField('oneof_string'))
+
+ m.oneof_string = ""
+ self.assertEqual('oneof_string', m.WhichOneof('oneof_field'))
+ self.assertTrue(m.HasField('oneof_string'))
+ self.assertFalse(m.HasField('oneof_uint32'))
+
+ def testOneofSemantics(self, message_module):
+ m = message_module.TestAllTypes()
+ self.assertIs(None, m.WhichOneof('oneof_field'))
+
+ m.oneof_uint32 = 11
+ self.assertEqual('oneof_uint32', m.WhichOneof('oneof_field'))
+ self.assertTrue(m.HasField('oneof_uint32'))
+
+ m.oneof_string = u'foo'
+ self.assertEqual('oneof_string', m.WhichOneof('oneof_field'))
+ self.assertFalse(m.HasField('oneof_uint32'))
+ self.assertTrue(m.HasField('oneof_string'))
+
+ # Read nested message accessor without accessing submessage.
+ m.oneof_nested_message
+ self.assertEqual('oneof_string', m.WhichOneof('oneof_field'))
+ self.assertTrue(m.HasField('oneof_string'))
+ self.assertFalse(m.HasField('oneof_nested_message'))
+
+ # Read accessor of nested message without accessing submessage.
+ m.oneof_nested_message.bb
+ self.assertEqual('oneof_string', m.WhichOneof('oneof_field'))
+ self.assertTrue(m.HasField('oneof_string'))
+ self.assertFalse(m.HasField('oneof_nested_message'))
+
+ m.oneof_nested_message.bb = 11
+ self.assertEqual('oneof_nested_message', m.WhichOneof('oneof_field'))
+ self.assertFalse(m.HasField('oneof_string'))
+ self.assertTrue(m.HasField('oneof_nested_message'))
+
+ m.oneof_bytes = b'bb'
+ self.assertEqual('oneof_bytes', m.WhichOneof('oneof_field'))
+ self.assertFalse(m.HasField('oneof_nested_message'))
+ self.assertTrue(m.HasField('oneof_bytes'))
+
+ def testOneofCompositeFieldReadAccess(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+
+ self.ensureNestedMessageExists(m, 'oneof_nested_message')
+ self.assertEqual('oneof_uint32', m.WhichOneof('oneof_field'))
+ self.assertEqual(11, m.oneof_uint32)
+
+ def testOneofWhichOneof(self, message_module):
+ m = message_module.TestAllTypes()
+ self.assertIs(None, m.WhichOneof('oneof_field'))
+ if message_module is unittest_pb2:
+ self.assertFalse(m.HasField('oneof_field'))
+
+ m.oneof_uint32 = 11
+ self.assertEqual('oneof_uint32', m.WhichOneof('oneof_field'))
+ if message_module is unittest_pb2:
+ self.assertTrue(m.HasField('oneof_field'))
+
+ m.oneof_bytes = b'bb'
+ self.assertEqual('oneof_bytes', m.WhichOneof('oneof_field'))
+
+ m.ClearField('oneof_bytes')
+ self.assertIs(None, m.WhichOneof('oneof_field'))
+ if message_module is unittest_pb2:
+ self.assertFalse(m.HasField('oneof_field'))
+
+ def testOneofClearField(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+ m.ClearField('oneof_field')
+ if message_module is unittest_pb2:
+ self.assertFalse(m.HasField('oneof_field'))
+ self.assertFalse(m.HasField('oneof_uint32'))
+ self.assertIs(None, m.WhichOneof('oneof_field'))
+
+ def testOneofClearSetField(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+ m.ClearField('oneof_uint32')
+ if message_module is unittest_pb2:
+ self.assertFalse(m.HasField('oneof_field'))
+ self.assertFalse(m.HasField('oneof_uint32'))
+ self.assertIs(None, m.WhichOneof('oneof_field'))
+
+ def testOneofClearUnsetField(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+ self.ensureNestedMessageExists(m, 'oneof_nested_message')
+ m.ClearField('oneof_nested_message')
+ self.assertEqual(11, m.oneof_uint32)
+ if message_module is unittest_pb2:
+ self.assertTrue(m.HasField('oneof_field'))
+ self.assertTrue(m.HasField('oneof_uint32'))
+ self.assertEqual('oneof_uint32', m.WhichOneof('oneof_field'))
+
+ def testOneofDeserialize(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+ m2 = message_module.TestAllTypes()
+ m2.ParseFromString(m.SerializeToString())
+ self.assertEqual('oneof_uint32', m2.WhichOneof('oneof_field'))
+
+ def testOneofCopyFrom(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+ m2 = message_module.TestAllTypes()
+ m2.CopyFrom(m)
+ self.assertEqual('oneof_uint32', m2.WhichOneof('oneof_field'))
+
+ def testOneofNestedMergeFrom(self, message_module):
+ m = message_module.NestedTestAllTypes()
+ m.payload.oneof_uint32 = 11
+ m2 = message_module.NestedTestAllTypes()
+ m2.payload.oneof_bytes = b'bb'
+ m2.child.payload.oneof_bytes = b'bb'
+ m2.MergeFrom(m)
+ self.assertEqual('oneof_uint32', m2.payload.WhichOneof('oneof_field'))
+ self.assertEqual('oneof_bytes', m2.child.payload.WhichOneof('oneof_field'))
+
+ def testOneofMessageMergeFrom(self, message_module):
+ m = message_module.NestedTestAllTypes()
+ m.payload.oneof_nested_message.bb = 11
+ m.child.payload.oneof_nested_message.bb = 12
+ m2 = message_module.NestedTestAllTypes()
+ m2.payload.oneof_uint32 = 13
+ m2.MergeFrom(m)
+ self.assertEqual('oneof_nested_message',
+ m2.payload.WhichOneof('oneof_field'))
+ self.assertEqual('oneof_nested_message',
+ m2.child.payload.WhichOneof('oneof_field'))
+
+ def testOneofNestedMessageInit(self, message_module):
+ m = message_module.TestAllTypes(
+ oneof_nested_message=message_module.TestAllTypes.NestedMessage())
+ self.assertEqual('oneof_nested_message', m.WhichOneof('oneof_field'))
+
+ def testOneofClear(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+ m.Clear()
+ self.assertIsNone(m.WhichOneof('oneof_field'))
+ m.oneof_bytes = b'bb'
+ self.assertEqual('oneof_bytes', m.WhichOneof('oneof_field'))
+
+ def testAssignByteStringToUnicodeField(self, message_module):
+ """Assigning a byte string to a string field should result
+ in the value being converted to a Unicode string."""
+ m = message_module.TestAllTypes()
+ m.optional_string = str('')
+ self.assertIsInstance(m.optional_string, six.text_type)
+
+ def testLongValuedSlice(self, message_module):
+ """It should be possible to use long-valued indicies in slices
+
+ This didn't used to work in the v2 C++ implementation.
+ """
+ m = message_module.TestAllTypes()
+
+ # Repeated scalar
+ m.repeated_int32.append(1)
+ sl = m.repeated_int32[long(0):long(len(m.repeated_int32))]
+ self.assertEqual(len(m.repeated_int32), len(sl))
+
+ # Repeated composite
+ m.repeated_nested_message.add().bb = 3
+ sl = m.repeated_nested_message[long(0):long(len(m.repeated_nested_message))]
+ self.assertEqual(len(m.repeated_nested_message), len(sl))
+
+ def testExtendShouldNotSwallowExceptions(self, message_module):
+ """This didn't use to work in the v2 C++ implementation."""
+ m = message_module.TestAllTypes()
+ with self.assertRaises(NameError) as _:
+ m.repeated_int32.extend(a for i in range(10)) # pylint: disable=undefined-variable
+ with self.assertRaises(NameError) as _:
+ m.repeated_nested_enum.extend(
+ a for i in range(10)) # pylint: disable=undefined-variable
+
+ FALSY_VALUES = [None, False, 0, 0.0, b'', u'', bytearray(), [], {}, set()]
+
+ def testExtendInt32WithNothing(self, message_module):
+ """Test no-ops extending repeated int32 fields."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_int32)
+
+ # TODO(ptucker): Deprecate this behavior. b/18413862
+ for falsy_value in MessageTest.FALSY_VALUES:
+ m.repeated_int32.extend(falsy_value)
+ self.assertSequenceEqual([], m.repeated_int32)
+
+ m.repeated_int32.extend([])
+ self.assertSequenceEqual([], m.repeated_int32)
+
+ def testExtendFloatWithNothing(self, message_module):
+ """Test no-ops extending repeated float fields."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_float)
+
+ # TODO(ptucker): Deprecate this behavior. b/18413862
+ for falsy_value in MessageTest.FALSY_VALUES:
+ m.repeated_float.extend(falsy_value)
+ self.assertSequenceEqual([], m.repeated_float)
+
+ m.repeated_float.extend([])
+ self.assertSequenceEqual([], m.repeated_float)
+
+ def testExtendStringWithNothing(self, message_module):
+ """Test no-ops extending repeated string fields."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_string)
+
+ # TODO(ptucker): Deprecate this behavior. b/18413862
+ for falsy_value in MessageTest.FALSY_VALUES:
+ m.repeated_string.extend(falsy_value)
+ self.assertSequenceEqual([], m.repeated_string)
+
+ m.repeated_string.extend([])
+ self.assertSequenceEqual([], m.repeated_string)
+
+ def testExtendInt32WithPythonList(self, message_module):
+ """Test extending repeated int32 fields with python lists."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_int32)
+ m.repeated_int32.extend([0])
+ self.assertSequenceEqual([0], m.repeated_int32)
+ m.repeated_int32.extend([1, 2])
+ self.assertSequenceEqual([0, 1, 2], m.repeated_int32)
+ m.repeated_int32.extend([3, 4])
+ self.assertSequenceEqual([0, 1, 2, 3, 4], m.repeated_int32)
+
+ def testExtendFloatWithPythonList(self, message_module):
+ """Test extending repeated float fields with python lists."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_float)
+ m.repeated_float.extend([0.0])
+ self.assertSequenceEqual([0.0], m.repeated_float)
+ m.repeated_float.extend([1.0, 2.0])
+ self.assertSequenceEqual([0.0, 1.0, 2.0], m.repeated_float)
+ m.repeated_float.extend([3.0, 4.0])
+ self.assertSequenceEqual([0.0, 1.0, 2.0, 3.0, 4.0], m.repeated_float)
+
+ def testExtendStringWithPythonList(self, message_module):
+ """Test extending repeated string fields with python lists."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_string)
+ m.repeated_string.extend([''])
+ self.assertSequenceEqual([''], m.repeated_string)
+ m.repeated_string.extend(['11', '22'])
+ self.assertSequenceEqual(['', '11', '22'], m.repeated_string)
+ m.repeated_string.extend(['33', '44'])
+ self.assertSequenceEqual(['', '11', '22', '33', '44'], m.repeated_string)
+
+ def testExtendStringWithString(self, message_module):
+ """Test extending repeated string fields with characters from a string."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_string)
+ m.repeated_string.extend('abc')
+ self.assertSequenceEqual(['a', 'b', 'c'], m.repeated_string)
+
+ class TestIterable(object):
+ """This iterable object mimics the behavior of numpy.array.
+
+ __nonzero__ fails for length > 1, and returns bool(item[0]) for length == 1.
+
+ """
+
+ def __init__(self, values=None):
+ self._list = values or []
+
+ def __nonzero__(self):
+ size = len(self._list)
+ if size == 0:
+ return False
+ if size == 1:
+ return bool(self._list[0])
+ raise ValueError('Truth value is ambiguous.')
+
+ def __len__(self):
+ return len(self._list)
+
+ def __iter__(self):
+ return self._list.__iter__()
+
+ def testExtendInt32WithIterable(self, message_module):
+ """Test extending repeated int32 fields with iterable."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_int32)
+ m.repeated_int32.extend(MessageTest.TestIterable([]))
+ self.assertSequenceEqual([], m.repeated_int32)
+ m.repeated_int32.extend(MessageTest.TestIterable([0]))
+ self.assertSequenceEqual([0], m.repeated_int32)
+ m.repeated_int32.extend(MessageTest.TestIterable([1, 2]))
+ self.assertSequenceEqual([0, 1, 2], m.repeated_int32)
+ m.repeated_int32.extend(MessageTest.TestIterable([3, 4]))
+ self.assertSequenceEqual([0, 1, 2, 3, 4], m.repeated_int32)
+
+ def testExtendFloatWithIterable(self, message_module):
+ """Test extending repeated float fields with iterable."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_float)
+ m.repeated_float.extend(MessageTest.TestIterable([]))
+ self.assertSequenceEqual([], m.repeated_float)
+ m.repeated_float.extend(MessageTest.TestIterable([0.0]))
+ self.assertSequenceEqual([0.0], m.repeated_float)
+ m.repeated_float.extend(MessageTest.TestIterable([1.0, 2.0]))
+ self.assertSequenceEqual([0.0, 1.0, 2.0], m.repeated_float)
+ m.repeated_float.extend(MessageTest.TestIterable([3.0, 4.0]))
+ self.assertSequenceEqual([0.0, 1.0, 2.0, 3.0, 4.0], m.repeated_float)
+
+ def testExtendStringWithIterable(self, message_module):
+ """Test extending repeated string fields with iterable."""
+ m = message_module.TestAllTypes()
+ self.assertSequenceEqual([], m.repeated_string)
+ m.repeated_string.extend(MessageTest.TestIterable([]))
+ self.assertSequenceEqual([], m.repeated_string)
+ m.repeated_string.extend(MessageTest.TestIterable(['']))
+ self.assertSequenceEqual([''], m.repeated_string)
+ m.repeated_string.extend(MessageTest.TestIterable(['1', '2']))
+ self.assertSequenceEqual(['', '1', '2'], m.repeated_string)
+ m.repeated_string.extend(MessageTest.TestIterable(['3', '4']))
+ self.assertSequenceEqual(['', '1', '2', '3', '4'], m.repeated_string)
+
+ def testPickleRepeatedScalarContainer(self, message_module):
+ # TODO(tibell): The pure-Python implementation support pickling of
+ # scalar containers in *some* cases. For now the cpp2 version
+ # throws an exception to avoid a segfault. Investigate if we
+ # want to support pickling of these fields.
+ #
+ # For more information see: https://b2.corp.google.com/u/0/issues/18677897
+ if (api_implementation.Type() != 'cpp' or
+ api_implementation.Version() == 2):
+ return
+ m = message_module.TestAllTypes()
+ with self.assertRaises(pickle.PickleError) as _:
+ pickle.dumps(m.repeated_int32, pickle.HIGHEST_PROTOCOL)
+
+ def testSortEmptyRepeatedCompositeContainer(self, message_module):
+ """Exercise a scenario that has led to segfaults in the past.
+ """
+ m = message_module.TestAllTypes()
+ m.repeated_nested_message.sort()
+
+ def testHasFieldOnRepeatedField(self, message_module):
+ """Using HasField on a repeated field should raise an exception.
+ """
+ m = message_module.TestAllTypes()
+ with self.assertRaises(ValueError) as _:
+ m.HasField('repeated_int32')
+
+ def testRepeatedScalarFieldPop(self, message_module):
+ m = message_module.TestAllTypes()
+ with self.assertRaises(IndexError) as _:
+ m.repeated_int32.pop()
+ m.repeated_int32.extend(range(5))
+ self.assertEqual(4, m.repeated_int32.pop())
+ self.assertEqual(0, m.repeated_int32.pop(0))
+ self.assertEqual(2, m.repeated_int32.pop(1))
+ self.assertEqual([1, 3], m.repeated_int32)
+
+ def testRepeatedCompositeFieldPop(self, message_module):
+ m = message_module.TestAllTypes()
+ with self.assertRaises(IndexError) as _:
+ m.repeated_nested_message.pop()
+ for i in range(5):
+ n = m.repeated_nested_message.add()
+ n.bb = i
+ self.assertEqual(4, m.repeated_nested_message.pop().bb)
+ self.assertEqual(0, m.repeated_nested_message.pop(0).bb)
+ self.assertEqual(2, m.repeated_nested_message.pop(1).bb)
+ self.assertEqual([1, 3], [n.bb for n in m.repeated_nested_message])
+
+
+# Class to test proto2-only features (required, extensions, etc.)
+class Proto2Test(unittest.TestCase):
+
+ def testFieldPresence(self):
+ message = unittest_pb2.TestAllTypes()
+
+ self.assertFalse(message.HasField("optional_int32"))
+ self.assertFalse(message.HasField("optional_bool"))
+ self.assertFalse(message.HasField("optional_nested_message"))
+
+ with self.assertRaises(ValueError):
+ message.HasField("field_doesnt_exist")
+
+ with self.assertRaises(ValueError):
+ message.HasField("repeated_int32")
+ with self.assertRaises(ValueError):
+ message.HasField("repeated_nested_message")
+
+ self.assertEqual(0, message.optional_int32)
+ self.assertEqual(False, message.optional_bool)
+ self.assertEqual(0, message.optional_nested_message.bb)
+
+ # Fields are set even when setting the values to default values.
+ message.optional_int32 = 0
+ message.optional_bool = False
+ message.optional_nested_message.bb = 0
+ self.assertTrue(message.HasField("optional_int32"))
+ self.assertTrue(message.HasField("optional_bool"))
+ self.assertTrue(message.HasField("optional_nested_message"))
+
+ # Set the fields to non-default values.
+ message.optional_int32 = 5
+ message.optional_bool = True
+ message.optional_nested_message.bb = 15
+
+ self.assertTrue(message.HasField("optional_int32"))
+ self.assertTrue(message.HasField("optional_bool"))
+ self.assertTrue(message.HasField("optional_nested_message"))
+
+ # Clearing the fields unsets them and resets their value to default.
+ message.ClearField("optional_int32")
+ message.ClearField("optional_bool")
+ message.ClearField("optional_nested_message")
+
+ self.assertFalse(message.HasField("optional_int32"))
+ self.assertFalse(message.HasField("optional_bool"))
+ self.assertFalse(message.HasField("optional_nested_message"))
+ self.assertEqual(0, message.optional_int32)
+ self.assertEqual(False, message.optional_bool)
+ self.assertEqual(0, message.optional_nested_message.bb)
+
+ # TODO(tibell): The C++ implementations actually allows assignment
+ # of unknown enum values to *scalar* fields (but not repeated
+ # fields). Once checked enum fields becomes the default in the
+ # Python implementation, the C++ implementation should follow suit.
+ def testAssignInvalidEnum(self):
+ """It should not be possible to assign an invalid enum number to an
+ enum field."""
+ m = unittest_pb2.TestAllTypes()
+
+ with self.assertRaises(ValueError) as _:
+ m.optional_nested_enum = 1234567
+ self.assertRaises(ValueError, m.repeated_nested_enum.append, 1234567)
+
+ def testGoldenExtensions(self):
+ golden_data = test_util.GoldenFileData('golden_message')
+ golden_message = unittest_pb2.TestAllExtensions()
+ golden_message.ParseFromString(golden_data)
+ all_set = unittest_pb2.TestAllExtensions()
+ test_util.SetAllExtensions(all_set)
+ self.assertEqual(all_set, golden_message)
+ self.assertEqual(golden_data, golden_message.SerializeToString())
+ golden_copy = copy.deepcopy(golden_message)
+ self.assertEqual(golden_data, golden_copy.SerializeToString())
+
+ def testGoldenPackedExtensions(self):
+ golden_data = test_util.GoldenFileData('golden_packed_fields_message')
+ golden_message = unittest_pb2.TestPackedExtensions()
+ golden_message.ParseFromString(golden_data)
+ all_set = unittest_pb2.TestPackedExtensions()
+ test_util.SetAllPackedExtensions(all_set)
+ self.assertEqual(all_set, golden_message)
+ self.assertEqual(golden_data, all_set.SerializeToString())
+ golden_copy = copy.deepcopy(golden_message)
+ self.assertEqual(golden_data, golden_copy.SerializeToString())
+
+ def testPickleIncompleteProto(self):
+ golden_message = unittest_pb2.TestRequired(a=1)
+ pickled_message = pickle.dumps(golden_message)
+
+ unpickled_message = pickle.loads(pickled_message)
+ self.assertEqual(unpickled_message, golden_message)
+ self.assertEqual(unpickled_message.a, 1)
+ # This is still an incomplete proto - so serializing should fail
+ self.assertRaises(message.EncodeError, unpickled_message.SerializeToString)
+
+
+ # TODO(haberman): this isn't really a proto2-specific test except that this
+ # message has a required field in it. Should probably be factored out so
+ # that we can test the other parts with proto3.
+ def testParsingMerge(self):
+ """Check the merge behavior when a required or optional field appears
+ multiple times in the input."""
+ messages = [
+ unittest_pb2.TestAllTypes(),
+ unittest_pb2.TestAllTypes(),
+ unittest_pb2.TestAllTypes() ]
+ messages[0].optional_int32 = 1
+ messages[1].optional_int64 = 2
+ messages[2].optional_int32 = 3
+ messages[2].optional_string = 'hello'
+
+ merged_message = unittest_pb2.TestAllTypes()
+ merged_message.optional_int32 = 3
+ merged_message.optional_int64 = 2
+ merged_message.optional_string = 'hello'
+
+ generator = unittest_pb2.TestParsingMerge.RepeatedFieldsGenerator()
+ generator.field1.extend(messages)
+ generator.field2.extend(messages)
+ generator.field3.extend(messages)
+ generator.ext1.extend(messages)
+ generator.ext2.extend(messages)
+ generator.group1.add().field1.MergeFrom(messages[0])
+ generator.group1.add().field1.MergeFrom(messages[1])
+ generator.group1.add().field1.MergeFrom(messages[2])
+ generator.group2.add().field1.MergeFrom(messages[0])
+ generator.group2.add().field1.MergeFrom(messages[1])
+ generator.group2.add().field1.MergeFrom(messages[2])
+
+ data = generator.SerializeToString()
+ parsing_merge = unittest_pb2.TestParsingMerge()
+ parsing_merge.ParseFromString(data)
+
+ # Required and optional fields should be merged.
+ self.assertEqual(parsing_merge.required_all_types, merged_message)
+ self.assertEqual(parsing_merge.optional_all_types, merged_message)
+ self.assertEqual(parsing_merge.optionalgroup.optional_group_all_types,
+ merged_message)
+ self.assertEqual(parsing_merge.Extensions[
+ unittest_pb2.TestParsingMerge.optional_ext],
+ merged_message)
+
+ # Repeated fields should not be merged.
+ self.assertEqual(len(parsing_merge.repeated_all_types), 3)
+ self.assertEqual(len(parsing_merge.repeatedgroup), 3)
+ self.assertEqual(len(parsing_merge.Extensions[
+ unittest_pb2.TestParsingMerge.repeated_ext]), 3)
+
+ def testPythonicInit(self):
+ message = unittest_pb2.TestAllTypes(
+ optional_int32=100,
+ optional_fixed32=200,
+ optional_float=300.5,
+ optional_bytes=b'x',
+ optionalgroup={'a': 400},
+ optional_nested_message={'bb': 500},
+ optional_nested_enum='BAZ',
+ repeatedgroup=[{'a': 600},
+ {'a': 700}],
+ repeated_nested_enum=['FOO', unittest_pb2.TestAllTypes.BAR],
+ default_int32=800,
+ oneof_string='y')
+ self.assertIsInstance(message, unittest_pb2.TestAllTypes)
+ self.assertEqual(100, message.optional_int32)
+ self.assertEqual(200, message.optional_fixed32)
+ self.assertEqual(300.5, message.optional_float)
+ self.assertEqual(b'x', message.optional_bytes)
+ self.assertEqual(400, message.optionalgroup.a)
+ self.assertIsInstance(message.optional_nested_message, unittest_pb2.TestAllTypes.NestedMessage)
+ self.assertEqual(500, message.optional_nested_message.bb)
+ self.assertEqual(unittest_pb2.TestAllTypes.BAZ,
+ message.optional_nested_enum)
+ self.assertEqual(2, len(message.repeatedgroup))
+ self.assertEqual(600, message.repeatedgroup[0].a)
+ self.assertEqual(700, message.repeatedgroup[1].a)
+ self.assertEqual(2, len(message.repeated_nested_enum))
+ self.assertEqual(unittest_pb2.TestAllTypes.FOO,
+ message.repeated_nested_enum[0])
+ self.assertEqual(unittest_pb2.TestAllTypes.BAR,
+ message.repeated_nested_enum[1])
+ self.assertEqual(800, message.default_int32)
+ self.assertEqual('y', message.oneof_string)
+ self.assertFalse(message.HasField('optional_int64'))
+ self.assertEqual(0, len(message.repeated_float))
+ self.assertEqual(42, message.default_int64)
+
+ message = unittest_pb2.TestAllTypes(optional_nested_enum=u'BAZ')
+ self.assertEqual(unittest_pb2.TestAllTypes.BAZ,
+ message.optional_nested_enum)
+
+ with self.assertRaises(ValueError):
+ unittest_pb2.TestAllTypes(
+ optional_nested_message={'INVALID_NESTED_FIELD': 17})
+
+ with self.assertRaises(TypeError):
+ unittest_pb2.TestAllTypes(
+ optional_nested_message={'bb': 'INVALID_VALUE_TYPE'})
+
+ with self.assertRaises(ValueError):
+ unittest_pb2.TestAllTypes(optional_nested_enum='INVALID_LABEL')
+
+ with self.assertRaises(ValueError):
+ unittest_pb2.TestAllTypes(repeated_nested_enum='FOO')
+
+
+
+# Class to test proto3-only features/behavior (updated field presence & enums)
+class Proto3Test(unittest.TestCase):
+
+ # Utility method for comparing equality with a map.
+ def assertMapIterEquals(self, map_iter, dict_value):
+ # Avoid mutating caller's copy.
+ dict_value = dict(dict_value)
+
+ for k, v in map_iter:
+ self.assertEqual(v, dict_value[k])
+ del dict_value[k]
+
+ self.assertEqual({}, dict_value)
+
+ def testFieldPresence(self):
+ message = unittest_proto3_arena_pb2.TestAllTypes()
+
+ # We can't test presence of non-repeated, non-submessage fields.
+ with self.assertRaises(ValueError):
+ message.HasField('optional_int32')
+ with self.assertRaises(ValueError):
+ message.HasField('optional_float')
+ with self.assertRaises(ValueError):
+ message.HasField('optional_string')
+ with self.assertRaises(ValueError):
+ message.HasField('optional_bool')
+
+ # But we can still test presence of submessage fields.
+ self.assertFalse(message.HasField('optional_nested_message'))
+
+ # As with proto2, we can't test presence of fields that don't exist, or
+ # repeated fields.
+ with self.assertRaises(ValueError):
+ message.HasField('field_doesnt_exist')
+
+ with self.assertRaises(ValueError):
+ message.HasField('repeated_int32')
+ with self.assertRaises(ValueError):
+ message.HasField('repeated_nested_message')
+
+ # Fields should default to their type-specific default.
+ self.assertEqual(0, message.optional_int32)
+ self.assertEqual(0, message.optional_float)
+ self.assertEqual('', message.optional_string)
+ self.assertEqual(False, message.optional_bool)
+ self.assertEqual(0, message.optional_nested_message.bb)
+
+ # Setting a submessage should still return proper presence information.
+ message.optional_nested_message.bb = 0
+ self.assertTrue(message.HasField('optional_nested_message'))
+
+ # Set the fields to non-default values.
+ message.optional_int32 = 5
+ message.optional_float = 1.1
+ message.optional_string = 'abc'
+ message.optional_bool = True
+ message.optional_nested_message.bb = 15
+
+ # Clearing the fields unsets them and resets their value to default.
+ message.ClearField('optional_int32')
+ message.ClearField('optional_float')
+ message.ClearField('optional_string')
+ message.ClearField('optional_bool')
+ message.ClearField('optional_nested_message')
+
+ self.assertEqual(0, message.optional_int32)
+ self.assertEqual(0, message.optional_float)
+ self.assertEqual('', message.optional_string)
+ self.assertEqual(False, message.optional_bool)
+ self.assertEqual(0, message.optional_nested_message.bb)
+
+ def testAssignUnknownEnum(self):
+ """Assigning an unknown enum value is allowed and preserves the value."""
+ m = unittest_proto3_arena_pb2.TestAllTypes()
+
+ m.optional_nested_enum = 1234567
+ self.assertEqual(1234567, m.optional_nested_enum)
+ m.repeated_nested_enum.append(22334455)
+ self.assertEqual(22334455, m.repeated_nested_enum[0])
+ # Assignment is a different code path than append for the C++ impl.
+ m.repeated_nested_enum[0] = 7654321
+ self.assertEqual(7654321, m.repeated_nested_enum[0])
+ serialized = m.SerializeToString()
+
+ m2 = unittest_proto3_arena_pb2.TestAllTypes()
+ m2.ParseFromString(serialized)
+ self.assertEqual(1234567, m2.optional_nested_enum)
+ self.assertEqual(7654321, m2.repeated_nested_enum[0])
+
+ # Map isn't really a proto3-only feature. But there is no proto2 equivalent
+ # of google/protobuf/map_unittest.proto right now, so it's not easy to
+ # test both with the same test like we do for the other proto2/proto3 tests.
+ # (google/protobuf/map_protobuf_unittest.proto is very different in the set
+ # of messages and fields it contains).
+ def testScalarMapDefaults(self):
+ msg = map_unittest_pb2.TestMap()
+
+ # Scalars start out unset.
+ self.assertFalse(-123 in msg.map_int32_int32)
+ self.assertFalse(-2**33 in msg.map_int64_int64)
+ self.assertFalse(123 in msg.map_uint32_uint32)
+ self.assertFalse(2**33 in msg.map_uint64_uint64)
+ self.assertFalse(123 in msg.map_int32_double)
+ self.assertFalse(False in msg.map_bool_bool)
+ self.assertFalse('abc' in msg.map_string_string)
+ self.assertFalse(111 in msg.map_int32_bytes)
+ self.assertFalse(888 in msg.map_int32_enum)
+
+ # Accessing an unset key returns the default.
+ self.assertEqual(0, msg.map_int32_int32[-123])
+ self.assertEqual(0, msg.map_int64_int64[-2**33])
+ self.assertEqual(0, msg.map_uint32_uint32[123])
+ self.assertEqual(0, msg.map_uint64_uint64[2**33])
+ self.assertEqual(0.0, msg.map_int32_double[123])
+ self.assertTrue(isinstance(msg.map_int32_double[123], float))
+ self.assertEqual(False, msg.map_bool_bool[False])
+ self.assertTrue(isinstance(msg.map_bool_bool[False], bool))
+ self.assertEqual('', msg.map_string_string['abc'])
+ self.assertEqual(b'', msg.map_int32_bytes[111])
+ self.assertEqual(0, msg.map_int32_enum[888])
+
+ # It also sets the value in the map
+ self.assertTrue(-123 in msg.map_int32_int32)
+ self.assertTrue(-2**33 in msg.map_int64_int64)
+ self.assertTrue(123 in msg.map_uint32_uint32)
+ self.assertTrue(2**33 in msg.map_uint64_uint64)
+ self.assertTrue(123 in msg.map_int32_double)
+ self.assertTrue(False in msg.map_bool_bool)
+ self.assertTrue('abc' in msg.map_string_string)
+ self.assertTrue(111 in msg.map_int32_bytes)
+ self.assertTrue(888 in msg.map_int32_enum)
+
+ self.assertIsInstance(msg.map_string_string['abc'], six.text_type)
+
+ # Accessing an unset key still throws TypeError if the type of the key
+ # is incorrect.
+ with self.assertRaises(TypeError):
+ msg.map_string_string[123]
+
+ with self.assertRaises(TypeError):
+ 123 in msg.map_string_string
+
+ def testMapGet(self):
+ # Need to test that get() properly returns the default, even though the dict
+ # has defaultdict-like semantics.
+ msg = map_unittest_pb2.TestMap()
+
+ self.assertIsNone(msg.map_int32_int32.get(5))
+ self.assertEqual(10, msg.map_int32_int32.get(5, 10))
+ self.assertIsNone(msg.map_int32_int32.get(5))
+
+ msg.map_int32_int32[5] = 15
+ self.assertEqual(15, msg.map_int32_int32.get(5))
+
+ self.assertIsNone(msg.map_int32_foreign_message.get(5))
+ self.assertEqual(10, msg.map_int32_foreign_message.get(5, 10))
+
+ submsg = msg.map_int32_foreign_message[5]
+ self.assertIs(submsg, msg.map_int32_foreign_message.get(5))
+
+ def testScalarMap(self):
+ msg = map_unittest_pb2.TestMap()
+
+ self.assertEqual(0, len(msg.map_int32_int32))
+ self.assertFalse(5 in msg.map_int32_int32)
+
+ msg.map_int32_int32[-123] = -456
+ msg.map_int64_int64[-2**33] = -2**34
+ msg.map_uint32_uint32[123] = 456
+ msg.map_uint64_uint64[2**33] = 2**34
+ msg.map_string_string['abc'] = '123'
+ msg.map_int32_enum[888] = 2
+
+ self.assertEqual([], msg.FindInitializationErrors())
+
+ self.assertEqual(1, len(msg.map_string_string))
+
+ # Bad key.
+ with self.assertRaises(TypeError):
+ msg.map_string_string[123] = '123'
+
+ # Verify that trying to assign a bad key doesn't actually add a member to
+ # the map.
+ self.assertEqual(1, len(msg.map_string_string))
+
+ # Bad value.
+ with self.assertRaises(TypeError):
+ msg.map_string_string['123'] = 123
+
+ serialized = msg.SerializeToString()
+ msg2 = map_unittest_pb2.TestMap()
+ msg2.ParseFromString(serialized)
+
+ # Bad key.
+ with self.assertRaises(TypeError):
+ msg2.map_string_string[123] = '123'
+
+ # Bad value.
+ with self.assertRaises(TypeError):
+ msg2.map_string_string['123'] = 123
+
+ self.assertEqual(-456, msg2.map_int32_int32[-123])
+ self.assertEqual(-2**34, msg2.map_int64_int64[-2**33])
+ self.assertEqual(456, msg2.map_uint32_uint32[123])
+ self.assertEqual(2**34, msg2.map_uint64_uint64[2**33])
+ self.assertEqual('123', msg2.map_string_string['abc'])
+ self.assertEqual(2, msg2.map_int32_enum[888])
+
+ def testStringUnicodeConversionInMap(self):
+ msg = map_unittest_pb2.TestMap()
+
+ unicode_obj = u'\u1234'
+ bytes_obj = unicode_obj.encode('utf8')
+
+ msg.map_string_string[bytes_obj] = bytes_obj
+
+ (key, value) = list(msg.map_string_string.items())[0]
+
+ self.assertEqual(key, unicode_obj)
+ self.assertEqual(value, unicode_obj)
+
+ self.assertIsInstance(key, six.text_type)
+ self.assertIsInstance(value, six.text_type)
+
+ def testMessageMap(self):
+ msg = map_unittest_pb2.TestMap()
+
+ self.assertEqual(0, len(msg.map_int32_foreign_message))
+ self.assertFalse(5 in msg.map_int32_foreign_message)
+
+ msg.map_int32_foreign_message[123]
+ # get_or_create() is an alias for getitem.
+ msg.map_int32_foreign_message.get_or_create(-456)
+
+ self.assertEqual(2, len(msg.map_int32_foreign_message))
+ self.assertIn(123, msg.map_int32_foreign_message)
+ self.assertIn(-456, msg.map_int32_foreign_message)
+ self.assertEqual(2, len(msg.map_int32_foreign_message))
+
+ # Bad key.
+ with self.assertRaises(TypeError):
+ msg.map_int32_foreign_message['123']
+
+ # Can't assign directly to submessage.
+ with self.assertRaises(ValueError):
+ msg.map_int32_foreign_message[999] = msg.map_int32_foreign_message[123]
+
+ # Verify that trying to assign a bad key doesn't actually add a member to
+ # the map.
+ self.assertEqual(2, len(msg.map_int32_foreign_message))
+
+ serialized = msg.SerializeToString()
+ msg2 = map_unittest_pb2.TestMap()
+ msg2.ParseFromString(serialized)
+
+ self.assertEqual(2, len(msg2.map_int32_foreign_message))
+ self.assertIn(123, msg2.map_int32_foreign_message)
+ self.assertIn(-456, msg2.map_int32_foreign_message)
+ self.assertEqual(2, len(msg2.map_int32_foreign_message))
+
+ def testMergeFrom(self):
+ msg = map_unittest_pb2.TestMap()
+ msg.map_int32_int32[12] = 34
+ msg.map_int32_int32[56] = 78
+ msg.map_int64_int64[22] = 33
+ msg.map_int32_foreign_message[111].c = 5
+ msg.map_int32_foreign_message[222].c = 10
+
+ msg2 = map_unittest_pb2.TestMap()
+ msg2.map_int32_int32[12] = 55
+ msg2.map_int64_int64[88] = 99
+ msg2.map_int32_foreign_message[222].c = 15
+ msg2.map_int32_foreign_message[222].d = 20
+ old_map_value = msg2.map_int32_foreign_message[222]
+
+ msg2.MergeFrom(msg)
+
+ self.assertEqual(34, msg2.map_int32_int32[12])
+ self.assertEqual(78, msg2.map_int32_int32[56])
+ self.assertEqual(33, msg2.map_int64_int64[22])
+ self.assertEqual(99, msg2.map_int64_int64[88])
+ self.assertEqual(5, msg2.map_int32_foreign_message[111].c)
+ self.assertEqual(10, msg2.map_int32_foreign_message[222].c)
+ self.assertFalse(msg2.map_int32_foreign_message[222].HasField('d'))
+ self.assertEqual(15, old_map_value.c)
+
+ # Verify that there is only one entry per key, even though the MergeFrom
+ # may have internally created multiple entries for a single key in the
+ # list representation.
+ as_dict = {}
+ for key in msg2.map_int32_foreign_message:
+ self.assertFalse(key in as_dict)
+ as_dict[key] = msg2.map_int32_foreign_message[key].c
+
+ self.assertEqual({111: 5, 222: 10}, as_dict)
+
+ # Special case: test that delete of item really removes the item, even if
+ # there might have physically been duplicate keys due to the previous merge.
+ # This is only a special case for the C++ implementation which stores the
+ # map as an array.
+ del msg2.map_int32_int32[12]
+ self.assertFalse(12 in msg2.map_int32_int32)
+
+ del msg2.map_int32_foreign_message[222]
+ self.assertFalse(222 in msg2.map_int32_foreign_message)
+
+ def testMergeFromBadType(self):
+ msg = map_unittest_pb2.TestMap()
+ with self.assertRaisesRegexp(
+ TypeError,
+ r'Parameter to MergeFrom\(\) must be instance of same class: expected '
+ r'.*TestMap got int\.'):
+ msg.MergeFrom(1)
+
+ def testCopyFromBadType(self):
+ msg = map_unittest_pb2.TestMap()
+ with self.assertRaisesRegexp(
+ TypeError,
+ r'Parameter to [A-Za-z]*From\(\) must be instance of same class: '
+ r'expected .*TestMap got int\.'):
+ msg.CopyFrom(1)
+
+ def testIntegerMapWithLongs(self):
+ msg = map_unittest_pb2.TestMap()
+ msg.map_int32_int32[long(-123)] = long(-456)
+ msg.map_int64_int64[long(-2**33)] = long(-2**34)
+ msg.map_uint32_uint32[long(123)] = long(456)
+ msg.map_uint64_uint64[long(2**33)] = long(2**34)
+
+ serialized = msg.SerializeToString()
+ msg2 = map_unittest_pb2.TestMap()
+ msg2.ParseFromString(serialized)
+
+ self.assertEqual(-456, msg2.map_int32_int32[-123])
+ self.assertEqual(-2**34, msg2.map_int64_int64[-2**33])
+ self.assertEqual(456, msg2.map_uint32_uint32[123])
+ self.assertEqual(2**34, msg2.map_uint64_uint64[2**33])
+
+ def testMapAssignmentCausesPresence(self):
+ msg = map_unittest_pb2.TestMapSubmessage()
+ msg.test_map.map_int32_int32[123] = 456
+
+ serialized = msg.SerializeToString()
+ msg2 = map_unittest_pb2.TestMapSubmessage()
+ msg2.ParseFromString(serialized)
+
+ self.assertEqual(msg, msg2)
+
+ # Now test that various mutations of the map properly invalidate the
+ # cached size of the submessage.
+ msg.test_map.map_int32_int32[888] = 999
+ serialized = msg.SerializeToString()
+ msg2.ParseFromString(serialized)
+ self.assertEqual(msg, msg2)
+
+ msg.test_map.map_int32_int32.clear()
+ serialized = msg.SerializeToString()
+ msg2.ParseFromString(serialized)
+ self.assertEqual(msg, msg2)
+
+ def testMapAssignmentCausesPresenceForSubmessages(self):
+ msg = map_unittest_pb2.TestMapSubmessage()
+ msg.test_map.map_int32_foreign_message[123].c = 5
+
+ serialized = msg.SerializeToString()
+ msg2 = map_unittest_pb2.TestMapSubmessage()
+ msg2.ParseFromString(serialized)
+
+ self.assertEqual(msg, msg2)
+
+ # Now test that various mutations of the map properly invalidate the
+ # cached size of the submessage.
+ msg.test_map.map_int32_foreign_message[888].c = 7
+ serialized = msg.SerializeToString()
+ msg2.ParseFromString(serialized)
+ self.assertEqual(msg, msg2)
+
+ msg.test_map.map_int32_foreign_message[888].MergeFrom(
+ msg.test_map.map_int32_foreign_message[123])
+ serialized = msg.SerializeToString()
+ msg2.ParseFromString(serialized)
+ self.assertEqual(msg, msg2)
+
+ msg.test_map.map_int32_foreign_message.clear()
+ serialized = msg.SerializeToString()
+ msg2.ParseFromString(serialized)
+ self.assertEqual(msg, msg2)
+
+ def testModifyMapWhileIterating(self):
+ msg = map_unittest_pb2.TestMap()
+
+ string_string_iter = iter(msg.map_string_string)
+ int32_foreign_iter = iter(msg.map_int32_foreign_message)
+
+ msg.map_string_string['abc'] = '123'
+ msg.map_int32_foreign_message[5].c = 5
+
+ with self.assertRaises(RuntimeError):
+ for key in string_string_iter:
+ pass
+
+ with self.assertRaises(RuntimeError):
+ for key in int32_foreign_iter:
+ pass
+
+ def testSubmessageMap(self):
+ msg = map_unittest_pb2.TestMap()
+
+ submsg = msg.map_int32_foreign_message[111]
+ self.assertIs(submsg, msg.map_int32_foreign_message[111])
+ self.assertIsInstance(submsg, unittest_pb2.ForeignMessage)
+
+ submsg.c = 5
+
+ serialized = msg.SerializeToString()
+ msg2 = map_unittest_pb2.TestMap()
+ msg2.ParseFromString(serialized)
+
+ self.assertEqual(5, msg2.map_int32_foreign_message[111].c)
+
+ # Doesn't allow direct submessage assignment.
+ with self.assertRaises(ValueError):
+ msg.map_int32_foreign_message[88] = unittest_pb2.ForeignMessage()
+
+ def testMapIteration(self):
+ msg = map_unittest_pb2.TestMap()
+
+ for k, v in msg.map_int32_int32.items():
+ # Should not be reached.
+ self.assertTrue(False)
+
+ msg.map_int32_int32[2] = 4
+ msg.map_int32_int32[3] = 6
+ msg.map_int32_int32[4] = 8
+ self.assertEqual(3, len(msg.map_int32_int32))
+
+ matching_dict = {2: 4, 3: 6, 4: 8}
+ self.assertMapIterEquals(msg.map_int32_int32.items(), matching_dict)
+
+ def testMapItems(self):
+ # Map items used to have strange behaviors when use c extension. Because
+ # [] may reorder the map and invalidate any exsting iterators.
+ # TODO(jieluo): Check if [] reordering the map is a bug or intended
+ # behavior.
+ msg = map_unittest_pb2.TestMap()
+ msg.map_string_string['local_init_op'] = ''
+ msg.map_string_string['trainable_variables'] = ''
+ msg.map_string_string['variables'] = ''
+ msg.map_string_string['init_op'] = ''
+ msg.map_string_string['summaries'] = ''
+ items1 = msg.map_string_string.items()
+ items2 = msg.map_string_string.items()
+ self.assertEqual(items1, items2)
+
+ def testMapIterationClearMessage(self):
+ # Iterator needs to work even if message and map are deleted.
+ msg = map_unittest_pb2.TestMap()
+
+ msg.map_int32_int32[2] = 4
+ msg.map_int32_int32[3] = 6
+ msg.map_int32_int32[4] = 8
+
+ it = msg.map_int32_int32.items()
+ del msg
+
+ matching_dict = {2: 4, 3: 6, 4: 8}
+ self.assertMapIterEquals(it, matching_dict)
+
+ def testMapConstruction(self):
+ msg = map_unittest_pb2.TestMap(map_int32_int32={1: 2, 3: 4})
+ self.assertEqual(2, msg.map_int32_int32[1])
+ self.assertEqual(4, msg.map_int32_int32[3])
+
+ msg = map_unittest_pb2.TestMap(
+ map_int32_foreign_message={3: unittest_pb2.ForeignMessage(c=5)})
+ self.assertEqual(5, msg.map_int32_foreign_message[3].c)
+
+ def testMapValidAfterFieldCleared(self):
+ # Map needs to work even if field is cleared.
+ # For the C++ implementation this tests the correctness of
+ # ScalarMapContainer::Release()
+ msg = map_unittest_pb2.TestMap()
+ int32_map = msg.map_int32_int32
+
+ int32_map[2] = 4
+ int32_map[3] = 6
+ int32_map[4] = 8
+
+ msg.ClearField('map_int32_int32')
+ self.assertEqual(b'', msg.SerializeToString())
+ matching_dict = {2: 4, 3: 6, 4: 8}
+ self.assertMapIterEquals(int32_map.items(), matching_dict)
+
+ def testMessageMapValidAfterFieldCleared(self):
+ # Map needs to work even if field is cleared.
+ # For the C++ implementation this tests the correctness of
+ # ScalarMapContainer::Release()
+ msg = map_unittest_pb2.TestMap()
+ int32_foreign_message = msg.map_int32_foreign_message
+
+ int32_foreign_message[2].c = 5
+
+ msg.ClearField('map_int32_foreign_message')
+ self.assertEqual(b'', msg.SerializeToString())
+ self.assertTrue(2 in int32_foreign_message.keys())
+
+ def testMapIterInvalidatedByClearField(self):
+ # Map iterator is invalidated when field is cleared.
+ # But this case does need to not crash the interpreter.
+ # For the C++ implementation this tests the correctness of
+ # ScalarMapContainer::Release()
+ msg = map_unittest_pb2.TestMap()
+
+ it = iter(msg.map_int32_int32)
+
+ msg.ClearField('map_int32_int32')
+ with self.assertRaises(RuntimeError):
+ for _ in it:
+ pass
+
+ it = iter(msg.map_int32_foreign_message)
+ msg.ClearField('map_int32_foreign_message')
+ with self.assertRaises(RuntimeError):
+ for _ in it:
+ pass
+
+ def testMapDelete(self):
+ msg = map_unittest_pb2.TestMap()
+
+ self.assertEqual(0, len(msg.map_int32_int32))
+
+ msg.map_int32_int32[4] = 6
+ self.assertEqual(1, len(msg.map_int32_int32))
+
+ with self.assertRaises(KeyError):
+ del msg.map_int32_int32[88]
+
+ del msg.map_int32_int32[4]
+ self.assertEqual(0, len(msg.map_int32_int32))
+
+ def testMapsAreMapping(self):
+ msg = map_unittest_pb2.TestMap()
+ self.assertIsInstance(msg.map_int32_int32, collections.Mapping)
+ self.assertIsInstance(msg.map_int32_int32, collections.MutableMapping)
+ self.assertIsInstance(msg.map_int32_foreign_message, collections.Mapping)
+ self.assertIsInstance(msg.map_int32_foreign_message,
+ collections.MutableMapping)
+
+ def testMapFindInitializationErrorsSmokeTest(self):
+ msg = map_unittest_pb2.TestMap()
+ msg.map_string_string['abc'] = '123'
+ msg.map_int32_int32[35] = 64
+ msg.map_string_foreign_message['foo'].c = 5
+ self.assertEqual(0, len(msg.FindInitializationErrors()))
+
+
+
+class ValidTypeNamesTest(unittest.TestCase):
+
+ def assertImportFromName(self, msg, base_name):
+ # Parse <type 'module.class_name'> to extra 'some.name' as a string.
+ tp_name = str(type(msg)).split("'")[1]
+ valid_names = ('Repeated%sContainer' % base_name,
+ 'Repeated%sFieldContainer' % base_name)
+ self.assertTrue(any(tp_name.endswith(v) for v in valid_names),
+ '%r does end with any of %r' % (tp_name, valid_names))
+
+ parts = tp_name.split('.')
+ class_name = parts[-1]
+ module_name = '.'.join(parts[:-1])
+ __import__(module_name, fromlist=[class_name])
+
+ def testTypeNamesCanBeImported(self):
+ # If import doesn't work, pickling won't work either.
+ pb = unittest_pb2.TestAllTypes()
+ self.assertImportFromName(pb.repeated_int32, 'Scalar')
+ self.assertImportFromName(pb.repeated_nested_message, 'Composite')
+
+class PackedFieldTest(unittest.TestCase):
+
+ def setMessage(self, message):
+ message.repeated_int32.append(1)
+ message.repeated_int64.append(1)
+ message.repeated_uint32.append(1)
+ message.repeated_uint64.append(1)
+ message.repeated_sint32.append(1)
+ message.repeated_sint64.append(1)
+ message.repeated_fixed32.append(1)
+ message.repeated_fixed64.append(1)
+ message.repeated_sfixed32.append(1)
+ message.repeated_sfixed64.append(1)
+ message.repeated_float.append(1.0)
+ message.repeated_double.append(1.0)
+ message.repeated_bool.append(True)
+ message.repeated_nested_enum.append(1)
+
+ def testPackedFields(self):
+ message = packed_field_test_pb2.TestPackedTypes()
+ self.setMessage(message)
+ golden_data = (b'\x0A\x01\x01'
+ b'\x12\x01\x01'
+ b'\x1A\x01\x01'
+ b'\x22\x01\x01'
+ b'\x2A\x01\x02'
+ b'\x32\x01\x02'
+ b'\x3A\x04\x01\x00\x00\x00'
+ b'\x42\x08\x01\x00\x00\x00\x00\x00\x00\x00'
+ b'\x4A\x04\x01\x00\x00\x00'
+ b'\x52\x08\x01\x00\x00\x00\x00\x00\x00\x00'
+ b'\x5A\x04\x00\x00\x80\x3f'
+ b'\x62\x08\x00\x00\x00\x00\x00\x00\xf0\x3f'
+ b'\x6A\x01\x01'
+ b'\x72\x01\x01')
+ self.assertEqual(golden_data, message.SerializeToString())
+
+ def testUnpackedFields(self):
+ message = packed_field_test_pb2.TestUnpackedTypes()
+ self.setMessage(message)
+ golden_data = (b'\x08\x01'
+ b'\x10\x01'
+ b'\x18\x01'
+ b'\x20\x01'
+ b'\x28\x02'
+ b'\x30\x02'
+ b'\x3D\x01\x00\x00\x00'
+ b'\x41\x01\x00\x00\x00\x00\x00\x00\x00'
+ b'\x4D\x01\x00\x00\x00'
+ b'\x51\x01\x00\x00\x00\x00\x00\x00\x00'
+ b'\x5D\x00\x00\x80\x3f'
+ b'\x61\x00\x00\x00\x00\x00\x00\xf0\x3f'
+ b'\x68\x01'
+ b'\x70\x01')
+ self.assertEqual(golden_data, message.SerializeToString())
+
+
+@unittest.skipIf(api_implementation.Type() != 'cpp',
+ 'explicit tests of the C++ implementation')
+class OversizeProtosTest(unittest.TestCase):
+
+ def setUp(self):
+ self.file_desc = """
+ name: "f/f.msg2"
+ package: "f"
+ message_type {
+ name: "msg1"
+ field {
+ name: "payload"
+ number: 1
+ label: LABEL_OPTIONAL
+ type: TYPE_STRING
+ }
+ }
+ message_type {
+ name: "msg2"
+ field {
+ name: "field"
+ number: 1
+ label: LABEL_OPTIONAL
+ type: TYPE_MESSAGE
+ type_name: "msg1"
+ }
+ }
+ """
+ pool = descriptor_pool.DescriptorPool()
+ desc = descriptor_pb2.FileDescriptorProto()
+ text_format.Parse(self.file_desc, desc)
+ pool.Add(desc)
+ self.proto_cls = message_factory.MessageFactory(pool).GetPrototype(
+ pool.FindMessageTypeByName('f.msg2'))
+ self.p = self.proto_cls()
+ self.p.field.payload = 'c' * (1024 * 1024 * 64 + 1)
+ self.p_serialized = self.p.SerializeToString()
+
+ def testAssertOversizeProto(self):
+ from google.protobuf.pyext._message import SetAllowOversizeProtos
+ SetAllowOversizeProtos(False)
+ q = self.proto_cls()
+ try:
+ q.ParseFromString(self.p_serialized)
+ except message.DecodeError as e:
+ self.assertEqual(str(e), 'Error parsing message')
+
+ def testSucceedOversizeProto(self):
+ from google.protobuf.pyext._message import SetAllowOversizeProtos
+ SetAllowOversizeProtos(True)
+ q = self.proto_cls()
+ q.ParseFromString(self.p_serialized)
+ self.assertEqual(self.p.field.payload, q.field.payload)
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/missing_enum_values.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/missing_enum_values.proto
new file mode 100644
index 0000000000..1850be5bb7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/missing_enum_values.proto
@@ -0,0 +1,56 @@
+// 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.
+
+syntax = "proto2";
+
+package google.protobuf.python.internal;
+
+message TestEnumValues {
+ enum NestedEnum {
+ ZERO = 0;
+ ONE = 1;
+ }
+ optional NestedEnum optional_nested_enum = 1;
+ repeated NestedEnum repeated_nested_enum = 2;
+ repeated NestedEnum packed_nested_enum = 3 [packed = true];
+}
+
+message TestMissingEnumValues {
+ enum NestedEnum {
+ TWO = 2;
+ }
+ optional NestedEnum optional_nested_enum = 1;
+ repeated NestedEnum repeated_nested_enum = 2;
+ repeated NestedEnum packed_nested_enum = 3 [packed = true];
+}
+
+message JustString {
+ required string dummy = 1;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions.proto
new file mode 100644
index 0000000000..78f1467361
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions.proto
@@ -0,0 +1,59 @@
+// 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: robinson@google.com (Will Robinson)
+
+syntax = "proto2";
+
+package google.protobuf.internal;
+
+
+message TopLevelMessage {
+ optional ExtendedMessage submessage = 1;
+}
+
+
+message ExtendedMessage {
+ extensions 1 to max;
+}
+
+
+message ForeignMessage {
+ optional int32 foreign_message_int = 1;
+}
+
+
+extend ExtendedMessage {
+ optional int32 optional_int_extension = 1;
+ optional ForeignMessage optional_message_extension = 2;
+
+ repeated int32 repeated_int_extension = 3;
+ repeated ForeignMessage repeated_message_extension = 4;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions_dynamic.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions_dynamic.proto
new file mode 100644
index 0000000000..11f85ef60c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_extensions_dynamic.proto
@@ -0,0 +1,50 @@
+// 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: jasonh@google.com (Jason Hsueh)
+//
+// This file is used to test a corner case in the CPP implementation where the
+// generated C++ type is available for the extendee, but the extension is
+// defined in a file whose C++ type is not in the binary.
+
+syntax = "proto2";
+
+import "google/protobuf/internal/more_extensions.proto";
+
+package google.protobuf.internal;
+
+message DynamicMessageType {
+ optional int32 a = 1;
+}
+
+extend ExtendedMessage {
+ optional int32 dynamic_int32_extension = 100;
+ optional DynamicMessageType dynamic_message_extension = 101;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_messages.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_messages.proto
new file mode 100644
index 0000000000..2c6ab9efdf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/more_messages.proto
@@ -0,0 +1,52 @@
+// 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: robinson@google.com (Will Robinson)
+
+syntax = "proto2";
+
+package google.protobuf.internal;
+
+// A message where tag numbers are listed out of order, to allow us to test our
+// canonicalization of serialized output, which should always be in tag order.
+// We also mix in some extensions for extra fun.
+message OutOfOrderFields {
+ optional sint32 optional_sint32 = 5;
+ extensions 4 to 4;
+ optional uint32 optional_uint32 = 3;
+ extensions 2 to 2;
+ optional int32 optional_int32 = 1;
+};
+
+
+extend OutOfOrderFields {
+ optional uint64 optional_uint64 = 4;
+ optional int64 optional_int64 = 2;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/packed_field_test.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/packed_field_test.proto
new file mode 100644
index 0000000000..0dfdc10a87
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/packed_field_test.proto
@@ -0,0 +1,73 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf.python.internal;
+
+message TestPackedTypes {
+ enum NestedEnum {
+ FOO = 0;
+ BAR = 1;
+ BAZ = 2;
+ }
+
+ repeated int32 repeated_int32 = 1;
+ repeated int64 repeated_int64 = 2;
+ repeated uint32 repeated_uint32 = 3;
+ repeated uint64 repeated_uint64 = 4;
+ repeated sint32 repeated_sint32 = 5;
+ repeated sint64 repeated_sint64 = 6;
+ repeated fixed32 repeated_fixed32 = 7;
+ repeated fixed64 repeated_fixed64 = 8;
+ repeated sfixed32 repeated_sfixed32 = 9;
+ repeated sfixed64 repeated_sfixed64 = 10;
+ repeated float repeated_float = 11;
+ repeated double repeated_double = 12;
+ repeated bool repeated_bool = 13;
+ repeated NestedEnum repeated_nested_enum = 14;
+}
+
+message TestUnpackedTypes {
+ repeated int32 repeated_int32 = 1 [packed = false];
+ repeated int64 repeated_int64 = 2 [packed = false];
+ repeated uint32 repeated_uint32 = 3 [packed = false];
+ repeated uint64 repeated_uint64 = 4 [packed = false];
+ repeated sint32 repeated_sint32 = 5 [packed = false];
+ repeated sint64 repeated_sint64 = 6 [packed = false];
+ repeated fixed32 repeated_fixed32 = 7 [packed = false];
+ repeated fixed64 repeated_fixed64 = 8 [packed = false];
+ repeated sfixed32 repeated_sfixed32 = 9 [packed = false];
+ repeated sfixed64 repeated_sfixed64 = 10 [packed = false];
+ repeated float repeated_float = 11 [packed = false];
+ repeated double repeated_double = 12 [packed = false];
+ repeated bool repeated_bool = 13 [packed = false];
+ repeated TestPackedTypes.NestedEnum repeated_nested_enum = 14 [packed = false];
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/proto_builder_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/proto_builder_test.py
new file mode 100644
index 0000000000..36dfbfded8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/proto_builder_test.py
@@ -0,0 +1,96 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests for google.protobuf.proto_builder."""
+
+try:
+ from collections import OrderedDict
+except ImportError:
+ from ordereddict import OrderedDict #PY26
+try:
+ import unittest2 as unittest
+except ImportError:
+ import unittest
+
+from google.protobuf import descriptor_pb2
+from google.protobuf import descriptor_pool
+from google.protobuf import proto_builder
+from google.protobuf import text_format
+
+
+class ProtoBuilderTest(unittest.TestCase):
+
+ def setUp(self):
+ self.ordered_fields = OrderedDict([
+ ('foo', descriptor_pb2.FieldDescriptorProto.TYPE_INT64),
+ ('bar', descriptor_pb2.FieldDescriptorProto.TYPE_STRING),
+ ])
+ self._fields = dict(self.ordered_fields)
+
+ def testMakeSimpleProtoClass(self):
+ """Test that we can create a proto class."""
+ proto_cls = proto_builder.MakeSimpleProtoClass(
+ self._fields,
+ full_name='net.proto2.python.public.proto_builder_test.Test')
+ proto = proto_cls()
+ proto.foo = 12345
+ proto.bar = 'asdf'
+ self.assertMultiLineEqual(
+ 'bar: "asdf"\nfoo: 12345\n', text_format.MessageToString(proto))
+
+ def testOrderedFields(self):
+ """Test that the field order is maintained when given an OrderedDict."""
+ proto_cls = proto_builder.MakeSimpleProtoClass(
+ self.ordered_fields,
+ full_name='net.proto2.python.public.proto_builder_test.OrderedTest')
+ proto = proto_cls()
+ proto.foo = 12345
+ proto.bar = 'asdf'
+ self.assertMultiLineEqual(
+ 'foo: 12345\nbar: "asdf"\n', text_format.MessageToString(proto))
+
+ def testMakeSameProtoClassTwice(self):
+ """Test that the DescriptorPool is used."""
+ pool = descriptor_pool.DescriptorPool()
+ proto_cls1 = proto_builder.MakeSimpleProtoClass(
+ self._fields,
+ full_name='net.proto2.python.public.proto_builder_test.Test',
+ pool=pool)
+ proto_cls2 = proto_builder.MakeSimpleProtoClass(
+ self._fields,
+ full_name='net.proto2.python.public.proto_builder_test.Test',
+ pool=pool)
+ self.assertIs(proto_cls1.DESCRIPTOR, proto_cls2.DESCRIPTOR)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/python_message.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/python_message.py
new file mode 100755
index 0000000000..c0d0ad451f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/python_message.py
@@ -0,0 +1,1550 @@
+# 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.
+
+# This code is meant to work on Python 2.4 and above only.
+#
+# TODO(robinson): Helpers for verbose, common checks like seeing if a
+# descriptor's cpp_type is CPPTYPE_MESSAGE.
+
+"""Contains a metaclass and helper functions used to create
+protocol message classes from Descriptor objects at runtime.
+
+Recall that a metaclass is the "type" of a class.
+(A class is to a metaclass what an instance is to a class.)
+
+In this case, we use the GeneratedProtocolMessageType metaclass
+to inject all the useful functionality into the classes
+output by the protocol compiler at compile-time.
+
+The upshot of all this is that the real implementation
+details for ALL pure-Python protocol buffers are *here in
+this file*.
+"""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+from io import BytesIO
+import sys
+import struct
+import weakref
+
+import six
+try:
+ import six.moves.copyreg as copyreg
+except ImportError:
+ # On some platforms, for example gMac, we run native Python because there is
+ # nothing like hermetic Python. This means lesser control on the system and
+ # the six.moves package may be missing (is missing on 20150321 on gMac). Be
+ # extra conservative and try to load the old replacement if it fails.
+ import copy_reg as copyreg
+
+# We use "as" to avoid name collisions with variables.
+from google.protobuf.internal import containers
+from google.protobuf.internal import decoder
+from google.protobuf.internal import encoder
+from google.protobuf.internal import enum_type_wrapper
+from google.protobuf.internal import message_listener as message_listener_mod
+from google.protobuf.internal import type_checkers
+from google.protobuf.internal import well_known_types
+from google.protobuf.internal import wire_format
+from google.protobuf import descriptor as descriptor_mod
+from google.protobuf import message as message_mod
+from google.protobuf import text_format
+
+_FieldDescriptor = descriptor_mod.FieldDescriptor
+_AnyFullTypeName = 'google.protobuf.Any'
+
+
+class GeneratedProtocolMessageType(type):
+
+ """Metaclass for protocol message classes created at runtime from Descriptors.
+
+ We add implementations for all methods described in the Message class. We
+ also create properties to allow getting/setting all fields in the protocol
+ message. Finally, we create slots to prevent users from accidentally
+ "setting" nonexistent fields in the protocol message, which then wouldn't get
+ serialized / deserialized properly.
+
+ The protocol compiler currently uses this metaclass to create protocol
+ message classes at runtime. Clients can also manually create their own
+ classes at runtime, as in this example:
+
+ mydescriptor = Descriptor(.....)
+ factory = symbol_database.Default()
+ factory.pool.AddDescriptor(mydescriptor)
+ MyProtoClass = factory.GetPrototype(mydescriptor)
+ myproto_instance = MyProtoClass()
+ myproto.foo_field = 23
+ ...
+ """
+
+ # Must be consistent with the protocol-compiler code in
+ # proto2/compiler/internal/generator.*.
+ _DESCRIPTOR_KEY = 'DESCRIPTOR'
+
+ def __new__(cls, name, bases, dictionary):
+ """Custom allocation for runtime-generated class types.
+
+ We override __new__ because this is apparently the only place
+ where we can meaningfully set __slots__ on the class we're creating(?).
+ (The interplay between metaclasses and slots is not very well-documented).
+
+ Args:
+ name: Name of the class (ignored, but required by the
+ metaclass protocol).
+ bases: Base classes of the class we're constructing.
+ (Should be message.Message). We ignore this field, but
+ it's required by the metaclass protocol
+ dictionary: The class dictionary of the class we're
+ constructing. dictionary[_DESCRIPTOR_KEY] must contain
+ a Descriptor object describing this protocol message
+ type.
+
+ Returns:
+ Newly-allocated class.
+ """
+ descriptor = dictionary[GeneratedProtocolMessageType._DESCRIPTOR_KEY]
+ if descriptor.full_name in well_known_types.WKTBASES:
+ bases += (well_known_types.WKTBASES[descriptor.full_name],)
+ _AddClassAttributesForNestedExtensions(descriptor, dictionary)
+ _AddSlots(descriptor, dictionary)
+
+ superclass = super(GeneratedProtocolMessageType, cls)
+ new_class = superclass.__new__(cls, name, bases, dictionary)
+ return new_class
+
+ def __init__(cls, name, bases, dictionary):
+ """Here we perform the majority of our work on the class.
+ We add enum getters, an __init__ method, implementations
+ of all Message methods, and properties for all fields
+ in the protocol type.
+
+ Args:
+ name: Name of the class (ignored, but required by the
+ metaclass protocol).
+ bases: Base classes of the class we're constructing.
+ (Should be message.Message). We ignore this field, but
+ it's required by the metaclass protocol
+ dictionary: The class dictionary of the class we're
+ constructing. dictionary[_DESCRIPTOR_KEY] must contain
+ a Descriptor object describing this protocol message
+ type.
+ """
+ descriptor = dictionary[GeneratedProtocolMessageType._DESCRIPTOR_KEY]
+ cls._decoders_by_tag = {}
+ cls._extensions_by_name = {}
+ cls._extensions_by_number = {}
+ if (descriptor.has_options and
+ descriptor.GetOptions().message_set_wire_format):
+ cls._decoders_by_tag[decoder.MESSAGE_SET_ITEM_TAG] = (
+ decoder.MessageSetItemDecoder(cls._extensions_by_number), None)
+
+ # Attach stuff to each FieldDescriptor for quick lookup later on.
+ for field in descriptor.fields:
+ _AttachFieldHelpers(cls, field)
+
+ descriptor._concrete_class = cls # pylint: disable=protected-access
+ _AddEnumValues(descriptor, cls)
+ _AddInitMethod(descriptor, cls)
+ _AddPropertiesForFields(descriptor, cls)
+ _AddPropertiesForExtensions(descriptor, cls)
+ _AddStaticMethods(cls)
+ _AddMessageMethods(descriptor, cls)
+ _AddPrivateHelperMethods(descriptor, cls)
+ copyreg.pickle(cls, lambda obj: (cls, (), obj.__getstate__()))
+
+ superclass = super(GeneratedProtocolMessageType, cls)
+ superclass.__init__(name, bases, dictionary)
+
+
+# Stateless helpers for GeneratedProtocolMessageType below.
+# Outside clients should not access these directly.
+#
+# I opted not to make any of these methods on the metaclass, to make it more
+# clear that I'm not really using any state there and to keep clients from
+# thinking that they have direct access to these construction helpers.
+
+
+def _PropertyName(proto_field_name):
+ """Returns the name of the public property attribute which
+ clients can use to get and (in some cases) set the value
+ of a protocol message field.
+
+ Args:
+ proto_field_name: The protocol message field name, exactly
+ as it appears (or would appear) in a .proto file.
+ """
+ # TODO(robinson): Escape Python keywords (e.g., yield), and test this support.
+ # nnorwitz makes my day by writing:
+ # """
+ # FYI. See the keyword module in the stdlib. This could be as simple as:
+ #
+ # if keyword.iskeyword(proto_field_name):
+ # return proto_field_name + "_"
+ # return proto_field_name
+ # """
+ # Kenton says: The above is a BAD IDEA. People rely on being able to use
+ # getattr() and setattr() to reflectively manipulate field values. If we
+ # rename the properties, then every such user has to also make sure to apply
+ # the same transformation. Note that currently if you name a field "yield",
+ # you can still access it just fine using getattr/setattr -- it's not even
+ # that cumbersome to do so.
+ # TODO(kenton): Remove this method entirely if/when everyone agrees with my
+ # position.
+ return proto_field_name
+
+
+def _VerifyExtensionHandle(message, extension_handle):
+ """Verify that the given extension handle is valid."""
+
+ if not isinstance(extension_handle, _FieldDescriptor):
+ raise KeyError('HasExtension() expects an extension handle, got: %s' %
+ extension_handle)
+
+ if not extension_handle.is_extension:
+ raise KeyError('"%s" is not an extension.' % extension_handle.full_name)
+
+ if not extension_handle.containing_type:
+ raise KeyError('"%s" is missing a containing_type.'
+ % extension_handle.full_name)
+
+ if extension_handle.containing_type is not message.DESCRIPTOR:
+ raise KeyError('Extension "%s" extends message type "%s", but this '
+ 'message is of type "%s".' %
+ (extension_handle.full_name,
+ extension_handle.containing_type.full_name,
+ message.DESCRIPTOR.full_name))
+
+
+def _AddSlots(message_descriptor, dictionary):
+ """Adds a __slots__ entry to dictionary, containing the names of all valid
+ attributes for this message type.
+
+ Args:
+ message_descriptor: A Descriptor instance describing this message type.
+ dictionary: Class dictionary to which we'll add a '__slots__' entry.
+ """
+ dictionary['__slots__'] = ['_cached_byte_size',
+ '_cached_byte_size_dirty',
+ '_fields',
+ '_unknown_fields',
+ '_is_present_in_parent',
+ '_listener',
+ '_listener_for_children',
+ '__weakref__',
+ '_oneofs']
+
+
+def _IsMessageSetExtension(field):
+ return (field.is_extension and
+ field.containing_type.has_options and
+ field.containing_type.GetOptions().message_set_wire_format and
+ field.type == _FieldDescriptor.TYPE_MESSAGE and
+ field.label == _FieldDescriptor.LABEL_OPTIONAL)
+
+
+def _IsMapField(field):
+ return (field.type == _FieldDescriptor.TYPE_MESSAGE and
+ field.message_type.has_options and
+ field.message_type.GetOptions().map_entry)
+
+
+def _IsMessageMapField(field):
+ value_type = field.message_type.fields_by_name["value"]
+ return value_type.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE
+
+
+def _AttachFieldHelpers(cls, field_descriptor):
+ is_repeated = (field_descriptor.label == _FieldDescriptor.LABEL_REPEATED)
+ is_packable = (is_repeated and
+ wire_format.IsTypePackable(field_descriptor.type))
+ if not is_packable:
+ is_packed = False
+ elif field_descriptor.containing_type.syntax == "proto2":
+ is_packed = (field_descriptor.has_options and
+ field_descriptor.GetOptions().packed)
+ else:
+ has_packed_false = (field_descriptor.has_options and
+ field_descriptor.GetOptions().HasField("packed") and
+ field_descriptor.GetOptions().packed == False)
+ is_packed = not has_packed_false
+ is_map_entry = _IsMapField(field_descriptor)
+
+ if is_map_entry:
+ field_encoder = encoder.MapEncoder(field_descriptor)
+ sizer = encoder.MapSizer(field_descriptor)
+ elif _IsMessageSetExtension(field_descriptor):
+ field_encoder = encoder.MessageSetItemEncoder(field_descriptor.number)
+ sizer = encoder.MessageSetItemSizer(field_descriptor.number)
+ else:
+ field_encoder = type_checkers.TYPE_TO_ENCODER[field_descriptor.type](
+ field_descriptor.number, is_repeated, is_packed)
+ sizer = type_checkers.TYPE_TO_SIZER[field_descriptor.type](
+ field_descriptor.number, is_repeated, is_packed)
+
+ field_descriptor._encoder = field_encoder
+ field_descriptor._sizer = sizer
+ field_descriptor._default_constructor = _DefaultValueConstructorForField(
+ field_descriptor)
+
+ def AddDecoder(wiretype, is_packed):
+ tag_bytes = encoder.TagBytes(field_descriptor.number, wiretype)
+ decode_type = field_descriptor.type
+ if (decode_type == _FieldDescriptor.TYPE_ENUM and
+ type_checkers.SupportsOpenEnums(field_descriptor)):
+ decode_type = _FieldDescriptor.TYPE_INT32
+
+ oneof_descriptor = None
+ if field_descriptor.containing_oneof is not None:
+ oneof_descriptor = field_descriptor
+
+ if is_map_entry:
+ is_message_map = _IsMessageMapField(field_descriptor)
+
+ field_decoder = decoder.MapDecoder(
+ field_descriptor, _GetInitializeDefaultForMap(field_descriptor),
+ is_message_map)
+ else:
+ field_decoder = type_checkers.TYPE_TO_DECODER[decode_type](
+ field_descriptor.number, is_repeated, is_packed,
+ field_descriptor, field_descriptor._default_constructor)
+
+ cls._decoders_by_tag[tag_bytes] = (field_decoder, oneof_descriptor)
+
+ AddDecoder(type_checkers.FIELD_TYPE_TO_WIRE_TYPE[field_descriptor.type],
+ False)
+
+ if is_repeated and wire_format.IsTypePackable(field_descriptor.type):
+ # To support wire compatibility of adding packed = true, add a decoder for
+ # packed values regardless of the field's options.
+ AddDecoder(wire_format.WIRETYPE_LENGTH_DELIMITED, True)
+
+
+def _AddClassAttributesForNestedExtensions(descriptor, dictionary):
+ extension_dict = descriptor.extensions_by_name
+ for extension_name, extension_field in extension_dict.items():
+ assert extension_name not in dictionary
+ dictionary[extension_name] = extension_field
+
+
+def _AddEnumValues(descriptor, cls):
+ """Sets class-level attributes for all enum fields defined in this message.
+
+ Also exporting a class-level object that can name enum values.
+
+ Args:
+ descriptor: Descriptor object for this message type.
+ cls: Class we're constructing for this message type.
+ """
+ for enum_type in descriptor.enum_types:
+ setattr(cls, enum_type.name, enum_type_wrapper.EnumTypeWrapper(enum_type))
+ for enum_value in enum_type.values:
+ setattr(cls, enum_value.name, enum_value.number)
+
+
+def _GetInitializeDefaultForMap(field):
+ if field.label != _FieldDescriptor.LABEL_REPEATED:
+ raise ValueError('map_entry set on non-repeated field %s' % (
+ field.name))
+ fields_by_name = field.message_type.fields_by_name
+ key_checker = type_checkers.GetTypeChecker(fields_by_name['key'])
+
+ value_field = fields_by_name['value']
+ if _IsMessageMapField(field):
+ def MakeMessageMapDefault(message):
+ return containers.MessageMap(
+ message._listener_for_children, value_field.message_type, key_checker)
+ return MakeMessageMapDefault
+ else:
+ value_checker = type_checkers.GetTypeChecker(value_field)
+ def MakePrimitiveMapDefault(message):
+ return containers.ScalarMap(
+ message._listener_for_children, key_checker, value_checker)
+ return MakePrimitiveMapDefault
+
+def _DefaultValueConstructorForField(field):
+ """Returns a function which returns a default value for a field.
+
+ Args:
+ field: FieldDescriptor object for this field.
+
+ The returned function has one argument:
+ message: Message instance containing this field, or a weakref proxy
+ of same.
+
+ That function in turn returns a default value for this field. The default
+ value may refer back to |message| via a weak reference.
+ """
+
+ if _IsMapField(field):
+ return _GetInitializeDefaultForMap(field)
+
+ if field.label == _FieldDescriptor.LABEL_REPEATED:
+ if field.has_default_value and field.default_value != []:
+ raise ValueError('Repeated field default value not empty list: %s' % (
+ field.default_value))
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ # We can't look at _concrete_class yet since it might not have
+ # been set. (Depends on order in which we initialize the classes).
+ message_type = field.message_type
+ def MakeRepeatedMessageDefault(message):
+ return containers.RepeatedCompositeFieldContainer(
+ message._listener_for_children, field.message_type)
+ return MakeRepeatedMessageDefault
+ else:
+ type_checker = type_checkers.GetTypeChecker(field)
+ def MakeRepeatedScalarDefault(message):
+ return containers.RepeatedScalarFieldContainer(
+ message._listener_for_children, type_checker)
+ return MakeRepeatedScalarDefault
+
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ # _concrete_class may not yet be initialized.
+ message_type = field.message_type
+ def MakeSubMessageDefault(message):
+ result = message_type._concrete_class()
+ result._SetListener(
+ _OneofListener(message, field)
+ if field.containing_oneof is not None
+ else message._listener_for_children)
+ return result
+ return MakeSubMessageDefault
+
+ def MakeScalarDefault(message):
+ # TODO(protobuf-team): This may be broken since there may not be
+ # default_value. Combine with has_default_value somehow.
+ return field.default_value
+ return MakeScalarDefault
+
+
+def _ReraiseTypeErrorWithFieldName(message_name, field_name):
+ """Re-raise the currently-handled TypeError with the field name added."""
+ exc = sys.exc_info()[1]
+ if len(exc.args) == 1 and type(exc) is TypeError:
+ # simple TypeError; add field name to exception message
+ exc = TypeError('%s for field %s.%s' % (str(exc), message_name, field_name))
+
+ # re-raise possibly-amended exception with original traceback:
+ six.reraise(type(exc), exc, sys.exc_info()[2])
+
+
+def _AddInitMethod(message_descriptor, cls):
+ """Adds an __init__ method to cls."""
+
+ def _GetIntegerEnumValue(enum_type, value):
+ """Convert a string or integer enum value to an integer.
+
+ If the value is a string, it is converted to the enum value in
+ enum_type with the same name. If the value is not a string, it's
+ returned as-is. (No conversion or bounds-checking is done.)
+ """
+ if isinstance(value, six.string_types):
+ try:
+ return enum_type.values_by_name[value].number
+ except KeyError:
+ raise ValueError('Enum type %s: unknown label "%s"' % (
+ enum_type.full_name, value))
+ return value
+
+ def init(self, **kwargs):
+ self._cached_byte_size = 0
+ self._cached_byte_size_dirty = len(kwargs) > 0
+ self._fields = {}
+ # Contains a mapping from oneof field descriptors to the descriptor
+ # of the currently set field in that oneof field.
+ self._oneofs = {}
+
+ # _unknown_fields is () when empty for efficiency, and will be turned into
+ # a list if fields are added.
+ self._unknown_fields = ()
+ self._is_present_in_parent = False
+ self._listener = message_listener_mod.NullMessageListener()
+ self._listener_for_children = _Listener(self)
+ for field_name, field_value in kwargs.items():
+ field = _GetFieldByName(message_descriptor, field_name)
+ if field is None:
+ raise TypeError("%s() got an unexpected keyword argument '%s'" %
+ (message_descriptor.name, field_name))
+ if field_value is None:
+ # field=None is the same as no field at all.
+ continue
+ if field.label == _FieldDescriptor.LABEL_REPEATED:
+ copy = field._default_constructor(self)
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE: # Composite
+ if _IsMapField(field):
+ if _IsMessageMapField(field):
+ for key in field_value:
+ copy[key].MergeFrom(field_value[key])
+ else:
+ copy.update(field_value)
+ else:
+ for val in field_value:
+ if isinstance(val, dict):
+ copy.add(**val)
+ else:
+ copy.add().MergeFrom(val)
+ else: # Scalar
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_ENUM:
+ field_value = [_GetIntegerEnumValue(field.enum_type, val)
+ for val in field_value]
+ copy.extend(field_value)
+ self._fields[field] = copy
+ elif field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ copy = field._default_constructor(self)
+ new_val = field_value
+ if isinstance(field_value, dict):
+ new_val = field.message_type._concrete_class(**field_value)
+ try:
+ copy.MergeFrom(new_val)
+ except TypeError:
+ _ReraiseTypeErrorWithFieldName(message_descriptor.name, field_name)
+ self._fields[field] = copy
+ else:
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_ENUM:
+ field_value = _GetIntegerEnumValue(field.enum_type, field_value)
+ try:
+ setattr(self, field_name, field_value)
+ except TypeError:
+ _ReraiseTypeErrorWithFieldName(message_descriptor.name, field_name)
+
+ init.__module__ = None
+ init.__doc__ = None
+ cls.__init__ = init
+
+
+def _GetFieldByName(message_descriptor, field_name):
+ """Returns a field descriptor by field name.
+
+ Args:
+ message_descriptor: A Descriptor describing all fields in message.
+ field_name: The name of the field to retrieve.
+ Returns:
+ The field descriptor associated with the field name.
+ """
+ try:
+ return message_descriptor.fields_by_name[field_name]
+ except KeyError:
+ raise ValueError('Protocol message %s has no "%s" field.' %
+ (message_descriptor.name, field_name))
+
+
+def _AddPropertiesForFields(descriptor, cls):
+ """Adds properties for all fields in this protocol message type."""
+ for field in descriptor.fields:
+ _AddPropertiesForField(field, cls)
+
+ if descriptor.is_extendable:
+ # _ExtensionDict is just an adaptor with no state so we allocate a new one
+ # every time it is accessed.
+ cls.Extensions = property(lambda self: _ExtensionDict(self))
+
+
+def _AddPropertiesForField(field, cls):
+ """Adds a public property for a protocol message field.
+ Clients can use this property to get and (in the case
+ of non-repeated scalar fields) directly set the value
+ of a protocol message field.
+
+ Args:
+ field: A FieldDescriptor for this field.
+ cls: The class we're constructing.
+ """
+ # Catch it if we add other types that we should
+ # handle specially here.
+ assert _FieldDescriptor.MAX_CPPTYPE == 10
+
+ constant_name = field.name.upper() + "_FIELD_NUMBER"
+ setattr(cls, constant_name, field.number)
+
+ if field.label == _FieldDescriptor.LABEL_REPEATED:
+ _AddPropertiesForRepeatedField(field, cls)
+ elif field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ _AddPropertiesForNonRepeatedCompositeField(field, cls)
+ else:
+ _AddPropertiesForNonRepeatedScalarField(field, cls)
+
+
+def _AddPropertiesForRepeatedField(field, cls):
+ """Adds a public property for a "repeated" protocol message field. Clients
+ can use this property to get the value of the field, which will be either a
+ _RepeatedScalarFieldContainer or _RepeatedCompositeFieldContainer (see
+ below).
+
+ Note that when clients add values to these containers, we perform
+ type-checking in the case of repeated scalar fields, and we also set any
+ necessary "has" bits as a side-effect.
+
+ Args:
+ field: A FieldDescriptor for this field.
+ cls: The class we're constructing.
+ """
+ proto_field_name = field.name
+ property_name = _PropertyName(proto_field_name)
+
+ def getter(self):
+ field_value = self._fields.get(field)
+ if field_value is None:
+ # Construct a new object to represent this field.
+ field_value = field._default_constructor(self)
+
+ # Atomically check if another thread has preempted us and, if not, swap
+ # in the new object we just created. If someone has preempted us, we
+ # take that object and discard ours.
+ # WARNING: We are relying on setdefault() being atomic. This is true
+ # in CPython but we haven't investigated others. This warning appears
+ # in several other locations in this file.
+ field_value = self._fields.setdefault(field, field_value)
+ return field_value
+ getter.__module__ = None
+ getter.__doc__ = 'Getter for %s.' % proto_field_name
+
+ # We define a setter just so we can throw an exception with a more
+ # helpful error message.
+ def setter(self, new_value):
+ raise AttributeError('Assignment not allowed to repeated field '
+ '"%s" in protocol message object.' % proto_field_name)
+
+ doc = 'Magic attribute generated for "%s" proto field.' % proto_field_name
+ setattr(cls, property_name, property(getter, setter, doc=doc))
+
+
+def _AddPropertiesForNonRepeatedScalarField(field, cls):
+ """Adds a public property for a nonrepeated, scalar protocol message field.
+ Clients can use this property to get and directly set the value of the field.
+ Note that when the client sets the value of a field by using this property,
+ all necessary "has" bits are set as a side-effect, and we also perform
+ type-checking.
+
+ Args:
+ field: A FieldDescriptor for this field.
+ cls: The class we're constructing.
+ """
+ proto_field_name = field.name
+ property_name = _PropertyName(proto_field_name)
+ type_checker = type_checkers.GetTypeChecker(field)
+ default_value = field.default_value
+ valid_values = set()
+ is_proto3 = field.containing_type.syntax == "proto3"
+
+ def getter(self):
+ # TODO(protobuf-team): This may be broken since there may not be
+ # default_value. Combine with has_default_value somehow.
+ return self._fields.get(field, default_value)
+ getter.__module__ = None
+ getter.__doc__ = 'Getter for %s.' % proto_field_name
+
+ clear_when_set_to_default = is_proto3 and not field.containing_oneof
+
+ def field_setter(self, new_value):
+ # pylint: disable=protected-access
+ # Testing the value for truthiness captures all of the proto3 defaults
+ # (0, 0.0, enum 0, and False).
+ new_value = type_checker.CheckValue(new_value)
+ if clear_when_set_to_default and not new_value:
+ self._fields.pop(field, None)
+ else:
+ self._fields[field] = new_value
+ # Check _cached_byte_size_dirty inline to improve performance, since scalar
+ # setters are called frequently.
+ if not self._cached_byte_size_dirty:
+ self._Modified()
+
+ if field.containing_oneof:
+ def setter(self, new_value):
+ field_setter(self, new_value)
+ self._UpdateOneofState(field)
+ else:
+ setter = field_setter
+
+ setter.__module__ = None
+ setter.__doc__ = 'Setter for %s.' % proto_field_name
+
+ # Add a property to encapsulate the getter/setter.
+ doc = 'Magic attribute generated for "%s" proto field.' % proto_field_name
+ setattr(cls, property_name, property(getter, setter, doc=doc))
+
+
+def _AddPropertiesForNonRepeatedCompositeField(field, cls):
+ """Adds a public property for a nonrepeated, composite protocol message field.
+ A composite field is a "group" or "message" field.
+
+ Clients can use this property to get the value of the field, but cannot
+ assign to the property directly.
+
+ Args:
+ field: A FieldDescriptor for this field.
+ cls: The class we're constructing.
+ """
+ # TODO(robinson): Remove duplication with similar method
+ # for non-repeated scalars.
+ proto_field_name = field.name
+ property_name = _PropertyName(proto_field_name)
+
+ def getter(self):
+ field_value = self._fields.get(field)
+ if field_value is None:
+ # Construct a new object to represent this field.
+ field_value = field._default_constructor(self)
+
+ # Atomically check if another thread has preempted us and, if not, swap
+ # in the new object we just created. If someone has preempted us, we
+ # take that object and discard ours.
+ # WARNING: We are relying on setdefault() being atomic. This is true
+ # in CPython but we haven't investigated others. This warning appears
+ # in several other locations in this file.
+ field_value = self._fields.setdefault(field, field_value)
+ return field_value
+ getter.__module__ = None
+ getter.__doc__ = 'Getter for %s.' % proto_field_name
+
+ # We define a setter just so we can throw an exception with a more
+ # helpful error message.
+ def setter(self, new_value):
+ raise AttributeError('Assignment not allowed to composite field '
+ '"%s" in protocol message object.' % proto_field_name)
+
+ # Add a property to encapsulate the getter.
+ doc = 'Magic attribute generated for "%s" proto field.' % proto_field_name
+ setattr(cls, property_name, property(getter, setter, doc=doc))
+
+
+def _AddPropertiesForExtensions(descriptor, cls):
+ """Adds properties for all fields in this protocol message type."""
+ extension_dict = descriptor.extensions_by_name
+ for extension_name, extension_field in extension_dict.items():
+ constant_name = extension_name.upper() + "_FIELD_NUMBER"
+ setattr(cls, constant_name, extension_field.number)
+
+
+def _AddStaticMethods(cls):
+ # TODO(robinson): This probably needs to be thread-safe(?)
+ def RegisterExtension(extension_handle):
+ extension_handle.containing_type = cls.DESCRIPTOR
+ _AttachFieldHelpers(cls, extension_handle)
+
+ # Try to insert our extension, failing if an extension with the same number
+ # already exists.
+ actual_handle = cls._extensions_by_number.setdefault(
+ extension_handle.number, extension_handle)
+ if actual_handle is not extension_handle:
+ raise AssertionError(
+ 'Extensions "%s" and "%s" both try to extend message type "%s" with '
+ 'field number %d.' %
+ (extension_handle.full_name, actual_handle.full_name,
+ cls.DESCRIPTOR.full_name, extension_handle.number))
+
+ cls._extensions_by_name[extension_handle.full_name] = extension_handle
+
+ handle = extension_handle # avoid line wrapping
+ if _IsMessageSetExtension(handle):
+ # MessageSet extension. Also register under type name.
+ cls._extensions_by_name[
+ extension_handle.message_type.full_name] = extension_handle
+
+ cls.RegisterExtension = staticmethod(RegisterExtension)
+
+ def FromString(s):
+ message = cls()
+ message.MergeFromString(s)
+ return message
+ cls.FromString = staticmethod(FromString)
+
+
+def _IsPresent(item):
+ """Given a (FieldDescriptor, value) tuple from _fields, return true if the
+ value should be included in the list returned by ListFields()."""
+
+ if item[0].label == _FieldDescriptor.LABEL_REPEATED:
+ return bool(item[1])
+ elif item[0].cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ return item[1]._is_present_in_parent
+ else:
+ return True
+
+
+def _AddListFieldsMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+
+ def ListFields(self):
+ all_fields = [item for item in self._fields.items() if _IsPresent(item)]
+ all_fields.sort(key = lambda item: item[0].number)
+ return all_fields
+
+ cls.ListFields = ListFields
+
+_Proto3HasError = 'Protocol message has no non-repeated submessage field "%s"'
+_Proto2HasError = 'Protocol message has no non-repeated field "%s"'
+
+def _AddHasFieldMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+
+ is_proto3 = (message_descriptor.syntax == "proto3")
+ error_msg = _Proto3HasError if is_proto3 else _Proto2HasError
+
+ hassable_fields = {}
+ for field in message_descriptor.fields:
+ if field.label == _FieldDescriptor.LABEL_REPEATED:
+ continue
+ # For proto3, only submessages and fields inside a oneof have presence.
+ if (is_proto3 and field.cpp_type != _FieldDescriptor.CPPTYPE_MESSAGE and
+ not field.containing_oneof):
+ continue
+ hassable_fields[field.name] = field
+
+ if not is_proto3:
+ # Fields inside oneofs are never repeated (enforced by the compiler).
+ for oneof in message_descriptor.oneofs:
+ hassable_fields[oneof.name] = oneof
+
+ def HasField(self, field_name):
+ try:
+ field = hassable_fields[field_name]
+ except KeyError:
+ raise ValueError(error_msg % field_name)
+
+ if isinstance(field, descriptor_mod.OneofDescriptor):
+ try:
+ return HasField(self, self._oneofs[field].name)
+ except KeyError:
+ return False
+ else:
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ value = self._fields.get(field)
+ return value is not None and value._is_present_in_parent
+ else:
+ return field in self._fields
+
+ cls.HasField = HasField
+
+
+def _AddClearFieldMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+ def ClearField(self, field_name):
+ try:
+ field = message_descriptor.fields_by_name[field_name]
+ except KeyError:
+ try:
+ field = message_descriptor.oneofs_by_name[field_name]
+ if field in self._oneofs:
+ field = self._oneofs[field]
+ else:
+ return
+ except KeyError:
+ raise ValueError('Protocol message %s() has no "%s" field.' %
+ (message_descriptor.name, field_name))
+
+ if field in self._fields:
+ # To match the C++ implementation, we need to invalidate iterators
+ # for map fields when ClearField() happens.
+ if hasattr(self._fields[field], 'InvalidateIterators'):
+ self._fields[field].InvalidateIterators()
+
+ # Note: If the field is a sub-message, its listener will still point
+ # at us. That's fine, because the worst than can happen is that it
+ # will call _Modified() and invalidate our byte size. Big deal.
+ del self._fields[field]
+
+ if self._oneofs.get(field.containing_oneof, None) is field:
+ del self._oneofs[field.containing_oneof]
+
+ # Always call _Modified() -- even if nothing was changed, this is
+ # a mutating method, and thus calling it should cause the field to become
+ # present in the parent message.
+ self._Modified()
+
+ cls.ClearField = ClearField
+
+
+def _AddClearExtensionMethod(cls):
+ """Helper for _AddMessageMethods()."""
+ def ClearExtension(self, extension_handle):
+ _VerifyExtensionHandle(self, extension_handle)
+
+ # Similar to ClearField(), above.
+ if extension_handle in self._fields:
+ del self._fields[extension_handle]
+ self._Modified()
+ cls.ClearExtension = ClearExtension
+
+
+def _AddHasExtensionMethod(cls):
+ """Helper for _AddMessageMethods()."""
+ def HasExtension(self, extension_handle):
+ _VerifyExtensionHandle(self, extension_handle)
+ if extension_handle.label == _FieldDescriptor.LABEL_REPEATED:
+ raise KeyError('"%s" is repeated.' % extension_handle.full_name)
+
+ if extension_handle.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ value = self._fields.get(extension_handle)
+ return value is not None and value._is_present_in_parent
+ else:
+ return extension_handle in self._fields
+ cls.HasExtension = HasExtension
+
+def _InternalUnpackAny(msg):
+ """Unpacks Any message and returns the unpacked message.
+
+ This internal method is differnt from public Any Unpack method which takes
+ the target message as argument. _InternalUnpackAny method does not have
+ target message type and need to find the message type in descriptor pool.
+
+ Args:
+ msg: An Any message to be unpacked.
+
+ Returns:
+ The unpacked message.
+ """
+ # TODO(amauryfa): Don't use the factory of generated messages.
+ # To make Any work with custom factories, use the message factory of the
+ # parent message.
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf import symbol_database
+ factory = symbol_database.Default()
+
+ type_url = msg.type_url
+
+ if not type_url:
+ return None
+
+ # TODO(haberman): For now we just strip the hostname. Better logic will be
+ # required.
+ type_name = type_url.split('/')[-1]
+ descriptor = factory.pool.FindMessageTypeByName(type_name)
+
+ if descriptor is None:
+ return None
+
+ message_class = factory.GetPrototype(descriptor)
+ message = message_class()
+
+ message.ParseFromString(msg.value)
+ return message
+
+
+def _AddEqualsMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+ def __eq__(self, other):
+ if (not isinstance(other, message_mod.Message) or
+ other.DESCRIPTOR != self.DESCRIPTOR):
+ return False
+
+ if self is other:
+ return True
+
+ if self.DESCRIPTOR.full_name == _AnyFullTypeName:
+ any_a = _InternalUnpackAny(self)
+ any_b = _InternalUnpackAny(other)
+ if any_a and any_b:
+ return any_a == any_b
+
+ if not self.ListFields() == other.ListFields():
+ return False
+
+ # Sort unknown fields because their order shouldn't affect equality test.
+ unknown_fields = list(self._unknown_fields)
+ unknown_fields.sort()
+ other_unknown_fields = list(other._unknown_fields)
+ other_unknown_fields.sort()
+
+ return unknown_fields == other_unknown_fields
+
+ cls.__eq__ = __eq__
+
+
+def _AddStrMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+ def __str__(self):
+ return text_format.MessageToString(self)
+ cls.__str__ = __str__
+
+
+def _AddReprMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+ def __repr__(self):
+ return text_format.MessageToString(self)
+ cls.__repr__ = __repr__
+
+
+def _AddUnicodeMethod(unused_message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+
+ def __unicode__(self):
+ return text_format.MessageToString(self, as_utf8=True).decode('utf-8')
+ cls.__unicode__ = __unicode__
+
+
+def _BytesForNonRepeatedElement(value, field_number, field_type):
+ """Returns the number of bytes needed to serialize a non-repeated element.
+ The returned byte count includes space for tag information and any
+ other additional space associated with serializing value.
+
+ Args:
+ value: Value we're serializing.
+ field_number: Field number of this value. (Since the field number
+ is stored as part of a varint-encoded tag, this has an impact
+ on the total bytes required to serialize the value).
+ field_type: The type of the field. One of the TYPE_* constants
+ within FieldDescriptor.
+ """
+ try:
+ fn = type_checkers.TYPE_TO_BYTE_SIZE_FN[field_type]
+ return fn(field_number, value)
+ except KeyError:
+ raise message_mod.EncodeError('Unrecognized field type: %d' % field_type)
+
+
+def _AddByteSizeMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+
+ def ByteSize(self):
+ if not self._cached_byte_size_dirty:
+ return self._cached_byte_size
+
+ size = 0
+ for field_descriptor, field_value in self.ListFields():
+ size += field_descriptor._sizer(field_value)
+
+ for tag_bytes, value_bytes in self._unknown_fields:
+ size += len(tag_bytes) + len(value_bytes)
+
+ self._cached_byte_size = size
+ self._cached_byte_size_dirty = False
+ self._listener_for_children.dirty = False
+ return size
+
+ cls.ByteSize = ByteSize
+
+
+def _AddSerializeToStringMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+
+ def SerializeToString(self):
+ # Check if the message has all of its required fields set.
+ errors = []
+ if not self.IsInitialized():
+ raise message_mod.EncodeError(
+ 'Message %s is missing required fields: %s' % (
+ self.DESCRIPTOR.full_name, ','.join(self.FindInitializationErrors())))
+ return self.SerializePartialToString()
+ cls.SerializeToString = SerializeToString
+
+
+def _AddSerializePartialToStringMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+
+ def SerializePartialToString(self):
+ out = BytesIO()
+ self._InternalSerialize(out.write)
+ return out.getvalue()
+ cls.SerializePartialToString = SerializePartialToString
+
+ def InternalSerialize(self, write_bytes):
+ for field_descriptor, field_value in self.ListFields():
+ field_descriptor._encoder(write_bytes, field_value)
+ for tag_bytes, value_bytes in self._unknown_fields:
+ write_bytes(tag_bytes)
+ write_bytes(value_bytes)
+ cls._InternalSerialize = InternalSerialize
+
+
+def _AddMergeFromStringMethod(message_descriptor, cls):
+ """Helper for _AddMessageMethods()."""
+ def MergeFromString(self, serialized):
+ length = len(serialized)
+ try:
+ if self._InternalParse(serialized, 0, length) != length:
+ # The only reason _InternalParse would return early is if it
+ # encountered an end-group tag.
+ raise message_mod.DecodeError('Unexpected end-group tag.')
+ except (IndexError, TypeError):
+ # Now ord(buf[p:p+1]) == ord('') gets TypeError.
+ raise message_mod.DecodeError('Truncated message.')
+ except struct.error as e:
+ raise message_mod.DecodeError(e)
+ return length # Return this for legacy reasons.
+ cls.MergeFromString = MergeFromString
+
+ local_ReadTag = decoder.ReadTag
+ local_SkipField = decoder.SkipField
+ decoders_by_tag = cls._decoders_by_tag
+ is_proto3 = message_descriptor.syntax == "proto3"
+
+ def InternalParse(self, buffer, pos, end):
+ self._Modified()
+ field_dict = self._fields
+ unknown_field_list = self._unknown_fields
+ while pos != end:
+ (tag_bytes, new_pos) = local_ReadTag(buffer, pos)
+ field_decoder, field_desc = decoders_by_tag.get(tag_bytes, (None, None))
+ if field_decoder is None:
+ value_start_pos = new_pos
+ new_pos = local_SkipField(buffer, new_pos, end, tag_bytes)
+ if new_pos == -1:
+ return pos
+ if not is_proto3:
+ if not unknown_field_list:
+ unknown_field_list = self._unknown_fields = []
+ unknown_field_list.append(
+ (tag_bytes, buffer[value_start_pos:new_pos]))
+ pos = new_pos
+ else:
+ pos = field_decoder(buffer, new_pos, end, self, field_dict)
+ if field_desc:
+ self._UpdateOneofState(field_desc)
+ return pos
+ cls._InternalParse = InternalParse
+
+
+def _AddIsInitializedMethod(message_descriptor, cls):
+ """Adds the IsInitialized and FindInitializationError methods to the
+ protocol message class."""
+
+ required_fields = [field for field in message_descriptor.fields
+ if field.label == _FieldDescriptor.LABEL_REQUIRED]
+
+ def IsInitialized(self, errors=None):
+ """Checks if all required fields of a message are set.
+
+ Args:
+ errors: A list which, if provided, will be populated with the field
+ paths of all missing required fields.
+
+ Returns:
+ True iff the specified message has all required fields set.
+ """
+
+ # Performance is critical so we avoid HasField() and ListFields().
+
+ for field in required_fields:
+ if (field not in self._fields or
+ (field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE and
+ not self._fields[field]._is_present_in_parent)):
+ if errors is not None:
+ errors.extend(self.FindInitializationErrors())
+ return False
+
+ for field, value in list(self._fields.items()): # dict can change size!
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ if field.label == _FieldDescriptor.LABEL_REPEATED:
+ if (field.message_type.has_options and
+ field.message_type.GetOptions().map_entry):
+ continue
+ for element in value:
+ if not element.IsInitialized():
+ if errors is not None:
+ errors.extend(self.FindInitializationErrors())
+ return False
+ elif value._is_present_in_parent and not value.IsInitialized():
+ if errors is not None:
+ errors.extend(self.FindInitializationErrors())
+ return False
+
+ return True
+
+ cls.IsInitialized = IsInitialized
+
+ def FindInitializationErrors(self):
+ """Finds required fields which are not initialized.
+
+ Returns:
+ A list of strings. Each string is a path to an uninitialized field from
+ the top-level message, e.g. "foo.bar[5].baz".
+ """
+
+ errors = [] # simplify things
+
+ for field in required_fields:
+ if not self.HasField(field.name):
+ errors.append(field.name)
+
+ for field, value in self.ListFields():
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ if field.is_extension:
+ name = "(%s)" % field.full_name
+ else:
+ name = field.name
+
+ if _IsMapField(field):
+ if _IsMessageMapField(field):
+ for key in value:
+ element = value[key]
+ prefix = "%s[%s]." % (name, key)
+ sub_errors = element.FindInitializationErrors()
+ errors += [prefix + error for error in sub_errors]
+ else:
+ # ScalarMaps can't have any initialization errors.
+ pass
+ elif field.label == _FieldDescriptor.LABEL_REPEATED:
+ for i in range(len(value)):
+ element = value[i]
+ prefix = "%s[%d]." % (name, i)
+ sub_errors = element.FindInitializationErrors()
+ errors += [prefix + error for error in sub_errors]
+ else:
+ prefix = name + "."
+ sub_errors = value.FindInitializationErrors()
+ errors += [prefix + error for error in sub_errors]
+
+ return errors
+
+ cls.FindInitializationErrors = FindInitializationErrors
+
+
+def _AddMergeFromMethod(cls):
+ LABEL_REPEATED = _FieldDescriptor.LABEL_REPEATED
+ CPPTYPE_MESSAGE = _FieldDescriptor.CPPTYPE_MESSAGE
+
+ def MergeFrom(self, msg):
+ if not isinstance(msg, cls):
+ raise TypeError(
+ "Parameter to MergeFrom() must be instance of same class: "
+ "expected %s got %s." % (cls.__name__, type(msg).__name__))
+
+ assert msg is not self
+ self._Modified()
+
+ fields = self._fields
+
+ for field, value in msg._fields.items():
+ if field.label == LABEL_REPEATED:
+ field_value = fields.get(field)
+ if field_value is None:
+ # Construct a new object to represent this field.
+ field_value = field._default_constructor(self)
+ fields[field] = field_value
+ field_value.MergeFrom(value)
+ elif field.cpp_type == CPPTYPE_MESSAGE:
+ if value._is_present_in_parent:
+ field_value = fields.get(field)
+ if field_value is None:
+ # Construct a new object to represent this field.
+ field_value = field._default_constructor(self)
+ fields[field] = field_value
+ field_value.MergeFrom(value)
+ else:
+ self._fields[field] = value
+ if field.containing_oneof:
+ self._UpdateOneofState(field)
+
+ if msg._unknown_fields:
+ if not self._unknown_fields:
+ self._unknown_fields = []
+ self._unknown_fields.extend(msg._unknown_fields)
+
+ cls.MergeFrom = MergeFrom
+
+
+def _AddWhichOneofMethod(message_descriptor, cls):
+ def WhichOneof(self, oneof_name):
+ """Returns the name of the currently set field inside a oneof, or None."""
+ try:
+ field = message_descriptor.oneofs_by_name[oneof_name]
+ except KeyError:
+ raise ValueError(
+ 'Protocol message has no oneof "%s" field.' % oneof_name)
+
+ nested_field = self._oneofs.get(field, None)
+ if nested_field is not None and self.HasField(nested_field.name):
+ return nested_field.name
+ else:
+ return None
+
+ cls.WhichOneof = WhichOneof
+
+
+def _Clear(self):
+ # Clear fields.
+ self._fields = {}
+ self._unknown_fields = ()
+ self._oneofs = {}
+ self._Modified()
+
+
+def _DiscardUnknownFields(self):
+ self._unknown_fields = []
+ for field, value in self.ListFields():
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ if field.label == _FieldDescriptor.LABEL_REPEATED:
+ for sub_message in value:
+ sub_message.DiscardUnknownFields()
+ else:
+ value.DiscardUnknownFields()
+
+
+def _SetListener(self, listener):
+ if listener is None:
+ self._listener = message_listener_mod.NullMessageListener()
+ else:
+ self._listener = listener
+
+
+def _AddMessageMethods(message_descriptor, cls):
+ """Adds implementations of all Message methods to cls."""
+ _AddListFieldsMethod(message_descriptor, cls)
+ _AddHasFieldMethod(message_descriptor, cls)
+ _AddClearFieldMethod(message_descriptor, cls)
+ if message_descriptor.is_extendable:
+ _AddClearExtensionMethod(cls)
+ _AddHasExtensionMethod(cls)
+ _AddEqualsMethod(message_descriptor, cls)
+ _AddStrMethod(message_descriptor, cls)
+ _AddReprMethod(message_descriptor, cls)
+ _AddUnicodeMethod(message_descriptor, cls)
+ _AddByteSizeMethod(message_descriptor, cls)
+ _AddSerializeToStringMethod(message_descriptor, cls)
+ _AddSerializePartialToStringMethod(message_descriptor, cls)
+ _AddMergeFromStringMethod(message_descriptor, cls)
+ _AddIsInitializedMethod(message_descriptor, cls)
+ _AddMergeFromMethod(cls)
+ _AddWhichOneofMethod(message_descriptor, cls)
+ # Adds methods which do not depend on cls.
+ cls.Clear = _Clear
+ cls.DiscardUnknownFields = _DiscardUnknownFields
+ cls._SetListener = _SetListener
+
+
+def _AddPrivateHelperMethods(message_descriptor, cls):
+ """Adds implementation of private helper methods to cls."""
+
+ def Modified(self):
+ """Sets the _cached_byte_size_dirty bit to true,
+ and propagates this to our listener iff this was a state change.
+ """
+
+ # Note: Some callers check _cached_byte_size_dirty before calling
+ # _Modified() as an extra optimization. So, if this method is ever
+ # changed such that it does stuff even when _cached_byte_size_dirty is
+ # already true, the callers need to be updated.
+ if not self._cached_byte_size_dirty:
+ self._cached_byte_size_dirty = True
+ self._listener_for_children.dirty = True
+ self._is_present_in_parent = True
+ self._listener.Modified()
+
+ def _UpdateOneofState(self, field):
+ """Sets field as the active field in its containing oneof.
+
+ Will also delete currently active field in the oneof, if it is different
+ from the argument. Does not mark the message as modified.
+ """
+ other_field = self._oneofs.setdefault(field.containing_oneof, field)
+ if other_field is not field:
+ del self._fields[other_field]
+ self._oneofs[field.containing_oneof] = field
+
+ cls._Modified = Modified
+ cls.SetInParent = Modified
+ cls._UpdateOneofState = _UpdateOneofState
+
+
+class _Listener(object):
+
+ """MessageListener implementation that a parent message registers with its
+ child message.
+
+ In order to support semantics like:
+
+ foo.bar.baz.qux = 23
+ assert foo.HasField('bar')
+
+ ...child objects must have back references to their parents.
+ This helper class is at the heart of this support.
+ """
+
+ def __init__(self, parent_message):
+ """Args:
+ parent_message: The message whose _Modified() method we should call when
+ we receive Modified() messages.
+ """
+ # This listener establishes a back reference from a child (contained) object
+ # to its parent (containing) object. We make this a weak reference to avoid
+ # creating cyclic garbage when the client finishes with the 'parent' object
+ # in the tree.
+ if isinstance(parent_message, weakref.ProxyType):
+ self._parent_message_weakref = parent_message
+ else:
+ self._parent_message_weakref = weakref.proxy(parent_message)
+
+ # As an optimization, we also indicate directly on the listener whether
+ # or not the parent message is dirty. This way we can avoid traversing
+ # up the tree in the common case.
+ self.dirty = False
+
+ def Modified(self):
+ if self.dirty:
+ return
+ try:
+ # Propagate the signal to our parents iff this is the first field set.
+ self._parent_message_weakref._Modified()
+ except ReferenceError:
+ # We can get here if a client has kept a reference to a child object,
+ # and is now setting a field on it, but the child's parent has been
+ # garbage-collected. This is not an error.
+ pass
+
+
+class _OneofListener(_Listener):
+ """Special listener implementation for setting composite oneof fields."""
+
+ def __init__(self, parent_message, field):
+ """Args:
+ parent_message: The message whose _Modified() method we should call when
+ we receive Modified() messages.
+ field: The descriptor of the field being set in the parent message.
+ """
+ super(_OneofListener, self).__init__(parent_message)
+ self._field = field
+
+ def Modified(self):
+ """Also updates the state of the containing oneof in the parent message."""
+ try:
+ self._parent_message_weakref._UpdateOneofState(self._field)
+ super(_OneofListener, self).Modified()
+ except ReferenceError:
+ pass
+
+
+# TODO(robinson): Move elsewhere? This file is getting pretty ridiculous...
+# TODO(robinson): Unify error handling of "unknown extension" crap.
+# TODO(robinson): Support iteritems()-style iteration over all
+# extensions with the "has" bits turned on?
+class _ExtensionDict(object):
+
+ """Dict-like container for supporting an indexable "Extensions"
+ field on proto instances.
+
+ Note that in all cases we expect extension handles to be
+ FieldDescriptors.
+ """
+
+ def __init__(self, extended_message):
+ """extended_message: Message instance for which we are the Extensions dict.
+ """
+
+ self._extended_message = extended_message
+
+ def __getitem__(self, extension_handle):
+ """Returns the current value of the given extension handle."""
+
+ _VerifyExtensionHandle(self._extended_message, extension_handle)
+
+ result = self._extended_message._fields.get(extension_handle)
+ if result is not None:
+ return result
+
+ if extension_handle.label == _FieldDescriptor.LABEL_REPEATED:
+ result = extension_handle._default_constructor(self._extended_message)
+ elif extension_handle.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE:
+ result = extension_handle.message_type._concrete_class()
+ try:
+ result._SetListener(self._extended_message._listener_for_children)
+ except ReferenceError:
+ pass
+ else:
+ # Singular scalar -- just return the default without inserting into the
+ # dict.
+ return extension_handle.default_value
+
+ # Atomically check if another thread has preempted us and, if not, swap
+ # in the new object we just created. If someone has preempted us, we
+ # take that object and discard ours.
+ # WARNING: We are relying on setdefault() being atomic. This is true
+ # in CPython but we haven't investigated others. This warning appears
+ # in several other locations in this file.
+ result = self._extended_message._fields.setdefault(
+ extension_handle, result)
+
+ return result
+
+ def __eq__(self, other):
+ if not isinstance(other, self.__class__):
+ return False
+
+ my_fields = self._extended_message.ListFields()
+ other_fields = other._extended_message.ListFields()
+
+ # Get rid of non-extension fields.
+ my_fields = [ field for field in my_fields if field.is_extension ]
+ other_fields = [ field for field in other_fields if field.is_extension ]
+
+ return my_fields == other_fields
+
+ def __ne__(self, other):
+ return not self == other
+
+ def __hash__(self):
+ raise TypeError('unhashable object')
+
+ # Note that this is only meaningful for non-repeated, scalar extension
+ # fields. Note also that we may have to call _Modified() when we do
+ # successfully set a field this way, to set any necssary "has" bits in the
+ # ancestors of the extended message.
+ def __setitem__(self, extension_handle, value):
+ """If extension_handle specifies a non-repeated, scalar extension
+ field, sets the value of that field.
+ """
+
+ _VerifyExtensionHandle(self._extended_message, extension_handle)
+
+ if (extension_handle.label == _FieldDescriptor.LABEL_REPEATED or
+ extension_handle.cpp_type == _FieldDescriptor.CPPTYPE_MESSAGE):
+ raise TypeError(
+ 'Cannot assign to extension "%s" because it is a repeated or '
+ 'composite type.' % extension_handle.full_name)
+
+ # It's slightly wasteful to lookup the type checker each time,
+ # but we expect this to be a vanishingly uncommon case anyway.
+ type_checker = type_checkers.GetTypeChecker(extension_handle)
+ # pylint: disable=protected-access
+ self._extended_message._fields[extension_handle] = (
+ type_checker.CheckValue(value))
+ self._extended_message._Modified()
+
+ def _FindExtensionByName(self, name):
+ """Tries to find a known extension with the specified name.
+
+ Args:
+ name: Extension full name.
+
+ Returns:
+ Extension field descriptor.
+ """
+ return self._extended_message._extensions_by_name.get(name, None)
+
+ def _FindExtensionByNumber(self, number):
+ """Tries to find a known extension with the field number.
+
+ Args:
+ number: Extension field number.
+
+ Returns:
+ Extension field descriptor.
+ """
+ return self._extended_message._extensions_by_number.get(number, None)
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/reflection_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/reflection_test.py
new file mode 100755
index 0000000000..20e5d245d3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/reflection_test.py
@@ -0,0 +1,2984 @@
+#! /usr/bin/env python
+# -*- coding: utf-8 -*-
+#
+# 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.
+
+"""Unittest for reflection.py, which also indirectly tests the output of the
+pure-Python protocol compiler.
+"""
+
+import copy
+import gc
+import operator
+import six
+import struct
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import unittest_import_pb2
+from google.protobuf import unittest_mset_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import descriptor_pb2
+from google.protobuf import descriptor
+from google.protobuf import message
+from google.protobuf import reflection
+from google.protobuf import text_format
+from google.protobuf.internal import api_implementation
+from google.protobuf.internal import more_extensions_pb2
+from google.protobuf.internal import more_messages_pb2
+from google.protobuf.internal import message_set_extensions_pb2
+from google.protobuf.internal import wire_format
+from google.protobuf.internal import test_util
+from google.protobuf.internal import decoder
+
+
+class _MiniDecoder(object):
+ """Decodes a stream of values from a string.
+
+ Once upon a time we actually had a class called decoder.Decoder. Then we
+ got rid of it during a redesign that made decoding much, much faster overall.
+ But a couple tests in this file used it to check that the serialized form of
+ a message was correct. So, this class implements just the methods that were
+ used by said tests, so that we don't have to rewrite the tests.
+ """
+
+ def __init__(self, bytes):
+ self._bytes = bytes
+ self._pos = 0
+
+ def ReadVarint(self):
+ result, self._pos = decoder._DecodeVarint(self._bytes, self._pos)
+ return result
+
+ ReadInt32 = ReadVarint
+ ReadInt64 = ReadVarint
+ ReadUInt32 = ReadVarint
+ ReadUInt64 = ReadVarint
+
+ def ReadSInt64(self):
+ return wire_format.ZigZagDecode(self.ReadVarint())
+
+ ReadSInt32 = ReadSInt64
+
+ def ReadFieldNumberAndWireType(self):
+ return wire_format.UnpackTag(self.ReadVarint())
+
+ def ReadFloat(self):
+ result = struct.unpack("<f", self._bytes[self._pos:self._pos+4])[0]
+ self._pos += 4
+ return result
+
+ def ReadDouble(self):
+ result = struct.unpack("<d", self._bytes[self._pos:self._pos+8])[0]
+ self._pos += 8
+ return result
+
+ def EndOfStream(self):
+ return self._pos == len(self._bytes)
+
+
+class ReflectionTest(unittest.TestCase):
+
+ def assertListsEqual(self, values, others):
+ self.assertEqual(len(values), len(others))
+ for i in range(len(values)):
+ self.assertEqual(values[i], others[i])
+
+ def testScalarConstructor(self):
+ # Constructor with only scalar types should succeed.
+ proto = unittest_pb2.TestAllTypes(
+ optional_int32=24,
+ optional_double=54.321,
+ optional_string='optional_string',
+ optional_float=None)
+
+ self.assertEqual(24, proto.optional_int32)
+ self.assertEqual(54.321, proto.optional_double)
+ self.assertEqual('optional_string', proto.optional_string)
+ self.assertFalse(proto.HasField("optional_float"))
+
+ def testRepeatedScalarConstructor(self):
+ # Constructor with only repeated scalar types should succeed.
+ proto = unittest_pb2.TestAllTypes(
+ repeated_int32=[1, 2, 3, 4],
+ repeated_double=[1.23, 54.321],
+ repeated_bool=[True, False, False],
+ repeated_string=["optional_string"],
+ repeated_float=None)
+
+ self.assertEqual([1, 2, 3, 4], list(proto.repeated_int32))
+ self.assertEqual([1.23, 54.321], list(proto.repeated_double))
+ self.assertEqual([True, False, False], list(proto.repeated_bool))
+ self.assertEqual(["optional_string"], list(proto.repeated_string))
+ self.assertEqual([], list(proto.repeated_float))
+
+ def testRepeatedCompositeConstructor(self):
+ # Constructor with only repeated composite types should succeed.
+ proto = unittest_pb2.TestAllTypes(
+ repeated_nested_message=[
+ unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.FOO),
+ unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.BAR)],
+ repeated_foreign_message=[
+ unittest_pb2.ForeignMessage(c=-43),
+ unittest_pb2.ForeignMessage(c=45324),
+ unittest_pb2.ForeignMessage(c=12)],
+ repeatedgroup=[
+ unittest_pb2.TestAllTypes.RepeatedGroup(),
+ unittest_pb2.TestAllTypes.RepeatedGroup(a=1),
+ unittest_pb2.TestAllTypes.RepeatedGroup(a=2)])
+
+ self.assertEqual(
+ [unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.FOO),
+ unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.BAR)],
+ list(proto.repeated_nested_message))
+ self.assertEqual(
+ [unittest_pb2.ForeignMessage(c=-43),
+ unittest_pb2.ForeignMessage(c=45324),
+ unittest_pb2.ForeignMessage(c=12)],
+ list(proto.repeated_foreign_message))
+ self.assertEqual(
+ [unittest_pb2.TestAllTypes.RepeatedGroup(),
+ unittest_pb2.TestAllTypes.RepeatedGroup(a=1),
+ unittest_pb2.TestAllTypes.RepeatedGroup(a=2)],
+ list(proto.repeatedgroup))
+
+ def testMixedConstructor(self):
+ # Constructor with only mixed types should succeed.
+ proto = unittest_pb2.TestAllTypes(
+ optional_int32=24,
+ optional_string='optional_string',
+ repeated_double=[1.23, 54.321],
+ repeated_bool=[True, False, False],
+ repeated_nested_message=[
+ unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.FOO),
+ unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.BAR)],
+ repeated_foreign_message=[
+ unittest_pb2.ForeignMessage(c=-43),
+ unittest_pb2.ForeignMessage(c=45324),
+ unittest_pb2.ForeignMessage(c=12)],
+ optional_nested_message=None)
+
+ self.assertEqual(24, proto.optional_int32)
+ self.assertEqual('optional_string', proto.optional_string)
+ self.assertEqual([1.23, 54.321], list(proto.repeated_double))
+ self.assertEqual([True, False, False], list(proto.repeated_bool))
+ self.assertEqual(
+ [unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.FOO),
+ unittest_pb2.TestAllTypes.NestedMessage(
+ bb=unittest_pb2.TestAllTypes.BAR)],
+ list(proto.repeated_nested_message))
+ self.assertEqual(
+ [unittest_pb2.ForeignMessage(c=-43),
+ unittest_pb2.ForeignMessage(c=45324),
+ unittest_pb2.ForeignMessage(c=12)],
+ list(proto.repeated_foreign_message))
+ self.assertFalse(proto.HasField("optional_nested_message"))
+
+ def testConstructorTypeError(self):
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, optional_int32="foo")
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, optional_string=1234)
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, optional_nested_message=1234)
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, repeated_int32=1234)
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, repeated_int32=["foo"])
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, repeated_string=1234)
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, repeated_string=[1234])
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, repeated_nested_message=1234)
+ self.assertRaises(
+ TypeError, unittest_pb2.TestAllTypes, repeated_nested_message=[1234])
+
+ def testConstructorInvalidatesCachedByteSize(self):
+ message = unittest_pb2.TestAllTypes(optional_int32 = 12)
+ self.assertEqual(2, message.ByteSize())
+
+ message = unittest_pb2.TestAllTypes(
+ optional_nested_message = unittest_pb2.TestAllTypes.NestedMessage())
+ self.assertEqual(3, message.ByteSize())
+
+ message = unittest_pb2.TestAllTypes(repeated_int32 = [12])
+ self.assertEqual(3, message.ByteSize())
+
+ message = unittest_pb2.TestAllTypes(
+ repeated_nested_message = [unittest_pb2.TestAllTypes.NestedMessage()])
+ self.assertEqual(3, message.ByteSize())
+
+ def testSimpleHasBits(self):
+ # Test a scalar.
+ proto = unittest_pb2.TestAllTypes()
+ self.assertTrue(not proto.HasField('optional_int32'))
+ self.assertEqual(0, proto.optional_int32)
+ # HasField() shouldn't be true if all we've done is
+ # read the default value.
+ self.assertTrue(not proto.HasField('optional_int32'))
+ proto.optional_int32 = 1
+ # Setting a value however *should* set the "has" bit.
+ self.assertTrue(proto.HasField('optional_int32'))
+ proto.ClearField('optional_int32')
+ # And clearing that value should unset the "has" bit.
+ self.assertTrue(not proto.HasField('optional_int32'))
+
+ def testHasBitsWithSinglyNestedScalar(self):
+ # Helper used to test foreign messages and groups.
+ #
+ # composite_field_name should be the name of a non-repeated
+ # composite (i.e., foreign or group) field in TestAllTypes,
+ # and scalar_field_name should be the name of an integer-valued
+ # scalar field within that composite.
+ #
+ # I never thought I'd miss C++ macros and templates so much. :(
+ # This helper is semantically just:
+ #
+ # assert proto.composite_field.scalar_field == 0
+ # assert not proto.composite_field.HasField('scalar_field')
+ # assert not proto.HasField('composite_field')
+ #
+ # proto.composite_field.scalar_field = 10
+ # old_composite_field = proto.composite_field
+ #
+ # assert proto.composite_field.scalar_field == 10
+ # assert proto.composite_field.HasField('scalar_field')
+ # assert proto.HasField('composite_field')
+ #
+ # proto.ClearField('composite_field')
+ #
+ # assert not proto.composite_field.HasField('scalar_field')
+ # assert not proto.HasField('composite_field')
+ # assert proto.composite_field.scalar_field == 0
+ #
+ # # Now ensure that ClearField('composite_field') disconnected
+ # # the old field object from the object tree...
+ # assert old_composite_field is not proto.composite_field
+ # old_composite_field.scalar_field = 20
+ # assert not proto.composite_field.HasField('scalar_field')
+ # assert not proto.HasField('composite_field')
+ def TestCompositeHasBits(composite_field_name, scalar_field_name):
+ proto = unittest_pb2.TestAllTypes()
+ # First, check that we can get the scalar value, and see that it's the
+ # default (0), but that proto.HasField('omposite') and
+ # proto.composite.HasField('scalar') will still return False.
+ composite_field = getattr(proto, composite_field_name)
+ original_scalar_value = getattr(composite_field, scalar_field_name)
+ self.assertEqual(0, original_scalar_value)
+ # Assert that the composite object does not "have" the scalar.
+ self.assertTrue(not composite_field.HasField(scalar_field_name))
+ # Assert that proto does not "have" the composite field.
+ self.assertTrue(not proto.HasField(composite_field_name))
+
+ # Now set the scalar within the composite field. Ensure that the setting
+ # is reflected, and that proto.HasField('composite') and
+ # proto.composite.HasField('scalar') now both return True.
+ new_val = 20
+ setattr(composite_field, scalar_field_name, new_val)
+ self.assertEqual(new_val, getattr(composite_field, scalar_field_name))
+ # Hold on to a reference to the current composite_field object.
+ old_composite_field = composite_field
+ # Assert that the has methods now return true.
+ self.assertTrue(composite_field.HasField(scalar_field_name))
+ self.assertTrue(proto.HasField(composite_field_name))
+
+ # Now call the clear method...
+ proto.ClearField(composite_field_name)
+
+ # ...and ensure that the "has" bits are all back to False...
+ composite_field = getattr(proto, composite_field_name)
+ self.assertTrue(not composite_field.HasField(scalar_field_name))
+ self.assertTrue(not proto.HasField(composite_field_name))
+ # ...and ensure that the scalar field has returned to its default.
+ self.assertEqual(0, getattr(composite_field, scalar_field_name))
+
+ self.assertTrue(old_composite_field is not composite_field)
+ setattr(old_composite_field, scalar_field_name, new_val)
+ self.assertTrue(not composite_field.HasField(scalar_field_name))
+ self.assertTrue(not proto.HasField(composite_field_name))
+ self.assertEqual(0, getattr(composite_field, scalar_field_name))
+
+ # Test simple, single-level nesting when we set a scalar.
+ TestCompositeHasBits('optionalgroup', 'a')
+ TestCompositeHasBits('optional_nested_message', 'bb')
+ TestCompositeHasBits('optional_foreign_message', 'c')
+ TestCompositeHasBits('optional_import_message', 'd')
+
+ def testReferencesToNestedMessage(self):
+ proto = unittest_pb2.TestAllTypes()
+ nested = proto.optional_nested_message
+ del proto
+ # A previous version had a bug where this would raise an exception when
+ # hitting a now-dead weak reference.
+ nested.bb = 23
+
+ def testDisconnectingNestedMessageBeforeSettingField(self):
+ proto = unittest_pb2.TestAllTypes()
+ nested = proto.optional_nested_message
+ proto.ClearField('optional_nested_message') # Should disconnect from parent
+ self.assertTrue(nested is not proto.optional_nested_message)
+ nested.bb = 23
+ self.assertTrue(not proto.HasField('optional_nested_message'))
+ self.assertEqual(0, proto.optional_nested_message.bb)
+
+ def testGetDefaultMessageAfterDisconnectingDefaultMessage(self):
+ proto = unittest_pb2.TestAllTypes()
+ nested = proto.optional_nested_message
+ proto.ClearField('optional_nested_message')
+ del proto
+ del nested
+ # Force a garbage collect so that the underlying CMessages are freed along
+ # with the Messages they point to. This is to make sure we're not deleting
+ # default message instances.
+ gc.collect()
+ proto = unittest_pb2.TestAllTypes()
+ nested = proto.optional_nested_message
+
+ def testDisconnectingNestedMessageAfterSettingField(self):
+ proto = unittest_pb2.TestAllTypes()
+ nested = proto.optional_nested_message
+ nested.bb = 5
+ self.assertTrue(proto.HasField('optional_nested_message'))
+ proto.ClearField('optional_nested_message') # Should disconnect from parent
+ self.assertEqual(5, nested.bb)
+ self.assertEqual(0, proto.optional_nested_message.bb)
+ self.assertTrue(nested is not proto.optional_nested_message)
+ nested.bb = 23
+ self.assertTrue(not proto.HasField('optional_nested_message'))
+ self.assertEqual(0, proto.optional_nested_message.bb)
+
+ def testDisconnectingNestedMessageBeforeGettingField(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertTrue(not proto.HasField('optional_nested_message'))
+ proto.ClearField('optional_nested_message')
+ self.assertTrue(not proto.HasField('optional_nested_message'))
+
+ def testDisconnectingNestedMessageAfterMerge(self):
+ # This test exercises the code path that does not use ReleaseMessage().
+ # The underlying fear is that if we use ReleaseMessage() incorrectly,
+ # we will have memory leaks. It's hard to check that that doesn't happen,
+ # but at least we can exercise that code path to make sure it works.
+ proto1 = unittest_pb2.TestAllTypes()
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.optional_nested_message.bb = 5
+ proto1.MergeFrom(proto2)
+ self.assertTrue(proto1.HasField('optional_nested_message'))
+ proto1.ClearField('optional_nested_message')
+ self.assertTrue(not proto1.HasField('optional_nested_message'))
+
+ def testDisconnectingLazyNestedMessage(self):
+ # This test exercises releasing a nested message that is lazy. This test
+ # only exercises real code in the C++ implementation as Python does not
+ # support lazy parsing, but the current C++ implementation results in
+ # memory corruption and a crash.
+ if api_implementation.Type() != 'python':
+ return
+ proto = unittest_pb2.TestAllTypes()
+ proto.optional_lazy_message.bb = 5
+ proto.ClearField('optional_lazy_message')
+ del proto
+ gc.collect()
+
+ def testHasBitsWhenModifyingRepeatedFields(self):
+ # Test nesting when we add an element to a repeated field in a submessage.
+ proto = unittest_pb2.TestNestedMessageHasBits()
+ proto.optional_nested_message.nestedmessage_repeated_int32.append(5)
+ self.assertEqual(
+ [5], proto.optional_nested_message.nestedmessage_repeated_int32)
+ self.assertTrue(proto.HasField('optional_nested_message'))
+
+ # Do the same test, but with a repeated composite field within the
+ # submessage.
+ proto.ClearField('optional_nested_message')
+ self.assertTrue(not proto.HasField('optional_nested_message'))
+ proto.optional_nested_message.nestedmessage_repeated_foreignmessage.add()
+ self.assertTrue(proto.HasField('optional_nested_message'))
+
+ def testHasBitsForManyLevelsOfNesting(self):
+ # Test nesting many levels deep.
+ recursive_proto = unittest_pb2.TestMutualRecursionA()
+ self.assertTrue(not recursive_proto.HasField('bb'))
+ self.assertEqual(0, recursive_proto.bb.a.bb.a.bb.optional_int32)
+ self.assertTrue(not recursive_proto.HasField('bb'))
+ recursive_proto.bb.a.bb.a.bb.optional_int32 = 5
+ self.assertEqual(5, recursive_proto.bb.a.bb.a.bb.optional_int32)
+ self.assertTrue(recursive_proto.HasField('bb'))
+ self.assertTrue(recursive_proto.bb.HasField('a'))
+ self.assertTrue(recursive_proto.bb.a.HasField('bb'))
+ self.assertTrue(recursive_proto.bb.a.bb.HasField('a'))
+ self.assertTrue(recursive_proto.bb.a.bb.a.HasField('bb'))
+ self.assertTrue(not recursive_proto.bb.a.bb.a.bb.HasField('a'))
+ self.assertTrue(recursive_proto.bb.a.bb.a.bb.HasField('optional_int32'))
+
+ def testSingularListFields(self):
+ proto = unittest_pb2.TestAllTypes()
+ proto.optional_fixed32 = 1
+ proto.optional_int32 = 5
+ proto.optional_string = 'foo'
+ # Access sub-message but don't set it yet.
+ nested_message = proto.optional_nested_message
+ self.assertEqual(
+ [ (proto.DESCRIPTOR.fields_by_name['optional_int32' ], 5),
+ (proto.DESCRIPTOR.fields_by_name['optional_fixed32'], 1),
+ (proto.DESCRIPTOR.fields_by_name['optional_string' ], 'foo') ],
+ proto.ListFields())
+
+ proto.optional_nested_message.bb = 123
+ self.assertEqual(
+ [ (proto.DESCRIPTOR.fields_by_name['optional_int32' ], 5),
+ (proto.DESCRIPTOR.fields_by_name['optional_fixed32'], 1),
+ (proto.DESCRIPTOR.fields_by_name['optional_string' ], 'foo'),
+ (proto.DESCRIPTOR.fields_by_name['optional_nested_message' ],
+ nested_message) ],
+ proto.ListFields())
+
+ def testRepeatedListFields(self):
+ proto = unittest_pb2.TestAllTypes()
+ proto.repeated_fixed32.append(1)
+ proto.repeated_int32.append(5)
+ proto.repeated_int32.append(11)
+ proto.repeated_string.extend(['foo', 'bar'])
+ proto.repeated_string.extend([])
+ proto.repeated_string.append('baz')
+ proto.repeated_string.extend(str(x) for x in range(2))
+ proto.optional_int32 = 21
+ proto.repeated_bool # Access but don't set anything; should not be listed.
+ self.assertEqual(
+ [ (proto.DESCRIPTOR.fields_by_name['optional_int32' ], 21),
+ (proto.DESCRIPTOR.fields_by_name['repeated_int32' ], [5, 11]),
+ (proto.DESCRIPTOR.fields_by_name['repeated_fixed32'], [1]),
+ (proto.DESCRIPTOR.fields_by_name['repeated_string' ],
+ ['foo', 'bar', 'baz', '0', '1']) ],
+ proto.ListFields())
+
+ def testSingularListExtensions(self):
+ proto = unittest_pb2.TestAllExtensions()
+ proto.Extensions[unittest_pb2.optional_fixed32_extension] = 1
+ proto.Extensions[unittest_pb2.optional_int32_extension ] = 5
+ proto.Extensions[unittest_pb2.optional_string_extension ] = 'foo'
+ self.assertEqual(
+ [ (unittest_pb2.optional_int32_extension , 5),
+ (unittest_pb2.optional_fixed32_extension, 1),
+ (unittest_pb2.optional_string_extension , 'foo') ],
+ proto.ListFields())
+
+ def testRepeatedListExtensions(self):
+ proto = unittest_pb2.TestAllExtensions()
+ proto.Extensions[unittest_pb2.repeated_fixed32_extension].append(1)
+ proto.Extensions[unittest_pb2.repeated_int32_extension ].append(5)
+ proto.Extensions[unittest_pb2.repeated_int32_extension ].append(11)
+ proto.Extensions[unittest_pb2.repeated_string_extension ].append('foo')
+ proto.Extensions[unittest_pb2.repeated_string_extension ].append('bar')
+ proto.Extensions[unittest_pb2.repeated_string_extension ].append('baz')
+ proto.Extensions[unittest_pb2.optional_int32_extension ] = 21
+ self.assertEqual(
+ [ (unittest_pb2.optional_int32_extension , 21),
+ (unittest_pb2.repeated_int32_extension , [5, 11]),
+ (unittest_pb2.repeated_fixed32_extension, [1]),
+ (unittest_pb2.repeated_string_extension , ['foo', 'bar', 'baz']) ],
+ proto.ListFields())
+
+ def testListFieldsAndExtensions(self):
+ proto = unittest_pb2.TestFieldOrderings()
+ test_util.SetAllFieldsAndExtensions(proto)
+ unittest_pb2.my_extension_int
+ self.assertEqual(
+ [ (proto.DESCRIPTOR.fields_by_name['my_int' ], 1),
+ (unittest_pb2.my_extension_int , 23),
+ (proto.DESCRIPTOR.fields_by_name['my_string'], 'foo'),
+ (unittest_pb2.my_extension_string , 'bar'),
+ (proto.DESCRIPTOR.fields_by_name['my_float' ], 1.0) ],
+ proto.ListFields())
+
+ def testDefaultValues(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(0, proto.optional_int32)
+ self.assertEqual(0, proto.optional_int64)
+ self.assertEqual(0, proto.optional_uint32)
+ self.assertEqual(0, proto.optional_uint64)
+ self.assertEqual(0, proto.optional_sint32)
+ self.assertEqual(0, proto.optional_sint64)
+ self.assertEqual(0, proto.optional_fixed32)
+ self.assertEqual(0, proto.optional_fixed64)
+ self.assertEqual(0, proto.optional_sfixed32)
+ self.assertEqual(0, proto.optional_sfixed64)
+ self.assertEqual(0.0, proto.optional_float)
+ self.assertEqual(0.0, proto.optional_double)
+ self.assertEqual(False, proto.optional_bool)
+ self.assertEqual('', proto.optional_string)
+ self.assertEqual(b'', proto.optional_bytes)
+
+ self.assertEqual(41, proto.default_int32)
+ self.assertEqual(42, proto.default_int64)
+ self.assertEqual(43, proto.default_uint32)
+ self.assertEqual(44, proto.default_uint64)
+ self.assertEqual(-45, proto.default_sint32)
+ self.assertEqual(46, proto.default_sint64)
+ self.assertEqual(47, proto.default_fixed32)
+ self.assertEqual(48, proto.default_fixed64)
+ self.assertEqual(49, proto.default_sfixed32)
+ self.assertEqual(-50, proto.default_sfixed64)
+ self.assertEqual(51.5, proto.default_float)
+ self.assertEqual(52e3, proto.default_double)
+ self.assertEqual(True, proto.default_bool)
+ self.assertEqual('hello', proto.default_string)
+ self.assertEqual(b'world', proto.default_bytes)
+ self.assertEqual(unittest_pb2.TestAllTypes.BAR, proto.default_nested_enum)
+ self.assertEqual(unittest_pb2.FOREIGN_BAR, proto.default_foreign_enum)
+ self.assertEqual(unittest_import_pb2.IMPORT_BAR,
+ proto.default_import_enum)
+
+ proto = unittest_pb2.TestExtremeDefaultValues()
+ self.assertEqual(u'\u1234', proto.utf8_string)
+
+ def testHasFieldWithUnknownFieldName(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertRaises(ValueError, proto.HasField, 'nonexistent_field')
+
+ def testClearFieldWithUnknownFieldName(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertRaises(ValueError, proto.ClearField, 'nonexistent_field')
+
+ def testClearRemovesChildren(self):
+ # Make sure there aren't any implementation bugs that are only partially
+ # clearing the message (which can happen in the more complex C++
+ # implementation which has parallel message lists).
+ proto = unittest_pb2.TestRequiredForeign()
+ for i in range(10):
+ proto.repeated_message.add()
+ proto2 = unittest_pb2.TestRequiredForeign()
+ proto.CopyFrom(proto2)
+ self.assertRaises(IndexError, lambda: proto.repeated_message[5])
+
+ def testDisallowedAssignments(self):
+ # It's illegal to assign values directly to repeated fields
+ # or to nonrepeated composite fields. Ensure that this fails.
+ proto = unittest_pb2.TestAllTypes()
+ # Repeated fields.
+ self.assertRaises(AttributeError, setattr, proto, 'repeated_int32', 10)
+ # Lists shouldn't work, either.
+ self.assertRaises(AttributeError, setattr, proto, 'repeated_int32', [10])
+ # Composite fields.
+ self.assertRaises(AttributeError, setattr, proto,
+ 'optional_nested_message', 23)
+ # Assignment to a repeated nested message field without specifying
+ # the index in the array of nested messages.
+ self.assertRaises(AttributeError, setattr, proto.repeated_nested_message,
+ 'bb', 34)
+ # Assignment to an attribute of a repeated field.
+ self.assertRaises(AttributeError, setattr, proto.repeated_float,
+ 'some_attribute', 34)
+ # proto.nonexistent_field = 23 should fail as well.
+ self.assertRaises(AttributeError, setattr, proto, 'nonexistent_field', 23)
+
+ def testSingleScalarTypeSafety(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertRaises(TypeError, setattr, proto, 'optional_int32', 1.1)
+ self.assertRaises(TypeError, setattr, proto, 'optional_int32', 'foo')
+ self.assertRaises(TypeError, setattr, proto, 'optional_string', 10)
+ self.assertRaises(TypeError, setattr, proto, 'optional_bytes', 10)
+
+ def testIntegerTypes(self):
+ def TestGetAndDeserialize(field_name, value, expected_type):
+ proto = unittest_pb2.TestAllTypes()
+ setattr(proto, field_name, value)
+ self.assertIsInstance(getattr(proto, field_name), expected_type)
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.ParseFromString(proto.SerializeToString())
+ self.assertIsInstance(getattr(proto2, field_name), expected_type)
+
+ TestGetAndDeserialize('optional_int32', 1, int)
+ TestGetAndDeserialize('optional_int32', 1 << 30, int)
+ TestGetAndDeserialize('optional_uint32', 1 << 30, int)
+ try:
+ integer_64 = long
+ except NameError: # Python3
+ integer_64 = int
+ if struct.calcsize('L') == 4:
+ # Python only has signed ints, so 32-bit python can't fit an uint32
+ # in an int.
+ TestGetAndDeserialize('optional_uint32', 1 << 31, long)
+ else:
+ # 64-bit python can fit uint32 inside an int
+ TestGetAndDeserialize('optional_uint32', 1 << 31, int)
+ TestGetAndDeserialize('optional_int64', 1 << 30, integer_64)
+ TestGetAndDeserialize('optional_int64', 1 << 60, integer_64)
+ TestGetAndDeserialize('optional_uint64', 1 << 30, integer_64)
+ TestGetAndDeserialize('optional_uint64', 1 << 60, integer_64)
+
+ def testSingleScalarBoundsChecking(self):
+ def TestMinAndMaxIntegers(field_name, expected_min, expected_max):
+ pb = unittest_pb2.TestAllTypes()
+ setattr(pb, field_name, expected_min)
+ self.assertEqual(expected_min, getattr(pb, field_name))
+ setattr(pb, field_name, expected_max)
+ self.assertEqual(expected_max, getattr(pb, field_name))
+ self.assertRaises(ValueError, setattr, pb, field_name, expected_min - 1)
+ self.assertRaises(ValueError, setattr, pb, field_name, expected_max + 1)
+
+ TestMinAndMaxIntegers('optional_int32', -(1 << 31), (1 << 31) - 1)
+ TestMinAndMaxIntegers('optional_uint32', 0, 0xffffffff)
+ TestMinAndMaxIntegers('optional_int64', -(1 << 63), (1 << 63) - 1)
+ TestMinAndMaxIntegers('optional_uint64', 0, 0xffffffffffffffff)
+
+ pb = unittest_pb2.TestAllTypes()
+ pb.optional_nested_enum = 1
+ self.assertEqual(1, pb.optional_nested_enum)
+
+ def testRepeatedScalarTypeSafety(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertRaises(TypeError, proto.repeated_int32.append, 1.1)
+ self.assertRaises(TypeError, proto.repeated_int32.append, 'foo')
+ self.assertRaises(TypeError, proto.repeated_string, 10)
+ self.assertRaises(TypeError, proto.repeated_bytes, 10)
+
+ proto.repeated_int32.append(10)
+ proto.repeated_int32[0] = 23
+ self.assertRaises(IndexError, proto.repeated_int32.__setitem__, 500, 23)
+ self.assertRaises(TypeError, proto.repeated_int32.__setitem__, 0, 'abc')
+
+ # Repeated enums tests.
+ #proto.repeated_nested_enum.append(0)
+
+ def testSingleScalarGettersAndSetters(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(0, proto.optional_int32)
+ proto.optional_int32 = 1
+ self.assertEqual(1, proto.optional_int32)
+
+ proto.optional_uint64 = 0xffffffffffff
+ self.assertEqual(0xffffffffffff, proto.optional_uint64)
+ proto.optional_uint64 = 0xffffffffffffffff
+ self.assertEqual(0xffffffffffffffff, proto.optional_uint64)
+ # TODO(robinson): Test all other scalar field types.
+
+ def testSingleScalarClearField(self):
+ proto = unittest_pb2.TestAllTypes()
+ # Should be allowed to clear something that's not there (a no-op).
+ proto.ClearField('optional_int32')
+ proto.optional_int32 = 1
+ self.assertTrue(proto.HasField('optional_int32'))
+ proto.ClearField('optional_int32')
+ self.assertEqual(0, proto.optional_int32)
+ self.assertTrue(not proto.HasField('optional_int32'))
+ # TODO(robinson): Test all other scalar field types.
+
+ def testEnums(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(1, proto.FOO)
+ self.assertEqual(1, unittest_pb2.TestAllTypes.FOO)
+ self.assertEqual(2, proto.BAR)
+ self.assertEqual(2, unittest_pb2.TestAllTypes.BAR)
+ self.assertEqual(3, proto.BAZ)
+ self.assertEqual(3, unittest_pb2.TestAllTypes.BAZ)
+
+ def testEnum_Name(self):
+ self.assertEqual('FOREIGN_FOO',
+ unittest_pb2.ForeignEnum.Name(unittest_pb2.FOREIGN_FOO))
+ self.assertEqual('FOREIGN_BAR',
+ unittest_pb2.ForeignEnum.Name(unittest_pb2.FOREIGN_BAR))
+ self.assertEqual('FOREIGN_BAZ',
+ unittest_pb2.ForeignEnum.Name(unittest_pb2.FOREIGN_BAZ))
+ self.assertRaises(ValueError,
+ unittest_pb2.ForeignEnum.Name, 11312)
+
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual('FOO',
+ proto.NestedEnum.Name(proto.FOO))
+ self.assertEqual('FOO',
+ unittest_pb2.TestAllTypes.NestedEnum.Name(proto.FOO))
+ self.assertEqual('BAR',
+ proto.NestedEnum.Name(proto.BAR))
+ self.assertEqual('BAR',
+ unittest_pb2.TestAllTypes.NestedEnum.Name(proto.BAR))
+ self.assertEqual('BAZ',
+ proto.NestedEnum.Name(proto.BAZ))
+ self.assertEqual('BAZ',
+ unittest_pb2.TestAllTypes.NestedEnum.Name(proto.BAZ))
+ self.assertRaises(ValueError,
+ proto.NestedEnum.Name, 11312)
+ self.assertRaises(ValueError,
+ unittest_pb2.TestAllTypes.NestedEnum.Name, 11312)
+
+ def testEnum_Value(self):
+ self.assertEqual(unittest_pb2.FOREIGN_FOO,
+ unittest_pb2.ForeignEnum.Value('FOREIGN_FOO'))
+ self.assertEqual(unittest_pb2.FOREIGN_BAR,
+ unittest_pb2.ForeignEnum.Value('FOREIGN_BAR'))
+ self.assertEqual(unittest_pb2.FOREIGN_BAZ,
+ unittest_pb2.ForeignEnum.Value('FOREIGN_BAZ'))
+ self.assertRaises(ValueError,
+ unittest_pb2.ForeignEnum.Value, 'FO')
+
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(proto.FOO,
+ proto.NestedEnum.Value('FOO'))
+ self.assertEqual(proto.FOO,
+ unittest_pb2.TestAllTypes.NestedEnum.Value('FOO'))
+ self.assertEqual(proto.BAR,
+ proto.NestedEnum.Value('BAR'))
+ self.assertEqual(proto.BAR,
+ unittest_pb2.TestAllTypes.NestedEnum.Value('BAR'))
+ self.assertEqual(proto.BAZ,
+ proto.NestedEnum.Value('BAZ'))
+ self.assertEqual(proto.BAZ,
+ unittest_pb2.TestAllTypes.NestedEnum.Value('BAZ'))
+ self.assertRaises(ValueError,
+ proto.NestedEnum.Value, 'Foo')
+ self.assertRaises(ValueError,
+ unittest_pb2.TestAllTypes.NestedEnum.Value, 'Foo')
+
+ def testEnum_KeysAndValues(self):
+ self.assertEqual(['FOREIGN_FOO', 'FOREIGN_BAR', 'FOREIGN_BAZ'],
+ list(unittest_pb2.ForeignEnum.keys()))
+ self.assertEqual([4, 5, 6],
+ list(unittest_pb2.ForeignEnum.values()))
+ self.assertEqual([('FOREIGN_FOO', 4), ('FOREIGN_BAR', 5),
+ ('FOREIGN_BAZ', 6)],
+ list(unittest_pb2.ForeignEnum.items()))
+
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(['FOO', 'BAR', 'BAZ', 'NEG'], list(proto.NestedEnum.keys()))
+ self.assertEqual([1, 2, 3, -1], list(proto.NestedEnum.values()))
+ self.assertEqual([('FOO', 1), ('BAR', 2), ('BAZ', 3), ('NEG', -1)],
+ list(proto.NestedEnum.items()))
+
+ def testRepeatedScalars(self):
+ proto = unittest_pb2.TestAllTypes()
+
+ self.assertTrue(not proto.repeated_int32)
+ self.assertEqual(0, len(proto.repeated_int32))
+ proto.repeated_int32.append(5)
+ proto.repeated_int32.append(10)
+ proto.repeated_int32.append(15)
+ self.assertTrue(proto.repeated_int32)
+ self.assertEqual(3, len(proto.repeated_int32))
+
+ self.assertEqual([5, 10, 15], proto.repeated_int32)
+
+ # Test single retrieval.
+ self.assertEqual(5, proto.repeated_int32[0])
+ self.assertEqual(15, proto.repeated_int32[-1])
+ # Test out-of-bounds indices.
+ self.assertRaises(IndexError, proto.repeated_int32.__getitem__, 1234)
+ self.assertRaises(IndexError, proto.repeated_int32.__getitem__, -1234)
+ # Test incorrect types passed to __getitem__.
+ self.assertRaises(TypeError, proto.repeated_int32.__getitem__, 'foo')
+ self.assertRaises(TypeError, proto.repeated_int32.__getitem__, None)
+
+ # Test single assignment.
+ proto.repeated_int32[1] = 20
+ self.assertEqual([5, 20, 15], proto.repeated_int32)
+
+ # Test insertion.
+ proto.repeated_int32.insert(1, 25)
+ self.assertEqual([5, 25, 20, 15], proto.repeated_int32)
+
+ # Test slice retrieval.
+ proto.repeated_int32.append(30)
+ self.assertEqual([25, 20, 15], proto.repeated_int32[1:4])
+ self.assertEqual([5, 25, 20, 15, 30], proto.repeated_int32[:])
+
+ # Test slice assignment with an iterator
+ proto.repeated_int32[1:4] = (i for i in range(3))
+ self.assertEqual([5, 0, 1, 2, 30], proto.repeated_int32)
+
+ # Test slice assignment.
+ proto.repeated_int32[1:4] = [35, 40, 45]
+ self.assertEqual([5, 35, 40, 45, 30], proto.repeated_int32)
+
+ # Test that we can use the field as an iterator.
+ result = []
+ for i in proto.repeated_int32:
+ result.append(i)
+ self.assertEqual([5, 35, 40, 45, 30], result)
+
+ # Test single deletion.
+ del proto.repeated_int32[2]
+ self.assertEqual([5, 35, 45, 30], proto.repeated_int32)
+
+ # Test slice deletion.
+ del proto.repeated_int32[2:]
+ self.assertEqual([5, 35], proto.repeated_int32)
+
+ # Test extending.
+ proto.repeated_int32.extend([3, 13])
+ self.assertEqual([5, 35, 3, 13], proto.repeated_int32)
+
+ # Test clearing.
+ proto.ClearField('repeated_int32')
+ self.assertTrue(not proto.repeated_int32)
+ self.assertEqual(0, len(proto.repeated_int32))
+
+ proto.repeated_int32.append(1)
+ self.assertEqual(1, proto.repeated_int32[-1])
+ # Test assignment to a negative index.
+ proto.repeated_int32[-1] = 2
+ self.assertEqual(2, proto.repeated_int32[-1])
+
+ # Test deletion at negative indices.
+ proto.repeated_int32[:] = [0, 1, 2, 3]
+ del proto.repeated_int32[-1]
+ self.assertEqual([0, 1, 2], proto.repeated_int32)
+
+ del proto.repeated_int32[-2]
+ self.assertEqual([0, 2], proto.repeated_int32)
+
+ self.assertRaises(IndexError, proto.repeated_int32.__delitem__, -3)
+ self.assertRaises(IndexError, proto.repeated_int32.__delitem__, 300)
+
+ del proto.repeated_int32[-2:-1]
+ self.assertEqual([2], proto.repeated_int32)
+
+ del proto.repeated_int32[100:10000]
+ self.assertEqual([2], proto.repeated_int32)
+
+ def testRepeatedScalarsRemove(self):
+ proto = unittest_pb2.TestAllTypes()
+
+ self.assertTrue(not proto.repeated_int32)
+ self.assertEqual(0, len(proto.repeated_int32))
+ proto.repeated_int32.append(5)
+ proto.repeated_int32.append(10)
+ proto.repeated_int32.append(5)
+ proto.repeated_int32.append(5)
+
+ self.assertEqual(4, len(proto.repeated_int32))
+ proto.repeated_int32.remove(5)
+ self.assertEqual(3, len(proto.repeated_int32))
+ self.assertEqual(10, proto.repeated_int32[0])
+ self.assertEqual(5, proto.repeated_int32[1])
+ self.assertEqual(5, proto.repeated_int32[2])
+
+ proto.repeated_int32.remove(5)
+ self.assertEqual(2, len(proto.repeated_int32))
+ self.assertEqual(10, proto.repeated_int32[0])
+ self.assertEqual(5, proto.repeated_int32[1])
+
+ proto.repeated_int32.remove(10)
+ self.assertEqual(1, len(proto.repeated_int32))
+ self.assertEqual(5, proto.repeated_int32[0])
+
+ # Remove a non-existent element.
+ self.assertRaises(ValueError, proto.repeated_int32.remove, 123)
+
+ def testRepeatedComposites(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertTrue(not proto.repeated_nested_message)
+ self.assertEqual(0, len(proto.repeated_nested_message))
+ m0 = proto.repeated_nested_message.add()
+ m1 = proto.repeated_nested_message.add()
+ self.assertTrue(proto.repeated_nested_message)
+ self.assertEqual(2, len(proto.repeated_nested_message))
+ self.assertListsEqual([m0, m1], proto.repeated_nested_message)
+ self.assertIsInstance(m0, unittest_pb2.TestAllTypes.NestedMessage)
+
+ # Test out-of-bounds indices.
+ self.assertRaises(IndexError, proto.repeated_nested_message.__getitem__,
+ 1234)
+ self.assertRaises(IndexError, proto.repeated_nested_message.__getitem__,
+ -1234)
+
+ # Test incorrect types passed to __getitem__.
+ self.assertRaises(TypeError, proto.repeated_nested_message.__getitem__,
+ 'foo')
+ self.assertRaises(TypeError, proto.repeated_nested_message.__getitem__,
+ None)
+
+ # Test slice retrieval.
+ m2 = proto.repeated_nested_message.add()
+ m3 = proto.repeated_nested_message.add()
+ m4 = proto.repeated_nested_message.add()
+ self.assertListsEqual(
+ [m1, m2, m3], proto.repeated_nested_message[1:4])
+ self.assertListsEqual(
+ [m0, m1, m2, m3, m4], proto.repeated_nested_message[:])
+ self.assertListsEqual(
+ [m0, m1], proto.repeated_nested_message[:2])
+ self.assertListsEqual(
+ [m2, m3, m4], proto.repeated_nested_message[2:])
+ self.assertEqual(
+ m0, proto.repeated_nested_message[0])
+ self.assertListsEqual(
+ [m0], proto.repeated_nested_message[:1])
+
+ # Test that we can use the field as an iterator.
+ result = []
+ for i in proto.repeated_nested_message:
+ result.append(i)
+ self.assertListsEqual([m0, m1, m2, m3, m4], result)
+
+ # Test single deletion.
+ del proto.repeated_nested_message[2]
+ self.assertListsEqual([m0, m1, m3, m4], proto.repeated_nested_message)
+
+ # Test slice deletion.
+ del proto.repeated_nested_message[2:]
+ self.assertListsEqual([m0, m1], proto.repeated_nested_message)
+
+ # Test extending.
+ n1 = unittest_pb2.TestAllTypes.NestedMessage(bb=1)
+ n2 = unittest_pb2.TestAllTypes.NestedMessage(bb=2)
+ proto.repeated_nested_message.extend([n1,n2])
+ self.assertEqual(4, len(proto.repeated_nested_message))
+ self.assertEqual(n1, proto.repeated_nested_message[2])
+ self.assertEqual(n2, proto.repeated_nested_message[3])
+
+ # Test clearing.
+ proto.ClearField('repeated_nested_message')
+ self.assertTrue(not proto.repeated_nested_message)
+ self.assertEqual(0, len(proto.repeated_nested_message))
+
+ # Test constructing an element while adding it.
+ proto.repeated_nested_message.add(bb=23)
+ self.assertEqual(1, len(proto.repeated_nested_message))
+ self.assertEqual(23, proto.repeated_nested_message[0].bb)
+ self.assertRaises(TypeError, proto.repeated_nested_message.add, 23)
+
+ def testRepeatedCompositeRemove(self):
+ proto = unittest_pb2.TestAllTypes()
+
+ self.assertEqual(0, len(proto.repeated_nested_message))
+ m0 = proto.repeated_nested_message.add()
+ # Need to set some differentiating variable so m0 != m1 != m2:
+ m0.bb = len(proto.repeated_nested_message)
+ m1 = proto.repeated_nested_message.add()
+ m1.bb = len(proto.repeated_nested_message)
+ self.assertTrue(m0 != m1)
+ m2 = proto.repeated_nested_message.add()
+ m2.bb = len(proto.repeated_nested_message)
+ self.assertListsEqual([m0, m1, m2], proto.repeated_nested_message)
+
+ self.assertEqual(3, len(proto.repeated_nested_message))
+ proto.repeated_nested_message.remove(m0)
+ self.assertEqual(2, len(proto.repeated_nested_message))
+ self.assertEqual(m1, proto.repeated_nested_message[0])
+ self.assertEqual(m2, proto.repeated_nested_message[1])
+
+ # Removing m0 again or removing None should raise error
+ self.assertRaises(ValueError, proto.repeated_nested_message.remove, m0)
+ self.assertRaises(ValueError, proto.repeated_nested_message.remove, None)
+ self.assertEqual(2, len(proto.repeated_nested_message))
+
+ proto.repeated_nested_message.remove(m2)
+ self.assertEqual(1, len(proto.repeated_nested_message))
+ self.assertEqual(m1, proto.repeated_nested_message[0])
+
+ def testHandWrittenReflection(self):
+ # Hand written extensions are only supported by the pure-Python
+ # implementation of the API.
+ if api_implementation.Type() != 'python':
+ return
+
+ FieldDescriptor = descriptor.FieldDescriptor
+ foo_field_descriptor = FieldDescriptor(
+ name='foo_field', full_name='MyProto.foo_field',
+ index=0, number=1, type=FieldDescriptor.TYPE_INT64,
+ cpp_type=FieldDescriptor.CPPTYPE_INT64,
+ label=FieldDescriptor.LABEL_OPTIONAL, default_value=0,
+ containing_type=None, message_type=None, enum_type=None,
+ is_extension=False, extension_scope=None,
+ options=descriptor_pb2.FieldOptions())
+ mydescriptor = descriptor.Descriptor(
+ name='MyProto', full_name='MyProto', filename='ignored',
+ containing_type=None, nested_types=[], enum_types=[],
+ fields=[foo_field_descriptor], extensions=[],
+ options=descriptor_pb2.MessageOptions())
+ class MyProtoClass(six.with_metaclass(reflection.GeneratedProtocolMessageType, message.Message)):
+ DESCRIPTOR = mydescriptor
+ myproto_instance = MyProtoClass()
+ self.assertEqual(0, myproto_instance.foo_field)
+ self.assertTrue(not myproto_instance.HasField('foo_field'))
+ myproto_instance.foo_field = 23
+ self.assertEqual(23, myproto_instance.foo_field)
+ self.assertTrue(myproto_instance.HasField('foo_field'))
+
+ def testDescriptorProtoSupport(self):
+ # Hand written descriptors/reflection are only supported by the pure-Python
+ # implementation of the API.
+ if api_implementation.Type() != 'python':
+ return
+
+ def AddDescriptorField(proto, field_name, field_type):
+ AddDescriptorField.field_index += 1
+ new_field = proto.field.add()
+ new_field.name = field_name
+ new_field.type = field_type
+ new_field.number = AddDescriptorField.field_index
+ new_field.label = descriptor_pb2.FieldDescriptorProto.LABEL_OPTIONAL
+
+ AddDescriptorField.field_index = 0
+
+ desc_proto = descriptor_pb2.DescriptorProto()
+ desc_proto.name = 'Car'
+ fdp = descriptor_pb2.FieldDescriptorProto
+ AddDescriptorField(desc_proto, 'name', fdp.TYPE_STRING)
+ AddDescriptorField(desc_proto, 'year', fdp.TYPE_INT64)
+ AddDescriptorField(desc_proto, 'automatic', fdp.TYPE_BOOL)
+ AddDescriptorField(desc_proto, 'price', fdp.TYPE_DOUBLE)
+ # Add a repeated field
+ AddDescriptorField.field_index += 1
+ new_field = desc_proto.field.add()
+ new_field.name = 'owners'
+ new_field.type = fdp.TYPE_STRING
+ new_field.number = AddDescriptorField.field_index
+ new_field.label = descriptor_pb2.FieldDescriptorProto.LABEL_REPEATED
+
+ desc = descriptor.MakeDescriptor(desc_proto)
+ self.assertTrue('name' in desc.fields_by_name)
+ self.assertTrue('year' in desc.fields_by_name)
+ self.assertTrue('automatic' in desc.fields_by_name)
+ self.assertTrue('price' in desc.fields_by_name)
+ self.assertTrue('owners' in desc.fields_by_name)
+
+ class CarMessage(six.with_metaclass(reflection.GeneratedProtocolMessageType, message.Message)):
+ DESCRIPTOR = desc
+
+ prius = CarMessage()
+ prius.name = 'prius'
+ prius.year = 2010
+ prius.automatic = True
+ prius.price = 25134.75
+ prius.owners.extend(['bob', 'susan'])
+
+ serialized_prius = prius.SerializeToString()
+ new_prius = reflection.ParseMessage(desc, serialized_prius)
+ self.assertTrue(new_prius is not prius)
+ self.assertEqual(prius, new_prius)
+
+ # these are unnecessary assuming message equality works as advertised but
+ # explicitly check to be safe since we're mucking about in metaclass foo
+ self.assertEqual(prius.name, new_prius.name)
+ self.assertEqual(prius.year, new_prius.year)
+ self.assertEqual(prius.automatic, new_prius.automatic)
+ self.assertEqual(prius.price, new_prius.price)
+ self.assertEqual(prius.owners, new_prius.owners)
+
+ def testTopLevelExtensionsForOptionalScalar(self):
+ extendee_proto = unittest_pb2.TestAllExtensions()
+ extension = unittest_pb2.optional_int32_extension
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+ self.assertEqual(0, extendee_proto.Extensions[extension])
+ # As with normal scalar fields, just doing a read doesn't actually set the
+ # "has" bit.
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+ # Actually set the thing.
+ extendee_proto.Extensions[extension] = 23
+ self.assertEqual(23, extendee_proto.Extensions[extension])
+ self.assertTrue(extendee_proto.HasExtension(extension))
+ # Ensure that clearing works as well.
+ extendee_proto.ClearExtension(extension)
+ self.assertEqual(0, extendee_proto.Extensions[extension])
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+
+ def testTopLevelExtensionsForRepeatedScalar(self):
+ extendee_proto = unittest_pb2.TestAllExtensions()
+ extension = unittest_pb2.repeated_string_extension
+ self.assertEqual(0, len(extendee_proto.Extensions[extension]))
+ extendee_proto.Extensions[extension].append('foo')
+ self.assertEqual(['foo'], extendee_proto.Extensions[extension])
+ string_list = extendee_proto.Extensions[extension]
+ extendee_proto.ClearExtension(extension)
+ self.assertEqual(0, len(extendee_proto.Extensions[extension]))
+ self.assertTrue(string_list is not extendee_proto.Extensions[extension])
+ # Shouldn't be allowed to do Extensions[extension] = 'a'
+ self.assertRaises(TypeError, operator.setitem, extendee_proto.Extensions,
+ extension, 'a')
+
+ def testTopLevelExtensionsForOptionalMessage(self):
+ extendee_proto = unittest_pb2.TestAllExtensions()
+ extension = unittest_pb2.optional_foreign_message_extension
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+ self.assertEqual(0, extendee_proto.Extensions[extension].c)
+ # As with normal (non-extension) fields, merely reading from the
+ # thing shouldn't set the "has" bit.
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+ extendee_proto.Extensions[extension].c = 23
+ self.assertEqual(23, extendee_proto.Extensions[extension].c)
+ self.assertTrue(extendee_proto.HasExtension(extension))
+ # Save a reference here.
+ foreign_message = extendee_proto.Extensions[extension]
+ extendee_proto.ClearExtension(extension)
+ self.assertTrue(foreign_message is not extendee_proto.Extensions[extension])
+ # Setting a field on foreign_message now shouldn't set
+ # any "has" bits on extendee_proto.
+ foreign_message.c = 42
+ self.assertEqual(42, foreign_message.c)
+ self.assertTrue(foreign_message.HasField('c'))
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+ # Shouldn't be allowed to do Extensions[extension] = 'a'
+ self.assertRaises(TypeError, operator.setitem, extendee_proto.Extensions,
+ extension, 'a')
+
+ def testTopLevelExtensionsForRepeatedMessage(self):
+ extendee_proto = unittest_pb2.TestAllExtensions()
+ extension = unittest_pb2.repeatedgroup_extension
+ self.assertEqual(0, len(extendee_proto.Extensions[extension]))
+ group = extendee_proto.Extensions[extension].add()
+ group.a = 23
+ self.assertEqual(23, extendee_proto.Extensions[extension][0].a)
+ group.a = 42
+ self.assertEqual(42, extendee_proto.Extensions[extension][0].a)
+ group_list = extendee_proto.Extensions[extension]
+ extendee_proto.ClearExtension(extension)
+ self.assertEqual(0, len(extendee_proto.Extensions[extension]))
+ self.assertTrue(group_list is not extendee_proto.Extensions[extension])
+ # Shouldn't be allowed to do Extensions[extension] = 'a'
+ self.assertRaises(TypeError, operator.setitem, extendee_proto.Extensions,
+ extension, 'a')
+
+ def testNestedExtensions(self):
+ extendee_proto = unittest_pb2.TestAllExtensions()
+ extension = unittest_pb2.TestRequired.single
+
+ # We just test the non-repeated case.
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+ required = extendee_proto.Extensions[extension]
+ self.assertEqual(0, required.a)
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+ required.a = 23
+ self.assertEqual(23, extendee_proto.Extensions[extension].a)
+ self.assertTrue(extendee_proto.HasExtension(extension))
+ extendee_proto.ClearExtension(extension)
+ self.assertTrue(required is not extendee_proto.Extensions[extension])
+ self.assertTrue(not extendee_proto.HasExtension(extension))
+
+ def testRegisteredExtensions(self):
+ self.assertTrue('protobuf_unittest.optional_int32_extension' in
+ unittest_pb2.TestAllExtensions._extensions_by_name)
+ self.assertTrue(1 in unittest_pb2.TestAllExtensions._extensions_by_number)
+ # Make sure extensions haven't been registered into types that shouldn't
+ # have any.
+ self.assertEqual(0, len(unittest_pb2.TestAllTypes._extensions_by_name))
+
+ # If message A directly contains message B, and
+ # a.HasField('b') is currently False, then mutating any
+ # extension in B should change a.HasField('b') to True
+ # (and so on up the object tree).
+ def testHasBitsForAncestorsOfExtendedMessage(self):
+ # Optional scalar extension.
+ toplevel = more_extensions_pb2.TopLevelMessage()
+ self.assertTrue(not toplevel.HasField('submessage'))
+ self.assertEqual(0, toplevel.submessage.Extensions[
+ more_extensions_pb2.optional_int_extension])
+ self.assertTrue(not toplevel.HasField('submessage'))
+ toplevel.submessage.Extensions[
+ more_extensions_pb2.optional_int_extension] = 23
+ self.assertEqual(23, toplevel.submessage.Extensions[
+ more_extensions_pb2.optional_int_extension])
+ self.assertTrue(toplevel.HasField('submessage'))
+
+ # Repeated scalar extension.
+ toplevel = more_extensions_pb2.TopLevelMessage()
+ self.assertTrue(not toplevel.HasField('submessage'))
+ self.assertEqual([], toplevel.submessage.Extensions[
+ more_extensions_pb2.repeated_int_extension])
+ self.assertTrue(not toplevel.HasField('submessage'))
+ toplevel.submessage.Extensions[
+ more_extensions_pb2.repeated_int_extension].append(23)
+ self.assertEqual([23], toplevel.submessage.Extensions[
+ more_extensions_pb2.repeated_int_extension])
+ self.assertTrue(toplevel.HasField('submessage'))
+
+ # Optional message extension.
+ toplevel = more_extensions_pb2.TopLevelMessage()
+ self.assertTrue(not toplevel.HasField('submessage'))
+ self.assertEqual(0, toplevel.submessage.Extensions[
+ more_extensions_pb2.optional_message_extension].foreign_message_int)
+ self.assertTrue(not toplevel.HasField('submessage'))
+ toplevel.submessage.Extensions[
+ more_extensions_pb2.optional_message_extension].foreign_message_int = 23
+ self.assertEqual(23, toplevel.submessage.Extensions[
+ more_extensions_pb2.optional_message_extension].foreign_message_int)
+ self.assertTrue(toplevel.HasField('submessage'))
+
+ # Repeated message extension.
+ toplevel = more_extensions_pb2.TopLevelMessage()
+ self.assertTrue(not toplevel.HasField('submessage'))
+ self.assertEqual(0, len(toplevel.submessage.Extensions[
+ more_extensions_pb2.repeated_message_extension]))
+ self.assertTrue(not toplevel.HasField('submessage'))
+ foreign = toplevel.submessage.Extensions[
+ more_extensions_pb2.repeated_message_extension].add()
+ self.assertEqual(foreign, toplevel.submessage.Extensions[
+ more_extensions_pb2.repeated_message_extension][0])
+ self.assertTrue(toplevel.HasField('submessage'))
+
+ def testDisconnectionAfterClearingEmptyMessage(self):
+ toplevel = more_extensions_pb2.TopLevelMessage()
+ extendee_proto = toplevel.submessage
+ extension = more_extensions_pb2.optional_message_extension
+ extension_proto = extendee_proto.Extensions[extension]
+ extendee_proto.ClearExtension(extension)
+ extension_proto.foreign_message_int = 23
+
+ self.assertTrue(extension_proto is not extendee_proto.Extensions[extension])
+
+ def testExtensionFailureModes(self):
+ extendee_proto = unittest_pb2.TestAllExtensions()
+
+ # Try non-extension-handle arguments to HasExtension,
+ # ClearExtension(), and Extensions[]...
+ self.assertRaises(KeyError, extendee_proto.HasExtension, 1234)
+ self.assertRaises(KeyError, extendee_proto.ClearExtension, 1234)
+ self.assertRaises(KeyError, extendee_proto.Extensions.__getitem__, 1234)
+ self.assertRaises(KeyError, extendee_proto.Extensions.__setitem__, 1234, 5)
+
+ # Try something that *is* an extension handle, just not for
+ # this message...
+ for unknown_handle in (more_extensions_pb2.optional_int_extension,
+ more_extensions_pb2.optional_message_extension,
+ more_extensions_pb2.repeated_int_extension,
+ more_extensions_pb2.repeated_message_extension):
+ self.assertRaises(KeyError, extendee_proto.HasExtension,
+ unknown_handle)
+ self.assertRaises(KeyError, extendee_proto.ClearExtension,
+ unknown_handle)
+ self.assertRaises(KeyError, extendee_proto.Extensions.__getitem__,
+ unknown_handle)
+ self.assertRaises(KeyError, extendee_proto.Extensions.__setitem__,
+ unknown_handle, 5)
+
+ # Try call HasExtension() with a valid handle, but for a
+ # *repeated* field. (Just as with non-extension repeated
+ # fields, Has*() isn't supported for extension repeated fields).
+ self.assertRaises(KeyError, extendee_proto.HasExtension,
+ unittest_pb2.repeated_string_extension)
+
+ def testStaticParseFrom(self):
+ proto1 = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(proto1)
+
+ string1 = proto1.SerializeToString()
+ proto2 = unittest_pb2.TestAllTypes.FromString(string1)
+
+ # Messages should be equal.
+ self.assertEqual(proto2, proto1)
+
+ def testMergeFromSingularField(self):
+ # Test merge with just a singular field.
+ proto1 = unittest_pb2.TestAllTypes()
+ proto1.optional_int32 = 1
+
+ proto2 = unittest_pb2.TestAllTypes()
+ # This shouldn't get overwritten.
+ proto2.optional_string = 'value'
+
+ proto2.MergeFrom(proto1)
+ self.assertEqual(1, proto2.optional_int32)
+ self.assertEqual('value', proto2.optional_string)
+
+ def testMergeFromRepeatedField(self):
+ # Test merge with just a repeated field.
+ proto1 = unittest_pb2.TestAllTypes()
+ proto1.repeated_int32.append(1)
+ proto1.repeated_int32.append(2)
+
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.repeated_int32.append(0)
+ proto2.MergeFrom(proto1)
+
+ self.assertEqual(0, proto2.repeated_int32[0])
+ self.assertEqual(1, proto2.repeated_int32[1])
+ self.assertEqual(2, proto2.repeated_int32[2])
+
+ def testMergeFromOptionalGroup(self):
+ # Test merge with an optional group.
+ proto1 = unittest_pb2.TestAllTypes()
+ proto1.optionalgroup.a = 12
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.MergeFrom(proto1)
+ self.assertEqual(12, proto2.optionalgroup.a)
+
+ def testMergeFromRepeatedNestedMessage(self):
+ # Test merge with a repeated nested message.
+ proto1 = unittest_pb2.TestAllTypes()
+ m = proto1.repeated_nested_message.add()
+ m.bb = 123
+ m = proto1.repeated_nested_message.add()
+ m.bb = 321
+
+ proto2 = unittest_pb2.TestAllTypes()
+ m = proto2.repeated_nested_message.add()
+ m.bb = 999
+ proto2.MergeFrom(proto1)
+ self.assertEqual(999, proto2.repeated_nested_message[0].bb)
+ self.assertEqual(123, proto2.repeated_nested_message[1].bb)
+ self.assertEqual(321, proto2.repeated_nested_message[2].bb)
+
+ proto3 = unittest_pb2.TestAllTypes()
+ proto3.repeated_nested_message.MergeFrom(proto2.repeated_nested_message)
+ self.assertEqual(999, proto3.repeated_nested_message[0].bb)
+ self.assertEqual(123, proto3.repeated_nested_message[1].bb)
+ self.assertEqual(321, proto3.repeated_nested_message[2].bb)
+
+ def testMergeFromAllFields(self):
+ # With all fields set.
+ proto1 = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(proto1)
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.MergeFrom(proto1)
+
+ # Messages should be equal.
+ self.assertEqual(proto2, proto1)
+
+ # Serialized string should be equal too.
+ string1 = proto1.SerializeToString()
+ string2 = proto2.SerializeToString()
+ self.assertEqual(string1, string2)
+
+ def testMergeFromExtensionsSingular(self):
+ proto1 = unittest_pb2.TestAllExtensions()
+ proto1.Extensions[unittest_pb2.optional_int32_extension] = 1
+
+ proto2 = unittest_pb2.TestAllExtensions()
+ proto2.MergeFrom(proto1)
+ self.assertEqual(
+ 1, proto2.Extensions[unittest_pb2.optional_int32_extension])
+
+ def testMergeFromExtensionsRepeated(self):
+ proto1 = unittest_pb2.TestAllExtensions()
+ proto1.Extensions[unittest_pb2.repeated_int32_extension].append(1)
+ proto1.Extensions[unittest_pb2.repeated_int32_extension].append(2)
+
+ proto2 = unittest_pb2.TestAllExtensions()
+ proto2.Extensions[unittest_pb2.repeated_int32_extension].append(0)
+ proto2.MergeFrom(proto1)
+ self.assertEqual(
+ 3, len(proto2.Extensions[unittest_pb2.repeated_int32_extension]))
+ self.assertEqual(
+ 0, proto2.Extensions[unittest_pb2.repeated_int32_extension][0])
+ self.assertEqual(
+ 1, proto2.Extensions[unittest_pb2.repeated_int32_extension][1])
+ self.assertEqual(
+ 2, proto2.Extensions[unittest_pb2.repeated_int32_extension][2])
+
+ def testMergeFromExtensionsNestedMessage(self):
+ proto1 = unittest_pb2.TestAllExtensions()
+ ext1 = proto1.Extensions[
+ unittest_pb2.repeated_nested_message_extension]
+ m = ext1.add()
+ m.bb = 222
+ m = ext1.add()
+ m.bb = 333
+
+ proto2 = unittest_pb2.TestAllExtensions()
+ ext2 = proto2.Extensions[
+ unittest_pb2.repeated_nested_message_extension]
+ m = ext2.add()
+ m.bb = 111
+
+ proto2.MergeFrom(proto1)
+ ext2 = proto2.Extensions[
+ unittest_pb2.repeated_nested_message_extension]
+ self.assertEqual(3, len(ext2))
+ self.assertEqual(111, ext2[0].bb)
+ self.assertEqual(222, ext2[1].bb)
+ self.assertEqual(333, ext2[2].bb)
+
+ def testMergeFromBug(self):
+ message1 = unittest_pb2.TestAllTypes()
+ message2 = unittest_pb2.TestAllTypes()
+
+ # Cause optional_nested_message to be instantiated within message1, even
+ # though it is not considered to be "present".
+ message1.optional_nested_message
+ self.assertFalse(message1.HasField('optional_nested_message'))
+
+ # Merge into message2. This should not instantiate the field is message2.
+ message2.MergeFrom(message1)
+ self.assertFalse(message2.HasField('optional_nested_message'))
+
+ def testCopyFromSingularField(self):
+ # Test copy with just a singular field.
+ proto1 = unittest_pb2.TestAllTypes()
+ proto1.optional_int32 = 1
+ proto1.optional_string = 'important-text'
+
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.optional_string = 'value'
+
+ proto2.CopyFrom(proto1)
+ self.assertEqual(1, proto2.optional_int32)
+ self.assertEqual('important-text', proto2.optional_string)
+
+ def testCopyFromRepeatedField(self):
+ # Test copy with a repeated field.
+ proto1 = unittest_pb2.TestAllTypes()
+ proto1.repeated_int32.append(1)
+ proto1.repeated_int32.append(2)
+
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.repeated_int32.append(0)
+ proto2.CopyFrom(proto1)
+
+ self.assertEqual(1, proto2.repeated_int32[0])
+ self.assertEqual(2, proto2.repeated_int32[1])
+
+ def testCopyFromAllFields(self):
+ # With all fields set.
+ proto1 = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(proto1)
+ proto2 = unittest_pb2.TestAllTypes()
+ proto2.CopyFrom(proto1)
+
+ # Messages should be equal.
+ self.assertEqual(proto2, proto1)
+
+ # Serialized string should be equal too.
+ string1 = proto1.SerializeToString()
+ string2 = proto2.SerializeToString()
+ self.assertEqual(string1, string2)
+
+ def testCopyFromSelf(self):
+ proto1 = unittest_pb2.TestAllTypes()
+ proto1.repeated_int32.append(1)
+ proto1.optional_int32 = 2
+ proto1.optional_string = 'important-text'
+
+ proto1.CopyFrom(proto1)
+ self.assertEqual(1, proto1.repeated_int32[0])
+ self.assertEqual(2, proto1.optional_int32)
+ self.assertEqual('important-text', proto1.optional_string)
+
+ def testCopyFromBadType(self):
+ # The python implementation doesn't raise an exception in this
+ # case. In theory it should.
+ if api_implementation.Type() == 'python':
+ return
+ proto1 = unittest_pb2.TestAllTypes()
+ proto2 = unittest_pb2.TestAllExtensions()
+ self.assertRaises(TypeError, proto1.CopyFrom, proto2)
+
+ def testDeepCopy(self):
+ proto1 = unittest_pb2.TestAllTypes()
+ proto1.optional_int32 = 1
+ proto2 = copy.deepcopy(proto1)
+ self.assertEqual(1, proto2.optional_int32)
+
+ proto1.repeated_int32.append(2)
+ proto1.repeated_int32.append(3)
+ container = copy.deepcopy(proto1.repeated_int32)
+ self.assertEqual([2, 3], container)
+
+ # TODO(anuraag): Implement deepcopy for repeated composite / extension dict
+
+ def testClear(self):
+ proto = unittest_pb2.TestAllTypes()
+ # C++ implementation does not support lazy fields right now so leave it
+ # out for now.
+ if api_implementation.Type() == 'python':
+ test_util.SetAllFields(proto)
+ else:
+ test_util.SetAllNonLazyFields(proto)
+ # Clear the message.
+ proto.Clear()
+ self.assertEqual(proto.ByteSize(), 0)
+ empty_proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(proto, empty_proto)
+
+ # Test if extensions which were set are cleared.
+ proto = unittest_pb2.TestAllExtensions()
+ test_util.SetAllExtensions(proto)
+ # Clear the message.
+ proto.Clear()
+ self.assertEqual(proto.ByteSize(), 0)
+ empty_proto = unittest_pb2.TestAllExtensions()
+ self.assertEqual(proto, empty_proto)
+
+ def testDisconnectingBeforeClear(self):
+ proto = unittest_pb2.TestAllTypes()
+ nested = proto.optional_nested_message
+ proto.Clear()
+ self.assertTrue(nested is not proto.optional_nested_message)
+ nested.bb = 23
+ self.assertTrue(not proto.HasField('optional_nested_message'))
+ self.assertEqual(0, proto.optional_nested_message.bb)
+
+ proto = unittest_pb2.TestAllTypes()
+ nested = proto.optional_nested_message
+ nested.bb = 5
+ foreign = proto.optional_foreign_message
+ foreign.c = 6
+
+ proto.Clear()
+ self.assertTrue(nested is not proto.optional_nested_message)
+ self.assertTrue(foreign is not proto.optional_foreign_message)
+ self.assertEqual(5, nested.bb)
+ self.assertEqual(6, foreign.c)
+ nested.bb = 15
+ foreign.c = 16
+ self.assertFalse(proto.HasField('optional_nested_message'))
+ self.assertEqual(0, proto.optional_nested_message.bb)
+ self.assertFalse(proto.HasField('optional_foreign_message'))
+ self.assertEqual(0, proto.optional_foreign_message.c)
+
+ def testOneOf(self):
+ proto = unittest_pb2.TestAllTypes()
+ proto.oneof_uint32 = 10
+ proto.oneof_nested_message.bb = 11
+ self.assertEqual(11, proto.oneof_nested_message.bb)
+ self.assertFalse(proto.HasField('oneof_uint32'))
+ nested = proto.oneof_nested_message
+ proto.oneof_string = 'abc'
+ self.assertEqual('abc', proto.oneof_string)
+ self.assertEqual(11, nested.bb)
+ self.assertFalse(proto.HasField('oneof_nested_message'))
+
+ def assertInitialized(self, proto):
+ self.assertTrue(proto.IsInitialized())
+ # Neither method should raise an exception.
+ proto.SerializeToString()
+ proto.SerializePartialToString()
+
+ def assertNotInitialized(self, proto):
+ self.assertFalse(proto.IsInitialized())
+ self.assertRaises(message.EncodeError, proto.SerializeToString)
+ # "Partial" serialization doesn't care if message is uninitialized.
+ proto.SerializePartialToString()
+
+ def testIsInitialized(self):
+ # Trivial cases - all optional fields and extensions.
+ proto = unittest_pb2.TestAllTypes()
+ self.assertInitialized(proto)
+ proto = unittest_pb2.TestAllExtensions()
+ self.assertInitialized(proto)
+
+ # The case of uninitialized required fields.
+ proto = unittest_pb2.TestRequired()
+ self.assertNotInitialized(proto)
+ proto.a = proto.b = proto.c = 2
+ self.assertInitialized(proto)
+
+ # The case of uninitialized submessage.
+ proto = unittest_pb2.TestRequiredForeign()
+ self.assertInitialized(proto)
+ proto.optional_message.a = 1
+ self.assertNotInitialized(proto)
+ proto.optional_message.b = 0
+ proto.optional_message.c = 0
+ self.assertInitialized(proto)
+
+ # Uninitialized repeated submessage.
+ message1 = proto.repeated_message.add()
+ self.assertNotInitialized(proto)
+ message1.a = message1.b = message1.c = 0
+ self.assertInitialized(proto)
+
+ # Uninitialized repeated group in an extension.
+ proto = unittest_pb2.TestAllExtensions()
+ extension = unittest_pb2.TestRequired.multi
+ message1 = proto.Extensions[extension].add()
+ message2 = proto.Extensions[extension].add()
+ self.assertNotInitialized(proto)
+ message1.a = 1
+ message1.b = 1
+ message1.c = 1
+ self.assertNotInitialized(proto)
+ message2.a = 2
+ message2.b = 2
+ message2.c = 2
+ self.assertInitialized(proto)
+
+ # Uninitialized nonrepeated message in an extension.
+ proto = unittest_pb2.TestAllExtensions()
+ extension = unittest_pb2.TestRequired.single
+ proto.Extensions[extension].a = 1
+ self.assertNotInitialized(proto)
+ proto.Extensions[extension].b = 2
+ proto.Extensions[extension].c = 3
+ self.assertInitialized(proto)
+
+ # Try passing an errors list.
+ errors = []
+ proto = unittest_pb2.TestRequired()
+ self.assertFalse(proto.IsInitialized(errors))
+ self.assertEqual(errors, ['a', 'b', 'c'])
+
+ @unittest.skipIf(
+ api_implementation.Type() != 'cpp' or api_implementation.Version() != 2,
+ 'Errors are only available from the most recent C++ implementation.')
+ def testFileDescriptorErrors(self):
+ file_name = 'test_file_descriptor_errors.proto'
+ package_name = 'test_file_descriptor_errors.proto'
+ file_descriptor_proto = descriptor_pb2.FileDescriptorProto()
+ file_descriptor_proto.name = file_name
+ file_descriptor_proto.package = package_name
+ m1 = file_descriptor_proto.message_type.add()
+ m1.name = 'msg1'
+ # Compiles the proto into the C++ descriptor pool
+ descriptor.FileDescriptor(
+ file_name,
+ package_name,
+ serialized_pb=file_descriptor_proto.SerializeToString())
+ # Add a FileDescriptorProto that has duplicate symbols
+ another_file_name = 'another_test_file_descriptor_errors.proto'
+ file_descriptor_proto.name = another_file_name
+ m2 = file_descriptor_proto.message_type.add()
+ m2.name = 'msg2'
+ with self.assertRaises(TypeError) as cm:
+ descriptor.FileDescriptor(
+ another_file_name,
+ package_name,
+ serialized_pb=file_descriptor_proto.SerializeToString())
+ self.assertTrue(hasattr(cm, 'exception'), '%s not raised' %
+ getattr(cm.expected, '__name__', cm.expected))
+ self.assertIn('test_file_descriptor_errors.proto', str(cm.exception))
+ # Error message will say something about this definition being a
+ # duplicate, though we don't check the message exactly to avoid a
+ # dependency on the C++ logging code.
+ self.assertIn('test_file_descriptor_errors.msg1', str(cm.exception))
+
+ def testStringUTF8Encoding(self):
+ proto = unittest_pb2.TestAllTypes()
+
+ # Assignment of a unicode object to a field of type 'bytes' is not allowed.
+ self.assertRaises(TypeError,
+ setattr, proto, 'optional_bytes', u'unicode object')
+
+ # Check that the default value is of python's 'unicode' type.
+ self.assertEqual(type(proto.optional_string), six.text_type)
+
+ proto.optional_string = six.text_type('Testing')
+ self.assertEqual(proto.optional_string, str('Testing'))
+
+ # Assign a value of type 'str' which can be encoded in UTF-8.
+ proto.optional_string = str('Testing')
+ self.assertEqual(proto.optional_string, six.text_type('Testing'))
+
+ # Try to assign a 'bytes' object which contains non-UTF-8.
+ self.assertRaises(ValueError,
+ setattr, proto, 'optional_string', b'a\x80a')
+ # No exception: Assign already encoded UTF-8 bytes to a string field.
+ utf8_bytes = u'ТеÑÑ‚'.encode('utf-8')
+ proto.optional_string = utf8_bytes
+ # No exception: Assign the a non-ascii unicode object.
+ proto.optional_string = u'ТеÑÑ‚'
+ # No exception thrown (normal str assignment containing ASCII).
+ proto.optional_string = 'abc'
+
+ def testStringUTF8Serialization(self):
+ proto = message_set_extensions_pb2.TestMessageSet()
+ extension_message = message_set_extensions_pb2.TestMessageSetExtension2
+ extension = extension_message.message_set_extension
+
+ test_utf8 = u'ТеÑÑ‚'
+ test_utf8_bytes = test_utf8.encode('utf-8')
+
+ # 'Test' in another language, using UTF-8 charset.
+ proto.Extensions[extension].str = test_utf8
+
+ # Serialize using the MessageSet wire format (this is specified in the
+ # .proto file).
+ serialized = proto.SerializeToString()
+
+ # Check byte size.
+ self.assertEqual(proto.ByteSize(), len(serialized))
+
+ raw = unittest_mset_pb2.RawMessageSet()
+ bytes_read = raw.MergeFromString(serialized)
+ self.assertEqual(len(serialized), bytes_read)
+
+ message2 = message_set_extensions_pb2.TestMessageSetExtension2()
+
+ self.assertEqual(1, len(raw.item))
+ # Check that the type_id is the same as the tag ID in the .proto file.
+ self.assertEqual(raw.item[0].type_id, 98418634)
+
+ # Check the actual bytes on the wire.
+ self.assertTrue(raw.item[0].message.endswith(test_utf8_bytes))
+ bytes_read = message2.MergeFromString(raw.item[0].message)
+ self.assertEqual(len(raw.item[0].message), bytes_read)
+
+ self.assertEqual(type(message2.str), six.text_type)
+ self.assertEqual(message2.str, test_utf8)
+
+ # The pure Python API throws an exception on MergeFromString(),
+ # if any of the string fields of the message can't be UTF-8 decoded.
+ # The C++ implementation of the API has no way to check that on
+ # MergeFromString and thus has no way to throw the exception.
+ #
+ # The pure Python API always returns objects of type 'unicode' (UTF-8
+ # encoded), or 'bytes' (in 7 bit ASCII).
+ badbytes = raw.item[0].message.replace(
+ test_utf8_bytes, len(test_utf8_bytes) * b'\xff')
+
+ unicode_decode_failed = False
+ try:
+ message2.MergeFromString(badbytes)
+ except UnicodeDecodeError:
+ unicode_decode_failed = True
+ string_field = message2.str
+ self.assertTrue(unicode_decode_failed or type(string_field) is bytes)
+
+ def testBytesInTextFormat(self):
+ proto = unittest_pb2.TestAllTypes(optional_bytes=b'\x00\x7f\x80\xff')
+ self.assertEqual(u'optional_bytes: "\\000\\177\\200\\377"\n',
+ six.text_type(proto))
+
+ def testEmptyNestedMessage(self):
+ proto = unittest_pb2.TestAllTypes()
+ proto.optional_nested_message.MergeFrom(
+ unittest_pb2.TestAllTypes.NestedMessage())
+ self.assertTrue(proto.HasField('optional_nested_message'))
+
+ proto = unittest_pb2.TestAllTypes()
+ proto.optional_nested_message.CopyFrom(
+ unittest_pb2.TestAllTypes.NestedMessage())
+ self.assertTrue(proto.HasField('optional_nested_message'))
+
+ proto = unittest_pb2.TestAllTypes()
+ bytes_read = proto.optional_nested_message.MergeFromString(b'')
+ self.assertEqual(0, bytes_read)
+ self.assertTrue(proto.HasField('optional_nested_message'))
+
+ proto = unittest_pb2.TestAllTypes()
+ proto.optional_nested_message.ParseFromString(b'')
+ self.assertTrue(proto.HasField('optional_nested_message'))
+
+ serialized = proto.SerializeToString()
+ proto2 = unittest_pb2.TestAllTypes()
+ self.assertEqual(
+ len(serialized),
+ proto2.MergeFromString(serialized))
+ self.assertTrue(proto2.HasField('optional_nested_message'))
+
+ def testSetInParent(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertFalse(proto.HasField('optionalgroup'))
+ proto.optionalgroup.SetInParent()
+ self.assertTrue(proto.HasField('optionalgroup'))
+
+ def testPackageInitializationImport(self):
+ """Test that we can import nested messages from their __init__.py.
+
+ Such setup is not trivial since at the time of processing of __init__.py one
+ can't refer to its submodules by name in code, so expressions like
+ google.protobuf.internal.import_test_package.inner_pb2
+ don't work. They do work in imports, so we have assign an alias at import
+ and then use that alias in generated code.
+ """
+ # We import here since it's the import that used to fail, and we want
+ # the failure to have the right context.
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf.internal import import_test_package
+ # pylint: enable=g-import-not-at-top
+ msg = import_test_package.myproto.Outer()
+ # Just check the default value.
+ self.assertEqual(57, msg.inner.value)
+
+# Since we had so many tests for protocol buffer equality, we broke these out
+# into separate TestCase classes.
+
+
+class TestAllTypesEqualityTest(unittest.TestCase):
+
+ def setUp(self):
+ self.first_proto = unittest_pb2.TestAllTypes()
+ self.second_proto = unittest_pb2.TestAllTypes()
+
+ def testNotHashable(self):
+ self.assertRaises(TypeError, hash, self.first_proto)
+
+ def testSelfEquality(self):
+ self.assertEqual(self.first_proto, self.first_proto)
+
+ def testEmptyProtosEqual(self):
+ self.assertEqual(self.first_proto, self.second_proto)
+
+
+class FullProtosEqualityTest(unittest.TestCase):
+
+ """Equality tests using completely-full protos as a starting point."""
+
+ def setUp(self):
+ self.first_proto = unittest_pb2.TestAllTypes()
+ self.second_proto = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(self.first_proto)
+ test_util.SetAllFields(self.second_proto)
+
+ def testNotHashable(self):
+ self.assertRaises(TypeError, hash, self.first_proto)
+
+ def testNoneNotEqual(self):
+ self.assertNotEqual(self.first_proto, None)
+ self.assertNotEqual(None, self.second_proto)
+
+ def testNotEqualToOtherMessage(self):
+ third_proto = unittest_pb2.TestRequired()
+ self.assertNotEqual(self.first_proto, third_proto)
+ self.assertNotEqual(third_proto, self.second_proto)
+
+ def testAllFieldsFilledEquality(self):
+ self.assertEqual(self.first_proto, self.second_proto)
+
+ def testNonRepeatedScalar(self):
+ # Nonrepeated scalar field change should cause inequality.
+ self.first_proto.optional_int32 += 1
+ self.assertNotEqual(self.first_proto, self.second_proto)
+ # ...as should clearing a field.
+ self.first_proto.ClearField('optional_int32')
+ self.assertNotEqual(self.first_proto, self.second_proto)
+
+ def testNonRepeatedComposite(self):
+ # Change a nonrepeated composite field.
+ self.first_proto.optional_nested_message.bb += 1
+ self.assertNotEqual(self.first_proto, self.second_proto)
+ self.first_proto.optional_nested_message.bb -= 1
+ self.assertEqual(self.first_proto, self.second_proto)
+ # Clear a field in the nested message.
+ self.first_proto.optional_nested_message.ClearField('bb')
+ self.assertNotEqual(self.first_proto, self.second_proto)
+ self.first_proto.optional_nested_message.bb = (
+ self.second_proto.optional_nested_message.bb)
+ self.assertEqual(self.first_proto, self.second_proto)
+ # Remove the nested message entirely.
+ self.first_proto.ClearField('optional_nested_message')
+ self.assertNotEqual(self.first_proto, self.second_proto)
+
+ def testRepeatedScalar(self):
+ # Change a repeated scalar field.
+ self.first_proto.repeated_int32.append(5)
+ self.assertNotEqual(self.first_proto, self.second_proto)
+ self.first_proto.ClearField('repeated_int32')
+ self.assertNotEqual(self.first_proto, self.second_proto)
+
+ def testRepeatedComposite(self):
+ # Change value within a repeated composite field.
+ self.first_proto.repeated_nested_message[0].bb += 1
+ self.assertNotEqual(self.first_proto, self.second_proto)
+ self.first_proto.repeated_nested_message[0].bb -= 1
+ self.assertEqual(self.first_proto, self.second_proto)
+ # Add a value to a repeated composite field.
+ self.first_proto.repeated_nested_message.add()
+ self.assertNotEqual(self.first_proto, self.second_proto)
+ self.second_proto.repeated_nested_message.add()
+ self.assertEqual(self.first_proto, self.second_proto)
+
+ def testNonRepeatedScalarHasBits(self):
+ # Ensure that we test "has" bits as well as value for
+ # nonrepeated scalar field.
+ self.first_proto.ClearField('optional_int32')
+ self.second_proto.optional_int32 = 0
+ self.assertNotEqual(self.first_proto, self.second_proto)
+
+ def testNonRepeatedCompositeHasBits(self):
+ # Ensure that we test "has" bits as well as value for
+ # nonrepeated composite field.
+ self.first_proto.ClearField('optional_nested_message')
+ self.second_proto.optional_nested_message.ClearField('bb')
+ self.assertNotEqual(self.first_proto, self.second_proto)
+ self.first_proto.optional_nested_message.bb = 0
+ self.first_proto.optional_nested_message.ClearField('bb')
+ self.assertEqual(self.first_proto, self.second_proto)
+
+
+class ExtensionEqualityTest(unittest.TestCase):
+
+ def testExtensionEquality(self):
+ first_proto = unittest_pb2.TestAllExtensions()
+ second_proto = unittest_pb2.TestAllExtensions()
+ self.assertEqual(first_proto, second_proto)
+ test_util.SetAllExtensions(first_proto)
+ self.assertNotEqual(first_proto, second_proto)
+ test_util.SetAllExtensions(second_proto)
+ self.assertEqual(first_proto, second_proto)
+
+ # Ensure that we check value equality.
+ first_proto.Extensions[unittest_pb2.optional_int32_extension] += 1
+ self.assertNotEqual(first_proto, second_proto)
+ first_proto.Extensions[unittest_pb2.optional_int32_extension] -= 1
+ self.assertEqual(first_proto, second_proto)
+
+ # Ensure that we also look at "has" bits.
+ first_proto.ClearExtension(unittest_pb2.optional_int32_extension)
+ second_proto.Extensions[unittest_pb2.optional_int32_extension] = 0
+ self.assertNotEqual(first_proto, second_proto)
+ first_proto.Extensions[unittest_pb2.optional_int32_extension] = 0
+ self.assertEqual(first_proto, second_proto)
+
+ # Ensure that differences in cached values
+ # don't matter if "has" bits are both false.
+ first_proto = unittest_pb2.TestAllExtensions()
+ second_proto = unittest_pb2.TestAllExtensions()
+ self.assertEqual(
+ 0, first_proto.Extensions[unittest_pb2.optional_int32_extension])
+ self.assertEqual(first_proto, second_proto)
+
+
+class MutualRecursionEqualityTest(unittest.TestCase):
+
+ def testEqualityWithMutualRecursion(self):
+ first_proto = unittest_pb2.TestMutualRecursionA()
+ second_proto = unittest_pb2.TestMutualRecursionA()
+ self.assertEqual(first_proto, second_proto)
+ first_proto.bb.a.bb.optional_int32 = 23
+ self.assertNotEqual(first_proto, second_proto)
+ second_proto.bb.a.bb.optional_int32 = 23
+ self.assertEqual(first_proto, second_proto)
+
+
+class ByteSizeTest(unittest.TestCase):
+
+ def setUp(self):
+ self.proto = unittest_pb2.TestAllTypes()
+ self.extended_proto = more_extensions_pb2.ExtendedMessage()
+ self.packed_proto = unittest_pb2.TestPackedTypes()
+ self.packed_extended_proto = unittest_pb2.TestPackedExtensions()
+
+ def Size(self):
+ return self.proto.ByteSize()
+
+ def testEmptyMessage(self):
+ self.assertEqual(0, self.proto.ByteSize())
+
+ def testSizedOnKwargs(self):
+ # Use a separate message to ensure testing right after creation.
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(0, proto.ByteSize())
+ proto_kwargs = unittest_pb2.TestAllTypes(optional_int64 = 1)
+ # One byte for the tag, one to encode varint 1.
+ self.assertEqual(2, proto_kwargs.ByteSize())
+
+ def testVarints(self):
+ def Test(i, expected_varint_size):
+ self.proto.Clear()
+ self.proto.optional_int64 = i
+ # Add one to the varint size for the tag info
+ # for tag 1.
+ self.assertEqual(expected_varint_size + 1, self.Size())
+ Test(0, 1)
+ Test(1, 1)
+ for i, num_bytes in zip(range(7, 63, 7), range(1, 10000)):
+ Test((1 << i) - 1, num_bytes)
+ Test(-1, 10)
+ Test(-2, 10)
+ Test(-(1 << 63), 10)
+
+ def testStrings(self):
+ self.proto.optional_string = ''
+ # Need one byte for tag info (tag #14), and one byte for length.
+ self.assertEqual(2, self.Size())
+
+ self.proto.optional_string = 'abc'
+ # Need one byte for tag info (tag #14), and one byte for length.
+ self.assertEqual(2 + len(self.proto.optional_string), self.Size())
+
+ self.proto.optional_string = 'x' * 128
+ # Need one byte for tag info (tag #14), and TWO bytes for length.
+ self.assertEqual(3 + len(self.proto.optional_string), self.Size())
+
+ def testOtherNumerics(self):
+ self.proto.optional_fixed32 = 1234
+ # One byte for tag and 4 bytes for fixed32.
+ self.assertEqual(5, self.Size())
+ self.proto = unittest_pb2.TestAllTypes()
+
+ self.proto.optional_fixed64 = 1234
+ # One byte for tag and 8 bytes for fixed64.
+ self.assertEqual(9, self.Size())
+ self.proto = unittest_pb2.TestAllTypes()
+
+ self.proto.optional_float = 1.234
+ # One byte for tag and 4 bytes for float.
+ self.assertEqual(5, self.Size())
+ self.proto = unittest_pb2.TestAllTypes()
+
+ self.proto.optional_double = 1.234
+ # One byte for tag and 8 bytes for float.
+ self.assertEqual(9, self.Size())
+ self.proto = unittest_pb2.TestAllTypes()
+
+ self.proto.optional_sint32 = 64
+ # One byte for tag and 2 bytes for zig-zag-encoded 64.
+ self.assertEqual(3, self.Size())
+ self.proto = unittest_pb2.TestAllTypes()
+
+ def testComposites(self):
+ # 3 bytes.
+ self.proto.optional_nested_message.bb = (1 << 14)
+ # Plus one byte for bb tag.
+ # Plus 1 byte for optional_nested_message serialized size.
+ # Plus two bytes for optional_nested_message tag.
+ self.assertEqual(3 + 1 + 1 + 2, self.Size())
+
+ def testGroups(self):
+ # 4 bytes.
+ self.proto.optionalgroup.a = (1 << 21)
+ # Plus two bytes for |a| tag.
+ # Plus 2 * two bytes for START_GROUP and END_GROUP tags.
+ self.assertEqual(4 + 2 + 2*2, self.Size())
+
+ def testRepeatedScalars(self):
+ self.proto.repeated_int32.append(10) # 1 byte.
+ self.proto.repeated_int32.append(128) # 2 bytes.
+ # Also need 2 bytes for each entry for tag.
+ self.assertEqual(1 + 2 + 2*2, self.Size())
+
+ def testRepeatedScalarsExtend(self):
+ self.proto.repeated_int32.extend([10, 128]) # 3 bytes.
+ # Also need 2 bytes for each entry for tag.
+ self.assertEqual(1 + 2 + 2*2, self.Size())
+
+ def testRepeatedScalarsRemove(self):
+ self.proto.repeated_int32.append(10) # 1 byte.
+ self.proto.repeated_int32.append(128) # 2 bytes.
+ # Also need 2 bytes for each entry for tag.
+ self.assertEqual(1 + 2 + 2*2, self.Size())
+ self.proto.repeated_int32.remove(128)
+ self.assertEqual(1 + 2, self.Size())
+
+ def testRepeatedComposites(self):
+ # Empty message. 2 bytes tag plus 1 byte length.
+ foreign_message_0 = self.proto.repeated_nested_message.add()
+ # 2 bytes tag plus 1 byte length plus 1 byte bb tag 1 byte int.
+ foreign_message_1 = self.proto.repeated_nested_message.add()
+ foreign_message_1.bb = 7
+ self.assertEqual(2 + 1 + 2 + 1 + 1 + 1, self.Size())
+
+ def testRepeatedCompositesDelete(self):
+ # Empty message. 2 bytes tag plus 1 byte length.
+ foreign_message_0 = self.proto.repeated_nested_message.add()
+ # 2 bytes tag plus 1 byte length plus 1 byte bb tag 1 byte int.
+ foreign_message_1 = self.proto.repeated_nested_message.add()
+ foreign_message_1.bb = 9
+ self.assertEqual(2 + 1 + 2 + 1 + 1 + 1, self.Size())
+
+ # 2 bytes tag plus 1 byte length plus 1 byte bb tag 1 byte int.
+ del self.proto.repeated_nested_message[0]
+ self.assertEqual(2 + 1 + 1 + 1, self.Size())
+
+ # Now add a new message.
+ foreign_message_2 = self.proto.repeated_nested_message.add()
+ foreign_message_2.bb = 12
+
+ # 2 bytes tag plus 1 byte length plus 1 byte bb tag 1 byte int.
+ # 2 bytes tag plus 1 byte length plus 1 byte bb tag 1 byte int.
+ self.assertEqual(2 + 1 + 1 + 1 + 2 + 1 + 1 + 1, self.Size())
+
+ # 2 bytes tag plus 1 byte length plus 1 byte bb tag 1 byte int.
+ del self.proto.repeated_nested_message[1]
+ self.assertEqual(2 + 1 + 1 + 1, self.Size())
+
+ del self.proto.repeated_nested_message[0]
+ self.assertEqual(0, self.Size())
+
+ def testRepeatedGroups(self):
+ # 2-byte START_GROUP plus 2-byte END_GROUP.
+ group_0 = self.proto.repeatedgroup.add()
+ # 2-byte START_GROUP plus 2-byte |a| tag + 1-byte |a|
+ # plus 2-byte END_GROUP.
+ group_1 = self.proto.repeatedgroup.add()
+ group_1.a = 7
+ self.assertEqual(2 + 2 + 2 + 2 + 1 + 2, self.Size())
+
+ def testExtensions(self):
+ proto = unittest_pb2.TestAllExtensions()
+ self.assertEqual(0, proto.ByteSize())
+ extension = unittest_pb2.optional_int32_extension # Field #1, 1 byte.
+ proto.Extensions[extension] = 23
+ # 1 byte for tag, 1 byte for value.
+ self.assertEqual(2, proto.ByteSize())
+
+ def testCacheInvalidationForNonrepeatedScalar(self):
+ # Test non-extension.
+ self.proto.optional_int32 = 1
+ self.assertEqual(2, self.proto.ByteSize())
+ self.proto.optional_int32 = 128
+ self.assertEqual(3, self.proto.ByteSize())
+ self.proto.ClearField('optional_int32')
+ self.assertEqual(0, self.proto.ByteSize())
+
+ # Test within extension.
+ extension = more_extensions_pb2.optional_int_extension
+ self.extended_proto.Extensions[extension] = 1
+ self.assertEqual(2, self.extended_proto.ByteSize())
+ self.extended_proto.Extensions[extension] = 128
+ self.assertEqual(3, self.extended_proto.ByteSize())
+ self.extended_proto.ClearExtension(extension)
+ self.assertEqual(0, self.extended_proto.ByteSize())
+
+ def testCacheInvalidationForRepeatedScalar(self):
+ # Test non-extension.
+ self.proto.repeated_int32.append(1)
+ self.assertEqual(3, self.proto.ByteSize())
+ self.proto.repeated_int32.append(1)
+ self.assertEqual(6, self.proto.ByteSize())
+ self.proto.repeated_int32[1] = 128
+ self.assertEqual(7, self.proto.ByteSize())
+ self.proto.ClearField('repeated_int32')
+ self.assertEqual(0, self.proto.ByteSize())
+
+ # Test within extension.
+ extension = more_extensions_pb2.repeated_int_extension
+ repeated = self.extended_proto.Extensions[extension]
+ repeated.append(1)
+ self.assertEqual(2, self.extended_proto.ByteSize())
+ repeated.append(1)
+ self.assertEqual(4, self.extended_proto.ByteSize())
+ repeated[1] = 128
+ self.assertEqual(5, self.extended_proto.ByteSize())
+ self.extended_proto.ClearExtension(extension)
+ self.assertEqual(0, self.extended_proto.ByteSize())
+
+ def testCacheInvalidationForNonrepeatedMessage(self):
+ # Test non-extension.
+ self.proto.optional_foreign_message.c = 1
+ self.assertEqual(5, self.proto.ByteSize())
+ self.proto.optional_foreign_message.c = 128
+ self.assertEqual(6, self.proto.ByteSize())
+ self.proto.optional_foreign_message.ClearField('c')
+ self.assertEqual(3, self.proto.ByteSize())
+ self.proto.ClearField('optional_foreign_message')
+ self.assertEqual(0, self.proto.ByteSize())
+
+ if api_implementation.Type() == 'python':
+ # This is only possible in pure-Python implementation of the API.
+ child = self.proto.optional_foreign_message
+ self.proto.ClearField('optional_foreign_message')
+ child.c = 128
+ self.assertEqual(0, self.proto.ByteSize())
+
+ # Test within extension.
+ extension = more_extensions_pb2.optional_message_extension
+ child = self.extended_proto.Extensions[extension]
+ self.assertEqual(0, self.extended_proto.ByteSize())
+ child.foreign_message_int = 1
+ self.assertEqual(4, self.extended_proto.ByteSize())
+ child.foreign_message_int = 128
+ self.assertEqual(5, self.extended_proto.ByteSize())
+ self.extended_proto.ClearExtension(extension)
+ self.assertEqual(0, self.extended_proto.ByteSize())
+
+ def testCacheInvalidationForRepeatedMessage(self):
+ # Test non-extension.
+ child0 = self.proto.repeated_foreign_message.add()
+ self.assertEqual(3, self.proto.ByteSize())
+ self.proto.repeated_foreign_message.add()
+ self.assertEqual(6, self.proto.ByteSize())
+ child0.c = 1
+ self.assertEqual(8, self.proto.ByteSize())
+ self.proto.ClearField('repeated_foreign_message')
+ self.assertEqual(0, self.proto.ByteSize())
+
+ # Test within extension.
+ extension = more_extensions_pb2.repeated_message_extension
+ child_list = self.extended_proto.Extensions[extension]
+ child0 = child_list.add()
+ self.assertEqual(2, self.extended_proto.ByteSize())
+ child_list.add()
+ self.assertEqual(4, self.extended_proto.ByteSize())
+ child0.foreign_message_int = 1
+ self.assertEqual(6, self.extended_proto.ByteSize())
+ child0.ClearField('foreign_message_int')
+ self.assertEqual(4, self.extended_proto.ByteSize())
+ self.extended_proto.ClearExtension(extension)
+ self.assertEqual(0, self.extended_proto.ByteSize())
+
+ def testPackedRepeatedScalars(self):
+ self.assertEqual(0, self.packed_proto.ByteSize())
+
+ self.packed_proto.packed_int32.append(10) # 1 byte.
+ self.packed_proto.packed_int32.append(128) # 2 bytes.
+ # The tag is 2 bytes (the field number is 90), and the varint
+ # storing the length is 1 byte.
+ int_size = 1 + 2 + 3
+ self.assertEqual(int_size, self.packed_proto.ByteSize())
+
+ self.packed_proto.packed_double.append(4.2) # 8 bytes
+ self.packed_proto.packed_double.append(3.25) # 8 bytes
+ # 2 more tag bytes, 1 more length byte.
+ double_size = 8 + 8 + 3
+ self.assertEqual(int_size+double_size, self.packed_proto.ByteSize())
+
+ self.packed_proto.ClearField('packed_int32')
+ self.assertEqual(double_size, self.packed_proto.ByteSize())
+
+ def testPackedExtensions(self):
+ self.assertEqual(0, self.packed_extended_proto.ByteSize())
+ extension = self.packed_extended_proto.Extensions[
+ unittest_pb2.packed_fixed32_extension]
+ extension.extend([1, 2, 3, 4]) # 16 bytes
+ # Tag is 3 bytes.
+ self.assertEqual(19, self.packed_extended_proto.ByteSize())
+
+
+# Issues to be sure to cover include:
+# * Handling of unrecognized tags ("uninterpreted_bytes").
+# * Handling of MessageSets.
+# * Consistent ordering of tags in the wire format,
+# including ordering between extensions and non-extension
+# fields.
+# * Consistent serialization of negative numbers, especially
+# negative int32s.
+# * Handling of empty submessages (with and without "has"
+# bits set).
+
+class SerializationTest(unittest.TestCase):
+
+ def testSerializeEmtpyMessage(self):
+ first_proto = unittest_pb2.TestAllTypes()
+ second_proto = unittest_pb2.TestAllTypes()
+ serialized = first_proto.SerializeToString()
+ self.assertEqual(first_proto.ByteSize(), len(serialized))
+ self.assertEqual(
+ len(serialized),
+ second_proto.MergeFromString(serialized))
+ self.assertEqual(first_proto, second_proto)
+
+ def testSerializeAllFields(self):
+ first_proto = unittest_pb2.TestAllTypes()
+ second_proto = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(first_proto)
+ serialized = first_proto.SerializeToString()
+ self.assertEqual(first_proto.ByteSize(), len(serialized))
+ self.assertEqual(
+ len(serialized),
+ second_proto.MergeFromString(serialized))
+ self.assertEqual(first_proto, second_proto)
+
+ def testSerializeAllExtensions(self):
+ first_proto = unittest_pb2.TestAllExtensions()
+ second_proto = unittest_pb2.TestAllExtensions()
+ test_util.SetAllExtensions(first_proto)
+ serialized = first_proto.SerializeToString()
+ self.assertEqual(
+ len(serialized),
+ second_proto.MergeFromString(serialized))
+ self.assertEqual(first_proto, second_proto)
+
+ def testSerializeWithOptionalGroup(self):
+ first_proto = unittest_pb2.TestAllTypes()
+ second_proto = unittest_pb2.TestAllTypes()
+ first_proto.optionalgroup.a = 242
+ serialized = first_proto.SerializeToString()
+ self.assertEqual(
+ len(serialized),
+ second_proto.MergeFromString(serialized))
+ self.assertEqual(first_proto, second_proto)
+
+ def testSerializeNegativeValues(self):
+ first_proto = unittest_pb2.TestAllTypes()
+
+ first_proto.optional_int32 = -1
+ first_proto.optional_int64 = -(2 << 40)
+ first_proto.optional_sint32 = -3
+ first_proto.optional_sint64 = -(4 << 40)
+ first_proto.optional_sfixed32 = -5
+ first_proto.optional_sfixed64 = -(6 << 40)
+
+ second_proto = unittest_pb2.TestAllTypes.FromString(
+ first_proto.SerializeToString())
+
+ self.assertEqual(first_proto, second_proto)
+
+ def testParseTruncated(self):
+ # This test is only applicable for the Python implementation of the API.
+ if api_implementation.Type() != 'python':
+ return
+
+ first_proto = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(first_proto)
+ serialized = first_proto.SerializeToString()
+
+ for truncation_point in range(len(serialized) + 1):
+ try:
+ second_proto = unittest_pb2.TestAllTypes()
+ unknown_fields = unittest_pb2.TestEmptyMessage()
+ pos = second_proto._InternalParse(serialized, 0, truncation_point)
+ # If we didn't raise an error then we read exactly the amount expected.
+ self.assertEqual(truncation_point, pos)
+
+ # Parsing to unknown fields should not throw if parsing to known fields
+ # did not.
+ try:
+ pos2 = unknown_fields._InternalParse(serialized, 0, truncation_point)
+ self.assertEqual(truncation_point, pos2)
+ except message.DecodeError:
+ self.fail('Parsing unknown fields failed when parsing known fields '
+ 'did not.')
+ except message.DecodeError:
+ # Parsing unknown fields should also fail.
+ self.assertRaises(message.DecodeError, unknown_fields._InternalParse,
+ serialized, 0, truncation_point)
+
+ def testCanonicalSerializationOrder(self):
+ proto = more_messages_pb2.OutOfOrderFields()
+ # These are also their tag numbers. Even though we're setting these in
+ # reverse-tag order AND they're listed in reverse tag-order in the .proto
+ # file, they should nonetheless be serialized in tag order.
+ proto.optional_sint32 = 5
+ proto.Extensions[more_messages_pb2.optional_uint64] = 4
+ proto.optional_uint32 = 3
+ proto.Extensions[more_messages_pb2.optional_int64] = 2
+ proto.optional_int32 = 1
+ serialized = proto.SerializeToString()
+ self.assertEqual(proto.ByteSize(), len(serialized))
+ d = _MiniDecoder(serialized)
+ ReadTag = d.ReadFieldNumberAndWireType
+ self.assertEqual((1, wire_format.WIRETYPE_VARINT), ReadTag())
+ self.assertEqual(1, d.ReadInt32())
+ self.assertEqual((2, wire_format.WIRETYPE_VARINT), ReadTag())
+ self.assertEqual(2, d.ReadInt64())
+ self.assertEqual((3, wire_format.WIRETYPE_VARINT), ReadTag())
+ self.assertEqual(3, d.ReadUInt32())
+ self.assertEqual((4, wire_format.WIRETYPE_VARINT), ReadTag())
+ self.assertEqual(4, d.ReadUInt64())
+ self.assertEqual((5, wire_format.WIRETYPE_VARINT), ReadTag())
+ self.assertEqual(5, d.ReadSInt32())
+
+ def testCanonicalSerializationOrderSameAsCpp(self):
+ # Copy of the same test we use for C++.
+ proto = unittest_pb2.TestFieldOrderings()
+ test_util.SetAllFieldsAndExtensions(proto)
+ serialized = proto.SerializeToString()
+ test_util.ExpectAllFieldsAndExtensionsInOrder(serialized)
+
+ def testMergeFromStringWhenFieldsAlreadySet(self):
+ first_proto = unittest_pb2.TestAllTypes()
+ first_proto.repeated_string.append('foobar')
+ first_proto.optional_int32 = 23
+ first_proto.optional_nested_message.bb = 42
+ serialized = first_proto.SerializeToString()
+
+ second_proto = unittest_pb2.TestAllTypes()
+ second_proto.repeated_string.append('baz')
+ second_proto.optional_int32 = 100
+ second_proto.optional_nested_message.bb = 999
+
+ bytes_parsed = second_proto.MergeFromString(serialized)
+ self.assertEqual(len(serialized), bytes_parsed)
+
+ # Ensure that we append to repeated fields.
+ self.assertEqual(['baz', 'foobar'], list(second_proto.repeated_string))
+ # Ensure that we overwrite nonrepeatd scalars.
+ self.assertEqual(23, second_proto.optional_int32)
+ # Ensure that we recursively call MergeFromString() on
+ # submessages.
+ self.assertEqual(42, second_proto.optional_nested_message.bb)
+
+ def testMessageSetWireFormat(self):
+ proto = message_set_extensions_pb2.TestMessageSet()
+ extension_message1 = message_set_extensions_pb2.TestMessageSetExtension1
+ extension_message2 = message_set_extensions_pb2.TestMessageSetExtension2
+ extension1 = extension_message1.message_set_extension
+ extension2 = extension_message2.message_set_extension
+ extension3 = message_set_extensions_pb2.message_set_extension3
+ proto.Extensions[extension1].i = 123
+ proto.Extensions[extension2].str = 'foo'
+ proto.Extensions[extension3].text = 'bar'
+
+ # Serialize using the MessageSet wire format (this is specified in the
+ # .proto file).
+ serialized = proto.SerializeToString()
+
+ raw = unittest_mset_pb2.RawMessageSet()
+ self.assertEqual(False,
+ raw.DESCRIPTOR.GetOptions().message_set_wire_format)
+ self.assertEqual(
+ len(serialized),
+ raw.MergeFromString(serialized))
+ self.assertEqual(3, len(raw.item))
+
+ message1 = message_set_extensions_pb2.TestMessageSetExtension1()
+ self.assertEqual(
+ len(raw.item[0].message),
+ message1.MergeFromString(raw.item[0].message))
+ self.assertEqual(123, message1.i)
+
+ message2 = message_set_extensions_pb2.TestMessageSetExtension2()
+ self.assertEqual(
+ len(raw.item[1].message),
+ message2.MergeFromString(raw.item[1].message))
+ self.assertEqual('foo', message2.str)
+
+ message3 = message_set_extensions_pb2.TestMessageSetExtension3()
+ self.assertEqual(
+ len(raw.item[2].message),
+ message3.MergeFromString(raw.item[2].message))
+ self.assertEqual('bar', message3.text)
+
+ # Deserialize using the MessageSet wire format.
+ proto2 = message_set_extensions_pb2.TestMessageSet()
+ self.assertEqual(
+ len(serialized),
+ proto2.MergeFromString(serialized))
+ self.assertEqual(123, proto2.Extensions[extension1].i)
+ self.assertEqual('foo', proto2.Extensions[extension2].str)
+ self.assertEqual('bar', proto2.Extensions[extension3].text)
+
+ # Check byte size.
+ self.assertEqual(proto2.ByteSize(), len(serialized))
+ self.assertEqual(proto.ByteSize(), len(serialized))
+
+ def testMessageSetWireFormatUnknownExtension(self):
+ # Create a message using the message set wire format with an unknown
+ # message.
+ raw = unittest_mset_pb2.RawMessageSet()
+
+ # Add an item.
+ item = raw.item.add()
+ item.type_id = 98418603
+ extension_message1 = message_set_extensions_pb2.TestMessageSetExtension1
+ message1 = message_set_extensions_pb2.TestMessageSetExtension1()
+ message1.i = 12345
+ item.message = message1.SerializeToString()
+
+ # Add a second, unknown extension.
+ item = raw.item.add()
+ item.type_id = 98418604
+ extension_message1 = message_set_extensions_pb2.TestMessageSetExtension1
+ message1 = message_set_extensions_pb2.TestMessageSetExtension1()
+ message1.i = 12346
+ item.message = message1.SerializeToString()
+
+ # Add another unknown extension.
+ item = raw.item.add()
+ item.type_id = 98418605
+ message1 = message_set_extensions_pb2.TestMessageSetExtension2()
+ message1.str = 'foo'
+ item.message = message1.SerializeToString()
+
+ serialized = raw.SerializeToString()
+
+ # Parse message using the message set wire format.
+ proto = message_set_extensions_pb2.TestMessageSet()
+ self.assertEqual(
+ len(serialized),
+ proto.MergeFromString(serialized))
+
+ # Check that the message parsed well.
+ extension_message1 = message_set_extensions_pb2.TestMessageSetExtension1
+ extension1 = extension_message1.message_set_extension
+ self.assertEqual(12345, proto.Extensions[extension1].i)
+
+ def testUnknownFields(self):
+ proto = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(proto)
+
+ serialized = proto.SerializeToString()
+
+ # The empty message should be parsable with all of the fields
+ # unknown.
+ proto2 = unittest_pb2.TestEmptyMessage()
+
+ # Parsing this message should succeed.
+ self.assertEqual(
+ len(serialized),
+ proto2.MergeFromString(serialized))
+
+ # Now test with a int64 field set.
+ proto = unittest_pb2.TestAllTypes()
+ proto.optional_int64 = 0x0fffffffffffffff
+ serialized = proto.SerializeToString()
+ # The empty message should be parsable with all of the fields
+ # unknown.
+ proto2 = unittest_pb2.TestEmptyMessage()
+ # Parsing this message should succeed.
+ self.assertEqual(
+ len(serialized),
+ proto2.MergeFromString(serialized))
+
+ def _CheckRaises(self, exc_class, callable_obj, exception):
+ """This method checks if the excpetion type and message are as expected."""
+ try:
+ callable_obj()
+ except exc_class as ex:
+ # Check if the exception message is the right one.
+ self.assertEqual(exception, str(ex))
+ return
+ else:
+ raise self.failureException('%s not raised' % str(exc_class))
+
+ def testSerializeUninitialized(self):
+ proto = unittest_pb2.TestRequired()
+ self._CheckRaises(
+ message.EncodeError,
+ proto.SerializeToString,
+ 'Message protobuf_unittest.TestRequired is missing required fields: '
+ 'a,b,c')
+ # Shouldn't raise exceptions.
+ partial = proto.SerializePartialToString()
+
+ proto2 = unittest_pb2.TestRequired()
+ self.assertFalse(proto2.HasField('a'))
+ # proto2 ParseFromString does not check that required fields are set.
+ proto2.ParseFromString(partial)
+ self.assertFalse(proto2.HasField('a'))
+
+ proto.a = 1
+ self._CheckRaises(
+ message.EncodeError,
+ proto.SerializeToString,
+ 'Message protobuf_unittest.TestRequired is missing required fields: b,c')
+ # Shouldn't raise exceptions.
+ partial = proto.SerializePartialToString()
+
+ proto.b = 2
+ self._CheckRaises(
+ message.EncodeError,
+ proto.SerializeToString,
+ 'Message protobuf_unittest.TestRequired is missing required fields: c')
+ # Shouldn't raise exceptions.
+ partial = proto.SerializePartialToString()
+
+ proto.c = 3
+ serialized = proto.SerializeToString()
+ # Shouldn't raise exceptions.
+ partial = proto.SerializePartialToString()
+
+ proto2 = unittest_pb2.TestRequired()
+ self.assertEqual(
+ len(serialized),
+ proto2.MergeFromString(serialized))
+ self.assertEqual(1, proto2.a)
+ self.assertEqual(2, proto2.b)
+ self.assertEqual(3, proto2.c)
+ self.assertEqual(
+ len(partial),
+ proto2.MergeFromString(partial))
+ self.assertEqual(1, proto2.a)
+ self.assertEqual(2, proto2.b)
+ self.assertEqual(3, proto2.c)
+
+ def testSerializeUninitializedSubMessage(self):
+ proto = unittest_pb2.TestRequiredForeign()
+
+ # Sub-message doesn't exist yet, so this succeeds.
+ proto.SerializeToString()
+
+ proto.optional_message.a = 1
+ self._CheckRaises(
+ message.EncodeError,
+ proto.SerializeToString,
+ 'Message protobuf_unittest.TestRequiredForeign '
+ 'is missing required fields: '
+ 'optional_message.b,optional_message.c')
+
+ proto.optional_message.b = 2
+ proto.optional_message.c = 3
+ proto.SerializeToString()
+
+ proto.repeated_message.add().a = 1
+ proto.repeated_message.add().b = 2
+ self._CheckRaises(
+ message.EncodeError,
+ proto.SerializeToString,
+ 'Message protobuf_unittest.TestRequiredForeign is missing required fields: '
+ 'repeated_message[0].b,repeated_message[0].c,'
+ 'repeated_message[1].a,repeated_message[1].c')
+
+ proto.repeated_message[0].b = 2
+ proto.repeated_message[0].c = 3
+ proto.repeated_message[1].a = 1
+ proto.repeated_message[1].c = 3
+ proto.SerializeToString()
+
+ def testSerializeAllPackedFields(self):
+ first_proto = unittest_pb2.TestPackedTypes()
+ second_proto = unittest_pb2.TestPackedTypes()
+ test_util.SetAllPackedFields(first_proto)
+ serialized = first_proto.SerializeToString()
+ self.assertEqual(first_proto.ByteSize(), len(serialized))
+ bytes_read = second_proto.MergeFromString(serialized)
+ self.assertEqual(second_proto.ByteSize(), bytes_read)
+ self.assertEqual(first_proto, second_proto)
+
+ def testSerializeAllPackedExtensions(self):
+ first_proto = unittest_pb2.TestPackedExtensions()
+ second_proto = unittest_pb2.TestPackedExtensions()
+ test_util.SetAllPackedExtensions(first_proto)
+ serialized = first_proto.SerializeToString()
+ bytes_read = second_proto.MergeFromString(serialized)
+ self.assertEqual(second_proto.ByteSize(), bytes_read)
+ self.assertEqual(first_proto, second_proto)
+
+ def testMergePackedFromStringWhenSomeFieldsAlreadySet(self):
+ first_proto = unittest_pb2.TestPackedTypes()
+ first_proto.packed_int32.extend([1, 2])
+ first_proto.packed_double.append(3.0)
+ serialized = first_proto.SerializeToString()
+
+ second_proto = unittest_pb2.TestPackedTypes()
+ second_proto.packed_int32.append(3)
+ second_proto.packed_double.extend([1.0, 2.0])
+ second_proto.packed_sint32.append(4)
+
+ self.assertEqual(
+ len(serialized),
+ second_proto.MergeFromString(serialized))
+ self.assertEqual([3, 1, 2], second_proto.packed_int32)
+ self.assertEqual([1.0, 2.0, 3.0], second_proto.packed_double)
+ self.assertEqual([4], second_proto.packed_sint32)
+
+ def testPackedFieldsWireFormat(self):
+ proto = unittest_pb2.TestPackedTypes()
+ proto.packed_int32.extend([1, 2, 150, 3]) # 1 + 1 + 2 + 1 bytes
+ proto.packed_double.extend([1.0, 1000.0]) # 8 + 8 bytes
+ proto.packed_float.append(2.0) # 4 bytes, will be before double
+ serialized = proto.SerializeToString()
+ self.assertEqual(proto.ByteSize(), len(serialized))
+ d = _MiniDecoder(serialized)
+ ReadTag = d.ReadFieldNumberAndWireType
+ self.assertEqual((90, wire_format.WIRETYPE_LENGTH_DELIMITED), ReadTag())
+ self.assertEqual(1+1+1+2, d.ReadInt32())
+ self.assertEqual(1, d.ReadInt32())
+ self.assertEqual(2, d.ReadInt32())
+ self.assertEqual(150, d.ReadInt32())
+ self.assertEqual(3, d.ReadInt32())
+ self.assertEqual((100, wire_format.WIRETYPE_LENGTH_DELIMITED), ReadTag())
+ self.assertEqual(4, d.ReadInt32())
+ self.assertEqual(2.0, d.ReadFloat())
+ self.assertEqual((101, wire_format.WIRETYPE_LENGTH_DELIMITED), ReadTag())
+ self.assertEqual(8+8, d.ReadInt32())
+ self.assertEqual(1.0, d.ReadDouble())
+ self.assertEqual(1000.0, d.ReadDouble())
+ self.assertTrue(d.EndOfStream())
+
+ def testParsePackedFromUnpacked(self):
+ unpacked = unittest_pb2.TestUnpackedTypes()
+ test_util.SetAllUnpackedFields(unpacked)
+ packed = unittest_pb2.TestPackedTypes()
+ serialized = unpacked.SerializeToString()
+ self.assertEqual(
+ len(serialized),
+ packed.MergeFromString(serialized))
+ expected = unittest_pb2.TestPackedTypes()
+ test_util.SetAllPackedFields(expected)
+ self.assertEqual(expected, packed)
+
+ def testParseUnpackedFromPacked(self):
+ packed = unittest_pb2.TestPackedTypes()
+ test_util.SetAllPackedFields(packed)
+ unpacked = unittest_pb2.TestUnpackedTypes()
+ serialized = packed.SerializeToString()
+ self.assertEqual(
+ len(serialized),
+ unpacked.MergeFromString(serialized))
+ expected = unittest_pb2.TestUnpackedTypes()
+ test_util.SetAllUnpackedFields(expected)
+ self.assertEqual(expected, unpacked)
+
+ def testFieldNumbers(self):
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(unittest_pb2.TestAllTypes.NestedMessage.BB_FIELD_NUMBER, 1)
+ self.assertEqual(unittest_pb2.TestAllTypes.OPTIONAL_INT32_FIELD_NUMBER, 1)
+ self.assertEqual(unittest_pb2.TestAllTypes.OPTIONALGROUP_FIELD_NUMBER, 16)
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.OPTIONAL_NESTED_MESSAGE_FIELD_NUMBER, 18)
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.OPTIONAL_NESTED_ENUM_FIELD_NUMBER, 21)
+ self.assertEqual(unittest_pb2.TestAllTypes.REPEATED_INT32_FIELD_NUMBER, 31)
+ self.assertEqual(unittest_pb2.TestAllTypes.REPEATEDGROUP_FIELD_NUMBER, 46)
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.REPEATED_NESTED_MESSAGE_FIELD_NUMBER, 48)
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.REPEATED_NESTED_ENUM_FIELD_NUMBER, 51)
+
+ def testExtensionFieldNumbers(self):
+ self.assertEqual(unittest_pb2.TestRequired.single.number, 1000)
+ self.assertEqual(unittest_pb2.TestRequired.SINGLE_FIELD_NUMBER, 1000)
+ self.assertEqual(unittest_pb2.TestRequired.multi.number, 1001)
+ self.assertEqual(unittest_pb2.TestRequired.MULTI_FIELD_NUMBER, 1001)
+ self.assertEqual(unittest_pb2.optional_int32_extension.number, 1)
+ self.assertEqual(unittest_pb2.OPTIONAL_INT32_EXTENSION_FIELD_NUMBER, 1)
+ self.assertEqual(unittest_pb2.optionalgroup_extension.number, 16)
+ self.assertEqual(unittest_pb2.OPTIONALGROUP_EXTENSION_FIELD_NUMBER, 16)
+ self.assertEqual(unittest_pb2.optional_nested_message_extension.number, 18)
+ self.assertEqual(
+ unittest_pb2.OPTIONAL_NESTED_MESSAGE_EXTENSION_FIELD_NUMBER, 18)
+ self.assertEqual(unittest_pb2.optional_nested_enum_extension.number, 21)
+ self.assertEqual(unittest_pb2.OPTIONAL_NESTED_ENUM_EXTENSION_FIELD_NUMBER,
+ 21)
+ self.assertEqual(unittest_pb2.repeated_int32_extension.number, 31)
+ self.assertEqual(unittest_pb2.REPEATED_INT32_EXTENSION_FIELD_NUMBER, 31)
+ self.assertEqual(unittest_pb2.repeatedgroup_extension.number, 46)
+ self.assertEqual(unittest_pb2.REPEATEDGROUP_EXTENSION_FIELD_NUMBER, 46)
+ self.assertEqual(unittest_pb2.repeated_nested_message_extension.number, 48)
+ self.assertEqual(
+ unittest_pb2.REPEATED_NESTED_MESSAGE_EXTENSION_FIELD_NUMBER, 48)
+ self.assertEqual(unittest_pb2.repeated_nested_enum_extension.number, 51)
+ self.assertEqual(unittest_pb2.REPEATED_NESTED_ENUM_EXTENSION_FIELD_NUMBER,
+ 51)
+
+ def testInitKwargs(self):
+ proto = unittest_pb2.TestAllTypes(
+ optional_int32=1,
+ optional_string='foo',
+ optional_bool=True,
+ optional_bytes=b'bar',
+ optional_nested_message=unittest_pb2.TestAllTypes.NestedMessage(bb=1),
+ optional_foreign_message=unittest_pb2.ForeignMessage(c=1),
+ optional_nested_enum=unittest_pb2.TestAllTypes.FOO,
+ optional_foreign_enum=unittest_pb2.FOREIGN_FOO,
+ repeated_int32=[1, 2, 3])
+ self.assertTrue(proto.IsInitialized())
+ self.assertTrue(proto.HasField('optional_int32'))
+ self.assertTrue(proto.HasField('optional_string'))
+ self.assertTrue(proto.HasField('optional_bool'))
+ self.assertTrue(proto.HasField('optional_bytes'))
+ self.assertTrue(proto.HasField('optional_nested_message'))
+ self.assertTrue(proto.HasField('optional_foreign_message'))
+ self.assertTrue(proto.HasField('optional_nested_enum'))
+ self.assertTrue(proto.HasField('optional_foreign_enum'))
+ self.assertEqual(1, proto.optional_int32)
+ self.assertEqual('foo', proto.optional_string)
+ self.assertEqual(True, proto.optional_bool)
+ self.assertEqual(b'bar', proto.optional_bytes)
+ self.assertEqual(1, proto.optional_nested_message.bb)
+ self.assertEqual(1, proto.optional_foreign_message.c)
+ self.assertEqual(unittest_pb2.TestAllTypes.FOO,
+ proto.optional_nested_enum)
+ self.assertEqual(unittest_pb2.FOREIGN_FOO, proto.optional_foreign_enum)
+ self.assertEqual([1, 2, 3], proto.repeated_int32)
+
+ def testInitArgsUnknownFieldName(self):
+ def InitalizeEmptyMessageWithExtraKeywordArg():
+ unused_proto = unittest_pb2.TestEmptyMessage(unknown='unknown')
+ self._CheckRaises(
+ ValueError,
+ InitalizeEmptyMessageWithExtraKeywordArg,
+ 'Protocol message TestEmptyMessage has no "unknown" field.')
+
+ def testInitRequiredKwargs(self):
+ proto = unittest_pb2.TestRequired(a=1, b=1, c=1)
+ self.assertTrue(proto.IsInitialized())
+ self.assertTrue(proto.HasField('a'))
+ self.assertTrue(proto.HasField('b'))
+ self.assertTrue(proto.HasField('c'))
+ self.assertTrue(not proto.HasField('dummy2'))
+ self.assertEqual(1, proto.a)
+ self.assertEqual(1, proto.b)
+ self.assertEqual(1, proto.c)
+
+ def testInitRequiredForeignKwargs(self):
+ proto = unittest_pb2.TestRequiredForeign(
+ optional_message=unittest_pb2.TestRequired(a=1, b=1, c=1))
+ self.assertTrue(proto.IsInitialized())
+ self.assertTrue(proto.HasField('optional_message'))
+ self.assertTrue(proto.optional_message.IsInitialized())
+ self.assertTrue(proto.optional_message.HasField('a'))
+ self.assertTrue(proto.optional_message.HasField('b'))
+ self.assertTrue(proto.optional_message.HasField('c'))
+ self.assertTrue(not proto.optional_message.HasField('dummy2'))
+ self.assertEqual(unittest_pb2.TestRequired(a=1, b=1, c=1),
+ proto.optional_message)
+ self.assertEqual(1, proto.optional_message.a)
+ self.assertEqual(1, proto.optional_message.b)
+ self.assertEqual(1, proto.optional_message.c)
+
+ def testInitRepeatedKwargs(self):
+ proto = unittest_pb2.TestAllTypes(repeated_int32=[1, 2, 3])
+ self.assertTrue(proto.IsInitialized())
+ self.assertEqual(1, proto.repeated_int32[0])
+ self.assertEqual(2, proto.repeated_int32[1])
+ self.assertEqual(3, proto.repeated_int32[2])
+
+
+class OptionsTest(unittest.TestCase):
+
+ def testMessageOptions(self):
+ proto = message_set_extensions_pb2.TestMessageSet()
+ self.assertEqual(True,
+ proto.DESCRIPTOR.GetOptions().message_set_wire_format)
+ proto = unittest_pb2.TestAllTypes()
+ self.assertEqual(False,
+ proto.DESCRIPTOR.GetOptions().message_set_wire_format)
+
+ def testPackedOptions(self):
+ proto = unittest_pb2.TestAllTypes()
+ proto.optional_int32 = 1
+ proto.optional_double = 3.0
+ for field_descriptor, _ in proto.ListFields():
+ self.assertEqual(False, field_descriptor.GetOptions().packed)
+
+ proto = unittest_pb2.TestPackedTypes()
+ proto.packed_int32.append(1)
+ proto.packed_double.append(3.0)
+ for field_descriptor, _ in proto.ListFields():
+ self.assertEqual(True, field_descriptor.GetOptions().packed)
+ self.assertEqual(descriptor.FieldDescriptor.LABEL_REPEATED,
+ field_descriptor.label)
+
+
+
+class ClassAPITest(unittest.TestCase):
+
+ @unittest.skipIf(
+ api_implementation.Type() == 'cpp' and api_implementation.Version() == 2,
+ 'C++ implementation requires a call to MakeDescriptor()')
+ def testMakeClassWithNestedDescriptor(self):
+ leaf_desc = descriptor.Descriptor('leaf', 'package.parent.child.leaf', '',
+ containing_type=None, fields=[],
+ nested_types=[], enum_types=[],
+ extensions=[])
+ child_desc = descriptor.Descriptor('child', 'package.parent.child', '',
+ containing_type=None, fields=[],
+ nested_types=[leaf_desc], enum_types=[],
+ extensions=[])
+ sibling_desc = descriptor.Descriptor('sibling', 'package.parent.sibling',
+ '', containing_type=None, fields=[],
+ nested_types=[], enum_types=[],
+ extensions=[])
+ parent_desc = descriptor.Descriptor('parent', 'package.parent', '',
+ containing_type=None, fields=[],
+ nested_types=[child_desc, sibling_desc],
+ enum_types=[], extensions=[])
+ message_class = reflection.MakeClass(parent_desc)
+ self.assertIn('child', message_class.__dict__)
+ self.assertIn('sibling', message_class.__dict__)
+ self.assertIn('leaf', message_class.child.__dict__)
+
+ def _GetSerializedFileDescriptor(self, name):
+ """Get a serialized representation of a test FileDescriptorProto.
+
+ Args:
+ name: All calls to this must use a unique message name, to avoid
+ collisions in the cpp descriptor pool.
+ Returns:
+ A string containing the serialized form of a test FileDescriptorProto.
+ """
+ file_descriptor_str = (
+ 'message_type {'
+ ' name: "' + name + '"'
+ ' field {'
+ ' name: "flat"'
+ ' number: 1'
+ ' label: LABEL_REPEATED'
+ ' type: TYPE_UINT32'
+ ' }'
+ ' field {'
+ ' name: "bar"'
+ ' number: 2'
+ ' label: LABEL_OPTIONAL'
+ ' type: TYPE_MESSAGE'
+ ' type_name: "Bar"'
+ ' }'
+ ' nested_type {'
+ ' name: "Bar"'
+ ' field {'
+ ' name: "baz"'
+ ' number: 3'
+ ' label: LABEL_OPTIONAL'
+ ' type: TYPE_MESSAGE'
+ ' type_name: "Baz"'
+ ' }'
+ ' nested_type {'
+ ' name: "Baz"'
+ ' enum_type {'
+ ' name: "deep_enum"'
+ ' value {'
+ ' name: "VALUE_A"'
+ ' number: 0'
+ ' }'
+ ' }'
+ ' field {'
+ ' name: "deep"'
+ ' number: 4'
+ ' label: LABEL_OPTIONAL'
+ ' type: TYPE_UINT32'
+ ' }'
+ ' }'
+ ' }'
+ '}')
+ file_descriptor = descriptor_pb2.FileDescriptorProto()
+ text_format.Merge(file_descriptor_str, file_descriptor)
+ return file_descriptor.SerializeToString()
+
+ def testParsingFlatClassWithExplicitClassDeclaration(self):
+ """Test that the generated class can parse a flat message."""
+ # TODO(xiaofeng): This test fails with cpp implemetnation in the call
+ # of six.with_metaclass(). The other two callsites of with_metaclass
+ # in this file are both excluded from cpp test, so it might be expected
+ # to fail. Need someone more familiar with the python code to take a
+ # look at this.
+ if api_implementation.Type() != 'python':
+ return
+ file_descriptor = descriptor_pb2.FileDescriptorProto()
+ file_descriptor.ParseFromString(self._GetSerializedFileDescriptor('A'))
+ msg_descriptor = descriptor.MakeDescriptor(
+ file_descriptor.message_type[0])
+
+ class MessageClass(six.with_metaclass(reflection.GeneratedProtocolMessageType, message.Message)):
+ DESCRIPTOR = msg_descriptor
+ msg = MessageClass()
+ msg_str = (
+ 'flat: 0 '
+ 'flat: 1 '
+ 'flat: 2 ')
+ text_format.Merge(msg_str, msg)
+ self.assertEqual(msg.flat, [0, 1, 2])
+
+ def testParsingFlatClass(self):
+ """Test that the generated class can parse a flat message."""
+ file_descriptor = descriptor_pb2.FileDescriptorProto()
+ file_descriptor.ParseFromString(self._GetSerializedFileDescriptor('B'))
+ msg_descriptor = descriptor.MakeDescriptor(
+ file_descriptor.message_type[0])
+ msg_class = reflection.MakeClass(msg_descriptor)
+ msg = msg_class()
+ msg_str = (
+ 'flat: 0 '
+ 'flat: 1 '
+ 'flat: 2 ')
+ text_format.Merge(msg_str, msg)
+ self.assertEqual(msg.flat, [0, 1, 2])
+
+ def testParsingNestedClass(self):
+ """Test that the generated class can parse a nested message."""
+ file_descriptor = descriptor_pb2.FileDescriptorProto()
+ file_descriptor.ParseFromString(self._GetSerializedFileDescriptor('C'))
+ msg_descriptor = descriptor.MakeDescriptor(
+ file_descriptor.message_type[0])
+ msg_class = reflection.MakeClass(msg_descriptor)
+ msg = msg_class()
+ msg_str = (
+ 'bar {'
+ ' baz {'
+ ' deep: 4'
+ ' }'
+ '}')
+ text_format.Merge(msg_str, msg)
+ self.assertEqual(msg.bar.baz.deep, 4)
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/service_reflection_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/service_reflection_test.py
new file mode 100755
index 0000000000..62900b1d15
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/service_reflection_test.py
@@ -0,0 +1,140 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests for google.protobuf.internal.service_reflection."""
+
+__author__ = 'petar@google.com (Petar Petrov)'
+
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import unittest_pb2
+from google.protobuf import service_reflection
+from google.protobuf import service
+
+
+class FooUnitTest(unittest.TestCase):
+
+ def testService(self):
+ class MockRpcChannel(service.RpcChannel):
+ def CallMethod(self, method, controller, request, response, callback):
+ self.method = method
+ self.controller = controller
+ self.request = request
+ callback(response)
+
+ class MockRpcController(service.RpcController):
+ def SetFailed(self, msg):
+ self.failure_message = msg
+
+ self.callback_response = None
+
+ class MyService(unittest_pb2.TestService):
+ pass
+
+ self.callback_response = None
+
+ def MyCallback(response):
+ self.callback_response = response
+
+ rpc_controller = MockRpcController()
+ channel = MockRpcChannel()
+ srvc = MyService()
+ srvc.Foo(rpc_controller, unittest_pb2.FooRequest(), MyCallback)
+ self.assertEqual('Method Foo not implemented.',
+ rpc_controller.failure_message)
+ self.assertEqual(None, self.callback_response)
+
+ rpc_controller.failure_message = None
+
+ service_descriptor = unittest_pb2.TestService.GetDescriptor()
+ srvc.CallMethod(service_descriptor.methods[1], rpc_controller,
+ unittest_pb2.BarRequest(), MyCallback)
+ self.assertEqual('Method Bar not implemented.',
+ rpc_controller.failure_message)
+ self.assertEqual(None, self.callback_response)
+
+ class MyServiceImpl(unittest_pb2.TestService):
+ def Foo(self, rpc_controller, request, done):
+ self.foo_called = True
+ def Bar(self, rpc_controller, request, done):
+ self.bar_called = True
+
+ srvc = MyServiceImpl()
+ rpc_controller.failure_message = None
+ srvc.Foo(rpc_controller, unittest_pb2.FooRequest(), MyCallback)
+ self.assertEqual(None, rpc_controller.failure_message)
+ self.assertEqual(True, srvc.foo_called)
+
+ rpc_controller.failure_message = None
+ srvc.CallMethod(service_descriptor.methods[1], rpc_controller,
+ unittest_pb2.BarRequest(), MyCallback)
+ self.assertEqual(None, rpc_controller.failure_message)
+ self.assertEqual(True, srvc.bar_called)
+
+ def testServiceStub(self):
+ class MockRpcChannel(service.RpcChannel):
+ def CallMethod(self, method, controller, request,
+ response_class, callback):
+ self.method = method
+ self.controller = controller
+ self.request = request
+ callback(response_class())
+
+ self.callback_response = None
+
+ def MyCallback(response):
+ self.callback_response = response
+
+ channel = MockRpcChannel()
+ stub = unittest_pb2.TestService_Stub(channel)
+ rpc_controller = 'controller'
+ request = 'request'
+
+ # GetDescriptor now static, still works as instance method for compatibility
+ self.assertEqual(unittest_pb2.TestService_Stub.GetDescriptor(),
+ stub.GetDescriptor())
+
+ # Invoke method.
+ stub.Foo(rpc_controller, request, MyCallback)
+
+ self.assertIsInstance(self.callback_response, unittest_pb2.FooResponse)
+ self.assertEqual(request, channel.request)
+ self.assertEqual(rpc_controller, channel.controller)
+ self.assertEqual(stub.GetDescriptor().methods[0], channel.method)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/symbol_database_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/symbol_database_test.py
new file mode 100644
index 0000000000..4f5173b2a2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/symbol_database_test.py
@@ -0,0 +1,131 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests for google.protobuf.symbol_database."""
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import unittest_pb2
+from google.protobuf import descriptor
+from google.protobuf import descriptor_pool
+from google.protobuf import symbol_database
+
+
+class SymbolDatabaseTest(unittest.TestCase):
+
+ def _Database(self):
+ if descriptor._USE_C_DESCRIPTORS:
+ # The C++ implementation does not allow mixing descriptors from
+ # different pools.
+ db = symbol_database.SymbolDatabase(pool=descriptor_pool.Default())
+ else:
+ db = symbol_database.SymbolDatabase()
+ # Register representative types from unittest_pb2.
+ db.RegisterFileDescriptor(unittest_pb2.DESCRIPTOR)
+ db.RegisterMessage(unittest_pb2.TestAllTypes)
+ db.RegisterMessage(unittest_pb2.TestAllTypes.NestedMessage)
+ db.RegisterMessage(unittest_pb2.TestAllTypes.OptionalGroup)
+ db.RegisterMessage(unittest_pb2.TestAllTypes.RepeatedGroup)
+ db.RegisterEnumDescriptor(unittest_pb2.ForeignEnum.DESCRIPTOR)
+ db.RegisterEnumDescriptor(unittest_pb2.TestAllTypes.NestedEnum.DESCRIPTOR)
+ return db
+
+ def testGetPrototype(self):
+ instance = self._Database().GetPrototype(
+ unittest_pb2.TestAllTypes.DESCRIPTOR)
+ self.assertTrue(instance is unittest_pb2.TestAllTypes)
+
+ def testGetMessages(self):
+ messages = self._Database().GetMessages(
+ ['google/protobuf/unittest.proto'])
+ self.assertTrue(
+ unittest_pb2.TestAllTypes is
+ messages['protobuf_unittest.TestAllTypes'])
+
+ def testGetSymbol(self):
+ self.assertEqual(
+ unittest_pb2.TestAllTypes, self._Database().GetSymbol(
+ 'protobuf_unittest.TestAllTypes'))
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.NestedMessage, self._Database().GetSymbol(
+ 'protobuf_unittest.TestAllTypes.NestedMessage'))
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.OptionalGroup, self._Database().GetSymbol(
+ 'protobuf_unittest.TestAllTypes.OptionalGroup'))
+ self.assertEqual(
+ unittest_pb2.TestAllTypes.RepeatedGroup, self._Database().GetSymbol(
+ 'protobuf_unittest.TestAllTypes.RepeatedGroup'))
+
+ def testEnums(self):
+ # Check registration of types in the pool.
+ self.assertEqual(
+ 'protobuf_unittest.ForeignEnum',
+ self._Database().pool.FindEnumTypeByName(
+ 'protobuf_unittest.ForeignEnum').full_name)
+ self.assertEqual(
+ 'protobuf_unittest.TestAllTypes.NestedEnum',
+ self._Database().pool.FindEnumTypeByName(
+ 'protobuf_unittest.TestAllTypes.NestedEnum').full_name)
+
+ def testFindMessageTypeByName(self):
+ self.assertEqual(
+ 'protobuf_unittest.TestAllTypes',
+ self._Database().pool.FindMessageTypeByName(
+ 'protobuf_unittest.TestAllTypes').full_name)
+ self.assertEqual(
+ 'protobuf_unittest.TestAllTypes.NestedMessage',
+ self._Database().pool.FindMessageTypeByName(
+ 'protobuf_unittest.TestAllTypes.NestedMessage').full_name)
+
+ def testFindFindContainingSymbol(self):
+ # Lookup based on either enum or message.
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ self._Database().pool.FindFileContainingSymbol(
+ 'protobuf_unittest.TestAllTypes.NestedEnum').name)
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ self._Database().pool.FindFileContainingSymbol(
+ 'protobuf_unittest.TestAllTypes').name)
+
+ def testFindFileByName(self):
+ self.assertEqual(
+ 'google/protobuf/unittest.proto',
+ self._Database().pool.FindFileByName(
+ 'google/protobuf/unittest.proto').name)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/test_bad_identifiers.proto b/third_party/protobuf/3.0.0/python/google/protobuf/internal/test_bad_identifiers.proto
new file mode 100644
index 0000000000..c4860ea88a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/test_bad_identifiers.proto
@@ -0,0 +1,53 @@
+// 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)
+
+syntax = "proto2";
+
+package protobuf_unittest;
+
+option py_generic_services = true;
+
+message TestBadIdentifiers {
+ extensions 100 to max;
+}
+
+// Make sure these reasonable extension names don't conflict with internal
+// variables.
+extend TestBadIdentifiers {
+ optional string message = 100 [default="foo"];
+ optional string descriptor = 101 [default="bar"];
+ optional string reflection = 102 [default="baz"];
+ optional string service = 103 [default="qux"];
+}
+
+message AnotherMessage {}
+service AnotherService {}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/test_util.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/test_util.py
new file mode 100755
index 0000000000..2c805599b6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/test_util.py
@@ -0,0 +1,696 @@
+# 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.
+
+"""Utilities for Python proto2 tests.
+
+This is intentionally modeled on C++ code in
+//google/protobuf/test_util.*.
+"""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+import os.path
+
+import sys
+
+from google.protobuf import unittest_import_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import descriptor_pb2
+
+# Tests whether the given TestAllTypes message is proto2 or not.
+# This is used to gate several fields/features that only exist
+# for the proto2 version of the message.
+def IsProto2(message):
+ return message.DESCRIPTOR.syntax == "proto2"
+
+def SetAllNonLazyFields(message):
+ """Sets every non-lazy field in the message to a unique value.
+
+ Args:
+ message: A TestAllTypes instance.
+ """
+
+ #
+ # Optional fields.
+ #
+
+ message.optional_int32 = 101
+ message.optional_int64 = 102
+ message.optional_uint32 = 103
+ message.optional_uint64 = 104
+ message.optional_sint32 = 105
+ message.optional_sint64 = 106
+ message.optional_fixed32 = 107
+ message.optional_fixed64 = 108
+ message.optional_sfixed32 = 109
+ message.optional_sfixed64 = 110
+ message.optional_float = 111
+ message.optional_double = 112
+ message.optional_bool = True
+ message.optional_string = u'115'
+ message.optional_bytes = b'116'
+
+ if IsProto2(message):
+ message.optionalgroup.a = 117
+ message.optional_nested_message.bb = 118
+ message.optional_foreign_message.c = 119
+ message.optional_import_message.d = 120
+ message.optional_public_import_message.e = 126
+
+ message.optional_nested_enum = unittest_pb2.TestAllTypes.BAZ
+ message.optional_foreign_enum = unittest_pb2.FOREIGN_BAZ
+ if IsProto2(message):
+ message.optional_import_enum = unittest_import_pb2.IMPORT_BAZ
+
+ message.optional_string_piece = u'124'
+ message.optional_cord = u'125'
+
+ #
+ # Repeated fields.
+ #
+
+ message.repeated_int32.append(201)
+ message.repeated_int64.append(202)
+ message.repeated_uint32.append(203)
+ message.repeated_uint64.append(204)
+ message.repeated_sint32.append(205)
+ message.repeated_sint64.append(206)
+ message.repeated_fixed32.append(207)
+ message.repeated_fixed64.append(208)
+ message.repeated_sfixed32.append(209)
+ message.repeated_sfixed64.append(210)
+ message.repeated_float.append(211)
+ message.repeated_double.append(212)
+ message.repeated_bool.append(True)
+ message.repeated_string.append(u'215')
+ message.repeated_bytes.append(b'216')
+
+ if IsProto2(message):
+ message.repeatedgroup.add().a = 217
+ message.repeated_nested_message.add().bb = 218
+ message.repeated_foreign_message.add().c = 219
+ message.repeated_import_message.add().d = 220
+ message.repeated_lazy_message.add().bb = 227
+
+ message.repeated_nested_enum.append(unittest_pb2.TestAllTypes.BAR)
+ message.repeated_foreign_enum.append(unittest_pb2.FOREIGN_BAR)
+ if IsProto2(message):
+ message.repeated_import_enum.append(unittest_import_pb2.IMPORT_BAR)
+
+ message.repeated_string_piece.append(u'224')
+ message.repeated_cord.append(u'225')
+
+ # Add a second one of each field.
+ message.repeated_int32.append(301)
+ message.repeated_int64.append(302)
+ message.repeated_uint32.append(303)
+ message.repeated_uint64.append(304)
+ message.repeated_sint32.append(305)
+ message.repeated_sint64.append(306)
+ message.repeated_fixed32.append(307)
+ message.repeated_fixed64.append(308)
+ message.repeated_sfixed32.append(309)
+ message.repeated_sfixed64.append(310)
+ message.repeated_float.append(311)
+ message.repeated_double.append(312)
+ message.repeated_bool.append(False)
+ message.repeated_string.append(u'315')
+ message.repeated_bytes.append(b'316')
+
+ if IsProto2(message):
+ message.repeatedgroup.add().a = 317
+ message.repeated_nested_message.add().bb = 318
+ message.repeated_foreign_message.add().c = 319
+ message.repeated_import_message.add().d = 320
+ message.repeated_lazy_message.add().bb = 327
+
+ message.repeated_nested_enum.append(unittest_pb2.TestAllTypes.BAZ)
+ message.repeated_foreign_enum.append(unittest_pb2.FOREIGN_BAZ)
+ if IsProto2(message):
+ message.repeated_import_enum.append(unittest_import_pb2.IMPORT_BAZ)
+
+ message.repeated_string_piece.append(u'324')
+ message.repeated_cord.append(u'325')
+
+ #
+ # Fields that have defaults.
+ #
+
+ if IsProto2(message):
+ message.default_int32 = 401
+ message.default_int64 = 402
+ message.default_uint32 = 403
+ message.default_uint64 = 404
+ message.default_sint32 = 405
+ message.default_sint64 = 406
+ message.default_fixed32 = 407
+ message.default_fixed64 = 408
+ message.default_sfixed32 = 409
+ message.default_sfixed64 = 410
+ message.default_float = 411
+ message.default_double = 412
+ message.default_bool = False
+ message.default_string = '415'
+ message.default_bytes = b'416'
+
+ message.default_nested_enum = unittest_pb2.TestAllTypes.FOO
+ message.default_foreign_enum = unittest_pb2.FOREIGN_FOO
+ message.default_import_enum = unittest_import_pb2.IMPORT_FOO
+
+ message.default_string_piece = '424'
+ message.default_cord = '425'
+
+ message.oneof_uint32 = 601
+ message.oneof_nested_message.bb = 602
+ message.oneof_string = '603'
+ message.oneof_bytes = b'604'
+
+
+def SetAllFields(message):
+ SetAllNonLazyFields(message)
+ message.optional_lazy_message.bb = 127
+
+
+def SetAllExtensions(message):
+ """Sets every extension in the message to a unique value.
+
+ Args:
+ message: A unittest_pb2.TestAllExtensions instance.
+ """
+
+ extensions = message.Extensions
+ pb2 = unittest_pb2
+ import_pb2 = unittest_import_pb2
+
+ #
+ # Optional fields.
+ #
+
+ extensions[pb2.optional_int32_extension] = 101
+ extensions[pb2.optional_int64_extension] = 102
+ extensions[pb2.optional_uint32_extension] = 103
+ extensions[pb2.optional_uint64_extension] = 104
+ extensions[pb2.optional_sint32_extension] = 105
+ extensions[pb2.optional_sint64_extension] = 106
+ extensions[pb2.optional_fixed32_extension] = 107
+ extensions[pb2.optional_fixed64_extension] = 108
+ extensions[pb2.optional_sfixed32_extension] = 109
+ extensions[pb2.optional_sfixed64_extension] = 110
+ extensions[pb2.optional_float_extension] = 111
+ extensions[pb2.optional_double_extension] = 112
+ extensions[pb2.optional_bool_extension] = True
+ extensions[pb2.optional_string_extension] = u'115'
+ extensions[pb2.optional_bytes_extension] = b'116'
+
+ extensions[pb2.optionalgroup_extension].a = 117
+ extensions[pb2.optional_nested_message_extension].bb = 118
+ extensions[pb2.optional_foreign_message_extension].c = 119
+ extensions[pb2.optional_import_message_extension].d = 120
+ extensions[pb2.optional_public_import_message_extension].e = 126
+ extensions[pb2.optional_lazy_message_extension].bb = 127
+
+ extensions[pb2.optional_nested_enum_extension] = pb2.TestAllTypes.BAZ
+ extensions[pb2.optional_nested_enum_extension] = pb2.TestAllTypes.BAZ
+ extensions[pb2.optional_foreign_enum_extension] = pb2.FOREIGN_BAZ
+ extensions[pb2.optional_import_enum_extension] = import_pb2.IMPORT_BAZ
+
+ extensions[pb2.optional_string_piece_extension] = u'124'
+ extensions[pb2.optional_cord_extension] = u'125'
+
+ #
+ # Repeated fields.
+ #
+
+ extensions[pb2.repeated_int32_extension].append(201)
+ extensions[pb2.repeated_int64_extension].append(202)
+ extensions[pb2.repeated_uint32_extension].append(203)
+ extensions[pb2.repeated_uint64_extension].append(204)
+ extensions[pb2.repeated_sint32_extension].append(205)
+ extensions[pb2.repeated_sint64_extension].append(206)
+ extensions[pb2.repeated_fixed32_extension].append(207)
+ extensions[pb2.repeated_fixed64_extension].append(208)
+ extensions[pb2.repeated_sfixed32_extension].append(209)
+ extensions[pb2.repeated_sfixed64_extension].append(210)
+ extensions[pb2.repeated_float_extension].append(211)
+ extensions[pb2.repeated_double_extension].append(212)
+ extensions[pb2.repeated_bool_extension].append(True)
+ extensions[pb2.repeated_string_extension].append(u'215')
+ extensions[pb2.repeated_bytes_extension].append(b'216')
+
+ extensions[pb2.repeatedgroup_extension].add().a = 217
+ extensions[pb2.repeated_nested_message_extension].add().bb = 218
+ extensions[pb2.repeated_foreign_message_extension].add().c = 219
+ extensions[pb2.repeated_import_message_extension].add().d = 220
+ extensions[pb2.repeated_lazy_message_extension].add().bb = 227
+
+ extensions[pb2.repeated_nested_enum_extension].append(pb2.TestAllTypes.BAR)
+ extensions[pb2.repeated_foreign_enum_extension].append(pb2.FOREIGN_BAR)
+ extensions[pb2.repeated_import_enum_extension].append(import_pb2.IMPORT_BAR)
+
+ extensions[pb2.repeated_string_piece_extension].append(u'224')
+ extensions[pb2.repeated_cord_extension].append(u'225')
+
+ # Append a second one of each field.
+ extensions[pb2.repeated_int32_extension].append(301)
+ extensions[pb2.repeated_int64_extension].append(302)
+ extensions[pb2.repeated_uint32_extension].append(303)
+ extensions[pb2.repeated_uint64_extension].append(304)
+ extensions[pb2.repeated_sint32_extension].append(305)
+ extensions[pb2.repeated_sint64_extension].append(306)
+ extensions[pb2.repeated_fixed32_extension].append(307)
+ extensions[pb2.repeated_fixed64_extension].append(308)
+ extensions[pb2.repeated_sfixed32_extension].append(309)
+ extensions[pb2.repeated_sfixed64_extension].append(310)
+ extensions[pb2.repeated_float_extension].append(311)
+ extensions[pb2.repeated_double_extension].append(312)
+ extensions[pb2.repeated_bool_extension].append(False)
+ extensions[pb2.repeated_string_extension].append(u'315')
+ extensions[pb2.repeated_bytes_extension].append(b'316')
+
+ extensions[pb2.repeatedgroup_extension].add().a = 317
+ extensions[pb2.repeated_nested_message_extension].add().bb = 318
+ extensions[pb2.repeated_foreign_message_extension].add().c = 319
+ extensions[pb2.repeated_import_message_extension].add().d = 320
+ extensions[pb2.repeated_lazy_message_extension].add().bb = 327
+
+ extensions[pb2.repeated_nested_enum_extension].append(pb2.TestAllTypes.BAZ)
+ extensions[pb2.repeated_foreign_enum_extension].append(pb2.FOREIGN_BAZ)
+ extensions[pb2.repeated_import_enum_extension].append(import_pb2.IMPORT_BAZ)
+
+ extensions[pb2.repeated_string_piece_extension].append(u'324')
+ extensions[pb2.repeated_cord_extension].append(u'325')
+
+ #
+ # Fields with defaults.
+ #
+
+ extensions[pb2.default_int32_extension] = 401
+ extensions[pb2.default_int64_extension] = 402
+ extensions[pb2.default_uint32_extension] = 403
+ extensions[pb2.default_uint64_extension] = 404
+ extensions[pb2.default_sint32_extension] = 405
+ extensions[pb2.default_sint64_extension] = 406
+ extensions[pb2.default_fixed32_extension] = 407
+ extensions[pb2.default_fixed64_extension] = 408
+ extensions[pb2.default_sfixed32_extension] = 409
+ extensions[pb2.default_sfixed64_extension] = 410
+ extensions[pb2.default_float_extension] = 411
+ extensions[pb2.default_double_extension] = 412
+ extensions[pb2.default_bool_extension] = False
+ extensions[pb2.default_string_extension] = u'415'
+ extensions[pb2.default_bytes_extension] = b'416'
+
+ extensions[pb2.default_nested_enum_extension] = pb2.TestAllTypes.FOO
+ extensions[pb2.default_foreign_enum_extension] = pb2.FOREIGN_FOO
+ extensions[pb2.default_import_enum_extension] = import_pb2.IMPORT_FOO
+
+ extensions[pb2.default_string_piece_extension] = u'424'
+ extensions[pb2.default_cord_extension] = '425'
+
+ extensions[pb2.oneof_uint32_extension] = 601
+ extensions[pb2.oneof_nested_message_extension].bb = 602
+ extensions[pb2.oneof_string_extension] = u'603'
+ extensions[pb2.oneof_bytes_extension] = b'604'
+
+
+def SetAllFieldsAndExtensions(message):
+ """Sets every field and extension in the message to a unique value.
+
+ Args:
+ message: A unittest_pb2.TestAllExtensions message.
+ """
+ message.my_int = 1
+ message.my_string = 'foo'
+ message.my_float = 1.0
+ message.Extensions[unittest_pb2.my_extension_int] = 23
+ message.Extensions[unittest_pb2.my_extension_string] = 'bar'
+
+
+def ExpectAllFieldsAndExtensionsInOrder(serialized):
+ """Ensures that serialized is the serialization we expect for a message
+ filled with SetAllFieldsAndExtensions(). (Specifically, ensures that the
+ serialization is in canonical, tag-number order).
+ """
+ my_extension_int = unittest_pb2.my_extension_int
+ my_extension_string = unittest_pb2.my_extension_string
+ expected_strings = []
+ message = unittest_pb2.TestFieldOrderings()
+ message.my_int = 1 # Field 1.
+ expected_strings.append(message.SerializeToString())
+ message.Clear()
+ message.Extensions[my_extension_int] = 23 # Field 5.
+ expected_strings.append(message.SerializeToString())
+ message.Clear()
+ message.my_string = 'foo' # Field 11.
+ expected_strings.append(message.SerializeToString())
+ message.Clear()
+ message.Extensions[my_extension_string] = 'bar' # Field 50.
+ expected_strings.append(message.SerializeToString())
+ message.Clear()
+ message.my_float = 1.0
+ expected_strings.append(message.SerializeToString())
+ message.Clear()
+ expected = b''.join(expected_strings)
+
+ if expected != serialized:
+ raise ValueError('Expected %r, found %r' % (expected, serialized))
+
+
+def ExpectAllFieldsSet(test_case, message):
+ """Check all fields for correct values have after Set*Fields() is called."""
+ test_case.assertTrue(message.HasField('optional_int32'))
+ test_case.assertTrue(message.HasField('optional_int64'))
+ test_case.assertTrue(message.HasField('optional_uint32'))
+ test_case.assertTrue(message.HasField('optional_uint64'))
+ test_case.assertTrue(message.HasField('optional_sint32'))
+ test_case.assertTrue(message.HasField('optional_sint64'))
+ test_case.assertTrue(message.HasField('optional_fixed32'))
+ test_case.assertTrue(message.HasField('optional_fixed64'))
+ test_case.assertTrue(message.HasField('optional_sfixed32'))
+ test_case.assertTrue(message.HasField('optional_sfixed64'))
+ test_case.assertTrue(message.HasField('optional_float'))
+ test_case.assertTrue(message.HasField('optional_double'))
+ test_case.assertTrue(message.HasField('optional_bool'))
+ test_case.assertTrue(message.HasField('optional_string'))
+ test_case.assertTrue(message.HasField('optional_bytes'))
+
+ if IsProto2(message):
+ test_case.assertTrue(message.HasField('optionalgroup'))
+ test_case.assertTrue(message.HasField('optional_nested_message'))
+ test_case.assertTrue(message.HasField('optional_foreign_message'))
+ test_case.assertTrue(message.HasField('optional_import_message'))
+
+ test_case.assertTrue(message.optionalgroup.HasField('a'))
+ test_case.assertTrue(message.optional_nested_message.HasField('bb'))
+ test_case.assertTrue(message.optional_foreign_message.HasField('c'))
+ test_case.assertTrue(message.optional_import_message.HasField('d'))
+
+ test_case.assertTrue(message.HasField('optional_nested_enum'))
+ test_case.assertTrue(message.HasField('optional_foreign_enum'))
+ if IsProto2(message):
+ test_case.assertTrue(message.HasField('optional_import_enum'))
+
+ test_case.assertTrue(message.HasField('optional_string_piece'))
+ test_case.assertTrue(message.HasField('optional_cord'))
+
+ test_case.assertEqual(101, message.optional_int32)
+ test_case.assertEqual(102, message.optional_int64)
+ test_case.assertEqual(103, message.optional_uint32)
+ test_case.assertEqual(104, message.optional_uint64)
+ test_case.assertEqual(105, message.optional_sint32)
+ test_case.assertEqual(106, message.optional_sint64)
+ test_case.assertEqual(107, message.optional_fixed32)
+ test_case.assertEqual(108, message.optional_fixed64)
+ test_case.assertEqual(109, message.optional_sfixed32)
+ test_case.assertEqual(110, message.optional_sfixed64)
+ test_case.assertEqual(111, message.optional_float)
+ test_case.assertEqual(112, message.optional_double)
+ test_case.assertEqual(True, message.optional_bool)
+ test_case.assertEqual('115', message.optional_string)
+ test_case.assertEqual(b'116', message.optional_bytes)
+
+ if IsProto2(message):
+ test_case.assertEqual(117, message.optionalgroup.a)
+ test_case.assertEqual(118, message.optional_nested_message.bb)
+ test_case.assertEqual(119, message.optional_foreign_message.c)
+ test_case.assertEqual(120, message.optional_import_message.d)
+ test_case.assertEqual(126, message.optional_public_import_message.e)
+ test_case.assertEqual(127, message.optional_lazy_message.bb)
+
+ test_case.assertEqual(unittest_pb2.TestAllTypes.BAZ,
+ message.optional_nested_enum)
+ test_case.assertEqual(unittest_pb2.FOREIGN_BAZ,
+ message.optional_foreign_enum)
+ if IsProto2(message):
+ test_case.assertEqual(unittest_import_pb2.IMPORT_BAZ,
+ message.optional_import_enum)
+
+ # -----------------------------------------------------------------
+
+ test_case.assertEqual(2, len(message.repeated_int32))
+ test_case.assertEqual(2, len(message.repeated_int64))
+ test_case.assertEqual(2, len(message.repeated_uint32))
+ test_case.assertEqual(2, len(message.repeated_uint64))
+ test_case.assertEqual(2, len(message.repeated_sint32))
+ test_case.assertEqual(2, len(message.repeated_sint64))
+ test_case.assertEqual(2, len(message.repeated_fixed32))
+ test_case.assertEqual(2, len(message.repeated_fixed64))
+ test_case.assertEqual(2, len(message.repeated_sfixed32))
+ test_case.assertEqual(2, len(message.repeated_sfixed64))
+ test_case.assertEqual(2, len(message.repeated_float))
+ test_case.assertEqual(2, len(message.repeated_double))
+ test_case.assertEqual(2, len(message.repeated_bool))
+ test_case.assertEqual(2, len(message.repeated_string))
+ test_case.assertEqual(2, len(message.repeated_bytes))
+
+ if IsProto2(message):
+ test_case.assertEqual(2, len(message.repeatedgroup))
+ test_case.assertEqual(2, len(message.repeated_nested_message))
+ test_case.assertEqual(2, len(message.repeated_foreign_message))
+ test_case.assertEqual(2, len(message.repeated_import_message))
+ test_case.assertEqual(2, len(message.repeated_nested_enum))
+ test_case.assertEqual(2, len(message.repeated_foreign_enum))
+ if IsProto2(message):
+ test_case.assertEqual(2, len(message.repeated_import_enum))
+
+ test_case.assertEqual(2, len(message.repeated_string_piece))
+ test_case.assertEqual(2, len(message.repeated_cord))
+
+ test_case.assertEqual(201, message.repeated_int32[0])
+ test_case.assertEqual(202, message.repeated_int64[0])
+ test_case.assertEqual(203, message.repeated_uint32[0])
+ test_case.assertEqual(204, message.repeated_uint64[0])
+ test_case.assertEqual(205, message.repeated_sint32[0])
+ test_case.assertEqual(206, message.repeated_sint64[0])
+ test_case.assertEqual(207, message.repeated_fixed32[0])
+ test_case.assertEqual(208, message.repeated_fixed64[0])
+ test_case.assertEqual(209, message.repeated_sfixed32[0])
+ test_case.assertEqual(210, message.repeated_sfixed64[0])
+ test_case.assertEqual(211, message.repeated_float[0])
+ test_case.assertEqual(212, message.repeated_double[0])
+ test_case.assertEqual(True, message.repeated_bool[0])
+ test_case.assertEqual('215', message.repeated_string[0])
+ test_case.assertEqual(b'216', message.repeated_bytes[0])
+
+ if IsProto2(message):
+ test_case.assertEqual(217, message.repeatedgroup[0].a)
+ test_case.assertEqual(218, message.repeated_nested_message[0].bb)
+ test_case.assertEqual(219, message.repeated_foreign_message[0].c)
+ test_case.assertEqual(220, message.repeated_import_message[0].d)
+ test_case.assertEqual(227, message.repeated_lazy_message[0].bb)
+
+ test_case.assertEqual(unittest_pb2.TestAllTypes.BAR,
+ message.repeated_nested_enum[0])
+ test_case.assertEqual(unittest_pb2.FOREIGN_BAR,
+ message.repeated_foreign_enum[0])
+ if IsProto2(message):
+ test_case.assertEqual(unittest_import_pb2.IMPORT_BAR,
+ message.repeated_import_enum[0])
+
+ test_case.assertEqual(301, message.repeated_int32[1])
+ test_case.assertEqual(302, message.repeated_int64[1])
+ test_case.assertEqual(303, message.repeated_uint32[1])
+ test_case.assertEqual(304, message.repeated_uint64[1])
+ test_case.assertEqual(305, message.repeated_sint32[1])
+ test_case.assertEqual(306, message.repeated_sint64[1])
+ test_case.assertEqual(307, message.repeated_fixed32[1])
+ test_case.assertEqual(308, message.repeated_fixed64[1])
+ test_case.assertEqual(309, message.repeated_sfixed32[1])
+ test_case.assertEqual(310, message.repeated_sfixed64[1])
+ test_case.assertEqual(311, message.repeated_float[1])
+ test_case.assertEqual(312, message.repeated_double[1])
+ test_case.assertEqual(False, message.repeated_bool[1])
+ test_case.assertEqual('315', message.repeated_string[1])
+ test_case.assertEqual(b'316', message.repeated_bytes[1])
+
+ if IsProto2(message):
+ test_case.assertEqual(317, message.repeatedgroup[1].a)
+ test_case.assertEqual(318, message.repeated_nested_message[1].bb)
+ test_case.assertEqual(319, message.repeated_foreign_message[1].c)
+ test_case.assertEqual(320, message.repeated_import_message[1].d)
+ test_case.assertEqual(327, message.repeated_lazy_message[1].bb)
+
+ test_case.assertEqual(unittest_pb2.TestAllTypes.BAZ,
+ message.repeated_nested_enum[1])
+ test_case.assertEqual(unittest_pb2.FOREIGN_BAZ,
+ message.repeated_foreign_enum[1])
+ if IsProto2(message):
+ test_case.assertEqual(unittest_import_pb2.IMPORT_BAZ,
+ message.repeated_import_enum[1])
+
+ # -----------------------------------------------------------------
+
+ if IsProto2(message):
+ test_case.assertTrue(message.HasField('default_int32'))
+ test_case.assertTrue(message.HasField('default_int64'))
+ test_case.assertTrue(message.HasField('default_uint32'))
+ test_case.assertTrue(message.HasField('default_uint64'))
+ test_case.assertTrue(message.HasField('default_sint32'))
+ test_case.assertTrue(message.HasField('default_sint64'))
+ test_case.assertTrue(message.HasField('default_fixed32'))
+ test_case.assertTrue(message.HasField('default_fixed64'))
+ test_case.assertTrue(message.HasField('default_sfixed32'))
+ test_case.assertTrue(message.HasField('default_sfixed64'))
+ test_case.assertTrue(message.HasField('default_float'))
+ test_case.assertTrue(message.HasField('default_double'))
+ test_case.assertTrue(message.HasField('default_bool'))
+ test_case.assertTrue(message.HasField('default_string'))
+ test_case.assertTrue(message.HasField('default_bytes'))
+
+ test_case.assertTrue(message.HasField('default_nested_enum'))
+ test_case.assertTrue(message.HasField('default_foreign_enum'))
+ test_case.assertTrue(message.HasField('default_import_enum'))
+
+ test_case.assertEqual(401, message.default_int32)
+ test_case.assertEqual(402, message.default_int64)
+ test_case.assertEqual(403, message.default_uint32)
+ test_case.assertEqual(404, message.default_uint64)
+ test_case.assertEqual(405, message.default_sint32)
+ test_case.assertEqual(406, message.default_sint64)
+ test_case.assertEqual(407, message.default_fixed32)
+ test_case.assertEqual(408, message.default_fixed64)
+ test_case.assertEqual(409, message.default_sfixed32)
+ test_case.assertEqual(410, message.default_sfixed64)
+ test_case.assertEqual(411, message.default_float)
+ test_case.assertEqual(412, message.default_double)
+ test_case.assertEqual(False, message.default_bool)
+ test_case.assertEqual('415', message.default_string)
+ test_case.assertEqual(b'416', message.default_bytes)
+
+ test_case.assertEqual(unittest_pb2.TestAllTypes.FOO,
+ message.default_nested_enum)
+ test_case.assertEqual(unittest_pb2.FOREIGN_FOO,
+ message.default_foreign_enum)
+ test_case.assertEqual(unittest_import_pb2.IMPORT_FOO,
+ message.default_import_enum)
+
+
+def GoldenFile(filename):
+ """Finds the given golden file and returns a file object representing it."""
+
+ # Search up the directory tree looking for the C++ protobuf source code.
+ path = '.'
+ while os.path.exists(path):
+ if os.path.exists(os.path.join(path, 'src/google/protobuf')):
+ # Found it. Load the golden file from the testdata directory.
+ full_path = os.path.join(path, 'src/google/protobuf/testdata', filename)
+ return open(full_path, 'rb')
+ path = os.path.join(path, '..')
+
+ # Search internally.
+ path = '.'
+ full_path = os.path.join(path, 'third_party/py/google/protobuf/testdata',
+ filename)
+ if os.path.exists(full_path):
+ # Found it. Load the golden file from the testdata directory.
+ return open(full_path, 'rb')
+
+ raise RuntimeError(
+ 'Could not find golden files. This test must be run from within the '
+ 'protobuf source package so that it can read test data files from the '
+ 'C++ source tree.')
+
+
+def GoldenFileData(filename):
+ """Finds the given golden file and returns its contents."""
+ with GoldenFile(filename) as f:
+ return f.read()
+
+
+def SetAllPackedFields(message):
+ """Sets every field in the message to a unique value.
+
+ Args:
+ message: A TestPackedTypes instance.
+ """
+ message.packed_int32.extend([601, 701])
+ message.packed_int64.extend([602, 702])
+ message.packed_uint32.extend([603, 703])
+ message.packed_uint64.extend([604, 704])
+ message.packed_sint32.extend([605, 705])
+ message.packed_sint64.extend([606, 706])
+ message.packed_fixed32.extend([607, 707])
+ message.packed_fixed64.extend([608, 708])
+ message.packed_sfixed32.extend([609, 709])
+ message.packed_sfixed64.extend([610, 710])
+ message.packed_float.extend([611.0, 711.0])
+ message.packed_double.extend([612.0, 712.0])
+ message.packed_bool.extend([True, False])
+ message.packed_enum.extend([unittest_pb2.FOREIGN_BAR,
+ unittest_pb2.FOREIGN_BAZ])
+
+
+def SetAllPackedExtensions(message):
+ """Sets every extension in the message to a unique value.
+
+ Args:
+ message: A unittest_pb2.TestPackedExtensions instance.
+ """
+ extensions = message.Extensions
+ pb2 = unittest_pb2
+
+ extensions[pb2.packed_int32_extension].extend([601, 701])
+ extensions[pb2.packed_int64_extension].extend([602, 702])
+ extensions[pb2.packed_uint32_extension].extend([603, 703])
+ extensions[pb2.packed_uint64_extension].extend([604, 704])
+ extensions[pb2.packed_sint32_extension].extend([605, 705])
+ extensions[pb2.packed_sint64_extension].extend([606, 706])
+ extensions[pb2.packed_fixed32_extension].extend([607, 707])
+ extensions[pb2.packed_fixed64_extension].extend([608, 708])
+ extensions[pb2.packed_sfixed32_extension].extend([609, 709])
+ extensions[pb2.packed_sfixed64_extension].extend([610, 710])
+ extensions[pb2.packed_float_extension].extend([611.0, 711.0])
+ extensions[pb2.packed_double_extension].extend([612.0, 712.0])
+ extensions[pb2.packed_bool_extension].extend([True, False])
+ extensions[pb2.packed_enum_extension].extend([unittest_pb2.FOREIGN_BAR,
+ unittest_pb2.FOREIGN_BAZ])
+
+
+def SetAllUnpackedFields(message):
+ """Sets every field in the message to a unique value.
+
+ Args:
+ message: A unittest_pb2.TestUnpackedTypes instance.
+ """
+ message.unpacked_int32.extend([601, 701])
+ message.unpacked_int64.extend([602, 702])
+ message.unpacked_uint32.extend([603, 703])
+ message.unpacked_uint64.extend([604, 704])
+ message.unpacked_sint32.extend([605, 705])
+ message.unpacked_sint64.extend([606, 706])
+ message.unpacked_fixed32.extend([607, 707])
+ message.unpacked_fixed64.extend([608, 708])
+ message.unpacked_sfixed32.extend([609, 709])
+ message.unpacked_sfixed64.extend([610, 710])
+ message.unpacked_float.extend([611.0, 711.0])
+ message.unpacked_double.extend([612.0, 712.0])
+ message.unpacked_bool.extend([True, False])
+ message.unpacked_enum.extend([unittest_pb2.FOREIGN_BAR,
+ unittest_pb2.FOREIGN_BAZ])
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/text_encoding_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/text_encoding_test.py
new file mode 100755
index 0000000000..c7d182c444
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/text_encoding_test.py
@@ -0,0 +1,72 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Tests for google.protobuf.text_encoding."""
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import text_encoding
+
+TEST_VALUES = [
+ ("foo\\rbar\\nbaz\\t",
+ "foo\\rbar\\nbaz\\t",
+ b"foo\rbar\nbaz\t"),
+ ("\\'full of \\\"sound\\\" and \\\"fury\\\"\\'",
+ "\\'full of \\\"sound\\\" and \\\"fury\\\"\\'",
+ b"'full of \"sound\" and \"fury\"'"),
+ ("signi\\\\fying\\\\ nothing\\\\",
+ "signi\\\\fying\\\\ nothing\\\\",
+ b"signi\\fying\\ nothing\\"),
+ ("\\010\\t\\n\\013\\014\\r",
+ "\x08\\t\\n\x0b\x0c\\r",
+ b"\010\011\012\013\014\015")]
+
+
+class TextEncodingTestCase(unittest.TestCase):
+ def testCEscape(self):
+ for escaped, escaped_utf8, unescaped in TEST_VALUES:
+ self.assertEqual(escaped,
+ text_encoding.CEscape(unescaped, as_utf8=False))
+ self.assertEqual(escaped_utf8,
+ text_encoding.CEscape(unescaped, as_utf8=True))
+
+ def testCUnescape(self):
+ for escaped, escaped_utf8, unescaped in TEST_VALUES:
+ self.assertEqual(unescaped, text_encoding.CUnescape(escaped))
+ self.assertEqual(unescaped, text_encoding.CUnescape(escaped_utf8))
+
+
+if __name__ == "__main__":
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/text_format_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/text_format_test.py
new file mode 100755
index 0000000000..0e38e0e9e9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/text_format_test.py
@@ -0,0 +1,1359 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Test for google.protobuf.text_format."""
+
+__author__ = 'kenton@google.com (Kenton Varda)'
+
+
+import re
+import six
+import string
+
+try:
+ import unittest2 as unittest # PY26, pylint: disable=g-import-not-at-top
+except ImportError:
+ import unittest # pylint: disable=g-import-not-at-top
+
+from google.protobuf.internal import _parameterized
+
+from google.protobuf import any_test_pb2
+from google.protobuf import map_unittest_pb2
+from google.protobuf import unittest_mset_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import unittest_proto3_arena_pb2
+from google.protobuf.internal import api_implementation
+from google.protobuf.internal import test_util
+from google.protobuf.internal import message_set_extensions_pb2
+from google.protobuf import descriptor_pool
+from google.protobuf import text_format
+
+
+# Low-level nuts-n-bolts tests.
+class SimpleTextFormatTests(unittest.TestCase):
+
+ # The members of _QUOTES are formatted into a regexp template that
+ # expects single characters. Therefore it's an error (in addition to being
+ # non-sensical in the first place) to try to specify a "quote mark" that is
+ # more than one character.
+ def testQuoteMarksAreSingleChars(self):
+ for quote in text_format._QUOTES:
+ self.assertEqual(1, len(quote))
+
+
+# Base class with some common functionality.
+class TextFormatBase(unittest.TestCase):
+
+ def ReadGolden(self, golden_filename):
+ with test_util.GoldenFile(golden_filename) as f:
+ return (f.readlines() if str is bytes else # PY3
+ [golden_line.decode('utf-8') for golden_line in f])
+
+ def CompareToGoldenFile(self, text, golden_filename):
+ golden_lines = self.ReadGolden(golden_filename)
+ self.assertMultiLineEqual(text, ''.join(golden_lines))
+
+ def CompareToGoldenText(self, text, golden_text):
+ self.assertEqual(text, golden_text)
+
+ def RemoveRedundantZeros(self, text):
+ # Some platforms print 1e+5 as 1e+005. This is fine, but we need to remove
+ # these zeros in order to match the golden file.
+ text = text.replace('e+0','e+').replace('e+0','e+') \
+ .replace('e-0','e-').replace('e-0','e-')
+ # Floating point fields are printed with .0 suffix even if they are
+ # actualy integer numbers.
+ text = re.compile(r'\.0$', re.MULTILINE).sub('', text)
+ return text
+
+
+@_parameterized.Parameters((unittest_pb2), (unittest_proto3_arena_pb2))
+class TextFormatTest(TextFormatBase):
+
+ def testPrintExotic(self, message_module):
+ message = message_module.TestAllTypes()
+ message.repeated_int64.append(-9223372036854775808)
+ message.repeated_uint64.append(18446744073709551615)
+ message.repeated_double.append(123.456)
+ message.repeated_double.append(1.23e22)
+ message.repeated_double.append(1.23e-18)
+ message.repeated_string.append('\000\001\a\b\f\n\r\t\v\\\'"')
+ message.repeated_string.append(u'\u00fc\ua71f')
+ self.CompareToGoldenText(
+ self.RemoveRedundantZeros(text_format.MessageToString(message)),
+ 'repeated_int64: -9223372036854775808\n'
+ 'repeated_uint64: 18446744073709551615\n'
+ 'repeated_double: 123.456\n'
+ 'repeated_double: 1.23e+22\n'
+ 'repeated_double: 1.23e-18\n'
+ 'repeated_string:'
+ ' "\\000\\001\\007\\010\\014\\n\\r\\t\\013\\\\\\\'\\""\n'
+ 'repeated_string: "\\303\\274\\352\\234\\237"\n')
+
+ def testPrintExoticUnicodeSubclass(self, message_module):
+
+ class UnicodeSub(six.text_type):
+ pass
+
+ message = message_module.TestAllTypes()
+ message.repeated_string.append(UnicodeSub(u'\u00fc\ua71f'))
+ self.CompareToGoldenText(
+ text_format.MessageToString(message),
+ 'repeated_string: "\\303\\274\\352\\234\\237"\n')
+
+ def testPrintNestedMessageAsOneLine(self, message_module):
+ message = message_module.TestAllTypes()
+ msg = message.repeated_nested_message.add()
+ msg.bb = 42
+ self.CompareToGoldenText(
+ text_format.MessageToString(message, as_one_line=True),
+ 'repeated_nested_message { bb: 42 }')
+
+ def testPrintRepeatedFieldsAsOneLine(self, message_module):
+ message = message_module.TestAllTypes()
+ message.repeated_int32.append(1)
+ message.repeated_int32.append(1)
+ message.repeated_int32.append(3)
+ message.repeated_string.append('Google')
+ message.repeated_string.append('Zurich')
+ self.CompareToGoldenText(
+ text_format.MessageToString(message, as_one_line=True),
+ 'repeated_int32: 1 repeated_int32: 1 repeated_int32: 3 '
+ 'repeated_string: "Google" repeated_string: "Zurich"')
+
+ def testPrintNestedNewLineInStringAsOneLine(self, message_module):
+ message = message_module.TestAllTypes()
+ message.optional_string = 'a\nnew\nline'
+ self.CompareToGoldenText(
+ text_format.MessageToString(message, as_one_line=True),
+ 'optional_string: "a\\nnew\\nline"')
+
+ def testPrintExoticAsOneLine(self, message_module):
+ message = message_module.TestAllTypes()
+ message.repeated_int64.append(-9223372036854775808)
+ message.repeated_uint64.append(18446744073709551615)
+ message.repeated_double.append(123.456)
+ message.repeated_double.append(1.23e22)
+ message.repeated_double.append(1.23e-18)
+ message.repeated_string.append('\000\001\a\b\f\n\r\t\v\\\'"')
+ message.repeated_string.append(u'\u00fc\ua71f')
+ self.CompareToGoldenText(
+ self.RemoveRedundantZeros(text_format.MessageToString(
+ message, as_one_line=True)),
+ 'repeated_int64: -9223372036854775808'
+ ' repeated_uint64: 18446744073709551615'
+ ' repeated_double: 123.456'
+ ' repeated_double: 1.23e+22'
+ ' repeated_double: 1.23e-18'
+ ' repeated_string: '
+ '"\\000\\001\\007\\010\\014\\n\\r\\t\\013\\\\\\\'\\""'
+ ' repeated_string: "\\303\\274\\352\\234\\237"')
+
+ def testRoundTripExoticAsOneLine(self, message_module):
+ message = message_module.TestAllTypes()
+ message.repeated_int64.append(-9223372036854775808)
+ message.repeated_uint64.append(18446744073709551615)
+ message.repeated_double.append(123.456)
+ message.repeated_double.append(1.23e22)
+ message.repeated_double.append(1.23e-18)
+ message.repeated_string.append('\000\001\a\b\f\n\r\t\v\\\'"')
+ message.repeated_string.append(u'\u00fc\ua71f')
+
+ # Test as_utf8 = False.
+ wire_text = text_format.MessageToString(message,
+ as_one_line=True,
+ as_utf8=False)
+ parsed_message = message_module.TestAllTypes()
+ r = text_format.Parse(wire_text, parsed_message)
+ self.assertIs(r, parsed_message)
+ self.assertEqual(message, parsed_message)
+
+ # Test as_utf8 = True.
+ wire_text = text_format.MessageToString(message,
+ as_one_line=True,
+ as_utf8=True)
+ parsed_message = message_module.TestAllTypes()
+ r = text_format.Parse(wire_text, parsed_message)
+ self.assertIs(r, parsed_message)
+ self.assertEqual(message, parsed_message,
+ '\n%s != %s' % (message, parsed_message))
+
+ def testPrintRawUtf8String(self, message_module):
+ message = message_module.TestAllTypes()
+ message.repeated_string.append(u'\u00fc\ua71f')
+ text = text_format.MessageToString(message, as_utf8=True)
+ self.CompareToGoldenText(text, 'repeated_string: "\303\274\352\234\237"\n')
+ parsed_message = message_module.TestAllTypes()
+ text_format.Parse(text, parsed_message)
+ self.assertEqual(message, parsed_message,
+ '\n%s != %s' % (message, parsed_message))
+
+ def testPrintFloatFormat(self, message_module):
+ # Check that float_format argument is passed to sub-message formatting.
+ message = message_module.NestedTestAllTypes()
+ # We use 1.25 as it is a round number in binary. The proto 32-bit float
+ # will not gain additional imprecise digits as a 64-bit Python float and
+ # show up in its str. 32-bit 1.2 is noisy when extended to 64-bit:
+ # >>> struct.unpack('f', struct.pack('f', 1.2))[0]
+ # 1.2000000476837158
+ # >>> struct.unpack('f', struct.pack('f', 1.25))[0]
+ # 1.25
+ message.payload.optional_float = 1.25
+ # Check rounding at 15 significant digits
+ message.payload.optional_double = -.000003456789012345678
+ # Check no decimal point.
+ message.payload.repeated_float.append(-5642)
+ # Check no trailing zeros.
+ message.payload.repeated_double.append(.000078900)
+ formatted_fields = ['optional_float: 1.25',
+ 'optional_double: -3.45678901234568e-6',
+ 'repeated_float: -5642', 'repeated_double: 7.89e-5']
+ text_message = text_format.MessageToString(message, float_format='.15g')
+ self.CompareToGoldenText(
+ self.RemoveRedundantZeros(text_message),
+ 'payload {{\n {0}\n {1}\n {2}\n {3}\n}}\n'.format(
+ *formatted_fields))
+ # as_one_line=True is a separate code branch where float_format is passed.
+ text_message = text_format.MessageToString(message,
+ as_one_line=True,
+ float_format='.15g')
+ self.CompareToGoldenText(
+ self.RemoveRedundantZeros(text_message),
+ 'payload {{ {0} {1} {2} {3} }}'.format(*formatted_fields))
+
+ def testMessageToString(self, message_module):
+ message = message_module.ForeignMessage()
+ message.c = 123
+ self.assertEqual('c: 123\n', str(message))
+
+ def testPrintField(self, message_module):
+ message = message_module.TestAllTypes()
+ field = message.DESCRIPTOR.fields_by_name['optional_float']
+ value = message.optional_float
+ out = text_format.TextWriter(False)
+ text_format.PrintField(field, value, out)
+ self.assertEqual('optional_float: 0.0\n', out.getvalue())
+ out.close()
+ # Test Printer
+ out = text_format.TextWriter(False)
+ printer = text_format._Printer(out)
+ printer.PrintField(field, value)
+ self.assertEqual('optional_float: 0.0\n', out.getvalue())
+ out.close()
+
+ def testPrintFieldValue(self, message_module):
+ message = message_module.TestAllTypes()
+ field = message.DESCRIPTOR.fields_by_name['optional_float']
+ value = message.optional_float
+ out = text_format.TextWriter(False)
+ text_format.PrintFieldValue(field, value, out)
+ self.assertEqual('0.0', out.getvalue())
+ out.close()
+ # Test Printer
+ out = text_format.TextWriter(False)
+ printer = text_format._Printer(out)
+ printer.PrintFieldValue(field, value)
+ self.assertEqual('0.0', out.getvalue())
+ out.close()
+
+ def testParseAllFields(self, message_module):
+ message = message_module.TestAllTypes()
+ test_util.SetAllFields(message)
+ ascii_text = text_format.MessageToString(message)
+
+ parsed_message = message_module.TestAllTypes()
+ text_format.Parse(ascii_text, parsed_message)
+ self.assertEqual(message, parsed_message)
+ if message_module is unittest_pb2:
+ test_util.ExpectAllFieldsSet(self, message)
+
+ def testParseExotic(self, message_module):
+ message = message_module.TestAllTypes()
+ text = ('repeated_int64: -9223372036854775808\n'
+ 'repeated_uint64: 18446744073709551615\n'
+ 'repeated_double: 123.456\n'
+ 'repeated_double: 1.23e+22\n'
+ 'repeated_double: 1.23e-18\n'
+ 'repeated_string: \n'
+ '"\\000\\001\\007\\010\\014\\n\\r\\t\\013\\\\\\\'\\""\n'
+ 'repeated_string: "foo" \'corge\' "grault"\n'
+ 'repeated_string: "\\303\\274\\352\\234\\237"\n'
+ 'repeated_string: "\\xc3\\xbc"\n'
+ 'repeated_string: "\xc3\xbc"\n')
+ text_format.Parse(text, message)
+
+ self.assertEqual(-9223372036854775808, message.repeated_int64[0])
+ self.assertEqual(18446744073709551615, message.repeated_uint64[0])
+ self.assertEqual(123.456, message.repeated_double[0])
+ self.assertEqual(1.23e22, message.repeated_double[1])
+ self.assertEqual(1.23e-18, message.repeated_double[2])
+ self.assertEqual('\000\001\a\b\f\n\r\t\v\\\'"', message.repeated_string[0])
+ self.assertEqual('foocorgegrault', message.repeated_string[1])
+ self.assertEqual(u'\u00fc\ua71f', message.repeated_string[2])
+ self.assertEqual(u'\u00fc', message.repeated_string[3])
+
+ def testParseTrailingCommas(self, message_module):
+ message = message_module.TestAllTypes()
+ text = ('repeated_int64: 100;\n'
+ 'repeated_int64: 200;\n'
+ 'repeated_int64: 300,\n'
+ 'repeated_string: "one",\n'
+ 'repeated_string: "two";\n')
+ text_format.Parse(text, message)
+
+ self.assertEqual(100, message.repeated_int64[0])
+ self.assertEqual(200, message.repeated_int64[1])
+ self.assertEqual(300, message.repeated_int64[2])
+ self.assertEqual(u'one', message.repeated_string[0])
+ self.assertEqual(u'two', message.repeated_string[1])
+
+ def testParseRepeatedScalarShortFormat(self, message_module):
+ message = message_module.TestAllTypes()
+ text = ('repeated_int64: [100, 200];\n'
+ 'repeated_int64: 300,\n'
+ 'repeated_string: ["one", "two"];\n')
+ text_format.Parse(text, message)
+
+ self.assertEqual(100, message.repeated_int64[0])
+ self.assertEqual(200, message.repeated_int64[1])
+ self.assertEqual(300, message.repeated_int64[2])
+ self.assertEqual(u'one', message.repeated_string[0])
+ self.assertEqual(u'two', message.repeated_string[1])
+
+ def testParseRepeatedMessageShortFormat(self, message_module):
+ message = message_module.TestAllTypes()
+ text = ('repeated_nested_message: [{bb: 100}, {bb: 200}],\n'
+ 'repeated_nested_message: {bb: 300}\n'
+ 'repeated_nested_message [{bb: 400}];\n')
+ text_format.Parse(text, message)
+
+ self.assertEqual(100, message.repeated_nested_message[0].bb)
+ self.assertEqual(200, message.repeated_nested_message[1].bb)
+ self.assertEqual(300, message.repeated_nested_message[2].bb)
+ self.assertEqual(400, message.repeated_nested_message[3].bb)
+
+ def testParseEmptyText(self, message_module):
+ message = message_module.TestAllTypes()
+ text = ''
+ text_format.Parse(text, message)
+ self.assertEqual(message_module.TestAllTypes(), message)
+
+ def testParseInvalidUtf8(self, message_module):
+ message = message_module.TestAllTypes()
+ text = 'repeated_string: "\\xc3\\xc3"'
+ self.assertRaises(text_format.ParseError, text_format.Parse, text, message)
+
+ def testParseSingleWord(self, message_module):
+ message = message_module.TestAllTypes()
+ text = 'foo'
+ six.assertRaisesRegex(self, text_format.ParseError, (
+ r'1:1 : Message type "\w+.TestAllTypes" has no field named '
+ r'"foo".'), text_format.Parse, text, message)
+
+ def testParseUnknownField(self, message_module):
+ message = message_module.TestAllTypes()
+ text = 'unknown_field: 8\n'
+ six.assertRaisesRegex(self, text_format.ParseError, (
+ r'1:1 : Message type "\w+.TestAllTypes" has no field named '
+ r'"unknown_field".'), text_format.Parse, text, message)
+
+ def testParseBadEnumValue(self, message_module):
+ message = message_module.TestAllTypes()
+ text = 'optional_nested_enum: BARR'
+ six.assertRaisesRegex(self, text_format.ParseError,
+ (r'1:23 : Enum type "\w+.TestAllTypes.NestedEnum" '
+ r'has no value named BARR.'), text_format.Parse,
+ text, message)
+
+ message = message_module.TestAllTypes()
+ text = 'optional_nested_enum: 100'
+ six.assertRaisesRegex(self, text_format.ParseError,
+ (r'1:23 : Enum type "\w+.TestAllTypes.NestedEnum" '
+ r'has no value with number 100.'), text_format.Parse,
+ text, message)
+
+ def testParseBadIntValue(self, message_module):
+ message = message_module.TestAllTypes()
+ text = 'optional_int32: bork'
+ six.assertRaisesRegex(self, text_format.ParseError,
+ ('1:17 : Couldn\'t parse integer: bork'),
+ text_format.Parse, text, message)
+
+ def testParseStringFieldUnescape(self, message_module):
+ message = message_module.TestAllTypes()
+ text = r'''repeated_string: "\xf\x62"
+ repeated_string: "\\xf\\x62"
+ repeated_string: "\\\xf\\\x62"
+ repeated_string: "\\\\xf\\\\x62"
+ repeated_string: "\\\\\xf\\\\\x62"
+ repeated_string: "\x5cx20"'''
+
+ text_format.Parse(text, message)
+
+ SLASH = '\\'
+ self.assertEqual('\x0fb', message.repeated_string[0])
+ self.assertEqual(SLASH + 'xf' + SLASH + 'x62', message.repeated_string[1])
+ self.assertEqual(SLASH + '\x0f' + SLASH + 'b', message.repeated_string[2])
+ self.assertEqual(SLASH + SLASH + 'xf' + SLASH + SLASH + 'x62',
+ message.repeated_string[3])
+ self.assertEqual(SLASH + SLASH + '\x0f' + SLASH + SLASH + 'b',
+ message.repeated_string[4])
+ self.assertEqual(SLASH + 'x20', message.repeated_string[5])
+
+ def testMergeDuplicateScalars(self, message_module):
+ message = message_module.TestAllTypes()
+ text = ('optional_int32: 42 ' 'optional_int32: 67')
+ r = text_format.Merge(text, message)
+ self.assertIs(r, message)
+ self.assertEqual(67, message.optional_int32)
+
+ def testMergeDuplicateNestedMessageScalars(self, message_module):
+ message = message_module.TestAllTypes()
+ text = ('optional_nested_message { bb: 1 } '
+ 'optional_nested_message { bb: 2 }')
+ r = text_format.Merge(text, message)
+ self.assertTrue(r is message)
+ self.assertEqual(2, message.optional_nested_message.bb)
+
+ def testParseOneof(self, message_module):
+ m = message_module.TestAllTypes()
+ m.oneof_uint32 = 11
+ m2 = message_module.TestAllTypes()
+ text_format.Parse(text_format.MessageToString(m), m2)
+ self.assertEqual('oneof_uint32', m2.WhichOneof('oneof_field'))
+
+ def testParseMultipleOneof(self, message_module):
+ m_string = '\n'.join(['oneof_uint32: 11', 'oneof_string: "foo"'])
+ m2 = message_module.TestAllTypes()
+ if message_module is unittest_pb2:
+ with self.assertRaisesRegexp(text_format.ParseError,
+ ' is specified along with field '):
+ text_format.Parse(m_string, m2)
+ else:
+ text_format.Parse(m_string, m2)
+ self.assertEqual('oneof_string', m2.WhichOneof('oneof_field'))
+
+
+# These are tests that aren't fundamentally specific to proto2, but are at
+# the moment because of differences between the proto2 and proto3 test schemas.
+# Ideally the schemas would be made more similar so these tests could pass.
+class OnlyWorksWithProto2RightNowTests(TextFormatBase):
+
+ def testPrintAllFieldsPointy(self):
+ message = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(message)
+ self.CompareToGoldenFile(
+ self.RemoveRedundantZeros(text_format.MessageToString(
+ message, pointy_brackets=True)),
+ 'text_format_unittest_data_pointy_oneof.txt')
+
+ def testParseGolden(self):
+ golden_text = '\n'.join(self.ReadGolden(
+ 'text_format_unittest_data_oneof_implemented.txt'))
+ parsed_message = unittest_pb2.TestAllTypes()
+ r = text_format.Parse(golden_text, parsed_message)
+ self.assertIs(r, parsed_message)
+
+ message = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(message)
+ self.assertEqual(message, parsed_message)
+
+ def testPrintAllFields(self):
+ message = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(message)
+ self.CompareToGoldenFile(
+ self.RemoveRedundantZeros(text_format.MessageToString(message)),
+ 'text_format_unittest_data_oneof_implemented.txt')
+
+ def testPrintInIndexOrder(self):
+ message = unittest_pb2.TestFieldOrderings()
+ message.my_string = '115'
+ message.my_int = 101
+ message.my_float = 111
+ message.optional_nested_message.oo = 0
+ message.optional_nested_message.bb = 1
+ self.CompareToGoldenText(
+ self.RemoveRedundantZeros(text_format.MessageToString(
+ message, use_index_order=True)),
+ 'my_string: \"115\"\nmy_int: 101\nmy_float: 111\n'
+ 'optional_nested_message {\n oo: 0\n bb: 1\n}\n')
+ self.CompareToGoldenText(
+ self.RemoveRedundantZeros(text_format.MessageToString(message)),
+ 'my_int: 101\nmy_string: \"115\"\nmy_float: 111\n'
+ 'optional_nested_message {\n bb: 1\n oo: 0\n}\n')
+
+ def testMergeLinesGolden(self):
+ opened = self.ReadGolden('text_format_unittest_data_oneof_implemented.txt')
+ parsed_message = unittest_pb2.TestAllTypes()
+ r = text_format.MergeLines(opened, parsed_message)
+ self.assertIs(r, parsed_message)
+
+ message = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(message)
+ self.assertEqual(message, parsed_message)
+
+ def testParseLinesGolden(self):
+ opened = self.ReadGolden('text_format_unittest_data_oneof_implemented.txt')
+ parsed_message = unittest_pb2.TestAllTypes()
+ r = text_format.ParseLines(opened, parsed_message)
+ self.assertIs(r, parsed_message)
+
+ message = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(message)
+ self.assertEqual(message, parsed_message)
+
+ def testPrintMap(self):
+ message = map_unittest_pb2.TestMap()
+
+ message.map_int32_int32[-123] = -456
+ message.map_int64_int64[-2**33] = -2**34
+ message.map_uint32_uint32[123] = 456
+ message.map_uint64_uint64[2**33] = 2**34
+ message.map_string_string['abc'] = '123'
+ message.map_int32_foreign_message[111].c = 5
+
+ # Maps are serialized to text format using their underlying repeated
+ # representation.
+ self.CompareToGoldenText(
+ text_format.MessageToString(message), 'map_int32_int32 {\n'
+ ' key: -123\n'
+ ' value: -456\n'
+ '}\n'
+ 'map_int64_int64 {\n'
+ ' key: -8589934592\n'
+ ' value: -17179869184\n'
+ '}\n'
+ 'map_uint32_uint32 {\n'
+ ' key: 123\n'
+ ' value: 456\n'
+ '}\n'
+ 'map_uint64_uint64 {\n'
+ ' key: 8589934592\n'
+ ' value: 17179869184\n'
+ '}\n'
+ 'map_string_string {\n'
+ ' key: "abc"\n'
+ ' value: "123"\n'
+ '}\n'
+ 'map_int32_foreign_message {\n'
+ ' key: 111\n'
+ ' value {\n'
+ ' c: 5\n'
+ ' }\n'
+ '}\n')
+
+ def testMapOrderEnforcement(self):
+ message = map_unittest_pb2.TestMap()
+ for letter in string.ascii_uppercase[13:26]:
+ message.map_string_string[letter] = 'dummy'
+ for letter in reversed(string.ascii_uppercase[0:13]):
+ message.map_string_string[letter] = 'dummy'
+ golden = ''.join(('map_string_string {\n key: "%c"\n value: "dummy"\n}\n'
+ % (letter,) for letter in string.ascii_uppercase))
+ self.CompareToGoldenText(text_format.MessageToString(message), golden)
+
+ def testMapOrderSemantics(self):
+ golden_lines = self.ReadGolden('map_test_data.txt')
+ # The C++ implementation emits defaulted-value fields, while the Python
+ # implementation does not. Adjusting for this is awkward, but it is
+ # valuable to test against a common golden file.
+ line_blacklist = (' key: 0\n', ' value: 0\n', ' key: false\n',
+ ' value: false\n')
+ golden_lines = [line for line in golden_lines if line not in line_blacklist]
+
+ message = map_unittest_pb2.TestMap()
+ text_format.ParseLines(golden_lines, message)
+ candidate = text_format.MessageToString(message)
+ # The Python implementation emits "1.0" for the double value that the C++
+ # implementation emits as "1".
+ candidate = candidate.replace('1.0', '1', 2)
+ self.assertMultiLineEqual(candidate, ''.join(golden_lines))
+
+
+# Tests of proto2-only features (MessageSet, extensions, etc.).
+class Proto2Tests(TextFormatBase):
+
+ def testPrintMessageSet(self):
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ ext1 = unittest_mset_pb2.TestMessageSetExtension1.message_set_extension
+ ext2 = unittest_mset_pb2.TestMessageSetExtension2.message_set_extension
+ message.message_set.Extensions[ext1].i = 23
+ message.message_set.Extensions[ext2].str = 'foo'
+ self.CompareToGoldenText(
+ text_format.MessageToString(message), 'message_set {\n'
+ ' [protobuf_unittest.TestMessageSetExtension1] {\n'
+ ' i: 23\n'
+ ' }\n'
+ ' [protobuf_unittest.TestMessageSetExtension2] {\n'
+ ' str: \"foo\"\n'
+ ' }\n'
+ '}\n')
+
+ message = message_set_extensions_pb2.TestMessageSet()
+ ext = message_set_extensions_pb2.message_set_extension3
+ message.Extensions[ext].text = 'bar'
+ self.CompareToGoldenText(
+ text_format.MessageToString(message),
+ '[google.protobuf.internal.TestMessageSetExtension3] {\n'
+ ' text: \"bar\"\n'
+ '}\n')
+
+ def testPrintMessageSetByFieldNumber(self):
+ out = text_format.TextWriter(False)
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ ext1 = unittest_mset_pb2.TestMessageSetExtension1.message_set_extension
+ ext2 = unittest_mset_pb2.TestMessageSetExtension2.message_set_extension
+ message.message_set.Extensions[ext1].i = 23
+ message.message_set.Extensions[ext2].str = 'foo'
+ text_format.PrintMessage(message, out, use_field_number=True)
+ self.CompareToGoldenText(out.getvalue(), '1 {\n'
+ ' 1545008 {\n'
+ ' 15: 23\n'
+ ' }\n'
+ ' 1547769 {\n'
+ ' 25: \"foo\"\n'
+ ' }\n'
+ '}\n')
+ out.close()
+
+ def testPrintMessageSetAsOneLine(self):
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ ext1 = unittest_mset_pb2.TestMessageSetExtension1.message_set_extension
+ ext2 = unittest_mset_pb2.TestMessageSetExtension2.message_set_extension
+ message.message_set.Extensions[ext1].i = 23
+ message.message_set.Extensions[ext2].str = 'foo'
+ self.CompareToGoldenText(
+ text_format.MessageToString(message, as_one_line=True),
+ 'message_set {'
+ ' [protobuf_unittest.TestMessageSetExtension1] {'
+ ' i: 23'
+ ' }'
+ ' [protobuf_unittest.TestMessageSetExtension2] {'
+ ' str: \"foo\"'
+ ' }'
+ ' }')
+
+ def testParseMessageSet(self):
+ message = unittest_pb2.TestAllTypes()
+ text = ('repeated_uint64: 1\n' 'repeated_uint64: 2\n')
+ text_format.Parse(text, message)
+ self.assertEqual(1, message.repeated_uint64[0])
+ self.assertEqual(2, message.repeated_uint64[1])
+
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ text = ('message_set {\n'
+ ' [protobuf_unittest.TestMessageSetExtension1] {\n'
+ ' i: 23\n'
+ ' }\n'
+ ' [protobuf_unittest.TestMessageSetExtension2] {\n'
+ ' str: \"foo\"\n'
+ ' }\n'
+ '}\n')
+ text_format.Parse(text, message)
+ ext1 = unittest_mset_pb2.TestMessageSetExtension1.message_set_extension
+ ext2 = unittest_mset_pb2.TestMessageSetExtension2.message_set_extension
+ self.assertEqual(23, message.message_set.Extensions[ext1].i)
+ self.assertEqual('foo', message.message_set.Extensions[ext2].str)
+
+ def testParseMessageByFieldNumber(self):
+ message = unittest_pb2.TestAllTypes()
+ text = ('34: 1\n' 'repeated_uint64: 2\n')
+ text_format.Parse(text, message, allow_field_number=True)
+ self.assertEqual(1, message.repeated_uint64[0])
+ self.assertEqual(2, message.repeated_uint64[1])
+
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ text = ('1 {\n'
+ ' 1545008 {\n'
+ ' 15: 23\n'
+ ' }\n'
+ ' 1547769 {\n'
+ ' 25: \"foo\"\n'
+ ' }\n'
+ '}\n')
+ text_format.Parse(text, message, allow_field_number=True)
+ ext1 = unittest_mset_pb2.TestMessageSetExtension1.message_set_extension
+ ext2 = unittest_mset_pb2.TestMessageSetExtension2.message_set_extension
+ self.assertEqual(23, message.message_set.Extensions[ext1].i)
+ self.assertEqual('foo', message.message_set.Extensions[ext2].str)
+
+ # Can't parse field number without set allow_field_number=True.
+ message = unittest_pb2.TestAllTypes()
+ text = '34:1\n'
+ six.assertRaisesRegex(self, text_format.ParseError, (
+ r'1:1 : Message type "\w+.TestAllTypes" has no field named '
+ r'"34".'), text_format.Parse, text, message)
+
+ # Can't parse if field number is not found.
+ text = '1234:1\n'
+ six.assertRaisesRegex(
+ self,
+ text_format.ParseError,
+ (r'1:1 : Message type "\w+.TestAllTypes" has no field named '
+ r'"1234".'),
+ text_format.Parse,
+ text,
+ message,
+ allow_field_number=True)
+
+ def testPrintAllExtensions(self):
+ message = unittest_pb2.TestAllExtensions()
+ test_util.SetAllExtensions(message)
+ self.CompareToGoldenFile(
+ self.RemoveRedundantZeros(text_format.MessageToString(message)),
+ 'text_format_unittest_extensions_data.txt')
+
+ def testPrintAllExtensionsPointy(self):
+ message = unittest_pb2.TestAllExtensions()
+ test_util.SetAllExtensions(message)
+ self.CompareToGoldenFile(
+ self.RemoveRedundantZeros(text_format.MessageToString(
+ message, pointy_brackets=True)),
+ 'text_format_unittest_extensions_data_pointy.txt')
+
+ def testParseGoldenExtensions(self):
+ golden_text = '\n'.join(self.ReadGolden(
+ 'text_format_unittest_extensions_data.txt'))
+ parsed_message = unittest_pb2.TestAllExtensions()
+ text_format.Parse(golden_text, parsed_message)
+
+ message = unittest_pb2.TestAllExtensions()
+ test_util.SetAllExtensions(message)
+ self.assertEqual(message, parsed_message)
+
+ def testParseAllExtensions(self):
+ message = unittest_pb2.TestAllExtensions()
+ test_util.SetAllExtensions(message)
+ ascii_text = text_format.MessageToString(message)
+
+ parsed_message = unittest_pb2.TestAllExtensions()
+ text_format.Parse(ascii_text, parsed_message)
+ self.assertEqual(message, parsed_message)
+
+ def testParseAllowedUnknownExtension(self):
+ # Skip over unknown extension correctly.
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ text = ('message_set {\n'
+ ' [unknown_extension] {\n'
+ ' i: 23\n'
+ ' bin: "\xe0"'
+ ' [nested_unknown_ext]: {\n'
+ ' i: 23\n'
+ ' test: "test_string"\n'
+ ' floaty_float: -0.315\n'
+ ' num: -inf\n'
+ ' multiline_str: "abc"\n'
+ ' "def"\n'
+ ' "xyz."\n'
+ ' [nested_unknown_ext]: <\n'
+ ' i: 23\n'
+ ' i: 24\n'
+ ' pointfloat: .3\n'
+ ' test: "test_string"\n'
+ ' floaty_float: -0.315\n'
+ ' num: -inf\n'
+ ' long_string: "test" "test2" \n'
+ ' >\n'
+ ' }\n'
+ ' }\n'
+ ' [unknown_extension]: 5\n'
+ '}\n')
+ text_format.Parse(text, message, allow_unknown_extension=True)
+ golden = 'message_set {\n}\n'
+ self.CompareToGoldenText(text_format.MessageToString(message), golden)
+
+ # Catch parse errors in unknown extension.
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ malformed = ('message_set {\n'
+ ' [unknown_extension] {\n'
+ ' i:\n' # Missing value.
+ ' }\n'
+ '}\n')
+ six.assertRaisesRegex(self,
+ text_format.ParseError,
+ 'Invalid field value: }',
+ text_format.Parse,
+ malformed,
+ message,
+ allow_unknown_extension=True)
+
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ malformed = ('message_set {\n'
+ ' [unknown_extension] {\n'
+ ' str: "malformed string\n' # Missing closing quote.
+ ' }\n'
+ '}\n')
+ six.assertRaisesRegex(self,
+ text_format.ParseError,
+ 'Invalid field value: "',
+ text_format.Parse,
+ malformed,
+ message,
+ allow_unknown_extension=True)
+
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ malformed = ('message_set {\n'
+ ' [unknown_extension] {\n'
+ ' str: "malformed\n multiline\n string\n'
+ ' }\n'
+ '}\n')
+ six.assertRaisesRegex(self,
+ text_format.ParseError,
+ 'Invalid field value: "',
+ text_format.Parse,
+ malformed,
+ message,
+ allow_unknown_extension=True)
+
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ malformed = ('message_set {\n'
+ ' [malformed_extension] <\n'
+ ' i: -5\n'
+ ' \n' # Missing '>' here.
+ '}\n')
+ six.assertRaisesRegex(self,
+ text_format.ParseError,
+ '5:1 : Expected ">".',
+ text_format.Parse,
+ malformed,
+ message,
+ allow_unknown_extension=True)
+
+ # Don't allow unknown fields with allow_unknown_extension=True.
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ malformed = ('message_set {\n'
+ ' unknown_field: true\n'
+ ' \n' # Missing '>' here.
+ '}\n')
+ six.assertRaisesRegex(self,
+ text_format.ParseError,
+ ('2:3 : Message type '
+ '"proto2_wireformat_unittest.TestMessageSet" has no'
+ ' field named "unknown_field".'),
+ text_format.Parse,
+ malformed,
+ message,
+ allow_unknown_extension=True)
+
+ # Parse known extension correcty.
+ message = unittest_mset_pb2.TestMessageSetContainer()
+ text = ('message_set {\n'
+ ' [protobuf_unittest.TestMessageSetExtension1] {\n'
+ ' i: 23\n'
+ ' }\n'
+ ' [protobuf_unittest.TestMessageSetExtension2] {\n'
+ ' str: \"foo\"\n'
+ ' }\n'
+ '}\n')
+ text_format.Parse(text, message, allow_unknown_extension=True)
+ ext1 = unittest_mset_pb2.TestMessageSetExtension1.message_set_extension
+ ext2 = unittest_mset_pb2.TestMessageSetExtension2.message_set_extension
+ self.assertEqual(23, message.message_set.Extensions[ext1].i)
+ self.assertEqual('foo', message.message_set.Extensions[ext2].str)
+
+ def testParseBadExtension(self):
+ message = unittest_pb2.TestAllExtensions()
+ text = '[unknown_extension]: 8\n'
+ six.assertRaisesRegex(self, text_format.ParseError,
+ '1:2 : Extension "unknown_extension" not registered.',
+ text_format.Parse, text, message)
+ message = unittest_pb2.TestAllTypes()
+ six.assertRaisesRegex(self, text_format.ParseError, (
+ '1:2 : Message type "protobuf_unittest.TestAllTypes" does not have '
+ 'extensions.'), text_format.Parse, text, message)
+
+ def testMergeDuplicateExtensionScalars(self):
+ message = unittest_pb2.TestAllExtensions()
+ text = ('[protobuf_unittest.optional_int32_extension]: 42 '
+ '[protobuf_unittest.optional_int32_extension]: 67')
+ text_format.Merge(text, message)
+ self.assertEqual(67,
+ message.Extensions[unittest_pb2.optional_int32_extension])
+
+ def testParseDuplicateExtensionScalars(self):
+ message = unittest_pb2.TestAllExtensions()
+ text = ('[protobuf_unittest.optional_int32_extension]: 42 '
+ '[protobuf_unittest.optional_int32_extension]: 67')
+ six.assertRaisesRegex(self, text_format.ParseError, (
+ '1:96 : Message type "protobuf_unittest.TestAllExtensions" '
+ 'should not have multiple '
+ '"protobuf_unittest.optional_int32_extension" extensions.'),
+ text_format.Parse, text, message)
+
+ def testParseDuplicateNestedMessageScalars(self):
+ message = unittest_pb2.TestAllTypes()
+ text = ('optional_nested_message { bb: 1 } '
+ 'optional_nested_message { bb: 2 }')
+ six.assertRaisesRegex(self, text_format.ParseError, (
+ '1:65 : Message type "protobuf_unittest.TestAllTypes.NestedMessage" '
+ 'should not have multiple "bb" fields.'), text_format.Parse, text,
+ message)
+
+ def testParseDuplicateScalars(self):
+ message = unittest_pb2.TestAllTypes()
+ text = ('optional_int32: 42 ' 'optional_int32: 67')
+ six.assertRaisesRegex(self, text_format.ParseError, (
+ '1:36 : Message type "protobuf_unittest.TestAllTypes" should not '
+ 'have multiple "optional_int32" fields.'), text_format.Parse, text,
+ message)
+
+ def testParseGroupNotClosed(self):
+ message = unittest_pb2.TestAllTypes()
+ text = 'RepeatedGroup: <'
+ six.assertRaisesRegex(self, text_format.ParseError, '1:16 : Expected ">".',
+ text_format.Parse, text, message)
+ text = 'RepeatedGroup: {'
+ six.assertRaisesRegex(self, text_format.ParseError, '1:16 : Expected "}".',
+ text_format.Parse, text, message)
+
+ def testParseEmptyGroup(self):
+ message = unittest_pb2.TestAllTypes()
+ text = 'OptionalGroup: {}'
+ text_format.Parse(text, message)
+ self.assertTrue(message.HasField('optionalgroup'))
+
+ message.Clear()
+
+ message = unittest_pb2.TestAllTypes()
+ text = 'OptionalGroup: <>'
+ text_format.Parse(text, message)
+ self.assertTrue(message.HasField('optionalgroup'))
+
+ # Maps aren't really proto2-only, but our test schema only has maps for
+ # proto2.
+ def testParseMap(self):
+ text = ('map_int32_int32 {\n'
+ ' key: -123\n'
+ ' value: -456\n'
+ '}\n'
+ 'map_int64_int64 {\n'
+ ' key: -8589934592\n'
+ ' value: -17179869184\n'
+ '}\n'
+ 'map_uint32_uint32 {\n'
+ ' key: 123\n'
+ ' value: 456\n'
+ '}\n'
+ 'map_uint64_uint64 {\n'
+ ' key: 8589934592\n'
+ ' value: 17179869184\n'
+ '}\n'
+ 'map_string_string {\n'
+ ' key: "abc"\n'
+ ' value: "123"\n'
+ '}\n'
+ 'map_int32_foreign_message {\n'
+ ' key: 111\n'
+ ' value {\n'
+ ' c: 5\n'
+ ' }\n'
+ '}\n')
+ message = map_unittest_pb2.TestMap()
+ text_format.Parse(text, message)
+
+ self.assertEqual(-456, message.map_int32_int32[-123])
+ self.assertEqual(-2**34, message.map_int64_int64[-2**33])
+ self.assertEqual(456, message.map_uint32_uint32[123])
+ self.assertEqual(2**34, message.map_uint64_uint64[2**33])
+ self.assertEqual('123', message.map_string_string['abc'])
+ self.assertEqual(5, message.map_int32_foreign_message[111].c)
+
+
+class Proto3Tests(unittest.TestCase):
+
+ def testPrintMessageExpandAny(self):
+ packed_message = unittest_pb2.OneString()
+ packed_message.data = 'string'
+ message = any_test_pb2.TestAny()
+ message.any_value.Pack(packed_message)
+ self.assertEqual(
+ text_format.MessageToString(message,
+ descriptor_pool=descriptor_pool.Default()),
+ 'any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string"\n'
+ ' }\n'
+ '}\n')
+
+ def testPrintMessageExpandAnyRepeated(self):
+ packed_message = unittest_pb2.OneString()
+ message = any_test_pb2.TestAny()
+ packed_message.data = 'string0'
+ message.repeated_any_value.add().Pack(packed_message)
+ packed_message.data = 'string1'
+ message.repeated_any_value.add().Pack(packed_message)
+ self.assertEqual(
+ text_format.MessageToString(message,
+ descriptor_pool=descriptor_pool.Default()),
+ 'repeated_any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string0"\n'
+ ' }\n'
+ '}\n'
+ 'repeated_any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string1"\n'
+ ' }\n'
+ '}\n')
+
+ def testPrintMessageExpandAnyNoDescriptorPool(self):
+ packed_message = unittest_pb2.OneString()
+ packed_message.data = 'string'
+ message = any_test_pb2.TestAny()
+ message.any_value.Pack(packed_message)
+ self.assertEqual(
+ text_format.MessageToString(message, descriptor_pool=None),
+ 'any_value {\n'
+ ' type_url: "type.googleapis.com/protobuf_unittest.OneString"\n'
+ ' value: "\\n\\006string"\n'
+ '}\n')
+
+ def testPrintMessageExpandAnyDescriptorPoolMissingType(self):
+ packed_message = unittest_pb2.OneString()
+ packed_message.data = 'string'
+ message = any_test_pb2.TestAny()
+ message.any_value.Pack(packed_message)
+ empty_pool = descriptor_pool.DescriptorPool()
+ self.assertEqual(
+ text_format.MessageToString(message, descriptor_pool=empty_pool),
+ 'any_value {\n'
+ ' type_url: "type.googleapis.com/protobuf_unittest.OneString"\n'
+ ' value: "\\n\\006string"\n'
+ '}\n')
+
+ def testPrintMessageExpandAnyPointyBrackets(self):
+ packed_message = unittest_pb2.OneString()
+ packed_message.data = 'string'
+ message = any_test_pb2.TestAny()
+ message.any_value.Pack(packed_message)
+ self.assertEqual(
+ text_format.MessageToString(message,
+ pointy_brackets=True,
+ descriptor_pool=descriptor_pool.Default()),
+ 'any_value <\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] <\n'
+ ' data: "string"\n'
+ ' >\n'
+ '>\n')
+
+ def testPrintMessageExpandAnyAsOneLine(self):
+ packed_message = unittest_pb2.OneString()
+ packed_message.data = 'string'
+ message = any_test_pb2.TestAny()
+ message.any_value.Pack(packed_message)
+ self.assertEqual(
+ text_format.MessageToString(message,
+ as_one_line=True,
+ descriptor_pool=descriptor_pool.Default()),
+ 'any_value {'
+ ' [type.googleapis.com/protobuf_unittest.OneString]'
+ ' { data: "string" } '
+ '}')
+
+ def testPrintMessageExpandAnyAsOneLinePointyBrackets(self):
+ packed_message = unittest_pb2.OneString()
+ packed_message.data = 'string'
+ message = any_test_pb2.TestAny()
+ message.any_value.Pack(packed_message)
+ self.assertEqual(
+ text_format.MessageToString(message,
+ as_one_line=True,
+ pointy_brackets=True,
+ descriptor_pool=descriptor_pool.Default()),
+ 'any_value <'
+ ' [type.googleapis.com/protobuf_unittest.OneString]'
+ ' < data: "string" > '
+ '>')
+
+ def testMergeExpandedAny(self):
+ message = any_test_pb2.TestAny()
+ text = ('any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string"\n'
+ ' }\n'
+ '}\n')
+ text_format.Merge(text, message, descriptor_pool=descriptor_pool.Default())
+ packed_message = unittest_pb2.OneString()
+ message.any_value.Unpack(packed_message)
+ self.assertEqual('string', packed_message.data)
+
+ def testMergeExpandedAnyRepeated(self):
+ message = any_test_pb2.TestAny()
+ text = ('repeated_any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string0"\n'
+ ' }\n'
+ '}\n'
+ 'repeated_any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string1"\n'
+ ' }\n'
+ '}\n')
+ text_format.Merge(text, message, descriptor_pool=descriptor_pool.Default())
+ packed_message = unittest_pb2.OneString()
+ message.repeated_any_value[0].Unpack(packed_message)
+ self.assertEqual('string0', packed_message.data)
+ message.repeated_any_value[1].Unpack(packed_message)
+ self.assertEqual('string1', packed_message.data)
+
+ def testMergeExpandedAnyPointyBrackets(self):
+ message = any_test_pb2.TestAny()
+ text = ('any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] <\n'
+ ' data: "string"\n'
+ ' >\n'
+ '}\n')
+ text_format.Merge(text, message, descriptor_pool=descriptor_pool.Default())
+ packed_message = unittest_pb2.OneString()
+ message.any_value.Unpack(packed_message)
+ self.assertEqual('string', packed_message.data)
+
+ def testMergeExpandedAnyNoDescriptorPool(self):
+ message = any_test_pb2.TestAny()
+ text = ('any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string"\n'
+ ' }\n'
+ '}\n')
+ with self.assertRaises(text_format.ParseError) as e:
+ text_format.Merge(text, message, descriptor_pool=None)
+ self.assertEqual(str(e.exception),
+ 'Descriptor pool required to parse expanded Any field')
+
+ def testMergeExpandedAnyDescriptorPoolMissingType(self):
+ message = any_test_pb2.TestAny()
+ text = ('any_value {\n'
+ ' [type.googleapis.com/protobuf_unittest.OneString] {\n'
+ ' data: "string"\n'
+ ' }\n'
+ '}\n')
+ with self.assertRaises(text_format.ParseError) as e:
+ empty_pool = descriptor_pool.DescriptorPool()
+ text_format.Merge(text, message, descriptor_pool=empty_pool)
+ self.assertEqual(
+ str(e.exception),
+ 'Type protobuf_unittest.OneString not found in descriptor pool')
+
+ def testMergeUnexpandedAny(self):
+ text = ('any_value {\n'
+ ' type_url: "type.googleapis.com/protobuf_unittest.OneString"\n'
+ ' value: "\\n\\006string"\n'
+ '}\n')
+ message = any_test_pb2.TestAny()
+ text_format.Merge(text, message)
+ packed_message = unittest_pb2.OneString()
+ message.any_value.Unpack(packed_message)
+ self.assertEqual('string', packed_message.data)
+
+
+class TokenizerTest(unittest.TestCase):
+
+ def testSimpleTokenCases(self):
+ text = ('identifier1:"string1"\n \n\n'
+ 'identifier2 : \n \n123 \n identifier3 :\'string\'\n'
+ 'identifiER_4 : 1.1e+2 ID5:-0.23 ID6:\'aaaa\\\'bbbb\'\n'
+ 'ID7 : "aa\\"bb"\n\n\n\n ID8: {A:inf B:-inf C:true D:false}\n'
+ 'ID9: 22 ID10: -111111111111111111 ID11: -22\n'
+ 'ID12: 2222222222222222222 ID13: 1.23456f ID14: 1.2e+2f '
+ 'false_bool: 0 true_BOOL:t \n true_bool1: 1 false_BOOL1:f ')
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ methods = [(tokenizer.ConsumeIdentifier, 'identifier1'), ':',
+ (tokenizer.ConsumeString, 'string1'),
+ (tokenizer.ConsumeIdentifier, 'identifier2'), ':',
+ (tokenizer.ConsumeInteger, 123),
+ (tokenizer.ConsumeIdentifier, 'identifier3'), ':',
+ (tokenizer.ConsumeString, 'string'),
+ (tokenizer.ConsumeIdentifier, 'identifiER_4'), ':',
+ (tokenizer.ConsumeFloat, 1.1e+2),
+ (tokenizer.ConsumeIdentifier, 'ID5'), ':',
+ (tokenizer.ConsumeFloat, -0.23),
+ (tokenizer.ConsumeIdentifier, 'ID6'), ':',
+ (tokenizer.ConsumeString, 'aaaa\'bbbb'),
+ (tokenizer.ConsumeIdentifier, 'ID7'), ':',
+ (tokenizer.ConsumeString, 'aa\"bb'),
+ (tokenizer.ConsumeIdentifier, 'ID8'), ':', '{',
+ (tokenizer.ConsumeIdentifier, 'A'), ':',
+ (tokenizer.ConsumeFloat, float('inf')),
+ (tokenizer.ConsumeIdentifier, 'B'), ':',
+ (tokenizer.ConsumeFloat, -float('inf')),
+ (tokenizer.ConsumeIdentifier, 'C'), ':',
+ (tokenizer.ConsumeBool, True),
+ (tokenizer.ConsumeIdentifier, 'D'), ':',
+ (tokenizer.ConsumeBool, False), '}',
+ (tokenizer.ConsumeIdentifier, 'ID9'), ':',
+ (tokenizer.ConsumeInteger, 22),
+ (tokenizer.ConsumeIdentifier, 'ID10'), ':',
+ (tokenizer.ConsumeInteger, -111111111111111111),
+ (tokenizer.ConsumeIdentifier, 'ID11'), ':',
+ (tokenizer.ConsumeInteger, -22),
+ (tokenizer.ConsumeIdentifier, 'ID12'), ':',
+ (tokenizer.ConsumeInteger, 2222222222222222222),
+ (tokenizer.ConsumeIdentifier, 'ID13'), ':',
+ (tokenizer.ConsumeFloat, 1.23456),
+ (tokenizer.ConsumeIdentifier, 'ID14'), ':',
+ (tokenizer.ConsumeFloat, 1.2e+2),
+ (tokenizer.ConsumeIdentifier, 'false_bool'), ':',
+ (tokenizer.ConsumeBool, False),
+ (tokenizer.ConsumeIdentifier, 'true_BOOL'), ':',
+ (tokenizer.ConsumeBool, True),
+ (tokenizer.ConsumeIdentifier, 'true_bool1'), ':',
+ (tokenizer.ConsumeBool, True),
+ (tokenizer.ConsumeIdentifier, 'false_BOOL1'), ':',
+ (tokenizer.ConsumeBool, False)]
+
+ i = 0
+ while not tokenizer.AtEnd():
+ m = methods[i]
+ if isinstance(m, str):
+ token = tokenizer.token
+ self.assertEqual(token, m)
+ tokenizer.NextToken()
+ else:
+ self.assertEqual(m[1], m[0]())
+ i += 1
+
+ def testConsumeAbstractIntegers(self):
+ # This test only tests the failures in the integer parsing methods as well
+ # as the '0' special cases.
+ int64_max = (1 << 63) - 1
+ uint32_max = (1 << 32) - 1
+ text = '-1 %d %d' % (uint32_max + 1, int64_max + 1)
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertEqual(-1, tokenizer.ConsumeInteger())
+
+ self.assertEqual(uint32_max + 1, tokenizer.ConsumeInteger())
+
+ self.assertEqual(int64_max + 1, tokenizer.ConsumeInteger())
+ self.assertTrue(tokenizer.AtEnd())
+
+ text = '-0 0'
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertEqual(0, tokenizer.ConsumeInteger())
+ self.assertEqual(0, tokenizer.ConsumeInteger())
+ self.assertTrue(tokenizer.AtEnd())
+
+ def testConsumeIntegers(self):
+ # This test only tests the failures in the integer parsing methods as well
+ # as the '0' special cases.
+ int64_max = (1 << 63) - 1
+ uint32_max = (1 << 32) - 1
+ text = '-1 %d %d' % (uint32_max + 1, int64_max + 1)
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertRaises(text_format.ParseError,
+ text_format._ConsumeUint32, tokenizer)
+ self.assertRaises(text_format.ParseError,
+ text_format._ConsumeUint64, tokenizer)
+ self.assertEqual(-1, text_format._ConsumeInt32(tokenizer))
+
+ self.assertRaises(text_format.ParseError,
+ text_format._ConsumeUint32, tokenizer)
+ self.assertRaises(text_format.ParseError,
+ text_format._ConsumeInt32, tokenizer)
+ self.assertEqual(uint32_max + 1, text_format._ConsumeInt64(tokenizer))
+
+ self.assertRaises(text_format.ParseError,
+ text_format._ConsumeInt64, tokenizer)
+ self.assertEqual(int64_max + 1, text_format._ConsumeUint64(tokenizer))
+ self.assertTrue(tokenizer.AtEnd())
+
+ text = '-0 -0 0 0'
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertEqual(0, text_format._ConsumeUint32(tokenizer))
+ self.assertEqual(0, text_format._ConsumeUint64(tokenizer))
+ self.assertEqual(0, text_format._ConsumeUint32(tokenizer))
+ self.assertEqual(0, text_format._ConsumeUint64(tokenizer))
+ self.assertTrue(tokenizer.AtEnd())
+
+ def testConsumeByteString(self):
+ text = '"string1\''
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeByteString)
+
+ text = 'string1"'
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeByteString)
+
+ text = '\n"\\xt"'
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeByteString)
+
+ text = '\n"\\"'
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeByteString)
+
+ text = '\n"\\x"'
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeByteString)
+
+ def testConsumeBool(self):
+ text = 'not-a-bool'
+ tokenizer = text_format.Tokenizer(text.splitlines())
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeBool)
+
+ def testSkipComment(self):
+ tokenizer = text_format.Tokenizer('# some comment'.splitlines())
+ self.assertTrue(tokenizer.AtEnd())
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeComment)
+
+ def testConsumeComment(self):
+ tokenizer = text_format.Tokenizer('# some comment'.splitlines(),
+ skip_comments=False)
+ self.assertFalse(tokenizer.AtEnd())
+ self.assertEqual('# some comment', tokenizer.ConsumeComment())
+ self.assertTrue(tokenizer.AtEnd())
+
+ def testConsumeTwoComments(self):
+ text = '# some comment\n# another comment'
+ tokenizer = text_format.Tokenizer(text.splitlines(), skip_comments=False)
+ self.assertEqual('# some comment', tokenizer.ConsumeComment())
+ self.assertFalse(tokenizer.AtEnd())
+ self.assertEqual('# another comment', tokenizer.ConsumeComment())
+ self.assertTrue(tokenizer.AtEnd())
+
+ def testConsumeTrailingComment(self):
+ text = 'some_number: 4\n# some comment'
+ tokenizer = text_format.Tokenizer(text.splitlines(), skip_comments=False)
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeComment)
+
+ self.assertEqual('some_number', tokenizer.ConsumeIdentifier())
+ self.assertEqual(tokenizer.token, ':')
+ tokenizer.NextToken()
+ self.assertRaises(text_format.ParseError, tokenizer.ConsumeComment)
+ self.assertEqual(4, tokenizer.ConsumeInteger())
+ self.assertFalse(tokenizer.AtEnd())
+
+ self.assertEqual('# some comment', tokenizer.ConsumeComment())
+ self.assertTrue(tokenizer.AtEnd())
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/type_checkers.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/type_checkers.py
new file mode 100755
index 0000000000..1be3ad9a3c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/type_checkers.py
@@ -0,0 +1,352 @@
+# 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.
+
+"""Provides type checking routines.
+
+This module defines type checking utilities in the forms of dictionaries:
+
+VALUE_CHECKERS: A dictionary of field types and a value validation object.
+TYPE_TO_BYTE_SIZE_FN: A dictionary with field types and a size computing
+ function.
+TYPE_TO_SERIALIZE_METHOD: A dictionary with field types and serialization
+ function.
+FIELD_TYPE_TO_WIRE_TYPE: A dictionary with field typed and their
+ coresponding wire types.
+TYPE_TO_DESERIALIZE_METHOD: A dictionary with field types and deserialization
+ function.
+"""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+import six
+
+if six.PY3:
+ long = int
+
+from google.protobuf.internal import api_implementation
+from google.protobuf.internal import decoder
+from google.protobuf.internal import encoder
+from google.protobuf.internal import wire_format
+from google.protobuf import descriptor
+
+_FieldDescriptor = descriptor.FieldDescriptor
+
+def SupportsOpenEnums(field_descriptor):
+ return field_descriptor.containing_type.syntax == "proto3"
+
+def GetTypeChecker(field):
+ """Returns a type checker for a message field of the specified types.
+
+ Args:
+ field: FieldDescriptor object for this field.
+
+ Returns:
+ An instance of TypeChecker which can be used to verify the types
+ of values assigned to a field of the specified type.
+ """
+ if (field.cpp_type == _FieldDescriptor.CPPTYPE_STRING and
+ field.type == _FieldDescriptor.TYPE_STRING):
+ return UnicodeValueChecker()
+ if field.cpp_type == _FieldDescriptor.CPPTYPE_ENUM:
+ if SupportsOpenEnums(field):
+ # When open enums are supported, any int32 can be assigned.
+ return _VALUE_CHECKERS[_FieldDescriptor.CPPTYPE_INT32]
+ else:
+ return EnumValueChecker(field.enum_type)
+ return _VALUE_CHECKERS[field.cpp_type]
+
+
+# None of the typecheckers below make any attempt to guard against people
+# subclassing builtin types and doing weird things. We're not trying to
+# protect against malicious clients here, just people accidentally shooting
+# themselves in the foot in obvious ways.
+
+class TypeChecker(object):
+
+ """Type checker used to catch type errors as early as possible
+ when the client is setting scalar fields in protocol messages.
+ """
+
+ def __init__(self, *acceptable_types):
+ self._acceptable_types = acceptable_types
+
+ def CheckValue(self, proposed_value):
+ """Type check the provided value and return it.
+
+ The returned value might have been normalized to another type.
+ """
+ if not isinstance(proposed_value, self._acceptable_types):
+ message = ('%.1024r has type %s, but expected one of: %s' %
+ (proposed_value, type(proposed_value), self._acceptable_types))
+ raise TypeError(message)
+ return proposed_value
+
+
+class TypeCheckerWithDefault(TypeChecker):
+
+ def __init__(self, default_value, *acceptable_types):
+ TypeChecker.__init__(self, acceptable_types)
+ self._default_value = default_value
+
+ def DefaultValue(self):
+ return self._default_value
+
+
+# IntValueChecker and its subclasses perform integer type-checks
+# and bounds-checks.
+class IntValueChecker(object):
+
+ """Checker used for integer fields. Performs type-check and range check."""
+
+ def CheckValue(self, proposed_value):
+ if not isinstance(proposed_value, six.integer_types):
+ message = ('%.1024r has type %s, but expected one of: %s' %
+ (proposed_value, type(proposed_value), six.integer_types))
+ raise TypeError(message)
+ if not self._MIN <= proposed_value <= self._MAX:
+ raise ValueError('Value out of range: %d' % proposed_value)
+ # We force 32-bit values to int and 64-bit values to long to make
+ # alternate implementations where the distinction is more significant
+ # (e.g. the C++ implementation) simpler.
+ proposed_value = self._TYPE(proposed_value)
+ return proposed_value
+
+ def DefaultValue(self):
+ return 0
+
+
+class EnumValueChecker(object):
+
+ """Checker used for enum fields. Performs type-check and range check."""
+
+ def __init__(self, enum_type):
+ self._enum_type = enum_type
+
+ def CheckValue(self, proposed_value):
+ if not isinstance(proposed_value, six.integer_types):
+ message = ('%.1024r has type %s, but expected one of: %s' %
+ (proposed_value, type(proposed_value), six.integer_types))
+ raise TypeError(message)
+ if proposed_value not in self._enum_type.values_by_number:
+ raise ValueError('Unknown enum value: %d' % proposed_value)
+ return proposed_value
+
+ def DefaultValue(self):
+ return self._enum_type.values[0].number
+
+
+class UnicodeValueChecker(object):
+
+ """Checker used for string fields.
+
+ Always returns a unicode value, even if the input is of type str.
+ """
+
+ def CheckValue(self, proposed_value):
+ if not isinstance(proposed_value, (bytes, six.text_type)):
+ message = ('%.1024r has type %s, but expected one of: %s' %
+ (proposed_value, type(proposed_value), (bytes, six.text_type)))
+ raise TypeError(message)
+
+ # If the value is of type 'bytes' make sure that it is valid UTF-8 data.
+ if isinstance(proposed_value, bytes):
+ try:
+ proposed_value = proposed_value.decode('utf-8')
+ except UnicodeDecodeError:
+ raise ValueError('%.1024r has type bytes, but isn\'t valid UTF-8 '
+ 'encoding. Non-UTF-8 strings must be converted to '
+ 'unicode objects before being added.' %
+ (proposed_value))
+ return proposed_value
+
+ def DefaultValue(self):
+ return u""
+
+
+class Int32ValueChecker(IntValueChecker):
+ # We're sure to use ints instead of longs here since comparison may be more
+ # efficient.
+ _MIN = -2147483648
+ _MAX = 2147483647
+ _TYPE = int
+
+
+class Uint32ValueChecker(IntValueChecker):
+ _MIN = 0
+ _MAX = (1 << 32) - 1
+ _TYPE = int
+
+
+class Int64ValueChecker(IntValueChecker):
+ _MIN = -(1 << 63)
+ _MAX = (1 << 63) - 1
+ _TYPE = long
+
+
+class Uint64ValueChecker(IntValueChecker):
+ _MIN = 0
+ _MAX = (1 << 64) - 1
+ _TYPE = long
+
+
+# Type-checkers for all scalar CPPTYPEs.
+_VALUE_CHECKERS = {
+ _FieldDescriptor.CPPTYPE_INT32: Int32ValueChecker(),
+ _FieldDescriptor.CPPTYPE_INT64: Int64ValueChecker(),
+ _FieldDescriptor.CPPTYPE_UINT32: Uint32ValueChecker(),
+ _FieldDescriptor.CPPTYPE_UINT64: Uint64ValueChecker(),
+ _FieldDescriptor.CPPTYPE_DOUBLE: TypeCheckerWithDefault(
+ 0.0, float, int, long),
+ _FieldDescriptor.CPPTYPE_FLOAT: TypeCheckerWithDefault(
+ 0.0, float, int, long),
+ _FieldDescriptor.CPPTYPE_BOOL: TypeCheckerWithDefault(
+ False, bool, int),
+ _FieldDescriptor.CPPTYPE_STRING: TypeCheckerWithDefault(b'', bytes),
+ }
+
+
+# Map from field type to a function F, such that F(field_num, value)
+# gives the total byte size for a value of the given type. This
+# byte size includes tag information and any other additional space
+# associated with serializing "value".
+TYPE_TO_BYTE_SIZE_FN = {
+ _FieldDescriptor.TYPE_DOUBLE: wire_format.DoubleByteSize,
+ _FieldDescriptor.TYPE_FLOAT: wire_format.FloatByteSize,
+ _FieldDescriptor.TYPE_INT64: wire_format.Int64ByteSize,
+ _FieldDescriptor.TYPE_UINT64: wire_format.UInt64ByteSize,
+ _FieldDescriptor.TYPE_INT32: wire_format.Int32ByteSize,
+ _FieldDescriptor.TYPE_FIXED64: wire_format.Fixed64ByteSize,
+ _FieldDescriptor.TYPE_FIXED32: wire_format.Fixed32ByteSize,
+ _FieldDescriptor.TYPE_BOOL: wire_format.BoolByteSize,
+ _FieldDescriptor.TYPE_STRING: wire_format.StringByteSize,
+ _FieldDescriptor.TYPE_GROUP: wire_format.GroupByteSize,
+ _FieldDescriptor.TYPE_MESSAGE: wire_format.MessageByteSize,
+ _FieldDescriptor.TYPE_BYTES: wire_format.BytesByteSize,
+ _FieldDescriptor.TYPE_UINT32: wire_format.UInt32ByteSize,
+ _FieldDescriptor.TYPE_ENUM: wire_format.EnumByteSize,
+ _FieldDescriptor.TYPE_SFIXED32: wire_format.SFixed32ByteSize,
+ _FieldDescriptor.TYPE_SFIXED64: wire_format.SFixed64ByteSize,
+ _FieldDescriptor.TYPE_SINT32: wire_format.SInt32ByteSize,
+ _FieldDescriptor.TYPE_SINT64: wire_format.SInt64ByteSize
+ }
+
+
+# Maps from field types to encoder constructors.
+TYPE_TO_ENCODER = {
+ _FieldDescriptor.TYPE_DOUBLE: encoder.DoubleEncoder,
+ _FieldDescriptor.TYPE_FLOAT: encoder.FloatEncoder,
+ _FieldDescriptor.TYPE_INT64: encoder.Int64Encoder,
+ _FieldDescriptor.TYPE_UINT64: encoder.UInt64Encoder,
+ _FieldDescriptor.TYPE_INT32: encoder.Int32Encoder,
+ _FieldDescriptor.TYPE_FIXED64: encoder.Fixed64Encoder,
+ _FieldDescriptor.TYPE_FIXED32: encoder.Fixed32Encoder,
+ _FieldDescriptor.TYPE_BOOL: encoder.BoolEncoder,
+ _FieldDescriptor.TYPE_STRING: encoder.StringEncoder,
+ _FieldDescriptor.TYPE_GROUP: encoder.GroupEncoder,
+ _FieldDescriptor.TYPE_MESSAGE: encoder.MessageEncoder,
+ _FieldDescriptor.TYPE_BYTES: encoder.BytesEncoder,
+ _FieldDescriptor.TYPE_UINT32: encoder.UInt32Encoder,
+ _FieldDescriptor.TYPE_ENUM: encoder.EnumEncoder,
+ _FieldDescriptor.TYPE_SFIXED32: encoder.SFixed32Encoder,
+ _FieldDescriptor.TYPE_SFIXED64: encoder.SFixed64Encoder,
+ _FieldDescriptor.TYPE_SINT32: encoder.SInt32Encoder,
+ _FieldDescriptor.TYPE_SINT64: encoder.SInt64Encoder,
+ }
+
+
+# Maps from field types to sizer constructors.
+TYPE_TO_SIZER = {
+ _FieldDescriptor.TYPE_DOUBLE: encoder.DoubleSizer,
+ _FieldDescriptor.TYPE_FLOAT: encoder.FloatSizer,
+ _FieldDescriptor.TYPE_INT64: encoder.Int64Sizer,
+ _FieldDescriptor.TYPE_UINT64: encoder.UInt64Sizer,
+ _FieldDescriptor.TYPE_INT32: encoder.Int32Sizer,
+ _FieldDescriptor.TYPE_FIXED64: encoder.Fixed64Sizer,
+ _FieldDescriptor.TYPE_FIXED32: encoder.Fixed32Sizer,
+ _FieldDescriptor.TYPE_BOOL: encoder.BoolSizer,
+ _FieldDescriptor.TYPE_STRING: encoder.StringSizer,
+ _FieldDescriptor.TYPE_GROUP: encoder.GroupSizer,
+ _FieldDescriptor.TYPE_MESSAGE: encoder.MessageSizer,
+ _FieldDescriptor.TYPE_BYTES: encoder.BytesSizer,
+ _FieldDescriptor.TYPE_UINT32: encoder.UInt32Sizer,
+ _FieldDescriptor.TYPE_ENUM: encoder.EnumSizer,
+ _FieldDescriptor.TYPE_SFIXED32: encoder.SFixed32Sizer,
+ _FieldDescriptor.TYPE_SFIXED64: encoder.SFixed64Sizer,
+ _FieldDescriptor.TYPE_SINT32: encoder.SInt32Sizer,
+ _FieldDescriptor.TYPE_SINT64: encoder.SInt64Sizer,
+ }
+
+
+# Maps from field type to a decoder constructor.
+TYPE_TO_DECODER = {
+ _FieldDescriptor.TYPE_DOUBLE: decoder.DoubleDecoder,
+ _FieldDescriptor.TYPE_FLOAT: decoder.FloatDecoder,
+ _FieldDescriptor.TYPE_INT64: decoder.Int64Decoder,
+ _FieldDescriptor.TYPE_UINT64: decoder.UInt64Decoder,
+ _FieldDescriptor.TYPE_INT32: decoder.Int32Decoder,
+ _FieldDescriptor.TYPE_FIXED64: decoder.Fixed64Decoder,
+ _FieldDescriptor.TYPE_FIXED32: decoder.Fixed32Decoder,
+ _FieldDescriptor.TYPE_BOOL: decoder.BoolDecoder,
+ _FieldDescriptor.TYPE_STRING: decoder.StringDecoder,
+ _FieldDescriptor.TYPE_GROUP: decoder.GroupDecoder,
+ _FieldDescriptor.TYPE_MESSAGE: decoder.MessageDecoder,
+ _FieldDescriptor.TYPE_BYTES: decoder.BytesDecoder,
+ _FieldDescriptor.TYPE_UINT32: decoder.UInt32Decoder,
+ _FieldDescriptor.TYPE_ENUM: decoder.EnumDecoder,
+ _FieldDescriptor.TYPE_SFIXED32: decoder.SFixed32Decoder,
+ _FieldDescriptor.TYPE_SFIXED64: decoder.SFixed64Decoder,
+ _FieldDescriptor.TYPE_SINT32: decoder.SInt32Decoder,
+ _FieldDescriptor.TYPE_SINT64: decoder.SInt64Decoder,
+ }
+
+# Maps from field type to expected wiretype.
+FIELD_TYPE_TO_WIRE_TYPE = {
+ _FieldDescriptor.TYPE_DOUBLE: wire_format.WIRETYPE_FIXED64,
+ _FieldDescriptor.TYPE_FLOAT: wire_format.WIRETYPE_FIXED32,
+ _FieldDescriptor.TYPE_INT64: wire_format.WIRETYPE_VARINT,
+ _FieldDescriptor.TYPE_UINT64: wire_format.WIRETYPE_VARINT,
+ _FieldDescriptor.TYPE_INT32: wire_format.WIRETYPE_VARINT,
+ _FieldDescriptor.TYPE_FIXED64: wire_format.WIRETYPE_FIXED64,
+ _FieldDescriptor.TYPE_FIXED32: wire_format.WIRETYPE_FIXED32,
+ _FieldDescriptor.TYPE_BOOL: wire_format.WIRETYPE_VARINT,
+ _FieldDescriptor.TYPE_STRING:
+ wire_format.WIRETYPE_LENGTH_DELIMITED,
+ _FieldDescriptor.TYPE_GROUP: wire_format.WIRETYPE_START_GROUP,
+ _FieldDescriptor.TYPE_MESSAGE:
+ wire_format.WIRETYPE_LENGTH_DELIMITED,
+ _FieldDescriptor.TYPE_BYTES:
+ wire_format.WIRETYPE_LENGTH_DELIMITED,
+ _FieldDescriptor.TYPE_UINT32: wire_format.WIRETYPE_VARINT,
+ _FieldDescriptor.TYPE_ENUM: wire_format.WIRETYPE_VARINT,
+ _FieldDescriptor.TYPE_SFIXED32: wire_format.WIRETYPE_FIXED32,
+ _FieldDescriptor.TYPE_SFIXED64: wire_format.WIRETYPE_FIXED64,
+ _FieldDescriptor.TYPE_SINT32: wire_format.WIRETYPE_VARINT,
+ _FieldDescriptor.TYPE_SINT64: wire_format.WIRETYPE_VARINT,
+ }
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/unknown_fields_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/unknown_fields_test.py
new file mode 100755
index 0000000000..84073f1c53
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/unknown_fields_test.py
@@ -0,0 +1,320 @@
+#! /usr/bin/env python
+# -*- coding: utf-8 -*-
+#
+# 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.
+
+"""Test for preservation of unknown fields in the pure Python implementation."""
+
+__author__ = 'bohdank@google.com (Bohdan Koval)'
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+from google.protobuf import unittest_mset_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf import unittest_proto3_arena_pb2
+from google.protobuf.internal import api_implementation
+from google.protobuf.internal import encoder
+from google.protobuf.internal import message_set_extensions_pb2
+from google.protobuf.internal import missing_enum_values_pb2
+from google.protobuf.internal import test_util
+from google.protobuf.internal import type_checkers
+
+
+def SkipIfCppImplementation(func):
+ return unittest.skipIf(
+ api_implementation.Type() == 'cpp' and api_implementation.Version() == 2,
+ 'C++ implementation does not expose unknown fields to Python')(func)
+
+
+class UnknownFieldsTest(unittest.TestCase):
+
+ def setUp(self):
+ self.descriptor = unittest_pb2.TestAllTypes.DESCRIPTOR
+ self.all_fields = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(self.all_fields)
+ self.all_fields_data = self.all_fields.SerializeToString()
+ self.empty_message = unittest_pb2.TestEmptyMessage()
+ self.empty_message.ParseFromString(self.all_fields_data)
+
+ def testSerialize(self):
+ data = self.empty_message.SerializeToString()
+
+ # Don't use assertEqual because we don't want to dump raw binary data to
+ # stdout.
+ self.assertTrue(data == self.all_fields_data)
+
+ def testSerializeProto3(self):
+ # Verify that proto3 doesn't preserve unknown fields.
+ message = unittest_proto3_arena_pb2.TestEmptyMessage()
+ message.ParseFromString(self.all_fields_data)
+ self.assertEqual(0, len(message.SerializeToString()))
+
+ def testByteSize(self):
+ self.assertEqual(self.all_fields.ByteSize(), self.empty_message.ByteSize())
+
+ def testListFields(self):
+ # Make sure ListFields doesn't return unknown fields.
+ self.assertEqual(0, len(self.empty_message.ListFields()))
+
+ def testSerializeMessageSetWireFormatUnknownExtension(self):
+ # Create a message using the message set wire format with an unknown
+ # message.
+ raw = unittest_mset_pb2.RawMessageSet()
+
+ # Add an unknown extension.
+ item = raw.item.add()
+ item.type_id = 98418603
+ message1 = message_set_extensions_pb2.TestMessageSetExtension1()
+ message1.i = 12345
+ item.message = message1.SerializeToString()
+
+ serialized = raw.SerializeToString()
+
+ # Parse message using the message set wire format.
+ proto = message_set_extensions_pb2.TestMessageSet()
+ proto.MergeFromString(serialized)
+
+ # Verify that the unknown extension is serialized unchanged
+ reserialized = proto.SerializeToString()
+ new_raw = unittest_mset_pb2.RawMessageSet()
+ new_raw.MergeFromString(reserialized)
+ self.assertEqual(raw, new_raw)
+
+ def testEquals(self):
+ message = unittest_pb2.TestEmptyMessage()
+ message.ParseFromString(self.all_fields_data)
+ self.assertEqual(self.empty_message, message)
+
+ self.all_fields.ClearField('optional_string')
+ message.ParseFromString(self.all_fields.SerializeToString())
+ self.assertNotEqual(self.empty_message, message)
+
+ def testDiscardUnknownFields(self):
+ self.empty_message.DiscardUnknownFields()
+ self.assertEqual(b'', self.empty_message.SerializeToString())
+ # Test message field and repeated message field.
+ message = unittest_pb2.TestAllTypes()
+ other_message = unittest_pb2.TestAllTypes()
+ other_message.optional_string = 'discard'
+ message.optional_nested_message.ParseFromString(
+ other_message.SerializeToString())
+ message.repeated_nested_message.add().ParseFromString(
+ other_message.SerializeToString())
+ self.assertNotEqual(
+ b'', message.optional_nested_message.SerializeToString())
+ self.assertNotEqual(
+ b'', message.repeated_nested_message[0].SerializeToString())
+ message.DiscardUnknownFields()
+ self.assertEqual(b'', message.optional_nested_message.SerializeToString())
+ self.assertEqual(
+ b'', message.repeated_nested_message[0].SerializeToString())
+
+
+class UnknownFieldsAccessorsTest(unittest.TestCase):
+
+ def setUp(self):
+ self.descriptor = unittest_pb2.TestAllTypes.DESCRIPTOR
+ self.all_fields = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(self.all_fields)
+ self.all_fields_data = self.all_fields.SerializeToString()
+ self.empty_message = unittest_pb2.TestEmptyMessage()
+ self.empty_message.ParseFromString(self.all_fields_data)
+ if api_implementation.Type() != 'cpp':
+ # _unknown_fields is an implementation detail.
+ self.unknown_fields = self.empty_message._unknown_fields
+
+ # All the tests that use GetField() check an implementation detail of the
+ # Python implementation, which stores unknown fields as serialized strings.
+ # These tests are skipped by the C++ implementation: it's enough to check that
+ # the message is correctly serialized.
+
+ def GetField(self, name):
+ field_descriptor = self.descriptor.fields_by_name[name]
+ wire_type = type_checkers.FIELD_TYPE_TO_WIRE_TYPE[field_descriptor.type]
+ field_tag = encoder.TagBytes(field_descriptor.number, wire_type)
+ result_dict = {}
+ for tag_bytes, value in self.unknown_fields:
+ if tag_bytes == field_tag:
+ decoder = unittest_pb2.TestAllTypes._decoders_by_tag[tag_bytes][0]
+ decoder(value, 0, len(value), self.all_fields, result_dict)
+ return result_dict[field_descriptor]
+
+ @SkipIfCppImplementation
+ def testEnum(self):
+ value = self.GetField('optional_nested_enum')
+ self.assertEqual(self.all_fields.optional_nested_enum, value)
+
+ @SkipIfCppImplementation
+ def testRepeatedEnum(self):
+ value = self.GetField('repeated_nested_enum')
+ self.assertEqual(self.all_fields.repeated_nested_enum, value)
+
+ @SkipIfCppImplementation
+ def testVarint(self):
+ value = self.GetField('optional_int32')
+ self.assertEqual(self.all_fields.optional_int32, value)
+
+ @SkipIfCppImplementation
+ def testFixed32(self):
+ value = self.GetField('optional_fixed32')
+ self.assertEqual(self.all_fields.optional_fixed32, value)
+
+ @SkipIfCppImplementation
+ def testFixed64(self):
+ value = self.GetField('optional_fixed64')
+ self.assertEqual(self.all_fields.optional_fixed64, value)
+
+ @SkipIfCppImplementation
+ def testLengthDelimited(self):
+ value = self.GetField('optional_string')
+ self.assertEqual(self.all_fields.optional_string, value)
+
+ @SkipIfCppImplementation
+ def testGroup(self):
+ value = self.GetField('optionalgroup')
+ self.assertEqual(self.all_fields.optionalgroup, value)
+
+ def testCopyFrom(self):
+ message = unittest_pb2.TestEmptyMessage()
+ message.CopyFrom(self.empty_message)
+ self.assertEqual(message.SerializeToString(), self.all_fields_data)
+
+ def testMergeFrom(self):
+ message = unittest_pb2.TestAllTypes()
+ message.optional_int32 = 1
+ message.optional_uint32 = 2
+ source = unittest_pb2.TestEmptyMessage()
+ source.ParseFromString(message.SerializeToString())
+
+ message.ClearField('optional_int32')
+ message.optional_int64 = 3
+ message.optional_uint32 = 4
+ destination = unittest_pb2.TestEmptyMessage()
+ destination.ParseFromString(message.SerializeToString())
+
+ destination.MergeFrom(source)
+ # Check that the fields where correctly merged, even stored in the unknown
+ # fields set.
+ message.ParseFromString(destination.SerializeToString())
+ self.assertEqual(message.optional_int32, 1)
+ self.assertEqual(message.optional_uint32, 2)
+ self.assertEqual(message.optional_int64, 3)
+
+ def testClear(self):
+ self.empty_message.Clear()
+ # All cleared, even unknown fields.
+ self.assertEqual(self.empty_message.SerializeToString(), b'')
+
+ def testUnknownExtensions(self):
+ message = unittest_pb2.TestEmptyMessageWithExtensions()
+ message.ParseFromString(self.all_fields_data)
+ self.assertEqual(message.SerializeToString(), self.all_fields_data)
+
+
+class UnknownEnumValuesTest(unittest.TestCase):
+
+ def setUp(self):
+ self.descriptor = missing_enum_values_pb2.TestEnumValues.DESCRIPTOR
+
+ self.message = missing_enum_values_pb2.TestEnumValues()
+ self.message.optional_nested_enum = (
+ missing_enum_values_pb2.TestEnumValues.ZERO)
+ self.message.repeated_nested_enum.extend([
+ missing_enum_values_pb2.TestEnumValues.ZERO,
+ missing_enum_values_pb2.TestEnumValues.ONE,
+ ])
+ self.message.packed_nested_enum.extend([
+ missing_enum_values_pb2.TestEnumValues.ZERO,
+ missing_enum_values_pb2.TestEnumValues.ONE,
+ ])
+ self.message_data = self.message.SerializeToString()
+ self.missing_message = missing_enum_values_pb2.TestMissingEnumValues()
+ self.missing_message.ParseFromString(self.message_data)
+ if api_implementation.Type() != 'cpp':
+ # _unknown_fields is an implementation detail.
+ self.unknown_fields = self.missing_message._unknown_fields
+
+ # All the tests that use GetField() check an implementation detail of the
+ # Python implementation, which stores unknown fields as serialized strings.
+ # These tests are skipped by the C++ implementation: it's enough to check that
+ # the message is correctly serialized.
+
+ def GetField(self, name):
+ field_descriptor = self.descriptor.fields_by_name[name]
+ wire_type = type_checkers.FIELD_TYPE_TO_WIRE_TYPE[field_descriptor.type]
+ field_tag = encoder.TagBytes(field_descriptor.number, wire_type)
+ result_dict = {}
+ for tag_bytes, value in self.unknown_fields:
+ if tag_bytes == field_tag:
+ decoder = missing_enum_values_pb2.TestEnumValues._decoders_by_tag[
+ tag_bytes][0]
+ decoder(value, 0, len(value), self.message, result_dict)
+ return result_dict[field_descriptor]
+
+ def testUnknownParseMismatchEnumValue(self):
+ just_string = missing_enum_values_pb2.JustString()
+ just_string.dummy = 'blah'
+
+ missing = missing_enum_values_pb2.TestEnumValues()
+ # The parse is invalid, storing the string proto into the set of
+ # unknown fields.
+ missing.ParseFromString(just_string.SerializeToString())
+
+ # Fetching the enum field shouldn't crash, instead returning the
+ # default value.
+ self.assertEqual(missing.optional_nested_enum, 0)
+
+ @SkipIfCppImplementation
+ def testUnknownEnumValue(self):
+ self.assertFalse(self.missing_message.HasField('optional_nested_enum'))
+ value = self.GetField('optional_nested_enum')
+ self.assertEqual(self.message.optional_nested_enum, value)
+
+ @SkipIfCppImplementation
+ def testUnknownRepeatedEnumValue(self):
+ value = self.GetField('repeated_nested_enum')
+ self.assertEqual(self.message.repeated_nested_enum, value)
+
+ @SkipIfCppImplementation
+ def testUnknownPackedEnumValue(self):
+ value = self.GetField('packed_nested_enum')
+ self.assertEqual(self.message.packed_nested_enum, value)
+
+ def testRoundTrip(self):
+ new_message = missing_enum_values_pb2.TestEnumValues()
+ new_message.ParseFromString(self.missing_message.SerializeToString())
+ self.assertEqual(self.message, new_message)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types.py
new file mode 100644
index 0000000000..7c5dffd0fc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types.py
@@ -0,0 +1,724 @@
+# 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.
+
+"""Contains well known classes.
+
+This files defines well known classes which need extra maintenance including:
+ - Any
+ - Duration
+ - FieldMask
+ - Struct
+ - Timestamp
+"""
+
+__author__ = 'jieluo@google.com (Jie Luo)'
+
+from datetime import datetime
+from datetime import timedelta
+import six
+
+from google.protobuf.descriptor import FieldDescriptor
+
+_TIMESTAMPFOMAT = '%Y-%m-%dT%H:%M:%S'
+_NANOS_PER_SECOND = 1000000000
+_NANOS_PER_MILLISECOND = 1000000
+_NANOS_PER_MICROSECOND = 1000
+_MILLIS_PER_SECOND = 1000
+_MICROS_PER_SECOND = 1000000
+_SECONDS_PER_DAY = 24 * 3600
+
+
+class Error(Exception):
+ """Top-level module error."""
+
+
+class ParseError(Error):
+ """Thrown in case of parsing error."""
+
+
+class Any(object):
+ """Class for Any Message type."""
+
+ def Pack(self, msg, type_url_prefix='type.googleapis.com/'):
+ """Packs the specified message into current Any message."""
+ if len(type_url_prefix) < 1 or type_url_prefix[-1] != '/':
+ self.type_url = '%s/%s' % (type_url_prefix, msg.DESCRIPTOR.full_name)
+ else:
+ self.type_url = '%s%s' % (type_url_prefix, msg.DESCRIPTOR.full_name)
+ self.value = msg.SerializeToString()
+
+ def Unpack(self, msg):
+ """Unpacks the current Any message into specified message."""
+ descriptor = msg.DESCRIPTOR
+ if not self.Is(descriptor):
+ return False
+ msg.ParseFromString(self.value)
+ return True
+
+ def TypeName(self):
+ """Returns the protobuf type name of the inner message."""
+ # Only last part is to be used: b/25630112
+ return self.type_url.split('/')[-1]
+
+ def Is(self, descriptor):
+ """Checks if this Any represents the given protobuf type."""
+ return self.TypeName() == descriptor.full_name
+
+
+class Timestamp(object):
+ """Class for Timestamp message type."""
+
+ def ToJsonString(self):
+ """Converts Timestamp to RFC 3339 date string format.
+
+ Returns:
+ A string converted from timestamp. The string is always Z-normalized
+ and uses 3, 6 or 9 fractional digits as required to represent the
+ exact time. Example of the return format: '1972-01-01T10:00:20.021Z'
+ """
+ nanos = self.nanos % _NANOS_PER_SECOND
+ total_sec = self.seconds + (self.nanos - nanos) // _NANOS_PER_SECOND
+ seconds = total_sec % _SECONDS_PER_DAY
+ days = (total_sec - seconds) // _SECONDS_PER_DAY
+ dt = datetime(1970, 1, 1) + timedelta(days, seconds)
+
+ result = dt.isoformat()
+ if (nanos % 1e9) == 0:
+ # If there are 0 fractional digits, the fractional
+ # point '.' should be omitted when serializing.
+ return result + 'Z'
+ if (nanos % 1e6) == 0:
+ # Serialize 3 fractional digits.
+ return result + '.%03dZ' % (nanos / 1e6)
+ if (nanos % 1e3) == 0:
+ # Serialize 6 fractional digits.
+ return result + '.%06dZ' % (nanos / 1e3)
+ # Serialize 9 fractional digits.
+ return result + '.%09dZ' % nanos
+
+ def FromJsonString(self, value):
+ """Parse a RFC 3339 date string format to Timestamp.
+
+ Args:
+ value: A date string. Any fractional digits (or none) and any offset are
+ accepted as long as they fit into nano-seconds precision.
+ Example of accepted format: '1972-01-01T10:00:20.021-05:00'
+
+ Raises:
+ ParseError: On parsing problems.
+ """
+ timezone_offset = value.find('Z')
+ if timezone_offset == -1:
+ timezone_offset = value.find('+')
+ if timezone_offset == -1:
+ timezone_offset = value.rfind('-')
+ if timezone_offset == -1:
+ raise ParseError(
+ 'Failed to parse timestamp: missing valid timezone offset.')
+ time_value = value[0:timezone_offset]
+ # Parse datetime and nanos.
+ point_position = time_value.find('.')
+ if point_position == -1:
+ second_value = time_value
+ nano_value = ''
+ else:
+ second_value = time_value[:point_position]
+ nano_value = time_value[point_position + 1:]
+ date_object = datetime.strptime(second_value, _TIMESTAMPFOMAT)
+ td = date_object - datetime(1970, 1, 1)
+ seconds = td.seconds + td.days * _SECONDS_PER_DAY
+ if len(nano_value) > 9:
+ raise ParseError(
+ 'Failed to parse Timestamp: nanos {0} more than '
+ '9 fractional digits.'.format(nano_value))
+ if nano_value:
+ nanos = round(float('0.' + nano_value) * 1e9)
+ else:
+ nanos = 0
+ # Parse timezone offsets.
+ if value[timezone_offset] == 'Z':
+ if len(value) != timezone_offset + 1:
+ raise ParseError('Failed to parse timestamp: invalid trailing'
+ ' data {0}.'.format(value))
+ else:
+ timezone = value[timezone_offset:]
+ pos = timezone.find(':')
+ if pos == -1:
+ raise ParseError(
+ 'Invalid timezone offset value: {0}.'.format(timezone))
+ if timezone[0] == '+':
+ seconds -= (int(timezone[1:pos])*60+int(timezone[pos+1:]))*60
+ else:
+ seconds += (int(timezone[1:pos])*60+int(timezone[pos+1:]))*60
+ # Set seconds and nanos
+ self.seconds = int(seconds)
+ self.nanos = int(nanos)
+
+ def GetCurrentTime(self):
+ """Get the current UTC into Timestamp."""
+ self.FromDatetime(datetime.utcnow())
+
+ def ToNanoseconds(self):
+ """Converts Timestamp to nanoseconds since epoch."""
+ return self.seconds * _NANOS_PER_SECOND + self.nanos
+
+ def ToMicroseconds(self):
+ """Converts Timestamp to microseconds since epoch."""
+ return (self.seconds * _MICROS_PER_SECOND +
+ self.nanos // _NANOS_PER_MICROSECOND)
+
+ def ToMilliseconds(self):
+ """Converts Timestamp to milliseconds since epoch."""
+ return (self.seconds * _MILLIS_PER_SECOND +
+ self.nanos // _NANOS_PER_MILLISECOND)
+
+ def ToSeconds(self):
+ """Converts Timestamp to seconds since epoch."""
+ return self.seconds
+
+ def FromNanoseconds(self, nanos):
+ """Converts nanoseconds since epoch to Timestamp."""
+ self.seconds = nanos // _NANOS_PER_SECOND
+ self.nanos = nanos % _NANOS_PER_SECOND
+
+ def FromMicroseconds(self, micros):
+ """Converts microseconds since epoch to Timestamp."""
+ self.seconds = micros // _MICROS_PER_SECOND
+ self.nanos = (micros % _MICROS_PER_SECOND) * _NANOS_PER_MICROSECOND
+
+ def FromMilliseconds(self, millis):
+ """Converts milliseconds since epoch to Timestamp."""
+ self.seconds = millis // _MILLIS_PER_SECOND
+ self.nanos = (millis % _MILLIS_PER_SECOND) * _NANOS_PER_MILLISECOND
+
+ def FromSeconds(self, seconds):
+ """Converts seconds since epoch to Timestamp."""
+ self.seconds = seconds
+ self.nanos = 0
+
+ def ToDatetime(self):
+ """Converts Timestamp to datetime."""
+ return datetime.utcfromtimestamp(
+ self.seconds + self.nanos / float(_NANOS_PER_SECOND))
+
+ def FromDatetime(self, dt):
+ """Converts datetime to Timestamp."""
+ td = dt - datetime(1970, 1, 1)
+ self.seconds = td.seconds + td.days * _SECONDS_PER_DAY
+ self.nanos = td.microseconds * _NANOS_PER_MICROSECOND
+
+
+class Duration(object):
+ """Class for Duration message type."""
+
+ def ToJsonString(self):
+ """Converts Duration to string format.
+
+ Returns:
+ A string converted from self. The string format will contains
+ 3, 6, or 9 fractional digits depending on the precision required to
+ represent the exact Duration value. For example: "1s", "1.010s",
+ "1.000000100s", "-3.100s"
+ """
+ if self.seconds < 0 or self.nanos < 0:
+ result = '-'
+ seconds = - self.seconds + int((0 - self.nanos) // 1e9)
+ nanos = (0 - self.nanos) % 1e9
+ else:
+ result = ''
+ seconds = self.seconds + int(self.nanos // 1e9)
+ nanos = self.nanos % 1e9
+ result += '%d' % seconds
+ if (nanos % 1e9) == 0:
+ # If there are 0 fractional digits, the fractional
+ # point '.' should be omitted when serializing.
+ return result + 's'
+ if (nanos % 1e6) == 0:
+ # Serialize 3 fractional digits.
+ return result + '.%03ds' % (nanos / 1e6)
+ if (nanos % 1e3) == 0:
+ # Serialize 6 fractional digits.
+ return result + '.%06ds' % (nanos / 1e3)
+ # Serialize 9 fractional digits.
+ return result + '.%09ds' % nanos
+
+ def FromJsonString(self, value):
+ """Converts a string to Duration.
+
+ Args:
+ value: A string to be converted. The string must end with 's'. Any
+ fractional digits (or none) are accepted as long as they fit into
+ precision. For example: "1s", "1.01s", "1.0000001s", "-3.100s
+
+ Raises:
+ ParseError: On parsing problems.
+ """
+ if len(value) < 1 or value[-1] != 's':
+ raise ParseError(
+ 'Duration must end with letter "s": {0}.'.format(value))
+ try:
+ pos = value.find('.')
+ if pos == -1:
+ self.seconds = int(value[:-1])
+ self.nanos = 0
+ else:
+ self.seconds = int(value[:pos])
+ if value[0] == '-':
+ self.nanos = int(round(float('-0{0}'.format(value[pos: -1])) *1e9))
+ else:
+ self.nanos = int(round(float('0{0}'.format(value[pos: -1])) *1e9))
+ except ValueError:
+ raise ParseError(
+ 'Couldn\'t parse duration: {0}.'.format(value))
+
+ def ToNanoseconds(self):
+ """Converts a Duration to nanoseconds."""
+ return self.seconds * _NANOS_PER_SECOND + self.nanos
+
+ def ToMicroseconds(self):
+ """Converts a Duration to microseconds."""
+ micros = _RoundTowardZero(self.nanos, _NANOS_PER_MICROSECOND)
+ return self.seconds * _MICROS_PER_SECOND + micros
+
+ def ToMilliseconds(self):
+ """Converts a Duration to milliseconds."""
+ millis = _RoundTowardZero(self.nanos, _NANOS_PER_MILLISECOND)
+ return self.seconds * _MILLIS_PER_SECOND + millis
+
+ def ToSeconds(self):
+ """Converts a Duration to seconds."""
+ return self.seconds
+
+ def FromNanoseconds(self, nanos):
+ """Converts nanoseconds to Duration."""
+ self._NormalizeDuration(nanos // _NANOS_PER_SECOND,
+ nanos % _NANOS_PER_SECOND)
+
+ def FromMicroseconds(self, micros):
+ """Converts microseconds to Duration."""
+ self._NormalizeDuration(
+ micros // _MICROS_PER_SECOND,
+ (micros % _MICROS_PER_SECOND) * _NANOS_PER_MICROSECOND)
+
+ def FromMilliseconds(self, millis):
+ """Converts milliseconds to Duration."""
+ self._NormalizeDuration(
+ millis // _MILLIS_PER_SECOND,
+ (millis % _MILLIS_PER_SECOND) * _NANOS_PER_MILLISECOND)
+
+ def FromSeconds(self, seconds):
+ """Converts seconds to Duration."""
+ self.seconds = seconds
+ self.nanos = 0
+
+ def ToTimedelta(self):
+ """Converts Duration to timedelta."""
+ return timedelta(
+ seconds=self.seconds, microseconds=_RoundTowardZero(
+ self.nanos, _NANOS_PER_MICROSECOND))
+
+ def FromTimedelta(self, td):
+ """Convertd timedelta to Duration."""
+ self._NormalizeDuration(td.seconds + td.days * _SECONDS_PER_DAY,
+ td.microseconds * _NANOS_PER_MICROSECOND)
+
+ def _NormalizeDuration(self, seconds, nanos):
+ """Set Duration by seconds and nonas."""
+ # Force nanos to be negative if the duration is negative.
+ if seconds < 0 and nanos > 0:
+ seconds += 1
+ nanos -= _NANOS_PER_SECOND
+ self.seconds = seconds
+ self.nanos = nanos
+
+
+def _RoundTowardZero(value, divider):
+ """Truncates the remainder part after division."""
+ # For some languanges, the sign of the remainder is implementation
+ # dependent if any of the operands is negative. Here we enforce
+ # "rounded toward zero" semantics. For example, for (-5) / 2 an
+ # implementation may give -3 as the result with the remainder being
+ # 1. This function ensures we always return -2 (closer to zero).
+ result = value // divider
+ remainder = value % divider
+ if result < 0 and remainder > 0:
+ return result + 1
+ else:
+ return result
+
+
+class FieldMask(object):
+ """Class for FieldMask message type."""
+
+ def ToJsonString(self):
+ """Converts FieldMask to string according to proto3 JSON spec."""
+ return ','.join(self.paths)
+
+ def FromJsonString(self, value):
+ """Converts string to FieldMask according to proto3 JSON spec."""
+ self.Clear()
+ for path in value.split(','):
+ self.paths.append(path)
+
+ def IsValidForDescriptor(self, message_descriptor):
+ """Checks whether the FieldMask is valid for Message Descriptor."""
+ for path in self.paths:
+ if not _IsValidPath(message_descriptor, path):
+ return False
+ return True
+
+ def AllFieldsFromDescriptor(self, message_descriptor):
+ """Gets all direct fields of Message Descriptor to FieldMask."""
+ self.Clear()
+ for field in message_descriptor.fields:
+ self.paths.append(field.name)
+
+ def CanonicalFormFromMask(self, mask):
+ """Converts a FieldMask to the canonical form.
+
+ Removes paths that are covered by another path. For example,
+ "foo.bar" is covered by "foo" and will be removed if "foo"
+ is also in the FieldMask. Then sorts all paths in alphabetical order.
+
+ Args:
+ mask: The original FieldMask to be converted.
+ """
+ tree = _FieldMaskTree(mask)
+ tree.ToFieldMask(self)
+
+ def Union(self, mask1, mask2):
+ """Merges mask1 and mask2 into this FieldMask."""
+ _CheckFieldMaskMessage(mask1)
+ _CheckFieldMaskMessage(mask2)
+ tree = _FieldMaskTree(mask1)
+ tree.MergeFromFieldMask(mask2)
+ tree.ToFieldMask(self)
+
+ def Intersect(self, mask1, mask2):
+ """Intersects mask1 and mask2 into this FieldMask."""
+ _CheckFieldMaskMessage(mask1)
+ _CheckFieldMaskMessage(mask2)
+ tree = _FieldMaskTree(mask1)
+ intersection = _FieldMaskTree()
+ for path in mask2.paths:
+ tree.IntersectPath(path, intersection)
+ intersection.ToFieldMask(self)
+
+ def MergeMessage(
+ self, source, destination,
+ replace_message_field=False, replace_repeated_field=False):
+ """Merges fields specified in FieldMask from source to destination.
+
+ Args:
+ source: Source message.
+ destination: The destination message to be merged into.
+ replace_message_field: Replace message field if True. Merge message
+ field if False.
+ replace_repeated_field: Replace repeated field if True. Append
+ elements of repeated field if False.
+ """
+ tree = _FieldMaskTree(self)
+ tree.MergeMessage(
+ source, destination, replace_message_field, replace_repeated_field)
+
+
+def _IsValidPath(message_descriptor, path):
+ """Checks whether the path is valid for Message Descriptor."""
+ parts = path.split('.')
+ last = parts.pop()
+ for name in parts:
+ field = message_descriptor.fields_by_name[name]
+ if (field is None or
+ field.label == FieldDescriptor.LABEL_REPEATED or
+ field.type != FieldDescriptor.TYPE_MESSAGE):
+ return False
+ message_descriptor = field.message_type
+ return last in message_descriptor.fields_by_name
+
+
+def _CheckFieldMaskMessage(message):
+ """Raises ValueError if message is not a FieldMask."""
+ message_descriptor = message.DESCRIPTOR
+ if (message_descriptor.name != 'FieldMask' or
+ message_descriptor.file.name != 'google/protobuf/field_mask.proto'):
+ raise ValueError('Message {0} is not a FieldMask.'.format(
+ message_descriptor.full_name))
+
+
+class _FieldMaskTree(object):
+ """Represents a FieldMask in a tree structure.
+
+ For example, given a FieldMask "foo.bar,foo.baz,bar.baz",
+ the FieldMaskTree will be:
+ [_root] -+- foo -+- bar
+ | |
+ | +- baz
+ |
+ +- bar --- baz
+ In the tree, each leaf node represents a field path.
+ """
+
+ def __init__(self, field_mask=None):
+ """Initializes the tree by FieldMask."""
+ self._root = {}
+ if field_mask:
+ self.MergeFromFieldMask(field_mask)
+
+ def MergeFromFieldMask(self, field_mask):
+ """Merges a FieldMask to the tree."""
+ for path in field_mask.paths:
+ self.AddPath(path)
+
+ def AddPath(self, path):
+ """Adds a field path into the tree.
+
+ If the field path to add is a sub-path of an existing field path
+ in the tree (i.e., a leaf node), it means the tree already matches
+ the given path so nothing will be added to the tree. If the path
+ matches an existing non-leaf node in the tree, that non-leaf node
+ will be turned into a leaf node with all its children removed because
+ the path matches all the node's children. Otherwise, a new path will
+ be added.
+
+ Args:
+ path: The field path to add.
+ """
+ node = self._root
+ for name in path.split('.'):
+ if name not in node:
+ node[name] = {}
+ elif not node[name]:
+ # Pre-existing empty node implies we already have this entire tree.
+ return
+ node = node[name]
+ # Remove any sub-trees we might have had.
+ node.clear()
+
+ def ToFieldMask(self, field_mask):
+ """Converts the tree to a FieldMask."""
+ field_mask.Clear()
+ _AddFieldPaths(self._root, '', field_mask)
+
+ def IntersectPath(self, path, intersection):
+ """Calculates the intersection part of a field path with this tree.
+
+ Args:
+ path: The field path to calculates.
+ intersection: The out tree to record the intersection part.
+ """
+ node = self._root
+ for name in path.split('.'):
+ if name not in node:
+ return
+ elif not node[name]:
+ intersection.AddPath(path)
+ return
+ node = node[name]
+ intersection.AddLeafNodes(path, node)
+
+ def AddLeafNodes(self, prefix, node):
+ """Adds leaf nodes begin with prefix to this tree."""
+ if not node:
+ self.AddPath(prefix)
+ for name in node:
+ child_path = prefix + '.' + name
+ self.AddLeafNodes(child_path, node[name])
+
+ def MergeMessage(
+ self, source, destination,
+ replace_message, replace_repeated):
+ """Merge all fields specified by this tree from source to destination."""
+ _MergeMessage(
+ self._root, source, destination, replace_message, replace_repeated)
+
+
+def _StrConvert(value):
+ """Converts value to str if it is not."""
+ # This file is imported by c extension and some methods like ClearField
+ # requires string for the field name. py2/py3 has different text
+ # type and may use unicode.
+ if not isinstance(value, str):
+ return value.encode('utf-8')
+ return value
+
+
+def _MergeMessage(
+ node, source, destination, replace_message, replace_repeated):
+ """Merge all fields specified by a sub-tree from source to destination."""
+ source_descriptor = source.DESCRIPTOR
+ for name in node:
+ child = node[name]
+ field = source_descriptor.fields_by_name[name]
+ if field is None:
+ raise ValueError('Error: Can\'t find field {0} in message {1}.'.format(
+ name, source_descriptor.full_name))
+ if child:
+ # Sub-paths are only allowed for singular message fields.
+ if (field.label == FieldDescriptor.LABEL_REPEATED or
+ field.cpp_type != FieldDescriptor.CPPTYPE_MESSAGE):
+ raise ValueError('Error: Field {0} in message {1} is not a singular '
+ 'message field and cannot have sub-fields.'.format(
+ name, source_descriptor.full_name))
+ _MergeMessage(
+ child, getattr(source, name), getattr(destination, name),
+ replace_message, replace_repeated)
+ continue
+ if field.label == FieldDescriptor.LABEL_REPEATED:
+ if replace_repeated:
+ destination.ClearField(_StrConvert(name))
+ repeated_source = getattr(source, name)
+ repeated_destination = getattr(destination, name)
+ if field.cpp_type == FieldDescriptor.CPPTYPE_MESSAGE:
+ for item in repeated_source:
+ repeated_destination.add().MergeFrom(item)
+ else:
+ repeated_destination.extend(repeated_source)
+ else:
+ if field.cpp_type == FieldDescriptor.CPPTYPE_MESSAGE:
+ if replace_message:
+ destination.ClearField(_StrConvert(name))
+ if source.HasField(name):
+ getattr(destination, name).MergeFrom(getattr(source, name))
+ else:
+ setattr(destination, name, getattr(source, name))
+
+
+def _AddFieldPaths(node, prefix, field_mask):
+ """Adds the field paths descended from node to field_mask."""
+ if not node:
+ field_mask.paths.append(prefix)
+ return
+ for name in sorted(node):
+ if prefix:
+ child_path = prefix + '.' + name
+ else:
+ child_path = name
+ _AddFieldPaths(node[name], child_path, field_mask)
+
+
+_INT_OR_FLOAT = six.integer_types + (float,)
+
+
+def _SetStructValue(struct_value, value):
+ if value is None:
+ struct_value.null_value = 0
+ elif isinstance(value, bool):
+ # Note: this check must come before the number check because in Python
+ # True and False are also considered numbers.
+ struct_value.bool_value = value
+ elif isinstance(value, six.string_types):
+ struct_value.string_value = value
+ elif isinstance(value, _INT_OR_FLOAT):
+ struct_value.number_value = value
+ else:
+ raise ValueError('Unexpected type')
+
+
+def _GetStructValue(struct_value):
+ which = struct_value.WhichOneof('kind')
+ if which == 'struct_value':
+ return struct_value.struct_value
+ elif which == 'null_value':
+ return None
+ elif which == 'number_value':
+ return struct_value.number_value
+ elif which == 'string_value':
+ return struct_value.string_value
+ elif which == 'bool_value':
+ return struct_value.bool_value
+ elif which == 'list_value':
+ return struct_value.list_value
+ elif which is None:
+ raise ValueError('Value not set')
+
+
+class Struct(object):
+ """Class for Struct message type."""
+
+ __slots__ = []
+
+ def __getitem__(self, key):
+ return _GetStructValue(self.fields[key])
+
+ def __setitem__(self, key, value):
+ _SetStructValue(self.fields[key], value)
+
+ def get_or_create_list(self, key):
+ """Returns a list for this key, creating if it didn't exist already."""
+ return self.fields[key].list_value
+
+ def get_or_create_struct(self, key):
+ """Returns a struct for this key, creating if it didn't exist already."""
+ return self.fields[key].struct_value
+
+ # TODO(haberman): allow constructing/merging from dict.
+
+
+class ListValue(object):
+ """Class for ListValue message type."""
+
+ def __len__(self):
+ return len(self.values)
+
+ def append(self, value):
+ _SetStructValue(self.values.add(), value)
+
+ def extend(self, elem_seq):
+ for value in elem_seq:
+ self.append(value)
+
+ def __getitem__(self, index):
+ """Retrieves item by the specified index."""
+ return _GetStructValue(self.values.__getitem__(index))
+
+ def __setitem__(self, index, value):
+ _SetStructValue(self.values.__getitem__(index), value)
+
+ def items(self):
+ for i in range(len(self)):
+ yield self[i]
+
+ def add_struct(self):
+ """Appends and returns a struct value as the next value in the list."""
+ return self.values.add().struct_value
+
+ def add_list(self):
+ """Appends and returns a list value as the next value in the list."""
+ return self.values.add().list_value
+
+
+WKTBASES = {
+ 'google.protobuf.Any': Any,
+ 'google.protobuf.Duration': Duration,
+ 'google.protobuf.FieldMask': FieldMask,
+ 'google.protobuf.ListValue': ListValue,
+ 'google.protobuf.Struct': Struct,
+ 'google.protobuf.Timestamp': Timestamp,
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types_test.py
new file mode 100644
index 0000000000..2f32ac9941
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/well_known_types_test.py
@@ -0,0 +1,644 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Test for google.protobuf.internal.well_known_types."""
+
+__author__ = 'jieluo@google.com (Jie Luo)'
+
+from datetime import datetime
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import any_pb2
+from google.protobuf import duration_pb2
+from google.protobuf import field_mask_pb2
+from google.protobuf import struct_pb2
+from google.protobuf import timestamp_pb2
+from google.protobuf import unittest_pb2
+from google.protobuf.internal import any_test_pb2
+from google.protobuf.internal import test_util
+from google.protobuf.internal import well_known_types
+from google.protobuf import descriptor
+from google.protobuf import text_format
+
+
+class TimeUtilTestBase(unittest.TestCase):
+
+ def CheckTimestampConversion(self, message, text):
+ self.assertEqual(text, message.ToJsonString())
+ parsed_message = timestamp_pb2.Timestamp()
+ parsed_message.FromJsonString(text)
+ self.assertEqual(message, parsed_message)
+
+ def CheckDurationConversion(self, message, text):
+ self.assertEqual(text, message.ToJsonString())
+ parsed_message = duration_pb2.Duration()
+ parsed_message.FromJsonString(text)
+ self.assertEqual(message, parsed_message)
+
+
+class TimeUtilTest(TimeUtilTestBase):
+
+ def testTimestampSerializeAndParse(self):
+ message = timestamp_pb2.Timestamp()
+ # Generated output should contain 3, 6, or 9 fractional digits.
+ message.seconds = 0
+ message.nanos = 0
+ self.CheckTimestampConversion(message, '1970-01-01T00:00:00Z')
+ message.nanos = 10000000
+ self.CheckTimestampConversion(message, '1970-01-01T00:00:00.010Z')
+ message.nanos = 10000
+ self.CheckTimestampConversion(message, '1970-01-01T00:00:00.000010Z')
+ message.nanos = 10
+ self.CheckTimestampConversion(message, '1970-01-01T00:00:00.000000010Z')
+ # Test min timestamps.
+ message.seconds = -62135596800
+ message.nanos = 0
+ self.CheckTimestampConversion(message, '0001-01-01T00:00:00Z')
+ # Test max timestamps.
+ message.seconds = 253402300799
+ message.nanos = 999999999
+ self.CheckTimestampConversion(message, '9999-12-31T23:59:59.999999999Z')
+ # Test negative timestamps.
+ message.seconds = -1
+ self.CheckTimestampConversion(message, '1969-12-31T23:59:59.999999999Z')
+
+ # Parsing accepts an fractional digits as long as they fit into nano
+ # precision.
+ message.FromJsonString('1970-01-01T00:00:00.1Z')
+ self.assertEqual(0, message.seconds)
+ self.assertEqual(100000000, message.nanos)
+ # Parsing accpets offsets.
+ message.FromJsonString('1970-01-01T00:00:00-08:00')
+ self.assertEqual(8 * 3600, message.seconds)
+ self.assertEqual(0, message.nanos)
+
+ def testDurationSerializeAndParse(self):
+ message = duration_pb2.Duration()
+ # Generated output should contain 3, 6, or 9 fractional digits.
+ message.seconds = 0
+ message.nanos = 0
+ self.CheckDurationConversion(message, '0s')
+ message.nanos = 10000000
+ self.CheckDurationConversion(message, '0.010s')
+ message.nanos = 10000
+ self.CheckDurationConversion(message, '0.000010s')
+ message.nanos = 10
+ self.CheckDurationConversion(message, '0.000000010s')
+
+ # Test min and max
+ message.seconds = 315576000000
+ message.nanos = 999999999
+ self.CheckDurationConversion(message, '315576000000.999999999s')
+ message.seconds = -315576000000
+ message.nanos = -999999999
+ self.CheckDurationConversion(message, '-315576000000.999999999s')
+
+ # Parsing accepts an fractional digits as long as they fit into nano
+ # precision.
+ message.FromJsonString('0.1s')
+ self.assertEqual(100000000, message.nanos)
+ message.FromJsonString('0.0000001s')
+ self.assertEqual(100, message.nanos)
+
+ def testTimestampIntegerConversion(self):
+ message = timestamp_pb2.Timestamp()
+ message.FromNanoseconds(1)
+ self.assertEqual('1970-01-01T00:00:00.000000001Z',
+ message.ToJsonString())
+ self.assertEqual(1, message.ToNanoseconds())
+
+ message.FromNanoseconds(-1)
+ self.assertEqual('1969-12-31T23:59:59.999999999Z',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToNanoseconds())
+
+ message.FromMicroseconds(1)
+ self.assertEqual('1970-01-01T00:00:00.000001Z',
+ message.ToJsonString())
+ self.assertEqual(1, message.ToMicroseconds())
+
+ message.FromMicroseconds(-1)
+ self.assertEqual('1969-12-31T23:59:59.999999Z',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToMicroseconds())
+
+ message.FromMilliseconds(1)
+ self.assertEqual('1970-01-01T00:00:00.001Z',
+ message.ToJsonString())
+ self.assertEqual(1, message.ToMilliseconds())
+
+ message.FromMilliseconds(-1)
+ self.assertEqual('1969-12-31T23:59:59.999Z',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToMilliseconds())
+
+ message.FromSeconds(1)
+ self.assertEqual('1970-01-01T00:00:01Z',
+ message.ToJsonString())
+ self.assertEqual(1, message.ToSeconds())
+
+ message.FromSeconds(-1)
+ self.assertEqual('1969-12-31T23:59:59Z',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToSeconds())
+
+ message.FromNanoseconds(1999)
+ self.assertEqual(1, message.ToMicroseconds())
+ # For negative values, Timestamp will be rounded down.
+ # For example, "1969-12-31T23:59:59.5Z" (i.e., -0.5s) rounded to seconds
+ # will be "1969-12-31T23:59:59Z" (i.e., -1s) rather than
+ # "1970-01-01T00:00:00Z" (i.e., 0s).
+ message.FromNanoseconds(-1999)
+ self.assertEqual(-2, message.ToMicroseconds())
+
+ def testDurationIntegerConversion(self):
+ message = duration_pb2.Duration()
+ message.FromNanoseconds(1)
+ self.assertEqual('0.000000001s',
+ message.ToJsonString())
+ self.assertEqual(1, message.ToNanoseconds())
+
+ message.FromNanoseconds(-1)
+ self.assertEqual('-0.000000001s',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToNanoseconds())
+
+ message.FromMicroseconds(1)
+ self.assertEqual('0.000001s',
+ message.ToJsonString())
+ self.assertEqual(1, message.ToMicroseconds())
+
+ message.FromMicroseconds(-1)
+ self.assertEqual('-0.000001s',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToMicroseconds())
+
+ message.FromMilliseconds(1)
+ self.assertEqual('0.001s',
+ message.ToJsonString())
+ self.assertEqual(1, message.ToMilliseconds())
+
+ message.FromMilliseconds(-1)
+ self.assertEqual('-0.001s',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToMilliseconds())
+
+ message.FromSeconds(1)
+ self.assertEqual('1s', message.ToJsonString())
+ self.assertEqual(1, message.ToSeconds())
+
+ message.FromSeconds(-1)
+ self.assertEqual('-1s',
+ message.ToJsonString())
+ self.assertEqual(-1, message.ToSeconds())
+
+ # Test truncation behavior.
+ message.FromNanoseconds(1999)
+ self.assertEqual(1, message.ToMicroseconds())
+
+ # For negative values, Duration will be rounded towards 0.
+ message.FromNanoseconds(-1999)
+ self.assertEqual(-1, message.ToMicroseconds())
+
+ def testDatetimeConverison(self):
+ message = timestamp_pb2.Timestamp()
+ dt = datetime(1970, 1, 1)
+ message.FromDatetime(dt)
+ self.assertEqual(dt, message.ToDatetime())
+
+ message.FromMilliseconds(1999)
+ self.assertEqual(datetime(1970, 1, 1, 0, 0, 1, 999000),
+ message.ToDatetime())
+
+ def testTimedeltaConversion(self):
+ message = duration_pb2.Duration()
+ message.FromNanoseconds(1999999999)
+ td = message.ToTimedelta()
+ self.assertEqual(1, td.seconds)
+ self.assertEqual(999999, td.microseconds)
+
+ message.FromNanoseconds(-1999999999)
+ td = message.ToTimedelta()
+ self.assertEqual(-1, td.days)
+ self.assertEqual(86398, td.seconds)
+ self.assertEqual(1, td.microseconds)
+
+ message.FromMicroseconds(-1)
+ td = message.ToTimedelta()
+ self.assertEqual(-1, td.days)
+ self.assertEqual(86399, td.seconds)
+ self.assertEqual(999999, td.microseconds)
+ converted_message = duration_pb2.Duration()
+ converted_message.FromTimedelta(td)
+ self.assertEqual(message, converted_message)
+
+ def testInvalidTimestamp(self):
+ message = timestamp_pb2.Timestamp()
+ self.assertRaisesRegexp(
+ ValueError,
+ 'time data \'10000-01-01T00:00:00\' does not match'
+ ' format \'%Y-%m-%dT%H:%M:%S\'',
+ message.FromJsonString, '10000-01-01T00:00:00.00Z')
+ self.assertRaisesRegexp(
+ well_known_types.ParseError,
+ 'nanos 0123456789012 more than 9 fractional digits.',
+ message.FromJsonString,
+ '1970-01-01T00:00:00.0123456789012Z')
+ self.assertRaisesRegexp(
+ well_known_types.ParseError,
+ (r'Invalid timezone offset value: \+08.'),
+ message.FromJsonString,
+ '1972-01-01T01:00:00.01+08',)
+ self.assertRaisesRegexp(
+ ValueError,
+ 'year is out of range',
+ message.FromJsonString,
+ '0000-01-01T00:00:00Z')
+ message.seconds = 253402300800
+ self.assertRaisesRegexp(
+ OverflowError,
+ 'date value out of range',
+ message.ToJsonString)
+
+ def testInvalidDuration(self):
+ message = duration_pb2.Duration()
+ self.assertRaisesRegexp(
+ well_known_types.ParseError,
+ 'Duration must end with letter "s": 1.',
+ message.FromJsonString, '1')
+ self.assertRaisesRegexp(
+ well_known_types.ParseError,
+ 'Couldn\'t parse duration: 1...2s.',
+ message.FromJsonString, '1...2s')
+
+
+class FieldMaskTest(unittest.TestCase):
+
+ def testStringFormat(self):
+ mask = field_mask_pb2.FieldMask()
+ self.assertEqual('', mask.ToJsonString())
+ mask.paths.append('foo')
+ self.assertEqual('foo', mask.ToJsonString())
+ mask.paths.append('bar')
+ self.assertEqual('foo,bar', mask.ToJsonString())
+
+ mask.FromJsonString('')
+ self.assertEqual('', mask.ToJsonString())
+ mask.FromJsonString('foo')
+ self.assertEqual(['foo'], mask.paths)
+ mask.FromJsonString('foo,bar')
+ self.assertEqual(['foo', 'bar'], mask.paths)
+
+ def testDescriptorToFieldMask(self):
+ mask = field_mask_pb2.FieldMask()
+ msg_descriptor = unittest_pb2.TestAllTypes.DESCRIPTOR
+ mask.AllFieldsFromDescriptor(msg_descriptor)
+ self.assertEqual(75, len(mask.paths))
+ self.assertTrue(mask.IsValidForDescriptor(msg_descriptor))
+ for field in msg_descriptor.fields:
+ self.assertTrue(field.name in mask.paths)
+ mask.paths.append('optional_nested_message.bb')
+ self.assertTrue(mask.IsValidForDescriptor(msg_descriptor))
+ mask.paths.append('repeated_nested_message.bb')
+ self.assertFalse(mask.IsValidForDescriptor(msg_descriptor))
+
+ def testCanonicalFrom(self):
+ mask = field_mask_pb2.FieldMask()
+ out_mask = field_mask_pb2.FieldMask()
+ # Paths will be sorted.
+ mask.FromJsonString('baz.quz,bar,foo')
+ out_mask.CanonicalFormFromMask(mask)
+ self.assertEqual('bar,baz.quz,foo', out_mask.ToJsonString())
+ # Duplicated paths will be removed.
+ mask.FromJsonString('foo,bar,foo')
+ out_mask.CanonicalFormFromMask(mask)
+ self.assertEqual('bar,foo', out_mask.ToJsonString())
+ # Sub-paths of other paths will be removed.
+ mask.FromJsonString('foo.b1,bar.b1,foo.b2,bar')
+ out_mask.CanonicalFormFromMask(mask)
+ self.assertEqual('bar,foo.b1,foo.b2', out_mask.ToJsonString())
+
+ # Test more deeply nested cases.
+ mask.FromJsonString(
+ 'foo.bar.baz1,foo.bar.baz2.quz,foo.bar.baz2')
+ out_mask.CanonicalFormFromMask(mask)
+ self.assertEqual('foo.bar.baz1,foo.bar.baz2',
+ out_mask.ToJsonString())
+ mask.FromJsonString(
+ 'foo.bar.baz1,foo.bar.baz2,foo.bar.baz2.quz')
+ out_mask.CanonicalFormFromMask(mask)
+ self.assertEqual('foo.bar.baz1,foo.bar.baz2',
+ out_mask.ToJsonString())
+ mask.FromJsonString(
+ 'foo.bar.baz1,foo.bar.baz2,foo.bar.baz2.quz,foo.bar')
+ out_mask.CanonicalFormFromMask(mask)
+ self.assertEqual('foo.bar', out_mask.ToJsonString())
+ mask.FromJsonString(
+ 'foo.bar.baz1,foo.bar.baz2,foo.bar.baz2.quz,foo')
+ out_mask.CanonicalFormFromMask(mask)
+ self.assertEqual('foo', out_mask.ToJsonString())
+
+ def testUnion(self):
+ mask1 = field_mask_pb2.FieldMask()
+ mask2 = field_mask_pb2.FieldMask()
+ out_mask = field_mask_pb2.FieldMask()
+ mask1.FromJsonString('foo,baz')
+ mask2.FromJsonString('bar,quz')
+ out_mask.Union(mask1, mask2)
+ self.assertEqual('bar,baz,foo,quz', out_mask.ToJsonString())
+ # Overlap with duplicated paths.
+ mask1.FromJsonString('foo,baz.bb')
+ mask2.FromJsonString('baz.bb,quz')
+ out_mask.Union(mask1, mask2)
+ self.assertEqual('baz.bb,foo,quz', out_mask.ToJsonString())
+ # Overlap with paths covering some other paths.
+ mask1.FromJsonString('foo.bar.baz,quz')
+ mask2.FromJsonString('foo.bar,bar')
+ out_mask.Union(mask1, mask2)
+ self.assertEqual('bar,foo.bar,quz', out_mask.ToJsonString())
+
+ def testIntersect(self):
+ mask1 = field_mask_pb2.FieldMask()
+ mask2 = field_mask_pb2.FieldMask()
+ out_mask = field_mask_pb2.FieldMask()
+ # Test cases without overlapping.
+ mask1.FromJsonString('foo,baz')
+ mask2.FromJsonString('bar,quz')
+ out_mask.Intersect(mask1, mask2)
+ self.assertEqual('', out_mask.ToJsonString())
+ # Overlap with duplicated paths.
+ mask1.FromJsonString('foo,baz.bb')
+ mask2.FromJsonString('baz.bb,quz')
+ out_mask.Intersect(mask1, mask2)
+ self.assertEqual('baz.bb', out_mask.ToJsonString())
+ # Overlap with paths covering some other paths.
+ mask1.FromJsonString('foo.bar.baz,quz')
+ mask2.FromJsonString('foo.bar,bar')
+ out_mask.Intersect(mask1, mask2)
+ self.assertEqual('foo.bar.baz', out_mask.ToJsonString())
+ mask1.FromJsonString('foo.bar,bar')
+ mask2.FromJsonString('foo.bar.baz,quz')
+ out_mask.Intersect(mask1, mask2)
+ self.assertEqual('foo.bar.baz', out_mask.ToJsonString())
+
+ def testMergeMessage(self):
+ # Test merge one field.
+ src = unittest_pb2.TestAllTypes()
+ test_util.SetAllFields(src)
+ for field in src.DESCRIPTOR.fields:
+ if field.containing_oneof:
+ continue
+ field_name = field.name
+ dst = unittest_pb2.TestAllTypes()
+ # Only set one path to mask.
+ mask = field_mask_pb2.FieldMask()
+ mask.paths.append(field_name)
+ mask.MergeMessage(src, dst)
+ # The expected result message.
+ msg = unittest_pb2.TestAllTypes()
+ if field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ repeated_src = getattr(src, field_name)
+ repeated_msg = getattr(msg, field_name)
+ if field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ for item in repeated_src:
+ repeated_msg.add().CopyFrom(item)
+ else:
+ repeated_msg.extend(repeated_src)
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ getattr(msg, field_name).CopyFrom(getattr(src, field_name))
+ else:
+ setattr(msg, field_name, getattr(src, field_name))
+ # Only field specified in mask is merged.
+ self.assertEqual(msg, dst)
+
+ # Test merge nested fields.
+ nested_src = unittest_pb2.NestedTestAllTypes()
+ nested_dst = unittest_pb2.NestedTestAllTypes()
+ nested_src.child.payload.optional_int32 = 1234
+ nested_src.child.child.payload.optional_int32 = 5678
+ mask = field_mask_pb2.FieldMask()
+ mask.FromJsonString('child.payload')
+ mask.MergeMessage(nested_src, nested_dst)
+ self.assertEqual(1234, nested_dst.child.payload.optional_int32)
+ self.assertEqual(0, nested_dst.child.child.payload.optional_int32)
+
+ mask.FromJsonString('child.child.payload')
+ mask.MergeMessage(nested_src, nested_dst)
+ self.assertEqual(1234, nested_dst.child.payload.optional_int32)
+ self.assertEqual(5678, nested_dst.child.child.payload.optional_int32)
+
+ nested_dst.Clear()
+ mask.FromJsonString('child.child.payload')
+ mask.MergeMessage(nested_src, nested_dst)
+ self.assertEqual(0, nested_dst.child.payload.optional_int32)
+ self.assertEqual(5678, nested_dst.child.child.payload.optional_int32)
+
+ nested_dst.Clear()
+ mask.FromJsonString('child')
+ mask.MergeMessage(nested_src, nested_dst)
+ self.assertEqual(1234, nested_dst.child.payload.optional_int32)
+ self.assertEqual(5678, nested_dst.child.child.payload.optional_int32)
+
+ # Test MergeOptions.
+ nested_dst.Clear()
+ nested_dst.child.payload.optional_int64 = 4321
+ # Message fields will be merged by default.
+ mask.FromJsonString('child.payload')
+ mask.MergeMessage(nested_src, nested_dst)
+ self.assertEqual(1234, nested_dst.child.payload.optional_int32)
+ self.assertEqual(4321, nested_dst.child.payload.optional_int64)
+ # Change the behavior to replace message fields.
+ mask.FromJsonString('child.payload')
+ mask.MergeMessage(nested_src, nested_dst, True, False)
+ self.assertEqual(1234, nested_dst.child.payload.optional_int32)
+ self.assertEqual(0, nested_dst.child.payload.optional_int64)
+
+ # By default, fields missing in source are not cleared in destination.
+ nested_dst.payload.optional_int32 = 1234
+ self.assertTrue(nested_dst.HasField('payload'))
+ mask.FromJsonString('payload')
+ mask.MergeMessage(nested_src, nested_dst)
+ self.assertTrue(nested_dst.HasField('payload'))
+ # But they are cleared when replacing message fields.
+ nested_dst.Clear()
+ nested_dst.payload.optional_int32 = 1234
+ mask.FromJsonString('payload')
+ mask.MergeMessage(nested_src, nested_dst, True, False)
+ self.assertFalse(nested_dst.HasField('payload'))
+
+ nested_src.payload.repeated_int32.append(1234)
+ nested_dst.payload.repeated_int32.append(5678)
+ # Repeated fields will be appended by default.
+ mask.FromJsonString('payload.repeated_int32')
+ mask.MergeMessage(nested_src, nested_dst)
+ self.assertEqual(2, len(nested_dst.payload.repeated_int32))
+ self.assertEqual(5678, nested_dst.payload.repeated_int32[0])
+ self.assertEqual(1234, nested_dst.payload.repeated_int32[1])
+ # Change the behavior to replace repeated fields.
+ mask.FromJsonString('payload.repeated_int32')
+ mask.MergeMessage(nested_src, nested_dst, False, True)
+ self.assertEqual(1, len(nested_dst.payload.repeated_int32))
+ self.assertEqual(1234, nested_dst.payload.repeated_int32[0])
+
+
+class StructTest(unittest.TestCase):
+
+ def testStruct(self):
+ struct = struct_pb2.Struct()
+ struct_class = struct.__class__
+
+ struct['key1'] = 5
+ struct['key2'] = 'abc'
+ struct['key3'] = True
+ struct.get_or_create_struct('key4')['subkey'] = 11.0
+ struct_list = struct.get_or_create_list('key5')
+ struct_list.extend([6, 'seven', True, False, None])
+ struct_list.add_struct()['subkey2'] = 9
+
+ self.assertTrue(isinstance(struct, well_known_types.Struct))
+ self.assertEquals(5, struct['key1'])
+ self.assertEquals('abc', struct['key2'])
+ self.assertIs(True, struct['key3'])
+ self.assertEquals(11, struct['key4']['subkey'])
+ inner_struct = struct_class()
+ inner_struct['subkey2'] = 9
+ self.assertEquals([6, 'seven', True, False, None, inner_struct],
+ list(struct['key5'].items()))
+
+ serialized = struct.SerializeToString()
+
+ struct2 = struct_pb2.Struct()
+ struct2.ParseFromString(serialized)
+
+ self.assertEquals(struct, struct2)
+
+ self.assertTrue(isinstance(struct2, well_known_types.Struct))
+ self.assertEquals(5, struct2['key1'])
+ self.assertEquals('abc', struct2['key2'])
+ self.assertIs(True, struct2['key3'])
+ self.assertEquals(11, struct2['key4']['subkey'])
+ self.assertEquals([6, 'seven', True, False, None, inner_struct],
+ list(struct2['key5'].items()))
+
+ struct_list = struct2['key5']
+ self.assertEquals(6, struct_list[0])
+ self.assertEquals('seven', struct_list[1])
+ self.assertEquals(True, struct_list[2])
+ self.assertEquals(False, struct_list[3])
+ self.assertEquals(None, struct_list[4])
+ self.assertEquals(inner_struct, struct_list[5])
+
+ struct_list[1] = 7
+ self.assertEquals(7, struct_list[1])
+
+ struct_list.add_list().extend([1, 'two', True, False, None])
+ self.assertEquals([1, 'two', True, False, None],
+ list(struct_list[6].items()))
+
+ text_serialized = str(struct)
+ struct3 = struct_pb2.Struct()
+ text_format.Merge(text_serialized, struct3)
+ self.assertEquals(struct, struct3)
+
+ struct.get_or_create_struct('key3')['replace'] = 12
+ self.assertEquals(12, struct['key3']['replace'])
+
+
+class AnyTest(unittest.TestCase):
+
+ def testAnyMessage(self):
+ # Creates and sets message.
+ msg = any_test_pb2.TestAny()
+ msg_descriptor = msg.DESCRIPTOR
+ all_types = unittest_pb2.TestAllTypes()
+ all_descriptor = all_types.DESCRIPTOR
+ all_types.repeated_string.append(u'\u00fc\ua71f')
+ # Packs to Any.
+ msg.value.Pack(all_types)
+ self.assertEqual(msg.value.type_url,
+ 'type.googleapis.com/%s' % all_descriptor.full_name)
+ self.assertEqual(msg.value.value,
+ all_types.SerializeToString())
+ # Tests Is() method.
+ self.assertTrue(msg.value.Is(all_descriptor))
+ self.assertFalse(msg.value.Is(msg_descriptor))
+ # Unpacks Any.
+ unpacked_message = unittest_pb2.TestAllTypes()
+ self.assertTrue(msg.value.Unpack(unpacked_message))
+ self.assertEqual(all_types, unpacked_message)
+ # Unpacks to different type.
+ self.assertFalse(msg.value.Unpack(msg))
+ # Only Any messages have Pack method.
+ try:
+ msg.Pack(all_types)
+ except AttributeError:
+ pass
+ else:
+ raise AttributeError('%s should not have Pack method.' %
+ msg_descriptor.full_name)
+
+ def testMessageName(self):
+ # Creates and sets message.
+ submessage = any_test_pb2.TestAny()
+ submessage.int_value = 12345
+ msg = any_pb2.Any()
+ msg.Pack(submessage)
+ self.assertEqual(msg.TypeName(), 'google.protobuf.internal.TestAny')
+
+ def testPackWithCustomTypeUrl(self):
+ submessage = any_test_pb2.TestAny()
+ submessage.int_value = 12345
+ msg = any_pb2.Any()
+ # Pack with a custom type URL prefix.
+ msg.Pack(submessage, 'type.myservice.com')
+ self.assertEqual(msg.type_url,
+ 'type.myservice.com/%s' % submessage.DESCRIPTOR.full_name)
+ # Pack with a custom type URL prefix ending with '/'.
+ msg.Pack(submessage, 'type.myservice.com/')
+ self.assertEqual(msg.type_url,
+ 'type.myservice.com/%s' % submessage.DESCRIPTOR.full_name)
+ # Pack with an empty type URL prefix.
+ msg.Pack(submessage, '')
+ self.assertEqual(msg.type_url,
+ '/%s' % submessage.DESCRIPTOR.full_name)
+ # Test unpacking the type.
+ unpacked_message = any_test_pb2.TestAny()
+ self.assertTrue(msg.Unpack(unpacked_message))
+ self.assertEqual(submessage, unpacked_message)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format.py
new file mode 100755
index 0000000000..883f525585
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format.py
@@ -0,0 +1,268 @@
+# 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.
+
+"""Constants and static functions to support protocol buffer wire format."""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+import struct
+from google.protobuf import descriptor
+from google.protobuf import message
+
+
+TAG_TYPE_BITS = 3 # Number of bits used to hold type info in a proto tag.
+TAG_TYPE_MASK = (1 << TAG_TYPE_BITS) - 1 # 0x7
+
+# These numbers identify the wire type of a protocol buffer value.
+# We use the least-significant TAG_TYPE_BITS bits of the varint-encoded
+# tag-and-type to store one of these WIRETYPE_* constants.
+# These values must match WireType enum in google/protobuf/wire_format.h.
+WIRETYPE_VARINT = 0
+WIRETYPE_FIXED64 = 1
+WIRETYPE_LENGTH_DELIMITED = 2
+WIRETYPE_START_GROUP = 3
+WIRETYPE_END_GROUP = 4
+WIRETYPE_FIXED32 = 5
+_WIRETYPE_MAX = 5
+
+
+# Bounds for various integer types.
+INT32_MAX = int((1 << 31) - 1)
+INT32_MIN = int(-(1 << 31))
+UINT32_MAX = (1 << 32) - 1
+
+INT64_MAX = (1 << 63) - 1
+INT64_MIN = -(1 << 63)
+UINT64_MAX = (1 << 64) - 1
+
+# "struct" format strings that will encode/decode the specified formats.
+FORMAT_UINT32_LITTLE_ENDIAN = '<I'
+FORMAT_UINT64_LITTLE_ENDIAN = '<Q'
+FORMAT_FLOAT_LITTLE_ENDIAN = '<f'
+FORMAT_DOUBLE_LITTLE_ENDIAN = '<d'
+
+
+# We'll have to provide alternate implementations of AppendLittleEndian*() on
+# any architectures where these checks fail.
+if struct.calcsize(FORMAT_UINT32_LITTLE_ENDIAN) != 4:
+ raise AssertionError('Format "I" is not a 32-bit number.')
+if struct.calcsize(FORMAT_UINT64_LITTLE_ENDIAN) != 8:
+ raise AssertionError('Format "Q" is not a 64-bit number.')
+
+
+def PackTag(field_number, wire_type):
+ """Returns an unsigned 32-bit integer that encodes the field number and
+ wire type information in standard protocol message wire format.
+
+ Args:
+ field_number: Expected to be an integer in the range [1, 1 << 29)
+ wire_type: One of the WIRETYPE_* constants.
+ """
+ if not 0 <= wire_type <= _WIRETYPE_MAX:
+ raise message.EncodeError('Unknown wire type: %d' % wire_type)
+ return (field_number << TAG_TYPE_BITS) | wire_type
+
+
+def UnpackTag(tag):
+ """The inverse of PackTag(). Given an unsigned 32-bit number,
+ returns a (field_number, wire_type) tuple.
+ """
+ return (tag >> TAG_TYPE_BITS), (tag & TAG_TYPE_MASK)
+
+
+def ZigZagEncode(value):
+ """ZigZag Transform: Encodes signed integers so that they can be
+ effectively used with varint encoding. See wire_format.h for
+ more details.
+ """
+ if value >= 0:
+ return value << 1
+ return (value << 1) ^ (~0)
+
+
+def ZigZagDecode(value):
+ """Inverse of ZigZagEncode()."""
+ if not value & 0x1:
+ return value >> 1
+ return (value >> 1) ^ (~0)
+
+
+
+# The *ByteSize() functions below return the number of bytes required to
+# serialize "field number + type" information and then serialize the value.
+
+
+def Int32ByteSize(field_number, int32):
+ return Int64ByteSize(field_number, int32)
+
+
+def Int32ByteSizeNoTag(int32):
+ return _VarUInt64ByteSizeNoTag(0xffffffffffffffff & int32)
+
+
+def Int64ByteSize(field_number, int64):
+ # Have to convert to uint before calling UInt64ByteSize().
+ return UInt64ByteSize(field_number, 0xffffffffffffffff & int64)
+
+
+def UInt32ByteSize(field_number, uint32):
+ return UInt64ByteSize(field_number, uint32)
+
+
+def UInt64ByteSize(field_number, uint64):
+ return TagByteSize(field_number) + _VarUInt64ByteSizeNoTag(uint64)
+
+
+def SInt32ByteSize(field_number, int32):
+ return UInt32ByteSize(field_number, ZigZagEncode(int32))
+
+
+def SInt64ByteSize(field_number, int64):
+ return UInt64ByteSize(field_number, ZigZagEncode(int64))
+
+
+def Fixed32ByteSize(field_number, fixed32):
+ return TagByteSize(field_number) + 4
+
+
+def Fixed64ByteSize(field_number, fixed64):
+ return TagByteSize(field_number) + 8
+
+
+def SFixed32ByteSize(field_number, sfixed32):
+ return TagByteSize(field_number) + 4
+
+
+def SFixed64ByteSize(field_number, sfixed64):
+ return TagByteSize(field_number) + 8
+
+
+def FloatByteSize(field_number, flt):
+ return TagByteSize(field_number) + 4
+
+
+def DoubleByteSize(field_number, double):
+ return TagByteSize(field_number) + 8
+
+
+def BoolByteSize(field_number, b):
+ return TagByteSize(field_number) + 1
+
+
+def EnumByteSize(field_number, enum):
+ return UInt32ByteSize(field_number, enum)
+
+
+def StringByteSize(field_number, string):
+ return BytesByteSize(field_number, string.encode('utf-8'))
+
+
+def BytesByteSize(field_number, b):
+ return (TagByteSize(field_number)
+ + _VarUInt64ByteSizeNoTag(len(b))
+ + len(b))
+
+
+def GroupByteSize(field_number, message):
+ return (2 * TagByteSize(field_number) # START and END group.
+ + message.ByteSize())
+
+
+def MessageByteSize(field_number, message):
+ return (TagByteSize(field_number)
+ + _VarUInt64ByteSizeNoTag(message.ByteSize())
+ + message.ByteSize())
+
+
+def MessageSetItemByteSize(field_number, msg):
+ # First compute the sizes of the tags.
+ # There are 2 tags for the beginning and ending of the repeated group, that
+ # is field number 1, one with field number 2 (type_id) and one with field
+ # number 3 (message).
+ total_size = (2 * TagByteSize(1) + TagByteSize(2) + TagByteSize(3))
+
+ # Add the number of bytes for type_id.
+ total_size += _VarUInt64ByteSizeNoTag(field_number)
+
+ message_size = msg.ByteSize()
+
+ # The number of bytes for encoding the length of the message.
+ total_size += _VarUInt64ByteSizeNoTag(message_size)
+
+ # The size of the message.
+ total_size += message_size
+ return total_size
+
+
+def TagByteSize(field_number):
+ """Returns the bytes required to serialize a tag with this field number."""
+ # Just pass in type 0, since the type won't affect the tag+type size.
+ return _VarUInt64ByteSizeNoTag(PackTag(field_number, 0))
+
+
+# Private helper function for the *ByteSize() functions above.
+
+def _VarUInt64ByteSizeNoTag(uint64):
+ """Returns the number of bytes required to serialize a single varint
+ using boundary value comparisons. (unrolled loop optimization -WPierce)
+ uint64 must be unsigned.
+ """
+ if uint64 <= 0x7f: return 1
+ if uint64 <= 0x3fff: return 2
+ if uint64 <= 0x1fffff: return 3
+ if uint64 <= 0xfffffff: return 4
+ if uint64 <= 0x7ffffffff: return 5
+ if uint64 <= 0x3ffffffffff: return 6
+ if uint64 <= 0x1ffffffffffff: return 7
+ if uint64 <= 0xffffffffffffff: return 8
+ if uint64 <= 0x7fffffffffffffff: return 9
+ if uint64 > UINT64_MAX:
+ raise message.EncodeError('Value out of range: %d' % uint64)
+ return 10
+
+
+NON_PACKABLE_TYPES = (
+ descriptor.FieldDescriptor.TYPE_STRING,
+ descriptor.FieldDescriptor.TYPE_GROUP,
+ descriptor.FieldDescriptor.TYPE_MESSAGE,
+ descriptor.FieldDescriptor.TYPE_BYTES
+)
+
+
+def IsTypePackable(field_type):
+ """Return true iff packable = true is valid for fields of this type.
+
+ Args:
+ field_type: a FieldDescriptor::Type value.
+
+ Returns:
+ True iff fields of this type are packable.
+ """
+ return field_type not in NON_PACKABLE_TYPES
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format_test.py b/third_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format_test.py
new file mode 100755
index 0000000000..da120f3361
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/internal/wire_format_test.py
@@ -0,0 +1,257 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Test for google.protobuf.internal.wire_format."""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+try:
+ import unittest2 as unittest #PY26
+except ImportError:
+ import unittest
+
+from google.protobuf import message
+from google.protobuf.internal import wire_format
+
+
+class WireFormatTest(unittest.TestCase):
+
+ def testPackTag(self):
+ field_number = 0xabc
+ tag_type = 2
+ self.assertEqual((field_number << 3) | tag_type,
+ wire_format.PackTag(field_number, tag_type))
+ PackTag = wire_format.PackTag
+ # Number too high.
+ self.assertRaises(message.EncodeError, PackTag, field_number, 6)
+ # Number too low.
+ self.assertRaises(message.EncodeError, PackTag, field_number, -1)
+
+ def testUnpackTag(self):
+ # Test field numbers that will require various varint sizes.
+ for expected_field_number in (1, 15, 16, 2047, 2048):
+ for expected_wire_type in range(6): # Highest-numbered wiretype is 5.
+ field_number, wire_type = wire_format.UnpackTag(
+ wire_format.PackTag(expected_field_number, expected_wire_type))
+ self.assertEqual(expected_field_number, field_number)
+ self.assertEqual(expected_wire_type, wire_type)
+
+ self.assertRaises(TypeError, wire_format.UnpackTag, None)
+ self.assertRaises(TypeError, wire_format.UnpackTag, 'abc')
+ self.assertRaises(TypeError, wire_format.UnpackTag, 0.0)
+ self.assertRaises(TypeError, wire_format.UnpackTag, object())
+
+ def testZigZagEncode(self):
+ Z = wire_format.ZigZagEncode
+ self.assertEqual(0, Z(0))
+ self.assertEqual(1, Z(-1))
+ self.assertEqual(2, Z(1))
+ self.assertEqual(3, Z(-2))
+ self.assertEqual(4, Z(2))
+ self.assertEqual(0xfffffffe, Z(0x7fffffff))
+ self.assertEqual(0xffffffff, Z(-0x80000000))
+ self.assertEqual(0xfffffffffffffffe, Z(0x7fffffffffffffff))
+ self.assertEqual(0xffffffffffffffff, Z(-0x8000000000000000))
+
+ self.assertRaises(TypeError, Z, None)
+ self.assertRaises(TypeError, Z, 'abcd')
+ self.assertRaises(TypeError, Z, 0.0)
+ self.assertRaises(TypeError, Z, object())
+
+ def testZigZagDecode(self):
+ Z = wire_format.ZigZagDecode
+ self.assertEqual(0, Z(0))
+ self.assertEqual(-1, Z(1))
+ self.assertEqual(1, Z(2))
+ self.assertEqual(-2, Z(3))
+ self.assertEqual(2, Z(4))
+ self.assertEqual(0x7fffffff, Z(0xfffffffe))
+ self.assertEqual(-0x80000000, Z(0xffffffff))
+ self.assertEqual(0x7fffffffffffffff, Z(0xfffffffffffffffe))
+ self.assertEqual(-0x8000000000000000, Z(0xffffffffffffffff))
+
+ self.assertRaises(TypeError, Z, None)
+ self.assertRaises(TypeError, Z, 'abcd')
+ self.assertRaises(TypeError, Z, 0.0)
+ self.assertRaises(TypeError, Z, object())
+
+ def NumericByteSizeTestHelper(self, byte_size_fn, value, expected_value_size):
+ # Use field numbers that cause various byte sizes for the tag information.
+ for field_number, tag_bytes in ((15, 1), (16, 2), (2047, 2), (2048, 3)):
+ expected_size = expected_value_size + tag_bytes
+ actual_size = byte_size_fn(field_number, value)
+ self.assertEqual(expected_size, actual_size,
+ 'byte_size_fn: %s, field_number: %d, value: %r\n'
+ 'Expected: %d, Actual: %d'% (
+ byte_size_fn, field_number, value, expected_size, actual_size))
+
+ def testByteSizeFunctions(self):
+ # Test all numeric *ByteSize() functions.
+ NUMERIC_ARGS = [
+ # Int32ByteSize().
+ [wire_format.Int32ByteSize, 0, 1],
+ [wire_format.Int32ByteSize, 127, 1],
+ [wire_format.Int32ByteSize, 128, 2],
+ [wire_format.Int32ByteSize, -1, 10],
+ # Int64ByteSize().
+ [wire_format.Int64ByteSize, 0, 1],
+ [wire_format.Int64ByteSize, 127, 1],
+ [wire_format.Int64ByteSize, 128, 2],
+ [wire_format.Int64ByteSize, -1, 10],
+ # UInt32ByteSize().
+ [wire_format.UInt32ByteSize, 0, 1],
+ [wire_format.UInt32ByteSize, 127, 1],
+ [wire_format.UInt32ByteSize, 128, 2],
+ [wire_format.UInt32ByteSize, wire_format.UINT32_MAX, 5],
+ # UInt64ByteSize().
+ [wire_format.UInt64ByteSize, 0, 1],
+ [wire_format.UInt64ByteSize, 127, 1],
+ [wire_format.UInt64ByteSize, 128, 2],
+ [wire_format.UInt64ByteSize, wire_format.UINT64_MAX, 10],
+ # SInt32ByteSize().
+ [wire_format.SInt32ByteSize, 0, 1],
+ [wire_format.SInt32ByteSize, -1, 1],
+ [wire_format.SInt32ByteSize, 1, 1],
+ [wire_format.SInt32ByteSize, -63, 1],
+ [wire_format.SInt32ByteSize, 63, 1],
+ [wire_format.SInt32ByteSize, -64, 1],
+ [wire_format.SInt32ByteSize, 64, 2],
+ # SInt64ByteSize().
+ [wire_format.SInt64ByteSize, 0, 1],
+ [wire_format.SInt64ByteSize, -1, 1],
+ [wire_format.SInt64ByteSize, 1, 1],
+ [wire_format.SInt64ByteSize, -63, 1],
+ [wire_format.SInt64ByteSize, 63, 1],
+ [wire_format.SInt64ByteSize, -64, 1],
+ [wire_format.SInt64ByteSize, 64, 2],
+ # Fixed32ByteSize().
+ [wire_format.Fixed32ByteSize, 0, 4],
+ [wire_format.Fixed32ByteSize, wire_format.UINT32_MAX, 4],
+ # Fixed64ByteSize().
+ [wire_format.Fixed64ByteSize, 0, 8],
+ [wire_format.Fixed64ByteSize, wire_format.UINT64_MAX, 8],
+ # SFixed32ByteSize().
+ [wire_format.SFixed32ByteSize, 0, 4],
+ [wire_format.SFixed32ByteSize, wire_format.INT32_MIN, 4],
+ [wire_format.SFixed32ByteSize, wire_format.INT32_MAX, 4],
+ # SFixed64ByteSize().
+ [wire_format.SFixed64ByteSize, 0, 8],
+ [wire_format.SFixed64ByteSize, wire_format.INT64_MIN, 8],
+ [wire_format.SFixed64ByteSize, wire_format.INT64_MAX, 8],
+ # FloatByteSize().
+ [wire_format.FloatByteSize, 0.0, 4],
+ [wire_format.FloatByteSize, 1000000000.0, 4],
+ [wire_format.FloatByteSize, -1000000000.0, 4],
+ # DoubleByteSize().
+ [wire_format.DoubleByteSize, 0.0, 8],
+ [wire_format.DoubleByteSize, 1000000000.0, 8],
+ [wire_format.DoubleByteSize, -1000000000.0, 8],
+ # BoolByteSize().
+ [wire_format.BoolByteSize, False, 1],
+ [wire_format.BoolByteSize, True, 1],
+ # EnumByteSize().
+ [wire_format.EnumByteSize, 0, 1],
+ [wire_format.EnumByteSize, 127, 1],
+ [wire_format.EnumByteSize, 128, 2],
+ [wire_format.EnumByteSize, wire_format.UINT32_MAX, 5],
+ ]
+ for args in NUMERIC_ARGS:
+ self.NumericByteSizeTestHelper(*args)
+
+ # Test strings and bytes.
+ for byte_size_fn in (wire_format.StringByteSize, wire_format.BytesByteSize):
+ # 1 byte for tag, 1 byte for length, 3 bytes for contents.
+ self.assertEqual(5, byte_size_fn(10, 'abc'))
+ # 2 bytes for tag, 1 byte for length, 3 bytes for contents.
+ self.assertEqual(6, byte_size_fn(16, 'abc'))
+ # 2 bytes for tag, 2 bytes for length, 128 bytes for contents.
+ self.assertEqual(132, byte_size_fn(16, 'a' * 128))
+
+ # Test UTF-8 string byte size calculation.
+ # 1 byte for tag, 1 byte for length, 8 bytes for content.
+ self.assertEqual(10, wire_format.StringByteSize(
+ 5, b'\xd0\xa2\xd0\xb5\xd1\x81\xd1\x82'.decode('utf-8')))
+
+ class MockMessage(object):
+ def __init__(self, byte_size):
+ self.byte_size = byte_size
+ def ByteSize(self):
+ return self.byte_size
+
+ message_byte_size = 10
+ mock_message = MockMessage(byte_size=message_byte_size)
+ # Test groups.
+ # (2 * 1) bytes for begin and end tags, plus message_byte_size.
+ self.assertEqual(2 + message_byte_size,
+ wire_format.GroupByteSize(1, mock_message))
+ # (2 * 2) bytes for begin and end tags, plus message_byte_size.
+ self.assertEqual(4 + message_byte_size,
+ wire_format.GroupByteSize(16, mock_message))
+
+ # Test messages.
+ # 1 byte for tag, plus 1 byte for length, plus contents.
+ self.assertEqual(2 + mock_message.byte_size,
+ wire_format.MessageByteSize(1, mock_message))
+ # 2 bytes for tag, plus 1 byte for length, plus contents.
+ self.assertEqual(3 + mock_message.byte_size,
+ wire_format.MessageByteSize(16, mock_message))
+ # 2 bytes for tag, plus 2 bytes for length, plus contents.
+ mock_message.byte_size = 128
+ self.assertEqual(4 + mock_message.byte_size,
+ wire_format.MessageByteSize(16, mock_message))
+
+
+ # Test message set item byte size.
+ # 4 bytes for tags, plus 1 byte for length, plus 1 byte for type_id,
+ # plus contents.
+ mock_message.byte_size = 10
+ self.assertEqual(mock_message.byte_size + 6,
+ wire_format.MessageSetItemByteSize(1, mock_message))
+
+ # 4 bytes for tags, plus 2 bytes for length, plus 1 byte for type_id,
+ # plus contents.
+ mock_message.byte_size = 128
+ self.assertEqual(mock_message.byte_size + 7,
+ wire_format.MessageSetItemByteSize(1, mock_message))
+
+ # 4 bytes for tags, plus 2 bytes for length, plus 2 byte for type_id,
+ # plus contents.
+ self.assertEqual(mock_message.byte_size + 8,
+ wire_format.MessageSetItemByteSize(128, mock_message))
+
+ # Too-long varint.
+ self.assertRaises(message.EncodeError,
+ wire_format.UInt64ByteSize, 1, 1 << 128)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/json_format.py b/third_party/protobuf/3.0.0/python/google/protobuf/json_format.py
new file mode 100644
index 0000000000..bb6a19986e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/json_format.py
@@ -0,0 +1,664 @@
+# 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.
+
+"""Contains routines for printing protocol messages in JSON format.
+
+Simple usage example:
+
+ # Create a proto object and serialize it to a json format string.
+ message = my_proto_pb2.MyMessage(foo='bar')
+ json_string = json_format.MessageToJson(message)
+
+ # Parse a json format string to proto object.
+ message = json_format.Parse(json_string, my_proto_pb2.MyMessage())
+"""
+
+__author__ = 'jieluo@google.com (Jie Luo)'
+
+try:
+ from collections import OrderedDict
+except ImportError:
+ from ordereddict import OrderedDict #PY26
+import base64
+import json
+import math
+import re
+import six
+import sys
+
+from operator import methodcaller
+from google.protobuf import descriptor
+from google.protobuf import symbol_database
+
+_TIMESTAMPFOMAT = '%Y-%m-%dT%H:%M:%S'
+_INT_TYPES = frozenset([descriptor.FieldDescriptor.CPPTYPE_INT32,
+ descriptor.FieldDescriptor.CPPTYPE_UINT32,
+ descriptor.FieldDescriptor.CPPTYPE_INT64,
+ descriptor.FieldDescriptor.CPPTYPE_UINT64])
+_INT64_TYPES = frozenset([descriptor.FieldDescriptor.CPPTYPE_INT64,
+ descriptor.FieldDescriptor.CPPTYPE_UINT64])
+_FLOAT_TYPES = frozenset([descriptor.FieldDescriptor.CPPTYPE_FLOAT,
+ descriptor.FieldDescriptor.CPPTYPE_DOUBLE])
+_INFINITY = 'Infinity'
+_NEG_INFINITY = '-Infinity'
+_NAN = 'NaN'
+
+_UNPAIRED_SURROGATE_PATTERN = re.compile(six.u(
+ r'[\ud800-\udbff](?![\udc00-\udfff])|(?<![\ud800-\udbff])[\udc00-\udfff]'
+))
+
+class Error(Exception):
+ """Top-level module error for json_format."""
+
+
+class SerializeToJsonError(Error):
+ """Thrown if serialization to JSON fails."""
+
+
+class ParseError(Error):
+ """Thrown in case of parsing error."""
+
+
+def MessageToJson(message, including_default_value_fields=False):
+ """Converts protobuf message to JSON format.
+
+ Args:
+ message: The protocol buffers message instance to serialize.
+ including_default_value_fields: If True, singular primitive fields,
+ repeated fields, and map fields will always be serialized. If
+ False, only serialize non-empty fields. Singular message fields
+ and oneof fields are not affected by this option.
+
+ Returns:
+ A string containing the JSON formatted protocol buffer message.
+ """
+ printer = _Printer(including_default_value_fields)
+ return printer.ToJsonString(message)
+
+
+def _IsMapEntry(field):
+ return (field.type == descriptor.FieldDescriptor.TYPE_MESSAGE and
+ field.message_type.has_options and
+ field.message_type.GetOptions().map_entry)
+
+
+class _Printer(object):
+ """JSON format printer for protocol message."""
+
+ def __init__(self,
+ including_default_value_fields=False):
+ self.including_default_value_fields = including_default_value_fields
+
+ def ToJsonString(self, message):
+ js = self._MessageToJsonObject(message)
+ return json.dumps(js, indent=2)
+
+ def _MessageToJsonObject(self, message):
+ """Converts message to an object according to Proto3 JSON Specification."""
+ message_descriptor = message.DESCRIPTOR
+ full_name = message_descriptor.full_name
+ if _IsWrapperMessage(message_descriptor):
+ return self._WrapperMessageToJsonObject(message)
+ if full_name in _WKTJSONMETHODS:
+ return methodcaller(_WKTJSONMETHODS[full_name][0], message)(self)
+ js = {}
+ return self._RegularMessageToJsonObject(message, js)
+
+ def _RegularMessageToJsonObject(self, message, js):
+ """Converts normal message according to Proto3 JSON Specification."""
+ fields = message.ListFields()
+
+ try:
+ for field, value in fields:
+ name = field.camelcase_name
+ if _IsMapEntry(field):
+ # Convert a map field.
+ v_field = field.message_type.fields_by_name['value']
+ js_map = {}
+ for key in value:
+ if isinstance(key, bool):
+ if key:
+ recorded_key = 'true'
+ else:
+ recorded_key = 'false'
+ else:
+ recorded_key = key
+ js_map[recorded_key] = self._FieldToJsonObject(
+ v_field, value[key])
+ js[name] = js_map
+ elif field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ # Convert a repeated field.
+ js[name] = [self._FieldToJsonObject(field, k)
+ for k in value]
+ else:
+ js[name] = self._FieldToJsonObject(field, value)
+
+ # Serialize default value if including_default_value_fields is True.
+ if self.including_default_value_fields:
+ message_descriptor = message.DESCRIPTOR
+ for field in message_descriptor.fields:
+ # Singular message fields and oneof fields will not be affected.
+ if ((field.label != descriptor.FieldDescriptor.LABEL_REPEATED and
+ field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE) or
+ field.containing_oneof):
+ continue
+ name = field.camelcase_name
+ if name in js:
+ # Skip the field which has been serailized already.
+ continue
+ if _IsMapEntry(field):
+ js[name] = {}
+ elif field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ js[name] = []
+ else:
+ js[name] = self._FieldToJsonObject(field, field.default_value)
+
+ except ValueError as e:
+ raise SerializeToJsonError(
+ 'Failed to serialize {0} field: {1}.'.format(field.name, e))
+
+ return js
+
+ def _FieldToJsonObject(self, field, value):
+ """Converts field value according to Proto3 JSON Specification."""
+ if field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ return self._MessageToJsonObject(value)
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_ENUM:
+ enum_value = field.enum_type.values_by_number.get(value, None)
+ if enum_value is not None:
+ return enum_value.name
+ else:
+ raise SerializeToJsonError('Enum field contains an integer value '
+ 'which can not mapped to an enum value.')
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_STRING:
+ if field.type == descriptor.FieldDescriptor.TYPE_BYTES:
+ # Use base64 Data encoding for bytes
+ return base64.b64encode(value).decode('utf-8')
+ else:
+ return value
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_BOOL:
+ return bool(value)
+ elif field.cpp_type in _INT64_TYPES:
+ return str(value)
+ elif field.cpp_type in _FLOAT_TYPES:
+ if math.isinf(value):
+ if value < 0.0:
+ return _NEG_INFINITY
+ else:
+ return _INFINITY
+ if math.isnan(value):
+ return _NAN
+ return value
+
+ def _AnyMessageToJsonObject(self, message):
+ """Converts Any message according to Proto3 JSON Specification."""
+ if not message.ListFields():
+ return {}
+ # Must print @type first, use OrderedDict instead of {}
+ js = OrderedDict()
+ type_url = message.type_url
+ js['@type'] = type_url
+ sub_message = _CreateMessageFromTypeUrl(type_url)
+ sub_message.ParseFromString(message.value)
+ message_descriptor = sub_message.DESCRIPTOR
+ full_name = message_descriptor.full_name
+ if _IsWrapperMessage(message_descriptor):
+ js['value'] = self._WrapperMessageToJsonObject(sub_message)
+ return js
+ if full_name in _WKTJSONMETHODS:
+ js['value'] = methodcaller(_WKTJSONMETHODS[full_name][0],
+ sub_message)(self)
+ return js
+ return self._RegularMessageToJsonObject(sub_message, js)
+
+ def _GenericMessageToJsonObject(self, message):
+ """Converts message according to Proto3 JSON Specification."""
+ # Duration, Timestamp and FieldMask have ToJsonString method to do the
+ # convert. Users can also call the method directly.
+ return message.ToJsonString()
+
+ def _ValueMessageToJsonObject(self, message):
+ """Converts Value message according to Proto3 JSON Specification."""
+ which = message.WhichOneof('kind')
+ # If the Value message is not set treat as null_value when serialize
+ # to JSON. The parse back result will be different from original message.
+ if which is None or which == 'null_value':
+ return None
+ if which == 'list_value':
+ return self._ListValueMessageToJsonObject(message.list_value)
+ if which == 'struct_value':
+ value = message.struct_value
+ else:
+ value = getattr(message, which)
+ oneof_descriptor = message.DESCRIPTOR.fields_by_name[which]
+ return self._FieldToJsonObject(oneof_descriptor, value)
+
+ def _ListValueMessageToJsonObject(self, message):
+ """Converts ListValue message according to Proto3 JSON Specification."""
+ return [self._ValueMessageToJsonObject(value)
+ for value in message.values]
+
+ def _StructMessageToJsonObject(self, message):
+ """Converts Struct message according to Proto3 JSON Specification."""
+ fields = message.fields
+ ret = {}
+ for key in fields:
+ ret[key] = self._ValueMessageToJsonObject(fields[key])
+ return ret
+
+ def _WrapperMessageToJsonObject(self, message):
+ return self._FieldToJsonObject(
+ message.DESCRIPTOR.fields_by_name['value'], message.value)
+
+
+def _IsWrapperMessage(message_descriptor):
+ return message_descriptor.file.name == 'google/protobuf/wrappers.proto'
+
+
+def _DuplicateChecker(js):
+ result = {}
+ for name, value in js:
+ if name in result:
+ raise ParseError('Failed to load JSON: duplicate key {0}.'.format(name))
+ result[name] = value
+ return result
+
+
+def _CreateMessageFromTypeUrl(type_url):
+ # TODO(jieluo): Should add a way that users can register the type resolver
+ # instead of the default one.
+ db = symbol_database.Default()
+ type_name = type_url.split('/')[-1]
+ try:
+ message_descriptor = db.pool.FindMessageTypeByName(type_name)
+ except KeyError:
+ raise TypeError(
+ 'Can not find message descriptor by type_url: {0}.'.format(type_url))
+ message_class = db.GetPrototype(message_descriptor)
+ return message_class()
+
+
+def Parse(text, message, ignore_unknown_fields=False):
+ """Parses a JSON representation of a protocol message into a message.
+
+ Args:
+ text: Message JSON representation.
+ message: A protocol beffer message to merge into.
+ ignore_unknown_fields: If True, do not raise errors for unknown fields.
+
+ Returns:
+ The same message passed as argument.
+
+ Raises::
+ ParseError: On JSON parsing problems.
+ """
+ if not isinstance(text, six.text_type): text = text.decode('utf-8')
+ try:
+ if sys.version_info < (2, 7):
+ # object_pair_hook is not supported before python2.7
+ js = json.loads(text)
+ else:
+ js = json.loads(text, object_pairs_hook=_DuplicateChecker)
+ except ValueError as e:
+ raise ParseError('Failed to load JSON: {0}.'.format(str(e)))
+ parser = _Parser(ignore_unknown_fields)
+ parser.ConvertMessage(js, message)
+ return message
+
+
+_INT_OR_FLOAT = six.integer_types + (float,)
+
+
+class _Parser(object):
+ """JSON format parser for protocol message."""
+
+ def __init__(self,
+ ignore_unknown_fields):
+ self.ignore_unknown_fields = ignore_unknown_fields
+
+ def ConvertMessage(self, value, message):
+ """Convert a JSON object into a message.
+
+ Args:
+ value: A JSON object.
+ message: A WKT or regular protocol message to record the data.
+
+ Raises:
+ ParseError: In case of convert problems.
+ """
+ message_descriptor = message.DESCRIPTOR
+ full_name = message_descriptor.full_name
+ if _IsWrapperMessage(message_descriptor):
+ self._ConvertWrapperMessage(value, message)
+ elif full_name in _WKTJSONMETHODS:
+ methodcaller(_WKTJSONMETHODS[full_name][1], value, message)(self)
+ else:
+ self._ConvertFieldValuePair(value, message)
+
+ def _ConvertFieldValuePair(self, js, message):
+ """Convert field value pairs into regular message.
+
+ Args:
+ js: A JSON object to convert the field value pairs.
+ message: A regular protocol message to record the data.
+
+ Raises:
+ ParseError: In case of problems converting.
+ """
+ names = []
+ message_descriptor = message.DESCRIPTOR
+ for name in js:
+ try:
+ field = message_descriptor.fields_by_camelcase_name.get(name, None)
+ if not field:
+ if self.ignore_unknown_fields:
+ continue
+ raise ParseError(
+ 'Message type "{0}" has no field named "{1}".'.format(
+ message_descriptor.full_name, name))
+ if name in names:
+ raise ParseError('Message type "{0}" should not have multiple '
+ '"{1}" fields.'.format(
+ message.DESCRIPTOR.full_name, name))
+ names.append(name)
+ # Check no other oneof field is parsed.
+ if field.containing_oneof is not None:
+ oneof_name = field.containing_oneof.name
+ if oneof_name in names:
+ raise ParseError('Message type "{0}" should not have multiple '
+ '"{1}" oneof fields.'.format(
+ message.DESCRIPTOR.full_name, oneof_name))
+ names.append(oneof_name)
+
+ value = js[name]
+ if value is None:
+ message.ClearField(field.name)
+ continue
+
+ # Parse field value.
+ if _IsMapEntry(field):
+ message.ClearField(field.name)
+ self._ConvertMapFieldValue(value, message, field)
+ elif field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ message.ClearField(field.name)
+ if not isinstance(value, list):
+ raise ParseError('repeated field {0} must be in [] which is '
+ '{1}.'.format(name, value))
+ if field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ # Repeated message field.
+ for item in value:
+ sub_message = getattr(message, field.name).add()
+ # None is a null_value in Value.
+ if (item is None and
+ sub_message.DESCRIPTOR.full_name != 'google.protobuf.Value'):
+ raise ParseError('null is not allowed to be used as an element'
+ ' in a repeated field.')
+ self.ConvertMessage(item, sub_message)
+ else:
+ # Repeated scalar field.
+ for item in value:
+ if item is None:
+ raise ParseError('null is not allowed to be used as an element'
+ ' in a repeated field.')
+ getattr(message, field.name).append(
+ _ConvertScalarFieldValue(item, field))
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ sub_message = getattr(message, field.name)
+ self.ConvertMessage(value, sub_message)
+ else:
+ setattr(message, field.name, _ConvertScalarFieldValue(value, field))
+ except ParseError as e:
+ if field and field.containing_oneof is None:
+ raise ParseError('Failed to parse {0} field: {1}'.format(name, e))
+ else:
+ raise ParseError(str(e))
+ except ValueError as e:
+ raise ParseError('Failed to parse {0} field: {1}.'.format(name, e))
+ except TypeError as e:
+ raise ParseError('Failed to parse {0} field: {1}.'.format(name, e))
+
+ def _ConvertAnyMessage(self, value, message):
+ """Convert a JSON representation into Any message."""
+ if isinstance(value, dict) and not value:
+ return
+ try:
+ type_url = value['@type']
+ except KeyError:
+ raise ParseError('@type is missing when parsing any message.')
+
+ sub_message = _CreateMessageFromTypeUrl(type_url)
+ message_descriptor = sub_message.DESCRIPTOR
+ full_name = message_descriptor.full_name
+ if _IsWrapperMessage(message_descriptor):
+ self._ConvertWrapperMessage(value['value'], sub_message)
+ elif full_name in _WKTJSONMETHODS:
+ methodcaller(
+ _WKTJSONMETHODS[full_name][1], value['value'], sub_message)(self)
+ else:
+ del value['@type']
+ self._ConvertFieldValuePair(value, sub_message)
+ # Sets Any message
+ message.value = sub_message.SerializeToString()
+ message.type_url = type_url
+
+ def _ConvertGenericMessage(self, value, message):
+ """Convert a JSON representation into message with FromJsonString."""
+ # Durantion, Timestamp, FieldMask have FromJsonString method to do the
+ # convert. Users can also call the method directly.
+ message.FromJsonString(value)
+
+ def _ConvertValueMessage(self, value, message):
+ """Convert a JSON representation into Value message."""
+ if isinstance(value, dict):
+ self._ConvertStructMessage(value, message.struct_value)
+ elif isinstance(value, list):
+ self. _ConvertListValueMessage(value, message.list_value)
+ elif value is None:
+ message.null_value = 0
+ elif isinstance(value, bool):
+ message.bool_value = value
+ elif isinstance(value, six.string_types):
+ message.string_value = value
+ elif isinstance(value, _INT_OR_FLOAT):
+ message.number_value = value
+ else:
+ raise ParseError('Unexpected type for Value message.')
+
+ def _ConvertListValueMessage(self, value, message):
+ """Convert a JSON representation into ListValue message."""
+ if not isinstance(value, list):
+ raise ParseError(
+ 'ListValue must be in [] which is {0}.'.format(value))
+ message.ClearField('values')
+ for item in value:
+ self._ConvertValueMessage(item, message.values.add())
+
+ def _ConvertStructMessage(self, value, message):
+ """Convert a JSON representation into Struct message."""
+ if not isinstance(value, dict):
+ raise ParseError(
+ 'Struct must be in a dict which is {0}.'.format(value))
+ for key in value:
+ self._ConvertValueMessage(value[key], message.fields[key])
+ return
+
+ def _ConvertWrapperMessage(self, value, message):
+ """Convert a JSON representation into Wrapper message."""
+ field = message.DESCRIPTOR.fields_by_name['value']
+ setattr(message, 'value', _ConvertScalarFieldValue(value, field))
+
+ def _ConvertMapFieldValue(self, value, message, field):
+ """Convert map field value for a message map field.
+
+ Args:
+ value: A JSON object to convert the map field value.
+ message: A protocol message to record the converted data.
+ field: The descriptor of the map field to be converted.
+
+ Raises:
+ ParseError: In case of convert problems.
+ """
+ if not isinstance(value, dict):
+ raise ParseError(
+ 'Map field {0} must be in a dict which is {1}.'.format(
+ field.name, value))
+ key_field = field.message_type.fields_by_name['key']
+ value_field = field.message_type.fields_by_name['value']
+ for key in value:
+ key_value = _ConvertScalarFieldValue(key, key_field, True)
+ if value_field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ self.ConvertMessage(value[key], getattr(
+ message, field.name)[key_value])
+ else:
+ getattr(message, field.name)[key_value] = _ConvertScalarFieldValue(
+ value[key], value_field)
+
+
+def _ConvertScalarFieldValue(value, field, require_str=False):
+ """Convert a single scalar field value.
+
+ Args:
+ value: A scalar value to convert the scalar field value.
+ field: The descriptor of the field to convert.
+ require_str: If True, the field value must be a str.
+
+ Returns:
+ The converted scalar field value
+
+ Raises:
+ ParseError: In case of convert problems.
+ """
+ if field.cpp_type in _INT_TYPES:
+ return _ConvertInteger(value)
+ elif field.cpp_type in _FLOAT_TYPES:
+ return _ConvertFloat(value)
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_BOOL:
+ return _ConvertBool(value, require_str)
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_STRING:
+ if field.type == descriptor.FieldDescriptor.TYPE_BYTES:
+ return base64.b64decode(value)
+ else:
+ # Checking for unpaired surrogates appears to be unreliable,
+ # depending on the specific Python version, so we check manually.
+ if _UNPAIRED_SURROGATE_PATTERN.search(value):
+ raise ParseError('Unpaired surrogate')
+ return value
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_ENUM:
+ # Convert an enum value.
+ enum_value = field.enum_type.values_by_name.get(value, None)
+ if enum_value is None:
+ raise ParseError(
+ 'Enum value must be a string literal with double quotes. '
+ 'Type "{0}" has no value named {1}.'.format(
+ field.enum_type.full_name, value))
+ return enum_value.number
+
+
+def _ConvertInteger(value):
+ """Convert an integer.
+
+ Args:
+ value: A scalar value to convert.
+
+ Returns:
+ The integer value.
+
+ Raises:
+ ParseError: If an integer couldn't be consumed.
+ """
+ if isinstance(value, float):
+ raise ParseError('Couldn\'t parse integer: {0}.'.format(value))
+
+ if isinstance(value, six.text_type) and value.find(' ') != -1:
+ raise ParseError('Couldn\'t parse integer: "{0}".'.format(value))
+
+ return int(value)
+
+
+def _ConvertFloat(value):
+ """Convert an floating point number."""
+ if value == 'nan':
+ raise ParseError('Couldn\'t parse float "nan", use "NaN" instead.')
+ try:
+ # Assume Python compatible syntax.
+ return float(value)
+ except ValueError:
+ # Check alternative spellings.
+ if value == _NEG_INFINITY:
+ return float('-inf')
+ elif value == _INFINITY:
+ return float('inf')
+ elif value == _NAN:
+ return float('nan')
+ else:
+ raise ParseError('Couldn\'t parse float: {0}.'.format(value))
+
+
+def _ConvertBool(value, require_str):
+ """Convert a boolean value.
+
+ Args:
+ value: A scalar value to convert.
+ require_str: If True, value must be a str.
+
+ Returns:
+ The bool parsed.
+
+ Raises:
+ ParseError: If a boolean value couldn't be consumed.
+ """
+ if require_str:
+ if value == 'true':
+ return True
+ elif value == 'false':
+ return False
+ else:
+ raise ParseError('Expected "true" or "false", not {0}.'.format(value))
+
+ if not isinstance(value, bool):
+ raise ParseError('Expected true or false without quotes.')
+ return value
+
+_WKTJSONMETHODS = {
+ 'google.protobuf.Any': ['_AnyMessageToJsonObject',
+ '_ConvertAnyMessage'],
+ 'google.protobuf.Duration': ['_GenericMessageToJsonObject',
+ '_ConvertGenericMessage'],
+ 'google.protobuf.FieldMask': ['_GenericMessageToJsonObject',
+ '_ConvertGenericMessage'],
+ 'google.protobuf.ListValue': ['_ListValueMessageToJsonObject',
+ '_ConvertListValueMessage'],
+ 'google.protobuf.Struct': ['_StructMessageToJsonObject',
+ '_ConvertStructMessage'],
+ 'google.protobuf.Timestamp': ['_GenericMessageToJsonObject',
+ '_ConvertGenericMessage'],
+ 'google.protobuf.Value': ['_ValueMessageToJsonObject',
+ '_ConvertValueMessage']
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/message.py b/third_party/protobuf/3.0.0/python/google/protobuf/message.py
new file mode 100755
index 0000000000..606f735f3e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/message.py
@@ -0,0 +1,295 @@
+# 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.
+
+# TODO(robinson): We should just make these methods all "pure-virtual" and move
+# all implementation out, into reflection.py for now.
+
+
+"""Contains an abstract base class for protocol messages."""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+class Error(Exception): pass
+class DecodeError(Error): pass
+class EncodeError(Error): pass
+
+
+class Message(object):
+
+ """Abstract base class for protocol messages.
+
+ Protocol message classes are almost always generated by the protocol
+ compiler. These generated types subclass Message and implement the methods
+ shown below.
+
+ TODO(robinson): Link to an HTML document here.
+
+ TODO(robinson): Document that instances of this class will also
+ have an Extensions attribute with __getitem__ and __setitem__.
+ Again, not sure how to best convey this.
+
+ TODO(robinson): Document that the class must also have a static
+ RegisterExtension(extension_field) method.
+ Not sure how to best express at this point.
+ """
+
+ # TODO(robinson): Document these fields and methods.
+
+ __slots__ = []
+
+ DESCRIPTOR = None
+
+ def __deepcopy__(self, memo=None):
+ clone = type(self)()
+ clone.MergeFrom(self)
+ return clone
+
+ def __eq__(self, other_msg):
+ """Recursively compares two messages by value and structure."""
+ raise NotImplementedError
+
+ def __ne__(self, other_msg):
+ # Can't just say self != other_msg, since that would infinitely recurse. :)
+ return not self == other_msg
+
+ def __hash__(self):
+ raise TypeError('unhashable object')
+
+ def __str__(self):
+ """Outputs a human-readable representation of the message."""
+ raise NotImplementedError
+
+ def __unicode__(self):
+ """Outputs a human-readable representation of the message."""
+ raise NotImplementedError
+
+ def MergeFrom(self, other_msg):
+ """Merges the contents of the specified message into current message.
+
+ This method merges the contents of the specified message into the current
+ message. Singular fields that are set in the specified message overwrite
+ the corresponding fields in the current message. Repeated fields are
+ appended. Singular sub-messages and groups are recursively merged.
+
+ Args:
+ other_msg: Message to merge into the current message.
+ """
+ raise NotImplementedError
+
+ def CopyFrom(self, other_msg):
+ """Copies the content of the specified message into the current message.
+
+ The method clears the current message and then merges the specified
+ message using MergeFrom.
+
+ Args:
+ other_msg: Message to copy into the current one.
+ """
+ if self is other_msg:
+ return
+ self.Clear()
+ self.MergeFrom(other_msg)
+
+ def Clear(self):
+ """Clears all data that was set in the message."""
+ raise NotImplementedError
+
+ def SetInParent(self):
+ """Mark this as present in the parent.
+
+ This normally happens automatically when you assign a field of a
+ sub-message, but sometimes you want to make the sub-message
+ present while keeping it empty. If you find yourself using this,
+ you may want to reconsider your design."""
+ raise NotImplementedError
+
+ def IsInitialized(self):
+ """Checks if the message is initialized.
+
+ Returns:
+ The method returns True if the message is initialized (i.e. all of its
+ required fields are set).
+ """
+ raise NotImplementedError
+
+ # TODO(robinson): MergeFromString() should probably return None and be
+ # implemented in terms of a helper that returns the # of bytes read. Our
+ # deserialization routines would use the helper when recursively
+ # deserializing, but the end user would almost always just want the no-return
+ # MergeFromString().
+
+ def MergeFromString(self, serialized):
+ """Merges serialized protocol buffer data into this message.
+
+ When we find a field in |serialized| that is already present
+ in this message:
+ - If it's a "repeated" field, we append to the end of our list.
+ - Else, if it's a scalar, we overwrite our field.
+ - Else, (it's a nonrepeated composite), we recursively merge
+ into the existing composite.
+
+ TODO(robinson): Document handling of unknown fields.
+
+ Args:
+ serialized: Any object that allows us to call buffer(serialized)
+ to access a string of bytes using the buffer interface.
+
+ TODO(robinson): When we switch to a helper, this will return None.
+
+ Returns:
+ The number of bytes read from |serialized|.
+ For non-group messages, this will always be len(serialized),
+ but for messages which are actually groups, this will
+ generally be less than len(serialized), since we must
+ stop when we reach an END_GROUP tag. Note that if
+ we *do* stop because of an END_GROUP tag, the number
+ of bytes returned does not include the bytes
+ for the END_GROUP tag information.
+ """
+ raise NotImplementedError
+
+ def ParseFromString(self, serialized):
+ """Parse serialized protocol buffer data into this message.
+
+ Like MergeFromString(), except we clear the object first and
+ do not return the value that MergeFromString returns.
+ """
+ self.Clear()
+ self.MergeFromString(serialized)
+
+ def SerializeToString(self):
+ """Serializes the protocol message to a binary string.
+
+ Returns:
+ A binary string representation of the message if all of the required
+ fields in the message are set (i.e. the message is initialized).
+
+ Raises:
+ message.EncodeError if the message isn't initialized.
+ """
+ raise NotImplementedError
+
+ def SerializePartialToString(self):
+ """Serializes the protocol message to a binary string.
+
+ This method is similar to SerializeToString but doesn't check if the
+ message is initialized.
+
+ Returns:
+ A string representation of the partial message.
+ """
+ raise NotImplementedError
+
+ # TODO(robinson): Decide whether we like these better
+ # than auto-generated has_foo() and clear_foo() methods
+ # on the instances themselves. This way is less consistent
+ # with C++, but it makes reflection-type access easier and
+ # reduces the number of magically autogenerated things.
+ #
+ # TODO(robinson): Be sure to document (and test) exactly
+ # which field names are accepted here. Are we case-sensitive?
+ # What do we do with fields that share names with Python keywords
+ # like 'lambda' and 'yield'?
+ #
+ # nnorwitz says:
+ # """
+ # Typically (in python), an underscore is appended to names that are
+ # keywords. So they would become lambda_ or yield_.
+ # """
+ def ListFields(self):
+ """Returns a list of (FieldDescriptor, value) tuples for all
+ fields in the message which are not empty. A singular field is non-empty
+ if HasField() would return true, and a repeated field is non-empty if
+ it contains at least one element. The fields are ordered by field
+ number"""
+ raise NotImplementedError
+
+ def HasField(self, field_name):
+ """Checks if a certain field is set for the message, or if any field inside
+ a oneof group is set. Note that if the field_name is not defined in the
+ message descriptor, ValueError will be raised."""
+ raise NotImplementedError
+
+ def ClearField(self, field_name):
+ """Clears the contents of a given field, or the field set inside a oneof
+ group. If the name neither refers to a defined field or oneof group,
+ ValueError is raised."""
+ raise NotImplementedError
+
+ def WhichOneof(self, oneof_group):
+ """Returns the name of the field that is set inside a oneof group, or
+ None if no field is set. If no group with the given name exists, ValueError
+ will be raised."""
+ raise NotImplementedError
+
+ def HasExtension(self, extension_handle):
+ raise NotImplementedError
+
+ def ClearExtension(self, extension_handle):
+ raise NotImplementedError
+
+ def DiscardUnknownFields(self):
+ raise NotImplementedError
+
+ def ByteSize(self):
+ """Returns the serialized size of this message.
+ Recursively calls ByteSize() on all contained messages.
+ """
+ raise NotImplementedError
+
+ def _SetListener(self, message_listener):
+ """Internal method used by the protocol message implementation.
+ Clients should not call this directly.
+
+ Sets a listener that this message will call on certain state transitions.
+
+ The purpose of this method is to register back-edges from children to
+ parents at runtime, for the purpose of setting "has" bits and
+ byte-size-dirty bits in the parent and ancestor objects whenever a child or
+ descendant object is modified.
+
+ If the client wants to disconnect this Message from the object tree, she
+ explicitly sets callback to None.
+
+ If message_listener is None, unregisters any existing listener. Otherwise,
+ message_listener must implement the MessageListener interface in
+ internal/message_listener.py, and we discard any listener registered
+ via a previous _SetListener() call.
+ """
+ raise NotImplementedError
+
+ def __getstate__(self):
+ """Support the pickle protocol."""
+ return dict(serialized=self.SerializePartialToString())
+
+ def __setstate__(self, state):
+ """Support the pickle protocol."""
+ self.__init__()
+ self.ParseFromString(state['serialized'])
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/message_factory.py b/third_party/protobuf/3.0.0/python/google/protobuf/message_factory.py
new file mode 100644
index 0000000000..1b059d130b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/message_factory.py
@@ -0,0 +1,147 @@
+# 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.
+
+"""Provides a factory class for generating dynamic messages.
+
+The easiest way to use this class is if you have access to the FileDescriptor
+protos containing the messages you want to create you can just do the following:
+
+message_classes = message_factory.GetMessages(iterable_of_file_descriptors)
+my_proto_instance = message_classes['some.proto.package.MessageName']()
+"""
+
+__author__ = 'matthewtoia@google.com (Matt Toia)'
+
+from google.protobuf import descriptor_pool
+from google.protobuf import message
+from google.protobuf import reflection
+
+
+class MessageFactory(object):
+ """Factory for creating Proto2 messages from descriptors in a pool."""
+
+ def __init__(self, pool=None):
+ """Initializes a new factory."""
+ self.pool = pool or descriptor_pool.DescriptorPool()
+
+ # local cache of all classes built from protobuf descriptors
+ self._classes = {}
+
+ def GetPrototype(self, descriptor):
+ """Builds a proto2 message class based on the passed in descriptor.
+
+ Passing a descriptor with a fully qualified name matching a previous
+ invocation will cause the same class to be returned.
+
+ Args:
+ descriptor: The descriptor to build from.
+
+ Returns:
+ A class describing the passed in descriptor.
+ """
+ if descriptor.full_name not in self._classes:
+ descriptor_name = descriptor.name
+ if str is bytes: # PY2
+ descriptor_name = descriptor.name.encode('ascii', 'ignore')
+ result_class = reflection.GeneratedProtocolMessageType(
+ descriptor_name,
+ (message.Message,),
+ {'DESCRIPTOR': descriptor, '__module__': None})
+ # If module not set, it wrongly points to the reflection.py module.
+ self._classes[descriptor.full_name] = result_class
+ for field in descriptor.fields:
+ if field.message_type:
+ self.GetPrototype(field.message_type)
+ for extension in result_class.DESCRIPTOR.extensions:
+ if extension.containing_type.full_name not in self._classes:
+ self.GetPrototype(extension.containing_type)
+ extended_class = self._classes[extension.containing_type.full_name]
+ extended_class.RegisterExtension(extension)
+ return self._classes[descriptor.full_name]
+
+ def GetMessages(self, files):
+ """Gets all the messages from a specified file.
+
+ This will find and resolve dependencies, failing if the descriptor
+ pool cannot satisfy them.
+
+ Args:
+ files: The file names to extract messages from.
+
+ Returns:
+ A dictionary mapping proto names to the message classes. This will include
+ any dependent messages as well as any messages defined in the same file as
+ a specified message.
+ """
+ result = {}
+ for file_name in files:
+ file_desc = self.pool.FindFileByName(file_name)
+ for name, msg in file_desc.message_types_by_name.items():
+ if file_desc.package:
+ full_name = '.'.join([file_desc.package, name])
+ else:
+ full_name = msg.name
+ result[full_name] = self.GetPrototype(
+ self.pool.FindMessageTypeByName(full_name))
+
+ # While the extension FieldDescriptors are created by the descriptor pool,
+ # the python classes created in the factory need them to be registered
+ # explicitly, which is done below.
+ #
+ # The call to RegisterExtension will specifically check if the
+ # extension was already registered on the object and either
+ # ignore the registration if the original was the same, or raise
+ # an error if they were different.
+
+ for name, extension in file_desc.extensions_by_name.items():
+ if extension.containing_type.full_name not in self._classes:
+ self.GetPrototype(extension.containing_type)
+ extended_class = self._classes[extension.containing_type.full_name]
+ extended_class.RegisterExtension(extension)
+ return result
+
+
+_FACTORY = MessageFactory()
+
+
+def GetMessages(file_protos):
+ """Builds a dictionary of all the messages available in a set of files.
+
+ Args:
+ file_protos: A sequence of file protos to build messages out of.
+
+ Returns:
+ A dictionary mapping proto names to the message classes. This will include
+ any dependent messages as well as any messages defined in the same file as
+ a specified message.
+ """
+ for file_proto in file_protos:
+ _FACTORY.pool.Add(file_proto)
+ return _FACTORY.GetMessages([file_proto.name for file_proto in file_protos])
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/proto_builder.py b/third_party/protobuf/3.0.0/python/google/protobuf/proto_builder.py
new file mode 100644
index 0000000000..736caed385
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/proto_builder.py
@@ -0,0 +1,130 @@
+# 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.
+
+"""Dynamic Protobuf class creator."""
+
+try:
+ from collections import OrderedDict
+except ImportError:
+ from ordereddict import OrderedDict #PY26
+import hashlib
+import os
+
+from google.protobuf import descriptor_pb2
+from google.protobuf import message_factory
+
+
+def _GetMessageFromFactory(factory, full_name):
+ """Get a proto class from the MessageFactory by name.
+
+ Args:
+ factory: a MessageFactory instance.
+ full_name: str, the fully qualified name of the proto type.
+ Returns:
+ A class, for the type identified by full_name.
+ Raises:
+ KeyError, if the proto is not found in the factory's descriptor pool.
+ """
+ proto_descriptor = factory.pool.FindMessageTypeByName(full_name)
+ proto_cls = factory.GetPrototype(proto_descriptor)
+ return proto_cls
+
+
+def MakeSimpleProtoClass(fields, full_name=None, pool=None):
+ """Create a Protobuf class whose fields are basic types.
+
+ Note: this doesn't validate field names!
+
+ Args:
+ fields: dict of {name: field_type} mappings for each field in the proto. If
+ this is an OrderedDict the order will be maintained, otherwise the
+ fields will be sorted by name.
+ full_name: optional str, the fully-qualified name of the proto type.
+ pool: optional DescriptorPool instance.
+ Returns:
+ a class, the new protobuf class with a FileDescriptor.
+ """
+ factory = message_factory.MessageFactory(pool=pool)
+
+ if full_name is not None:
+ try:
+ proto_cls = _GetMessageFromFactory(factory, full_name)
+ return proto_cls
+ except KeyError:
+ # The factory's DescriptorPool doesn't know about this class yet.
+ pass
+
+ # Get a list of (name, field_type) tuples from the fields dict. If fields was
+ # an OrderedDict we keep the order, but otherwise we sort the field to ensure
+ # consistent ordering.
+ field_items = fields.items()
+ if not isinstance(fields, OrderedDict):
+ field_items = sorted(field_items)
+
+ # Use a consistent file name that is unlikely to conflict with any imported
+ # proto files.
+ fields_hash = hashlib.sha1()
+ for f_name, f_type in field_items:
+ fields_hash.update(f_name.encode('utf-8'))
+ fields_hash.update(str(f_type).encode('utf-8'))
+ proto_file_name = fields_hash.hexdigest() + '.proto'
+
+ # If the proto is anonymous, use the same hash to name it.
+ if full_name is None:
+ full_name = ('net.proto2.python.public.proto_builder.AnonymousProto_' +
+ fields_hash.hexdigest())
+ try:
+ proto_cls = _GetMessageFromFactory(factory, full_name)
+ return proto_cls
+ except KeyError:
+ # The factory's DescriptorPool doesn't know about this class yet.
+ pass
+
+ # This is the first time we see this proto: add a new descriptor to the pool.
+ factory.pool.Add(
+ _MakeFileDescriptorProto(proto_file_name, full_name, field_items))
+ return _GetMessageFromFactory(factory, full_name)
+
+
+def _MakeFileDescriptorProto(proto_file_name, full_name, field_items):
+ """Populate FileDescriptorProto for MessageFactory's DescriptorPool."""
+ package, name = full_name.rsplit('.', 1)
+ file_proto = descriptor_pb2.FileDescriptorProto()
+ file_proto.name = os.path.join(package.replace('.', '/'), proto_file_name)
+ file_proto.package = package
+ desc_proto = file_proto.message_type.add()
+ desc_proto.name = name
+ for f_number, (f_name, f_type) in enumerate(field_items, 1):
+ field_proto = desc_proto.field.add()
+ field_proto.name = f_name
+ field_proto.number = f_number
+ field_proto.label = descriptor_pb2.FieldDescriptorProto.LABEL_OPTIONAL
+ field_proto.type = f_type
+ return file_proto
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/README b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/README
new file mode 100644
index 0000000000..6d61cb45bf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/README
@@ -0,0 +1,6 @@
+This is the 'v2' C++ implementation for python proto2.
+
+It is active when:
+
+PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION=cpp
+PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION_VERSION=2
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/__init__.py b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/__init__.py
new file mode 100644
index 0000000000..5585614122
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/__init__.py
@@ -0,0 +1,4 @@
+try:
+ __import__('pkg_resources').declare_namespace(__name__)
+except ImportError:
+ __path__ = __import__('pkgutil').extend_path(__path__, __name__)
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/cpp_message.py b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/cpp_message.py
new file mode 100644
index 0000000000..fc8eb32d79
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/cpp_message.py
@@ -0,0 +1,65 @@
+# 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.
+
+"""Protocol message implementation hooks for C++ implementation.
+
+Contains helper functions used to create protocol message classes from
+Descriptor objects at runtime backed by the protocol buffer C++ API.
+"""
+
+__author__ = 'tibell@google.com (Johan Tibell)'
+
+from google.protobuf.pyext import _message
+
+
+class GeneratedProtocolMessageType(_message.MessageMeta):
+
+ """Metaclass for protocol message classes created at runtime from Descriptors.
+
+ The protocol compiler currently uses this metaclass to create protocol
+ message classes at runtime. Clients can also manually create their own
+ classes at runtime, as in this example:
+
+ mydescriptor = Descriptor(.....)
+ factory = symbol_database.Default()
+ factory.pool.AddDescriptor(mydescriptor)
+ MyProtoClass = factory.GetPrototype(mydescriptor)
+ myproto_instance = MyProtoClass()
+ myproto.foo_field = 23
+ ...
+
+ The above example will not work for nested types. If you wish to include them,
+ use reflection.MakeClass() instead of manually instantiating the class in
+ order to create the appropriate class structure.
+ """
+
+ # Must be consistent with the protocol-compiler code in
+ # proto2/compiler/internal/generator.*.
+ _DESCRIPTOR_KEY = 'DESCRIPTOR'
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.cc
new file mode 100644
index 0000000000..e6ef5ef50a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.cc
@@ -0,0 +1,1845 @@
+// 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: petar@google.com (Petar Petrov)
+
+#include <Python.h>
+#include <frameobject.h>
+#include <string>
+
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/pyext/descriptor.h>
+#include <google/protobuf/pyext/descriptor_containers.h>
+#include <google/protobuf/pyext/descriptor_pool.h>
+#include <google/protobuf/pyext/message.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+
+#if PY_MAJOR_VERSION >= 3
+ #define PyString_FromStringAndSize PyUnicode_FromStringAndSize
+ #define PyString_Check PyUnicode_Check
+ #define PyString_InternFromString PyUnicode_InternFromString
+ #define PyInt_FromLong PyLong_FromLong
+ #define PyInt_FromSize_t PyLong_FromSize_t
+ #if PY_VERSION_HEX < 0x03030000
+ #error "Python 3.0 - 3.2 are not supported."
+ #endif
+ #define PyString_AsStringAndSize(ob, charpp, sizep) \
+ (PyUnicode_Check(ob)? \
+ ((*(charpp) = PyUnicode_AsUTF8AndSize(ob, (sizep))) == NULL? -1: 0): \
+ PyBytes_AsStringAndSize(ob, (charpp), (sizep)))
+#endif
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+// Store interned descriptors, so that the same C++ descriptor yields the same
+// Python object. Objects are not immortal: this map does not own the
+// references, and items are deleted when the last reference to the object is
+// released.
+// This is enough to support the "is" operator on live objects.
+// All descriptors are stored here.
+hash_map<const void*, PyObject*> interned_descriptors;
+
+PyObject* PyString_FromCppString(const string& str) {
+ return PyString_FromStringAndSize(str.c_str(), str.size());
+}
+
+// Check that the calling Python code is the global scope of a _pb2.py module.
+// This function is used to support the current code generated by the proto
+// compiler, which creates descriptors, then update some properties.
+// For example:
+// message_descriptor = Descriptor(
+// name='Message',
+// fields = [FieldDescriptor(name='field')]
+// message_descriptor.fields[0].containing_type = message_descriptor
+//
+// This code is still executed, but the descriptors now have no other storage
+// than the (const) C++ pointer, and are immutable.
+// So we let this code pass, by simply ignoring the new value.
+//
+// From user code, descriptors still look immutable.
+//
+// TODO(amauryfa): Change the proto2 compiler to remove the assignments, and
+// remove this hack.
+bool _CalledFromGeneratedFile(int stacklevel) {
+#ifndef PYPY_VERSION
+ // This check is not critical and is somewhat difficult to implement correctly
+ // in PyPy.
+ PyFrameObject* frame = PyEval_GetFrame();
+ if (frame == NULL) {
+ return false;
+ }
+ while (stacklevel-- > 0) {
+ frame = frame->f_back;
+ if (frame == NULL) {
+ return false;
+ }
+ }
+ if (frame->f_globals != frame->f_locals) {
+ // Not at global module scope
+ return false;
+ }
+
+ if (frame->f_code->co_filename == NULL) {
+ return false;
+ }
+ char* filename;
+ Py_ssize_t filename_size;
+ if (PyString_AsStringAndSize(frame->f_code->co_filename,
+ &filename, &filename_size) < 0) {
+ // filename is not a string.
+ PyErr_Clear();
+ return false;
+ }
+ if (filename_size < 7) {
+ // filename is too short.
+ return false;
+ }
+ if (strcmp(&filename[filename_size - 7], "_pb2.py") != 0) {
+ // Filename is not ending with _pb2.
+ return false;
+ }
+#endif
+ return true;
+}
+
+// If the calling code is not a _pb2.py file, raise AttributeError.
+// To be used in attribute setters.
+static int CheckCalledFromGeneratedFile(const char* attr_name) {
+ if (_CalledFromGeneratedFile(0)) {
+ return 0;
+ }
+ PyErr_Format(PyExc_AttributeError,
+ "attribute is not writable: %s", attr_name);
+ return -1;
+}
+
+
+#ifndef PyVarObject_HEAD_INIT
+#define PyVarObject_HEAD_INIT(type, size) PyObject_HEAD_INIT(type) size,
+#endif
+#ifndef Py_TYPE
+#define Py_TYPE(ob) (((PyObject*)(ob))->ob_type)
+#endif
+
+
+// Helper functions for descriptor objects.
+
+// A set of templates to retrieve the C++ FileDescriptor of any descriptor.
+template<class DescriptorClass>
+const FileDescriptor* GetFileDescriptor(const DescriptorClass* descriptor) {
+ return descriptor->file();
+}
+template<>
+const FileDescriptor* GetFileDescriptor(const FileDescriptor* descriptor) {
+ return descriptor;
+}
+template<>
+const FileDescriptor* GetFileDescriptor(const EnumValueDescriptor* descriptor) {
+ return descriptor->type()->file();
+}
+template<>
+const FileDescriptor* GetFileDescriptor(const OneofDescriptor* descriptor) {
+ return descriptor->containing_type()->file();
+}
+template<>
+const FileDescriptor* GetFileDescriptor(const MethodDescriptor* descriptor) {
+ return descriptor->service()->file();
+}
+
+// Converts options into a Python protobuf, and cache the result.
+//
+// This is a bit tricky because options can contain extension fields defined in
+// the same proto file. In this case the options parsed from the serialized_pb
+// have unknown fields, and we need to parse them again.
+//
+// Always returns a new reference.
+template<class DescriptorClass>
+static PyObject* GetOrBuildOptions(const DescriptorClass *descriptor) {
+ // Options (and their extensions) are completely resolved in the proto file
+ // containing the descriptor.
+ PyDescriptorPool* pool = GetDescriptorPool_FromPool(
+ GetFileDescriptor(descriptor)->pool());
+
+ hash_map<const void*, PyObject*>* descriptor_options =
+ pool->descriptor_options;
+ // First search in the cache.
+ if (descriptor_options->find(descriptor) != descriptor_options->end()) {
+ PyObject *value = (*descriptor_options)[descriptor];
+ Py_INCREF(value);
+ return value;
+ }
+
+ // Build the Options object: get its Python class, and make a copy of the C++
+ // read-only instance.
+ const Message& options(descriptor->options());
+ const Descriptor *message_type = options.GetDescriptor();
+ CMessageClass* message_class(
+ cdescriptor_pool::GetMessageClass(pool, message_type));
+ if (message_class == NULL) {
+ // The Options message was not found in the current DescriptorPool.
+ // This means that the pool cannot contain any extensions to the Options
+ // message either, so falling back to the basic pool we can only increase
+ // the chances of successfully parsing the options.
+ PyErr_Clear();
+ pool = GetDefaultDescriptorPool();
+ message_class = cdescriptor_pool::GetMessageClass(pool, message_type);
+ }
+ if (message_class == NULL) {
+ PyErr_Format(PyExc_TypeError, "Could not retrieve class for Options: %s",
+ message_type->full_name().c_str());
+ return NULL;
+ }
+ ScopedPyObjectPtr value(
+ PyEval_CallObject(message_class->AsPyObject(), NULL));
+ if (value == NULL) {
+ return NULL;
+ }
+ if (!PyObject_TypeCheck(value.get(), &CMessage_Type)) {
+ PyErr_Format(PyExc_TypeError, "Invalid class for %s: %s",
+ message_type->full_name().c_str(),
+ Py_TYPE(value.get())->tp_name);
+ return NULL;
+ }
+ CMessage* cmsg = reinterpret_cast<CMessage*>(value.get());
+
+ const Reflection* reflection = options.GetReflection();
+ const UnknownFieldSet& unknown_fields(reflection->GetUnknownFields(options));
+ if (unknown_fields.empty()) {
+ cmsg->message->CopyFrom(options);
+ } else {
+ // Reparse options string! XXX call cmessage::MergeFromString
+ string serialized;
+ options.SerializeToString(&serialized);
+ io::CodedInputStream input(
+ reinterpret_cast<const uint8*>(serialized.c_str()), serialized.size());
+ input.SetExtensionRegistry(pool->pool, pool->message_factory);
+ bool success = cmsg->message->MergePartialFromCodedStream(&input);
+ if (!success) {
+ PyErr_Format(PyExc_ValueError, "Error parsing Options message");
+ return NULL;
+ }
+ }
+
+ // Cache the result.
+ Py_INCREF(value.get());
+ (*descriptor_options)[descriptor] = value.get();
+
+ return value.release();
+}
+
+// Copy the C++ descriptor to a Python message.
+// The Python message is an instance of descriptor_pb2.DescriptorProto
+// or similar.
+template<class DescriptorProtoClass, class DescriptorClass>
+static PyObject* CopyToPythonProto(const DescriptorClass *descriptor,
+ PyObject *target) {
+ const Descriptor* self_descriptor =
+ DescriptorProtoClass::default_instance().GetDescriptor();
+ CMessage* message = reinterpret_cast<CMessage*>(target);
+ if (!PyObject_TypeCheck(target, &CMessage_Type) ||
+ message->message->GetDescriptor() != self_descriptor) {
+ PyErr_Format(PyExc_TypeError, "Not a %s message",
+ self_descriptor->full_name().c_str());
+ return NULL;
+ }
+ cmessage::AssureWritable(message);
+ DescriptorProtoClass* descriptor_message =
+ static_cast<DescriptorProtoClass*>(message->message);
+ descriptor->CopyTo(descriptor_message);
+ Py_RETURN_NONE;
+}
+
+// All Descriptors classes share the same memory layout.
+typedef struct PyBaseDescriptor {
+ PyObject_HEAD
+
+ // Pointer to the C++ proto2 descriptor.
+ // Like all descriptors, it is owned by the global DescriptorPool.
+ const void* descriptor;
+
+ // Owned reference to the DescriptorPool, to ensure it is kept alive.
+ PyDescriptorPool* pool;
+} PyBaseDescriptor;
+
+
+// FileDescriptor structure "inherits" from the base descriptor.
+typedef struct PyFileDescriptor {
+ PyBaseDescriptor base;
+
+ // The cached version of serialized pb. Either NULL, or a Bytes string.
+ // We own the reference.
+ PyObject *serialized_pb;
+} PyFileDescriptor;
+
+
+namespace descriptor {
+
+// Creates or retrieve a Python descriptor of the specified type.
+// Objects are interned: the same descriptor will return the same object if it
+// was kept alive.
+// 'was_created' is an optional pointer to a bool, and is set to true if a new
+// object was allocated.
+// Always return a new reference.
+template<class DescriptorClass>
+PyObject* NewInternedDescriptor(PyTypeObject* type,
+ const DescriptorClass* descriptor,
+ bool* was_created) {
+ if (was_created) {
+ *was_created = false;
+ }
+ if (descriptor == NULL) {
+ PyErr_BadInternalCall();
+ return NULL;
+ }
+
+ // See if the object is in the map of interned descriptors
+ hash_map<const void*, PyObject*>::iterator it =
+ interned_descriptors.find(descriptor);
+ if (it != interned_descriptors.end()) {
+ GOOGLE_DCHECK(Py_TYPE(it->second) == type);
+ Py_INCREF(it->second);
+ return it->second;
+ }
+ // Create a new descriptor object
+ PyBaseDescriptor* py_descriptor = PyObject_New(
+ PyBaseDescriptor, type);
+ if (py_descriptor == NULL) {
+ return NULL;
+ }
+ py_descriptor->descriptor = descriptor;
+
+ // and cache it.
+ interned_descriptors.insert(
+ std::make_pair(descriptor, reinterpret_cast<PyObject*>(py_descriptor)));
+
+ // Ensures that the DescriptorPool stays alive.
+ PyDescriptorPool* pool = GetDescriptorPool_FromPool(
+ GetFileDescriptor(descriptor)->pool());
+ if (pool == NULL) {
+ // Don't DECREF, the object is not fully initialized.
+ PyObject_Del(py_descriptor);
+ return NULL;
+ }
+ Py_INCREF(pool);
+ py_descriptor->pool = pool;
+
+ if (was_created) {
+ *was_created = true;
+ }
+ return reinterpret_cast<PyObject*>(py_descriptor);
+}
+
+static void Dealloc(PyBaseDescriptor* self) {
+ // Remove from interned dictionary
+ interned_descriptors.erase(self->descriptor);
+ Py_CLEAR(self->pool);
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+static PyGetSetDef Getters[] = {
+ {NULL}
+};
+
+PyTypeObject PyBaseDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".DescriptorBase", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "Descriptors base class", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ 0, // tp_methods
+ 0, // tp_members
+ Getters, // tp_getset
+};
+
+} // namespace descriptor
+
+const void* PyDescriptor_AsVoidPtr(PyObject* obj) {
+ if (!PyObject_TypeCheck(obj, &descriptor::PyBaseDescriptor_Type)) {
+ PyErr_SetString(PyExc_TypeError, "Not a BaseDescriptor");
+ return NULL;
+ }
+ return reinterpret_cast<PyBaseDescriptor*>(obj)->descriptor;
+}
+
+namespace message_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const Descriptor* _GetDescriptor(PyBaseDescriptor* self) {
+ return reinterpret_cast<const Descriptor*>(self->descriptor);
+}
+
+static PyObject* GetName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetFullName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->full_name());
+}
+
+static PyObject* GetFile(PyBaseDescriptor *self, void *closure) {
+ return PyFileDescriptor_FromDescriptor(_GetDescriptor(self)->file());
+}
+
+static PyObject* GetConcreteClass(PyBaseDescriptor* self, void *closure) {
+ // Retuns the canonical class for the given descriptor.
+ // This is the class that was registered with the primary descriptor pool
+ // which contains this descriptor.
+ // This might not be the one you expect! For example the returned object does
+ // not know about extensions defined in a custom pool.
+ CMessageClass* concrete_class(cdescriptor_pool::GetMessageClass(
+ GetDescriptorPool_FromPool(_GetDescriptor(self)->file()->pool()),
+ _GetDescriptor(self)));
+ Py_XINCREF(concrete_class);
+ return concrete_class->AsPyObject();
+}
+
+static PyObject* GetFieldsByName(PyBaseDescriptor* self, void *closure) {
+ return NewMessageFieldsByName(_GetDescriptor(self));
+}
+
+static PyObject* GetFieldsByCamelcaseName(PyBaseDescriptor* self,
+ void *closure) {
+ return NewMessageFieldsByCamelcaseName(_GetDescriptor(self));
+}
+
+static PyObject* GetFieldsByNumber(PyBaseDescriptor* self, void *closure) {
+ return NewMessageFieldsByNumber(_GetDescriptor(self));
+}
+
+static PyObject* GetFieldsSeq(PyBaseDescriptor* self, void *closure) {
+ return NewMessageFieldsSeq(_GetDescriptor(self));
+}
+
+static PyObject* GetNestedTypesByName(PyBaseDescriptor* self, void *closure) {
+ return NewMessageNestedTypesByName(_GetDescriptor(self));
+}
+
+static PyObject* GetNestedTypesSeq(PyBaseDescriptor* self, void *closure) {
+ return NewMessageNestedTypesSeq(_GetDescriptor(self));
+}
+
+static PyObject* GetExtensionsByName(PyBaseDescriptor* self, void *closure) {
+ return NewMessageExtensionsByName(_GetDescriptor(self));
+}
+
+static PyObject* GetExtensions(PyBaseDescriptor* self, void *closure) {
+ return NewMessageExtensionsSeq(_GetDescriptor(self));
+}
+
+static PyObject* GetEnumsSeq(PyBaseDescriptor* self, void *closure) {
+ return NewMessageEnumsSeq(_GetDescriptor(self));
+}
+
+static PyObject* GetEnumTypesByName(PyBaseDescriptor* self, void *closure) {
+ return NewMessageEnumsByName(_GetDescriptor(self));
+}
+
+static PyObject* GetEnumValuesByName(PyBaseDescriptor* self, void *closure) {
+ return NewMessageEnumValuesByName(_GetDescriptor(self));
+}
+
+static PyObject* GetOneofsByName(PyBaseDescriptor* self, void *closure) {
+ return NewMessageOneofsByName(_GetDescriptor(self));
+}
+
+static PyObject* GetOneofsSeq(PyBaseDescriptor* self, void *closure) {
+ return NewMessageOneofsSeq(_GetDescriptor(self));
+}
+
+static PyObject* IsExtendable(PyBaseDescriptor *self, void *closure) {
+ if (_GetDescriptor(self)->extension_range_count() > 0) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+
+static PyObject* GetExtensionRanges(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* descriptor = _GetDescriptor(self);
+ PyObject* range_list = PyList_New(descriptor->extension_range_count());
+
+ for (int i = 0; i < descriptor->extension_range_count(); i++) {
+ const Descriptor::ExtensionRange* range = descriptor->extension_range(i);
+ PyObject* start = PyInt_FromLong(range->start);
+ PyObject* end = PyInt_FromLong(range->end);
+ PyList_SetItem(range_list, i, PyTuple_Pack(2, start, end));
+ }
+
+ return range_list;
+}
+
+static PyObject* GetContainingType(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* containing_type =
+ _GetDescriptor(self)->containing_type();
+ if (containing_type) {
+ return PyMessageDescriptor_FromDescriptor(containing_type);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static int SetContainingType(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("containing_type");
+}
+
+static PyObject* GetHasOptions(PyBaseDescriptor *self, void *closure) {
+ const MessageOptions& options(_GetDescriptor(self)->options());
+ if (&options != &MessageOptions::default_instance()) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+static int SetHasOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("has_options");
+}
+
+static PyObject* GetOptions(PyBaseDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static int SetOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("_options");
+}
+
+static PyObject* CopyToProto(PyBaseDescriptor *self, PyObject *target) {
+ return CopyToPythonProto<DescriptorProto>(_GetDescriptor(self), target);
+}
+
+static PyObject* EnumValueName(PyBaseDescriptor *self, PyObject *args) {
+ const char *enum_name;
+ int number;
+ if (!PyArg_ParseTuple(args, "si", &enum_name, &number))
+ return NULL;
+ const EnumDescriptor *enum_type =
+ _GetDescriptor(self)->FindEnumTypeByName(enum_name);
+ if (enum_type == NULL) {
+ PyErr_SetString(PyExc_KeyError, enum_name);
+ return NULL;
+ }
+ const EnumValueDescriptor *enum_value =
+ enum_type->FindValueByNumber(number);
+ if (enum_value == NULL) {
+ PyErr_Format(PyExc_KeyError, "%d", number);
+ return NULL;
+ }
+ return PyString_FromCppString(enum_value->name());
+}
+
+static PyObject* GetSyntax(PyBaseDescriptor *self, void *closure) {
+ return PyString_InternFromString(
+ FileDescriptor::SyntaxName(_GetDescriptor(self)->file()->syntax()));
+}
+
+static PyGetSetDef Getters[] = {
+ { "name", (getter)GetName, NULL, "Last name"},
+ { "full_name", (getter)GetFullName, NULL, "Full name"},
+ { "_concrete_class", (getter)GetConcreteClass, NULL, "concrete class"},
+ { "file", (getter)GetFile, NULL, "File descriptor"},
+
+ { "fields", (getter)GetFieldsSeq, NULL, "Fields sequence"},
+ { "fields_by_name", (getter)GetFieldsByName, NULL, "Fields by name"},
+ { "fields_by_camelcase_name", (getter)GetFieldsByCamelcaseName, NULL,
+ "Fields by camelCase name"},
+ { "fields_by_number", (getter)GetFieldsByNumber, NULL, "Fields by number"},
+ { "nested_types", (getter)GetNestedTypesSeq, NULL, "Nested types sequence"},
+ { "nested_types_by_name", (getter)GetNestedTypesByName, NULL,
+ "Nested types by name"},
+ { "extensions", (getter)GetExtensions, NULL, "Extensions Sequence"},
+ { "extensions_by_name", (getter)GetExtensionsByName, NULL,
+ "Extensions by name"},
+ { "extension_ranges", (getter)GetExtensionRanges, NULL, "Extension ranges"},
+ { "enum_types", (getter)GetEnumsSeq, NULL, "Enum sequence"},
+ { "enum_types_by_name", (getter)GetEnumTypesByName, NULL,
+ "Enum types by name"},
+ { "enum_values_by_name", (getter)GetEnumValuesByName, NULL,
+ "Enum values by name"},
+ { "oneofs_by_name", (getter)GetOneofsByName, NULL, "Oneofs by name"},
+ { "oneofs", (getter)GetOneofsSeq, NULL, "Oneofs by name"},
+ { "containing_type", (getter)GetContainingType, (setter)SetContainingType,
+ "Containing type"},
+ { "is_extendable", (getter)IsExtendable, (setter)NULL},
+ { "has_options", (getter)GetHasOptions, (setter)SetHasOptions, "Has Options"},
+ { "_options", (getter)NULL, (setter)SetOptions, "Options"},
+ { "syntax", (getter)GetSyntax, (setter)NULL, "Syntax"},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS, },
+ { "CopyToProto", (PyCFunction)CopyToProto, METH_O, },
+ { "EnumValueName", (PyCFunction)EnumValueName, METH_VARARGS, },
+ {NULL}
+};
+
+} // namespace message_descriptor
+
+PyTypeObject PyMessageDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".MessageDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Message Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ message_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ message_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+};
+
+PyObject* PyMessageDescriptor_FromDescriptor(
+ const Descriptor* message_descriptor) {
+ return descriptor::NewInternedDescriptor(
+ &PyMessageDescriptor_Type, message_descriptor, NULL);
+}
+
+const Descriptor* PyMessageDescriptor_AsDescriptor(PyObject* obj) {
+ if (!PyObject_TypeCheck(obj, &PyMessageDescriptor_Type)) {
+ PyErr_SetString(PyExc_TypeError, "Not a MessageDescriptor");
+ return NULL;
+ }
+ return reinterpret_cast<const Descriptor*>(
+ reinterpret_cast<PyBaseDescriptor*>(obj)->descriptor);
+}
+
+namespace field_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const FieldDescriptor* _GetDescriptor(
+ PyBaseDescriptor *self) {
+ return reinterpret_cast<const FieldDescriptor*>(self->descriptor);
+}
+
+static PyObject* GetFullName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->full_name());
+}
+
+static PyObject* GetName(PyBaseDescriptor *self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetCamelcaseName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->camelcase_name());
+}
+
+static PyObject* GetType(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->type());
+}
+
+static PyObject* GetCppType(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->cpp_type());
+}
+
+static PyObject* GetLabel(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->label());
+}
+
+static PyObject* GetNumber(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->number());
+}
+
+static PyObject* GetIndex(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->index());
+}
+
+static PyObject* GetID(PyBaseDescriptor *self, void *closure) {
+ return PyLong_FromVoidPtr(self);
+}
+
+static PyObject* IsExtension(PyBaseDescriptor *self, void *closure) {
+ return PyBool_FromLong(_GetDescriptor(self)->is_extension());
+}
+
+static PyObject* HasDefaultValue(PyBaseDescriptor *self, void *closure) {
+ return PyBool_FromLong(_GetDescriptor(self)->has_default_value());
+}
+
+static PyObject* GetDefaultValue(PyBaseDescriptor *self, void *closure) {
+ PyObject *result;
+
+ switch (_GetDescriptor(self)->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ int32 value = _GetDescriptor(self)->default_value_int32();
+ result = PyInt_FromLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ int64 value = _GetDescriptor(self)->default_value_int64();
+ result = PyLong_FromLongLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ uint32 value = _GetDescriptor(self)->default_value_uint32();
+ result = PyInt_FromSize_t(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ uint64 value = _GetDescriptor(self)->default_value_uint64();
+ result = PyLong_FromUnsignedLongLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ float value = _GetDescriptor(self)->default_value_float();
+ result = PyFloat_FromDouble(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value = _GetDescriptor(self)->default_value_double();
+ result = PyFloat_FromDouble(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ bool value = _GetDescriptor(self)->default_value_bool();
+ result = PyBool_FromLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string value = _GetDescriptor(self)->default_value_string();
+ result = ToStringObject(_GetDescriptor(self), value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ const EnumValueDescriptor* value =
+ _GetDescriptor(self)->default_value_enum();
+ result = PyInt_FromLong(value->number());
+ break;
+ }
+ default:
+ PyErr_Format(PyExc_NotImplementedError, "default value for %s",
+ _GetDescriptor(self)->full_name().c_str());
+ return NULL;
+ }
+ return result;
+}
+
+static PyObject* GetCDescriptor(PyObject *self, void *closure) {
+ Py_INCREF(self);
+ return self;
+}
+
+static PyObject *GetEnumType(PyBaseDescriptor *self, void *closure) {
+ const EnumDescriptor* enum_type = _GetDescriptor(self)->enum_type();
+ if (enum_type) {
+ return PyEnumDescriptor_FromDescriptor(enum_type);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static int SetEnumType(PyBaseDescriptor *self, PyObject *value, void *closure) {
+ return CheckCalledFromGeneratedFile("enum_type");
+}
+
+static PyObject *GetMessageType(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* message_type = _GetDescriptor(self)->message_type();
+ if (message_type) {
+ return PyMessageDescriptor_FromDescriptor(message_type);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static int SetMessageType(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("message_type");
+}
+
+static PyObject* GetContainingType(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* containing_type =
+ _GetDescriptor(self)->containing_type();
+ if (containing_type) {
+ return PyMessageDescriptor_FromDescriptor(containing_type);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static int SetContainingType(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("containing_type");
+}
+
+static PyObject* GetExtensionScope(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* extension_scope =
+ _GetDescriptor(self)->extension_scope();
+ if (extension_scope) {
+ return PyMessageDescriptor_FromDescriptor(extension_scope);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static PyObject* GetContainingOneof(PyBaseDescriptor *self, void *closure) {
+ const OneofDescriptor* containing_oneof =
+ _GetDescriptor(self)->containing_oneof();
+ if (containing_oneof) {
+ return PyOneofDescriptor_FromDescriptor(containing_oneof);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static int SetContainingOneof(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("containing_oneof");
+}
+
+static PyObject* GetHasOptions(PyBaseDescriptor *self, void *closure) {
+ const FieldOptions& options(_GetDescriptor(self)->options());
+ if (&options != &FieldOptions::default_instance()) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+static int SetHasOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("has_options");
+}
+
+static PyObject* GetOptions(PyBaseDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static int SetOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("_options");
+}
+
+
+static PyGetSetDef Getters[] = {
+ { "full_name", (getter)GetFullName, NULL, "Full name"},
+ { "name", (getter)GetName, NULL, "Unqualified name"},
+ { "camelcase_name", (getter)GetCamelcaseName, NULL, "Camelcase name"},
+ { "type", (getter)GetType, NULL, "C++ Type"},
+ { "cpp_type", (getter)GetCppType, NULL, "C++ Type"},
+ { "label", (getter)GetLabel, NULL, "Label"},
+ { "number", (getter)GetNumber, NULL, "Number"},
+ { "index", (getter)GetIndex, NULL, "Index"},
+ { "default_value", (getter)GetDefaultValue, NULL, "Default Value"},
+ { "has_default_value", (getter)HasDefaultValue},
+ { "is_extension", (getter)IsExtension, NULL, "ID"},
+ { "id", (getter)GetID, NULL, "ID"},
+ { "_cdescriptor", (getter)GetCDescriptor, NULL, "HAACK REMOVE ME"},
+
+ { "message_type", (getter)GetMessageType, (setter)SetMessageType,
+ "Message type"},
+ { "enum_type", (getter)GetEnumType, (setter)SetEnumType, "Enum type"},
+ { "containing_type", (getter)GetContainingType, (setter)SetContainingType,
+ "Containing type"},
+ { "extension_scope", (getter)GetExtensionScope, (setter)NULL,
+ "Extension scope"},
+ { "containing_oneof", (getter)GetContainingOneof, (setter)SetContainingOneof,
+ "Containing oneof"},
+ { "has_options", (getter)GetHasOptions, (setter)SetHasOptions, "Has Options"},
+ { "_options", (getter)NULL, (setter)SetOptions, "Options"},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS, },
+ {NULL}
+};
+
+} // namespace field_descriptor
+
+PyTypeObject PyFieldDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".FieldDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Field Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ field_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ field_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+};
+
+PyObject* PyFieldDescriptor_FromDescriptor(
+ const FieldDescriptor* field_descriptor) {
+ return descriptor::NewInternedDescriptor(
+ &PyFieldDescriptor_Type, field_descriptor, NULL);
+}
+
+const FieldDescriptor* PyFieldDescriptor_AsDescriptor(PyObject* obj) {
+ if (!PyObject_TypeCheck(obj, &PyFieldDescriptor_Type)) {
+ PyErr_SetString(PyExc_TypeError, "Not a FieldDescriptor");
+ return NULL;
+ }
+ return reinterpret_cast<const FieldDescriptor*>(
+ reinterpret_cast<PyBaseDescriptor*>(obj)->descriptor);
+}
+
+namespace enum_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const EnumDescriptor* _GetDescriptor(
+ PyBaseDescriptor *self) {
+ return reinterpret_cast<const EnumDescriptor*>(self->descriptor);
+}
+
+static PyObject* GetFullName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->full_name());
+}
+
+static PyObject* GetName(PyBaseDescriptor *self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetFile(PyBaseDescriptor *self, void *closure) {
+ return PyFileDescriptor_FromDescriptor(_GetDescriptor(self)->file());
+}
+
+static PyObject* GetEnumvaluesByName(PyBaseDescriptor* self, void *closure) {
+ return NewEnumValuesByName(_GetDescriptor(self));
+}
+
+static PyObject* GetEnumvaluesByNumber(PyBaseDescriptor* self, void *closure) {
+ return NewEnumValuesByNumber(_GetDescriptor(self));
+}
+
+static PyObject* GetEnumvaluesSeq(PyBaseDescriptor* self, void *closure) {
+ return NewEnumValuesSeq(_GetDescriptor(self));
+}
+
+static PyObject* GetContainingType(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* containing_type =
+ _GetDescriptor(self)->containing_type();
+ if (containing_type) {
+ return PyMessageDescriptor_FromDescriptor(containing_type);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static int SetContainingType(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("containing_type");
+}
+
+
+static PyObject* GetHasOptions(PyBaseDescriptor *self, void *closure) {
+ const EnumOptions& options(_GetDescriptor(self)->options());
+ if (&options != &EnumOptions::default_instance()) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+static int SetHasOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("has_options");
+}
+
+static PyObject* GetOptions(PyBaseDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static int SetOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("_options");
+}
+
+static PyObject* CopyToProto(PyBaseDescriptor *self, PyObject *target) {
+ return CopyToPythonProto<EnumDescriptorProto>(_GetDescriptor(self), target);
+}
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS, },
+ { "CopyToProto", (PyCFunction)CopyToProto, METH_O, },
+ {NULL}
+};
+
+static PyGetSetDef Getters[] = {
+ { "full_name", (getter)GetFullName, NULL, "Full name"},
+ { "name", (getter)GetName, NULL, "last name"},
+ { "file", (getter)GetFile, NULL, "File descriptor"},
+ { "values", (getter)GetEnumvaluesSeq, NULL, "values"},
+ { "values_by_name", (getter)GetEnumvaluesByName, NULL,
+ "Enum values by name"},
+ { "values_by_number", (getter)GetEnumvaluesByNumber, NULL,
+ "Enum values by number"},
+
+ { "containing_type", (getter)GetContainingType, (setter)SetContainingType,
+ "Containing type"},
+ { "has_options", (getter)GetHasOptions, (setter)SetHasOptions, "Has Options"},
+ { "_options", (getter)NULL, (setter)SetOptions, "Options"},
+ {NULL}
+};
+
+} // namespace enum_descriptor
+
+PyTypeObject PyEnumDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".EnumDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Enum Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ enum_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ enum_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+};
+
+PyObject* PyEnumDescriptor_FromDescriptor(
+ const EnumDescriptor* enum_descriptor) {
+ return descriptor::NewInternedDescriptor(
+ &PyEnumDescriptor_Type, enum_descriptor, NULL);
+}
+
+const EnumDescriptor* PyEnumDescriptor_AsDescriptor(PyObject* obj) {
+ if (!PyObject_TypeCheck(obj, &PyEnumDescriptor_Type)) {
+ PyErr_SetString(PyExc_TypeError, "Not an EnumDescriptor");
+ return NULL;
+ }
+ return reinterpret_cast<const EnumDescriptor*>(
+ reinterpret_cast<PyBaseDescriptor*>(obj)->descriptor);
+}
+
+namespace enumvalue_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const EnumValueDescriptor* _GetDescriptor(
+ PyBaseDescriptor *self) {
+ return reinterpret_cast<const EnumValueDescriptor*>(self->descriptor);
+}
+
+static PyObject* GetName(PyBaseDescriptor *self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetNumber(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->number());
+}
+
+static PyObject* GetIndex(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->index());
+}
+
+static PyObject* GetType(PyBaseDescriptor *self, void *closure) {
+ return PyEnumDescriptor_FromDescriptor(_GetDescriptor(self)->type());
+}
+
+static PyObject* GetHasOptions(PyBaseDescriptor *self, void *closure) {
+ const EnumValueOptions& options(_GetDescriptor(self)->options());
+ if (&options != &EnumValueOptions::default_instance()) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+static int SetHasOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("has_options");
+}
+
+static PyObject* GetOptions(PyBaseDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static int SetOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("_options");
+}
+
+
+static PyGetSetDef Getters[] = {
+ { "name", (getter)GetName, NULL, "name"},
+ { "number", (getter)GetNumber, NULL, "number"},
+ { "index", (getter)GetIndex, NULL, "index"},
+ { "type", (getter)GetType, NULL, "index"},
+
+ { "has_options", (getter)GetHasOptions, (setter)SetHasOptions, "Has Options"},
+ { "_options", (getter)NULL, (setter)SetOptions, "Options"},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS, },
+ {NULL}
+};
+
+} // namespace enumvalue_descriptor
+
+PyTypeObject PyEnumValueDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".EnumValueDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A EnumValue Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ enumvalue_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ enumvalue_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+};
+
+PyObject* PyEnumValueDescriptor_FromDescriptor(
+ const EnumValueDescriptor* enumvalue_descriptor) {
+ return descriptor::NewInternedDescriptor(
+ &PyEnumValueDescriptor_Type, enumvalue_descriptor, NULL);
+}
+
+namespace file_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const FileDescriptor* _GetDescriptor(PyFileDescriptor *self) {
+ return reinterpret_cast<const FileDescriptor*>(self->base.descriptor);
+}
+
+static void Dealloc(PyFileDescriptor* self) {
+ Py_XDECREF(self->serialized_pb);
+ descriptor::Dealloc(&self->base);
+}
+
+static PyObject* GetPool(PyFileDescriptor *self, void *closure) {
+ PyObject* pool = reinterpret_cast<PyObject*>(
+ GetDescriptorPool_FromPool(_GetDescriptor(self)->pool()));
+ Py_XINCREF(pool);
+ return pool;
+}
+
+static PyObject* GetName(PyFileDescriptor *self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetPackage(PyFileDescriptor *self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->package());
+}
+
+static PyObject* GetSerializedPb(PyFileDescriptor *self, void *closure) {
+ PyObject *serialized_pb = self->serialized_pb;
+ if (serialized_pb != NULL) {
+ Py_INCREF(serialized_pb);
+ return serialized_pb;
+ }
+ FileDescriptorProto file_proto;
+ _GetDescriptor(self)->CopyTo(&file_proto);
+ string contents;
+ file_proto.SerializePartialToString(&contents);
+ self->serialized_pb = PyBytes_FromStringAndSize(
+ contents.c_str(), contents.size());
+ if (self->serialized_pb == NULL) {
+ return NULL;
+ }
+ Py_INCREF(self->serialized_pb);
+ return self->serialized_pb;
+}
+
+static PyObject* GetMessageTypesByName(PyFileDescriptor* self, void *closure) {
+ return NewFileMessageTypesByName(_GetDescriptor(self));
+}
+
+static PyObject* GetEnumTypesByName(PyFileDescriptor* self, void *closure) {
+ return NewFileEnumTypesByName(_GetDescriptor(self));
+}
+
+static PyObject* GetExtensionsByName(PyFileDescriptor* self, void *closure) {
+ return NewFileExtensionsByName(_GetDescriptor(self));
+}
+
+static PyObject* GetServicesByName(PyFileDescriptor* self, void *closure) {
+ return NewFileServicesByName(_GetDescriptor(self));
+}
+
+static PyObject* GetDependencies(PyFileDescriptor* self, void *closure) {
+ return NewFileDependencies(_GetDescriptor(self));
+}
+
+static PyObject* GetPublicDependencies(PyFileDescriptor* self, void *closure) {
+ return NewFilePublicDependencies(_GetDescriptor(self));
+}
+
+static PyObject* GetHasOptions(PyFileDescriptor *self, void *closure) {
+ const FileOptions& options(_GetDescriptor(self)->options());
+ if (&options != &FileOptions::default_instance()) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+static int SetHasOptions(PyFileDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("has_options");
+}
+
+static PyObject* GetOptions(PyFileDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static int SetOptions(PyFileDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("_options");
+}
+
+static PyObject* GetSyntax(PyFileDescriptor *self, void *closure) {
+ return PyString_InternFromString(
+ FileDescriptor::SyntaxName(_GetDescriptor(self)->syntax()));
+}
+
+static PyObject* CopyToProto(PyFileDescriptor *self, PyObject *target) {
+ return CopyToPythonProto<FileDescriptorProto>(_GetDescriptor(self), target);
+}
+
+static PyGetSetDef Getters[] = {
+ { "pool", (getter)GetPool, NULL, "pool"},
+ { "name", (getter)GetName, NULL, "name"},
+ { "package", (getter)GetPackage, NULL, "package"},
+ { "serialized_pb", (getter)GetSerializedPb},
+ { "message_types_by_name", (getter)GetMessageTypesByName, NULL,
+ "Messages by name"},
+ { "enum_types_by_name", (getter)GetEnumTypesByName, NULL, "Enums by name"},
+ { "extensions_by_name", (getter)GetExtensionsByName, NULL,
+ "Extensions by name"},
+ { "services_by_name", (getter)GetServicesByName, NULL, "Services by name"},
+ { "dependencies", (getter)GetDependencies, NULL, "Dependencies"},
+ { "public_dependencies", (getter)GetPublicDependencies, NULL, "Dependencies"},
+
+ { "has_options", (getter)GetHasOptions, (setter)SetHasOptions, "Has Options"},
+ { "_options", (getter)NULL, (setter)SetOptions, "Options"},
+ { "syntax", (getter)GetSyntax, (setter)NULL, "Syntax"},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS, },
+ { "CopyToProto", (PyCFunction)CopyToProto, METH_O, },
+ {NULL}
+};
+
+} // namespace file_descriptor
+
+PyTypeObject PyFileDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".FileDescriptor", // tp_name
+ sizeof(PyFileDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)file_descriptor::Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A File Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ file_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ file_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ 0, // tp_alloc
+ 0, // tp_new
+ PyObject_Del, // tp_free
+};
+
+PyObject* PyFileDescriptor_FromDescriptor(
+ const FileDescriptor* file_descriptor) {
+ return PyFileDescriptor_FromDescriptorWithSerializedPb(file_descriptor,
+ NULL);
+}
+
+PyObject* PyFileDescriptor_FromDescriptorWithSerializedPb(
+ const FileDescriptor* file_descriptor, PyObject *serialized_pb) {
+ bool was_created;
+ PyObject* py_descriptor = descriptor::NewInternedDescriptor(
+ &PyFileDescriptor_Type, file_descriptor, &was_created);
+ if (py_descriptor == NULL) {
+ return NULL;
+ }
+ if (was_created) {
+ PyFileDescriptor* cfile_descriptor =
+ reinterpret_cast<PyFileDescriptor*>(py_descriptor);
+ Py_XINCREF(serialized_pb);
+ cfile_descriptor->serialized_pb = serialized_pb;
+ }
+ // TODO(amauryfa): In the case of a cached object, check that serialized_pb
+ // is the same as before.
+
+ return py_descriptor;
+}
+
+const FileDescriptor* PyFileDescriptor_AsDescriptor(PyObject* obj) {
+ if (!PyObject_TypeCheck(obj, &PyFileDescriptor_Type)) {
+ PyErr_SetString(PyExc_TypeError, "Not a FileDescriptor");
+ return NULL;
+ }
+ return reinterpret_cast<const FileDescriptor*>(
+ reinterpret_cast<PyBaseDescriptor*>(obj)->descriptor);
+}
+
+namespace oneof_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const OneofDescriptor* _GetDescriptor(
+ PyBaseDescriptor *self) {
+ return reinterpret_cast<const OneofDescriptor*>(self->descriptor);
+}
+
+static PyObject* GetName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetFullName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->full_name());
+}
+
+static PyObject* GetIndex(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->index());
+}
+
+static PyObject* GetFields(PyBaseDescriptor* self, void *closure) {
+ return NewOneofFieldsSeq(_GetDescriptor(self));
+}
+
+static PyObject* GetContainingType(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* containing_type =
+ _GetDescriptor(self)->containing_type();
+ if (containing_type) {
+ return PyMessageDescriptor_FromDescriptor(containing_type);
+ } else {
+ Py_RETURN_NONE;
+ }
+}
+
+static PyObject* GetHasOptions(PyBaseDescriptor *self, void *closure) {
+ const OneofOptions& options(_GetDescriptor(self)->options());
+ if (&options != &OneofOptions::default_instance()) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+static int SetHasOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("has_options");
+}
+
+static PyObject* GetOptions(PyBaseDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static int SetOptions(PyBaseDescriptor *self, PyObject *value,
+ void *closure) {
+ return CheckCalledFromGeneratedFile("_options");
+}
+
+static PyGetSetDef Getters[] = {
+ { "name", (getter)GetName, NULL, "Name"},
+ { "full_name", (getter)GetFullName, NULL, "Full name"},
+ { "index", (getter)GetIndex, NULL, "Index"},
+
+ { "containing_type", (getter)GetContainingType, NULL, "Containing type"},
+ { "has_options", (getter)GetHasOptions, (setter)SetHasOptions, "Has Options"},
+ { "_options", (getter)NULL, (setter)SetOptions, "Options"},
+ { "fields", (getter)GetFields, NULL, "Fields"},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS },
+ {NULL}
+};
+
+} // namespace oneof_descriptor
+
+PyTypeObject PyOneofDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".OneofDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Oneof Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ oneof_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ oneof_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+};
+
+PyObject* PyOneofDescriptor_FromDescriptor(
+ const OneofDescriptor* oneof_descriptor) {
+ return descriptor::NewInternedDescriptor(
+ &PyOneofDescriptor_Type, oneof_descriptor, NULL);
+}
+
+namespace service_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const ServiceDescriptor* _GetDescriptor(
+ PyBaseDescriptor *self) {
+ return reinterpret_cast<const ServiceDescriptor*>(self->descriptor);
+}
+
+static PyObject* GetName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetFullName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->full_name());
+}
+
+static PyObject* GetIndex(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->index());
+}
+
+static PyObject* GetMethods(PyBaseDescriptor* self, void *closure) {
+ return NewServiceMethodsSeq(_GetDescriptor(self));
+}
+
+static PyObject* GetMethodsByName(PyBaseDescriptor* self, void *closure) {
+ return NewServiceMethodsByName(_GetDescriptor(self));
+}
+
+static PyObject* FindMethodByName(PyBaseDescriptor *self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const MethodDescriptor* method_descriptor =
+ _GetDescriptor(self)->FindMethodByName(string(name, name_size));
+ if (method_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find method %.200s", name);
+ return NULL;
+ }
+
+ return PyMethodDescriptor_FromDescriptor(method_descriptor);
+}
+
+static PyObject* GetOptions(PyBaseDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static PyObject* CopyToProto(PyBaseDescriptor *self, PyObject *target) {
+ return CopyToPythonProto<ServiceDescriptorProto>(_GetDescriptor(self),
+ target);
+}
+
+static PyGetSetDef Getters[] = {
+ { "name", (getter)GetName, NULL, "Name", NULL},
+ { "full_name", (getter)GetFullName, NULL, "Full name", NULL},
+ { "index", (getter)GetIndex, NULL, "Index", NULL},
+
+ { "methods", (getter)GetMethods, NULL, "Methods", NULL},
+ { "methods_by_name", (getter)GetMethodsByName, NULL, "Methods by name", NULL},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS },
+ { "CopyToProto", (PyCFunction)CopyToProto, METH_O, },
+ { "FindMethodByName", (PyCFunction)FindMethodByName, METH_O },
+ {NULL}
+};
+
+} // namespace service_descriptor
+
+PyTypeObject PyServiceDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".ServiceDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Service Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ service_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ service_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+};
+
+PyObject* PyServiceDescriptor_FromDescriptor(
+ const ServiceDescriptor* service_descriptor) {
+ return descriptor::NewInternedDescriptor(
+ &PyServiceDescriptor_Type, service_descriptor, NULL);
+}
+
+namespace method_descriptor {
+
+// Unchecked accessor to the C++ pointer.
+static const MethodDescriptor* _GetDescriptor(
+ PyBaseDescriptor *self) {
+ return reinterpret_cast<const MethodDescriptor*>(self->descriptor);
+}
+
+static PyObject* GetName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->name());
+}
+
+static PyObject* GetFullName(PyBaseDescriptor* self, void *closure) {
+ return PyString_FromCppString(_GetDescriptor(self)->full_name());
+}
+
+static PyObject* GetIndex(PyBaseDescriptor *self, void *closure) {
+ return PyInt_FromLong(_GetDescriptor(self)->index());
+}
+
+static PyObject* GetContainingService(PyBaseDescriptor *self, void *closure) {
+ const ServiceDescriptor* containing_service =
+ _GetDescriptor(self)->service();
+ return PyServiceDescriptor_FromDescriptor(containing_service);
+}
+
+static PyObject* GetInputType(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* input_type = _GetDescriptor(self)->input_type();
+ return PyMessageDescriptor_FromDescriptor(input_type);
+}
+
+static PyObject* GetOutputType(PyBaseDescriptor *self, void *closure) {
+ const Descriptor* output_type = _GetDescriptor(self)->output_type();
+ return PyMessageDescriptor_FromDescriptor(output_type);
+}
+
+static PyObject* GetOptions(PyBaseDescriptor *self) {
+ return GetOrBuildOptions(_GetDescriptor(self));
+}
+
+static PyObject* CopyToProto(PyBaseDescriptor *self, PyObject *target) {
+ return CopyToPythonProto<MethodDescriptorProto>(_GetDescriptor(self), target);
+}
+
+static PyGetSetDef Getters[] = {
+ { "name", (getter)GetName, NULL, "Name", NULL},
+ { "full_name", (getter)GetFullName, NULL, "Full name", NULL},
+ { "index", (getter)GetIndex, NULL, "Index", NULL},
+ { "containing_service", (getter)GetContainingService, NULL,
+ "Containing service", NULL},
+ { "input_type", (getter)GetInputType, NULL, "Input type", NULL},
+ { "output_type", (getter)GetOutputType, NULL, "Output type", NULL},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "GetOptions", (PyCFunction)GetOptions, METH_NOARGS, },
+ { "CopyToProto", (PyCFunction)CopyToProto, METH_O, },
+ {NULL}
+};
+
+} // namespace method_descriptor
+
+PyTypeObject PyMethodDescriptor_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".MethodDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Method Descriptor", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ method_descriptor::Methods, // tp_methods
+ 0, // tp_members
+ method_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+};
+
+PyObject* PyMethodDescriptor_FromDescriptor(
+ const MethodDescriptor* method_descriptor) {
+ return descriptor::NewInternedDescriptor(
+ &PyMethodDescriptor_Type, method_descriptor, NULL);
+}
+
+// Add a enum values to a type dictionary.
+static bool AddEnumValues(PyTypeObject *type,
+ const EnumDescriptor* enum_descriptor) {
+ for (int i = 0; i < enum_descriptor->value_count(); ++i) {
+ const EnumValueDescriptor* value = enum_descriptor->value(i);
+ ScopedPyObjectPtr obj(PyInt_FromLong(value->number()));
+ if (obj == NULL) {
+ return false;
+ }
+ if (PyDict_SetItemString(type->tp_dict, value->name().c_str(), obj.get()) <
+ 0) {
+ return false;
+ }
+ }
+ return true;
+}
+
+static bool AddIntConstant(PyTypeObject *type, const char* name, int value) {
+ ScopedPyObjectPtr obj(PyInt_FromLong(value));
+ if (PyDict_SetItemString(type->tp_dict, name, obj.get()) < 0) {
+ return false;
+ }
+ return true;
+}
+
+
+bool InitDescriptor() {
+ if (PyType_Ready(&PyMessageDescriptor_Type) < 0)
+ return false;
+
+ if (PyType_Ready(&PyFieldDescriptor_Type) < 0)
+ return false;
+
+ if (!AddEnumValues(&PyFieldDescriptor_Type,
+ FieldDescriptorProto::Label_descriptor())) {
+ return false;
+ }
+ if (!AddEnumValues(&PyFieldDescriptor_Type,
+ FieldDescriptorProto::Type_descriptor())) {
+ return false;
+ }
+#define ADD_FIELDDESC_CONSTANT(NAME) AddIntConstant( \
+ &PyFieldDescriptor_Type, #NAME, FieldDescriptor::NAME)
+ if (!ADD_FIELDDESC_CONSTANT(CPPTYPE_INT32) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_INT64) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_UINT32) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_UINT64) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_DOUBLE) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_FLOAT) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_BOOL) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_ENUM) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_STRING) ||
+ !ADD_FIELDDESC_CONSTANT(CPPTYPE_MESSAGE)) {
+ return false;
+ }
+#undef ADD_FIELDDESC_CONSTANT
+
+ if (PyType_Ready(&PyEnumDescriptor_Type) < 0)
+ return false;
+
+ if (PyType_Ready(&PyEnumValueDescriptor_Type) < 0)
+ return false;
+
+ if (PyType_Ready(&PyFileDescriptor_Type) < 0)
+ return false;
+
+ if (PyType_Ready(&PyOneofDescriptor_Type) < 0)
+ return false;
+
+ if (PyType_Ready(&PyServiceDescriptor_Type) < 0)
+ return false;
+
+ if (PyType_Ready(&PyMethodDescriptor_Type) < 0)
+ return false;
+
+ if (!InitDescriptorMappingTypes())
+ return false;
+
+ return true;
+}
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.h
new file mode 100644
index 0000000000..1ae0e672ed
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor.h
@@ -0,0 +1,103 @@
+// 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: petar@google.com (Petar Petrov)
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_H__
+
+#include <Python.h>
+
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+extern PyTypeObject PyMessageDescriptor_Type;
+extern PyTypeObject PyFieldDescriptor_Type;
+extern PyTypeObject PyEnumDescriptor_Type;
+extern PyTypeObject PyEnumValueDescriptor_Type;
+extern PyTypeObject PyFileDescriptor_Type;
+extern PyTypeObject PyOneofDescriptor_Type;
+extern PyTypeObject PyServiceDescriptor_Type;
+extern PyTypeObject PyMethodDescriptor_Type;
+
+// Wraps a Descriptor in a Python object.
+// The C++ pointer is usually borrowed from the global DescriptorPool.
+// In any case, it must stay alive as long as the Python object.
+// Returns a new reference.
+PyObject* PyMessageDescriptor_FromDescriptor(const Descriptor* descriptor);
+PyObject* PyFieldDescriptor_FromDescriptor(const FieldDescriptor* descriptor);
+PyObject* PyEnumDescriptor_FromDescriptor(const EnumDescriptor* descriptor);
+PyObject* PyEnumValueDescriptor_FromDescriptor(
+ const EnumValueDescriptor* descriptor);
+PyObject* PyOneofDescriptor_FromDescriptor(const OneofDescriptor* descriptor);
+PyObject* PyFileDescriptor_FromDescriptor(
+ const FileDescriptor* file_descriptor);
+PyObject* PyServiceDescriptor_FromDescriptor(
+ const ServiceDescriptor* descriptor);
+PyObject* PyMethodDescriptor_FromDescriptor(
+ const MethodDescriptor* descriptor);
+
+// Alternate constructor of PyFileDescriptor, used when we already have a
+// serialized FileDescriptorProto that can be cached.
+// Returns a new reference.
+PyObject* PyFileDescriptor_FromDescriptorWithSerializedPb(
+ const FileDescriptor* file_descriptor, PyObject* serialized_pb);
+
+// Return the C++ descriptor pointer.
+// This function checks the parameter type; on error, return NULL with a Python
+// exception set.
+const Descriptor* PyMessageDescriptor_AsDescriptor(PyObject* obj);
+const FieldDescriptor* PyFieldDescriptor_AsDescriptor(PyObject* obj);
+const EnumDescriptor* PyEnumDescriptor_AsDescriptor(PyObject* obj);
+const FileDescriptor* PyFileDescriptor_AsDescriptor(PyObject* obj);
+
+// Returns the raw C++ pointer.
+const void* PyDescriptor_AsVoidPtr(PyObject* obj);
+
+// Check that the calling Python code is the global scope of a _pb2.py module.
+// This function is used to support the current code generated by the proto
+// compiler, which insists on modifying descriptors after they have been
+// created.
+//
+// stacklevel indicates which Python frame should be the _pb2.py module.
+//
+// Don't use this function outside descriptor classes.
+bool _CalledFromGeneratedFile(int stacklevel);
+
+bool InitDescriptor();
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.cc
new file mode 100644
index 0000000000..d0aae9c9b3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.cc
@@ -0,0 +1,1786 @@
+// 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.
+
+// Mappings and Sequences of descriptors.
+// Used by Descriptor.fields_by_name, EnumDescriptor.values...
+//
+// They avoid the allocation of a full dictionary or a full list: they simply
+// store a pointer to the parent descriptor, use the C++ Descriptor methods (see
+// google/protobuf/descriptor.h) to retrieve other descriptors, and create
+// Python objects on the fly.
+//
+// The containers fully conform to abc.Mapping and abc.Sequence, and behave just
+// like read-only dictionaries and lists.
+//
+// Because the interface of C++ Descriptors is quite regular, this file actually
+// defines only three types, the exact behavior of a container is controlled by
+// a DescriptorContainerDef structure, which contains functions that uses the
+// public Descriptor API.
+//
+// Note: This DescriptorContainerDef is similar to the "virtual methods table"
+// that a C++ compiler generates for a class. We have to make it explicit
+// because the Python API is based on C, and does not play well with C++
+// inheritance.
+
+#include <Python.h>
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/pyext/descriptor_containers.h>
+#include <google/protobuf/pyext/descriptor_pool.h>
+#include <google/protobuf/pyext/descriptor.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+
+#if PY_MAJOR_VERSION >= 3
+ #define PyString_FromStringAndSize PyUnicode_FromStringAndSize
+ #define PyString_FromFormat PyUnicode_FromFormat
+ #define PyInt_FromLong PyLong_FromLong
+ #if PY_VERSION_HEX < 0x03030000
+ #error "Python 3.0 - 3.2 are not supported."
+ #endif
+ #define PyString_AsStringAndSize(ob, charpp, sizep) \
+ (PyUnicode_Check(ob)? \
+ ((*(charpp) = PyUnicode_AsUTF8AndSize(ob, (sizep))) == NULL? -1: 0): \
+ PyBytes_AsStringAndSize(ob, (charpp), (sizep)))
+#endif
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+struct PyContainer;
+
+typedef int (*CountMethod)(PyContainer* self);
+typedef const void* (*GetByIndexMethod)(PyContainer* self, int index);
+typedef const void* (*GetByNameMethod)(PyContainer* self, const string& name);
+typedef const void* (*GetByCamelcaseNameMethod)(PyContainer* self,
+ const string& name);
+typedef const void* (*GetByNumberMethod)(PyContainer* self, int index);
+typedef PyObject* (*NewObjectFromItemMethod)(const void* descriptor);
+typedef const string& (*GetItemNameMethod)(const void* descriptor);
+typedef const string& (*GetItemCamelcaseNameMethod)(const void* descriptor);
+typedef int (*GetItemNumberMethod)(const void* descriptor);
+typedef int (*GetItemIndexMethod)(const void* descriptor);
+
+struct DescriptorContainerDef {
+ const char* mapping_name;
+ // Returns the number of items in the container.
+ CountMethod count_fn;
+ // Retrieve item by index (usually the order of declaration in the proto file)
+ // Used by sequences, but also iterators. 0 <= index < Count().
+ GetByIndexMethod get_by_index_fn;
+ // Retrieve item by name (usually a call to some 'FindByName' method).
+ // Used by "by_name" mappings.
+ GetByNameMethod get_by_name_fn;
+ // Retrieve item by camelcase name (usually a call to some
+ // 'FindByCamelcaseName' method). Used by "by_camelcase_name" mappings.
+ GetByCamelcaseNameMethod get_by_camelcase_name_fn;
+ // Retrieve item by declared number (field tag, or enum value).
+ // Used by "by_number" mappings.
+ GetByNumberMethod get_by_number_fn;
+ // Converts a item C++ descriptor to a Python object. Returns a new reference.
+ NewObjectFromItemMethod new_object_from_item_fn;
+ // Retrieve the name of an item. Used by iterators on "by_name" mappings.
+ GetItemNameMethod get_item_name_fn;
+ // Retrieve the camelcase name of an item. Used by iterators on
+ // "by_camelcase_name" mappings.
+ GetItemCamelcaseNameMethod get_item_camelcase_name_fn;
+ // Retrieve the number of an item. Used by iterators on "by_number" mappings.
+ GetItemNumberMethod get_item_number_fn;
+ // Retrieve the index of an item for the container type.
+ // Used by "__contains__".
+ // If not set, "x in sequence" will do a linear search.
+ GetItemIndexMethod get_item_index_fn;
+};
+
+struct PyContainer {
+ PyObject_HEAD
+
+ // The proto2 descriptor this container belongs to the global DescriptorPool.
+ const void* descriptor;
+
+ // A pointer to a static structure with function pointers that control the
+ // behavior of the container. Very similar to the table of virtual functions
+ // of a C++ class.
+ const DescriptorContainerDef* container_def;
+
+ // The kind of container: list, or dict by name or value.
+ enum ContainerKind {
+ KIND_SEQUENCE,
+ KIND_BYNAME,
+ KIND_BYCAMELCASENAME,
+ KIND_BYNUMBER,
+ } kind;
+};
+
+struct PyContainerIterator {
+ PyObject_HEAD
+
+ // The container we are iterating over. Own a reference.
+ PyContainer* container;
+
+ // The current index in the iterator.
+ int index;
+
+ // The kind of container: list, or dict by name or value.
+ enum IterKind {
+ KIND_ITERKEY,
+ KIND_ITERVALUE,
+ KIND_ITERITEM,
+ KIND_ITERVALUE_REVERSED, // For sequences
+ } kind;
+};
+
+namespace descriptor {
+
+// Returns the C++ item descriptor for a given Python key.
+// When the descriptor is found, return true and set *item.
+// When the descriptor is not found, return true, but set *item to NULL.
+// On error, returns false with an exception set.
+static bool _GetItemByKey(PyContainer* self, PyObject* key, const void** item) {
+ switch (self->kind) {
+ case PyContainer::KIND_BYNAME:
+ {
+ char* name;
+ Py_ssize_t name_size;
+ if (PyString_AsStringAndSize(key, &name, &name_size) < 0) {
+ if (PyErr_ExceptionMatches(PyExc_TypeError)) {
+ // Not a string, cannot be in the container.
+ PyErr_Clear();
+ *item = NULL;
+ return true;
+ }
+ return false;
+ }
+ *item = self->container_def->get_by_name_fn(
+ self, string(name, name_size));
+ return true;
+ }
+ case PyContainer::KIND_BYCAMELCASENAME:
+ {
+ char* camelcase_name;
+ Py_ssize_t name_size;
+ if (PyString_AsStringAndSize(key, &camelcase_name, &name_size) < 0) {
+ if (PyErr_ExceptionMatches(PyExc_TypeError)) {
+ // Not a string, cannot be in the container.
+ PyErr_Clear();
+ *item = NULL;
+ return true;
+ }
+ return false;
+ }
+ *item = self->container_def->get_by_camelcase_name_fn(
+ self, string(camelcase_name, name_size));
+ return true;
+ }
+ case PyContainer::KIND_BYNUMBER:
+ {
+ Py_ssize_t number = PyNumber_AsSsize_t(key, NULL);
+ if (number == -1 && PyErr_Occurred()) {
+ if (PyErr_ExceptionMatches(PyExc_TypeError)) {
+ // Not a number, cannot be in the container.
+ PyErr_Clear();
+ *item = NULL;
+ return true;
+ }
+ return false;
+ }
+ *item = self->container_def->get_by_number_fn(self, number);
+ return true;
+ }
+ default:
+ PyErr_SetNone(PyExc_NotImplementedError);
+ return false;
+ }
+}
+
+// Returns the key of the object at the given index.
+// Used when iterating over mappings.
+static PyObject* _NewKey_ByIndex(PyContainer* self, Py_ssize_t index) {
+ const void* item = self->container_def->get_by_index_fn(self, index);
+ switch (self->kind) {
+ case PyContainer::KIND_BYNAME:
+ {
+ const string& name(self->container_def->get_item_name_fn(item));
+ return PyString_FromStringAndSize(name.c_str(), name.size());
+ }
+ case PyContainer::KIND_BYCAMELCASENAME:
+ {
+ const string& name(
+ self->container_def->get_item_camelcase_name_fn(item));
+ return PyString_FromStringAndSize(name.c_str(), name.size());
+ }
+ case PyContainer::KIND_BYNUMBER:
+ {
+ int value = self->container_def->get_item_number_fn(item);
+ return PyInt_FromLong(value);
+ }
+ default:
+ PyErr_SetNone(PyExc_NotImplementedError);
+ return NULL;
+ }
+}
+
+// Returns the object at the given index.
+// Also used when iterating over mappings.
+static PyObject* _NewObj_ByIndex(PyContainer* self, Py_ssize_t index) {
+ return self->container_def->new_object_from_item_fn(
+ self->container_def->get_by_index_fn(self, index));
+}
+
+static Py_ssize_t Length(PyContainer* self) {
+ return self->container_def->count_fn(self);
+}
+
+// The DescriptorMapping type.
+
+static PyObject* Subscript(PyContainer* self, PyObject* key) {
+ const void* item = NULL;
+ if (!_GetItemByKey(self, key, &item)) {
+ return NULL;
+ }
+ if (!item) {
+ PyErr_SetObject(PyExc_KeyError, key);
+ return NULL;
+ }
+ return self->container_def->new_object_from_item_fn(item);
+}
+
+static int AssSubscript(PyContainer* self, PyObject* key, PyObject* value) {
+ if (_CalledFromGeneratedFile(0)) {
+ return 0;
+ }
+ PyErr_Format(PyExc_TypeError,
+ "'%.200s' object does not support item assignment",
+ Py_TYPE(self)->tp_name);
+ return -1;
+}
+
+static PyMappingMethods MappingMappingMethods = {
+ (lenfunc)Length, // mp_length
+ (binaryfunc)Subscript, // mp_subscript
+ (objobjargproc)AssSubscript, // mp_ass_subscript
+};
+
+static int Contains(PyContainer* self, PyObject* key) {
+ const void* item = NULL;
+ if (!_GetItemByKey(self, key, &item)) {
+ return -1;
+ }
+ if (item) {
+ return 1;
+ } else {
+ return 0;
+ }
+}
+
+static PyObject* ContainerRepr(PyContainer* self) {
+ const char* kind = "";
+ switch (self->kind) {
+ case PyContainer::KIND_SEQUENCE:
+ kind = "sequence";
+ break;
+ case PyContainer::KIND_BYNAME:
+ kind = "mapping by name";
+ break;
+ case PyContainer::KIND_BYCAMELCASENAME:
+ kind = "mapping by camelCase name";
+ break;
+ case PyContainer::KIND_BYNUMBER:
+ kind = "mapping by number";
+ break;
+ }
+ return PyString_FromFormat(
+ "<%s %s>", self->container_def->mapping_name, kind);
+}
+
+extern PyTypeObject DescriptorMapping_Type;
+extern PyTypeObject DescriptorSequence_Type;
+
+// A sequence container can only be equal to another sequence container, or (for
+// backward compatibility) to a list containing the same items.
+// Returns 1 if equal, 0 if unequal, -1 on error.
+static int DescriptorSequence_Equal(PyContainer* self, PyObject* other) {
+ // Check the identity of C++ pointers.
+ if (PyObject_TypeCheck(other, &DescriptorSequence_Type)) {
+ PyContainer* other_container = reinterpret_cast<PyContainer*>(other);
+ if (self->descriptor == other_container->descriptor &&
+ self->container_def == other_container->container_def &&
+ self->kind == other_container->kind) {
+ return 1;
+ } else {
+ return 0;
+ }
+ }
+
+ // If other is a list
+ if (PyList_Check(other)) {
+ // return list(self) == other
+ int size = Length(self);
+ if (size != PyList_Size(other)) {
+ return false;
+ }
+ for (int index = 0; index < size; index++) {
+ ScopedPyObjectPtr value1(_NewObj_ByIndex(self, index));
+ if (value1 == NULL) {
+ return -1;
+ }
+ PyObject* value2 = PyList_GetItem(other, index);
+ if (value2 == NULL) {
+ return -1;
+ }
+ int cmp = PyObject_RichCompareBool(value1.get(), value2, Py_EQ);
+ if (cmp != 1) // error or not equal
+ return cmp;
+ }
+ // All items were found and equal
+ return 1;
+ }
+
+ // Any other object is different.
+ return 0;
+}
+
+// A mapping container can only be equal to another mapping container, or (for
+// backward compatibility) to a dict containing the same items.
+// Returns 1 if equal, 0 if unequal, -1 on error.
+static int DescriptorMapping_Equal(PyContainer* self, PyObject* other) {
+ // Check the identity of C++ pointers.
+ if (PyObject_TypeCheck(other, &DescriptorMapping_Type)) {
+ PyContainer* other_container = reinterpret_cast<PyContainer*>(other);
+ if (self->descriptor == other_container->descriptor &&
+ self->container_def == other_container->container_def &&
+ self->kind == other_container->kind) {
+ return 1;
+ } else {
+ return 0;
+ }
+ }
+
+ // If other is a dict
+ if (PyDict_Check(other)) {
+ // equivalent to dict(self.items()) == other
+ int size = Length(self);
+ if (size != PyDict_Size(other)) {
+ return false;
+ }
+ for (int index = 0; index < size; index++) {
+ ScopedPyObjectPtr key(_NewKey_ByIndex(self, index));
+ if (key == NULL) {
+ return -1;
+ }
+ ScopedPyObjectPtr value1(_NewObj_ByIndex(self, index));
+ if (value1 == NULL) {
+ return -1;
+ }
+ PyObject* value2 = PyDict_GetItem(other, key.get());
+ if (value2 == NULL) {
+ // Not found in the other dictionary
+ return 0;
+ }
+ int cmp = PyObject_RichCompareBool(value1.get(), value2, Py_EQ);
+ if (cmp != 1) // error or not equal
+ return cmp;
+ }
+ // All items were found and equal
+ return 1;
+ }
+
+ // Any other object is different.
+ return 0;
+}
+
+static PyObject* RichCompare(PyContainer* self, PyObject* other, int opid) {
+ if (opid != Py_EQ && opid != Py_NE) {
+ Py_INCREF(Py_NotImplemented);
+ return Py_NotImplemented;
+ }
+
+ int result;
+
+ if (self->kind == PyContainer::KIND_SEQUENCE) {
+ result = DescriptorSequence_Equal(self, other);
+ } else {
+ result = DescriptorMapping_Equal(self, other);
+ }
+ if (result < 0) {
+ return NULL;
+ }
+ if (result ^ (opid == Py_NE)) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+
+static PySequenceMethods MappingSequenceMethods = {
+ 0, // sq_length
+ 0, // sq_concat
+ 0, // sq_repeat
+ 0, // sq_item
+ 0, // sq_slice
+ 0, // sq_ass_item
+ 0, // sq_ass_slice
+ (objobjproc)Contains, // sq_contains
+};
+
+static PyObject* Get(PyContainer* self, PyObject* args) {
+ PyObject* key;
+ PyObject* default_value = Py_None;
+ if (!PyArg_UnpackTuple(args, "get", 1, 2, &key, &default_value)) {
+ return NULL;
+ }
+
+ const void* item;
+ if (!_GetItemByKey(self, key, &item)) {
+ return NULL;
+ }
+ if (item == NULL) {
+ Py_INCREF(default_value);
+ return default_value;
+ }
+ return self->container_def->new_object_from_item_fn(item);
+}
+
+static PyObject* Keys(PyContainer* self, PyObject* args) {
+ Py_ssize_t count = Length(self);
+ ScopedPyObjectPtr list(PyList_New(count));
+ if (list == NULL) {
+ return NULL;
+ }
+ for (Py_ssize_t index = 0; index < count; ++index) {
+ PyObject* key = _NewKey_ByIndex(self, index);
+ if (key == NULL) {
+ return NULL;
+ }
+ PyList_SET_ITEM(list.get(), index, key);
+ }
+ return list.release();
+}
+
+static PyObject* Values(PyContainer* self, PyObject* args) {
+ Py_ssize_t count = Length(self);
+ ScopedPyObjectPtr list(PyList_New(count));
+ if (list == NULL) {
+ return NULL;
+ }
+ for (Py_ssize_t index = 0; index < count; ++index) {
+ PyObject* value = _NewObj_ByIndex(self, index);
+ if (value == NULL) {
+ return NULL;
+ }
+ PyList_SET_ITEM(list.get(), index, value);
+ }
+ return list.release();
+}
+
+static PyObject* Items(PyContainer* self, PyObject* args) {
+ Py_ssize_t count = Length(self);
+ ScopedPyObjectPtr list(PyList_New(count));
+ if (list == NULL) {
+ return NULL;
+ }
+ for (Py_ssize_t index = 0; index < count; ++index) {
+ ScopedPyObjectPtr obj(PyTuple_New(2));
+ if (obj == NULL) {
+ return NULL;
+ }
+ PyObject* key = _NewKey_ByIndex(self, index);
+ if (key == NULL) {
+ return NULL;
+ }
+ PyTuple_SET_ITEM(obj.get(), 0, key);
+ PyObject* value = _NewObj_ByIndex(self, index);
+ if (value == NULL) {
+ return NULL;
+ }
+ PyTuple_SET_ITEM(obj.get(), 1, value);
+ PyList_SET_ITEM(list.get(), index, obj.release());
+ }
+ return list.release();
+}
+
+static PyObject* NewContainerIterator(PyContainer* mapping,
+ PyContainerIterator::IterKind kind);
+
+static PyObject* Iter(PyContainer* self) {
+ return NewContainerIterator(self, PyContainerIterator::KIND_ITERKEY);
+}
+static PyObject* IterKeys(PyContainer* self, PyObject* args) {
+ return NewContainerIterator(self, PyContainerIterator::KIND_ITERKEY);
+}
+static PyObject* IterValues(PyContainer* self, PyObject* args) {
+ return NewContainerIterator(self, PyContainerIterator::KIND_ITERVALUE);
+}
+static PyObject* IterItems(PyContainer* self, PyObject* args) {
+ return NewContainerIterator(self, PyContainerIterator::KIND_ITERITEM);
+}
+
+static PyMethodDef MappingMethods[] = {
+ { "get", (PyCFunction)Get, METH_VARARGS, },
+ { "keys", (PyCFunction)Keys, METH_NOARGS, },
+ { "values", (PyCFunction)Values, METH_NOARGS, },
+ { "items", (PyCFunction)Items, METH_NOARGS, },
+ { "iterkeys", (PyCFunction)IterKeys, METH_NOARGS, },
+ { "itervalues", (PyCFunction)IterValues, METH_NOARGS, },
+ { "iteritems", (PyCFunction)IterItems, METH_NOARGS, },
+ {NULL}
+};
+
+PyTypeObject DescriptorMapping_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ "DescriptorMapping", // tp_name
+ sizeof(PyContainer), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ (reprfunc)ContainerRepr, // tp_repr
+ 0, // tp_as_number
+ &MappingSequenceMethods, // tp_as_sequence
+ &MappingMappingMethods, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ 0, // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ (richcmpfunc)RichCompare, // tp_richcompare
+ 0, // tp_weaklistoffset
+ (getiterfunc)Iter, // tp_iter
+ 0, // tp_iternext
+ MappingMethods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ 0, // tp_alloc
+ 0, // tp_new
+ 0, // tp_free
+};
+
+// The DescriptorSequence type.
+
+static PyObject* GetItem(PyContainer* self, Py_ssize_t index) {
+ if (index < 0) {
+ index += Length(self);
+ }
+ if (index < 0 || index >= Length(self)) {
+ PyErr_SetString(PyExc_IndexError, "index out of range");
+ return NULL;
+ }
+ return _NewObj_ByIndex(self, index);
+}
+
+static PyObject *
+SeqSubscript(PyContainer* self, PyObject* item) {
+ if (PyIndex_Check(item)) {
+ Py_ssize_t index;
+ index = PyNumber_AsSsize_t(item, PyExc_IndexError);
+ if (index == -1 && PyErr_Occurred())
+ return NULL;
+ return GetItem(self, index);
+ }
+ // Materialize the list and delegate the operation to it.
+ ScopedPyObjectPtr list(PyObject_CallFunctionObjArgs(
+ reinterpret_cast<PyObject*>(&PyList_Type), self, NULL));
+ if (list == NULL) {
+ return NULL;
+ }
+ return Py_TYPE(list.get())->tp_as_mapping->mp_subscript(list.get(), item);
+}
+
+// Returns the position of the item in the sequence, of -1 if not found.
+// This function never fails.
+int Find(PyContainer* self, PyObject* item) {
+ // The item can only be in one position: item.index.
+ // Check that self[item.index] == item, it's faster than a linear search.
+ //
+ // This assumes that sequences are only defined by syntax of the .proto file:
+ // a specific item belongs to only one sequence, depending on its position in
+ // the .proto file definition.
+ const void* descriptor_ptr = PyDescriptor_AsVoidPtr(item);
+ if (descriptor_ptr == NULL) {
+ // Not a descriptor, it cannot be in the list.
+ return -1;
+ }
+ if (self->container_def->get_item_index_fn) {
+ int index = self->container_def->get_item_index_fn(descriptor_ptr);
+ if (index < 0 || index >= Length(self)) {
+ // This index is not from this collection.
+ return -1;
+ }
+ if (self->container_def->get_by_index_fn(self, index) != descriptor_ptr) {
+ // The descriptor at this index is not the same.
+ return -1;
+ }
+ // self[item.index] == item, so return the index.
+ return index;
+ } else {
+ // Fall back to linear search.
+ int length = Length(self);
+ for (int index=0; index < length; index++) {
+ if (self->container_def->get_by_index_fn(self, index) == descriptor_ptr) {
+ return index;
+ }
+ }
+ // Not found
+ return -1;
+ }
+}
+
+// Implements list.index(): the position of the item is in the sequence.
+static PyObject* Index(PyContainer* self, PyObject* item) {
+ int position = Find(self, item);
+ if (position < 0) {
+ // Not found
+ PyErr_SetNone(PyExc_ValueError);
+ return NULL;
+ } else {
+ return PyInt_FromLong(position);
+ }
+}
+// Implements "list.__contains__()": is the object in the sequence.
+static int SeqContains(PyContainer* self, PyObject* item) {
+ int position = Find(self, item);
+ if (position < 0) {
+ return 0;
+ } else {
+ return 1;
+ }
+}
+
+// Implements list.count(): number of occurrences of the item in the sequence.
+// An item can only appear once in a sequence. If it exists, return 1.
+static PyObject* Count(PyContainer* self, PyObject* item) {
+ int position = Find(self, item);
+ if (position < 0) {
+ return PyInt_FromLong(0);
+ } else {
+ return PyInt_FromLong(1);
+ }
+}
+
+static PyObject* Append(PyContainer* self, PyObject* args) {
+ if (_CalledFromGeneratedFile(0)) {
+ Py_RETURN_NONE;
+ }
+ PyErr_Format(PyExc_TypeError,
+ "'%.200s' object is not a mutable sequence",
+ Py_TYPE(self)->tp_name);
+ return NULL;
+}
+
+static PyObject* Reversed(PyContainer* self, PyObject* args) {
+ return NewContainerIterator(self,
+ PyContainerIterator::KIND_ITERVALUE_REVERSED);
+}
+
+static PyMethodDef SeqMethods[] = {
+ { "index", (PyCFunction)Index, METH_O, },
+ { "count", (PyCFunction)Count, METH_O, },
+ { "append", (PyCFunction)Append, METH_O, },
+ { "__reversed__", (PyCFunction)Reversed, METH_NOARGS, },
+ {NULL}
+};
+
+static PySequenceMethods SeqSequenceMethods = {
+ (lenfunc)Length, // sq_length
+ 0, // sq_concat
+ 0, // sq_repeat
+ (ssizeargfunc)GetItem, // sq_item
+ 0, // sq_slice
+ 0, // sq_ass_item
+ 0, // sq_ass_slice
+ (objobjproc)SeqContains, // sq_contains
+};
+
+static PyMappingMethods SeqMappingMethods = {
+ (lenfunc)Length, // mp_length
+ (binaryfunc)SeqSubscript, // mp_subscript
+ 0, // mp_ass_subscript
+};
+
+PyTypeObject DescriptorSequence_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ "DescriptorSequence", // tp_name
+ sizeof(PyContainer), // tp_basicsize
+ 0, // tp_itemsize
+ 0, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ (reprfunc)ContainerRepr, // tp_repr
+ 0, // tp_as_number
+ &SeqSequenceMethods, // tp_as_sequence
+ &SeqMappingMethods, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ 0, // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ (richcmpfunc)RichCompare, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ SeqMethods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ 0, // tp_alloc
+ 0, // tp_new
+ 0, // tp_free
+};
+
+static PyObject* NewMappingByName(
+ DescriptorContainerDef* container_def, const void* descriptor) {
+ PyContainer* self = PyObject_New(PyContainer, &DescriptorMapping_Type);
+ if (self == NULL) {
+ return NULL;
+ }
+ self->descriptor = descriptor;
+ self->container_def = container_def;
+ self->kind = PyContainer::KIND_BYNAME;
+ return reinterpret_cast<PyObject*>(self);
+}
+
+static PyObject* NewMappingByCamelcaseName(
+ DescriptorContainerDef* container_def, const void* descriptor) {
+ PyContainer* self = PyObject_New(PyContainer, &DescriptorMapping_Type);
+ if (self == NULL) {
+ return NULL;
+ }
+ self->descriptor = descriptor;
+ self->container_def = container_def;
+ self->kind = PyContainer::KIND_BYCAMELCASENAME;
+ return reinterpret_cast<PyObject*>(self);
+}
+
+static PyObject* NewMappingByNumber(
+ DescriptorContainerDef* container_def, const void* descriptor) {
+ if (container_def->get_by_number_fn == NULL ||
+ container_def->get_item_number_fn == NULL) {
+ PyErr_SetNone(PyExc_NotImplementedError);
+ return NULL;
+ }
+ PyContainer* self = PyObject_New(PyContainer, &DescriptorMapping_Type);
+ if (self == NULL) {
+ return NULL;
+ }
+ self->descriptor = descriptor;
+ self->container_def = container_def;
+ self->kind = PyContainer::KIND_BYNUMBER;
+ return reinterpret_cast<PyObject*>(self);
+}
+
+static PyObject* NewSequence(
+ DescriptorContainerDef* container_def, const void* descriptor) {
+ PyContainer* self = PyObject_New(PyContainer, &DescriptorSequence_Type);
+ if (self == NULL) {
+ return NULL;
+ }
+ self->descriptor = descriptor;
+ self->container_def = container_def;
+ self->kind = PyContainer::KIND_SEQUENCE;
+ return reinterpret_cast<PyObject*>(self);
+}
+
+// Implement iterators over PyContainers.
+
+static void Iterator_Dealloc(PyContainerIterator* self) {
+ Py_CLEAR(self->container);
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+static PyObject* Iterator_Next(PyContainerIterator* self) {
+ int count = self->container->container_def->count_fn(self->container);
+ if (self->index >= count) {
+ // Return NULL with no exception to indicate the end.
+ return NULL;
+ }
+ int index = self->index;
+ self->index += 1;
+ switch (self->kind) {
+ case PyContainerIterator::KIND_ITERKEY:
+ return _NewKey_ByIndex(self->container, index);
+ case PyContainerIterator::KIND_ITERVALUE:
+ return _NewObj_ByIndex(self->container, index);
+ case PyContainerIterator::KIND_ITERVALUE_REVERSED:
+ return _NewObj_ByIndex(self->container, count - index - 1);
+ case PyContainerIterator::KIND_ITERITEM:
+ {
+ PyObject* obj = PyTuple_New(2);
+ if (obj == NULL) {
+ return NULL;
+ }
+ PyObject* key = _NewKey_ByIndex(self->container, index);
+ if (key == NULL) {
+ Py_DECREF(obj);
+ return NULL;
+ }
+ PyTuple_SET_ITEM(obj, 0, key);
+ PyObject* value = _NewObj_ByIndex(self->container, index);
+ if (value == NULL) {
+ Py_DECREF(obj);
+ return NULL;
+ }
+ PyTuple_SET_ITEM(obj, 1, value);
+ return obj;
+ }
+ default:
+ PyErr_SetNone(PyExc_NotImplementedError);
+ return NULL;
+ }
+}
+
+static PyTypeObject ContainerIterator_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ "DescriptorContainerIterator", // tp_name
+ sizeof(PyContainerIterator), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)Iterator_Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ 0, // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ PyObject_SelfIter, // tp_iter
+ (iternextfunc)Iterator_Next, // tp_iternext
+ 0, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ 0, // tp_alloc
+ 0, // tp_new
+ 0, // tp_free
+};
+
+static PyObject* NewContainerIterator(PyContainer* container,
+ PyContainerIterator::IterKind kind) {
+ PyContainerIterator* self = PyObject_New(PyContainerIterator,
+ &ContainerIterator_Type);
+ if (self == NULL) {
+ return NULL;
+ }
+ Py_INCREF(container);
+ self->container = container;
+ self->kind = kind;
+ self->index = 0;
+
+ return reinterpret_cast<PyObject*>(self);
+}
+
+} // namespace descriptor
+
+// Now define the real collections!
+
+namespace message_descriptor {
+
+typedef const Descriptor* ParentDescriptor;
+
+static ParentDescriptor GetDescriptor(PyContainer* self) {
+ return reinterpret_cast<ParentDescriptor>(self->descriptor);
+}
+
+namespace fields {
+
+typedef const FieldDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->field_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindFieldByName(name);
+}
+
+static ItemDescriptor GetByCamelcaseName(PyContainer* self,
+ const string& name) {
+ return GetDescriptor(self)->FindFieldByCamelcaseName(name);
+}
+
+static ItemDescriptor GetByNumber(PyContainer* self, int number) {
+ return GetDescriptor(self)->FindFieldByNumber(number);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->field(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyFieldDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static const string& GetItemCamelcaseName(ItemDescriptor item) {
+ return item->camelcase_name();
+}
+
+static int GetItemNumber(ItemDescriptor item) {
+ return item->number();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "MessageFields",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)GetByCamelcaseName,
+ (GetByNumberMethod)GetByNumber,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)GetItemCamelcaseName,
+ (GetItemNumberMethod)GetItemNumber,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace fields
+
+PyObject* NewMessageFieldsByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&fields::ContainerDef, descriptor);
+}
+
+PyObject* NewMessageFieldsByCamelcaseName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByCamelcaseName(&fields::ContainerDef,
+ descriptor);
+}
+
+PyObject* NewMessageFieldsByNumber(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByNumber(&fields::ContainerDef, descriptor);
+}
+
+PyObject* NewMessageFieldsSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&fields::ContainerDef, descriptor);
+}
+
+namespace nested_types {
+
+typedef const Descriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->nested_type_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindNestedTypeByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->nested_type(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyMessageDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "MessageNestedTypes",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace nested_types
+
+PyObject* NewMessageNestedTypesSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&nested_types::ContainerDef, descriptor);
+}
+
+PyObject* NewMessageNestedTypesByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&nested_types::ContainerDef, descriptor);
+}
+
+namespace enums {
+
+typedef const EnumDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->enum_type_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindEnumTypeByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->enum_type(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyEnumDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "MessageNestedEnums",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace enums
+
+PyObject* NewMessageEnumsByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&enums::ContainerDef, descriptor);
+}
+
+PyObject* NewMessageEnumsSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&enums::ContainerDef, descriptor);
+}
+
+namespace enumvalues {
+
+// This is the "enum_values_by_name" mapping, which collects values from all
+// enum types in a message.
+//
+// Note that the behavior of the C++ descriptor is different: it will search and
+// return the first value that matches the name, whereas the Python
+// implementation retrieves the last one.
+
+typedef const EnumValueDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ int count = 0;
+ for (int i = 0; i < GetDescriptor(self)->enum_type_count(); ++i) {
+ count += GetDescriptor(self)->enum_type(i)->value_count();
+ }
+ return count;
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindEnumValueByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ // This is not optimal, but the number of enums *types* in a given message
+ // is small. This function is only used when iterating over the mapping.
+ const EnumDescriptor* enum_type = NULL;
+ int enum_type_count = GetDescriptor(self)->enum_type_count();
+ for (int i = 0; i < enum_type_count; ++i) {
+ enum_type = GetDescriptor(self)->enum_type(i);
+ int enum_value_count = enum_type->value_count();
+ if (index < enum_value_count) {
+ // Found it!
+ break;
+ }
+ index -= enum_value_count;
+ }
+ // The next statement cannot overflow, because this function is only called by
+ // internal iterators which ensure that 0 <= index < Count().
+ return enum_type->value(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyEnumValueDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "MessageEnumValues",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)NULL,
+};
+
+} // namespace enumvalues
+
+PyObject* NewMessageEnumValuesByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&enumvalues::ContainerDef, descriptor);
+}
+
+namespace extensions {
+
+typedef const FieldDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->extension_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindExtensionByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->extension(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyFieldDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "MessageExtensions",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace extensions
+
+PyObject* NewMessageExtensionsByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&extensions::ContainerDef, descriptor);
+}
+
+PyObject* NewMessageExtensionsSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&extensions::ContainerDef, descriptor);
+}
+
+namespace oneofs {
+
+typedef const OneofDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->oneof_decl_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindOneofByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->oneof_decl(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyOneofDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "MessageOneofs",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace oneofs
+
+PyObject* NewMessageOneofsByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&oneofs::ContainerDef, descriptor);
+}
+
+PyObject* NewMessageOneofsSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&oneofs::ContainerDef, descriptor);
+}
+
+} // namespace message_descriptor
+
+namespace enum_descriptor {
+
+typedef const EnumDescriptor* ParentDescriptor;
+
+static ParentDescriptor GetDescriptor(PyContainer* self) {
+ return reinterpret_cast<ParentDescriptor>(self->descriptor);
+}
+
+namespace enumvalues {
+
+typedef const EnumValueDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->value_count();
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->value(index);
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindValueByName(name);
+}
+
+static ItemDescriptor GetByNumber(PyContainer* self, int number) {
+ return GetDescriptor(self)->FindValueByNumber(number);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyEnumValueDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemNumber(ItemDescriptor item) {
+ return item->number();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "EnumValues",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)GetByNumber,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)GetItemNumber,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace enumvalues
+
+PyObject* NewEnumValuesByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&enumvalues::ContainerDef, descriptor);
+}
+
+PyObject* NewEnumValuesByNumber(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByNumber(&enumvalues::ContainerDef, descriptor);
+}
+
+PyObject* NewEnumValuesSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&enumvalues::ContainerDef, descriptor);
+}
+
+} // namespace enum_descriptor
+
+namespace oneof_descriptor {
+
+typedef const OneofDescriptor* ParentDescriptor;
+
+static ParentDescriptor GetDescriptor(PyContainer* self) {
+ return reinterpret_cast<ParentDescriptor>(self->descriptor);
+}
+
+namespace fields {
+
+typedef const FieldDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->field_count();
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->field(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyFieldDescriptor_FromDescriptor(item);
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index_in_oneof();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "OneofFields",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)NULL,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)NULL,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace fields
+
+PyObject* NewOneofFieldsSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&fields::ContainerDef, descriptor);
+}
+
+} // namespace oneof_descriptor
+
+namespace service_descriptor {
+
+typedef const ServiceDescriptor* ParentDescriptor;
+
+static ParentDescriptor GetDescriptor(PyContainer* self) {
+ return reinterpret_cast<ParentDescriptor>(self->descriptor);
+}
+
+namespace methods {
+
+typedef const MethodDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->method_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindMethodByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->method(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyMethodDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "ServiceMethods",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace methods
+
+PyObject* NewServiceMethodsSeq(ParentDescriptor descriptor) {
+ return descriptor::NewSequence(&methods::ContainerDef, descriptor);
+}
+
+PyObject* NewServiceMethodsByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&methods::ContainerDef, descriptor);
+}
+
+} // namespace service_descriptor
+
+namespace file_descriptor {
+
+typedef const FileDescriptor* ParentDescriptor;
+
+static ParentDescriptor GetDescriptor(PyContainer* self) {
+ return reinterpret_cast<ParentDescriptor>(self->descriptor);
+}
+
+namespace messages {
+
+typedef const Descriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->message_type_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindMessageTypeByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->message_type(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyMessageDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "FileMessages",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace messages
+
+PyObject* NewFileMessageTypesByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&messages::ContainerDef, descriptor);
+}
+
+namespace enums {
+
+typedef const EnumDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->enum_type_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindEnumTypeByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->enum_type(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyEnumDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "FileEnums",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace enums
+
+PyObject* NewFileEnumTypesByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&enums::ContainerDef, descriptor);
+}
+
+namespace extensions {
+
+typedef const FieldDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->extension_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindExtensionByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->extension(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyFieldDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "FileExtensions",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace extensions
+
+PyObject* NewFileExtensionsByName(ParentDescriptor descriptor) {
+ return descriptor::NewMappingByName(&extensions::ContainerDef, descriptor);
+}
+
+namespace services {
+
+typedef const ServiceDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->service_count();
+}
+
+static ItemDescriptor GetByName(PyContainer* self, const string& name) {
+ return GetDescriptor(self)->FindServiceByName(name);
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->service(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyServiceDescriptor_FromDescriptor(item);
+}
+
+static const string& GetItemName(ItemDescriptor item) {
+ return item->name();
+}
+
+static int GetItemIndex(ItemDescriptor item) {
+ return item->index();
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "FileServices",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)GetByName,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)GetItemName,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)GetItemIndex,
+};
+
+} // namespace services
+
+PyObject* NewFileServicesByName(const FileDescriptor* descriptor) {
+ return descriptor::NewMappingByName(&services::ContainerDef, descriptor);
+}
+
+namespace dependencies {
+
+typedef const FileDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->dependency_count();
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->dependency(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyFileDescriptor_FromDescriptor(item);
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "FileDependencies",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)NULL,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)NULL,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)NULL,
+};
+
+} // namespace dependencies
+
+PyObject* NewFileDependencies(const FileDescriptor* descriptor) {
+ return descriptor::NewSequence(&dependencies::ContainerDef, descriptor);
+}
+
+namespace public_dependencies {
+
+typedef const FileDescriptor* ItemDescriptor;
+
+static int Count(PyContainer* self) {
+ return GetDescriptor(self)->public_dependency_count();
+}
+
+static ItemDescriptor GetByIndex(PyContainer* self, int index) {
+ return GetDescriptor(self)->public_dependency(index);
+}
+
+static PyObject* NewObjectFromItem(ItemDescriptor item) {
+ return PyFileDescriptor_FromDescriptor(item);
+}
+
+static DescriptorContainerDef ContainerDef = {
+ "FilePublicDependencies",
+ (CountMethod)Count,
+ (GetByIndexMethod)GetByIndex,
+ (GetByNameMethod)NULL,
+ (GetByCamelcaseNameMethod)NULL,
+ (GetByNumberMethod)NULL,
+ (NewObjectFromItemMethod)NewObjectFromItem,
+ (GetItemNameMethod)NULL,
+ (GetItemCamelcaseNameMethod)NULL,
+ (GetItemNumberMethod)NULL,
+ (GetItemIndexMethod)NULL,
+};
+
+} // namespace public_dependencies
+
+PyObject* NewFilePublicDependencies(const FileDescriptor* descriptor) {
+ return descriptor::NewSequence(&public_dependencies::ContainerDef,
+ descriptor);
+}
+
+} // namespace file_descriptor
+
+
+// Register all implementations
+
+bool InitDescriptorMappingTypes() {
+ if (PyType_Ready(&descriptor::DescriptorMapping_Type) < 0)
+ return false;
+ if (PyType_Ready(&descriptor::DescriptorSequence_Type) < 0)
+ return false;
+ if (PyType_Ready(&descriptor::ContainerIterator_Type) < 0)
+ return false;
+ return true;
+}
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.h
new file mode 100644
index 0000000000..83de07b68c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_containers.h
@@ -0,0 +1,109 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_CONTAINERS_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_CONTAINERS_H__
+
+// Mappings and Sequences of descriptors.
+// They implement containers like fields_by_name, EnumDescriptor.values...
+// See descriptor_containers.cc for more description.
+#include <Python.h>
+
+namespace google {
+namespace protobuf {
+
+class Descriptor;
+class FileDescriptor;
+class EnumDescriptor;
+class OneofDescriptor;
+class ServiceDescriptor;
+
+namespace python {
+
+// Initialize the various types and objects.
+bool InitDescriptorMappingTypes();
+
+// Each function below returns a Mapping, or a Sequence of descriptors.
+// They all return a new reference.
+
+namespace message_descriptor {
+PyObject* NewMessageFieldsByName(const Descriptor* descriptor);
+PyObject* NewMessageFieldsByCamelcaseName(const Descriptor* descriptor);
+PyObject* NewMessageFieldsByNumber(const Descriptor* descriptor);
+PyObject* NewMessageFieldsSeq(const Descriptor* descriptor);
+
+PyObject* NewMessageNestedTypesSeq(const Descriptor* descriptor);
+PyObject* NewMessageNestedTypesByName(const Descriptor* descriptor);
+
+PyObject* NewMessageEnumsByName(const Descriptor* descriptor);
+PyObject* NewMessageEnumsSeq(const Descriptor* descriptor);
+PyObject* NewMessageEnumValuesByName(const Descriptor* descriptor);
+
+PyObject* NewMessageExtensionsByName(const Descriptor* descriptor);
+PyObject* NewMessageExtensionsSeq(const Descriptor* descriptor);
+
+PyObject* NewMessageOneofsByName(const Descriptor* descriptor);
+PyObject* NewMessageOneofsSeq(const Descriptor* descriptor);
+} // namespace message_descriptor
+
+namespace enum_descriptor {
+PyObject* NewEnumValuesByName(const EnumDescriptor* descriptor);
+PyObject* NewEnumValuesByNumber(const EnumDescriptor* descriptor);
+PyObject* NewEnumValuesSeq(const EnumDescriptor* descriptor);
+} // namespace enum_descriptor
+
+namespace oneof_descriptor {
+PyObject* NewOneofFieldsSeq(const OneofDescriptor* descriptor);
+} // namespace oneof_descriptor
+
+namespace file_descriptor {
+PyObject* NewFileMessageTypesByName(const FileDescriptor* descriptor);
+
+PyObject* NewFileEnumTypesByName(const FileDescriptor* descriptor);
+
+PyObject* NewFileExtensionsByName(const FileDescriptor* descriptor);
+
+PyObject* NewFileServicesByName(const FileDescriptor* descriptor);
+
+PyObject* NewFileDependencies(const FileDescriptor* descriptor);
+PyObject* NewFilePublicDependencies(const FileDescriptor* descriptor);
+} // namespace file_descriptor
+
+namespace service_descriptor {
+PyObject* NewServiceMethodsSeq(const ServiceDescriptor* descriptor);
+PyObject* NewServiceMethodsByName(const ServiceDescriptor* descriptor);
+} // namespace service_descriptor
+
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_CONTAINERS_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.cc
new file mode 100644
index 0000000000..daa40cc720
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.cc
@@ -0,0 +1,148 @@
+// 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.
+
+// This file defines a C++ DescriptorDatabase, which wraps a Python Database
+// and delegate all its operations to Python methods.
+
+#include <google/protobuf/pyext/descriptor_database.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/pyext/message.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+PyDescriptorDatabase::PyDescriptorDatabase(PyObject* py_database)
+ : py_database_(py_database) {
+ Py_INCREF(py_database_);
+}
+
+PyDescriptorDatabase::~PyDescriptorDatabase() { Py_DECREF(py_database_); }
+
+// Convert a Python object to a FileDescriptorProto pointer.
+// Handles all kinds of Python errors, which are simply logged.
+static bool GetFileDescriptorProto(PyObject* py_descriptor,
+ FileDescriptorProto* output) {
+ if (py_descriptor == NULL) {
+ if (PyErr_ExceptionMatches(PyExc_KeyError)) {
+ // Expected error: item was simply not found.
+ PyErr_Clear();
+ } else {
+ GOOGLE_LOG(ERROR) << "DescriptorDatabase method raised an error";
+ PyErr_Print();
+ }
+ return false;
+ }
+ if (py_descriptor == Py_None) {
+ return false;
+ }
+ const Descriptor* filedescriptor_descriptor =
+ FileDescriptorProto::default_instance().GetDescriptor();
+ CMessage* message = reinterpret_cast<CMessage*>(py_descriptor);
+ if (PyObject_TypeCheck(py_descriptor, &CMessage_Type) &&
+ message->message->GetDescriptor() == filedescriptor_descriptor) {
+ // Fast path: Just use the pointer.
+ FileDescriptorProto* file_proto =
+ static_cast<FileDescriptorProto*>(message->message);
+ *output = *file_proto;
+ return true;
+ } else {
+ // Slow path: serialize the message. This allows to use databases which
+ // use a different implementation of FileDescriptorProto.
+ ScopedPyObjectPtr serialized_pb(
+ PyObject_CallMethod(py_descriptor, "SerializeToString", NULL));
+ if (serialized_pb == NULL) {
+ GOOGLE_LOG(ERROR)
+ << "DescriptorDatabase method did not return a FileDescriptorProto";
+ PyErr_Print();
+ return false;
+ }
+ char* str;
+ Py_ssize_t len;
+ if (PyBytes_AsStringAndSize(serialized_pb.get(), &str, &len) < 0) {
+ GOOGLE_LOG(ERROR)
+ << "DescriptorDatabase method did not return a FileDescriptorProto";
+ PyErr_Print();
+ return false;
+ }
+ FileDescriptorProto file_proto;
+ if (!file_proto.ParseFromArray(str, len)) {
+ GOOGLE_LOG(ERROR)
+ << "DescriptorDatabase method did not return a FileDescriptorProto";
+ return false;
+ }
+ *output = file_proto;
+ return true;
+ }
+}
+
+// Find a file by file name.
+bool PyDescriptorDatabase::FindFileByName(const string& filename,
+ FileDescriptorProto* output) {
+ ScopedPyObjectPtr py_descriptor(PyObject_CallMethod(
+ py_database_, "FindFileByName", "s#", filename.c_str(), filename.size()));
+ return GetFileDescriptorProto(py_descriptor.get(), output);
+}
+
+// Find the file that declares the given fully-qualified symbol name.
+bool PyDescriptorDatabase::FindFileContainingSymbol(
+ const string& symbol_name, FileDescriptorProto* output) {
+ ScopedPyObjectPtr py_descriptor(
+ PyObject_CallMethod(py_database_, "FindFileContainingSymbol", "s#",
+ symbol_name.c_str(), symbol_name.size()));
+ return GetFileDescriptorProto(py_descriptor.get(), output);
+}
+
+// Find the file which defines an extension extending the given message type
+// with the given field number.
+// Python DescriptorDatabases are not required to implement this method.
+bool PyDescriptorDatabase::FindFileContainingExtension(
+ const string& containing_type, int field_number,
+ FileDescriptorProto* output) {
+ ScopedPyObjectPtr py_method(
+ PyObject_GetAttrString(py_database_, "FindFileContainingExtension"));
+ if (py_method == NULL) {
+ // This method is not implemented, returns without error.
+ PyErr_Clear();
+ return false;
+ }
+ ScopedPyObjectPtr py_descriptor(
+ PyObject_CallFunction(py_method.get(), "s#i", containing_type.c_str(),
+ containing_type.size(), field_number));
+ return GetFileDescriptorProto(py_descriptor.get(), output);
+}
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.h
new file mode 100644
index 0000000000..fc71c4bcb0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_database.h
@@ -0,0 +1,75 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_DATABASE_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_DATABASE_H__
+
+#include <Python.h>
+
+#include <google/protobuf/descriptor_database.h>
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+class PyDescriptorDatabase : public DescriptorDatabase {
+ public:
+ explicit PyDescriptorDatabase(PyObject* py_database);
+ ~PyDescriptorDatabase();
+
+ // Implement the abstract interface. All these functions fill the output
+ // with a copy of FileDescriptorProto.
+
+ // Find a file by file name.
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output);
+
+ // Find the file that declares the given fully-qualified symbol name.
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output);
+
+ // Find the file which defines an extension extending the given message type
+ // with the given field number.
+ // Containing_type must be a fully-qualified type name.
+ // Python objects are not required to implement this method.
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output);
+
+ private:
+ // The python object that implements the database. The reference is owned.
+ PyObject* py_database_;
+};
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_DATABASE_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.cc
new file mode 100644
index 0000000000..cfd9869030
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.cc
@@ -0,0 +1,631 @@
+// 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.
+
+// Implements the DescriptorPool, which collects all descriptors.
+
+#include <Python.h>
+
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/pyext/descriptor.h>
+#include <google/protobuf/pyext/descriptor_database.h>
+#include <google/protobuf/pyext/descriptor_pool.h>
+#include <google/protobuf/pyext/message.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+
+#if PY_MAJOR_VERSION >= 3
+ #define PyString_FromStringAndSize PyUnicode_FromStringAndSize
+ #if PY_VERSION_HEX < 0x03030000
+ #error "Python 3.0 - 3.2 are not supported."
+ #endif
+ #define PyString_AsStringAndSize(ob, charpp, sizep) \
+ (PyUnicode_Check(ob)? \
+ ((*(charpp) = PyUnicode_AsUTF8AndSize(ob, (sizep))) == NULL? -1: 0): \
+ PyBytes_AsStringAndSize(ob, (charpp), (sizep)))
+#endif
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+// A map to cache Python Pools per C++ pointer.
+// Pointers are not owned here, and belong to the PyDescriptorPool.
+static hash_map<const DescriptorPool*, PyDescriptorPool*> descriptor_pool_map;
+
+namespace cdescriptor_pool {
+
+// Create a Python DescriptorPool object, but does not fill the "pool"
+// attribute.
+static PyDescriptorPool* _CreateDescriptorPool() {
+ PyDescriptorPool* cpool = PyObject_New(
+ PyDescriptorPool, &PyDescriptorPool_Type);
+ if (cpool == NULL) {
+ return NULL;
+ }
+
+ cpool->underlay = NULL;
+ cpool->database = NULL;
+
+ DynamicMessageFactory* message_factory = new DynamicMessageFactory();
+ // This option might be the default some day.
+ message_factory->SetDelegateToGeneratedFactory(true);
+ cpool->message_factory = message_factory;
+
+ // TODO(amauryfa): Rewrite the SymbolDatabase in C so that it uses the same
+ // storage.
+ cpool->classes_by_descriptor =
+ new PyDescriptorPool::ClassesByMessageMap();
+ cpool->descriptor_options =
+ new hash_map<const void*, PyObject *>();
+
+ return cpool;
+}
+
+// Create a Python DescriptorPool, using the given pool as an underlay:
+// new messages will be added to a custom pool, not to the underlay.
+//
+// Ownership of the underlay is not transferred, its pointer should
+// stay alive.
+static PyDescriptorPool* PyDescriptorPool_NewWithUnderlay(
+ const DescriptorPool* underlay) {
+ PyDescriptorPool* cpool = _CreateDescriptorPool();
+ if (cpool == NULL) {
+ return NULL;
+ }
+ cpool->pool = new DescriptorPool(underlay);
+ cpool->underlay = underlay;
+
+ if (!descriptor_pool_map.insert(
+ std::make_pair(cpool->pool, cpool)).second) {
+ // Should never happen -- would indicate an internal error / bug.
+ PyErr_SetString(PyExc_ValueError, "DescriptorPool already registered");
+ return NULL;
+ }
+
+ return cpool;
+}
+
+static PyDescriptorPool* PyDescriptorPool_NewWithDatabase(
+ DescriptorDatabase* database) {
+ PyDescriptorPool* cpool = _CreateDescriptorPool();
+ if (cpool == NULL) {
+ return NULL;
+ }
+ if (database != NULL) {
+ cpool->pool = new DescriptorPool(database);
+ cpool->database = database;
+ } else {
+ cpool->pool = new DescriptorPool();
+ }
+
+ if (!descriptor_pool_map.insert(std::make_pair(cpool->pool, cpool)).second) {
+ // Should never happen -- would indicate an internal error / bug.
+ PyErr_SetString(PyExc_ValueError, "DescriptorPool already registered");
+ return NULL;
+ }
+
+ return cpool;
+}
+
+// The public DescriptorPool constructor.
+static PyObject* New(PyTypeObject* type,
+ PyObject* args, PyObject* kwargs) {
+ static char* kwlist[] = {"descriptor_db", 0};
+ PyObject* py_database = NULL;
+ if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|O", kwlist, &py_database)) {
+ return NULL;
+ }
+ DescriptorDatabase* database = NULL;
+ if (py_database && py_database != Py_None) {
+ database = new PyDescriptorDatabase(py_database);
+ }
+ return reinterpret_cast<PyObject*>(
+ PyDescriptorPool_NewWithDatabase(database));
+}
+
+static void Dealloc(PyDescriptorPool* self) {
+ typedef PyDescriptorPool::ClassesByMessageMap::iterator iterator;
+ descriptor_pool_map.erase(self->pool);
+ for (iterator it = self->classes_by_descriptor->begin();
+ it != self->classes_by_descriptor->end(); ++it) {
+ Py_DECREF(it->second);
+ }
+ delete self->classes_by_descriptor;
+ for (hash_map<const void*, PyObject*>::iterator it =
+ self->descriptor_options->begin();
+ it != self->descriptor_options->end(); ++it) {
+ Py_DECREF(it->second);
+ }
+ delete self->descriptor_options;
+ delete self->message_factory;
+ delete self->database;
+ delete self->pool;
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+PyObject* FindMessageByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const Descriptor* message_descriptor =
+ self->pool->FindMessageTypeByName(string(name, name_size));
+
+ if (message_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find message %.200s", name);
+ return NULL;
+ }
+
+ return PyMessageDescriptor_FromDescriptor(message_descriptor);
+}
+
+// Add a message class to our database.
+int RegisterMessageClass(PyDescriptorPool* self,
+ const Descriptor* message_descriptor,
+ CMessageClass* message_class) {
+ Py_INCREF(message_class);
+ typedef PyDescriptorPool::ClassesByMessageMap::iterator iterator;
+ std::pair<iterator, bool> ret = self->classes_by_descriptor->insert(
+ std::make_pair(message_descriptor, message_class));
+ if (!ret.second) {
+ // Update case: DECREF the previous value.
+ Py_DECREF(ret.first->second);
+ ret.first->second = message_class;
+ }
+ return 0;
+}
+
+// Retrieve the message class added to our database.
+CMessageClass* GetMessageClass(PyDescriptorPool* self,
+ const Descriptor* message_descriptor) {
+ typedef PyDescriptorPool::ClassesByMessageMap::iterator iterator;
+ iterator ret = self->classes_by_descriptor->find(message_descriptor);
+ if (ret == self->classes_by_descriptor->end()) {
+ PyErr_Format(PyExc_TypeError, "No message class registered for '%s'",
+ message_descriptor->full_name().c_str());
+ return NULL;
+ } else {
+ return ret->second;
+ }
+}
+
+PyObject* FindFileByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const FileDescriptor* file_descriptor =
+ self->pool->FindFileByName(string(name, name_size));
+ if (file_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find file %.200s",
+ name);
+ return NULL;
+ }
+
+ return PyFileDescriptor_FromDescriptor(file_descriptor);
+}
+
+PyObject* FindFieldByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const FieldDescriptor* field_descriptor =
+ self->pool->FindFieldByName(string(name, name_size));
+ if (field_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find field %.200s",
+ name);
+ return NULL;
+ }
+
+ return PyFieldDescriptor_FromDescriptor(field_descriptor);
+}
+
+PyObject* FindExtensionByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const FieldDescriptor* field_descriptor =
+ self->pool->FindExtensionByName(string(name, name_size));
+ if (field_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find extension field %.200s", name);
+ return NULL;
+ }
+
+ return PyFieldDescriptor_FromDescriptor(field_descriptor);
+}
+
+PyObject* FindEnumTypeByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const EnumDescriptor* enum_descriptor =
+ self->pool->FindEnumTypeByName(string(name, name_size));
+ if (enum_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find enum %.200s", name);
+ return NULL;
+ }
+
+ return PyEnumDescriptor_FromDescriptor(enum_descriptor);
+}
+
+PyObject* FindOneofByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const OneofDescriptor* oneof_descriptor =
+ self->pool->FindOneofByName(string(name, name_size));
+ if (oneof_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find oneof %.200s", name);
+ return NULL;
+ }
+
+ return PyOneofDescriptor_FromDescriptor(oneof_descriptor);
+}
+
+PyObject* FindServiceByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const ServiceDescriptor* service_descriptor =
+ self->pool->FindServiceByName(string(name, name_size));
+ if (service_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find service %.200s", name);
+ return NULL;
+ }
+
+ return PyServiceDescriptor_FromDescriptor(service_descriptor);
+}
+
+PyObject* FindMethodByName(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const MethodDescriptor* method_descriptor =
+ self->pool->FindMethodByName(string(name, name_size));
+ if (method_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find method %.200s", name);
+ return NULL;
+ }
+
+ return PyMethodDescriptor_FromDescriptor(method_descriptor);
+}
+
+PyObject* FindFileContainingSymbol(PyDescriptorPool* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char* name;
+ if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
+ return NULL;
+ }
+
+ const FileDescriptor* file_descriptor =
+ self->pool->FindFileContainingSymbol(string(name, name_size));
+ if (file_descriptor == NULL) {
+ PyErr_Format(PyExc_KeyError, "Couldn't find symbol %.200s", name);
+ return NULL;
+ }
+
+ return PyFileDescriptor_FromDescriptor(file_descriptor);
+}
+
+// These functions should not exist -- the only valid way to create
+// descriptors is to call Add() or AddSerializedFile().
+// But these AddDescriptor() functions were created in Python and some people
+// call them, so we support them for now for compatibility.
+// However we do check that the existing descriptor already exists in the pool,
+// which appears to always be true for existing calls -- but then why do people
+// call a function that will just be a no-op?
+// TODO(amauryfa): Need to investigate further.
+
+PyObject* AddFileDescriptor(PyDescriptorPool* self, PyObject* descriptor) {
+ const FileDescriptor* file_descriptor =
+ PyFileDescriptor_AsDescriptor(descriptor);
+ if (!file_descriptor) {
+ return NULL;
+ }
+ if (file_descriptor !=
+ self->pool->FindFileByName(file_descriptor->name())) {
+ PyErr_Format(PyExc_ValueError,
+ "The file descriptor %s does not belong to this pool",
+ file_descriptor->name().c_str());
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+PyObject* AddDescriptor(PyDescriptorPool* self, PyObject* descriptor) {
+ const Descriptor* message_descriptor =
+ PyMessageDescriptor_AsDescriptor(descriptor);
+ if (!message_descriptor) {
+ return NULL;
+ }
+ if (message_descriptor !=
+ self->pool->FindMessageTypeByName(message_descriptor->full_name())) {
+ PyErr_Format(PyExc_ValueError,
+ "The message descriptor %s does not belong to this pool",
+ message_descriptor->full_name().c_str());
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+PyObject* AddEnumDescriptor(PyDescriptorPool* self, PyObject* descriptor) {
+ const EnumDescriptor* enum_descriptor =
+ PyEnumDescriptor_AsDescriptor(descriptor);
+ if (!enum_descriptor) {
+ return NULL;
+ }
+ if (enum_descriptor !=
+ self->pool->FindEnumTypeByName(enum_descriptor->full_name())) {
+ PyErr_Format(PyExc_ValueError,
+ "The enum descriptor %s does not belong to this pool",
+ enum_descriptor->full_name().c_str());
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+// The code below loads new Descriptors from a serialized FileDescriptorProto.
+
+
+// Collects errors that occur during proto file building to allow them to be
+// propagated in the python exception instead of only living in ERROR logs.
+class BuildFileErrorCollector : public DescriptorPool::ErrorCollector {
+ public:
+ BuildFileErrorCollector() : error_message(""), had_errors(false) {}
+
+ void AddError(const string& filename, const string& element_name,
+ const Message* descriptor, ErrorLocation location,
+ const string& message) {
+ // Replicates the logging behavior that happens in the C++ implementation
+ // when an error collector is not passed in.
+ if (!had_errors) {
+ error_message +=
+ ("Invalid proto descriptor for file \"" + filename + "\":\n");
+ had_errors = true;
+ }
+ // As this only happens on failure and will result in the program not
+ // running at all, no effort is made to optimize this string manipulation.
+ error_message += (" " + element_name + ": " + message + "\n");
+ }
+
+ string error_message;
+ bool had_errors;
+};
+
+PyObject* AddSerializedFile(PyDescriptorPool* self, PyObject* serialized_pb) {
+ char* message_type;
+ Py_ssize_t message_len;
+
+ if (self->database != NULL) {
+ PyErr_SetString(
+ PyExc_ValueError,
+ "Cannot call Add on a DescriptorPool that uses a DescriptorDatabase. "
+ "Add your file to the underlying database.");
+ return NULL;
+ }
+
+ if (PyBytes_AsStringAndSize(serialized_pb, &message_type, &message_len) < 0) {
+ return NULL;
+ }
+
+ FileDescriptorProto file_proto;
+ if (!file_proto.ParseFromArray(message_type, message_len)) {
+ PyErr_SetString(PyExc_TypeError, "Couldn't parse file content!");
+ return NULL;
+ }
+
+ // If the file was already part of a C++ library, all its descriptors are in
+ // the underlying pool. No need to do anything else.
+ const FileDescriptor* generated_file = NULL;
+ if (self->underlay) {
+ generated_file = self->underlay->FindFileByName(file_proto.name());
+ }
+ if (generated_file != NULL) {
+ return PyFileDescriptor_FromDescriptorWithSerializedPb(
+ generated_file, serialized_pb);
+ }
+
+ BuildFileErrorCollector error_collector;
+ const FileDescriptor* descriptor =
+ self->pool->BuildFileCollectingErrors(file_proto,
+ &error_collector);
+ if (descriptor == NULL) {
+ PyErr_Format(PyExc_TypeError,
+ "Couldn't build proto file into descriptor pool!\n%s",
+ error_collector.error_message.c_str());
+ return NULL;
+ }
+
+ return PyFileDescriptor_FromDescriptorWithSerializedPb(
+ descriptor, serialized_pb);
+}
+
+PyObject* Add(PyDescriptorPool* self, PyObject* file_descriptor_proto) {
+ ScopedPyObjectPtr serialized_pb(
+ PyObject_CallMethod(file_descriptor_proto, "SerializeToString", NULL));
+ if (serialized_pb == NULL) {
+ return NULL;
+ }
+ return AddSerializedFile(self, serialized_pb.get());
+}
+
+static PyMethodDef Methods[] = {
+ { "Add", (PyCFunction)Add, METH_O,
+ "Adds the FileDescriptorProto and its types to this pool." },
+ { "AddSerializedFile", (PyCFunction)AddSerializedFile, METH_O,
+ "Adds a serialized FileDescriptorProto to this pool." },
+
+ // TODO(amauryfa): Understand why the Python implementation differs from
+ // this one, ask users to use another API and deprecate these functions.
+ { "AddFileDescriptor", (PyCFunction)AddFileDescriptor, METH_O,
+ "No-op. Add() must have been called before." },
+ { "AddDescriptor", (PyCFunction)AddDescriptor, METH_O,
+ "No-op. Add() must have been called before." },
+ { "AddEnumDescriptor", (PyCFunction)AddEnumDescriptor, METH_O,
+ "No-op. Add() must have been called before." },
+
+ { "FindFileByName", (PyCFunction)FindFileByName, METH_O,
+ "Searches for a file descriptor by its .proto name." },
+ { "FindMessageTypeByName", (PyCFunction)FindMessageByName, METH_O,
+ "Searches for a message descriptor by full name." },
+ { "FindFieldByName", (PyCFunction)FindFieldByName, METH_O,
+ "Searches for a field descriptor by full name." },
+ { "FindExtensionByName", (PyCFunction)FindExtensionByName, METH_O,
+ "Searches for extension descriptor by full name." },
+ { "FindEnumTypeByName", (PyCFunction)FindEnumTypeByName, METH_O,
+ "Searches for enum type descriptor by full name." },
+ { "FindOneofByName", (PyCFunction)FindOneofByName, METH_O,
+ "Searches for oneof descriptor by full name." },
+ { "FindServiceByName", (PyCFunction)FindServiceByName, METH_O,
+ "Searches for service descriptor by full name." },
+ { "FindMethodByName", (PyCFunction)FindMethodByName, METH_O,
+ "Searches for method descriptor by full name." },
+
+ { "FindFileContainingSymbol", (PyCFunction)FindFileContainingSymbol, METH_O,
+ "Gets the FileDescriptor containing the specified symbol." },
+ {NULL}
+};
+
+} // namespace cdescriptor_pool
+
+PyTypeObject PyDescriptorPool_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".DescriptorPool", // tp_name
+ sizeof(PyDescriptorPool), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)cdescriptor_pool::Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Descriptor Pool", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ cdescriptor_pool::Methods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ 0, // tp_alloc
+ cdescriptor_pool::New, // tp_new
+ PyObject_Del, // tp_free
+};
+
+// This is the DescriptorPool which contains all the definitions from the
+// generated _pb2.py modules.
+static PyDescriptorPool* python_generated_pool = NULL;
+
+bool InitDescriptorPool() {
+ if (PyType_Ready(&PyDescriptorPool_Type) < 0)
+ return false;
+
+ // The Pool of messages declared in Python libraries.
+ // generated_pool() contains all messages already linked in C++ libraries, and
+ // is used as underlay.
+ python_generated_pool = cdescriptor_pool::PyDescriptorPool_NewWithUnderlay(
+ DescriptorPool::generated_pool());
+ if (python_generated_pool == NULL) {
+ return false;
+ }
+ // Register this pool to be found for C++-generated descriptors.
+ descriptor_pool_map.insert(
+ std::make_pair(DescriptorPool::generated_pool(),
+ python_generated_pool));
+
+ return true;
+}
+
+// The default DescriptorPool used everywhere in this module.
+// Today it's the python_generated_pool.
+// TODO(amauryfa): Remove all usages of this function: the pool should be
+// derived from the context.
+PyDescriptorPool* GetDefaultDescriptorPool() {
+ return python_generated_pool;
+}
+
+PyDescriptorPool* GetDescriptorPool_FromPool(const DescriptorPool* pool) {
+ // Fast path for standard descriptors.
+ if (pool == python_generated_pool->pool ||
+ pool == DescriptorPool::generated_pool()) {
+ return python_generated_pool;
+ }
+ hash_map<const DescriptorPool*, PyDescriptorPool*>::iterator it =
+ descriptor_pool_map.find(pool);
+ if (it == descriptor_pool_map.end()) {
+ PyErr_SetString(PyExc_KeyError, "Unknown descriptor pool");
+ return NULL;
+ }
+ return it->second;
+}
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.h
new file mode 100644
index 0000000000..2a42c11262
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/descriptor_pool.h
@@ -0,0 +1,167 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_POOL_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_POOL_H__
+
+#include <Python.h>
+
+#include <google/protobuf/stubs/hash.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+class MessageFactory;
+
+namespace python {
+
+// The (meta) type of all Messages classes.
+struct CMessageClass;
+
+// Wraps operations to the global DescriptorPool which contains information
+// about all messages and fields.
+//
+// There is normally one pool per process. We make it a Python object only
+// because it contains many Python references.
+// TODO(amauryfa): See whether such objects can appear in reference cycles, and
+// consider adding support for the cyclic GC.
+//
+// "Methods" that interacts with this DescriptorPool are in the cdescriptor_pool
+// namespace.
+typedef struct PyDescriptorPool {
+ PyObject_HEAD
+
+ // The C++ pool containing Descriptors.
+ DescriptorPool* pool;
+
+ // The C++ pool acting as an underlay. Can be NULL.
+ // This pointer is not owned and must stay alive.
+ const DescriptorPool* underlay;
+
+ // The C++ descriptor database used to fetch unknown protos. Can be NULL.
+ // This pointer is owned.
+ const DescriptorDatabase* database;
+
+ // DynamicMessageFactory used to create C++ instances of messages.
+ // This object cache the descriptors that were used, so the DescriptorPool
+ // needs to get rid of it before it can delete itself.
+ //
+ // Note: A C++ MessageFactory is different from the Python MessageFactory.
+ // The C++ one creates messages, when the Python one creates classes.
+ MessageFactory* message_factory;
+
+ // Make our own mapping to retrieve Python classes from C++ descriptors.
+ //
+ // Descriptor pointers stored here are owned by the DescriptorPool above.
+ // Python references to classes are owned by this PyDescriptorPool.
+ typedef hash_map<const Descriptor*, CMessageClass*> ClassesByMessageMap;
+ ClassesByMessageMap* classes_by_descriptor;
+
+ // Cache the options for any kind of descriptor.
+ // Descriptor pointers are owned by the DescriptorPool above.
+ // Python objects are owned by the map.
+ hash_map<const void*, PyObject*>* descriptor_options;
+} PyDescriptorPool;
+
+
+extern PyTypeObject PyDescriptorPool_Type;
+
+namespace cdescriptor_pool {
+
+// Looks up a message by name.
+// Returns a message Descriptor, or NULL if not found.
+const Descriptor* FindMessageTypeByName(PyDescriptorPool* self,
+ const string& name);
+
+// Registers a new Python class for the given message descriptor.
+// On error, returns -1 with a Python exception set.
+int RegisterMessageClass(PyDescriptorPool* self,
+ const Descriptor* message_descriptor,
+ CMessageClass* message_class);
+
+// Retrieves the Python class registered with the given message descriptor.
+//
+// Returns a *borrowed* reference if found, otherwise returns NULL with an
+// exception set.
+CMessageClass* GetMessageClass(PyDescriptorPool* self,
+ const Descriptor* message_descriptor);
+
+// The functions below are also exposed as methods of the DescriptorPool type.
+
+// Looks up a message by name. Returns a PyMessageDescriptor corresponding to
+// the field on success, or NULL on failure.
+//
+// Returns a new reference.
+PyObject* FindMessageByName(PyDescriptorPool* self, PyObject* name);
+
+// Looks up a field by name. Returns a PyFieldDescriptor corresponding to
+// the field on success, or NULL on failure.
+//
+// Returns a new reference.
+PyObject* FindFieldByName(PyDescriptorPool* self, PyObject* name);
+
+// Looks up an extension by name. Returns a PyFieldDescriptor corresponding
+// to the field on success, or NULL on failure.
+//
+// Returns a new reference.
+PyObject* FindExtensionByName(PyDescriptorPool* self, PyObject* arg);
+
+// Looks up an enum type by name. Returns a PyEnumDescriptor corresponding
+// to the field on success, or NULL on failure.
+//
+// Returns a new reference.
+PyObject* FindEnumTypeByName(PyDescriptorPool* self, PyObject* arg);
+
+// Looks up a oneof by name. Returns a COneofDescriptor corresponding
+// to the oneof on success, or NULL on failure.
+//
+// Returns a new reference.
+PyObject* FindOneofByName(PyDescriptorPool* self, PyObject* arg);
+
+} // namespace cdescriptor_pool
+
+// Retrieve the global descriptor pool owned by the _message module.
+// This is the one used by pb2.py generated modules.
+// Returns a *borrowed* reference.
+// "Default" pool used to register messages from _pb2.py modules.
+PyDescriptorPool* GetDefaultDescriptorPool();
+
+// Retrieve the python descriptor pool owning a C++ descriptor pool.
+// Returns a *borrowed* reference.
+PyDescriptorPool* GetDescriptorPool_FromPool(const DescriptorPool* pool);
+
+// Initialize objects used by this module.
+bool InitDescriptorPool();
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_POOL_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.cc
new file mode 100644
index 0000000000..21bbb8c2b1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.cc
@@ -0,0 +1,337 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#include <google/protobuf/pyext/extension_dict.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/pyext/descriptor.h>
+#include <google/protobuf/pyext/descriptor_pool.h>
+#include <google/protobuf/pyext/message.h>
+#include <google/protobuf/pyext/repeated_composite_container.h>
+#include <google/protobuf/pyext/repeated_scalar_container.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+#include <google/protobuf/stubs/shared_ptr.h>
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+namespace extension_dict {
+
+PyObject* len(ExtensionDict* self) {
+#if PY_MAJOR_VERSION >= 3
+ return PyLong_FromLong(PyDict_Size(self->values));
+#else
+ return PyInt_FromLong(PyDict_Size(self->values));
+#endif
+}
+
+// TODO(tibell): Use VisitCompositeField.
+int ReleaseExtension(ExtensionDict* self,
+ PyObject* extension,
+ const FieldDescriptor* descriptor) {
+ if (descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (repeated_composite_container::Release(
+ reinterpret_cast<RepeatedCompositeContainer*>(
+ extension)) < 0) {
+ return -1;
+ }
+ } else {
+ if (repeated_scalar_container::Release(
+ reinterpret_cast<RepeatedScalarContainer*>(
+ extension)) < 0) {
+ return -1;
+ }
+ }
+ } else if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (cmessage::ReleaseSubMessage(
+ self->parent, descriptor,
+ reinterpret_cast<CMessage*>(extension)) < 0) {
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+PyObject* subscript(ExtensionDict* self, PyObject* key) {
+ const FieldDescriptor* descriptor = cmessage::GetExtensionDescriptor(key);
+ if (descriptor == NULL) {
+ return NULL;
+ }
+ if (!CheckFieldBelongsToMessage(descriptor, self->message)) {
+ return NULL;
+ }
+
+ if (descriptor->label() != FieldDescriptor::LABEL_REPEATED &&
+ descriptor->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ return cmessage::InternalGetScalar(self->message, descriptor);
+ }
+
+ PyObject* value = PyDict_GetItem(self->values, key);
+ if (value != NULL) {
+ Py_INCREF(value);
+ return value;
+ }
+
+ if (self->parent == NULL) {
+ // We are in "detached" state. Don't allow further modifications.
+ // TODO(amauryfa): Support adding non-scalars to a detached extension dict.
+ // This probably requires to store the type of the main message.
+ PyErr_SetObject(PyExc_KeyError, key);
+ return NULL;
+ }
+
+ if (descriptor->label() != FieldDescriptor::LABEL_REPEATED &&
+ descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ PyObject* sub_message = cmessage::InternalGetSubMessage(
+ self->parent, descriptor);
+ if (sub_message == NULL) {
+ return NULL;
+ }
+ PyDict_SetItem(self->values, key, sub_message);
+ return sub_message;
+ }
+
+ if (descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ CMessageClass* message_class = cdescriptor_pool::GetMessageClass(
+ cmessage::GetDescriptorPoolForMessage(self->parent),
+ descriptor->message_type());
+ if (message_class == NULL) {
+ return NULL;
+ }
+ PyObject* py_container = repeated_composite_container::NewContainer(
+ self->parent, descriptor, message_class);
+ if (py_container == NULL) {
+ return NULL;
+ }
+ PyDict_SetItem(self->values, key, py_container);
+ return py_container;
+ } else {
+ PyObject* py_container = repeated_scalar_container::NewContainer(
+ self->parent, descriptor);
+ if (py_container == NULL) {
+ return NULL;
+ }
+ PyDict_SetItem(self->values, key, py_container);
+ return py_container;
+ }
+ }
+ PyErr_SetString(PyExc_ValueError, "control reached unexpected line");
+ return NULL;
+}
+
+int ass_subscript(ExtensionDict* self, PyObject* key, PyObject* value) {
+ const FieldDescriptor* descriptor = cmessage::GetExtensionDescriptor(key);
+ if (descriptor == NULL) {
+ return -1;
+ }
+ if (!CheckFieldBelongsToMessage(descriptor, self->message)) {
+ return -1;
+ }
+
+ if (descriptor->label() != FieldDescriptor::LABEL_OPTIONAL ||
+ descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ PyErr_SetString(PyExc_TypeError, "Extension is repeated and/or composite "
+ "type");
+ return -1;
+ }
+ if (self->parent) {
+ cmessage::AssureWritable(self->parent);
+ if (cmessage::InternalSetScalar(self->parent, descriptor, value) < 0) {
+ return -1;
+ }
+ }
+ // TODO(tibell): We shouldn't write scalars to the cache.
+ PyDict_SetItem(self->values, key, value);
+ return 0;
+}
+
+PyObject* ClearExtension(ExtensionDict* self, PyObject* extension) {
+ const FieldDescriptor* descriptor =
+ cmessage::GetExtensionDescriptor(extension);
+ if (descriptor == NULL) {
+ return NULL;
+ }
+ PyObject* value = PyDict_GetItem(self->values, extension);
+ if (self->parent) {
+ if (value != NULL) {
+ if (ReleaseExtension(self, value, descriptor) < 0) {
+ return NULL;
+ }
+ }
+ if (ScopedPyObjectPtr(cmessage::ClearFieldByDescriptor(
+ self->parent, descriptor)) == NULL) {
+ return NULL;
+ }
+ }
+ if (PyDict_DelItem(self->values, extension) < 0) {
+ PyErr_Clear();
+ }
+ Py_RETURN_NONE;
+}
+
+PyObject* HasExtension(ExtensionDict* self, PyObject* extension) {
+ const FieldDescriptor* descriptor =
+ cmessage::GetExtensionDescriptor(extension);
+ if (descriptor == NULL) {
+ return NULL;
+ }
+ if (self->parent) {
+ return cmessage::HasFieldByDescriptor(self->parent, descriptor);
+ } else {
+ int exists = PyDict_Contains(self->values, extension);
+ if (exists < 0) {
+ return NULL;
+ }
+ return PyBool_FromLong(exists);
+ }
+}
+
+PyObject* _FindExtensionByName(ExtensionDict* self, PyObject* name) {
+ ScopedPyObjectPtr extensions_by_name(PyObject_GetAttrString(
+ reinterpret_cast<PyObject*>(self->parent), "_extensions_by_name"));
+ if (extensions_by_name == NULL) {
+ return NULL;
+ }
+ PyObject* result = PyDict_GetItem(extensions_by_name.get(), name);
+ if (result == NULL) {
+ Py_RETURN_NONE;
+ } else {
+ Py_INCREF(result);
+ return result;
+ }
+}
+
+PyObject* _FindExtensionByNumber(ExtensionDict* self, PyObject* number) {
+ ScopedPyObjectPtr extensions_by_number(PyObject_GetAttrString(
+ reinterpret_cast<PyObject*>(self->parent), "_extensions_by_number"));
+ if (extensions_by_number == NULL) {
+ return NULL;
+ }
+ PyObject* result = PyDict_GetItem(extensions_by_number.get(), number);
+ if (result == NULL) {
+ Py_RETURN_NONE;
+ } else {
+ Py_INCREF(result);
+ return result;
+ }
+}
+
+ExtensionDict* NewExtensionDict(CMessage *parent) {
+ ExtensionDict* self = reinterpret_cast<ExtensionDict*>(
+ PyType_GenericAlloc(&ExtensionDict_Type, 0));
+ if (self == NULL) {
+ return NULL;
+ }
+
+ self->parent = parent; // Store a borrowed reference.
+ self->message = parent->message;
+ self->owner = parent->owner;
+ self->values = PyDict_New();
+ return self;
+}
+
+void dealloc(ExtensionDict* self) {
+ Py_CLEAR(self->values);
+ self->owner.reset();
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+static PyMappingMethods MpMethods = {
+ (lenfunc)len, /* mp_length */
+ (binaryfunc)subscript, /* mp_subscript */
+ (objobjargproc)ass_subscript,/* mp_ass_subscript */
+};
+
+#define EDMETHOD(name, args, doc) { #name, (PyCFunction)name, args, doc }
+static PyMethodDef Methods[] = {
+ EDMETHOD(ClearExtension, METH_O, "Clears an extension from the object."),
+ EDMETHOD(HasExtension, METH_O, "Checks if the object has an extension."),
+ EDMETHOD(_FindExtensionByName, METH_O,
+ "Finds an extension by name."),
+ EDMETHOD(_FindExtensionByNumber, METH_O,
+ "Finds an extension by field number."),
+ { NULL, NULL }
+};
+
+} // namespace extension_dict
+
+PyTypeObject ExtensionDict_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".ExtensionDict", // tp_name
+ sizeof(ExtensionDict), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)extension_dict::dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ &extension_dict::MpMethods, // tp_as_mapping
+ PyObject_HashNotImplemented, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "An extension dict", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ extension_dict::Methods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+};
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.h
new file mode 100644
index 0000000000..2456eda1e6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/extension_dict.h
@@ -0,0 +1,137 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_EXTENSION_DICT_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_EXTENSION_DICT_H__
+
+#include <Python.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+namespace google {
+namespace protobuf {
+
+class Message;
+class FieldDescriptor;
+
+#ifdef _SHARED_PTR_H
+using std::shared_ptr;
+#else
+using internal::shared_ptr;
+#endif
+
+namespace python {
+
+struct CMessage;
+
+typedef struct ExtensionDict {
+ PyObject_HEAD;
+
+ // This is the top-level C++ Message object that owns the whole
+ // proto tree. Every Python container class holds a
+ // reference to it in order to keep it alive as long as there's a
+ // Python object that references any part of the tree.
+ shared_ptr<Message> owner;
+
+ // Weak reference to parent message. Used to make sure
+ // the parent is writable when an extension field is modified.
+ CMessage* parent;
+
+ // Pointer to the C++ Message that this ExtensionDict extends.
+ // Not owned by us.
+ Message* message;
+
+ // A dict of child messages, indexed by Extension descriptors.
+ // Similar to CMessage::composite_fields.
+ PyObject* values;
+} ExtensionDict;
+
+extern PyTypeObject ExtensionDict_Type;
+
+namespace extension_dict {
+
+// Builds an Extensions dict for a specific message.
+ExtensionDict* NewExtensionDict(CMessage *parent);
+
+// Gets the number of extension values in this ExtensionDict as a python object.
+//
+// Returns a new reference.
+PyObject* len(ExtensionDict* self);
+
+// Releases extensions referenced outside this dictionary to keep outside
+// references alive.
+//
+// Returns 0 on success, -1 on failure.
+int ReleaseExtension(ExtensionDict* self,
+ PyObject* extension,
+ const FieldDescriptor* descriptor);
+
+// Gets an extension from the dict for the given extension descriptor.
+//
+// Returns a new reference.
+PyObject* subscript(ExtensionDict* self, PyObject* key);
+
+// Assigns a value to an extension in the dict. Can only be used for singular
+// simple types.
+//
+// Returns 0 on success, -1 on failure.
+int ass_subscript(ExtensionDict* self, PyObject* key, PyObject* value);
+
+// Clears an extension from the dict. Will release the extension if there
+// is still an external reference left to it.
+//
+// Returns None on success.
+PyObject* ClearExtension(ExtensionDict* self,
+ PyObject* extension);
+
+// Gets an extension from the dict given the extension name as opposed to
+// descriptor.
+//
+// Returns a new reference.
+PyObject* _FindExtensionByName(ExtensionDict* self, PyObject* name);
+
+// Gets an extension from the dict given the extension field number as
+// opposed to descriptor.
+//
+// Returns a new reference.
+PyObject* _FindExtensionByNumber(ExtensionDict* self, PyObject* number);
+
+} // namespace extension_dict
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_EXTENSION_DICT_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.cc
new file mode 100644
index 0000000000..0987b89832
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.cc
@@ -0,0 +1,970 @@
+// 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: haberman@google.com (Josh Haberman)
+
+#include <google/protobuf/pyext/map_container.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/map_field.h>
+#include <google/protobuf/map.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/pyext/message.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+
+#if PY_MAJOR_VERSION >= 3
+ #define PyInt_FromLong PyLong_FromLong
+ #define PyInt_FromSize_t PyLong_FromSize_t
+#endif
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+// Functions that need access to map reflection functionality.
+// They need to be contained in this class because it is friended.
+class MapReflectionFriend {
+ public:
+ // Methods that are in common between the map types.
+ static PyObject* Contains(PyObject* _self, PyObject* key);
+ static Py_ssize_t Length(PyObject* _self);
+ static PyObject* GetIterator(PyObject *_self);
+ static PyObject* IterNext(PyObject* _self);
+
+ // Methods that differ between the map types.
+ static PyObject* ScalarMapGetItem(PyObject* _self, PyObject* key);
+ static PyObject* MessageMapGetItem(PyObject* _self, PyObject* key);
+ static int ScalarMapSetItem(PyObject* _self, PyObject* key, PyObject* v);
+ static int MessageMapSetItem(PyObject* _self, PyObject* key, PyObject* v);
+};
+
+struct MapIterator {
+ PyObject_HEAD;
+
+ google::protobuf::scoped_ptr< ::google::protobuf::MapIterator> iter;
+
+ // A pointer back to the container, so we can notice changes to the version.
+ // We own a ref on this.
+ MapContainer* container;
+
+ // We need to keep a ref on the Message* too, because
+ // MapIterator::~MapIterator() accesses it. Normally this would be ok because
+ // the ref on container (above) would guarantee outlive semantics. However in
+ // the case of ClearField(), InitializeAndCopyToParentContainer() resets the
+ // message pointer (and the owner) to a different message, a copy of the
+ // original. But our iterator still points to the original, which could now
+ // get deleted before us.
+ //
+ // To prevent this, we ensure that the Message will always stay alive as long
+ // as this iterator does. This is solely for the benefit of the MapIterator
+ // destructor -- we should never actually access the iterator in this state
+ // except to delete it.
+ shared_ptr<Message> owner;
+
+ // The version of the map when we took the iterator to it.
+ //
+ // We store this so that if the map is modified during iteration we can throw
+ // an error.
+ uint64 version;
+
+ // True if the container is empty. We signal this separately to avoid calling
+ // any of the iteration methods, which are non-const.
+ bool empty;
+};
+
+Message* MapContainer::GetMutableMessage() {
+ cmessage::AssureWritable(parent);
+ return const_cast<Message*>(message);
+}
+
+// Consumes a reference on the Python string object.
+static bool PyStringToSTL(PyObject* py_string, string* stl_string) {
+ char *value;
+ Py_ssize_t value_len;
+
+ if (!py_string) {
+ return false;
+ }
+ if (PyBytes_AsStringAndSize(py_string, &value, &value_len) < 0) {
+ Py_DECREF(py_string);
+ return false;
+ } else {
+ stl_string->assign(value, value_len);
+ Py_DECREF(py_string);
+ return true;
+ }
+}
+
+static bool PythonToMapKey(PyObject* obj,
+ const FieldDescriptor* field_descriptor,
+ MapKey* key) {
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ GOOGLE_CHECK_GET_INT32(obj, value, false);
+ key->SetInt32Value(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ GOOGLE_CHECK_GET_INT64(obj, value, false);
+ key->SetInt64Value(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ GOOGLE_CHECK_GET_UINT32(obj, value, false);
+ key->SetUInt32Value(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ GOOGLE_CHECK_GET_UINT64(obj, value, false);
+ key->SetUInt64Value(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ GOOGLE_CHECK_GET_BOOL(obj, value, false);
+ key->SetBoolValue(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string str;
+ if (!PyStringToSTL(CheckString(obj, field_descriptor), &str)) {
+ return false;
+ }
+ key->SetStringValue(str);
+ break;
+ }
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Type %d cannot be a map key",
+ field_descriptor->cpp_type());
+ return false;
+ }
+ return true;
+}
+
+static PyObject* MapKeyToPython(const FieldDescriptor* field_descriptor,
+ const MapKey& key) {
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return PyInt_FromLong(key.GetInt32Value());
+ case FieldDescriptor::CPPTYPE_INT64:
+ return PyLong_FromLongLong(key.GetInt64Value());
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return PyInt_FromSize_t(key.GetUInt32Value());
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return PyLong_FromUnsignedLongLong(key.GetUInt64Value());
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return PyBool_FromLong(key.GetBoolValue());
+ case FieldDescriptor::CPPTYPE_STRING:
+ return ToStringObject(field_descriptor, key.GetStringValue());
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Couldn't convert type %d to value",
+ field_descriptor->cpp_type());
+ return NULL;
+ }
+}
+
+// This is only used for ScalarMap, so we don't need to handle the
+// CPPTYPE_MESSAGE case.
+PyObject* MapValueRefToPython(const FieldDescriptor* field_descriptor,
+ MapValueRef* value) {
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return PyInt_FromLong(value->GetInt32Value());
+ case FieldDescriptor::CPPTYPE_INT64:
+ return PyLong_FromLongLong(value->GetInt64Value());
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return PyInt_FromSize_t(value->GetUInt32Value());
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return PyLong_FromUnsignedLongLong(value->GetUInt64Value());
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return PyFloat_FromDouble(value->GetFloatValue());
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return PyFloat_FromDouble(value->GetDoubleValue());
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return PyBool_FromLong(value->GetBoolValue());
+ case FieldDescriptor::CPPTYPE_STRING:
+ return ToStringObject(field_descriptor, value->GetStringValue());
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return PyInt_FromLong(value->GetEnumValue());
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Couldn't convert type %d to value",
+ field_descriptor->cpp_type());
+ return NULL;
+ }
+}
+
+// This is only used for ScalarMap, so we don't need to handle the
+// CPPTYPE_MESSAGE case.
+static bool PythonToMapValueRef(PyObject* obj,
+ const FieldDescriptor* field_descriptor,
+ bool allow_unknown_enum_values,
+ MapValueRef* value_ref) {
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ GOOGLE_CHECK_GET_INT32(obj, value, false);
+ value_ref->SetInt32Value(value);
+ return true;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ GOOGLE_CHECK_GET_INT64(obj, value, false);
+ value_ref->SetInt64Value(value);
+ return true;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ GOOGLE_CHECK_GET_UINT32(obj, value, false);
+ value_ref->SetUInt32Value(value);
+ return true;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ GOOGLE_CHECK_GET_UINT64(obj, value, false);
+ value_ref->SetUInt64Value(value);
+ return true;
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ GOOGLE_CHECK_GET_FLOAT(obj, value, false);
+ value_ref->SetFloatValue(value);
+ return true;
+ }
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ GOOGLE_CHECK_GET_DOUBLE(obj, value, false);
+ value_ref->SetDoubleValue(value);
+ return true;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ GOOGLE_CHECK_GET_BOOL(obj, value, false);
+ value_ref->SetBoolValue(value);
+ return true;;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string str;
+ if (!PyStringToSTL(CheckString(obj, field_descriptor), &str)) {
+ return false;
+ }
+ value_ref->SetStringValue(str);
+ return true;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ GOOGLE_CHECK_GET_INT32(obj, value, false);
+ if (allow_unknown_enum_values) {
+ value_ref->SetEnumValue(value);
+ return true;
+ } else {
+ const EnumDescriptor* enum_descriptor = field_descriptor->enum_type();
+ const EnumValueDescriptor* enum_value =
+ enum_descriptor->FindValueByNumber(value);
+ if (enum_value != NULL) {
+ value_ref->SetEnumValue(value);
+ return true;
+ } else {
+ PyErr_Format(PyExc_ValueError, "Unknown enum value: %d", value);
+ return false;
+ }
+ }
+ break;
+ }
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Setting value to a field of unknown type %d",
+ field_descriptor->cpp_type());
+ return false;
+ }
+}
+
+// Map methods common to ScalarMap and MessageMap //////////////////////////////
+
+static MapContainer* GetMap(PyObject* obj) {
+ return reinterpret_cast<MapContainer*>(obj);
+}
+
+Py_ssize_t MapReflectionFriend::Length(PyObject* _self) {
+ MapContainer* self = GetMap(_self);
+ const google::protobuf::Message* message = self->message;
+ return message->GetReflection()->MapSize(*message,
+ self->parent_field_descriptor);
+}
+
+PyObject* Clear(PyObject* _self) {
+ MapContainer* self = GetMap(_self);
+ Message* message = self->GetMutableMessage();
+ const Reflection* reflection = message->GetReflection();
+
+ reflection->ClearField(message, self->parent_field_descriptor);
+
+ Py_RETURN_NONE;
+}
+
+PyObject* MapReflectionFriend::Contains(PyObject* _self, PyObject* key) {
+ MapContainer* self = GetMap(_self);
+
+ const Message* message = self->message;
+ const Reflection* reflection = message->GetReflection();
+ MapKey map_key;
+
+ if (!PythonToMapKey(key, self->key_field_descriptor, &map_key)) {
+ return NULL;
+ }
+
+ if (reflection->ContainsMapKey(*message, self->parent_field_descriptor,
+ map_key)) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+
+// Initializes the underlying Message object of "to" so it becomes a new parent
+// map container, and copies all the values from "from" to it. A child map
+// container can be released by passing it as both from and to (e.g. making it
+// the recipient of the new parent message and copying the values from itself).
+// In fact, this is the only supported use at the moment.
+static int InitializeAndCopyToParentContainer(MapContainer* from,
+ MapContainer* to) {
+ // For now we require from == to, re-evaluate if we want to support deep copy
+ // as in repeated_scalar_container.cc.
+ GOOGLE_DCHECK(from == to);
+ Message* new_message = from->message->New();
+
+ if (MapReflectionFriend::Length(reinterpret_cast<PyObject*>(from)) > 0) {
+ // A somewhat roundabout way of copying just one field from old_message to
+ // new_message. This is the best we can do with what Reflection gives us.
+ Message* mutable_old = from->GetMutableMessage();
+ vector<const FieldDescriptor*> fields;
+ fields.push_back(from->parent_field_descriptor);
+
+ // Move the map field into the new message.
+ mutable_old->GetReflection()->SwapFields(mutable_old, new_message, fields);
+
+ // If/when we support from != to, this will be required also to copy the
+ // map field back into the existing message:
+ // mutable_old->MergeFrom(*new_message);
+ }
+
+ // If from == to this could delete old_message.
+ to->owner.reset(new_message);
+
+ to->parent = NULL;
+ to->parent_field_descriptor = from->parent_field_descriptor;
+ to->message = new_message;
+
+ // Invalidate iterators, since they point to the old copy of the field.
+ to->version++;
+
+ return 0;
+}
+
+int MapContainer::Release() {
+ return InitializeAndCopyToParentContainer(this, this);
+}
+
+
+// ScalarMap ///////////////////////////////////////////////////////////////////
+
+PyObject *NewScalarMapContainer(
+ CMessage* parent, const google::protobuf::FieldDescriptor* parent_field_descriptor) {
+ if (!CheckFieldBelongsToMessage(parent_field_descriptor, parent->message)) {
+ return NULL;
+ }
+
+#if PY_MAJOR_VERSION >= 3
+ ScopedPyObjectPtr obj(PyType_GenericAlloc(
+ reinterpret_cast<PyTypeObject *>(ScalarMapContainer_Type), 0));
+#else
+ ScopedPyObjectPtr obj(PyType_GenericAlloc(&ScalarMapContainer_Type, 0));
+#endif
+ if (obj.get() == NULL) {
+ return PyErr_Format(PyExc_RuntimeError,
+ "Could not allocate new container.");
+ }
+
+ MapContainer* self = GetMap(obj.get());
+
+ self->message = parent->message;
+ self->parent = parent;
+ self->parent_field_descriptor = parent_field_descriptor;
+ self->owner = parent->owner;
+ self->version = 0;
+
+ self->key_field_descriptor =
+ parent_field_descriptor->message_type()->FindFieldByName("key");
+ self->value_field_descriptor =
+ parent_field_descriptor->message_type()->FindFieldByName("value");
+
+ if (self->key_field_descriptor == NULL ||
+ self->value_field_descriptor == NULL) {
+ return PyErr_Format(PyExc_KeyError,
+ "Map entry descriptor did not have key/value fields");
+ }
+
+ return obj.release();
+}
+
+PyObject* MapReflectionFriend::ScalarMapGetItem(PyObject* _self,
+ PyObject* key) {
+ MapContainer* self = GetMap(_self);
+
+ Message* message = self->GetMutableMessage();
+ const Reflection* reflection = message->GetReflection();
+ MapKey map_key;
+ MapValueRef value;
+
+ if (!PythonToMapKey(key, self->key_field_descriptor, &map_key)) {
+ return NULL;
+ }
+
+ if (reflection->InsertOrLookupMapValue(message, self->parent_field_descriptor,
+ map_key, &value)) {
+ self->version++;
+ }
+
+ return MapValueRefToPython(self->value_field_descriptor, &value);
+}
+
+int MapReflectionFriend::ScalarMapSetItem(PyObject* _self, PyObject* key,
+ PyObject* v) {
+ MapContainer* self = GetMap(_self);
+
+ Message* message = self->GetMutableMessage();
+ const Reflection* reflection = message->GetReflection();
+ MapKey map_key;
+ MapValueRef value;
+
+ if (!PythonToMapKey(key, self->key_field_descriptor, &map_key)) {
+ return -1;
+ }
+
+ self->version++;
+
+ if (v) {
+ // Set item to v.
+ reflection->InsertOrLookupMapValue(message, self->parent_field_descriptor,
+ map_key, &value);
+
+ return PythonToMapValueRef(v, self->value_field_descriptor,
+ reflection->SupportsUnknownEnumValues(), &value)
+ ? 0
+ : -1;
+ } else {
+ // Delete key from map.
+ if (reflection->DeleteMapValue(message, self->parent_field_descriptor,
+ map_key)) {
+ return 0;
+ } else {
+ PyErr_Format(PyExc_KeyError, "Key not present in map");
+ return -1;
+ }
+ }
+}
+
+static PyObject* ScalarMapGet(PyObject* self, PyObject* args) {
+ PyObject* key;
+ PyObject* default_value = NULL;
+ if (PyArg_ParseTuple(args, "O|O", &key, &default_value) < 0) {
+ return NULL;
+ }
+
+ ScopedPyObjectPtr is_present(MapReflectionFriend::Contains(self, key));
+ if (is_present.get() == NULL) {
+ return NULL;
+ }
+
+ if (PyObject_IsTrue(is_present.get())) {
+ return MapReflectionFriend::ScalarMapGetItem(self, key);
+ } else {
+ if (default_value != NULL) {
+ Py_INCREF(default_value);
+ return default_value;
+ } else {
+ Py_RETURN_NONE;
+ }
+ }
+}
+
+static void ScalarMapDealloc(PyObject* _self) {
+ MapContainer* self = GetMap(_self);
+ self->owner.reset();
+ Py_TYPE(_self)->tp_free(_self);
+}
+
+static PyMethodDef ScalarMapMethods[] = {
+ { "__contains__", MapReflectionFriend::Contains, METH_O,
+ "Tests whether a key is a member of the map." },
+ { "clear", (PyCFunction)Clear, METH_NOARGS,
+ "Removes all elements from the map." },
+ { "get", ScalarMapGet, METH_VARARGS,
+ "Gets the value for the given key if present, or otherwise a default" },
+ /*
+ { "__deepcopy__", (PyCFunction)DeepCopy, METH_VARARGS,
+ "Makes a deep copy of the class." },
+ { "__reduce__", (PyCFunction)Reduce, METH_NOARGS,
+ "Outputs picklable representation of the repeated field." },
+ */
+ {NULL, NULL},
+};
+
+#if PY_MAJOR_VERSION >= 3
+ static PyType_Slot ScalarMapContainer_Type_slots[] = {
+ {Py_tp_dealloc, (void *)ScalarMapDealloc},
+ {Py_mp_length, (void *)MapReflectionFriend::Length},
+ {Py_mp_subscript, (void *)MapReflectionFriend::ScalarMapGetItem},
+ {Py_mp_ass_subscript, (void *)MapReflectionFriend::ScalarMapSetItem},
+ {Py_tp_methods, (void *)ScalarMapMethods},
+ {Py_tp_iter, (void *)MapReflectionFriend::GetIterator},
+ {0, 0},
+ };
+
+ PyType_Spec ScalarMapContainer_Type_spec = {
+ FULL_MODULE_NAME ".ScalarMapContainer",
+ sizeof(MapContainer),
+ 0,
+ Py_TPFLAGS_DEFAULT,
+ ScalarMapContainer_Type_slots
+ };
+ PyObject *ScalarMapContainer_Type;
+#else
+ static PyMappingMethods ScalarMapMappingMethods = {
+ MapReflectionFriend::Length, // mp_length
+ MapReflectionFriend::ScalarMapGetItem, // mp_subscript
+ MapReflectionFriend::ScalarMapSetItem, // mp_ass_subscript
+ };
+
+ PyTypeObject ScalarMapContainer_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".ScalarMapContainer", // tp_name
+ sizeof(MapContainer), // tp_basicsize
+ 0, // tp_itemsize
+ ScalarMapDealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ &ScalarMapMappingMethods, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A scalar map container", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ MapReflectionFriend::GetIterator, // tp_iter
+ 0, // tp_iternext
+ ScalarMapMethods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ };
+#endif
+
+
+// MessageMap //////////////////////////////////////////////////////////////////
+
+static MessageMapContainer* GetMessageMap(PyObject* obj) {
+ return reinterpret_cast<MessageMapContainer*>(obj);
+}
+
+static PyObject* GetCMessage(MessageMapContainer* self, Message* message) {
+ // Get or create the CMessage object corresponding to this message.
+ ScopedPyObjectPtr key(PyLong_FromVoidPtr(message));
+ PyObject* ret = PyDict_GetItem(self->message_dict, key.get());
+
+ if (ret == NULL) {
+ CMessage* cmsg = cmessage::NewEmptyMessage(self->message_class);
+ ret = reinterpret_cast<PyObject*>(cmsg);
+
+ if (cmsg == NULL) {
+ return NULL;
+ }
+ cmsg->owner = self->owner;
+ cmsg->message = message;
+ cmsg->parent = self->parent;
+
+ if (PyDict_SetItem(self->message_dict, key.get(), ret) < 0) {
+ Py_DECREF(ret);
+ return NULL;
+ }
+ } else {
+ Py_INCREF(ret);
+ }
+
+ return ret;
+}
+
+PyObject* NewMessageMapContainer(
+ CMessage* parent, const google::protobuf::FieldDescriptor* parent_field_descriptor,
+ CMessageClass* message_class) {
+ if (!CheckFieldBelongsToMessage(parent_field_descriptor, parent->message)) {
+ return NULL;
+ }
+
+#if PY_MAJOR_VERSION >= 3
+ PyObject* obj = PyType_GenericAlloc(
+ reinterpret_cast<PyTypeObject *>(MessageMapContainer_Type), 0);
+#else
+ PyObject* obj = PyType_GenericAlloc(&MessageMapContainer_Type, 0);
+#endif
+ if (obj == NULL) {
+ return PyErr_Format(PyExc_RuntimeError,
+ "Could not allocate new container.");
+ }
+
+ MessageMapContainer* self = GetMessageMap(obj);
+
+ self->message = parent->message;
+ self->parent = parent;
+ self->parent_field_descriptor = parent_field_descriptor;
+ self->owner = parent->owner;
+ self->version = 0;
+
+ self->key_field_descriptor =
+ parent_field_descriptor->message_type()->FindFieldByName("key");
+ self->value_field_descriptor =
+ parent_field_descriptor->message_type()->FindFieldByName("value");
+
+ self->message_dict = PyDict_New();
+ if (self->message_dict == NULL) {
+ return PyErr_Format(PyExc_RuntimeError,
+ "Could not allocate message dict.");
+ }
+
+ Py_INCREF(message_class);
+ self->message_class = message_class;
+
+ if (self->key_field_descriptor == NULL ||
+ self->value_field_descriptor == NULL) {
+ Py_DECREF(obj);
+ return PyErr_Format(PyExc_KeyError,
+ "Map entry descriptor did not have key/value fields");
+ }
+
+ return obj;
+}
+
+int MapReflectionFriend::MessageMapSetItem(PyObject* _self, PyObject* key,
+ PyObject* v) {
+ if (v) {
+ PyErr_Format(PyExc_ValueError,
+ "Direct assignment of submessage not allowed");
+ return -1;
+ }
+
+ // Now we know that this is a delete, not a set.
+
+ MessageMapContainer* self = GetMessageMap(_self);
+ Message* message = self->GetMutableMessage();
+ const Reflection* reflection = message->GetReflection();
+ MapKey map_key;
+ MapValueRef value;
+
+ self->version++;
+
+ if (!PythonToMapKey(key, self->key_field_descriptor, &map_key)) {
+ return -1;
+ }
+
+ // Delete key from map.
+ if (reflection->DeleteMapValue(message, self->parent_field_descriptor,
+ map_key)) {
+ return 0;
+ } else {
+ PyErr_Format(PyExc_KeyError, "Key not present in map");
+ return -1;
+ }
+}
+
+PyObject* MapReflectionFriend::MessageMapGetItem(PyObject* _self,
+ PyObject* key) {
+ MessageMapContainer* self = GetMessageMap(_self);
+
+ Message* message = self->GetMutableMessage();
+ const Reflection* reflection = message->GetReflection();
+ MapKey map_key;
+ MapValueRef value;
+
+ if (!PythonToMapKey(key, self->key_field_descriptor, &map_key)) {
+ return NULL;
+ }
+
+ if (reflection->InsertOrLookupMapValue(message, self->parent_field_descriptor,
+ map_key, &value)) {
+ self->version++;
+ }
+
+ return GetCMessage(self, value.MutableMessageValue());
+}
+
+PyObject* MessageMapGet(PyObject* self, PyObject* args) {
+ PyObject* key;
+ PyObject* default_value = NULL;
+ if (PyArg_ParseTuple(args, "O|O", &key, &default_value) < 0) {
+ return NULL;
+ }
+
+ ScopedPyObjectPtr is_present(MapReflectionFriend::Contains(self, key));
+ if (is_present.get() == NULL) {
+ return NULL;
+ }
+
+ if (PyObject_IsTrue(is_present.get())) {
+ return MapReflectionFriend::MessageMapGetItem(self, key);
+ } else {
+ if (default_value != NULL) {
+ Py_INCREF(default_value);
+ return default_value;
+ } else {
+ Py_RETURN_NONE;
+ }
+ }
+}
+
+static void MessageMapDealloc(PyObject* _self) {
+ MessageMapContainer* self = GetMessageMap(_self);
+ self->owner.reset();
+ Py_DECREF(self->message_dict);
+ Py_DECREF(self->message_class);
+ Py_TYPE(_self)->tp_free(_self);
+}
+
+static PyMethodDef MessageMapMethods[] = {
+ { "__contains__", (PyCFunction)MapReflectionFriend::Contains, METH_O,
+ "Tests whether the map contains this element."},
+ { "clear", (PyCFunction)Clear, METH_NOARGS,
+ "Removes all elements from the map."},
+ { "get", MessageMapGet, METH_VARARGS,
+ "Gets the value for the given key if present, or otherwise a default" },
+ { "get_or_create", MapReflectionFriend::MessageMapGetItem, METH_O,
+ "Alias for getitem, useful to make explicit that the map is mutated." },
+ /*
+ { "__deepcopy__", (PyCFunction)DeepCopy, METH_VARARGS,
+ "Makes a deep copy of the class." },
+ { "__reduce__", (PyCFunction)Reduce, METH_NOARGS,
+ "Outputs picklable representation of the repeated field." },
+ */
+ {NULL, NULL},
+};
+
+#if PY_MAJOR_VERSION >= 3
+ static PyType_Slot MessageMapContainer_Type_slots[] = {
+ {Py_tp_dealloc, (void *)MessageMapDealloc},
+ {Py_mp_length, (void *)MapReflectionFriend::Length},
+ {Py_mp_subscript, (void *)MapReflectionFriend::MessageMapGetItem},
+ {Py_mp_ass_subscript, (void *)MapReflectionFriend::MessageMapSetItem},
+ {Py_tp_methods, (void *)MessageMapMethods},
+ {Py_tp_iter, (void *)MapReflectionFriend::GetIterator},
+ {0, 0}
+ };
+
+ PyType_Spec MessageMapContainer_Type_spec = {
+ FULL_MODULE_NAME ".MessageMapContainer",
+ sizeof(MessageMapContainer),
+ 0,
+ Py_TPFLAGS_DEFAULT,
+ MessageMapContainer_Type_slots
+ };
+
+ PyObject *MessageMapContainer_Type;
+#else
+ static PyMappingMethods MessageMapMappingMethods = {
+ MapReflectionFriend::Length, // mp_length
+ MapReflectionFriend::MessageMapGetItem, // mp_subscript
+ MapReflectionFriend::MessageMapSetItem, // mp_ass_subscript
+ };
+
+ PyTypeObject MessageMapContainer_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".MessageMapContainer", // tp_name
+ sizeof(MessageMapContainer), // tp_basicsize
+ 0, // tp_itemsize
+ MessageMapDealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ &MessageMapMappingMethods, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A map container for message", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ MapReflectionFriend::GetIterator, // tp_iter
+ 0, // tp_iternext
+ MessageMapMethods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ };
+#endif
+
+// MapIterator /////////////////////////////////////////////////////////////////
+
+static MapIterator* GetIter(PyObject* obj) {
+ return reinterpret_cast<MapIterator*>(obj);
+}
+
+PyObject* MapReflectionFriend::GetIterator(PyObject *_self) {
+ MapContainer* self = GetMap(_self);
+
+ ScopedPyObjectPtr obj(PyType_GenericAlloc(&MapIterator_Type, 0));
+ if (obj == NULL) {
+ return PyErr_Format(PyExc_KeyError, "Could not allocate iterator");
+ }
+
+ MapIterator* iter = GetIter(obj.get());
+
+ Py_INCREF(self);
+ iter->container = self;
+ iter->version = self->version;
+ iter->owner = self->owner;
+
+ if (MapReflectionFriend::Length(_self) > 0) {
+ Message* message = self->GetMutableMessage();
+ const Reflection* reflection = message->GetReflection();
+
+ iter->iter.reset(new ::google::protobuf::MapIterator(
+ reflection->MapBegin(message, self->parent_field_descriptor)));
+ }
+
+ return obj.release();
+}
+
+PyObject* MapReflectionFriend::IterNext(PyObject* _self) {
+ MapIterator* self = GetIter(_self);
+
+ // This won't catch mutations to the map performed by MergeFrom(); no easy way
+ // to address that.
+ if (self->version != self->container->version) {
+ return PyErr_Format(PyExc_RuntimeError,
+ "Map modified during iteration.");
+ }
+
+ if (self->iter.get() == NULL) {
+ return NULL;
+ }
+
+ Message* message = self->container->GetMutableMessage();
+ const Reflection* reflection = message->GetReflection();
+
+ if (*self->iter ==
+ reflection->MapEnd(message, self->container->parent_field_descriptor)) {
+ return NULL;
+ }
+
+ PyObject* ret = MapKeyToPython(self->container->key_field_descriptor,
+ self->iter->GetKey());
+
+ ++(*self->iter);
+
+ return ret;
+}
+
+static void DeallocMapIterator(PyObject* _self) {
+ MapIterator* self = GetIter(_self);
+ self->iter.reset();
+ self->owner.reset();
+ Py_XDECREF(self->container);
+ Py_TYPE(_self)->tp_free(_self);
+}
+
+PyTypeObject MapIterator_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".MapIterator", // tp_name
+ sizeof(MapIterator), // tp_basicsize
+ 0, // tp_itemsize
+ DeallocMapIterator, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A scalar map iterator", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ PyObject_SelfIter, // tp_iter
+ MapReflectionFriend::IterNext, // tp_iternext
+ 0, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+};
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.h
new file mode 100644
index 0000000000..fbd6713f73
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/map_container.h
@@ -0,0 +1,142 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_MAP_CONTAINER_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_MAP_CONTAINER_H__
+
+#include <Python.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+
+namespace google {
+namespace protobuf {
+
+class Message;
+
+#ifdef _SHARED_PTR_H
+using std::shared_ptr;
+#else
+using internal::shared_ptr;
+#endif
+
+namespace python {
+
+struct CMessage;
+struct CMessageClass;
+
+// This struct is used directly for ScalarMap, and is the base class of
+// MessageMapContainer, which is used for MessageMap.
+struct MapContainer {
+ PyObject_HEAD;
+
+ // This is the top-level C++ Message object that owns the whole
+ // proto tree. Every Python MapContainer holds a
+ // reference to it in order to keep it alive as long as there's a
+ // Python object that references any part of the tree.
+ shared_ptr<Message> owner;
+
+ // Pointer to the C++ Message that contains this container. The
+ // MapContainer does not own this pointer.
+ const Message* message;
+
+ // Use to get a mutable message when necessary.
+ Message* GetMutableMessage();
+
+ // Weak reference to a parent CMessage object (i.e. may be NULL.)
+ //
+ // Used to make sure all ancestors are also mutable when first
+ // modifying the container.
+ CMessage* parent;
+
+ // Pointer to the parent's descriptor that describes this
+ // field. Used together with the parent's message when making a
+ // default message instance mutable.
+ // The pointer is owned by the global DescriptorPool.
+ const FieldDescriptor* parent_field_descriptor;
+ const FieldDescriptor* key_field_descriptor;
+ const FieldDescriptor* value_field_descriptor;
+
+ // We bump this whenever we perform a mutation, to invalidate existing
+ // iterators.
+ uint64 version;
+
+ // Releases the messages in the container to a new message.
+ //
+ // Returns 0 on success, -1 on failure.
+ int Release();
+
+ // Set the owner field of self and any children of self.
+ void SetOwner(const shared_ptr<Message>& new_owner) {
+ owner = new_owner;
+ }
+};
+
+struct MessageMapContainer : public MapContainer {
+ // The type used to create new child messages.
+ CMessageClass* message_class;
+
+ // A dict mapping Message* -> CMessage.
+ PyObject* message_dict;
+};
+
+#if PY_MAJOR_VERSION >= 3
+ extern PyObject *MessageMapContainer_Type;
+ extern PyType_Spec MessageMapContainer_Type_spec;
+ extern PyObject *ScalarMapContainer_Type;
+ extern PyType_Spec ScalarMapContainer_Type_spec;
+#else
+ extern PyTypeObject MessageMapContainer_Type;
+ extern PyTypeObject ScalarMapContainer_Type;
+#endif
+
+extern PyTypeObject MapIterator_Type; // Both map types use the same iterator.
+
+// Builds a MapContainer object, from a parent message and a
+// field descriptor.
+extern PyObject* NewScalarMapContainer(
+ CMessage* parent, const FieldDescriptor* parent_field_descriptor);
+
+// Builds a MessageMap object, from a parent message and a
+// field descriptor.
+extern PyObject* NewMessageMapContainer(
+ CMessage* parent, const FieldDescriptor* parent_field_descriptor,
+ CMessageClass* message_class);
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_MAP_CONTAINER_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.cc
new file mode 100644
index 0000000000..5535338d44
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.cc
@@ -0,0 +1,3085 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#include <google/protobuf/pyext/message.h>
+
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+#include <structmember.h> // A Python header file.
+
+#ifndef PyVarObject_HEAD_INIT
+#define PyVarObject_HEAD_INIT(type, size) PyObject_HEAD_INIT(type) size,
+#endif
+#ifndef Py_TYPE
+#define Py_TYPE(ob) (((PyObject*)(ob))->ob_type)
+#endif
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/util/message_differencer.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/pyext/descriptor.h>
+#include <google/protobuf/pyext/descriptor_pool.h>
+#include <google/protobuf/pyext/extension_dict.h>
+#include <google/protobuf/pyext/repeated_composite_container.h>
+#include <google/protobuf/pyext/repeated_scalar_container.h>
+#include <google/protobuf/pyext/map_container.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#if PY_MAJOR_VERSION >= 3
+ #define PyInt_Check PyLong_Check
+ #define PyInt_AsLong PyLong_AsLong
+ #define PyInt_FromLong PyLong_FromLong
+ #define PyInt_FromSize_t PyLong_FromSize_t
+ #define PyString_Check PyUnicode_Check
+ #define PyString_FromString PyUnicode_FromString
+ #define PyString_FromStringAndSize PyUnicode_FromStringAndSize
+ #if PY_VERSION_HEX < 0x03030000
+ #error "Python 3.0 - 3.2 are not supported."
+ #else
+ #define PyString_AsString(ob) \
+ (PyUnicode_Check(ob)? PyUnicode_AsUTF8(ob): PyBytes_AsString(ob))
+ #define PyString_AsStringAndSize(ob, charpp, sizep) \
+ (PyUnicode_Check(ob)? \
+ ((*(charpp) = PyUnicode_AsUTF8AndSize(ob, (sizep))) == NULL? -1: 0): \
+ PyBytes_AsStringAndSize(ob, (charpp), (sizep)))
+ #endif
+#endif
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+static PyObject* kDESCRIPTOR;
+static PyObject* k_extensions_by_name;
+static PyObject* k_extensions_by_number;
+PyObject* EnumTypeWrapper_class;
+static PyObject* PythonMessage_class;
+static PyObject* kEmptyWeakref;
+static PyObject* WKT_classes = NULL;
+
+namespace message_meta {
+
+static int InsertEmptyWeakref(PyTypeObject* base);
+
+// Add the number of a field descriptor to the containing message class.
+// Equivalent to:
+// _cls.<field>_FIELD_NUMBER = <number>
+static bool AddFieldNumberToClass(
+ PyObject* cls, const FieldDescriptor* field_descriptor) {
+ string constant_name = field_descriptor->name() + "_FIELD_NUMBER";
+ UpperString(&constant_name);
+ ScopedPyObjectPtr attr_name(PyString_FromStringAndSize(
+ constant_name.c_str(), constant_name.size()));
+ if (attr_name == NULL) {
+ return false;
+ }
+ ScopedPyObjectPtr number(PyInt_FromLong(field_descriptor->number()));
+ if (number == NULL) {
+ return false;
+ }
+ if (PyObject_SetAttr(cls, attr_name.get(), number.get()) == -1) {
+ return false;
+ }
+ return true;
+}
+
+
+// Finalize the creation of the Message class.
+static int AddDescriptors(PyObject* cls, const Descriptor* descriptor) {
+ // If there are extension_ranges, the message is "extendable", and extension
+ // classes will register themselves in this class.
+ if (descriptor->extension_range_count() > 0) {
+ ScopedPyObjectPtr by_name(PyDict_New());
+ if (PyObject_SetAttr(cls, k_extensions_by_name, by_name.get()) < 0) {
+ return -1;
+ }
+ ScopedPyObjectPtr by_number(PyDict_New());
+ if (PyObject_SetAttr(cls, k_extensions_by_number, by_number.get()) < 0) {
+ return -1;
+ }
+ }
+
+ // For each field set: cls.<field>_FIELD_NUMBER = <number>
+ for (int i = 0; i < descriptor->field_count(); ++i) {
+ if (!AddFieldNumberToClass(cls, descriptor->field(i))) {
+ return -1;
+ }
+ }
+
+ // For each enum set cls.<enum name> = EnumTypeWrapper(<enum descriptor>).
+ for (int i = 0; i < descriptor->enum_type_count(); ++i) {
+ const EnumDescriptor* enum_descriptor = descriptor->enum_type(i);
+ ScopedPyObjectPtr enum_type(
+ PyEnumDescriptor_FromDescriptor(enum_descriptor));
+ if (enum_type == NULL) {
+ return -1;
+ }
+ // Add wrapped enum type to message class.
+ ScopedPyObjectPtr wrapped(PyObject_CallFunctionObjArgs(
+ EnumTypeWrapper_class, enum_type.get(), NULL));
+ if (wrapped == NULL) {
+ return -1;
+ }
+ if (PyObject_SetAttrString(
+ cls, enum_descriptor->name().c_str(), wrapped.get()) == -1) {
+ return -1;
+ }
+
+ // For each enum value add cls.<name> = <number>
+ for (int j = 0; j < enum_descriptor->value_count(); ++j) {
+ const EnumValueDescriptor* enum_value_descriptor =
+ enum_descriptor->value(j);
+ ScopedPyObjectPtr value_number(PyInt_FromLong(
+ enum_value_descriptor->number()));
+ if (value_number == NULL) {
+ return -1;
+ }
+ if (PyObject_SetAttrString(cls, enum_value_descriptor->name().c_str(),
+ value_number.get()) == -1) {
+ return -1;
+ }
+ }
+ }
+
+ // For each extension set cls.<extension name> = <extension descriptor>.
+ //
+ // Extension descriptors come from
+ // <message descriptor>.extensions_by_name[name]
+ // which was defined previously.
+ for (int i = 0; i < descriptor->extension_count(); ++i) {
+ const google::protobuf::FieldDescriptor* field = descriptor->extension(i);
+ ScopedPyObjectPtr extension_field(PyFieldDescriptor_FromDescriptor(field));
+ if (extension_field == NULL) {
+ return -1;
+ }
+
+ // Add the extension field to the message class.
+ if (PyObject_SetAttrString(
+ cls, field->name().c_str(), extension_field.get()) == -1) {
+ return -1;
+ }
+
+ // For each extension set cls.<extension name>_FIELD_NUMBER = <number>.
+ if (!AddFieldNumberToClass(cls, field)) {
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+static PyObject* New(PyTypeObject* type,
+ PyObject* args, PyObject* kwargs) {
+ static char *kwlist[] = {"name", "bases", "dict", 0};
+ PyObject *bases, *dict;
+ const char* name;
+
+ // Check arguments: (name, bases, dict)
+ if (!PyArg_ParseTupleAndKeywords(args, kwargs, "sO!O!:type", kwlist,
+ &name,
+ &PyTuple_Type, &bases,
+ &PyDict_Type, &dict)) {
+ return NULL;
+ }
+
+ // Check bases: only (), or (message.Message,) are allowed
+ if (!(PyTuple_GET_SIZE(bases) == 0 ||
+ (PyTuple_GET_SIZE(bases) == 1 &&
+ PyTuple_GET_ITEM(bases, 0) == PythonMessage_class))) {
+ PyErr_SetString(PyExc_TypeError,
+ "A Message class can only inherit from Message");
+ return NULL;
+ }
+
+ // Check dict['DESCRIPTOR']
+ PyObject* py_descriptor = PyDict_GetItem(dict, kDESCRIPTOR);
+ if (py_descriptor == NULL) {
+ PyErr_SetString(PyExc_TypeError, "Message class has no DESCRIPTOR");
+ return NULL;
+ }
+ if (!PyObject_TypeCheck(py_descriptor, &PyMessageDescriptor_Type)) {
+ PyErr_Format(PyExc_TypeError, "Expected a message Descriptor, got %s",
+ py_descriptor->ob_type->tp_name);
+ return NULL;
+ }
+
+ // Build the arguments to the base metaclass.
+ // We change the __bases__ classes.
+ ScopedPyObjectPtr new_args;
+ const Descriptor* message_descriptor =
+ PyMessageDescriptor_AsDescriptor(py_descriptor);
+ if (message_descriptor == NULL) {
+ return NULL;
+ }
+
+ if (WKT_classes == NULL) {
+ ScopedPyObjectPtr well_known_types(PyImport_ImportModule(
+ "google.protobuf.internal.well_known_types"));
+ GOOGLE_DCHECK(well_known_types != NULL);
+
+ WKT_classes = PyObject_GetAttrString(well_known_types.get(), "WKTBASES");
+ GOOGLE_DCHECK(WKT_classes != NULL);
+ }
+
+ PyObject* well_known_class = PyDict_GetItemString(
+ WKT_classes, message_descriptor->full_name().c_str());
+ if (well_known_class == NULL) {
+ new_args.reset(Py_BuildValue("s(OO)O", name, &CMessage_Type,
+ PythonMessage_class, dict));
+ } else {
+ new_args.reset(Py_BuildValue("s(OOO)O", name, &CMessage_Type,
+ PythonMessage_class, well_known_class, dict));
+ }
+
+ if (new_args == NULL) {
+ return NULL;
+ }
+ // Call the base metaclass.
+ ScopedPyObjectPtr result(PyType_Type.tp_new(type, new_args.get(), NULL));
+ if (result == NULL) {
+ return NULL;
+ }
+ CMessageClass* newtype = reinterpret_cast<CMessageClass*>(result.get());
+
+ // Insert the empty weakref into the base classes.
+ if (InsertEmptyWeakref(
+ reinterpret_cast<PyTypeObject*>(PythonMessage_class)) < 0 ||
+ InsertEmptyWeakref(&CMessage_Type) < 0) {
+ return NULL;
+ }
+
+ // Cache the descriptor, both as Python object and as C++ pointer.
+ const Descriptor* descriptor =
+ PyMessageDescriptor_AsDescriptor(py_descriptor);
+ if (descriptor == NULL) {
+ return NULL;
+ }
+ Py_INCREF(py_descriptor);
+ newtype->py_message_descriptor = py_descriptor;
+ newtype->message_descriptor = descriptor;
+ // TODO(amauryfa): Don't always use the canonical pool of the descriptor,
+ // use the MessageFactory optionally passed in the class dict.
+ newtype->py_descriptor_pool = GetDescriptorPool_FromPool(
+ descriptor->file()->pool());
+ if (newtype->py_descriptor_pool == NULL) {
+ return NULL;
+ }
+ Py_INCREF(newtype->py_descriptor_pool);
+
+ // Add the message to the DescriptorPool.
+ if (cdescriptor_pool::RegisterMessageClass(newtype->py_descriptor_pool,
+ descriptor, newtype) < 0) {
+ return NULL;
+ }
+
+ // Continue with type initialization: add other descriptors, enum values...
+ if (AddDescriptors(result.get(), descriptor) < 0) {
+ return NULL;
+ }
+ return result.release();
+}
+
+static void Dealloc(CMessageClass *self) {
+ Py_DECREF(self->py_message_descriptor);
+ Py_DECREF(self->py_descriptor_pool);
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+
+// This function inserts and empty weakref at the end of the list of
+// subclasses for the main protocol buffer Message class.
+//
+// This eliminates a O(n^2) behaviour in the internal add_subclass
+// routine.
+static int InsertEmptyWeakref(PyTypeObject *base_type) {
+#if PY_MAJOR_VERSION >= 3
+ // Python 3.4 has already included the fix for the issue that this
+ // hack addresses. For further background and the fix please see
+ // https://bugs.python.org/issue17936.
+ return 0;
+#else
+ PyObject *subclasses = base_type->tp_subclasses;
+ if (subclasses && PyList_CheckExact(subclasses)) {
+ return PyList_Append(subclasses, kEmptyWeakref);
+ }
+ return 0;
+#endif // PY_MAJOR_VERSION >= 3
+}
+
+} // namespace message_meta
+
+PyTypeObject CMessageClass_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".MessageMeta", // tp_name
+ sizeof(CMessageClass), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)message_meta::Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ 0, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, // tp_flags
+ "The metaclass of ProtocolMessages", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ 0, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ 0, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+ 0, // tp_alloc
+ message_meta::New, // tp_new
+};
+
+static CMessageClass* CheckMessageClass(PyTypeObject* cls) {
+ if (!PyObject_TypeCheck(cls, &CMessageClass_Type)) {
+ PyErr_Format(PyExc_TypeError, "Class %s is not a Message", cls->tp_name);
+ return NULL;
+ }
+ return reinterpret_cast<CMessageClass*>(cls);
+}
+
+static const Descriptor* GetMessageDescriptor(PyTypeObject* cls) {
+ CMessageClass* type = CheckMessageClass(cls);
+ if (type == NULL) {
+ return NULL;
+ }
+ return type->message_descriptor;
+}
+
+// Forward declarations
+namespace cmessage {
+int InternalReleaseFieldByDescriptor(
+ CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ PyObject* composite_field);
+} // namespace cmessage
+
+// ---------------------------------------------------------------------
+// Visiting the composite children of a CMessage
+
+struct ChildVisitor {
+ // Returns 0 on success, -1 on failure.
+ int VisitRepeatedCompositeContainer(RepeatedCompositeContainer* container) {
+ return 0;
+ }
+
+ // Returns 0 on success, -1 on failure.
+ int VisitRepeatedScalarContainer(RepeatedScalarContainer* container) {
+ return 0;
+ }
+
+ // Returns 0 on success, -1 on failure.
+ int VisitCMessage(CMessage* cmessage,
+ const FieldDescriptor* field_descriptor) {
+ return 0;
+ }
+};
+
+// Apply a function to a composite field. Does nothing if child is of
+// non-composite type.
+template<class Visitor>
+static int VisitCompositeField(const FieldDescriptor* descriptor,
+ PyObject* child,
+ Visitor visitor) {
+ if (descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (descriptor->is_map()) {
+ MapContainer* container = reinterpret_cast<MapContainer*>(child);
+ if (visitor.VisitMapContainer(container) == -1) {
+ return -1;
+ }
+ } else {
+ RepeatedCompositeContainer* container =
+ reinterpret_cast<RepeatedCompositeContainer*>(child);
+ if (visitor.VisitRepeatedCompositeContainer(container) == -1)
+ return -1;
+ }
+ } else {
+ RepeatedScalarContainer* container =
+ reinterpret_cast<RepeatedScalarContainer*>(child);
+ if (visitor.VisitRepeatedScalarContainer(container) == -1)
+ return -1;
+ }
+ } else if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ CMessage* cmsg = reinterpret_cast<CMessage*>(child);
+ if (visitor.VisitCMessage(cmsg, descriptor) == -1)
+ return -1;
+ }
+ // The ExtensionDict might contain non-composite fields, which we
+ // skip here.
+ return 0;
+}
+
+// Visit each composite field and extension field of this CMessage.
+// Returns -1 on error and 0 on success.
+template<class Visitor>
+int ForEachCompositeField(CMessage* self, Visitor visitor) {
+ Py_ssize_t pos = 0;
+ PyObject* key;
+ PyObject* field;
+
+ // Visit normal fields.
+ if (self->composite_fields) {
+ // Never use self->message in this function, it may be already freed.
+ const Descriptor* message_descriptor =
+ GetMessageDescriptor(Py_TYPE(self));
+ while (PyDict_Next(self->composite_fields, &pos, &key, &field)) {
+ Py_ssize_t key_str_size;
+ char *key_str_data;
+ if (PyString_AsStringAndSize(key, &key_str_data, &key_str_size) != 0)
+ return -1;
+ const string key_str(key_str_data, key_str_size);
+ const FieldDescriptor* descriptor =
+ message_descriptor->FindFieldByName(key_str);
+ if (descriptor != NULL) {
+ if (VisitCompositeField(descriptor, field, visitor) == -1)
+ return -1;
+ }
+ }
+ }
+
+ // Visit extension fields.
+ if (self->extensions != NULL) {
+ pos = 0;
+ while (PyDict_Next(self->extensions->values, &pos, &key, &field)) {
+ const FieldDescriptor* descriptor = cmessage::GetExtensionDescriptor(key);
+ if (descriptor == NULL)
+ return -1;
+ if (VisitCompositeField(descriptor, field, visitor) == -1)
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+// ---------------------------------------------------------------------
+
+// Constants used for integer type range checking.
+PyObject* kPythonZero;
+PyObject* kint32min_py;
+PyObject* kint32max_py;
+PyObject* kuint32max_py;
+PyObject* kint64min_py;
+PyObject* kint64max_py;
+PyObject* kuint64max_py;
+
+PyObject* EncodeError_class;
+PyObject* DecodeError_class;
+PyObject* PickleError_class;
+
+// Constant PyString values used for GetAttr/GetItem.
+static PyObject* k_cdescriptor;
+static PyObject* kfull_name;
+
+/* Is 64bit */
+void FormatTypeError(PyObject* arg, char* expected_types) {
+ PyObject* repr = PyObject_Repr(arg);
+ if (repr) {
+ PyErr_Format(PyExc_TypeError,
+ "%.100s has type %.100s, but expected one of: %s",
+ PyString_AsString(repr),
+ Py_TYPE(arg)->tp_name,
+ expected_types);
+ Py_DECREF(repr);
+ }
+}
+
+template<class T>
+bool CheckAndGetInteger(
+ PyObject* arg, T* value, PyObject* min, PyObject* max) {
+ bool is_long = PyLong_Check(arg);
+#if PY_MAJOR_VERSION < 3
+ if (!PyInt_Check(arg) && !is_long) {
+ FormatTypeError(arg, "int, long");
+ return false;
+ }
+ if (PyObject_Compare(min, arg) > 0 || PyObject_Compare(max, arg) < 0) {
+#else
+ if (!is_long) {
+ FormatTypeError(arg, "int");
+ return false;
+ }
+ if (PyObject_RichCompareBool(min, arg, Py_LE) != 1 ||
+ PyObject_RichCompareBool(max, arg, Py_GE) != 1) {
+#endif
+ if (!PyErr_Occurred()) {
+ PyObject *s = PyObject_Str(arg);
+ if (s) {
+ PyErr_Format(PyExc_ValueError,
+ "Value out of range: %s",
+ PyString_AsString(s));
+ Py_DECREF(s);
+ }
+ }
+ return false;
+ }
+#if PY_MAJOR_VERSION < 3
+ if (!is_long) {
+ *value = static_cast<T>(PyInt_AsLong(arg));
+ } else // NOLINT
+#endif
+ {
+ if (min == kPythonZero) {
+ *value = static_cast<T>(PyLong_AsUnsignedLongLong(arg));
+ } else {
+ *value = static_cast<T>(PyLong_AsLongLong(arg));
+ }
+ }
+ return true;
+}
+
+// These are referenced by repeated_scalar_container, and must
+// be explicitly instantiated.
+template bool CheckAndGetInteger<int32>(
+ PyObject*, int32*, PyObject*, PyObject*);
+template bool CheckAndGetInteger<int64>(
+ PyObject*, int64*, PyObject*, PyObject*);
+template bool CheckAndGetInteger<uint32>(
+ PyObject*, uint32*, PyObject*, PyObject*);
+template bool CheckAndGetInteger<uint64>(
+ PyObject*, uint64*, PyObject*, PyObject*);
+
+bool CheckAndGetDouble(PyObject* arg, double* value) {
+ if (!PyInt_Check(arg) && !PyLong_Check(arg) &&
+ !PyFloat_Check(arg)) {
+ FormatTypeError(arg, "int, long, float");
+ return false;
+ }
+ *value = PyFloat_AsDouble(arg);
+ return true;
+}
+
+bool CheckAndGetFloat(PyObject* arg, float* value) {
+ double double_value;
+ if (!CheckAndGetDouble(arg, &double_value)) {
+ return false;
+ }
+ *value = static_cast<float>(double_value);
+ return true;
+}
+
+bool CheckAndGetBool(PyObject* arg, bool* value) {
+ if (!PyInt_Check(arg) && !PyBool_Check(arg) && !PyLong_Check(arg)) {
+ FormatTypeError(arg, "int, long, bool");
+ return false;
+ }
+ *value = static_cast<bool>(PyInt_AsLong(arg));
+ return true;
+}
+
+// Checks whether the given object (which must be "bytes" or "unicode") contains
+// valid UTF-8.
+bool IsValidUTF8(PyObject* obj) {
+ if (PyBytes_Check(obj)) {
+ PyObject* unicode = PyUnicode_FromEncodedObject(obj, "utf-8", NULL);
+
+ // Clear the error indicator; we report our own error when desired.
+ PyErr_Clear();
+
+ if (unicode) {
+ Py_DECREF(unicode);
+ return true;
+ } else {
+ return false;
+ }
+ } else {
+ // Unicode object, known to be valid UTF-8.
+ return true;
+ }
+}
+
+bool AllowInvalidUTF8(const FieldDescriptor* field) { return false; }
+
+PyObject* CheckString(PyObject* arg, const FieldDescriptor* descriptor) {
+ GOOGLE_DCHECK(descriptor->type() == FieldDescriptor::TYPE_STRING ||
+ descriptor->type() == FieldDescriptor::TYPE_BYTES);
+ if (descriptor->type() == FieldDescriptor::TYPE_STRING) {
+ if (!PyBytes_Check(arg) && !PyUnicode_Check(arg)) {
+ FormatTypeError(arg, "bytes, unicode");
+ return NULL;
+ }
+
+ if (!IsValidUTF8(arg) && !AllowInvalidUTF8(descriptor)) {
+ PyObject* repr = PyObject_Repr(arg);
+ PyErr_Format(PyExc_ValueError,
+ "%s has type str, but isn't valid UTF-8 "
+ "encoding. Non-UTF-8 strings must be converted to "
+ "unicode objects before being added.",
+ PyString_AsString(repr));
+ Py_DECREF(repr);
+ return NULL;
+ }
+ } else if (!PyBytes_Check(arg)) {
+ FormatTypeError(arg, "bytes");
+ return NULL;
+ }
+
+ PyObject* encoded_string = NULL;
+ if (descriptor->type() == FieldDescriptor::TYPE_STRING) {
+ if (PyBytes_Check(arg)) {
+ // The bytes were already validated as correctly encoded UTF-8 above.
+ encoded_string = arg; // Already encoded.
+ Py_INCREF(encoded_string);
+ } else {
+ encoded_string = PyUnicode_AsEncodedObject(arg, "utf-8", NULL);
+ }
+ } else {
+ // In this case field type is "bytes".
+ encoded_string = arg;
+ Py_INCREF(encoded_string);
+ }
+
+ return encoded_string;
+}
+
+bool CheckAndSetString(
+ PyObject* arg, Message* message,
+ const FieldDescriptor* descriptor,
+ const Reflection* reflection,
+ bool append,
+ int index) {
+ ScopedPyObjectPtr encoded_string(CheckString(arg, descriptor));
+
+ if (encoded_string.get() == NULL) {
+ return false;
+ }
+
+ char* value;
+ Py_ssize_t value_len;
+ if (PyBytes_AsStringAndSize(encoded_string.get(), &value, &value_len) < 0) {
+ return false;
+ }
+
+ string value_string(value, value_len);
+ if (append) {
+ reflection->AddString(message, descriptor, value_string);
+ } else if (index < 0) {
+ reflection->SetString(message, descriptor, value_string);
+ } else {
+ reflection->SetRepeatedString(message, descriptor, index, value_string);
+ }
+ return true;
+}
+
+PyObject* ToStringObject(const FieldDescriptor* descriptor, string value) {
+ if (descriptor->type() != FieldDescriptor::TYPE_STRING) {
+ return PyBytes_FromStringAndSize(value.c_str(), value.length());
+ }
+
+ PyObject* result = PyUnicode_DecodeUTF8(value.c_str(), value.length(), NULL);
+ // If the string can't be decoded in UTF-8, just return a string object that
+ // contains the raw bytes. This can't happen if the value was assigned using
+ // the members of the Python message object, but can happen if the values were
+ // parsed from the wire (binary).
+ if (result == NULL) {
+ PyErr_Clear();
+ result = PyBytes_FromStringAndSize(value.c_str(), value.length());
+ }
+ return result;
+}
+
+bool CheckFieldBelongsToMessage(const FieldDescriptor* field_descriptor,
+ const Message* message) {
+ if (message->GetDescriptor() == field_descriptor->containing_type()) {
+ return true;
+ }
+ PyErr_Format(PyExc_KeyError, "Field '%s' does not belong to message '%s'",
+ field_descriptor->full_name().c_str(),
+ message->GetDescriptor()->full_name().c_str());
+ return false;
+}
+
+namespace cmessage {
+
+PyDescriptorPool* GetDescriptorPoolForMessage(CMessage* message) {
+ // No need to check the type: the type of instances of CMessage is always
+ // an instance of CMessageClass. Let's prove it with a debug-only check.
+ GOOGLE_DCHECK(PyObject_TypeCheck(message, &CMessage_Type));
+ return reinterpret_cast<CMessageClass*>(Py_TYPE(message))->py_descriptor_pool;
+}
+
+MessageFactory* GetFactoryForMessage(CMessage* message) {
+ return GetDescriptorPoolForMessage(message)->message_factory;
+}
+
+static int MaybeReleaseOverlappingOneofField(
+ CMessage* cmessage,
+ const FieldDescriptor* field) {
+#ifdef GOOGLE_PROTOBUF_HAS_ONEOF
+ Message* message = cmessage->message;
+ const Reflection* reflection = message->GetReflection();
+ if (!field->containing_oneof() ||
+ !reflection->HasOneof(*message, field->containing_oneof()) ||
+ reflection->HasField(*message, field)) {
+ // No other field in this oneof, no need to release.
+ return 0;
+ }
+
+ const OneofDescriptor* oneof = field->containing_oneof();
+ const FieldDescriptor* existing_field =
+ reflection->GetOneofFieldDescriptor(*message, oneof);
+ if (existing_field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Non-message fields don't need to be released.
+ return 0;
+ }
+ const char* field_name = existing_field->name().c_str();
+ PyObject* child_message = cmessage->composite_fields ?
+ PyDict_GetItemString(cmessage->composite_fields, field_name) : NULL;
+ if (child_message == NULL) {
+ // No python reference to this field so no need to release.
+ return 0;
+ }
+
+ if (InternalReleaseFieldByDescriptor(
+ cmessage, existing_field, child_message) < 0) {
+ return -1;
+ }
+ return PyDict_DelItemString(cmessage->composite_fields, field_name);
+#else
+ return 0;
+#endif
+}
+
+// ---------------------------------------------------------------------
+// Making a message writable
+
+static Message* GetMutableMessage(
+ CMessage* parent,
+ const FieldDescriptor* parent_field) {
+ Message* parent_message = parent->message;
+ const Reflection* reflection = parent_message->GetReflection();
+ if (MaybeReleaseOverlappingOneofField(parent, parent_field) < 0) {
+ return NULL;
+ }
+ return reflection->MutableMessage(
+ parent_message, parent_field, GetFactoryForMessage(parent));
+}
+
+struct FixupMessageReference : public ChildVisitor {
+ // message must outlive this object.
+ explicit FixupMessageReference(Message* message) :
+ message_(message) {}
+
+ int VisitRepeatedCompositeContainer(RepeatedCompositeContainer* container) {
+ container->message = message_;
+ return 0;
+ }
+
+ int VisitRepeatedScalarContainer(RepeatedScalarContainer* container) {
+ container->message = message_;
+ return 0;
+ }
+
+ int VisitMapContainer(MapContainer* container) {
+ container->message = message_;
+ return 0;
+ }
+
+ private:
+ Message* message_;
+};
+
+int AssureWritable(CMessage* self) {
+ if (self == NULL || !self->read_only) {
+ return 0;
+ }
+
+ if (self->parent == NULL) {
+ // If parent is NULL but we are trying to modify a read-only message, this
+ // is a reference to a constant default instance that needs to be replaced
+ // with a mutable top-level message.
+ self->message = self->message->New();
+ self->owner.reset(self->message);
+ // Cascade the new owner to eventual children: even if this message is
+ // empty, some submessages or repeated containers might exist already.
+ SetOwner(self, self->owner);
+ } else {
+ // Otherwise, we need a mutable child message.
+ if (AssureWritable(self->parent) == -1)
+ return -1;
+
+ // Make self->message writable.
+ Message* mutable_message = GetMutableMessage(
+ self->parent,
+ self->parent_field_descriptor);
+ if (mutable_message == NULL) {
+ return -1;
+ }
+ self->message = mutable_message;
+ }
+ self->read_only = false;
+
+ // When a CMessage is made writable its Message pointer is updated
+ // to point to a new mutable Message. When that happens we need to
+ // update any references to the old, read-only CMessage. There are
+ // four places such references occur: RepeatedScalarContainer,
+ // RepeatedCompositeContainer, MapContainer, and ExtensionDict.
+ if (self->extensions != NULL)
+ self->extensions->message = self->message;
+ if (ForEachCompositeField(self, FixupMessageReference(self->message)) == -1)
+ return -1;
+
+ return 0;
+}
+
+// --- Globals:
+
+// Retrieve a C++ FieldDescriptor for a message attribute.
+// The C++ message must be valid.
+// TODO(amauryfa): This function should stay internal, because exception
+// handling is not consistent.
+static const FieldDescriptor* GetFieldDescriptor(
+ CMessage* self, PyObject* name) {
+ const Descriptor *message_descriptor = self->message->GetDescriptor();
+ char* field_name;
+ Py_ssize_t size;
+ if (PyString_AsStringAndSize(name, &field_name, &size) < 0) {
+ return NULL;
+ }
+ const FieldDescriptor *field_descriptor =
+ message_descriptor->FindFieldByName(string(field_name, size));
+ if (field_descriptor == NULL) {
+ // Note: No exception is set!
+ return NULL;
+ }
+ return field_descriptor;
+}
+
+// Retrieve a C++ FieldDescriptor for an extension handle.
+const FieldDescriptor* GetExtensionDescriptor(PyObject* extension) {
+ ScopedPyObjectPtr cdescriptor;
+ if (!PyObject_TypeCheck(extension, &PyFieldDescriptor_Type)) {
+ // Most callers consider extensions as a plain dictionary. We should
+ // allow input which is not a field descriptor, and simply pretend it does
+ // not exist.
+ PyErr_SetObject(PyExc_KeyError, extension);
+ return NULL;
+ }
+ return PyFieldDescriptor_AsDescriptor(extension);
+}
+
+// If value is a string, convert it into an enum value based on the labels in
+// descriptor, otherwise simply return value. Always returns a new reference.
+static PyObject* GetIntegerEnumValue(const FieldDescriptor& descriptor,
+ PyObject* value) {
+ if (PyString_Check(value) || PyUnicode_Check(value)) {
+ const EnumDescriptor* enum_descriptor = descriptor.enum_type();
+ if (enum_descriptor == NULL) {
+ PyErr_SetString(PyExc_TypeError, "not an enum field");
+ return NULL;
+ }
+ char* enum_label;
+ Py_ssize_t size;
+ if (PyString_AsStringAndSize(value, &enum_label, &size) < 0) {
+ return NULL;
+ }
+ const EnumValueDescriptor* enum_value_descriptor =
+ enum_descriptor->FindValueByName(string(enum_label, size));
+ if (enum_value_descriptor == NULL) {
+ PyErr_SetString(PyExc_ValueError, "unknown enum label");
+ return NULL;
+ }
+ return PyInt_FromLong(enum_value_descriptor->number());
+ }
+ Py_INCREF(value);
+ return value;
+}
+
+// If cmessage_list is not NULL, this function releases values into the
+// container CMessages instead of just removing. Repeated composite container
+// needs to do this to make sure CMessages stay alive if they're still
+// referenced after deletion. Repeated scalar container doesn't need to worry.
+int InternalDeleteRepeatedField(
+ CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ PyObject* slice,
+ PyObject* cmessage_list) {
+ Message* message = self->message;
+ Py_ssize_t length, from, to, step, slice_length;
+ const Reflection* reflection = message->GetReflection();
+ int min, max;
+ length = reflection->FieldSize(*message, field_descriptor);
+
+ if (PyInt_Check(slice) || PyLong_Check(slice)) {
+ from = to = PyLong_AsLong(slice);
+ if (from < 0) {
+ from = to = length + from;
+ }
+ step = 1;
+ min = max = from;
+
+ // Range check.
+ if (from < 0 || from >= length) {
+ PyErr_Format(PyExc_IndexError, "list assignment index out of range");
+ return -1;
+ }
+ } else if (PySlice_Check(slice)) {
+ from = to = step = slice_length = 0;
+ PySlice_GetIndicesEx(
+#if PY_MAJOR_VERSION < 3
+ reinterpret_cast<PySliceObject*>(slice),
+#else
+ slice,
+#endif
+ length, &from, &to, &step, &slice_length);
+ if (from < to) {
+ min = from;
+ max = to - 1;
+ } else {
+ min = to + 1;
+ max = from;
+ }
+ } else {
+ PyErr_SetString(PyExc_TypeError, "list indices must be integers");
+ return -1;
+ }
+
+ Py_ssize_t i = from;
+ std::vector<bool> to_delete(length, false);
+ while (i >= min && i <= max) {
+ to_delete[i] = true;
+ i += step;
+ }
+
+ to = 0;
+ for (i = 0; i < length; ++i) {
+ if (!to_delete[i]) {
+ if (i != to) {
+ reflection->SwapElements(message, field_descriptor, i, to);
+ if (cmessage_list != NULL) {
+ // If a list of cmessages is passed in (i.e. from a repeated
+ // composite container), swap those as well to correspond to the
+ // swaps in the underlying message so they're in the right order
+ // when we start releasing.
+ PyObject* tmp = PyList_GET_ITEM(cmessage_list, i);
+ PyList_SET_ITEM(cmessage_list, i,
+ PyList_GET_ITEM(cmessage_list, to));
+ PyList_SET_ITEM(cmessage_list, to, tmp);
+ }
+ }
+ ++to;
+ }
+ }
+
+ while (i > to) {
+ if (cmessage_list == NULL) {
+ reflection->RemoveLast(message, field_descriptor);
+ } else {
+ CMessage* last_cmessage = reinterpret_cast<CMessage*>(
+ PyList_GET_ITEM(cmessage_list, PyList_GET_SIZE(cmessage_list) - 1));
+ repeated_composite_container::ReleaseLastTo(
+ self, field_descriptor, last_cmessage);
+ if (PySequence_DelItem(cmessage_list, -1) < 0) {
+ return -1;
+ }
+ }
+ --i;
+ }
+
+ return 0;
+}
+
+// Initializes fields of a message. Used in constructors.
+int InitAttributes(CMessage* self, PyObject* args, PyObject* kwargs) {
+ if (args != NULL && PyTuple_Size(args) != 0) {
+ PyErr_SetString(PyExc_TypeError, "No positional arguments allowed");
+ return -1;
+ }
+
+ if (kwargs == NULL) {
+ return 0;
+ }
+
+ Py_ssize_t pos = 0;
+ PyObject* name;
+ PyObject* value;
+ while (PyDict_Next(kwargs, &pos, &name, &value)) {
+ if (!PyString_Check(name)) {
+ PyErr_SetString(PyExc_ValueError, "Field name must be a string");
+ return -1;
+ }
+ const FieldDescriptor* descriptor = GetFieldDescriptor(self, name);
+ if (descriptor == NULL) {
+ PyErr_Format(PyExc_ValueError, "Protocol message %s has no \"%s\" field.",
+ self->message->GetDescriptor()->name().c_str(),
+ PyString_AsString(name));
+ return -1;
+ }
+ if (value == Py_None) {
+ // field=None is the same as no field at all.
+ continue;
+ }
+ if (descriptor->is_map()) {
+ ScopedPyObjectPtr map(GetAttr(self, name));
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ if (value_descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ Py_ssize_t map_pos = 0;
+ PyObject* map_key;
+ PyObject* map_value;
+ while (PyDict_Next(value, &map_pos, &map_key, &map_value)) {
+ ScopedPyObjectPtr function_return;
+ function_return.reset(PyObject_GetItem(map.get(), map_key));
+ if (function_return.get() == NULL) {
+ return -1;
+ }
+ ScopedPyObjectPtr ok(PyObject_CallMethod(
+ function_return.get(), "MergeFrom", "O", map_value));
+ if (ok.get() == NULL) {
+ return -1;
+ }
+ }
+ } else {
+ ScopedPyObjectPtr function_return;
+ function_return.reset(
+ PyObject_CallMethod(map.get(), "update", "O", value));
+ if (function_return.get() == NULL) {
+ return -1;
+ }
+ }
+ } else if (descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ ScopedPyObjectPtr container(GetAttr(self, name));
+ if (container == NULL) {
+ return -1;
+ }
+ if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ RepeatedCompositeContainer* rc_container =
+ reinterpret_cast<RepeatedCompositeContainer*>(container.get());
+ ScopedPyObjectPtr iter(PyObject_GetIter(value));
+ if (iter == NULL) {
+ PyErr_SetString(PyExc_TypeError, "Value must be iterable");
+ return -1;
+ }
+ ScopedPyObjectPtr next;
+ while ((next.reset(PyIter_Next(iter.get()))) != NULL) {
+ PyObject* kwargs = (PyDict_Check(next.get()) ? next.get() : NULL);
+ ScopedPyObjectPtr new_msg(
+ repeated_composite_container::Add(rc_container, NULL, kwargs));
+ if (new_msg == NULL) {
+ return -1;
+ }
+ if (kwargs == NULL) {
+ // next was not a dict, it's a message we need to merge
+ ScopedPyObjectPtr merged(MergeFrom(
+ reinterpret_cast<CMessage*>(new_msg.get()), next.get()));
+ if (merged.get() == NULL) {
+ return -1;
+ }
+ }
+ }
+ if (PyErr_Occurred()) {
+ // Check to see how PyIter_Next() exited.
+ return -1;
+ }
+ } else if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ RepeatedScalarContainer* rs_container =
+ reinterpret_cast<RepeatedScalarContainer*>(container.get());
+ ScopedPyObjectPtr iter(PyObject_GetIter(value));
+ if (iter == NULL) {
+ PyErr_SetString(PyExc_TypeError, "Value must be iterable");
+ return -1;
+ }
+ ScopedPyObjectPtr next;
+ while ((next.reset(PyIter_Next(iter.get()))) != NULL) {
+ ScopedPyObjectPtr enum_value(
+ GetIntegerEnumValue(*descriptor, next.get()));
+ if (enum_value == NULL) {
+ return -1;
+ }
+ ScopedPyObjectPtr new_msg(repeated_scalar_container::Append(
+ rs_container, enum_value.get()));
+ if (new_msg == NULL) {
+ return -1;
+ }
+ }
+ if (PyErr_Occurred()) {
+ // Check to see how PyIter_Next() exited.
+ return -1;
+ }
+ } else {
+ if (ScopedPyObjectPtr(repeated_scalar_container::Extend(
+ reinterpret_cast<RepeatedScalarContainer*>(container.get()),
+ value)) ==
+ NULL) {
+ return -1;
+ }
+ }
+ } else if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ ScopedPyObjectPtr message(GetAttr(self, name));
+ if (message == NULL) {
+ return -1;
+ }
+ CMessage* cmessage = reinterpret_cast<CMessage*>(message.get());
+ if (PyDict_Check(value)) {
+ if (InitAttributes(cmessage, NULL, value) < 0) {
+ return -1;
+ }
+ } else {
+ ScopedPyObjectPtr merged(MergeFrom(cmessage, value));
+ if (merged == NULL) {
+ return -1;
+ }
+ }
+ } else {
+ ScopedPyObjectPtr new_val;
+ if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ new_val.reset(GetIntegerEnumValue(*descriptor, value));
+ if (new_val == NULL) {
+ return -1;
+ }
+ }
+ if (SetAttr(self, name, (new_val.get() == NULL) ? value : new_val.get()) <
+ 0) {
+ return -1;
+ }
+ }
+ }
+ return 0;
+}
+
+// Allocates an incomplete Python Message: the caller must fill self->message,
+// self->owner and eventually self->parent.
+CMessage* NewEmptyMessage(CMessageClass* type) {
+ CMessage* self = reinterpret_cast<CMessage*>(
+ PyType_GenericAlloc(&type->super.ht_type, 0));
+ if (self == NULL) {
+ return NULL;
+ }
+
+ self->message = NULL;
+ self->parent = NULL;
+ self->parent_field_descriptor = NULL;
+ self->read_only = false;
+ self->extensions = NULL;
+
+ self->composite_fields = NULL;
+
+ return self;
+}
+
+// The __new__ method of Message classes.
+// Creates a new C++ message and takes ownership.
+static PyObject* New(PyTypeObject* cls,
+ PyObject* unused_args, PyObject* unused_kwargs) {
+ CMessageClass* type = CheckMessageClass(cls);
+ if (type == NULL) {
+ return NULL;
+ }
+ // Retrieve the message descriptor and the default instance (=prototype).
+ const Descriptor* message_descriptor = type->message_descriptor;
+ if (message_descriptor == NULL) {
+ return NULL;
+ }
+ const Message* default_message = type->py_descriptor_pool->message_factory
+ ->GetPrototype(message_descriptor);
+ if (default_message == NULL) {
+ PyErr_SetString(PyExc_TypeError, message_descriptor->full_name().c_str());
+ return NULL;
+ }
+
+ CMessage* self = NewEmptyMessage(type);
+ if (self == NULL) {
+ return NULL;
+ }
+ self->message = default_message->New();
+ self->owner.reset(self->message);
+ return reinterpret_cast<PyObject*>(self);
+}
+
+// The __init__ method of Message classes.
+// It initializes fields from keywords passed to the constructor.
+static int Init(CMessage* self, PyObject* args, PyObject* kwargs) {
+ return InitAttributes(self, args, kwargs);
+}
+
+// ---------------------------------------------------------------------
+// Deallocating a CMessage
+//
+// Deallocating a CMessage requires that we clear any weak references
+// from children to the message being deallocated.
+
+// Clear the weak reference from the child to the parent.
+struct ClearWeakReferences : public ChildVisitor {
+ int VisitRepeatedCompositeContainer(RepeatedCompositeContainer* container) {
+ container->parent = NULL;
+ // The elements in the container have the same parent as the
+ // container itself, so NULL out that pointer as well.
+ const Py_ssize_t n = PyList_GET_SIZE(container->child_messages);
+ for (Py_ssize_t i = 0; i < n; ++i) {
+ CMessage* child_cmessage = reinterpret_cast<CMessage*>(
+ PyList_GET_ITEM(container->child_messages, i));
+ child_cmessage->parent = NULL;
+ }
+ return 0;
+ }
+
+ int VisitRepeatedScalarContainer(RepeatedScalarContainer* container) {
+ container->parent = NULL;
+ return 0;
+ }
+
+ int VisitMapContainer(MapContainer* container) {
+ container->parent = NULL;
+ return 0;
+ }
+
+ int VisitCMessage(CMessage* cmessage,
+ const FieldDescriptor* field_descriptor) {
+ cmessage->parent = NULL;
+ return 0;
+ }
+};
+
+static void Dealloc(CMessage* self) {
+ // Null out all weak references from children to this message.
+ GOOGLE_CHECK_EQ(0, ForEachCompositeField(self, ClearWeakReferences()));
+ if (self->extensions) {
+ self->extensions->parent = NULL;
+ }
+
+ Py_CLEAR(self->extensions);
+ Py_CLEAR(self->composite_fields);
+ self->owner.reset();
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+// ---------------------------------------------------------------------
+
+
+PyObject* IsInitialized(CMessage* self, PyObject* args) {
+ PyObject* errors = NULL;
+ if (PyArg_ParseTuple(args, "|O", &errors) < 0) {
+ return NULL;
+ }
+ if (self->message->IsInitialized()) {
+ Py_RETURN_TRUE;
+ }
+ if (errors != NULL) {
+ ScopedPyObjectPtr initialization_errors(
+ FindInitializationErrors(self));
+ if (initialization_errors == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr extend_name(PyString_FromString("extend"));
+ if (extend_name == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr result(PyObject_CallMethodObjArgs(
+ errors,
+ extend_name.get(),
+ initialization_errors.get(),
+ NULL));
+ if (result == NULL) {
+ return NULL;
+ }
+ }
+ Py_RETURN_FALSE;
+}
+
+PyObject* HasFieldByDescriptor(
+ CMessage* self, const FieldDescriptor* field_descriptor) {
+ Message* message = self->message;
+ if (!CheckFieldBelongsToMessage(field_descriptor, message)) {
+ return NULL;
+ }
+ if (field_descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ PyErr_SetString(PyExc_KeyError,
+ "Field is repeated. A singular method is required.");
+ return NULL;
+ }
+ bool has_field =
+ message->GetReflection()->HasField(*message, field_descriptor);
+ return PyBool_FromLong(has_field ? 1 : 0);
+}
+
+const FieldDescriptor* FindFieldWithOneofs(
+ const Message* message, const string& field_name, bool* in_oneof) {
+ *in_oneof = false;
+ const Descriptor* descriptor = message->GetDescriptor();
+ const FieldDescriptor* field_descriptor =
+ descriptor->FindFieldByName(field_name);
+ if (field_descriptor != NULL) {
+ return field_descriptor;
+ }
+ const OneofDescriptor* oneof_desc =
+ descriptor->FindOneofByName(field_name);
+ if (oneof_desc != NULL) {
+ *in_oneof = true;
+ return message->GetReflection()->GetOneofFieldDescriptor(*message,
+ oneof_desc);
+ }
+ return NULL;
+}
+
+bool CheckHasPresence(const FieldDescriptor* field_descriptor, bool in_oneof) {
+ if (field_descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ PyErr_Format(PyExc_ValueError,
+ "Protocol message has no singular \"%s\" field.",
+ field_descriptor->name().c_str());
+ return false;
+ }
+
+ if (field_descriptor->file()->syntax() == FileDescriptor::SYNTAX_PROTO3) {
+ // HasField() for a oneof *itself* isn't supported.
+ if (in_oneof) {
+ PyErr_Format(PyExc_ValueError,
+ "Can't test oneof field \"%s\" for presence in proto3, use "
+ "WhichOneof instead.",
+ field_descriptor->containing_oneof()->name().c_str());
+ return false;
+ }
+
+ // ...but HasField() for fields *in* a oneof is supported.
+ if (field_descriptor->containing_oneof() != NULL) {
+ return true;
+ }
+
+ if (field_descriptor->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ PyErr_Format(
+ PyExc_ValueError,
+ "Can't test non-submessage field \"%s\" for presence in proto3.",
+ field_descriptor->name().c_str());
+ return false;
+ }
+ }
+
+ return true;
+}
+
+PyObject* HasField(CMessage* self, PyObject* arg) {
+ char* field_name;
+ Py_ssize_t size;
+#if PY_MAJOR_VERSION < 3
+ if (PyString_AsStringAndSize(arg, &field_name, &size) < 0) {
+ return NULL;
+ }
+#else
+ field_name = PyUnicode_AsUTF8AndSize(arg, &size);
+ if (!field_name) {
+ return NULL;
+ }
+#endif
+
+ Message* message = self->message;
+ bool is_in_oneof;
+ const FieldDescriptor* field_descriptor =
+ FindFieldWithOneofs(message, string(field_name, size), &is_in_oneof);
+ if (field_descriptor == NULL) {
+ if (!is_in_oneof) {
+ PyErr_Format(PyExc_ValueError, "Unknown field %s.", field_name);
+ return NULL;
+ } else {
+ Py_RETURN_FALSE;
+ }
+ }
+
+ if (!CheckHasPresence(field_descriptor, is_in_oneof)) {
+ return NULL;
+ }
+
+ if (message->GetReflection()->HasField(*message, field_descriptor)) {
+ Py_RETURN_TRUE;
+ }
+ if (!message->GetReflection()->SupportsUnknownEnumValues() &&
+ field_descriptor->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ // Special case: Python HasField() differs in semantics from C++
+ // slightly: we return HasField('enum_field') == true if there is
+ // an unknown enum value present. To implement this we have to
+ // look in the UnknownFieldSet.
+ const UnknownFieldSet& unknown_field_set =
+ message->GetReflection()->GetUnknownFields(*message);
+ for (int i = 0; i < unknown_field_set.field_count(); ++i) {
+ if (unknown_field_set.field(i).number() == field_descriptor->number()) {
+ Py_RETURN_TRUE;
+ }
+ }
+ }
+ Py_RETURN_FALSE;
+}
+
+PyObject* ClearExtension(CMessage* self, PyObject* extension) {
+ if (self->extensions != NULL) {
+ return extension_dict::ClearExtension(self->extensions, extension);
+ } else {
+ const FieldDescriptor* descriptor = GetExtensionDescriptor(extension);
+ if (descriptor == NULL) {
+ return NULL;
+ }
+ if (ScopedPyObjectPtr(ClearFieldByDescriptor(self, descriptor)) == NULL) {
+ return NULL;
+ }
+ }
+ Py_RETURN_NONE;
+}
+
+PyObject* HasExtension(CMessage* self, PyObject* extension) {
+ const FieldDescriptor* descriptor = GetExtensionDescriptor(extension);
+ if (descriptor == NULL) {
+ return NULL;
+ }
+ return HasFieldByDescriptor(self, descriptor);
+}
+
+// ---------------------------------------------------------------------
+// Releasing messages
+//
+// The Python API's ClearField() and Clear() methods behave
+// differently than their C++ counterparts. While the C++ versions
+// clears the children the Python versions detaches the children,
+// without touching their content. This impedance mismatch causes
+// some complexity in the implementation, which is captured in this
+// section.
+//
+// When a CMessage field is cleared we need to:
+//
+// * Release the Message used as the backing store for the CMessage
+// from its parent.
+//
+// * Change the owner field of the released CMessage and all of its
+// children to point to the newly released Message.
+//
+// * Clear the weak references from the released CMessage to the
+// parent.
+//
+// When a RepeatedCompositeContainer field is cleared we need to:
+//
+// * Release all the Message used as the backing store for the
+// CMessages stored in the container.
+//
+// * Change the owner field of all the released CMessage and all of
+// their children to point to the newly released Messages.
+//
+// * Clear the weak references from the released container to the
+// parent.
+
+struct SetOwnerVisitor : public ChildVisitor {
+ // new_owner must outlive this object.
+ explicit SetOwnerVisitor(const shared_ptr<Message>& new_owner)
+ : new_owner_(new_owner) {}
+
+ int VisitRepeatedCompositeContainer(RepeatedCompositeContainer* container) {
+ repeated_composite_container::SetOwner(container, new_owner_);
+ return 0;
+ }
+
+ int VisitRepeatedScalarContainer(RepeatedScalarContainer* container) {
+ repeated_scalar_container::SetOwner(container, new_owner_);
+ return 0;
+ }
+
+ int VisitMapContainer(MapContainer* container) {
+ container->SetOwner(new_owner_);
+ return 0;
+ }
+
+ int VisitCMessage(CMessage* cmessage,
+ const FieldDescriptor* field_descriptor) {
+ return SetOwner(cmessage, new_owner_);
+ }
+
+ private:
+ const shared_ptr<Message>& new_owner_;
+};
+
+// Change the owner of this CMessage and all its children, recursively.
+int SetOwner(CMessage* self, const shared_ptr<Message>& new_owner) {
+ self->owner = new_owner;
+ if (ForEachCompositeField(self, SetOwnerVisitor(new_owner)) == -1)
+ return -1;
+ return 0;
+}
+
+// Releases the message specified by 'field' and returns the
+// pointer. If the field does not exist a new message is created using
+// 'descriptor'. The caller takes ownership of the returned pointer.
+Message* ReleaseMessage(CMessage* self,
+ const Descriptor* descriptor,
+ const FieldDescriptor* field_descriptor) {
+ MessageFactory* message_factory = GetFactoryForMessage(self);
+ Message* released_message = self->message->GetReflection()->ReleaseMessage(
+ self->message, field_descriptor, message_factory);
+ // ReleaseMessage will return NULL which differs from
+ // child_cmessage->message, if the field does not exist. In this case,
+ // the latter points to the default instance via a const_cast<>, so we
+ // have to reset it to a new mutable object since we are taking ownership.
+ if (released_message == NULL) {
+ const Message* prototype = message_factory->GetPrototype(descriptor);
+ GOOGLE_DCHECK(prototype != NULL);
+ released_message = prototype->New();
+ }
+
+ return released_message;
+}
+
+int ReleaseSubMessage(CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ CMessage* child_cmessage) {
+ // Release the Message
+ shared_ptr<Message> released_message(ReleaseMessage(
+ self, child_cmessage->message->GetDescriptor(), field_descriptor));
+ child_cmessage->message = released_message.get();
+ child_cmessage->owner.swap(released_message);
+ child_cmessage->parent = NULL;
+ child_cmessage->parent_field_descriptor = NULL;
+ child_cmessage->read_only = false;
+ return ForEachCompositeField(child_cmessage,
+ SetOwnerVisitor(child_cmessage->owner));
+}
+
+struct ReleaseChild : public ChildVisitor {
+ // message must outlive this object.
+ explicit ReleaseChild(CMessage* parent) :
+ parent_(parent) {}
+
+ int VisitRepeatedCompositeContainer(RepeatedCompositeContainer* container) {
+ return repeated_composite_container::Release(container);
+ }
+
+ int VisitRepeatedScalarContainer(RepeatedScalarContainer* container) {
+ return repeated_scalar_container::Release(container);
+ }
+
+ int VisitMapContainer(MapContainer* container) {
+ return container->Release();
+ }
+
+ int VisitCMessage(CMessage* cmessage,
+ const FieldDescriptor* field_descriptor) {
+ return ReleaseSubMessage(parent_, field_descriptor, cmessage);
+ }
+
+ CMessage* parent_;
+};
+
+int InternalReleaseFieldByDescriptor(
+ CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ PyObject* composite_field) {
+ return VisitCompositeField(
+ field_descriptor,
+ composite_field,
+ ReleaseChild(self));
+}
+
+PyObject* ClearFieldByDescriptor(
+ CMessage* self,
+ const FieldDescriptor* descriptor) {
+ if (!CheckFieldBelongsToMessage(descriptor, self->message)) {
+ return NULL;
+ }
+ AssureWritable(self);
+ self->message->GetReflection()->ClearField(self->message, descriptor);
+ Py_RETURN_NONE;
+}
+
+PyObject* ClearField(CMessage* self, PyObject* arg) {
+ if (!PyString_Check(arg)) {
+ PyErr_SetString(PyExc_TypeError, "field name must be a string");
+ return NULL;
+ }
+#if PY_MAJOR_VERSION < 3
+ const char* field_name = PyString_AS_STRING(arg);
+ Py_ssize_t size = PyString_GET_SIZE(arg);
+#else
+ Py_ssize_t size;
+ const char* field_name = PyUnicode_AsUTF8AndSize(arg, &size);
+#endif
+ AssureWritable(self);
+ Message* message = self->message;
+ ScopedPyObjectPtr arg_in_oneof;
+ bool is_in_oneof;
+ const FieldDescriptor* field_descriptor =
+ FindFieldWithOneofs(message, string(field_name, size), &is_in_oneof);
+ if (field_descriptor == NULL) {
+ if (!is_in_oneof) {
+ PyErr_Format(PyExc_ValueError,
+ "Protocol message has no \"%s\" field.", field_name);
+ return NULL;
+ } else {
+ Py_RETURN_NONE;
+ }
+ } else if (is_in_oneof) {
+ const string& name = field_descriptor->name();
+ arg_in_oneof.reset(PyString_FromStringAndSize(name.c_str(), name.size()));
+ arg = arg_in_oneof.get();
+ }
+
+ PyObject* composite_field = self->composite_fields ?
+ PyDict_GetItem(self->composite_fields, arg) : NULL;
+
+ // Only release the field if there's a possibility that there are
+ // references to it.
+ if (composite_field != NULL) {
+ if (InternalReleaseFieldByDescriptor(self, field_descriptor,
+ composite_field) < 0) {
+ return NULL;
+ }
+ PyDict_DelItem(self->composite_fields, arg);
+ }
+ message->GetReflection()->ClearField(message, field_descriptor);
+ if (field_descriptor->cpp_type() == FieldDescriptor::CPPTYPE_ENUM &&
+ !message->GetReflection()->SupportsUnknownEnumValues()) {
+ UnknownFieldSet* unknown_field_set =
+ message->GetReflection()->MutableUnknownFields(message);
+ unknown_field_set->DeleteByNumber(field_descriptor->number());
+ }
+
+ Py_RETURN_NONE;
+}
+
+PyObject* Clear(CMessage* self) {
+ AssureWritable(self);
+ if (ForEachCompositeField(self, ReleaseChild(self)) == -1)
+ return NULL;
+ Py_CLEAR(self->extensions);
+ if (self->composite_fields) {
+ PyDict_Clear(self->composite_fields);
+ }
+ self->message->Clear();
+ Py_RETURN_NONE;
+}
+
+// ---------------------------------------------------------------------
+
+static string GetMessageName(CMessage* self) {
+ if (self->parent_field_descriptor != NULL) {
+ return self->parent_field_descriptor->full_name();
+ } else {
+ return self->message->GetDescriptor()->full_name();
+ }
+}
+
+static PyObject* SerializeToString(CMessage* self, PyObject* args) {
+ if (!self->message->IsInitialized()) {
+ ScopedPyObjectPtr errors(FindInitializationErrors(self));
+ if (errors == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr comma(PyString_FromString(","));
+ if (comma == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr joined(
+ PyObject_CallMethod(comma.get(), "join", "O", errors.get()));
+ if (joined == NULL) {
+ return NULL;
+ }
+
+ // TODO(haberman): this is a (hopefully temporary) hack. The unit testing
+ // infrastructure reloads all pure-Python modules for every test, but not
+ // C++ modules (because that's generally impossible:
+ // http://bugs.python.org/issue1144263). But if we cache EncodeError, we'll
+ // return the EncodeError from a previous load of the module, which won't
+ // match a user's attempt to catch EncodeError. So we have to look it up
+ // again every time.
+ ScopedPyObjectPtr message_module(PyImport_ImportModule(
+ "google.protobuf.message"));
+ if (message_module.get() == NULL) {
+ return NULL;
+ }
+
+ ScopedPyObjectPtr encode_error(
+ PyObject_GetAttrString(message_module.get(), "EncodeError"));
+ if (encode_error.get() == NULL) {
+ return NULL;
+ }
+ PyErr_Format(encode_error.get(),
+ "Message %s is missing required fields: %s",
+ GetMessageName(self).c_str(), PyString_AsString(joined.get()));
+ return NULL;
+ }
+ int size = self->message->ByteSize();
+ if (size <= 0) {
+ return PyBytes_FromString("");
+ }
+ PyObject* result = PyBytes_FromStringAndSize(NULL, size);
+ if (result == NULL) {
+ return NULL;
+ }
+ char* buffer = PyBytes_AS_STRING(result);
+ self->message->SerializeWithCachedSizesToArray(
+ reinterpret_cast<uint8*>(buffer));
+ return result;
+}
+
+static PyObject* SerializePartialToString(CMessage* self) {
+ string contents;
+ self->message->SerializePartialToString(&contents);
+ return PyBytes_FromStringAndSize(contents.c_str(), contents.size());
+}
+
+// Formats proto fields for ascii dumps using python formatting functions where
+// appropriate.
+class PythonFieldValuePrinter : public TextFormat::FieldValuePrinter {
+ public:
+ // Python has some differences from C++ when printing floating point numbers.
+ //
+ // 1) Trailing .0 is always printed.
+ // 2) (Python2) Output is rounded to 12 digits.
+ // 3) (Python3) The full precision of the double is preserved (and Python uses
+ // David M. Gay's dtoa(), when the C++ code uses SimpleDtoa. There are some
+ // differences, but they rarely happen)
+ //
+ // We override floating point printing with the C-API function for printing
+ // Python floats to ensure consistency.
+ string PrintFloat(float value) const { return PrintDouble(value); }
+ string PrintDouble(double value) const {
+ // This implementation is not highly optimized (it allocates two temporary
+ // Python objects) but it is simple and portable. If this is shown to be a
+ // performance bottleneck, we can optimize it, but the results will likely
+ // be more complicated to accommodate the differing behavior of double
+ // formatting between Python 2 and Python 3.
+ //
+ // (Though a valid question is: do we really want to make out output
+ // dependent on the Python version?)
+ ScopedPyObjectPtr py_value(PyFloat_FromDouble(value));
+ if (!py_value.get()) {
+ return string();
+ }
+
+ ScopedPyObjectPtr py_str(PyObject_Str(py_value.get()));
+ if (!py_str.get()) {
+ return string();
+ }
+
+ return string(PyString_AsString(py_str.get()));
+ }
+};
+
+static PyObject* ToStr(CMessage* self) {
+ TextFormat::Printer printer;
+ // Passes ownership
+ printer.SetDefaultFieldValuePrinter(new PythonFieldValuePrinter());
+ printer.SetHideUnknownFields(true);
+ string output;
+ if (!printer.PrintToString(*self->message, &output)) {
+ PyErr_SetString(PyExc_ValueError, "Unable to convert message to str");
+ return NULL;
+ }
+ return PyString_FromString(output.c_str());
+}
+
+PyObject* MergeFrom(CMessage* self, PyObject* arg) {
+ CMessage* other_message;
+ if (!PyObject_TypeCheck(arg, &CMessage_Type)) {
+ PyErr_Format(PyExc_TypeError,
+ "Parameter to MergeFrom() must be instance of same class: "
+ "expected %s got %s.",
+ self->message->GetDescriptor()->full_name().c_str(),
+ Py_TYPE(arg)->tp_name);
+ return NULL;
+ }
+
+ other_message = reinterpret_cast<CMessage*>(arg);
+ if (other_message->message->GetDescriptor() !=
+ self->message->GetDescriptor()) {
+ PyErr_Format(PyExc_TypeError,
+ "Parameter to MergeFrom() must be instance of same class: "
+ "expected %s got %s.",
+ self->message->GetDescriptor()->full_name().c_str(),
+ other_message->message->GetDescriptor()->full_name().c_str());
+ return NULL;
+ }
+ AssureWritable(self);
+
+ // TODO(tibell): Message::MergeFrom might turn some child Messages
+ // into mutable messages, invalidating the message field in the
+ // corresponding CMessages. We should run a FixupMessageReferences
+ // pass here.
+
+ self->message->MergeFrom(*other_message->message);
+ Py_RETURN_NONE;
+}
+
+static PyObject* CopyFrom(CMessage* self, PyObject* arg) {
+ CMessage* other_message;
+ if (!PyObject_TypeCheck(arg, &CMessage_Type)) {
+ PyErr_Format(PyExc_TypeError,
+ "Parameter to CopyFrom() must be instance of same class: "
+ "expected %s got %s.",
+ self->message->GetDescriptor()->full_name().c_str(),
+ Py_TYPE(arg)->tp_name);
+ return NULL;
+ }
+
+ other_message = reinterpret_cast<CMessage*>(arg);
+
+ if (self == other_message) {
+ Py_RETURN_NONE;
+ }
+
+ if (other_message->message->GetDescriptor() !=
+ self->message->GetDescriptor()) {
+ PyErr_Format(PyExc_TypeError,
+ "Parameter to CopyFrom() must be instance of same class: "
+ "expected %s got %s.",
+ self->message->GetDescriptor()->full_name().c_str(),
+ other_message->message->GetDescriptor()->full_name().c_str());
+ return NULL;
+ }
+
+ AssureWritable(self);
+
+ // CopyFrom on the message will not clean up self->composite_fields,
+ // which can leave us in an inconsistent state, so clear it out here.
+ (void)ScopedPyObjectPtr(Clear(self));
+
+ self->message->CopyFrom(*other_message->message);
+
+ Py_RETURN_NONE;
+}
+
+// Protobuf has a 64MB limit built in, this variable will override this. Please
+// do not enable this unless you fully understand the implications: protobufs
+// must all be kept in memory at the same time, so if they grow too big you may
+// get OOM errors. The protobuf APIs do not provide any tools for processing
+// protobufs in chunks. If you have protos this big you should break them up if
+// it is at all convenient to do so.
+static bool allow_oversize_protos = false;
+
+// Provide a method in the module to set allow_oversize_protos to a boolean
+// value. This method returns the newly value of allow_oversize_protos.
+PyObject* SetAllowOversizeProtos(PyObject* m, PyObject* arg) {
+ if (!arg || !PyBool_Check(arg)) {
+ PyErr_SetString(PyExc_TypeError,
+ "Argument to SetAllowOversizeProtos must be boolean");
+ return NULL;
+ }
+ allow_oversize_protos = PyObject_IsTrue(arg);
+ if (allow_oversize_protos) {
+ Py_RETURN_TRUE;
+ } else {
+ Py_RETURN_FALSE;
+ }
+}
+
+static PyObject* MergeFromString(CMessage* self, PyObject* arg) {
+ const void* data;
+ Py_ssize_t data_length;
+ if (PyObject_AsReadBuffer(arg, &data, &data_length) < 0) {
+ return NULL;
+ }
+
+ AssureWritable(self);
+ io::CodedInputStream input(
+ reinterpret_cast<const uint8*>(data), data_length);
+ if (allow_oversize_protos) {
+ input.SetTotalBytesLimit(INT_MAX, INT_MAX);
+ }
+ PyDescriptorPool* pool = GetDescriptorPoolForMessage(self);
+ input.SetExtensionRegistry(pool->pool, pool->message_factory);
+ bool success = self->message->MergePartialFromCodedStream(&input);
+ if (success) {
+ return PyInt_FromLong(input.CurrentPosition());
+ } else {
+ PyErr_Format(DecodeError_class, "Error parsing message");
+ return NULL;
+ }
+}
+
+static PyObject* ParseFromString(CMessage* self, PyObject* arg) {
+ if (ScopedPyObjectPtr(Clear(self)) == NULL) {
+ return NULL;
+ }
+ return MergeFromString(self, arg);
+}
+
+static PyObject* ByteSize(CMessage* self, PyObject* args) {
+ return PyLong_FromLong(self->message->ByteSize());
+}
+
+static PyObject* RegisterExtension(PyObject* cls,
+ PyObject* extension_handle) {
+ const FieldDescriptor* descriptor =
+ GetExtensionDescriptor(extension_handle);
+ if (descriptor == NULL) {
+ return NULL;
+ }
+
+ ScopedPyObjectPtr extensions_by_name(
+ PyObject_GetAttr(cls, k_extensions_by_name));
+ if (extensions_by_name == NULL) {
+ PyErr_SetString(PyExc_TypeError, "no extensions_by_name on class");
+ return NULL;
+ }
+ ScopedPyObjectPtr full_name(PyObject_GetAttr(extension_handle, kfull_name));
+ if (full_name == NULL) {
+ return NULL;
+ }
+
+ // If the extension was already registered, check that it is the same.
+ PyObject* existing_extension =
+ PyDict_GetItem(extensions_by_name.get(), full_name.get());
+ if (existing_extension != NULL) {
+ const FieldDescriptor* existing_extension_descriptor =
+ GetExtensionDescriptor(existing_extension);
+ if (existing_extension_descriptor != descriptor) {
+ PyErr_SetString(PyExc_ValueError, "Double registration of Extensions");
+ return NULL;
+ }
+ // Nothing else to do.
+ Py_RETURN_NONE;
+ }
+
+ if (PyDict_SetItem(extensions_by_name.get(), full_name.get(),
+ extension_handle) < 0) {
+ return NULL;
+ }
+
+ // Also store a mapping from extension number to implementing class.
+ ScopedPyObjectPtr extensions_by_number(
+ PyObject_GetAttr(cls, k_extensions_by_number));
+ if (extensions_by_number == NULL) {
+ PyErr_SetString(PyExc_TypeError, "no extensions_by_number on class");
+ return NULL;
+ }
+
+ ScopedPyObjectPtr number(PyObject_GetAttrString(extension_handle, "number"));
+ if (number == NULL) {
+ return NULL;
+ }
+
+ // If the extension was already registered by number, check that it is the
+ // same.
+ existing_extension = PyDict_GetItem(extensions_by_number.get(), number.get());
+ if (existing_extension != NULL) {
+ const FieldDescriptor* existing_extension_descriptor =
+ GetExtensionDescriptor(existing_extension);
+ if (existing_extension_descriptor != descriptor) {
+ const Descriptor* msg_desc = GetMessageDescriptor(
+ reinterpret_cast<PyTypeObject*>(cls));
+ PyErr_Format(
+ PyExc_ValueError,
+ "Extensions \"%s\" and \"%s\" both try to extend message type "
+ "\"%s\" with field number %ld.",
+ existing_extension_descriptor->full_name().c_str(),
+ descriptor->full_name().c_str(),
+ msg_desc->full_name().c_str(),
+ PyInt_AsLong(number.get()));
+ return NULL;
+ }
+ // Nothing else to do.
+ Py_RETURN_NONE;
+ }
+ if (PyDict_SetItem(extensions_by_number.get(), number.get(),
+ extension_handle) < 0) {
+ return NULL;
+ }
+
+ // Check if it's a message set
+ if (descriptor->is_extension() &&
+ descriptor->containing_type()->options().message_set_wire_format() &&
+ descriptor->type() == FieldDescriptor::TYPE_MESSAGE &&
+ descriptor->label() == FieldDescriptor::LABEL_OPTIONAL) {
+ ScopedPyObjectPtr message_name(PyString_FromStringAndSize(
+ descriptor->message_type()->full_name().c_str(),
+ descriptor->message_type()->full_name().size()));
+ if (message_name == NULL) {
+ return NULL;
+ }
+ PyDict_SetItem(extensions_by_name.get(), message_name.get(),
+ extension_handle);
+ }
+
+ Py_RETURN_NONE;
+}
+
+static PyObject* SetInParent(CMessage* self, PyObject* args) {
+ AssureWritable(self);
+ Py_RETURN_NONE;
+}
+
+static PyObject* WhichOneof(CMessage* self, PyObject* arg) {
+ Py_ssize_t name_size;
+ char *name_data;
+ if (PyString_AsStringAndSize(arg, &name_data, &name_size) < 0)
+ return NULL;
+ string oneof_name = string(name_data, name_size);
+ const OneofDescriptor* oneof_desc =
+ self->message->GetDescriptor()->FindOneofByName(oneof_name);
+ if (oneof_desc == NULL) {
+ PyErr_Format(PyExc_ValueError,
+ "Protocol message has no oneof \"%s\" field.",
+ oneof_name.c_str());
+ return NULL;
+ }
+ const FieldDescriptor* field_in_oneof =
+ self->message->GetReflection()->GetOneofFieldDescriptor(
+ *self->message, oneof_desc);
+ if (field_in_oneof == NULL) {
+ Py_RETURN_NONE;
+ } else {
+ const string& name = field_in_oneof->name();
+ return PyString_FromStringAndSize(name.c_str(), name.size());
+ }
+}
+
+static PyObject* GetExtensionDict(CMessage* self, void *closure);
+
+static PyObject* ListFields(CMessage* self) {
+ vector<const FieldDescriptor*> fields;
+ self->message->GetReflection()->ListFields(*self->message, &fields);
+
+ // Normally, the list will be exactly the size of the fields.
+ ScopedPyObjectPtr all_fields(PyList_New(fields.size()));
+ if (all_fields == NULL) {
+ return NULL;
+ }
+
+ // When there are unknown extensions, the py list will *not* contain
+ // the field information. Thus the actual size of the py list will be
+ // smaller than the size of fields. Set the actual size at the end.
+ Py_ssize_t actual_size = 0;
+ for (size_t i = 0; i < fields.size(); ++i) {
+ ScopedPyObjectPtr t(PyTuple_New(2));
+ if (t == NULL) {
+ return NULL;
+ }
+
+ if (fields[i]->is_extension()) {
+ ScopedPyObjectPtr extension_field(
+ PyFieldDescriptor_FromDescriptor(fields[i]));
+ if (extension_field == NULL) {
+ return NULL;
+ }
+ // With C++ descriptors, the field can always be retrieved, but for
+ // unknown extensions which have not been imported in Python code, there
+ // is no message class and we cannot retrieve the value.
+ // TODO(amauryfa): consider building the class on the fly!
+ if (fields[i]->message_type() != NULL &&
+ cdescriptor_pool::GetMessageClass(
+ GetDescriptorPoolForMessage(self),
+ fields[i]->message_type()) == NULL) {
+ PyErr_Clear();
+ continue;
+ }
+ ScopedPyObjectPtr extensions(GetExtensionDict(self, NULL));
+ if (extensions == NULL) {
+ return NULL;
+ }
+ // 'extension' reference later stolen by PyTuple_SET_ITEM.
+ PyObject* extension = PyObject_GetItem(
+ extensions.get(), extension_field.get());
+ if (extension == NULL) {
+ return NULL;
+ }
+ PyTuple_SET_ITEM(t.get(), 0, extension_field.release());
+ // Steals reference to 'extension'
+ PyTuple_SET_ITEM(t.get(), 1, extension);
+ } else {
+ // Normal field
+ const string& field_name = fields[i]->name();
+ ScopedPyObjectPtr py_field_name(PyString_FromStringAndSize(
+ field_name.c_str(), field_name.length()));
+ if (py_field_name == NULL) {
+ PyErr_SetString(PyExc_ValueError, "bad string");
+ return NULL;
+ }
+ ScopedPyObjectPtr field_descriptor(
+ PyFieldDescriptor_FromDescriptor(fields[i]));
+ if (field_descriptor == NULL) {
+ return NULL;
+ }
+
+ PyObject* field_value = GetAttr(self, py_field_name.get());
+ if (field_value == NULL) {
+ PyErr_SetObject(PyExc_ValueError, py_field_name.get());
+ return NULL;
+ }
+ PyTuple_SET_ITEM(t.get(), 0, field_descriptor.release());
+ PyTuple_SET_ITEM(t.get(), 1, field_value);
+ }
+ PyList_SET_ITEM(all_fields.get(), actual_size, t.release());
+ ++actual_size;
+ }
+ if (static_cast<size_t>(actual_size) != fields.size() &&
+ (PyList_SetSlice(all_fields.get(), actual_size, fields.size(), NULL) <
+ 0)) {
+ return NULL;
+ }
+ return all_fields.release();
+}
+
+static PyObject* DiscardUnknownFields(CMessage* self) {
+ AssureWritable(self);
+ self->message->DiscardUnknownFields();
+ Py_RETURN_NONE;
+}
+
+PyObject* FindInitializationErrors(CMessage* self) {
+ Message* message = self->message;
+ vector<string> errors;
+ message->FindInitializationErrors(&errors);
+
+ PyObject* error_list = PyList_New(errors.size());
+ if (error_list == NULL) {
+ return NULL;
+ }
+ for (size_t i = 0; i < errors.size(); ++i) {
+ const string& error = errors[i];
+ PyObject* error_string = PyString_FromStringAndSize(
+ error.c_str(), error.length());
+ if (error_string == NULL) {
+ Py_DECREF(error_list);
+ return NULL;
+ }
+ PyList_SET_ITEM(error_list, i, error_string);
+ }
+ return error_list;
+}
+
+static PyObject* RichCompare(CMessage* self, PyObject* other, int opid) {
+ // Only equality comparisons are implemented.
+ if (opid != Py_EQ && opid != Py_NE) {
+ Py_INCREF(Py_NotImplemented);
+ return Py_NotImplemented;
+ }
+ bool equals = true;
+ // If other is not a message, it cannot be equal.
+ if (!PyObject_TypeCheck(other, &CMessage_Type)) {
+ equals = false;
+ }
+ const google::protobuf::Message* other_message =
+ reinterpret_cast<CMessage*>(other)->message;
+ // If messages don't have the same descriptors, they are not equal.
+ if (equals &&
+ self->message->GetDescriptor() != other_message->GetDescriptor()) {
+ equals = false;
+ }
+ // Check the message contents.
+ if (equals && !google::protobuf::util::MessageDifferencer::Equals(
+ *self->message,
+ *reinterpret_cast<CMessage*>(other)->message)) {
+ equals = false;
+ }
+ if (equals ^ (opid == Py_EQ)) {
+ Py_RETURN_FALSE;
+ } else {
+ Py_RETURN_TRUE;
+ }
+}
+
+PyObject* InternalGetScalar(const Message* message,
+ const FieldDescriptor* field_descriptor) {
+ const Reflection* reflection = message->GetReflection();
+
+ if (!CheckFieldBelongsToMessage(field_descriptor, message)) {
+ return NULL;
+ }
+
+ PyObject* result = NULL;
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ int32 value = reflection->GetInt32(*message, field_descriptor);
+ result = PyInt_FromLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ int64 value = reflection->GetInt64(*message, field_descriptor);
+ result = PyLong_FromLongLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ uint32 value = reflection->GetUInt32(*message, field_descriptor);
+ result = PyInt_FromSize_t(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ uint64 value = reflection->GetUInt64(*message, field_descriptor);
+ result = PyLong_FromUnsignedLongLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ float value = reflection->GetFloat(*message, field_descriptor);
+ result = PyFloat_FromDouble(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value = reflection->GetDouble(*message, field_descriptor);
+ result = PyFloat_FromDouble(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ bool value = reflection->GetBool(*message, field_descriptor);
+ result = PyBool_FromLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string value = reflection->GetString(*message, field_descriptor);
+ result = ToStringObject(field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ if (!message->GetReflection()->SupportsUnknownEnumValues() &&
+ !message->GetReflection()->HasField(*message, field_descriptor)) {
+ // Look for the value in the unknown fields.
+ const UnknownFieldSet& unknown_field_set =
+ message->GetReflection()->GetUnknownFields(*message);
+ for (int i = 0; i < unknown_field_set.field_count(); ++i) {
+ if (unknown_field_set.field(i).number() ==
+ field_descriptor->number() &&
+ unknown_field_set.field(i).type() ==
+ google::protobuf::UnknownField::TYPE_VARINT) {
+ result = PyInt_FromLong(unknown_field_set.field(i).varint());
+ break;
+ }
+ }
+ }
+
+ if (result == NULL) {
+ const EnumValueDescriptor* enum_value =
+ message->GetReflection()->GetEnum(*message, field_descriptor);
+ result = PyInt_FromLong(enum_value->number());
+ }
+ break;
+ }
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Getting a value from a field of unknown type %d",
+ field_descriptor->cpp_type());
+ }
+
+ return result;
+}
+
+PyObject* InternalGetSubMessage(
+ CMessage* self, const FieldDescriptor* field_descriptor) {
+ const Reflection* reflection = self->message->GetReflection();
+ PyDescriptorPool* pool = GetDescriptorPoolForMessage(self);
+ const Message& sub_message = reflection->GetMessage(
+ *self->message, field_descriptor, pool->message_factory);
+
+ CMessageClass* message_class = cdescriptor_pool::GetMessageClass(
+ pool, field_descriptor->message_type());
+ if (message_class == NULL) {
+ return NULL;
+ }
+
+ CMessage* cmsg = cmessage::NewEmptyMessage(message_class);
+ if (cmsg == NULL) {
+ return NULL;
+ }
+
+ cmsg->owner = self->owner;
+ cmsg->parent = self;
+ cmsg->parent_field_descriptor = field_descriptor;
+ cmsg->read_only = !reflection->HasField(*self->message, field_descriptor);
+ cmsg->message = const_cast<Message*>(&sub_message);
+
+ return reinterpret_cast<PyObject*>(cmsg);
+}
+
+int InternalSetNonOneofScalar(
+ Message* message,
+ const FieldDescriptor* field_descriptor,
+ PyObject* arg) {
+ const Reflection* reflection = message->GetReflection();
+
+ if (!CheckFieldBelongsToMessage(field_descriptor, message)) {
+ return -1;
+ }
+
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ GOOGLE_CHECK_GET_INT32(arg, value, -1);
+ reflection->SetInt32(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ GOOGLE_CHECK_GET_INT64(arg, value, -1);
+ reflection->SetInt64(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ GOOGLE_CHECK_GET_UINT32(arg, value, -1);
+ reflection->SetUInt32(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ GOOGLE_CHECK_GET_UINT64(arg, value, -1);
+ reflection->SetUInt64(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ GOOGLE_CHECK_GET_FLOAT(arg, value, -1);
+ reflection->SetFloat(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ GOOGLE_CHECK_GET_DOUBLE(arg, value, -1);
+ reflection->SetDouble(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ GOOGLE_CHECK_GET_BOOL(arg, value, -1);
+ reflection->SetBool(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ if (!CheckAndSetString(
+ arg, message, field_descriptor, reflection, false, -1)) {
+ return -1;
+ }
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ GOOGLE_CHECK_GET_INT32(arg, value, -1);
+ if (reflection->SupportsUnknownEnumValues()) {
+ reflection->SetEnumValue(message, field_descriptor, value);
+ } else {
+ const EnumDescriptor* enum_descriptor = field_descriptor->enum_type();
+ const EnumValueDescriptor* enum_value =
+ enum_descriptor->FindValueByNumber(value);
+ if (enum_value != NULL) {
+ reflection->SetEnum(message, field_descriptor, enum_value);
+ } else {
+ PyErr_Format(PyExc_ValueError, "Unknown enum value: %d", value);
+ return -1;
+ }
+ }
+ break;
+ }
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Setting value to a field of unknown type %d",
+ field_descriptor->cpp_type());
+ return -1;
+ }
+
+ return 0;
+}
+
+int InternalSetScalar(
+ CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ PyObject* arg) {
+ if (!CheckFieldBelongsToMessage(field_descriptor, self->message)) {
+ return -1;
+ }
+
+ if (MaybeReleaseOverlappingOneofField(self, field_descriptor) < 0) {
+ return -1;
+ }
+
+ return InternalSetNonOneofScalar(self->message, field_descriptor, arg);
+}
+
+PyObject* FromString(PyTypeObject* cls, PyObject* serialized) {
+ PyObject* py_cmsg = PyObject_CallObject(
+ reinterpret_cast<PyObject*>(cls), NULL);
+ if (py_cmsg == NULL) {
+ return NULL;
+ }
+ CMessage* cmsg = reinterpret_cast<CMessage*>(py_cmsg);
+
+ ScopedPyObjectPtr py_length(MergeFromString(cmsg, serialized));
+ if (py_length == NULL) {
+ Py_DECREF(py_cmsg);
+ return NULL;
+ }
+
+ return py_cmsg;
+}
+
+PyObject* DeepCopy(CMessage* self, PyObject* arg) {
+ PyObject* clone = PyObject_CallObject(
+ reinterpret_cast<PyObject*>(Py_TYPE(self)), NULL);
+ if (clone == NULL) {
+ return NULL;
+ }
+ if (!PyObject_TypeCheck(clone, &CMessage_Type)) {
+ Py_DECREF(clone);
+ return NULL;
+ }
+ if (ScopedPyObjectPtr(MergeFrom(
+ reinterpret_cast<CMessage*>(clone),
+ reinterpret_cast<PyObject*>(self))) == NULL) {
+ Py_DECREF(clone);
+ return NULL;
+ }
+ return clone;
+}
+
+PyObject* ToUnicode(CMessage* self) {
+ // Lazy import to prevent circular dependencies
+ ScopedPyObjectPtr text_format(
+ PyImport_ImportModule("google.protobuf.text_format"));
+ if (text_format == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr method_name(PyString_FromString("MessageToString"));
+ if (method_name == NULL) {
+ return NULL;
+ }
+ Py_INCREF(Py_True);
+ ScopedPyObjectPtr encoded(PyObject_CallMethodObjArgs(
+ text_format.get(), method_name.get(), self, Py_True, NULL));
+ Py_DECREF(Py_True);
+ if (encoded == NULL) {
+ return NULL;
+ }
+#if PY_MAJOR_VERSION < 3
+ PyObject* decoded = PyString_AsDecodedObject(encoded.get(), "utf-8", NULL);
+#else
+ PyObject* decoded = PyUnicode_FromEncodedObject(encoded.get(), "utf-8", NULL);
+#endif
+ if (decoded == NULL) {
+ return NULL;
+ }
+ return decoded;
+}
+
+PyObject* Reduce(CMessage* self) {
+ ScopedPyObjectPtr constructor(reinterpret_cast<PyObject*>(Py_TYPE(self)));
+ constructor.inc();
+ ScopedPyObjectPtr args(PyTuple_New(0));
+ if (args == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr state(PyDict_New());
+ if (state == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr serialized(SerializePartialToString(self));
+ if (serialized == NULL) {
+ return NULL;
+ }
+ if (PyDict_SetItemString(state.get(), "serialized", serialized.get()) < 0) {
+ return NULL;
+ }
+ return Py_BuildValue("OOO", constructor.get(), args.get(), state.get());
+}
+
+PyObject* SetState(CMessage* self, PyObject* state) {
+ if (!PyDict_Check(state)) {
+ PyErr_SetString(PyExc_TypeError, "state not a dict");
+ return NULL;
+ }
+ PyObject* serialized = PyDict_GetItemString(state, "serialized");
+ if (serialized == NULL) {
+ return NULL;
+ }
+ if (ScopedPyObjectPtr(ParseFromString(self, serialized)) == NULL) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+// CMessage static methods:
+PyObject* _CheckCalledFromGeneratedFile(PyObject* unused,
+ PyObject* unused_arg) {
+ if (!_CalledFromGeneratedFile(1)) {
+ PyErr_SetString(PyExc_TypeError,
+ "Descriptors should not be created directly, "
+ "but only retrieved from their parent.");
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+static PyObject* GetExtensionDict(CMessage* self, void *closure) {
+ if (self->extensions) {
+ Py_INCREF(self->extensions);
+ return reinterpret_cast<PyObject*>(self->extensions);
+ }
+
+ // If there are extension_ranges, the message is "extendable". Allocate a
+ // dictionary to store the extension fields.
+ const Descriptor* descriptor = GetMessageDescriptor(Py_TYPE(self));
+ if (descriptor->extension_range_count() > 0) {
+ ExtensionDict* extension_dict = extension_dict::NewExtensionDict(self);
+ if (extension_dict == NULL) {
+ return NULL;
+ }
+ self->extensions = extension_dict;
+ Py_INCREF(self->extensions);
+ return reinterpret_cast<PyObject*>(self->extensions);
+ }
+
+ PyErr_SetNone(PyExc_AttributeError);
+ return NULL;
+}
+
+static PyGetSetDef Getters[] = {
+ {"Extensions", (getter)GetExtensionDict, NULL, "Extension dict"},
+ {NULL}
+};
+
+static PyMethodDef Methods[] = {
+ { "__deepcopy__", (PyCFunction)DeepCopy, METH_VARARGS,
+ "Makes a deep copy of the class." },
+ { "__reduce__", (PyCFunction)Reduce, METH_NOARGS,
+ "Outputs picklable representation of the message." },
+ { "__setstate__", (PyCFunction)SetState, METH_O,
+ "Inputs picklable representation of the message." },
+ { "__unicode__", (PyCFunction)ToUnicode, METH_NOARGS,
+ "Outputs a unicode representation of the message." },
+ { "ByteSize", (PyCFunction)ByteSize, METH_NOARGS,
+ "Returns the size of the message in bytes." },
+ { "Clear", (PyCFunction)Clear, METH_NOARGS,
+ "Clears the message." },
+ { "ClearExtension", (PyCFunction)ClearExtension, METH_O,
+ "Clears a message field." },
+ { "ClearField", (PyCFunction)ClearField, METH_O,
+ "Clears a message field." },
+ { "CopyFrom", (PyCFunction)CopyFrom, METH_O,
+ "Copies a protocol message into the current message." },
+ { "DiscardUnknownFields", (PyCFunction)DiscardUnknownFields, METH_NOARGS,
+ "Discards the unknown fields." },
+ { "FindInitializationErrors", (PyCFunction)FindInitializationErrors,
+ METH_NOARGS,
+ "Finds unset required fields." },
+ { "FromString", (PyCFunction)FromString, METH_O | METH_CLASS,
+ "Creates new method instance from given serialized data." },
+ { "HasExtension", (PyCFunction)HasExtension, METH_O,
+ "Checks if a message field is set." },
+ { "HasField", (PyCFunction)HasField, METH_O,
+ "Checks if a message field is set." },
+ { "IsInitialized", (PyCFunction)IsInitialized, METH_VARARGS,
+ "Checks if all required fields of a protocol message are set." },
+ { "ListFields", (PyCFunction)ListFields, METH_NOARGS,
+ "Lists all set fields of a message." },
+ { "MergeFrom", (PyCFunction)MergeFrom, METH_O,
+ "Merges a protocol message into the current message." },
+ { "MergeFromString", (PyCFunction)MergeFromString, METH_O,
+ "Merges a serialized message into the current message." },
+ { "ParseFromString", (PyCFunction)ParseFromString, METH_O,
+ "Parses a serialized message into the current message." },
+ { "RegisterExtension", (PyCFunction)RegisterExtension, METH_O | METH_CLASS,
+ "Registers an extension with the current message." },
+ { "SerializePartialToString", (PyCFunction)SerializePartialToString,
+ METH_NOARGS,
+ "Serializes the message to a string, even if it isn't initialized." },
+ { "SerializeToString", (PyCFunction)SerializeToString, METH_NOARGS,
+ "Serializes the message to a string, only for initialized messages." },
+ { "SetInParent", (PyCFunction)SetInParent, METH_NOARGS,
+ "Sets the has bit of the given field in its parent message." },
+ { "WhichOneof", (PyCFunction)WhichOneof, METH_O,
+ "Returns the name of the field set inside a oneof, "
+ "or None if no field is set." },
+
+ // Static Methods.
+ { "_CheckCalledFromGeneratedFile", (PyCFunction)_CheckCalledFromGeneratedFile,
+ METH_NOARGS | METH_STATIC,
+ "Raises TypeError if the caller is not in a _pb2.py file."},
+ { NULL, NULL}
+};
+
+static bool SetCompositeField(
+ CMessage* self, PyObject* name, PyObject* value) {
+ if (self->composite_fields == NULL) {
+ self->composite_fields = PyDict_New();
+ if (self->composite_fields == NULL) {
+ return false;
+ }
+ }
+ return PyDict_SetItem(self->composite_fields, name, value) == 0;
+}
+
+PyObject* GetAttr(CMessage* self, PyObject* name) {
+ PyObject* value = self->composite_fields ?
+ PyDict_GetItem(self->composite_fields, name) : NULL;
+ if (value != NULL) {
+ Py_INCREF(value);
+ return value;
+ }
+
+ const FieldDescriptor* field_descriptor = GetFieldDescriptor(self, name);
+ if (field_descriptor == NULL) {
+ return CMessage_Type.tp_base->tp_getattro(
+ reinterpret_cast<PyObject*>(self), name);
+ }
+
+ if (field_descriptor->is_map()) {
+ PyObject* py_container = NULL;
+ const Descriptor* entry_type = field_descriptor->message_type();
+ const FieldDescriptor* value_type = entry_type->FindFieldByName("value");
+ if (value_type->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ CMessageClass* value_class = cdescriptor_pool::GetMessageClass(
+ GetDescriptorPoolForMessage(self), value_type->message_type());
+ if (value_class == NULL) {
+ return NULL;
+ }
+ py_container =
+ NewMessageMapContainer(self, field_descriptor, value_class);
+ } else {
+ py_container = NewScalarMapContainer(self, field_descriptor);
+ }
+ if (py_container == NULL) {
+ return NULL;
+ }
+ if (!SetCompositeField(self, name, py_container)) {
+ Py_DECREF(py_container);
+ return NULL;
+ }
+ return py_container;
+ }
+
+ if (field_descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ PyObject* py_container = NULL;
+ if (field_descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ CMessageClass* message_class = cdescriptor_pool::GetMessageClass(
+ GetDescriptorPoolForMessage(self), field_descriptor->message_type());
+ if (message_class == NULL) {
+ return NULL;
+ }
+ py_container = repeated_composite_container::NewContainer(
+ self, field_descriptor, message_class);
+ } else {
+ py_container = repeated_scalar_container::NewContainer(
+ self, field_descriptor);
+ }
+ if (py_container == NULL) {
+ return NULL;
+ }
+ if (!SetCompositeField(self, name, py_container)) {
+ Py_DECREF(py_container);
+ return NULL;
+ }
+ return py_container;
+ }
+
+ if (field_descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ PyObject* sub_message = InternalGetSubMessage(self, field_descriptor);
+ if (sub_message == NULL) {
+ return NULL;
+ }
+ if (!SetCompositeField(self, name, sub_message)) {
+ Py_DECREF(sub_message);
+ return NULL;
+ }
+ return sub_message;
+ }
+
+ return InternalGetScalar(self->message, field_descriptor);
+}
+
+int SetAttr(CMessage* self, PyObject* name, PyObject* value) {
+ if (self->composite_fields && PyDict_Contains(self->composite_fields, name)) {
+ PyErr_SetString(PyExc_TypeError, "Can't set composite field");
+ return -1;
+ }
+
+ const FieldDescriptor* field_descriptor = GetFieldDescriptor(self, name);
+ if (field_descriptor != NULL) {
+ AssureWritable(self);
+ if (field_descriptor->label() == FieldDescriptor::LABEL_REPEATED) {
+ PyErr_Format(PyExc_AttributeError, "Assignment not allowed to repeated "
+ "field \"%s\" in protocol message object.",
+ field_descriptor->name().c_str());
+ return -1;
+ } else {
+ if (field_descriptor->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ PyErr_Format(PyExc_AttributeError, "Assignment not allowed to "
+ "field \"%s\" in protocol message object.",
+ field_descriptor->name().c_str());
+ return -1;
+ } else {
+ return InternalSetScalar(self, field_descriptor, value);
+ }
+ }
+ }
+
+ PyErr_Format(PyExc_AttributeError,
+ "Assignment not allowed "
+ "(no field \"%s\" in protocol message object).",
+ PyString_AsString(name));
+ return -1;
+}
+
+} // namespace cmessage
+
+PyTypeObject CMessage_Type = {
+ PyVarObject_HEAD_INIT(&CMessageClass_Type, 0)
+ FULL_MODULE_NAME ".CMessage", // tp_name
+ sizeof(CMessage), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)cmessage::Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ (reprfunc)cmessage::ToStr, // tp_repr
+ 0, // tp_as_number
+ 0, // tp_as_sequence
+ 0, // tp_as_mapping
+ PyObject_HashNotImplemented, // tp_hash
+ 0, // tp_call
+ (reprfunc)cmessage::ToStr, // tp_str
+ (getattrofunc)cmessage::GetAttr, // tp_getattro
+ (setattrofunc)cmessage::SetAttr, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, // tp_flags
+ "A ProtocolMessage", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ (richcmpfunc)cmessage::RichCompare, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ cmessage::Methods, // tp_methods
+ 0, // tp_members
+ cmessage::Getters, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ (initproc)cmessage::Init, // tp_init
+ 0, // tp_alloc
+ cmessage::New, // tp_new
+};
+
+// --- Exposing the C proto living inside Python proto to C code:
+
+const Message* (*GetCProtoInsidePyProtoPtr)(PyObject* msg);
+Message* (*MutableCProtoInsidePyProtoPtr)(PyObject* msg);
+
+static const Message* GetCProtoInsidePyProtoImpl(PyObject* msg) {
+ if (!PyObject_TypeCheck(msg, &CMessage_Type)) {
+ return NULL;
+ }
+ CMessage* cmsg = reinterpret_cast<CMessage*>(msg);
+ return cmsg->message;
+}
+
+static Message* MutableCProtoInsidePyProtoImpl(PyObject* msg) {
+ if (!PyObject_TypeCheck(msg, &CMessage_Type)) {
+ return NULL;
+ }
+ CMessage* cmsg = reinterpret_cast<CMessage*>(msg);
+ if ((cmsg->composite_fields && PyDict_Size(cmsg->composite_fields) != 0) ||
+ (cmsg->extensions != NULL &&
+ PyDict_Size(cmsg->extensions->values) != 0)) {
+ // There is currently no way of accurately syncing arbitrary changes to
+ // the underlying C++ message back to the CMessage (e.g. removed repeated
+ // composite containers). We only allow direct mutation of the underlying
+ // C++ message if there is no child data in the CMessage.
+ return NULL;
+ }
+ cmessage::AssureWritable(cmsg);
+ return cmsg->message;
+}
+
+static const char module_docstring[] =
+"python-proto2 is a module that can be used to enhance proto2 Python API\n"
+"performance.\n"
+"\n"
+"It provides access to the protocol buffers C++ reflection API that\n"
+"implements the basic protocol buffer functions.";
+
+void InitGlobals() {
+ // TODO(gps): Check all return values in this function for NULL and propagate
+ // the error (MemoryError) on up to result in an import failure. These should
+ // also be freed and reset to NULL during finalization.
+ kPythonZero = PyInt_FromLong(0);
+ kint32min_py = PyInt_FromLong(kint32min);
+ kint32max_py = PyInt_FromLong(kint32max);
+ kuint32max_py = PyLong_FromLongLong(kuint32max);
+ kint64min_py = PyLong_FromLongLong(kint64min);
+ kint64max_py = PyLong_FromLongLong(kint64max);
+ kuint64max_py = PyLong_FromUnsignedLongLong(kuint64max);
+
+ kDESCRIPTOR = PyString_FromString("DESCRIPTOR");
+ k_cdescriptor = PyString_FromString("_cdescriptor");
+ kfull_name = PyString_FromString("full_name");
+ k_extensions_by_name = PyString_FromString("_extensions_by_name");
+ k_extensions_by_number = PyString_FromString("_extensions_by_number");
+
+ PyObject *dummy_obj = PySet_New(NULL);
+ kEmptyWeakref = PyWeakref_NewRef(dummy_obj, NULL);
+ Py_DECREF(dummy_obj);
+}
+
+bool InitProto2MessageModule(PyObject *m) {
+ // Initialize types and globals in descriptor.cc
+ if (!InitDescriptor()) {
+ return false;
+ }
+
+ // Initialize types and globals in descriptor_pool.cc
+ if (!InitDescriptorPool()) {
+ return false;
+ }
+
+ // Initialize constants defined in this file.
+ InitGlobals();
+
+ CMessageClass_Type.tp_base = &PyType_Type;
+ if (PyType_Ready(&CMessageClass_Type) < 0) {
+ return false;
+ }
+ PyModule_AddObject(m, "MessageMeta",
+ reinterpret_cast<PyObject*>(&CMessageClass_Type));
+
+ if (PyType_Ready(&CMessage_Type) < 0) {
+ return false;
+ }
+
+ // DESCRIPTOR is set on each protocol buffer message class elsewhere, but set
+ // it here as well to document that subclasses need to set it.
+ PyDict_SetItem(CMessage_Type.tp_dict, kDESCRIPTOR, Py_None);
+ // Subclasses with message extensions will override _extensions_by_name and
+ // _extensions_by_number with fresh mutable dictionaries in AddDescriptors.
+ // All other classes can share this same immutable mapping.
+ ScopedPyObjectPtr empty_dict(PyDict_New());
+ if (empty_dict == NULL) {
+ return false;
+ }
+ ScopedPyObjectPtr immutable_dict(PyDictProxy_New(empty_dict.get()));
+ if (immutable_dict == NULL) {
+ return false;
+ }
+ if (PyDict_SetItem(CMessage_Type.tp_dict,
+ k_extensions_by_name, immutable_dict.get()) < 0) {
+ return false;
+ }
+ if (PyDict_SetItem(CMessage_Type.tp_dict,
+ k_extensions_by_number, immutable_dict.get()) < 0) {
+ return false;
+ }
+
+ PyModule_AddObject(m, "Message", reinterpret_cast<PyObject*>(&CMessage_Type));
+
+ // Initialize Repeated container types.
+ {
+ if (PyType_Ready(&RepeatedScalarContainer_Type) < 0) {
+ return false;
+ }
+
+ PyModule_AddObject(m, "RepeatedScalarContainer",
+ reinterpret_cast<PyObject*>(
+ &RepeatedScalarContainer_Type));
+
+ if (PyType_Ready(&RepeatedCompositeContainer_Type) < 0) {
+ return false;
+ }
+
+ PyModule_AddObject(
+ m, "RepeatedCompositeContainer",
+ reinterpret_cast<PyObject*>(
+ &RepeatedCompositeContainer_Type));
+
+ // Register them as collections.Sequence
+ ScopedPyObjectPtr collections(PyImport_ImportModule("collections"));
+ if (collections == NULL) {
+ return false;
+ }
+ ScopedPyObjectPtr mutable_sequence(
+ PyObject_GetAttrString(collections.get(), "MutableSequence"));
+ if (mutable_sequence == NULL) {
+ return false;
+ }
+ if (ScopedPyObjectPtr(
+ PyObject_CallMethod(mutable_sequence.get(), "register", "O",
+ &RepeatedScalarContainer_Type)) == NULL) {
+ return false;
+ }
+ if (ScopedPyObjectPtr(
+ PyObject_CallMethod(mutable_sequence.get(), "register", "O",
+ &RepeatedCompositeContainer_Type)) == NULL) {
+ return false;
+ }
+ }
+
+ // Initialize Map container types.
+ {
+ // ScalarMapContainer_Type derives from our MutableMapping type.
+ ScopedPyObjectPtr containers(PyImport_ImportModule(
+ "google.protobuf.internal.containers"));
+ if (containers == NULL) {
+ return false;
+ }
+
+ ScopedPyObjectPtr mutable_mapping(
+ PyObject_GetAttrString(containers.get(), "MutableMapping"));
+ if (mutable_mapping == NULL) {
+ return false;
+ }
+
+ if (!PyObject_TypeCheck(mutable_mapping.get(), &PyType_Type)) {
+ return false;
+ }
+
+ Py_INCREF(mutable_mapping.get());
+#if PY_MAJOR_VERSION >= 3
+ PyObject* bases = PyTuple_New(1);
+ PyTuple_SET_ITEM(bases, 0, mutable_mapping.get());
+
+ ScalarMapContainer_Type =
+ PyType_FromSpecWithBases(&ScalarMapContainer_Type_spec, bases);
+ PyModule_AddObject(m, "ScalarMapContainer", ScalarMapContainer_Type);
+#else
+ ScalarMapContainer_Type.tp_base =
+ reinterpret_cast<PyTypeObject*>(mutable_mapping.get());
+
+ if (PyType_Ready(&ScalarMapContainer_Type) < 0) {
+ return false;
+ }
+
+ PyModule_AddObject(m, "ScalarMapContainer",
+ reinterpret_cast<PyObject*>(&ScalarMapContainer_Type));
+#endif
+
+ if (PyType_Ready(&MapIterator_Type) < 0) {
+ return false;
+ }
+
+ PyModule_AddObject(m, "MapIterator",
+ reinterpret_cast<PyObject*>(&MapIterator_Type));
+
+
+#if PY_MAJOR_VERSION >= 3
+ MessageMapContainer_Type =
+ PyType_FromSpecWithBases(&MessageMapContainer_Type_spec, bases);
+ PyModule_AddObject(m, "MessageMapContainer", MessageMapContainer_Type);
+#else
+ Py_INCREF(mutable_mapping.get());
+ MessageMapContainer_Type.tp_base =
+ reinterpret_cast<PyTypeObject*>(mutable_mapping.get());
+
+ if (PyType_Ready(&MessageMapContainer_Type) < 0) {
+ return false;
+ }
+
+ PyModule_AddObject(m, "MessageMapContainer",
+ reinterpret_cast<PyObject*>(&MessageMapContainer_Type));
+#endif
+ }
+
+ if (PyType_Ready(&ExtensionDict_Type) < 0) {
+ return false;
+ }
+ PyModule_AddObject(
+ m, "ExtensionDict",
+ reinterpret_cast<PyObject*>(&ExtensionDict_Type));
+
+ // Expose the DescriptorPool used to hold all descriptors added from generated
+ // pb2.py files.
+ // PyModule_AddObject steals a reference.
+ Py_INCREF(GetDefaultDescriptorPool());
+ PyModule_AddObject(m, "default_pool",
+ reinterpret_cast<PyObject*>(GetDefaultDescriptorPool()));
+
+ PyModule_AddObject(m, "DescriptorPool", reinterpret_cast<PyObject*>(
+ &PyDescriptorPool_Type));
+
+ // This implementation provides full Descriptor types, we advertise it so that
+ // descriptor.py can use them in replacement of the Python classes.
+ PyModule_AddIntConstant(m, "_USE_C_DESCRIPTORS", 1);
+
+ PyModule_AddObject(m, "Descriptor", reinterpret_cast<PyObject*>(
+ &PyMessageDescriptor_Type));
+ PyModule_AddObject(m, "FieldDescriptor", reinterpret_cast<PyObject*>(
+ &PyFieldDescriptor_Type));
+ PyModule_AddObject(m, "EnumDescriptor", reinterpret_cast<PyObject*>(
+ &PyEnumDescriptor_Type));
+ PyModule_AddObject(m, "EnumValueDescriptor", reinterpret_cast<PyObject*>(
+ &PyEnumValueDescriptor_Type));
+ PyModule_AddObject(m, "FileDescriptor", reinterpret_cast<PyObject*>(
+ &PyFileDescriptor_Type));
+ PyModule_AddObject(m, "OneofDescriptor", reinterpret_cast<PyObject*>(
+ &PyOneofDescriptor_Type));
+ PyModule_AddObject(m, "ServiceDescriptor", reinterpret_cast<PyObject*>(
+ &PyServiceDescriptor_Type));
+ PyModule_AddObject(m, "MethodDescriptor", reinterpret_cast<PyObject*>(
+ &PyMethodDescriptor_Type));
+
+ PyObject* enum_type_wrapper = PyImport_ImportModule(
+ "google.protobuf.internal.enum_type_wrapper");
+ if (enum_type_wrapper == NULL) {
+ return false;
+ }
+ EnumTypeWrapper_class =
+ PyObject_GetAttrString(enum_type_wrapper, "EnumTypeWrapper");
+ Py_DECREF(enum_type_wrapper);
+
+ PyObject* message_module = PyImport_ImportModule(
+ "google.protobuf.message");
+ if (message_module == NULL) {
+ return false;
+ }
+ EncodeError_class = PyObject_GetAttrString(message_module, "EncodeError");
+ DecodeError_class = PyObject_GetAttrString(message_module, "DecodeError");
+ PythonMessage_class = PyObject_GetAttrString(message_module, "Message");
+ Py_DECREF(message_module);
+
+ PyObject* pickle_module = PyImport_ImportModule("pickle");
+ if (pickle_module == NULL) {
+ return false;
+ }
+ PickleError_class = PyObject_GetAttrString(pickle_module, "PickleError");
+ Py_DECREF(pickle_module);
+
+ // Override {Get,Mutable}CProtoInsidePyProto.
+ GetCProtoInsidePyProtoPtr = GetCProtoInsidePyProtoImpl;
+ MutableCProtoInsidePyProtoPtr = MutableCProtoInsidePyProtoImpl;
+
+ return true;
+}
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.h
new file mode 100644
index 0000000000..c44a2ae2b7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message.h
@@ -0,0 +1,367 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_MESSAGE_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_MESSAGE_H__
+
+#include <Python.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+
+namespace google {
+namespace protobuf {
+
+class Message;
+class Reflection;
+class FieldDescriptor;
+class Descriptor;
+class DescriptorPool;
+class MessageFactory;
+
+#ifdef _SHARED_PTR_H
+using std::shared_ptr;
+using std::string;
+#else
+using internal::shared_ptr;
+#endif
+
+namespace python {
+
+struct ExtensionDict;
+struct PyDescriptorPool;
+
+typedef struct CMessage {
+ PyObject_HEAD;
+
+ // This is the top-level C++ Message object that owns the whole
+ // proto tree. Every Python CMessage holds a reference to it in
+ // order to keep it alive as long as there's a Python object that
+ // references any part of the tree.
+ shared_ptr<Message> owner;
+
+ // Weak reference to a parent CMessage object. This is NULL for any top-level
+ // message and is set for any child message (i.e. a child submessage or a
+ // part of a repeated composite field).
+ //
+ // Used to make sure all ancestors are also mutable when first modifying
+ // a child submessage (in other words, turning a default message instance
+ // into a mutable one).
+ //
+ // If a submessage is released (becomes a new top-level message), this field
+ // MUST be set to NULL. The parent may get deallocated and further attempts
+ // to use this pointer will result in a crash.
+ struct CMessage* parent;
+
+ // Pointer to the parent's descriptor that describes this submessage.
+ // Used together with the parent's message when making a default message
+ // instance mutable.
+ // The pointer is owned by the global DescriptorPool.
+ const FieldDescriptor* parent_field_descriptor;
+
+ // Pointer to the C++ Message object for this CMessage. The
+ // CMessage does not own this pointer.
+ Message* message;
+
+ // Indicates this submessage is pointing to a default instance of a message.
+ // Submessages are always first created as read only messages and are then
+ // made writable, at which point this field is set to false.
+ bool read_only;
+
+ // A reference to a Python dictionary containing CMessage,
+ // RepeatedCompositeContainer, and RepeatedScalarContainer
+ // objects. Used as a cache to make sure we don't have to make a
+ // Python wrapper for the C++ Message objects on every access, or
+ // deal with the synchronization nightmare that could create.
+ PyObject* composite_fields;
+
+ // A reference to the dictionary containing the message's extensions.
+ // Similar to composite_fields, acting as a cache, but also contains the
+ // required extension dict logic.
+ ExtensionDict* extensions;
+} CMessage;
+
+extern PyTypeObject CMessage_Type;
+
+
+// The (meta) type of all Messages classes.
+// It allows us to cache some C++ pointers in the class object itself, they are
+// faster to extract than from the type's dictionary.
+
+struct CMessageClass {
+ // This is how CPython subclasses C structures: the base structure must be
+ // the first member of the object.
+ PyHeapTypeObject super;
+
+ // C++ descriptor of this message.
+ const Descriptor* message_descriptor;
+
+ // Owned reference, used to keep the pointer above alive.
+ PyObject* py_message_descriptor;
+
+ // The Python DescriptorPool used to create the class. It is needed to resolve
+ // fields descriptors, including extensions fields; its C++ MessageFactory is
+ // used to instantiate submessages.
+ // This can be different from DESCRIPTOR.file.pool, in the case of a custom
+ // DescriptorPool which defines new extensions.
+ // We own the reference, because it's important to keep the descriptors and
+ // factory alive.
+ PyDescriptorPool* py_descriptor_pool;
+
+ PyObject* AsPyObject() {
+ return reinterpret_cast<PyObject*>(this);
+ }
+};
+
+
+namespace cmessage {
+
+// Internal function to create a new empty Message Python object, but with empty
+// pointers to the C++ objects.
+// The caller must fill self->message, self->owner and eventually self->parent.
+CMessage* NewEmptyMessage(CMessageClass* type);
+
+// Release a submessage from its proto tree, making it a new top-level messgae.
+// A new message will be created if this is a read-only default instance.
+//
+// Corresponds to reflection api method ReleaseMessage.
+int ReleaseSubMessage(CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ CMessage* child_cmessage);
+
+// Retrieves the C++ descriptor of a Python Extension descriptor.
+// On error, return NULL with an exception set.
+const FieldDescriptor* GetExtensionDescriptor(PyObject* extension);
+
+// Initializes a new CMessage instance for a submessage. Only called once per
+// submessage as the result is cached in composite_fields.
+//
+// Corresponds to reflection api method GetMessage.
+PyObject* InternalGetSubMessage(
+ CMessage* self, const FieldDescriptor* field_descriptor);
+
+// Deletes a range of C++ submessages in a repeated field (following a
+// removal in a RepeatedCompositeContainer).
+//
+// Releases messages to the provided cmessage_list if it is not NULL rather
+// than just removing them from the underlying proto. This cmessage_list must
+// have a CMessage for each underlying submessage. The CMessages referred to
+// by slice will be removed from cmessage_list by this function.
+//
+// Corresponds to reflection api method RemoveLast.
+int InternalDeleteRepeatedField(CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ PyObject* slice, PyObject* cmessage_list);
+
+// Sets the specified scalar value to the message.
+int InternalSetScalar(CMessage* self,
+ const FieldDescriptor* field_descriptor,
+ PyObject* value);
+
+// Sets the specified scalar value to the message. Requires it is not a Oneof.
+int InternalSetNonOneofScalar(Message* message,
+ const FieldDescriptor* field_descriptor,
+ PyObject* arg);
+
+// Retrieves the specified scalar value from the message.
+//
+// Returns a new python reference.
+PyObject* InternalGetScalar(const Message* message,
+ const FieldDescriptor* field_descriptor);
+
+// Clears the message, removing all contained data. Extension dictionary and
+// submessages are released first if there are remaining external references.
+//
+// Corresponds to message api method Clear.
+PyObject* Clear(CMessage* self);
+
+// Clears the data described by the given descriptor. Used to clear extensions
+// (which don't have names). Extension release is handled by ExtensionDict
+// class, not this function.
+// TODO(anuraag): Try to make this discrepancy in release semantics with
+// ClearField less confusing.
+//
+// Corresponds to reflection api method ClearField.
+PyObject* ClearFieldByDescriptor(
+ CMessage* self, const FieldDescriptor* descriptor);
+
+// Clears the data for the given field name. The message is released if there
+// are any external references.
+//
+// Corresponds to reflection api method ClearField.
+PyObject* ClearField(CMessage* self, PyObject* arg);
+
+// Checks if the message has the field described by the descriptor. Used for
+// extensions (which have no name).
+//
+// Corresponds to reflection api method HasField
+PyObject* HasFieldByDescriptor(
+ CMessage* self, const FieldDescriptor* field_descriptor);
+
+// Checks if the message has the named field.
+//
+// Corresponds to reflection api method HasField.
+PyObject* HasField(CMessage* self, PyObject* arg);
+
+// Initializes values of fields on a newly constructed message.
+// Note that positional arguments are disallowed: 'args' must be NULL or the
+// empty tuple.
+int InitAttributes(CMessage* self, PyObject* args, PyObject* kwargs);
+
+PyObject* MergeFrom(CMessage* self, PyObject* arg);
+
+// Retrieves an attribute named 'name' from CMessage 'self'. Returns
+// the attribute value on success, or NULL on failure.
+//
+// Returns a new reference.
+PyObject* GetAttr(CMessage* self, PyObject* name);
+
+// Set the value of the attribute named 'name', for CMessage 'self',
+// to the value 'value'. Returns -1 on failure.
+int SetAttr(CMessage* self, PyObject* name, PyObject* value);
+
+PyObject* FindInitializationErrors(CMessage* self);
+
+// Set the owner field of self and any children of self, recursively.
+// Used when self is being released and thus has a new owner (the
+// released Message.)
+int SetOwner(CMessage* self, const shared_ptr<Message>& new_owner);
+
+int AssureWritable(CMessage* self);
+
+// Returns the "best" DescriptorPool for the given message.
+// This is often equivalent to message.DESCRIPTOR.pool, but not always, when
+// the message class was created from a MessageFactory using a custom pool which
+// uses the generated pool as an underlay.
+//
+// The returned pool is suitable for finding fields and building submessages,
+// even in the case of extensions.
+PyDescriptorPool* GetDescriptorPoolForMessage(CMessage* message);
+
+PyObject* SetAllowOversizeProtos(PyObject* m, PyObject* arg);
+
+} // namespace cmessage
+
+
+/* Is 64bit */
+#define IS_64BIT (SIZEOF_LONG == 8)
+
+#define FIELD_IS_REPEATED(field_descriptor) \
+ ((field_descriptor)->label() == FieldDescriptor::LABEL_REPEATED)
+
+#define GOOGLE_CHECK_GET_INT32(arg, value, err) \
+ int32 value; \
+ if (!CheckAndGetInteger(arg, &value, kint32min_py, kint32max_py)) { \
+ return err; \
+ }
+
+#define GOOGLE_CHECK_GET_INT64(arg, value, err) \
+ int64 value; \
+ if (!CheckAndGetInteger(arg, &value, kint64min_py, kint64max_py)) { \
+ return err; \
+ }
+
+#define GOOGLE_CHECK_GET_UINT32(arg, value, err) \
+ uint32 value; \
+ if (!CheckAndGetInteger(arg, &value, kPythonZero, kuint32max_py)) { \
+ return err; \
+ }
+
+#define GOOGLE_CHECK_GET_UINT64(arg, value, err) \
+ uint64 value; \
+ if (!CheckAndGetInteger(arg, &value, kPythonZero, kuint64max_py)) { \
+ return err; \
+ }
+
+#define GOOGLE_CHECK_GET_FLOAT(arg, value, err) \
+ float value; \
+ if (!CheckAndGetFloat(arg, &value)) { \
+ return err; \
+ } \
+
+#define GOOGLE_CHECK_GET_DOUBLE(arg, value, err) \
+ double value; \
+ if (!CheckAndGetDouble(arg, &value)) { \
+ return err; \
+ }
+
+#define GOOGLE_CHECK_GET_BOOL(arg, value, err) \
+ bool value; \
+ if (!CheckAndGetBool(arg, &value)) { \
+ return err; \
+ }
+
+
+extern PyObject* kPythonZero;
+extern PyObject* kint32min_py;
+extern PyObject* kint32max_py;
+extern PyObject* kuint32max_py;
+extern PyObject* kint64min_py;
+extern PyObject* kint64max_py;
+extern PyObject* kuint64max_py;
+
+#define FULL_MODULE_NAME "google.protobuf.pyext._message"
+
+void FormatTypeError(PyObject* arg, char* expected_types);
+template<class T>
+bool CheckAndGetInteger(
+ PyObject* arg, T* value, PyObject* min, PyObject* max);
+bool CheckAndGetDouble(PyObject* arg, double* value);
+bool CheckAndGetFloat(PyObject* arg, float* value);
+bool CheckAndGetBool(PyObject* arg, bool* value);
+PyObject* CheckString(PyObject* arg, const FieldDescriptor* descriptor);
+bool CheckAndSetString(
+ PyObject* arg, Message* message,
+ const FieldDescriptor* descriptor,
+ const Reflection* reflection,
+ bool append,
+ int index);
+PyObject* ToStringObject(const FieldDescriptor* descriptor, string value);
+
+// Check if the passed field descriptor belongs to the given message.
+// If not, return false and set a Python exception (a KeyError)
+bool CheckFieldBelongsToMessage(const FieldDescriptor* field_descriptor,
+ const Message* message);
+
+extern PyObject* PickleError_class;
+
+bool InitProto2MessageModule(PyObject *m);
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message_module.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message_module.cc
new file mode 100644
index 0000000000..d90d9de35a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/message_module.cc
@@ -0,0 +1,88 @@
+// 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.
+
+#include <google/protobuf/pyext/message.h>
+
+static const char module_docstring[] =
+"python-proto2 is a module that can be used to enhance proto2 Python API\n"
+"performance.\n"
+"\n"
+"It provides access to the protocol buffers C++ reflection API that\n"
+"implements the basic protocol buffer functions.";
+
+static PyMethodDef ModuleMethods[] = {
+ {"SetAllowOversizeProtos",
+ (PyCFunction)google::protobuf::python::cmessage::SetAllowOversizeProtos,
+ METH_O, "Enable/disable oversize proto parsing."},
+ { NULL, NULL}
+};
+
+#if PY_MAJOR_VERSION >= 3
+static struct PyModuleDef _module = {
+ PyModuleDef_HEAD_INIT,
+ "_message",
+ module_docstring,
+ -1,
+ ModuleMethods, /* m_methods */
+ NULL,
+ NULL,
+ NULL,
+ NULL
+};
+#define INITFUNC PyInit__message
+#define INITFUNC_ERRORVAL NULL
+#else // Python 2
+#define INITFUNC init_message
+#define INITFUNC_ERRORVAL
+#endif
+
+extern "C" {
+ PyMODINIT_FUNC INITFUNC(void) {
+ PyObject* m;
+#if PY_MAJOR_VERSION >= 3
+ m = PyModule_Create(&_module);
+#else
+ m = Py_InitModule3("_message", ModuleMethods,
+ module_docstring);
+#endif
+ if (m == NULL) {
+ return INITFUNC_ERRORVAL;
+ }
+
+ if (!google::protobuf::python::InitProto2MessageModule(m)) {
+ Py_DECREF(m);
+ return INITFUNC_ERRORVAL;
+ }
+
+#if PY_MAJOR_VERSION >= 3
+ return m;
+#endif
+ }
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/proto2_api_test.proto b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/proto2_api_test.proto
new file mode 100644
index 0000000000..18aecfb7d6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/proto2_api_test.proto
@@ -0,0 +1,40 @@
+// 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.
+
+syntax = "proto2";
+
+import "google/protobuf/internal/cpp/proto1_api_test.proto";
+
+package google.protobuf.python.internal;
+
+message TestNestedProto1APIMessage {
+ optional int32 a = 1;
+ optional TestMessage.NestedMessage b = 2;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/python.proto b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/python.proto
new file mode 100644
index 0000000000..cce645d71a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/python.proto
@@ -0,0 +1,68 @@
+// 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: tibell@google.com (Johan Tibell)
+//
+// These message definitions are used to exercises known corner cases
+// in the C++ implementation of the Python API.
+
+syntax = "proto2";
+
+package google.protobuf.python.internal;
+
+// Protos optimized for SPEED use a strict superset of the generated code
+// of equivalent ones optimized for CODE_SIZE, so we should optimize all our
+// tests for speed unless explicitly testing code size optimization.
+option optimize_for = SPEED;
+
+message TestAllTypes {
+ message NestedMessage {
+ optional int32 bb = 1;
+ optional ForeignMessage cc = 2;
+ }
+
+ repeated NestedMessage repeated_nested_message = 1;
+ optional NestedMessage optional_nested_message = 2;
+ optional int32 optional_int32 = 3;
+}
+
+message ForeignMessage {
+ optional int32 c = 1;
+ repeated int32 d = 2;
+}
+
+message TestAllExtensions {
+ extensions 1 to max;
+}
+
+extend TestAllExtensions {
+ optional TestAllTypes.NestedMessage optional_nested_message_extension = 1;
+ repeated TestAllTypes.NestedMessage repeated_nested_message_extension = 2;
+}
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/python_protobuf.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/python_protobuf.h
new file mode 100644
index 0000000000..beb6e4604a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/python_protobuf.h
@@ -0,0 +1,57 @@
+// 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: qrczak@google.com (Marcin Kowalczyk)
+//
+// This module exposes the C proto inside the given Python proto, in
+// case the Python proto is implemented with a C proto.
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_PYTHON_PROTOBUF_H__
+#define GOOGLE_PROTOBUF_PYTHON_PYTHON_PROTOBUF_H__
+
+#include <Python.h>
+
+namespace google {
+namespace protobuf {
+
+class Message;
+
+namespace python {
+
+// Return the pointer to the C proto inside the given Python proto,
+// or NULL when this is not a Python proto implemented with a C proto.
+const Message* GetCProtoInsidePyProto(PyObject* msg);
+Message* MutableCProtoInsidePyProto(PyObject* msg);
+
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_PYTHON_PROTOBUF_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.cc
new file mode 100644
index 0000000000..bb2f6db287
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.cc
@@ -0,0 +1,612 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#include <google/protobuf/pyext/repeated_composite_container.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/pyext/descriptor.h>
+#include <google/protobuf/pyext/descriptor_pool.h>
+#include <google/protobuf/pyext/message.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+
+#if PY_MAJOR_VERSION >= 3
+ #define PyInt_Check PyLong_Check
+ #define PyInt_AsLong PyLong_AsLong
+ #define PyInt_FromLong PyLong_FromLong
+#endif
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+namespace repeated_composite_container {
+
+// TODO(tibell): We might also want to check:
+// GOOGLE_CHECK_NOTNULL((self)->owner.get());
+#define GOOGLE_CHECK_ATTACHED(self) \
+ do { \
+ GOOGLE_CHECK_NOTNULL((self)->message); \
+ GOOGLE_CHECK_NOTNULL((self)->parent_field_descriptor); \
+ } while (0);
+
+#define GOOGLE_CHECK_RELEASED(self) \
+ do { \
+ GOOGLE_CHECK((self)->owner.get() == NULL); \
+ GOOGLE_CHECK((self)->message == NULL); \
+ GOOGLE_CHECK((self)->parent_field_descriptor == NULL); \
+ GOOGLE_CHECK((self)->parent == NULL); \
+ } while (0);
+
+// ---------------------------------------------------------------------
+// len()
+
+static Py_ssize_t Length(RepeatedCompositeContainer* self) {
+ Message* message = self->message;
+ if (message != NULL) {
+ return message->GetReflection()->FieldSize(*message,
+ self->parent_field_descriptor);
+ } else {
+ // The container has been released (i.e. by a call to Clear() or
+ // ClearField() on the parent) and thus there's no message.
+ return PyList_GET_SIZE(self->child_messages);
+ }
+}
+
+// Returns 0 if successful; returns -1 and sets an exception if
+// unsuccessful.
+static int UpdateChildMessages(RepeatedCompositeContainer* self) {
+ if (self->message == NULL)
+ return 0;
+
+ // A MergeFrom on a parent message could have caused extra messages to be
+ // added in the underlying protobuf so add them to our list. They can never
+ // be removed in such a way so there's no need to worry about that.
+ Py_ssize_t message_length = Length(self);
+ Py_ssize_t child_length = PyList_GET_SIZE(self->child_messages);
+ Message* message = self->message;
+ const Reflection* reflection = message->GetReflection();
+ for (Py_ssize_t i = child_length; i < message_length; ++i) {
+ const Message& sub_message = reflection->GetRepeatedMessage(
+ *(self->message), self->parent_field_descriptor, i);
+ CMessage* cmsg = cmessage::NewEmptyMessage(self->child_message_class);
+ ScopedPyObjectPtr py_cmsg(reinterpret_cast<PyObject*>(cmsg));
+ if (cmsg == NULL) {
+ return -1;
+ }
+ cmsg->owner = self->owner;
+ cmsg->message = const_cast<Message*>(&sub_message);
+ cmsg->parent = self->parent;
+ if (PyList_Append(self->child_messages, py_cmsg.get()) < 0) {
+ return -1;
+ }
+ }
+ return 0;
+}
+
+// ---------------------------------------------------------------------
+// add()
+
+static PyObject* AddToAttached(RepeatedCompositeContainer* self,
+ PyObject* args,
+ PyObject* kwargs) {
+ GOOGLE_CHECK_ATTACHED(self);
+
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ if (cmessage::AssureWritable(self->parent) == -1)
+ return NULL;
+ Message* message = self->message;
+ Message* sub_message =
+ message->GetReflection()->AddMessage(message,
+ self->parent_field_descriptor);
+ CMessage* cmsg = cmessage::NewEmptyMessage(self->child_message_class);
+ if (cmsg == NULL)
+ return NULL;
+
+ cmsg->owner = self->owner;
+ cmsg->message = sub_message;
+ cmsg->parent = self->parent;
+ if (cmessage::InitAttributes(cmsg, args, kwargs) < 0) {
+ Py_DECREF(cmsg);
+ return NULL;
+ }
+
+ PyObject* py_cmsg = reinterpret_cast<PyObject*>(cmsg);
+ if (PyList_Append(self->child_messages, py_cmsg) < 0) {
+ Py_DECREF(py_cmsg);
+ return NULL;
+ }
+ return py_cmsg;
+}
+
+static PyObject* AddToReleased(RepeatedCompositeContainer* self,
+ PyObject* args,
+ PyObject* kwargs) {
+ GOOGLE_CHECK_RELEASED(self);
+
+ // Create a new Message detached from the rest.
+ PyObject* py_cmsg = PyEval_CallObjectWithKeywords(
+ self->child_message_class->AsPyObject(), args, kwargs);
+ if (py_cmsg == NULL)
+ return NULL;
+
+ if (PyList_Append(self->child_messages, py_cmsg) < 0) {
+ Py_DECREF(py_cmsg);
+ return NULL;
+ }
+ return py_cmsg;
+}
+
+PyObject* Add(RepeatedCompositeContainer* self,
+ PyObject* args,
+ PyObject* kwargs) {
+ if (self->message == NULL)
+ return AddToReleased(self, args, kwargs);
+ else
+ return AddToAttached(self, args, kwargs);
+}
+
+// ---------------------------------------------------------------------
+// extend()
+
+PyObject* Extend(RepeatedCompositeContainer* self, PyObject* value) {
+ cmessage::AssureWritable(self->parent);
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ ScopedPyObjectPtr iter(PyObject_GetIter(value));
+ if (iter == NULL) {
+ PyErr_SetString(PyExc_TypeError, "Value must be iterable");
+ return NULL;
+ }
+ ScopedPyObjectPtr next;
+ while ((next.reset(PyIter_Next(iter.get()))) != NULL) {
+ if (!PyObject_TypeCheck(next.get(), &CMessage_Type)) {
+ PyErr_SetString(PyExc_TypeError, "Not a cmessage");
+ return NULL;
+ }
+ ScopedPyObjectPtr new_message(Add(self, NULL, NULL));
+ if (new_message == NULL) {
+ return NULL;
+ }
+ CMessage* new_cmessage = reinterpret_cast<CMessage*>(new_message.get());
+ if (ScopedPyObjectPtr(cmessage::MergeFrom(new_cmessage, next.get())) ==
+ NULL) {
+ return NULL;
+ }
+ }
+ if (PyErr_Occurred()) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+PyObject* MergeFrom(RepeatedCompositeContainer* self, PyObject* other) {
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ return Extend(self, other);
+}
+
+PyObject* Subscript(RepeatedCompositeContainer* self, PyObject* slice) {
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ // Just forward the call to the subscript-handling function of the
+ // list containing the child messages.
+ return PyObject_GetItem(self->child_messages, slice);
+}
+
+int AssignSubscript(RepeatedCompositeContainer* self,
+ PyObject* slice,
+ PyObject* value) {
+ if (UpdateChildMessages(self) < 0) {
+ return -1;
+ }
+ if (value != NULL) {
+ PyErr_SetString(PyExc_TypeError, "does not support assignment");
+ return -1;
+ }
+
+ // Delete from the underlying Message, if any.
+ if (self->parent != NULL) {
+ if (cmessage::InternalDeleteRepeatedField(self->parent,
+ self->parent_field_descriptor,
+ slice,
+ self->child_messages) < 0) {
+ return -1;
+ }
+ } else {
+ Py_ssize_t from;
+ Py_ssize_t to;
+ Py_ssize_t step;
+ Py_ssize_t length = Length(self);
+ Py_ssize_t slicelength;
+ if (PySlice_Check(slice)) {
+#if PY_MAJOR_VERSION >= 3
+ if (PySlice_GetIndicesEx(slice,
+#else
+ if (PySlice_GetIndicesEx(reinterpret_cast<PySliceObject*>(slice),
+#endif
+ length, &from, &to, &step, &slicelength) == -1) {
+ return -1;
+ }
+ return PySequence_DelSlice(self->child_messages, from, to);
+ } else if (PyInt_Check(slice) || PyLong_Check(slice)) {
+ from = to = PyLong_AsLong(slice);
+ if (from < 0) {
+ from = to = length + from;
+ }
+ return PySequence_DelItem(self->child_messages, from);
+ }
+ }
+
+ return 0;
+}
+
+static PyObject* Remove(RepeatedCompositeContainer* self, PyObject* value) {
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ Py_ssize_t index = PySequence_Index(self->child_messages, value);
+ if (index == -1) {
+ return NULL;
+ }
+ ScopedPyObjectPtr py_index(PyLong_FromLong(index));
+ if (AssignSubscript(self, py_index.get(), NULL) < 0) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+static PyObject* RichCompare(RepeatedCompositeContainer* self,
+ PyObject* other,
+ int opid) {
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ if (!PyObject_TypeCheck(other, &RepeatedCompositeContainer_Type)) {
+ PyErr_SetString(PyExc_TypeError,
+ "Can only compare repeated composite fields "
+ "against other repeated composite fields.");
+ return NULL;
+ }
+ if (opid == Py_EQ || opid == Py_NE) {
+ // TODO(anuraag): Don't make new lists just for this...
+ ScopedPyObjectPtr full_slice(PySlice_New(NULL, NULL, NULL));
+ if (full_slice == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr list(Subscript(self, full_slice.get()));
+ if (list == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr other_list(
+ Subscript(reinterpret_cast<RepeatedCompositeContainer*>(other),
+ full_slice.get()));
+ if (other_list == NULL) {
+ return NULL;
+ }
+ return PyObject_RichCompare(list.get(), other_list.get(), opid);
+ } else {
+ Py_INCREF(Py_NotImplemented);
+ return Py_NotImplemented;
+ }
+}
+
+// ---------------------------------------------------------------------
+// sort()
+
+static void ReorderAttached(RepeatedCompositeContainer* self) {
+ Message* message = self->message;
+ const Reflection* reflection = message->GetReflection();
+ const FieldDescriptor* descriptor = self->parent_field_descriptor;
+ const Py_ssize_t length = Length(self);
+
+ // Since Python protobuf objects are never arena-allocated, adding and
+ // removing message pointers to the underlying array is just updating
+ // pointers.
+ for (Py_ssize_t i = 0; i < length; ++i)
+ reflection->ReleaseLast(message, descriptor);
+
+ for (Py_ssize_t i = 0; i < length; ++i) {
+ CMessage* py_cmsg = reinterpret_cast<CMessage*>(
+ PyList_GET_ITEM(self->child_messages, i));
+ reflection->AddAllocatedMessage(message, descriptor, py_cmsg->message);
+ }
+}
+
+// Returns 0 if successful; returns -1 and sets an exception if
+// unsuccessful.
+static int SortPythonMessages(RepeatedCompositeContainer* self,
+ PyObject* args,
+ PyObject* kwds) {
+ ScopedPyObjectPtr m(PyObject_GetAttrString(self->child_messages, "sort"));
+ if (m == NULL)
+ return -1;
+ if (PyObject_Call(m.get(), args, kwds) == NULL)
+ return -1;
+ if (self->message != NULL) {
+ ReorderAttached(self);
+ }
+ return 0;
+}
+
+static PyObject* Sort(RepeatedCompositeContainer* self,
+ PyObject* args,
+ PyObject* kwds) {
+ // Support the old sort_function argument for backwards
+ // compatibility.
+ if (kwds != NULL) {
+ PyObject* sort_func = PyDict_GetItemString(kwds, "sort_function");
+ if (sort_func != NULL) {
+ // Must set before deleting as sort_func is a borrowed reference
+ // and kwds might be the only thing keeping it alive.
+ PyDict_SetItemString(kwds, "cmp", sort_func);
+ PyDict_DelItemString(kwds, "sort_function");
+ }
+ }
+
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ if (SortPythonMessages(self, args, kwds) < 0) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+// ---------------------------------------------------------------------
+
+static PyObject* Item(RepeatedCompositeContainer* self, Py_ssize_t index) {
+ if (UpdateChildMessages(self) < 0) {
+ return NULL;
+ }
+ Py_ssize_t length = Length(self);
+ if (index < 0) {
+ index = length + index;
+ }
+ PyObject* item = PyList_GetItem(self->child_messages, index);
+ if (item == NULL) {
+ return NULL;
+ }
+ Py_INCREF(item);
+ return item;
+}
+
+static PyObject* Pop(RepeatedCompositeContainer* self,
+ PyObject* args) {
+ Py_ssize_t index = -1;
+ if (!PyArg_ParseTuple(args, "|n", &index)) {
+ return NULL;
+ }
+ PyObject* item = Item(self, index);
+ if (item == NULL) {
+ PyErr_Format(PyExc_IndexError,
+ "list index (%zd) out of range",
+ index);
+ return NULL;
+ }
+ ScopedPyObjectPtr py_index(PyLong_FromSsize_t(index));
+ if (AssignSubscript(self, py_index.get(), NULL) < 0) {
+ return NULL;
+ }
+ return item;
+}
+
+// Release field of parent message and transfer the ownership to target.
+void ReleaseLastTo(CMessage* parent,
+ const FieldDescriptor* field,
+ CMessage* target) {
+ GOOGLE_CHECK_NOTNULL(parent);
+ GOOGLE_CHECK_NOTNULL(field);
+ GOOGLE_CHECK_NOTNULL(target);
+
+ shared_ptr<Message> released_message(
+ parent->message->GetReflection()->ReleaseLast(parent->message, field));
+ // TODO(tibell): Deal with proto1.
+
+ target->parent = NULL;
+ target->parent_field_descriptor = NULL;
+ target->message = released_message.get();
+ target->read_only = false;
+ cmessage::SetOwner(target, released_message);
+}
+
+// Called to release a container using
+// ClearField('container_field_name') on the parent.
+int Release(RepeatedCompositeContainer* self) {
+ if (UpdateChildMessages(self) < 0) {
+ PyErr_WriteUnraisable(PyBytes_FromString("Failed to update released "
+ "messages"));
+ return -1;
+ }
+
+ Message* message = self->message;
+ const FieldDescriptor* field = self->parent_field_descriptor;
+
+ // The reflection API only lets us release the last message in a
+ // repeated field. Therefore we iterate through the children
+ // starting with the last one.
+ const Py_ssize_t size = PyList_GET_SIZE(self->child_messages);
+ GOOGLE_DCHECK_EQ(size, message->GetReflection()->FieldSize(*message, field));
+ for (Py_ssize_t i = size - 1; i >= 0; --i) {
+ CMessage* child_cmessage = reinterpret_cast<CMessage*>(
+ PyList_GET_ITEM(self->child_messages, i));
+ ReleaseLastTo(self->parent, field, child_cmessage);
+ }
+
+ // Detach from containing message.
+ self->parent = NULL;
+ self->parent_field_descriptor = NULL;
+ self->message = NULL;
+ self->owner.reset();
+
+ return 0;
+}
+
+int SetOwner(RepeatedCompositeContainer* self,
+ const shared_ptr<Message>& new_owner) {
+ GOOGLE_CHECK_ATTACHED(self);
+
+ self->owner = new_owner;
+ const Py_ssize_t n = PyList_GET_SIZE(self->child_messages);
+ for (Py_ssize_t i = 0; i < n; ++i) {
+ PyObject* msg = PyList_GET_ITEM(self->child_messages, i);
+ if (cmessage::SetOwner(reinterpret_cast<CMessage*>(msg), new_owner) == -1) {
+ return -1;
+ }
+ }
+ return 0;
+}
+
+// The private constructor of RepeatedCompositeContainer objects.
+PyObject *NewContainer(
+ CMessage* parent,
+ const FieldDescriptor* parent_field_descriptor,
+ CMessageClass* concrete_class) {
+ if (!CheckFieldBelongsToMessage(parent_field_descriptor, parent->message)) {
+ return NULL;
+ }
+
+ RepeatedCompositeContainer* self =
+ reinterpret_cast<RepeatedCompositeContainer*>(
+ PyType_GenericAlloc(&RepeatedCompositeContainer_Type, 0));
+ if (self == NULL) {
+ return NULL;
+ }
+
+ self->message = parent->message;
+ self->parent = parent;
+ self->parent_field_descriptor = parent_field_descriptor;
+ self->owner = parent->owner;
+ Py_INCREF(concrete_class);
+ self->child_message_class = concrete_class;
+ self->child_messages = PyList_New(0);
+
+ return reinterpret_cast<PyObject*>(self);
+}
+
+static void Dealloc(RepeatedCompositeContainer* self) {
+ Py_CLEAR(self->child_messages);
+ Py_CLEAR(self->child_message_class);
+ // TODO(tibell): Do we need to call delete on these objects to make
+ // sure their destructors are called?
+ self->owner.reset();
+
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+static PySequenceMethods SqMethods = {
+ (lenfunc)Length, /* sq_length */
+ 0, /* sq_concat */
+ 0, /* sq_repeat */
+ (ssizeargfunc)Item /* sq_item */
+};
+
+static PyMappingMethods MpMethods = {
+ (lenfunc)Length, /* mp_length */
+ (binaryfunc)Subscript, /* mp_subscript */
+ (objobjargproc)AssignSubscript,/* mp_ass_subscript */
+};
+
+static PyMethodDef Methods[] = {
+ { "add", (PyCFunction) Add, METH_VARARGS | METH_KEYWORDS,
+ "Adds an object to the repeated container." },
+ { "extend", (PyCFunction) Extend, METH_O,
+ "Adds objects to the repeated container." },
+ { "pop", (PyCFunction)Pop, METH_VARARGS,
+ "Removes an object from the repeated container and returns it." },
+ { "remove", (PyCFunction) Remove, METH_O,
+ "Removes an object from the repeated container." },
+ { "sort", (PyCFunction) Sort, METH_VARARGS | METH_KEYWORDS,
+ "Sorts the repeated container." },
+ { "MergeFrom", (PyCFunction) MergeFrom, METH_O,
+ "Adds objects to the repeated container." },
+ { NULL, NULL }
+};
+
+} // namespace repeated_composite_container
+
+PyTypeObject RepeatedCompositeContainer_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".RepeatedCompositeContainer", // tp_name
+ sizeof(RepeatedCompositeContainer), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)repeated_composite_container::Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ &repeated_composite_container::SqMethods, // tp_as_sequence
+ &repeated_composite_container::MpMethods, // tp_as_mapping
+ PyObject_HashNotImplemented, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Repeated scalar container", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ (richcmpfunc)repeated_composite_container::RichCompare, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ repeated_composite_container::Methods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+};
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.h
new file mode 100644
index 0000000000..a7b56b61b3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_composite_container.h
@@ -0,0 +1,179 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_COMPOSITE_CONTAINER_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_COMPOSITE_CONTAINER_H__
+
+#include <Python.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+
+namespace google {
+namespace protobuf {
+
+class FieldDescriptor;
+class Message;
+
+#ifdef _SHARED_PTR_H
+using std::shared_ptr;
+#else
+using internal::shared_ptr;
+#endif
+
+namespace python {
+
+struct CMessage;
+struct CMessageClass;
+
+// A RepeatedCompositeContainer can be in one of two states: attached
+// or released.
+//
+// When in the attached state all modifications to the container are
+// done both on the 'message' and on the 'child_messages'
+// list. In this state all Messages referred to by the children in
+// 'child_messages' are owner by the 'owner'.
+//
+// When in the released state 'message', 'owner', 'parent', and
+// 'parent_field_descriptor' are NULL.
+typedef struct RepeatedCompositeContainer {
+ PyObject_HEAD;
+
+ // This is the top-level C++ Message object that owns the whole
+ // proto tree. Every Python RepeatedCompositeContainer holds a
+ // reference to it in order to keep it alive as long as there's a
+ // Python object that references any part of the tree.
+ shared_ptr<Message> owner;
+
+ // Weak reference to parent object. May be NULL. Used to make sure
+ // the parent is writable before modifying the
+ // RepeatedCompositeContainer.
+ CMessage* parent;
+
+ // A descriptor used to modify the underlying 'message'.
+ // The pointer is owned by the global DescriptorPool.
+ const FieldDescriptor* parent_field_descriptor;
+
+ // Pointer to the C++ Message that contains this container. The
+ // RepeatedCompositeContainer does not own this pointer.
+ //
+ // If NULL, this message has been released from its parent (by
+ // calling Clear() or ClearField() on the parent.
+ Message* message;
+
+ // The type used to create new child messages.
+ CMessageClass* child_message_class;
+
+ // A list of child messages.
+ PyObject* child_messages;
+} RepeatedCompositeContainer;
+
+extern PyTypeObject RepeatedCompositeContainer_Type;
+
+namespace repeated_composite_container {
+
+// Builds a RepeatedCompositeContainer object, from a parent message and a
+// field descriptor.
+PyObject *NewContainer(
+ CMessage* parent,
+ const FieldDescriptor* parent_field_descriptor,
+ CMessageClass *child_message_class);
+
+// Appends a new CMessage to the container and returns it. The
+// CMessage is initialized using the content of kwargs.
+//
+// Returns a new reference if successful; returns NULL and sets an
+// exception if unsuccessful.
+PyObject* Add(RepeatedCompositeContainer* self,
+ PyObject* args,
+ PyObject* kwargs);
+
+// Appends all the CMessages in the input iterator to the container.
+//
+// Returns None if successful; returns NULL and sets an exception if
+// unsuccessful.
+PyObject* Extend(RepeatedCompositeContainer* self, PyObject* value);
+
+// Appends a new message to the container for each message in the
+// input iterator, merging each data element in. Equivalent to extend.
+//
+// Returns None if successful; returns NULL and sets an exception if
+// unsuccessful.
+PyObject* MergeFrom(RepeatedCompositeContainer* self, PyObject* other);
+
+// Accesses messages in the container.
+//
+// Returns a new reference to the message for an integer parameter.
+// Returns a new reference to a list of messages for a slice.
+PyObject* Subscript(RepeatedCompositeContainer* self, PyObject* slice);
+
+// Deletes items from the container (cannot be used for assignment).
+//
+// Returns 0 on success, -1 on failure.
+int AssignSubscript(RepeatedCompositeContainer* self,
+ PyObject* slice,
+ PyObject* value);
+
+// Releases the messages in the container to the given message.
+//
+// Returns 0 on success, -1 on failure.
+int ReleaseToMessage(RepeatedCompositeContainer* self, Message* new_message);
+
+// Releases the messages in the container to a new message.
+//
+// Returns 0 on success, -1 on failure.
+int Release(RepeatedCompositeContainer* self);
+
+// Returns 0 on success, -1 on failure.
+int SetOwner(RepeatedCompositeContainer* self,
+ const shared_ptr<Message>& new_owner);
+
+// Removes the last element of the repeated message field 'field' on
+// the Message 'parent', and transfers the ownership of the released
+// Message to 'target'.
+//
+// Corresponds to reflection api method ReleaseMessage.
+void ReleaseLastTo(CMessage* parent,
+ const FieldDescriptor* field,
+ CMessage* target);
+
+} // namespace repeated_composite_container
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_COMPOSITE_CONTAINER_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.cc b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.cc
new file mode 100644
index 0000000000..95da85f87b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.cc
@@ -0,0 +1,812 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#include <google/protobuf/pyext/repeated_scalar_container.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/pyext/descriptor.h>
+#include <google/protobuf/pyext/descriptor_pool.h>
+#include <google/protobuf/pyext/message.h>
+#include <google/protobuf/pyext/scoped_pyobject_ptr.h>
+
+#if PY_MAJOR_VERSION >= 3
+ #define PyInt_FromLong PyLong_FromLong
+ #if PY_VERSION_HEX < 0x03030000
+ #error "Python 3.0 - 3.2 are not supported."
+ #else
+ #define PyString_AsString(ob) \
+ (PyUnicode_Check(ob)? PyUnicode_AsUTF8(ob): PyBytes_AsString(ob))
+ #endif
+#endif
+
+namespace google {
+namespace protobuf {
+namespace python {
+
+namespace repeated_scalar_container {
+
+static int InternalAssignRepeatedField(
+ RepeatedScalarContainer* self, PyObject* list) {
+ self->message->GetReflection()->ClearField(self->message,
+ self->parent_field_descriptor);
+ for (Py_ssize_t i = 0; i < PyList_GET_SIZE(list); ++i) {
+ PyObject* value = PyList_GET_ITEM(list, i);
+ if (ScopedPyObjectPtr(Append(self, value)) == NULL) {
+ return -1;
+ }
+ }
+ return 0;
+}
+
+static Py_ssize_t Len(RepeatedScalarContainer* self) {
+ Message* message = self->message;
+ return message->GetReflection()->FieldSize(*message,
+ self->parent_field_descriptor);
+}
+
+static int AssignItem(RepeatedScalarContainer* self,
+ Py_ssize_t index,
+ PyObject* arg) {
+ cmessage::AssureWritable(self->parent);
+ Message* message = self->message;
+ const FieldDescriptor* field_descriptor = self->parent_field_descriptor;
+
+ const Reflection* reflection = message->GetReflection();
+ int field_size = reflection->FieldSize(*message, field_descriptor);
+ if (index < 0) {
+ index = field_size + index;
+ }
+ if (index < 0 || index >= field_size) {
+ PyErr_Format(PyExc_IndexError,
+ "list assignment index (%d) out of range",
+ static_cast<int>(index));
+ return -1;
+ }
+
+ if (arg == NULL) {
+ ScopedPyObjectPtr py_index(PyLong_FromLong(index));
+ return cmessage::InternalDeleteRepeatedField(self->parent, field_descriptor,
+ py_index.get(), NULL);
+ }
+
+ if (PySequence_Check(arg) && !(PyBytes_Check(arg) || PyUnicode_Check(arg))) {
+ PyErr_SetString(PyExc_TypeError, "Value must be scalar");
+ return -1;
+ }
+
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ GOOGLE_CHECK_GET_INT32(arg, value, -1);
+ reflection->SetRepeatedInt32(message, field_descriptor, index, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ GOOGLE_CHECK_GET_INT64(arg, value, -1);
+ reflection->SetRepeatedInt64(message, field_descriptor, index, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ GOOGLE_CHECK_GET_UINT32(arg, value, -1);
+ reflection->SetRepeatedUInt32(message, field_descriptor, index, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ GOOGLE_CHECK_GET_UINT64(arg, value, -1);
+ reflection->SetRepeatedUInt64(message, field_descriptor, index, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ GOOGLE_CHECK_GET_FLOAT(arg, value, -1);
+ reflection->SetRepeatedFloat(message, field_descriptor, index, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ GOOGLE_CHECK_GET_DOUBLE(arg, value, -1);
+ reflection->SetRepeatedDouble(message, field_descriptor, index, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ GOOGLE_CHECK_GET_BOOL(arg, value, -1);
+ reflection->SetRepeatedBool(message, field_descriptor, index, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ if (!CheckAndSetString(
+ arg, message, field_descriptor, reflection, false, index)) {
+ return -1;
+ }
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ GOOGLE_CHECK_GET_INT32(arg, value, -1);
+ if (reflection->SupportsUnknownEnumValues()) {
+ reflection->SetRepeatedEnumValue(message, field_descriptor, index,
+ value);
+ } else {
+ const EnumDescriptor* enum_descriptor = field_descriptor->enum_type();
+ const EnumValueDescriptor* enum_value =
+ enum_descriptor->FindValueByNumber(value);
+ if (enum_value != NULL) {
+ reflection->SetRepeatedEnum(message, field_descriptor, index,
+ enum_value);
+ } else {
+ ScopedPyObjectPtr s(PyObject_Str(arg));
+ if (s != NULL) {
+ PyErr_Format(PyExc_ValueError, "Unknown enum value: %s",
+ PyString_AsString(s.get()));
+ }
+ return -1;
+ }
+ }
+ break;
+ }
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Adding value to a field of unknown type %d",
+ field_descriptor->cpp_type());
+ return -1;
+ }
+ return 0;
+}
+
+static PyObject* Item(RepeatedScalarContainer* self, Py_ssize_t index) {
+ Message* message = self->message;
+ const FieldDescriptor* field_descriptor = self->parent_field_descriptor;
+ const Reflection* reflection = message->GetReflection();
+
+ int field_size = reflection->FieldSize(*message, field_descriptor);
+ if (index < 0) {
+ index = field_size + index;
+ }
+ if (index < 0 || index >= field_size) {
+ PyErr_Format(PyExc_IndexError,
+ "list index (%zd) out of range",
+ index);
+ return NULL;
+ }
+
+ PyObject* result = NULL;
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ int32 value = reflection->GetRepeatedInt32(
+ *message, field_descriptor, index);
+ result = PyInt_FromLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ int64 value = reflection->GetRepeatedInt64(
+ *message, field_descriptor, index);
+ result = PyLong_FromLongLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ uint32 value = reflection->GetRepeatedUInt32(
+ *message, field_descriptor, index);
+ result = PyLong_FromLongLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ uint64 value = reflection->GetRepeatedUInt64(
+ *message, field_descriptor, index);
+ result = PyLong_FromUnsignedLongLong(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ float value = reflection->GetRepeatedFloat(
+ *message, field_descriptor, index);
+ result = PyFloat_FromDouble(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value = reflection->GetRepeatedDouble(
+ *message, field_descriptor, index);
+ result = PyFloat_FromDouble(value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ bool value = reflection->GetRepeatedBool(
+ *message, field_descriptor, index);
+ result = PyBool_FromLong(value ? 1 : 0);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ const EnumValueDescriptor* enum_value =
+ message->GetReflection()->GetRepeatedEnum(
+ *message, field_descriptor, index);
+ result = PyInt_FromLong(enum_value->number());
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string value = reflection->GetRepeatedString(
+ *message, field_descriptor, index);
+ result = ToStringObject(field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_MESSAGE: {
+ PyObject* py_cmsg = PyObject_CallObject(reinterpret_cast<PyObject*>(
+ &CMessage_Type), NULL);
+ if (py_cmsg == NULL) {
+ return NULL;
+ }
+ CMessage* cmsg = reinterpret_cast<CMessage*>(py_cmsg);
+ const Message& msg = reflection->GetRepeatedMessage(
+ *message, field_descriptor, index);
+ cmsg->owner = self->owner;
+ cmsg->parent = self->parent;
+ cmsg->message = const_cast<Message*>(&msg);
+ cmsg->read_only = false;
+ result = reinterpret_cast<PyObject*>(py_cmsg);
+ break;
+ }
+ default:
+ PyErr_Format(
+ PyExc_SystemError,
+ "Getting value from a repeated field of unknown type %d",
+ field_descriptor->cpp_type());
+ }
+
+ return result;
+}
+
+static PyObject* Subscript(RepeatedScalarContainer* self, PyObject* slice) {
+ Py_ssize_t from;
+ Py_ssize_t to;
+ Py_ssize_t step;
+ Py_ssize_t length;
+ Py_ssize_t slicelength;
+ bool return_list = false;
+#if PY_MAJOR_VERSION < 3
+ if (PyInt_Check(slice)) {
+ from = to = PyInt_AsLong(slice);
+ } else // NOLINT
+#endif
+ if (PyLong_Check(slice)) {
+ from = to = PyLong_AsLong(slice);
+ } else if (PySlice_Check(slice)) {
+ length = Len(self);
+#if PY_MAJOR_VERSION >= 3
+ if (PySlice_GetIndicesEx(slice,
+#else
+ if (PySlice_GetIndicesEx(reinterpret_cast<PySliceObject*>(slice),
+#endif
+ length, &from, &to, &step, &slicelength) == -1) {
+ return NULL;
+ }
+ return_list = true;
+ } else {
+ PyErr_SetString(PyExc_TypeError, "list indices must be integers");
+ return NULL;
+ }
+
+ if (!return_list) {
+ return Item(self, from);
+ }
+
+ PyObject* list = PyList_New(0);
+ if (list == NULL) {
+ return NULL;
+ }
+ if (from <= to) {
+ if (step < 0) {
+ return list;
+ }
+ for (Py_ssize_t index = from; index < to; index += step) {
+ if (index < 0 || index >= length) {
+ break;
+ }
+ ScopedPyObjectPtr s(Item(self, index));
+ PyList_Append(list, s.get());
+ }
+ } else {
+ if (step > 0) {
+ return list;
+ }
+ for (Py_ssize_t index = from; index > to; index += step) {
+ if (index < 0 || index >= length) {
+ break;
+ }
+ ScopedPyObjectPtr s(Item(self, index));
+ PyList_Append(list, s.get());
+ }
+ }
+ return list;
+}
+
+PyObject* Append(RepeatedScalarContainer* self, PyObject* item) {
+ cmessage::AssureWritable(self->parent);
+ Message* message = self->message;
+ const FieldDescriptor* field_descriptor = self->parent_field_descriptor;
+
+ const Reflection* reflection = message->GetReflection();
+ switch (field_descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ GOOGLE_CHECK_GET_INT32(item, value, NULL);
+ reflection->AddInt32(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ GOOGLE_CHECK_GET_INT64(item, value, NULL);
+ reflection->AddInt64(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ GOOGLE_CHECK_GET_UINT32(item, value, NULL);
+ reflection->AddUInt32(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ GOOGLE_CHECK_GET_UINT64(item, value, NULL);
+ reflection->AddUInt64(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ GOOGLE_CHECK_GET_FLOAT(item, value, NULL);
+ reflection->AddFloat(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ GOOGLE_CHECK_GET_DOUBLE(item, value, NULL);
+ reflection->AddDouble(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ GOOGLE_CHECK_GET_BOOL(item, value, NULL);
+ reflection->AddBool(message, field_descriptor, value);
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ if (!CheckAndSetString(
+ item, message, field_descriptor, reflection, true, -1)) {
+ return NULL;
+ }
+ break;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ GOOGLE_CHECK_GET_INT32(item, value, NULL);
+ if (reflection->SupportsUnknownEnumValues()) {
+ reflection->AddEnumValue(message, field_descriptor, value);
+ } else {
+ const EnumDescriptor* enum_descriptor = field_descriptor->enum_type();
+ const EnumValueDescriptor* enum_value =
+ enum_descriptor->FindValueByNumber(value);
+ if (enum_value != NULL) {
+ reflection->AddEnum(message, field_descriptor, enum_value);
+ } else {
+ ScopedPyObjectPtr s(PyObject_Str(item));
+ if (s != NULL) {
+ PyErr_Format(PyExc_ValueError, "Unknown enum value: %s",
+ PyString_AsString(s.get()));
+ }
+ return NULL;
+ }
+ }
+ break;
+ }
+ default:
+ PyErr_Format(
+ PyExc_SystemError, "Adding value to a field of unknown type %d",
+ field_descriptor->cpp_type());
+ return NULL;
+ }
+
+ Py_RETURN_NONE;
+}
+
+static int AssSubscript(RepeatedScalarContainer* self,
+ PyObject* slice,
+ PyObject* value) {
+ Py_ssize_t from;
+ Py_ssize_t to;
+ Py_ssize_t step;
+ Py_ssize_t length;
+ Py_ssize_t slicelength;
+ bool create_list = false;
+
+ cmessage::AssureWritable(self->parent);
+ Message* message = self->message;
+ const FieldDescriptor* field_descriptor =
+ self->parent_field_descriptor;
+
+#if PY_MAJOR_VERSION < 3
+ if (PyInt_Check(slice)) {
+ from = to = PyInt_AsLong(slice);
+ } else
+#endif
+ if (PyLong_Check(slice)) {
+ from = to = PyLong_AsLong(slice);
+ } else if (PySlice_Check(slice)) {
+ const Reflection* reflection = message->GetReflection();
+ length = reflection->FieldSize(*message, field_descriptor);
+#if PY_MAJOR_VERSION >= 3
+ if (PySlice_GetIndicesEx(slice,
+#else
+ if (PySlice_GetIndicesEx(reinterpret_cast<PySliceObject*>(slice),
+#endif
+ length, &from, &to, &step, &slicelength) == -1) {
+ return -1;
+ }
+ create_list = true;
+ } else {
+ PyErr_SetString(PyExc_TypeError, "list indices must be integers");
+ return -1;
+ }
+
+ if (value == NULL) {
+ return cmessage::InternalDeleteRepeatedField(
+ self->parent, field_descriptor, slice, NULL);
+ }
+
+ if (!create_list) {
+ return AssignItem(self, from, value);
+ }
+
+ ScopedPyObjectPtr full_slice(PySlice_New(NULL, NULL, NULL));
+ if (full_slice == NULL) {
+ return -1;
+ }
+ ScopedPyObjectPtr new_list(Subscript(self, full_slice.get()));
+ if (new_list == NULL) {
+ return -1;
+ }
+ if (PySequence_SetSlice(new_list.get(), from, to, value) < 0) {
+ return -1;
+ }
+
+ return InternalAssignRepeatedField(self, new_list.get());
+}
+
+PyObject* Extend(RepeatedScalarContainer* self, PyObject* value) {
+ cmessage::AssureWritable(self->parent);
+
+ // TODO(ptucker): Deprecate this behavior. b/18413862
+ if (value == Py_None) {
+ Py_RETURN_NONE;
+ }
+ if ((Py_TYPE(value)->tp_as_sequence == NULL) && PyObject_Not(value)) {
+ Py_RETURN_NONE;
+ }
+
+ ScopedPyObjectPtr iter(PyObject_GetIter(value));
+ if (iter == NULL) {
+ PyErr_SetString(PyExc_TypeError, "Value must be iterable");
+ return NULL;
+ }
+ ScopedPyObjectPtr next;
+ while ((next.reset(PyIter_Next(iter.get()))) != NULL) {
+ if (ScopedPyObjectPtr(Append(self, next.get())) == NULL) {
+ return NULL;
+ }
+ }
+ if (PyErr_Occurred()) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+static PyObject* Insert(RepeatedScalarContainer* self, PyObject* args) {
+ Py_ssize_t index;
+ PyObject* value;
+ if (!PyArg_ParseTuple(args, "lO", &index, &value)) {
+ return NULL;
+ }
+ ScopedPyObjectPtr full_slice(PySlice_New(NULL, NULL, NULL));
+ ScopedPyObjectPtr new_list(Subscript(self, full_slice.get()));
+ if (PyList_Insert(new_list.get(), index, value) < 0) {
+ return NULL;
+ }
+ int ret = InternalAssignRepeatedField(self, new_list.get());
+ if (ret < 0) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+static PyObject* Remove(RepeatedScalarContainer* self, PyObject* value) {
+ Py_ssize_t match_index = -1;
+ for (Py_ssize_t i = 0; i < Len(self); ++i) {
+ ScopedPyObjectPtr elem(Item(self, i));
+ if (PyObject_RichCompareBool(elem.get(), value, Py_EQ)) {
+ match_index = i;
+ break;
+ }
+ }
+ if (match_index == -1) {
+ PyErr_SetString(PyExc_ValueError, "remove(x): x not in container");
+ return NULL;
+ }
+ if (AssignItem(self, match_index, NULL) < 0) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+static PyObject* RichCompare(RepeatedScalarContainer* self,
+ PyObject* other,
+ int opid) {
+ if (opid != Py_EQ && opid != Py_NE) {
+ Py_INCREF(Py_NotImplemented);
+ return Py_NotImplemented;
+ }
+
+ // Copy the contents of this repeated scalar container, and other if it is
+ // also a repeated scalar container, into Python lists so we can delegate
+ // to the list's compare method.
+
+ ScopedPyObjectPtr full_slice(PySlice_New(NULL, NULL, NULL));
+ if (full_slice == NULL) {
+ return NULL;
+ }
+
+ ScopedPyObjectPtr other_list_deleter;
+ if (PyObject_TypeCheck(other, &RepeatedScalarContainer_Type)) {
+ other_list_deleter.reset(Subscript(
+ reinterpret_cast<RepeatedScalarContainer*>(other), full_slice.get()));
+ other = other_list_deleter.get();
+ }
+
+ ScopedPyObjectPtr list(Subscript(self, full_slice.get()));
+ if (list == NULL) {
+ return NULL;
+ }
+ return PyObject_RichCompare(list.get(), other, opid);
+}
+
+PyObject* Reduce(RepeatedScalarContainer* unused_self) {
+ PyErr_Format(
+ PickleError_class,
+ "can't pickle repeated message fields, convert to list first");
+ return NULL;
+}
+
+static PyObject* Sort(RepeatedScalarContainer* self,
+ PyObject* args,
+ PyObject* kwds) {
+ // Support the old sort_function argument for backwards
+ // compatibility.
+ if (kwds != NULL) {
+ PyObject* sort_func = PyDict_GetItemString(kwds, "sort_function");
+ if (sort_func != NULL) {
+ // Must set before deleting as sort_func is a borrowed reference
+ // and kwds might be the only thing keeping it alive.
+ if (PyDict_SetItemString(kwds, "cmp", sort_func) == -1)
+ return NULL;
+ if (PyDict_DelItemString(kwds, "sort_function") == -1)
+ return NULL;
+ }
+ }
+
+ ScopedPyObjectPtr full_slice(PySlice_New(NULL, NULL, NULL));
+ if (full_slice == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr list(Subscript(self, full_slice.get()));
+ if (list == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr m(PyObject_GetAttrString(list.get(), "sort"));
+ if (m == NULL) {
+ return NULL;
+ }
+ ScopedPyObjectPtr res(PyObject_Call(m.get(), args, kwds));
+ if (res == NULL) {
+ return NULL;
+ }
+ int ret = InternalAssignRepeatedField(self, list.get());
+ if (ret < 0) {
+ return NULL;
+ }
+ Py_RETURN_NONE;
+}
+
+static PyObject* Pop(RepeatedScalarContainer* self,
+ PyObject* args) {
+ Py_ssize_t index = -1;
+ if (!PyArg_ParseTuple(args, "|n", &index)) {
+ return NULL;
+ }
+ PyObject* item = Item(self, index);
+ if (item == NULL) {
+ PyErr_Format(PyExc_IndexError,
+ "list index (%zd) out of range",
+ index);
+ return NULL;
+ }
+ if (AssignItem(self, index, NULL) < 0) {
+ return NULL;
+ }
+ return item;
+}
+
+// The private constructor of RepeatedScalarContainer objects.
+PyObject *NewContainer(
+ CMessage* parent, const FieldDescriptor* parent_field_descriptor) {
+ if (!CheckFieldBelongsToMessage(parent_field_descriptor, parent->message)) {
+ return NULL;
+ }
+
+ RepeatedScalarContainer* self = reinterpret_cast<RepeatedScalarContainer*>(
+ PyType_GenericAlloc(&RepeatedScalarContainer_Type, 0));
+ if (self == NULL) {
+ return NULL;
+ }
+
+ self->message = parent->message;
+ self->parent = parent;
+ self->parent_field_descriptor = parent_field_descriptor;
+ self->owner = parent->owner;
+
+ return reinterpret_cast<PyObject*>(self);
+}
+
+// Initializes the underlying Message object of "to" so it becomes a new parent
+// repeated scalar, and copies all the values from "from" to it. A child scalar
+// container can be released by passing it as both from and to (e.g. making it
+// the recipient of the new parent message and copying the values from itself).
+static int InitializeAndCopyToParentContainer(
+ RepeatedScalarContainer* from,
+ RepeatedScalarContainer* to) {
+ ScopedPyObjectPtr full_slice(PySlice_New(NULL, NULL, NULL));
+ if (full_slice == NULL) {
+ return -1;
+ }
+ ScopedPyObjectPtr values(Subscript(from, full_slice.get()));
+ if (values == NULL) {
+ return -1;
+ }
+ Message* new_message = from->message->New();
+ to->parent = NULL;
+ to->parent_field_descriptor = from->parent_field_descriptor;
+ to->message = new_message;
+ to->owner.reset(new_message);
+ if (InternalAssignRepeatedField(to, values.get()) < 0) {
+ return -1;
+ }
+ return 0;
+}
+
+int Release(RepeatedScalarContainer* self) {
+ return InitializeAndCopyToParentContainer(self, self);
+}
+
+PyObject* DeepCopy(RepeatedScalarContainer* self, PyObject* arg) {
+ RepeatedScalarContainer* clone = reinterpret_cast<RepeatedScalarContainer*>(
+ PyType_GenericAlloc(&RepeatedScalarContainer_Type, 0));
+ if (clone == NULL) {
+ return NULL;
+ }
+
+ if (InitializeAndCopyToParentContainer(self, clone) < 0) {
+ Py_DECREF(clone);
+ return NULL;
+ }
+ return reinterpret_cast<PyObject*>(clone);
+}
+
+static void Dealloc(RepeatedScalarContainer* self) {
+ self->owner.reset();
+ Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
+}
+
+void SetOwner(RepeatedScalarContainer* self,
+ const shared_ptr<Message>& new_owner) {
+ self->owner = new_owner;
+}
+
+static PySequenceMethods SqMethods = {
+ (lenfunc)Len, /* sq_length */
+ 0, /* sq_concat */
+ 0, /* sq_repeat */
+ (ssizeargfunc)Item, /* sq_item */
+ 0, /* sq_slice */
+ (ssizeobjargproc)AssignItem /* sq_ass_item */
+};
+
+static PyMappingMethods MpMethods = {
+ (lenfunc)Len, /* mp_length */
+ (binaryfunc)Subscript, /* mp_subscript */
+ (objobjargproc)AssSubscript, /* mp_ass_subscript */
+};
+
+static PyMethodDef Methods[] = {
+ { "__deepcopy__", (PyCFunction)DeepCopy, METH_VARARGS,
+ "Makes a deep copy of the class." },
+ { "__reduce__", (PyCFunction)Reduce, METH_NOARGS,
+ "Outputs picklable representation of the repeated field." },
+ { "append", (PyCFunction)Append, METH_O,
+ "Appends an object to the repeated container." },
+ { "extend", (PyCFunction)Extend, METH_O,
+ "Appends objects to the repeated container." },
+ { "insert", (PyCFunction)Insert, METH_VARARGS,
+ "Appends objects to the repeated container." },
+ { "pop", (PyCFunction)Pop, METH_VARARGS,
+ "Removes an object from the repeated container and returns it." },
+ { "remove", (PyCFunction)Remove, METH_O,
+ "Removes an object from the repeated container." },
+ { "sort", (PyCFunction)Sort, METH_VARARGS | METH_KEYWORDS,
+ "Sorts the repeated container."},
+ { NULL, NULL }
+};
+
+} // namespace repeated_scalar_container
+
+PyTypeObject RepeatedScalarContainer_Type = {
+ PyVarObject_HEAD_INIT(&PyType_Type, 0)
+ FULL_MODULE_NAME ".RepeatedScalarContainer", // tp_name
+ sizeof(RepeatedScalarContainer), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)repeated_scalar_container::Dealloc, // tp_dealloc
+ 0, // tp_print
+ 0, // tp_getattr
+ 0, // tp_setattr
+ 0, // tp_compare
+ 0, // tp_repr
+ 0, // tp_as_number
+ &repeated_scalar_container::SqMethods, // tp_as_sequence
+ &repeated_scalar_container::MpMethods, // tp_as_mapping
+ PyObject_HashNotImplemented, // tp_hash
+ 0, // tp_call
+ 0, // tp_str
+ 0, // tp_getattro
+ 0, // tp_setattro
+ 0, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A Repeated scalar container", // tp_doc
+ 0, // tp_traverse
+ 0, // tp_clear
+ (richcmpfunc)repeated_scalar_container::RichCompare, // tp_richcompare
+ 0, // tp_weaklistoffset
+ 0, // tp_iter
+ 0, // tp_iternext
+ repeated_scalar_container::Methods, // tp_methods
+ 0, // tp_members
+ 0, // tp_getset
+ 0, // tp_base
+ 0, // tp_dict
+ 0, // tp_descr_get
+ 0, // tp_descr_set
+ 0, // tp_dictoffset
+ 0, // tp_init
+};
+
+} // namespace python
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.h
new file mode 100644
index 0000000000..555e621c9b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/repeated_scalar_container.h
@@ -0,0 +1,122 @@
+// 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: anuraag@google.com (Anuraag Agrawal)
+// Author: tibell@google.com (Johan Tibell)
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_SCALAR_CONTAINER_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_SCALAR_CONTAINER_H__
+
+#include <Python.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+
+class Message;
+
+#ifdef _SHARED_PTR_H
+using std::shared_ptr;
+#else
+using internal::shared_ptr;
+#endif
+
+namespace python {
+
+struct CMessage;
+
+typedef struct RepeatedScalarContainer {
+ PyObject_HEAD;
+
+ // This is the top-level C++ Message object that owns the whole
+ // proto tree. Every Python RepeatedScalarContainer holds a
+ // reference to it in order to keep it alive as long as there's a
+ // Python object that references any part of the tree.
+ shared_ptr<Message> owner;
+
+ // Pointer to the C++ Message that contains this container. The
+ // RepeatedScalarContainer does not own this pointer.
+ Message* message;
+
+ // Weak reference to a parent CMessage object (i.e. may be NULL.)
+ //
+ // Used to make sure all ancestors are also mutable when first
+ // modifying the container.
+ CMessage* parent;
+
+ // Pointer to the parent's descriptor that describes this
+ // field. Used together with the parent's message when making a
+ // default message instance mutable.
+ // The pointer is owned by the global DescriptorPool.
+ const FieldDescriptor* parent_field_descriptor;
+} RepeatedScalarContainer;
+
+extern PyTypeObject RepeatedScalarContainer_Type;
+
+namespace repeated_scalar_container {
+
+// Builds a RepeatedScalarContainer object, from a parent message and a
+// field descriptor.
+extern PyObject *NewContainer(
+ CMessage* parent, const FieldDescriptor* parent_field_descriptor);
+
+// Appends the scalar 'item' to the end of the container 'self'.
+//
+// Returns None if successful; returns NULL and sets an exception if
+// unsuccessful.
+PyObject* Append(RepeatedScalarContainer* self, PyObject* item);
+
+// Releases the messages in the container to a new message.
+//
+// Returns 0 on success, -1 on failure.
+int Release(RepeatedScalarContainer* self);
+
+// Appends all the elements in the input iterator to the container.
+//
+// Returns None if successful; returns NULL and sets an exception if
+// unsuccessful.
+PyObject* Extend(RepeatedScalarContainer* self, PyObject* value);
+
+// Set the owner field of self and any children of self.
+void SetOwner(RepeatedScalarContainer* self,
+ const shared_ptr<Message>& new_owner);
+
+} // namespace repeated_scalar_container
+} // namespace python
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_SCALAR_CONTAINER_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/pyext/scoped_pyobject_ptr.h b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/scoped_pyobject_ptr.h
new file mode 100644
index 0000000000..a128cd4c61
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/pyext/scoped_pyobject_ptr.h
@@ -0,0 +1,96 @@
+// 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: tibell@google.com (Johan Tibell)
+
+#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_SCOPED_PYOBJECT_PTR_H__
+#define GOOGLE_PROTOBUF_PYTHON_CPP_SCOPED_PYOBJECT_PTR_H__
+
+#include <google/protobuf/stubs/common.h>
+
+#include <Python.h>
+
+namespace google {
+class ScopedPyObjectPtr {
+ public:
+ // Constructor. Defaults to initializing with NULL.
+ // There is no way to create an uninitialized ScopedPyObjectPtr.
+ explicit ScopedPyObjectPtr(PyObject* p = NULL) : ptr_(p) { }
+
+ // Destructor. If there is a PyObject object, delete it.
+ ~ScopedPyObjectPtr() {
+ Py_XDECREF(ptr_);
+ }
+
+ // Reset. Deletes the current owned object, if any.
+ // Then takes ownership of a new object, if given.
+ // This function must be called with a reference that you own.
+ // this->reset(this->get()) is wrong!
+ // this->reset(this->release()) is OK.
+ PyObject* reset(PyObject* p = NULL) {
+ Py_XDECREF(ptr_);
+ ptr_ = p;
+ return ptr_;
+ }
+
+ // Releases ownership of the object.
+ // The caller now owns the returned reference.
+ PyObject* release() {
+ PyObject* p = ptr_;
+ ptr_ = NULL;
+ return p;
+ }
+
+ PyObject* operator->() const {
+ assert(ptr_ != NULL);
+ return ptr_;
+ }
+
+ PyObject* get() const { return ptr_; }
+
+ Py_ssize_t refcnt() const { return Py_REFCNT(ptr_); }
+
+ void inc() const { Py_INCREF(ptr_); }
+
+ // Comparison operators.
+ // These return whether a ScopedPyObjectPtr and a raw pointer
+ // refer to the same object, not just to two different but equal
+ // objects.
+ bool operator==(const PyObject* p) const { return ptr_ == p; }
+ bool operator!=(const PyObject* p) const { return ptr_ != p; }
+
+ private:
+ PyObject* ptr_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ScopedPyObjectPtr);
+};
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_PYTHON_CPP_SCOPED_PYOBJECT_PTR_H__
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/reflection.py b/third_party/protobuf/3.0.0/python/google/protobuf/reflection.py
new file mode 100755
index 0000000000..51c8332120
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/reflection.py
@@ -0,0 +1,114 @@
+# 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.
+
+# This code is meant to work on Python 2.4 and above only.
+
+"""Contains a metaclass and helper functions used to create
+protocol message classes from Descriptor objects at runtime.
+
+Recall that a metaclass is the "type" of a class.
+(A class is to a metaclass what an instance is to a class.)
+
+In this case, we use the GeneratedProtocolMessageType metaclass
+to inject all the useful functionality into the classes
+output by the protocol compiler at compile-time.
+
+The upshot of all this is that the real implementation
+details for ALL pure-Python protocol buffers are *here in
+this file*.
+"""
+
+__author__ = 'robinson@google.com (Will Robinson)'
+
+
+from google.protobuf.internal import api_implementation
+from google.protobuf import message
+
+
+if api_implementation.Type() == 'cpp':
+ from google.protobuf.pyext import cpp_message as message_impl
+else:
+ from google.protobuf.internal import python_message as message_impl
+
+# The type of all Message classes.
+# Part of the public interface, but normally only used by message factories.
+GeneratedProtocolMessageType = message_impl.GeneratedProtocolMessageType
+
+
+def ParseMessage(descriptor, byte_str):
+ """Generate a new Message instance from this Descriptor and a byte string.
+
+ Args:
+ descriptor: Protobuf Descriptor object
+ byte_str: Serialized protocol buffer byte string
+
+ Returns:
+ Newly created protobuf Message object.
+ """
+ result_class = MakeClass(descriptor)
+ new_msg = result_class()
+ new_msg.ParseFromString(byte_str)
+ return new_msg
+
+
+def MakeClass(descriptor):
+ """Construct a class object for a protobuf described by descriptor.
+
+ Composite descriptors are handled by defining the new class as a member of the
+ parent class, recursing as deep as necessary.
+ This is the dynamic equivalent to:
+
+ class Parent(message.Message):
+ __metaclass__ = GeneratedProtocolMessageType
+ DESCRIPTOR = descriptor
+ class Child(message.Message):
+ __metaclass__ = GeneratedProtocolMessageType
+ DESCRIPTOR = descriptor.nested_types[0]
+
+ Sample usage:
+ file_descriptor = descriptor_pb2.FileDescriptorProto()
+ file_descriptor.ParseFromString(proto2_string)
+ msg_descriptor = descriptor.MakeDescriptor(file_descriptor.message_type[0])
+ msg_class = reflection.MakeClass(msg_descriptor)
+ msg = msg_class()
+
+ Args:
+ descriptor: A descriptor.Descriptor object describing the protobuf.
+ Returns:
+ The Message class object described by the descriptor.
+ """
+ attributes = {}
+ for name, nested_type in descriptor.nested_types_by_name.items():
+ attributes[name] = MakeClass(nested_type)
+
+ attributes[GeneratedProtocolMessageType._DESCRIPTOR_KEY] = descriptor
+
+ return GeneratedProtocolMessageType(str(descriptor.name), (message.Message,),
+ attributes)
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/service.py b/third_party/protobuf/3.0.0/python/google/protobuf/service.py
new file mode 100755
index 0000000000..9e00de7042
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/service.py
@@ -0,0 +1,226 @@
+# 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.
+
+"""DEPRECATED: Declares the RPC service interfaces.
+
+This module declares the abstract interfaces underlying proto2 RPC
+services. These are intended to be independent of any particular RPC
+implementation, so that proto2 services can be used on top of a variety
+of implementations. Starting with version 2.3.0, RPC implementations should
+not try to build on these, but should instead provide code generator plugins
+which generate code specific to the particular RPC implementation. This way
+the generated code can be more appropriate for the implementation in use
+and can avoid unnecessary layers of indirection.
+"""
+
+__author__ = 'petar@google.com (Petar Petrov)'
+
+
+class RpcException(Exception):
+ """Exception raised on failed blocking RPC method call."""
+ pass
+
+
+class Service(object):
+
+ """Abstract base interface for protocol-buffer-based RPC services.
+
+ Services themselves are abstract classes (implemented either by servers or as
+ stubs), but they subclass this base interface. The methods of this
+ interface can be used to call the methods of the service without knowing
+ its exact type at compile time (analogous to the Message interface).
+ """
+
+ def GetDescriptor():
+ """Retrieves this service's descriptor."""
+ raise NotImplementedError
+
+ def CallMethod(self, method_descriptor, rpc_controller,
+ request, done):
+ """Calls a method of the service specified by method_descriptor.
+
+ If "done" is None then the call is blocking and the response
+ message will be returned directly. Otherwise the call is asynchronous
+ and "done" will later be called with the response value.
+
+ In the blocking case, RpcException will be raised on error.
+
+ Preconditions:
+ * method_descriptor.service == GetDescriptor
+ * request is of the exact same classes as returned by
+ GetRequestClass(method).
+ * After the call has started, the request must not be modified.
+ * "rpc_controller" is of the correct type for the RPC implementation being
+ used by this Service. For stubs, the "correct type" depends on the
+ RpcChannel which the stub is using.
+
+ Postconditions:
+ * "done" will be called when the method is complete. This may be
+ before CallMethod() returns or it may be at some point in the future.
+ * If the RPC failed, the response value passed to "done" will be None.
+ Further details about the failure can be found by querying the
+ RpcController.
+ """
+ raise NotImplementedError
+
+ def GetRequestClass(self, method_descriptor):
+ """Returns the class of the request message for the specified method.
+
+ CallMethod() requires that the request is of a particular subclass of
+ Message. GetRequestClass() gets the default instance of this required
+ type.
+
+ Example:
+ method = service.GetDescriptor().FindMethodByName("Foo")
+ request = stub.GetRequestClass(method)()
+ request.ParseFromString(input)
+ service.CallMethod(method, request, callback)
+ """
+ raise NotImplementedError
+
+ def GetResponseClass(self, method_descriptor):
+ """Returns the class of the response message for the specified method.
+
+ This method isn't really needed, as the RpcChannel's CallMethod constructs
+ the response protocol message. It's provided anyway in case it is useful
+ for the caller to know the response type in advance.
+ """
+ raise NotImplementedError
+
+
+class RpcController(object):
+
+ """An RpcController mediates a single method call.
+
+ The primary purpose of the controller is to provide a way to manipulate
+ settings specific to the RPC implementation and to find out about RPC-level
+ errors. The methods provided by the RpcController interface are intended
+ to be a "least common denominator" set of features which we expect all
+ implementations to support. Specific implementations may provide more
+ advanced features (e.g. deadline propagation).
+ """
+
+ # Client-side methods below
+
+ def Reset(self):
+ """Resets the RpcController to its initial state.
+
+ After the RpcController has been reset, it may be reused in
+ a new call. Must not be called while an RPC is in progress.
+ """
+ raise NotImplementedError
+
+ def Failed(self):
+ """Returns true if the call failed.
+
+ After a call has finished, returns true if the call failed. The possible
+ reasons for failure depend on the RPC implementation. Failed() must not
+ be called before a call has finished. If Failed() returns true, the
+ contents of the response message are undefined.
+ """
+ raise NotImplementedError
+
+ def ErrorText(self):
+ """If Failed is true, returns a human-readable description of the error."""
+ raise NotImplementedError
+
+ def StartCancel(self):
+ """Initiate cancellation.
+
+ Advises the RPC system that the caller desires that the RPC call be
+ canceled. The RPC system may cancel it immediately, may wait awhile and
+ then cancel it, or may not even cancel the call at all. If the call is
+ canceled, the "done" callback will still be called and the RpcController
+ will indicate that the call failed at that time.
+ """
+ raise NotImplementedError
+
+ # Server-side methods below
+
+ def SetFailed(self, reason):
+ """Sets a failure reason.
+
+ Causes Failed() to return true on the client side. "reason" will be
+ incorporated into the message returned by ErrorText(). If you find
+ you need to return machine-readable information about failures, you
+ should incorporate it into your response protocol buffer and should
+ NOT call SetFailed().
+ """
+ raise NotImplementedError
+
+ def IsCanceled(self):
+ """Checks if the client cancelled the RPC.
+
+ If true, indicates that the client canceled the RPC, so the server may
+ as well give up on replying to it. The server should still call the
+ final "done" callback.
+ """
+ raise NotImplementedError
+
+ def NotifyOnCancel(self, callback):
+ """Sets a callback to invoke on cancel.
+
+ Asks that the given callback be called when the RPC is canceled. The
+ callback will always be called exactly once. If the RPC completes without
+ being canceled, the callback will be called after completion. If the RPC
+ has already been canceled when NotifyOnCancel() is called, the callback
+ will be called immediately.
+
+ NotifyOnCancel() must be called no more than once per request.
+ """
+ raise NotImplementedError
+
+
+class RpcChannel(object):
+
+ """Abstract interface for an RPC channel.
+
+ An RpcChannel represents a communication line to a service which can be used
+ to call that service's methods. The service may be running on another
+ machine. Normally, you should not use an RpcChannel directly, but instead
+ construct a stub {@link Service} wrapping it. Example:
+
+ Example:
+ RpcChannel channel = rpcImpl.Channel("remotehost.example.com:1234")
+ RpcController controller = rpcImpl.Controller()
+ MyService service = MyService_Stub(channel)
+ service.MyMethod(controller, request, callback)
+ """
+
+ def CallMethod(self, method_descriptor, rpc_controller,
+ request, response_class, done):
+ """Calls the method identified by the descriptor.
+
+ Call the given method of the remote service. The signature of this
+ procedure looks the same as Service.CallMethod(), but the requirements
+ are less strict in one important way: the request object doesn't have to
+ be of any specific class as long as its descriptor is method.input_type.
+ """
+ raise NotImplementedError
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/service_reflection.py b/third_party/protobuf/3.0.0/python/google/protobuf/service_reflection.py
new file mode 100755
index 0000000000..1c3636afe0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/service_reflection.py
@@ -0,0 +1,284 @@
+# 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.
+
+"""Contains metaclasses used to create protocol service and service stub
+classes from ServiceDescriptor objects at runtime.
+
+The GeneratedServiceType and GeneratedServiceStubType metaclasses are used to
+inject all useful functionality into the classes output by the protocol
+compiler at compile-time.
+"""
+
+__author__ = 'petar@google.com (Petar Petrov)'
+
+
+class GeneratedServiceType(type):
+
+ """Metaclass for service classes created at runtime from ServiceDescriptors.
+
+ Implementations for all methods described in the Service class are added here
+ by this class. We also create properties to allow getting/setting all fields
+ in the protocol message.
+
+ The protocol compiler currently uses this metaclass to create protocol service
+ classes at runtime. Clients can also manually create their own classes at
+ runtime, as in this example:
+
+ mydescriptor = ServiceDescriptor(.....)
+ class MyProtoService(service.Service):
+ __metaclass__ = GeneratedServiceType
+ DESCRIPTOR = mydescriptor
+ myservice_instance = MyProtoService()
+ ...
+ """
+
+ _DESCRIPTOR_KEY = 'DESCRIPTOR'
+
+ def __init__(cls, name, bases, dictionary):
+ """Creates a message service class.
+
+ Args:
+ name: Name of the class (ignored, but required by the metaclass
+ protocol).
+ bases: Base classes of the class being constructed.
+ dictionary: The class dictionary of the class being constructed.
+ dictionary[_DESCRIPTOR_KEY] must contain a ServiceDescriptor object
+ describing this protocol service type.
+ """
+ # Don't do anything if this class doesn't have a descriptor. This happens
+ # when a service class is subclassed.
+ if GeneratedServiceType._DESCRIPTOR_KEY not in dictionary:
+ return
+ descriptor = dictionary[GeneratedServiceType._DESCRIPTOR_KEY]
+ service_builder = _ServiceBuilder(descriptor)
+ service_builder.BuildService(cls)
+
+
+class GeneratedServiceStubType(GeneratedServiceType):
+
+ """Metaclass for service stubs created at runtime from ServiceDescriptors.
+
+ This class has similar responsibilities as GeneratedServiceType, except that
+ it creates the service stub classes.
+ """
+
+ _DESCRIPTOR_KEY = 'DESCRIPTOR'
+
+ def __init__(cls, name, bases, dictionary):
+ """Creates a message service stub class.
+
+ Args:
+ name: Name of the class (ignored, here).
+ bases: Base classes of the class being constructed.
+ dictionary: The class dictionary of the class being constructed.
+ dictionary[_DESCRIPTOR_KEY] must contain a ServiceDescriptor object
+ describing this protocol service type.
+ """
+ super(GeneratedServiceStubType, cls).__init__(name, bases, dictionary)
+ # Don't do anything if this class doesn't have a descriptor. This happens
+ # when a service stub is subclassed.
+ if GeneratedServiceStubType._DESCRIPTOR_KEY not in dictionary:
+ return
+ descriptor = dictionary[GeneratedServiceStubType._DESCRIPTOR_KEY]
+ service_stub_builder = _ServiceStubBuilder(descriptor)
+ service_stub_builder.BuildServiceStub(cls)
+
+
+class _ServiceBuilder(object):
+
+ """This class constructs a protocol service class using a service descriptor.
+
+ Given a service descriptor, this class constructs a class that represents
+ the specified service descriptor. One service builder instance constructs
+ exactly one service class. That means all instances of that class share the
+ same builder.
+ """
+
+ def __init__(self, service_descriptor):
+ """Initializes an instance of the service class builder.
+
+ Args:
+ service_descriptor: ServiceDescriptor to use when constructing the
+ service class.
+ """
+ self.descriptor = service_descriptor
+
+ def BuildService(self, cls):
+ """Constructs the service class.
+
+ Args:
+ cls: The class that will be constructed.
+ """
+
+ # CallMethod needs to operate with an instance of the Service class. This
+ # internal wrapper function exists only to be able to pass the service
+ # instance to the method that does the real CallMethod work.
+ def _WrapCallMethod(srvc, method_descriptor,
+ rpc_controller, request, callback):
+ return self._CallMethod(srvc, method_descriptor,
+ rpc_controller, request, callback)
+ self.cls = cls
+ cls.CallMethod = _WrapCallMethod
+ cls.GetDescriptor = staticmethod(lambda: self.descriptor)
+ cls.GetDescriptor.__doc__ = "Returns the service descriptor."
+ cls.GetRequestClass = self._GetRequestClass
+ cls.GetResponseClass = self._GetResponseClass
+ for method in self.descriptor.methods:
+ setattr(cls, method.name, self._GenerateNonImplementedMethod(method))
+
+ def _CallMethod(self, srvc, method_descriptor,
+ rpc_controller, request, callback):
+ """Calls the method described by a given method descriptor.
+
+ Args:
+ srvc: Instance of the service for which this method is called.
+ method_descriptor: Descriptor that represent the method to call.
+ rpc_controller: RPC controller to use for this method's execution.
+ request: Request protocol message.
+ callback: A callback to invoke after the method has completed.
+ """
+ if method_descriptor.containing_service != self.descriptor:
+ raise RuntimeError(
+ 'CallMethod() given method descriptor for wrong service type.')
+ method = getattr(srvc, method_descriptor.name)
+ return method(rpc_controller, request, callback)
+
+ def _GetRequestClass(self, method_descriptor):
+ """Returns the class of the request protocol message.
+
+ Args:
+ method_descriptor: Descriptor of the method for which to return the
+ request protocol message class.
+
+ Returns:
+ A class that represents the input protocol message of the specified
+ method.
+ """
+ if method_descriptor.containing_service != self.descriptor:
+ raise RuntimeError(
+ 'GetRequestClass() given method descriptor for wrong service type.')
+ return method_descriptor.input_type._concrete_class
+
+ def _GetResponseClass(self, method_descriptor):
+ """Returns the class of the response protocol message.
+
+ Args:
+ method_descriptor: Descriptor of the method for which to return the
+ response protocol message class.
+
+ Returns:
+ A class that represents the output protocol message of the specified
+ method.
+ """
+ if method_descriptor.containing_service != self.descriptor:
+ raise RuntimeError(
+ 'GetResponseClass() given method descriptor for wrong service type.')
+ return method_descriptor.output_type._concrete_class
+
+ def _GenerateNonImplementedMethod(self, method):
+ """Generates and returns a method that can be set for a service methods.
+
+ Args:
+ method: Descriptor of the service method for which a method is to be
+ generated.
+
+ Returns:
+ A method that can be added to the service class.
+ """
+ return lambda inst, rpc_controller, request, callback: (
+ self._NonImplementedMethod(method.name, rpc_controller, callback))
+
+ def _NonImplementedMethod(self, method_name, rpc_controller, callback):
+ """The body of all methods in the generated service class.
+
+ Args:
+ method_name: Name of the method being executed.
+ rpc_controller: RPC controller used to execute this method.
+ callback: A callback which will be invoked when the method finishes.
+ """
+ rpc_controller.SetFailed('Method %s not implemented.' % method_name)
+ callback(None)
+
+
+class _ServiceStubBuilder(object):
+
+ """Constructs a protocol service stub class using a service descriptor.
+
+ Given a service descriptor, this class constructs a suitable stub class.
+ A stub is just a type-safe wrapper around an RpcChannel which emulates a
+ local implementation of the service.
+
+ One service stub builder instance constructs exactly one class. It means all
+ instances of that class share the same service stub builder.
+ """
+
+ def __init__(self, service_descriptor):
+ """Initializes an instance of the service stub class builder.
+
+ Args:
+ service_descriptor: ServiceDescriptor to use when constructing the
+ stub class.
+ """
+ self.descriptor = service_descriptor
+
+ def BuildServiceStub(self, cls):
+ """Constructs the stub class.
+
+ Args:
+ cls: The class that will be constructed.
+ """
+
+ def _ServiceStubInit(stub, rpc_channel):
+ stub.rpc_channel = rpc_channel
+ self.cls = cls
+ cls.__init__ = _ServiceStubInit
+ for method in self.descriptor.methods:
+ setattr(cls, method.name, self._GenerateStubMethod(method))
+
+ def _GenerateStubMethod(self, method):
+ return (lambda inst, rpc_controller, request, callback=None:
+ self._StubMethod(inst, method, rpc_controller, request, callback))
+
+ def _StubMethod(self, stub, method_descriptor,
+ rpc_controller, request, callback):
+ """The body of all service methods in the generated stub class.
+
+ Args:
+ stub: Stub instance.
+ method_descriptor: Descriptor of the invoked method.
+ rpc_controller: Rpc controller to execute the method.
+ request: Request protocol message.
+ callback: A callback to execute when the method finishes.
+ Returns:
+ Response message (in case of blocking call).
+ """
+ return stub.rpc_channel.CallMethod(
+ method_descriptor, rpc_controller, request,
+ method_descriptor.output_type._concrete_class, callback)
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/symbol_database.py b/third_party/protobuf/3.0.0/python/google/protobuf/symbol_database.py
new file mode 100644
index 0000000000..aa466abd26
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/symbol_database.py
@@ -0,0 +1,169 @@
+# 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.
+
+"""A database of Python protocol buffer generated symbols.
+
+SymbolDatabase is the MessageFactory for messages generated at compile time,
+and makes it easy to create new instances of a registered type, given only the
+type's protocol buffer symbol name.
+
+Example usage:
+
+ db = symbol_database.SymbolDatabase()
+
+ # Register symbols of interest, from one or multiple files.
+ db.RegisterFileDescriptor(my_proto_pb2.DESCRIPTOR)
+ db.RegisterMessage(my_proto_pb2.MyMessage)
+ db.RegisterEnumDescriptor(my_proto_pb2.MyEnum.DESCRIPTOR)
+
+ # The database can be used as a MessageFactory, to generate types based on
+ # their name:
+ types = db.GetMessages(['my_proto.proto'])
+ my_message_instance = types['MyMessage']()
+
+ # The database's underlying descriptor pool can be queried, so it's not
+ # necessary to know a type's filename to be able to generate it:
+ filename = db.pool.FindFileContainingSymbol('MyMessage')
+ my_message_instance = db.GetMessages([filename])['MyMessage']()
+
+ # This functionality is also provided directly via a convenience method:
+ my_message_instance = db.GetSymbol('MyMessage')()
+"""
+
+
+from google.protobuf import descriptor_pool
+from google.protobuf import message_factory
+
+
+class SymbolDatabase(message_factory.MessageFactory):
+ """A database of Python generated symbols."""
+
+ def RegisterMessage(self, message):
+ """Registers the given message type in the local database.
+
+ Calls to GetSymbol() and GetMessages() will return messages registered here.
+
+ Args:
+ message: a message.Message, to be registered.
+
+ Returns:
+ The provided message.
+ """
+
+ desc = message.DESCRIPTOR
+ self._classes[desc.full_name] = message
+ self.pool.AddDescriptor(desc)
+ return message
+
+ def RegisterEnumDescriptor(self, enum_descriptor):
+ """Registers the given enum descriptor in the local database.
+
+ Args:
+ enum_descriptor: a descriptor.EnumDescriptor.
+
+ Returns:
+ The provided descriptor.
+ """
+ self.pool.AddEnumDescriptor(enum_descriptor)
+ return enum_descriptor
+
+ def RegisterFileDescriptor(self, file_descriptor):
+ """Registers the given file descriptor in the local database.
+
+ Args:
+ file_descriptor: a descriptor.FileDescriptor.
+
+ Returns:
+ The provided descriptor.
+ """
+ self.pool.AddFileDescriptor(file_descriptor)
+
+ def GetSymbol(self, symbol):
+ """Tries to find a symbol in the local database.
+
+ Currently, this method only returns message.Message instances, however, if
+ may be extended in future to support other symbol types.
+
+ Args:
+ symbol: A str, a protocol buffer symbol.
+
+ Returns:
+ A Python class corresponding to the symbol.
+
+ Raises:
+ KeyError: if the symbol could not be found.
+ """
+
+ return self._classes[symbol]
+
+ def GetMessages(self, files):
+ # TODO(amauryfa): Fix the differences with MessageFactory.
+ """Gets all registered messages from a specified file.
+
+ Only messages already created and registered will be returned; (this is the
+ case for imported _pb2 modules)
+ But unlike MessageFactory, this version also returns nested messages.
+
+ Args:
+ files: The file names to extract messages from.
+
+ Returns:
+ A dictionary mapping proto names to the message classes.
+
+ Raises:
+ KeyError: if a file could not be found.
+ """
+
+ def _GetAllMessageNames(desc):
+ """Walk a message Descriptor and recursively yields all message names."""
+ yield desc.full_name
+ for msg_desc in desc.nested_types:
+ for full_name in _GetAllMessageNames(msg_desc):
+ yield full_name
+
+ result = {}
+ for file_name in files:
+ file_desc = self.pool.FindFileByName(file_name)
+ for msg_desc in file_desc.message_types_by_name.values():
+ for full_name in _GetAllMessageNames(msg_desc):
+ try:
+ result[full_name] = self._classes[full_name]
+ except KeyError:
+ # This descriptor has no registered class, skip it.
+ pass
+ return result
+
+
+_DEFAULT = SymbolDatabase(pool=descriptor_pool.Default())
+
+
+def Default():
+ """Returns the default SymbolDatabase."""
+ return _DEFAULT
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/text_encoding.py b/third_party/protobuf/3.0.0/python/google/protobuf/text_encoding.py
new file mode 100644
index 0000000000..9899563825
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/text_encoding.py
@@ -0,0 +1,107 @@
+# 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.
+
+"""Encoding related utilities."""
+import re
+
+import six
+
+# Lookup table for utf8
+_cescape_utf8_to_str = [chr(i) for i in range(0, 256)]
+_cescape_utf8_to_str[9] = r'\t' # optional escape
+_cescape_utf8_to_str[10] = r'\n' # optional escape
+_cescape_utf8_to_str[13] = r'\r' # optional escape
+_cescape_utf8_to_str[39] = r"\'" # optional escape
+
+_cescape_utf8_to_str[34] = r'\"' # necessary escape
+_cescape_utf8_to_str[92] = r'\\' # necessary escape
+
+# Lookup table for non-utf8, with necessary escapes at (o >= 127 or o < 32)
+_cescape_byte_to_str = ([r'\%03o' % i for i in range(0, 32)] +
+ [chr(i) for i in range(32, 127)] +
+ [r'\%03o' % i for i in range(127, 256)])
+_cescape_byte_to_str[9] = r'\t' # optional escape
+_cescape_byte_to_str[10] = r'\n' # optional escape
+_cescape_byte_to_str[13] = r'\r' # optional escape
+_cescape_byte_to_str[39] = r"\'" # optional escape
+
+_cescape_byte_to_str[34] = r'\"' # necessary escape
+_cescape_byte_to_str[92] = r'\\' # necessary escape
+
+
+def CEscape(text, as_utf8):
+ """Escape a bytes string for use in an ascii protocol buffer.
+
+ text.encode('string_escape') does not seem to satisfy our needs as it
+ encodes unprintable characters using two-digit hex escapes whereas our
+ C++ unescaping function allows hex escapes to be any length. So,
+ "\0011".encode('string_escape') ends up being "\\x011", which will be
+ decoded in C++ as a single-character string with char code 0x11.
+
+ Args:
+ text: A byte string to be escaped
+ as_utf8: Specifies if result should be returned in UTF-8 encoding
+ Returns:
+ Escaped string
+ """
+ # PY3 hack: make Ord work for str and bytes:
+ # //platforms/networking/data uses unicode here, hence basestring.
+ Ord = ord if isinstance(text, six.string_types) else lambda x: x
+ if as_utf8:
+ return ''.join(_cescape_utf8_to_str[Ord(c)] for c in text)
+ return ''.join(_cescape_byte_to_str[Ord(c)] for c in text)
+
+
+_CUNESCAPE_HEX = re.compile(r'(\\+)x([0-9a-fA-F])(?![0-9a-fA-F])')
+_cescape_highbit_to_str = ([chr(i) for i in range(0, 127)] +
+ [r'\%03o' % i for i in range(127, 256)])
+
+
+def CUnescape(text):
+ """Unescape a text string with C-style escape sequences to UTF-8 bytes."""
+
+ def ReplaceHex(m):
+ # Only replace the match if the number of leading back slashes is odd. i.e.
+ # the slash itself is not escaped.
+ if len(m.group(1)) & 1:
+ return m.group(1) + 'x0' + m.group(2)
+ return m.group(0)
+
+ # This is required because the 'string_escape' encoding doesn't
+ # allow single-digit hex escapes (like '\xf').
+ result = _CUNESCAPE_HEX.sub(ReplaceHex, text)
+
+ if str is bytes: # PY2
+ return result.decode('string_escape')
+ result = ''.join(_cescape_highbit_to_str[ord(c)] for c in result)
+ return (result.encode('ascii') # Make it bytes to allow decode.
+ .decode('unicode_escape')
+ # Make it bytes again to return the proper type.
+ .encode('raw_unicode_escape'))
diff --git a/third_party/protobuf/3.0.0/python/google/protobuf/text_format.py b/third_party/protobuf/3.0.0/python/google/protobuf/text_format.py
new file mode 100755
index 0000000000..06b79d77d1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/python/google/protobuf/text_format.py
@@ -0,0 +1,1490 @@
+# 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.
+
+"""Contains routines for printing protocol messages in text format.
+
+Simple usage example:
+
+ # Create a proto object and serialize it to a text proto string.
+ message = my_proto_pb2.MyMessage(foo='bar')
+ text_proto = text_format.MessageToString(message)
+
+ # Parse a text proto string.
+ message = text_format.Parse(text_proto, my_proto_pb2.MyMessage())
+"""
+
+__author__ = 'kenton@google.com (Kenton Varda)'
+
+import io
+import re
+
+import six
+
+if six.PY3:
+ long = int # pylint: disable=redefined-builtin,invalid-name
+
+# pylint: disable=g-import-not-at-top
+from google.protobuf.internal import type_checkers
+from google.protobuf import descriptor
+from google.protobuf import text_encoding
+
+__all__ = ['MessageToString', 'PrintMessage', 'PrintField', 'PrintFieldValue',
+ 'Merge']
+
+_INTEGER_CHECKERS = (type_checkers.Uint32ValueChecker(),
+ type_checkers.Int32ValueChecker(),
+ type_checkers.Uint64ValueChecker(),
+ type_checkers.Int64ValueChecker())
+_FLOAT_INFINITY = re.compile('-?inf(?:inity)?f?', re.IGNORECASE)
+_FLOAT_NAN = re.compile('nanf?', re.IGNORECASE)
+_FLOAT_TYPES = frozenset([descriptor.FieldDescriptor.CPPTYPE_FLOAT,
+ descriptor.FieldDescriptor.CPPTYPE_DOUBLE])
+_QUOTES = frozenset(("'", '"'))
+_ANY_FULL_TYPE_NAME = 'google.protobuf.Any'
+
+
+class Error(Exception):
+ """Top-level module error for text_format."""
+
+
+class ParseError(Error):
+ """Thrown in case of text parsing or tokenizing error."""
+
+ def __init__(self, message=None, line=None, column=None):
+ if message is not None and line is not None:
+ loc = str(line)
+ if column is not None:
+ loc += ':{0}'.format(column)
+ message = '{0} : {1}'.format(loc, message)
+ if message is not None:
+ super(ParseError, self).__init__(message)
+ else:
+ super(ParseError, self).__init__()
+ self._line = line
+ self._column = column
+
+ def GetLine(self):
+ return self._line
+
+ def GetColumn(self):
+ return self._column
+
+
+class TextWriter(object):
+
+ def __init__(self, as_utf8):
+ if six.PY2:
+ self._writer = io.BytesIO()
+ else:
+ self._writer = io.StringIO()
+
+ def write(self, val):
+ if six.PY2:
+ if isinstance(val, six.text_type):
+ val = val.encode('utf-8')
+ return self._writer.write(val)
+
+ def close(self):
+ return self._writer.close()
+
+ def getvalue(self):
+ return self._writer.getvalue()
+
+
+def MessageToString(message,
+ as_utf8=False,
+ as_one_line=False,
+ pointy_brackets=False,
+ use_index_order=False,
+ float_format=None,
+ use_field_number=False,
+ descriptor_pool=None,
+ indent=0):
+ """Convert protobuf message to text format.
+
+ Floating point values can be formatted compactly with 15 digits of
+ precision (which is the most that IEEE 754 "double" can guarantee)
+ using float_format='.15g'. To ensure that converting to text and back to a
+ proto will result in an identical value, float_format='.17g' should be used.
+
+ Args:
+ message: The protocol buffers message.
+ as_utf8: Produce text output in UTF8 format.
+ as_one_line: Don't introduce newlines between fields.
+ pointy_brackets: If True, use angle brackets instead of curly braces for
+ nesting.
+ use_index_order: If True, print fields of a proto message using the order
+ defined in source code instead of the field number. By default, use the
+ field number order.
+ float_format: If set, use this to specify floating point number formatting
+ (per the "Format Specification Mini-Language"); otherwise, str() is used.
+ use_field_number: If True, print field numbers instead of names.
+ descriptor_pool: A DescriptorPool used to resolve Any types.
+ indent: The indent level, in terms of spaces, for pretty print.
+
+ Returns:
+ A string of the text formatted protocol buffer message.
+ """
+ out = TextWriter(as_utf8)
+ printer = _Printer(out, indent, as_utf8, as_one_line, pointy_brackets,
+ use_index_order, float_format, use_field_number,
+ descriptor_pool)
+ printer.PrintMessage(message)
+ result = out.getvalue()
+ out.close()
+ if as_one_line:
+ return result.rstrip()
+ return result
+
+
+def _IsMapEntry(field):
+ return (field.type == descriptor.FieldDescriptor.TYPE_MESSAGE and
+ field.message_type.has_options and
+ field.message_type.GetOptions().map_entry)
+
+
+def PrintMessage(message,
+ out,
+ indent=0,
+ as_utf8=False,
+ as_one_line=False,
+ pointy_brackets=False,
+ use_index_order=False,
+ float_format=None,
+ use_field_number=False,
+ descriptor_pool=None):
+ printer = _Printer(out, indent, as_utf8, as_one_line, pointy_brackets,
+ use_index_order, float_format, use_field_number,
+ descriptor_pool)
+ printer.PrintMessage(message)
+
+
+def PrintField(field,
+ value,
+ out,
+ indent=0,
+ as_utf8=False,
+ as_one_line=False,
+ pointy_brackets=False,
+ use_index_order=False,
+ float_format=None):
+ """Print a single field name/value pair."""
+ printer = _Printer(out, indent, as_utf8, as_one_line, pointy_brackets,
+ use_index_order, float_format)
+ printer.PrintField(field, value)
+
+
+def PrintFieldValue(field,
+ value,
+ out,
+ indent=0,
+ as_utf8=False,
+ as_one_line=False,
+ pointy_brackets=False,
+ use_index_order=False,
+ float_format=None):
+ """Print a single field value (not including name)."""
+ printer = _Printer(out, indent, as_utf8, as_one_line, pointy_brackets,
+ use_index_order, float_format)
+ printer.PrintFieldValue(field, value)
+
+
+def _BuildMessageFromTypeName(type_name, descriptor_pool):
+ """Returns a protobuf message instance.
+
+ Args:
+ type_name: Fully-qualified protobuf message type name string.
+ descriptor_pool: DescriptorPool instance.
+
+ Returns:
+ A Message instance of type matching type_name, or None if the a Descriptor
+ wasn't found matching type_name.
+ """
+ # pylint: disable=g-import-not-at-top
+ from google.protobuf import message_factory
+ factory = message_factory.MessageFactory(descriptor_pool)
+ try:
+ message_descriptor = descriptor_pool.FindMessageTypeByName(type_name)
+ except KeyError:
+ return None
+ message_type = factory.GetPrototype(message_descriptor)
+ return message_type()
+
+
+class _Printer(object):
+ """Text format printer for protocol message."""
+
+ def __init__(self,
+ out,
+ indent=0,
+ as_utf8=False,
+ as_one_line=False,
+ pointy_brackets=False,
+ use_index_order=False,
+ float_format=None,
+ use_field_number=False,
+ descriptor_pool=None):
+ """Initialize the Printer.
+
+ Floating point values can be formatted compactly with 15 digits of
+ precision (which is the most that IEEE 754 "double" can guarantee)
+ using float_format='.15g'. To ensure that converting to text and back to a
+ proto will result in an identical value, float_format='.17g' should be used.
+
+ Args:
+ out: To record the text format result.
+ indent: The indent level for pretty print.
+ as_utf8: Produce text output in UTF8 format.
+ as_one_line: Don't introduce newlines between fields.
+ pointy_brackets: If True, use angle brackets instead of curly braces for
+ nesting.
+ use_index_order: If True, print fields of a proto message using the order
+ defined in source code instead of the field number. By default, use the
+ field number order.
+ float_format: If set, use this to specify floating point number formatting
+ (per the "Format Specification Mini-Language"); otherwise, str() is
+ used.
+ use_field_number: If True, print field numbers instead of names.
+ descriptor_pool: A DescriptorPool used to resolve Any types.
+ """
+ self.out = out
+ self.indent = indent
+ self.as_utf8 = as_utf8
+ self.as_one_line = as_one_line
+ self.pointy_brackets = pointy_brackets
+ self.use_index_order = use_index_order
+ self.float_format = float_format
+ self.use_field_number = use_field_number
+ self.descriptor_pool = descriptor_pool
+
+ def _TryPrintAsAnyMessage(self, message):
+ """Serializes if message is a google.protobuf.Any field."""
+ packed_message = _BuildMessageFromTypeName(message.TypeName(),
+ self.descriptor_pool)
+ if packed_message:
+ packed_message.MergeFromString(message.value)
+ self.out.write('%s[%s]' % (self.indent * ' ', message.type_url))
+ self._PrintMessageFieldValue(packed_message)
+ self.out.write(' ' if self.as_one_line else '\n')
+ return True
+ else:
+ return False
+
+ def PrintMessage(self, message):
+ """Convert protobuf message to text format.
+
+ Args:
+ message: The protocol buffers message.
+ """
+ if (message.DESCRIPTOR.full_name == _ANY_FULL_TYPE_NAME and
+ self.descriptor_pool and self._TryPrintAsAnyMessage(message)):
+ return
+ fields = message.ListFields()
+ if self.use_index_order:
+ fields.sort(key=lambda x: x[0].index)
+ for field, value in fields:
+ if _IsMapEntry(field):
+ for key in sorted(value):
+ # This is slow for maps with submessage entires because it copies the
+ # entire tree. Unfortunately this would take significant refactoring
+ # of this file to work around.
+ #
+ # TODO(haberman): refactor and optimize if this becomes an issue.
+ entry_submsg = field.message_type._concrete_class(key=key,
+ value=value[key])
+ self.PrintField(field, entry_submsg)
+ elif field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ for element in value:
+ self.PrintField(field, element)
+ else:
+ self.PrintField(field, value)
+
+ def PrintField(self, field, value):
+ """Print a single field name/value pair."""
+ out = self.out
+ out.write(' ' * self.indent)
+ if self.use_field_number:
+ out.write(str(field.number))
+ else:
+ if field.is_extension:
+ out.write('[')
+ if (field.containing_type.GetOptions().message_set_wire_format and
+ field.type == descriptor.FieldDescriptor.TYPE_MESSAGE and
+ field.label == descriptor.FieldDescriptor.LABEL_OPTIONAL):
+ out.write(field.message_type.full_name)
+ else:
+ out.write(field.full_name)
+ out.write(']')
+ elif field.type == descriptor.FieldDescriptor.TYPE_GROUP:
+ # For groups, use the capitalized name.
+ out.write(field.message_type.name)
+ else:
+ out.write(field.name)
+
+ if field.cpp_type != descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ # The colon is optional in this case, but our cross-language golden files
+ # don't include it.
+ out.write(': ')
+
+ self.PrintFieldValue(field, value)
+ if self.as_one_line:
+ out.write(' ')
+ else:
+ out.write('\n')
+
+ def _PrintMessageFieldValue(self, value):
+ if self.pointy_brackets:
+ openb = '<'
+ closeb = '>'
+ else:
+ openb = '{'
+ closeb = '}'
+
+ if self.as_one_line:
+ self.out.write(' %s ' % openb)
+ self.PrintMessage(value)
+ self.out.write(closeb)
+ else:
+ self.out.write(' %s\n' % openb)
+ self.indent += 2
+ self.PrintMessage(value)
+ self.indent -= 2
+ self.out.write(' ' * self.indent + closeb)
+
+ def PrintFieldValue(self, field, value):
+ """Print a single field value (not including name).
+
+ For repeated fields, the value should be a single element.
+
+ Args:
+ field: The descriptor of the field to be printed.
+ value: The value of the field.
+ """
+ out = self.out
+ if field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ self._PrintMessageFieldValue(value)
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_ENUM:
+ enum_value = field.enum_type.values_by_number.get(value, None)
+ if enum_value is not None:
+ out.write(enum_value.name)
+ else:
+ out.write(str(value))
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_STRING:
+ out.write('\"')
+ if isinstance(value, six.text_type):
+ out_value = value.encode('utf-8')
+ else:
+ out_value = value
+ if field.type == descriptor.FieldDescriptor.TYPE_BYTES:
+ # We need to escape non-UTF8 chars in TYPE_BYTES field.
+ out_as_utf8 = False
+ else:
+ out_as_utf8 = self.as_utf8
+ out.write(text_encoding.CEscape(out_value, out_as_utf8))
+ out.write('\"')
+ elif field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_BOOL:
+ if value:
+ out.write('true')
+ else:
+ out.write('false')
+ elif field.cpp_type in _FLOAT_TYPES and self.float_format is not None:
+ out.write('{1:{0}}'.format(self.float_format, value))
+ else:
+ out.write(str(value))
+
+
+def Parse(text,
+ message,
+ allow_unknown_extension=False,
+ allow_field_number=False):
+ """Parses a text representation of a protocol message into a message.
+
+ Args:
+ text: Message text representation.
+ message: A protocol buffer message to merge into.
+ allow_unknown_extension: if True, skip over missing extensions and keep
+ parsing
+ allow_field_number: if True, both field number and field name are allowed.
+
+ Returns:
+ The same message passed as argument.
+
+ Raises:
+ ParseError: On text parsing problems.
+ """
+ if not isinstance(text, str):
+ text = text.decode('utf-8')
+ return ParseLines(
+ text.split('\n'), message, allow_unknown_extension, allow_field_number)
+
+
+def Merge(text,
+ message,
+ allow_unknown_extension=False,
+ allow_field_number=False,
+ descriptor_pool=None):
+ """Parses a text representation of a protocol message into a message.
+
+ Like Parse(), but allows repeated values for a non-repeated field, and uses
+ the last one.
+
+ Args:
+ text: Message text representation.
+ message: A protocol buffer message to merge into.
+ allow_unknown_extension: if True, skip over missing extensions and keep
+ parsing
+ allow_field_number: if True, both field number and field name are allowed.
+ descriptor_pool: A DescriptorPool used to resolve Any types.
+
+ Returns:
+ The same message passed as argument.
+
+ Raises:
+ ParseError: On text parsing problems.
+ """
+ return MergeLines(
+ text.split('\n'),
+ message,
+ allow_unknown_extension,
+ allow_field_number,
+ descriptor_pool=descriptor_pool)
+
+
+def ParseLines(lines,
+ message,
+ allow_unknown_extension=False,
+ allow_field_number=False):
+ """Parses a text representation of a protocol message into a message.
+
+ Args:
+ lines: An iterable of lines of a message's text representation.
+ message: A protocol buffer message to merge into.
+ allow_unknown_extension: if True, skip over missing extensions and keep
+ parsing
+ allow_field_number: if True, both field number and field name are allowed.
+ descriptor_pool: A DescriptorPool used to resolve Any types.
+
+ Returns:
+ The same message passed as argument.
+
+ Raises:
+ ParseError: On text parsing problems.
+ """
+ parser = _Parser(allow_unknown_extension, allow_field_number)
+ return parser.ParseLines(lines, message)
+
+
+def MergeLines(lines,
+ message,
+ allow_unknown_extension=False,
+ allow_field_number=False,
+ descriptor_pool=None):
+ """Parses a text representation of a protocol message into a message.
+
+ Args:
+ lines: An iterable of lines of a message's text representation.
+ message: A protocol buffer message to merge into.
+ allow_unknown_extension: if True, skip over missing extensions and keep
+ parsing
+ allow_field_number: if True, both field number and field name are allowed.
+
+ Returns:
+ The same message passed as argument.
+
+ Raises:
+ ParseError: On text parsing problems.
+ """
+ parser = _Parser(allow_unknown_extension,
+ allow_field_number,
+ descriptor_pool=descriptor_pool)
+ return parser.MergeLines(lines, message)
+
+
+class _Parser(object):
+ """Text format parser for protocol message."""
+
+ def __init__(self,
+ allow_unknown_extension=False,
+ allow_field_number=False,
+ descriptor_pool=None):
+ self.allow_unknown_extension = allow_unknown_extension
+ self.allow_field_number = allow_field_number
+ self.descriptor_pool = descriptor_pool
+
+ def ParseFromString(self, text, message):
+ """Parses a text representation of a protocol message into a message."""
+ if not isinstance(text, str):
+ text = text.decode('utf-8')
+ return self.ParseLines(text.split('\n'), message)
+
+ def ParseLines(self, lines, message):
+ """Parses a text representation of a protocol message into a message."""
+ self._allow_multiple_scalars = False
+ self._ParseOrMerge(lines, message)
+ return message
+
+ def MergeFromString(self, text, message):
+ """Merges a text representation of a protocol message into a message."""
+ return self._MergeLines(text.split('\n'), message)
+
+ def MergeLines(self, lines, message):
+ """Merges a text representation of a protocol message into a message."""
+ self._allow_multiple_scalars = True
+ self._ParseOrMerge(lines, message)
+ return message
+
+ def _ParseOrMerge(self, lines, message):
+ """Converts a text representation of a protocol message into a message.
+
+ Args:
+ lines: Lines of a message's text representation.
+ message: A protocol buffer message to merge into.
+
+ Raises:
+ ParseError: On text parsing problems.
+ """
+ tokenizer = Tokenizer(lines)
+ while not tokenizer.AtEnd():
+ self._MergeField(tokenizer, message)
+
+ def _MergeField(self, tokenizer, message):
+ """Merges a single protocol message field into a message.
+
+ Args:
+ tokenizer: A tokenizer to parse the field name and values.
+ message: A protocol message to record the data.
+
+ Raises:
+ ParseError: In case of text parsing problems.
+ """
+ message_descriptor = message.DESCRIPTOR
+ if (hasattr(message_descriptor, 'syntax') and
+ message_descriptor.syntax == 'proto3'):
+ # Proto3 doesn't represent presence so we can't test if multiple
+ # scalars have occurred. We have to allow them.
+ self._allow_multiple_scalars = True
+ if tokenizer.TryConsume('['):
+ name = [tokenizer.ConsumeIdentifier()]
+ while tokenizer.TryConsume('.'):
+ name.append(tokenizer.ConsumeIdentifier())
+ name = '.'.join(name)
+
+ if not message_descriptor.is_extendable:
+ raise tokenizer.ParseErrorPreviousToken(
+ 'Message type "%s" does not have extensions.' %
+ message_descriptor.full_name)
+ # pylint: disable=protected-access
+ field = message.Extensions._FindExtensionByName(name)
+ # pylint: enable=protected-access
+ if not field:
+ if self.allow_unknown_extension:
+ field = None
+ else:
+ raise tokenizer.ParseErrorPreviousToken(
+ 'Extension "%s" not registered.' % name)
+ elif message_descriptor != field.containing_type:
+ raise tokenizer.ParseErrorPreviousToken(
+ 'Extension "%s" does not extend message type "%s".' %
+ (name, message_descriptor.full_name))
+
+ tokenizer.Consume(']')
+
+ else:
+ name = tokenizer.ConsumeIdentifierOrNumber()
+ if self.allow_field_number and name.isdigit():
+ number = ParseInteger(name, True, True)
+ field = message_descriptor.fields_by_number.get(number, None)
+ if not field and message_descriptor.is_extendable:
+ field = message.Extensions._FindExtensionByNumber(number)
+ else:
+ field = message_descriptor.fields_by_name.get(name, None)
+
+ # Group names are expected to be capitalized as they appear in the
+ # .proto file, which actually matches their type names, not their field
+ # names.
+ if not field:
+ field = message_descriptor.fields_by_name.get(name.lower(), None)
+ if field and field.type != descriptor.FieldDescriptor.TYPE_GROUP:
+ field = None
+
+ if (field and field.type == descriptor.FieldDescriptor.TYPE_GROUP and
+ field.message_type.name != name):
+ field = None
+
+ if not field:
+ raise tokenizer.ParseErrorPreviousToken(
+ 'Message type "%s" has no field named "%s".' %
+ (message_descriptor.full_name, name))
+
+ if field:
+ if not self._allow_multiple_scalars and field.containing_oneof:
+ # Check if there's a different field set in this oneof.
+ # Note that we ignore the case if the same field was set before, and we
+ # apply _allow_multiple_scalars to non-scalar fields as well.
+ which_oneof = message.WhichOneof(field.containing_oneof.name)
+ if which_oneof is not None and which_oneof != field.name:
+ raise tokenizer.ParseErrorPreviousToken(
+ 'Field "%s" is specified along with field "%s", another member '
+ 'of oneof "%s" for message type "%s".' %
+ (field.name, which_oneof, field.containing_oneof.name,
+ message_descriptor.full_name))
+
+ if field.cpp_type == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ tokenizer.TryConsume(':')
+ merger = self._MergeMessageField
+ else:
+ tokenizer.Consume(':')
+ merger = self._MergeScalarField
+
+ if (field.label == descriptor.FieldDescriptor.LABEL_REPEATED and
+ tokenizer.TryConsume('[')):
+ # Short repeated format, e.g. "foo: [1, 2, 3]"
+ while True:
+ merger(tokenizer, message, field)
+ if tokenizer.TryConsume(']'):
+ break
+ tokenizer.Consume(',')
+
+ else:
+ merger(tokenizer, message, field)
+
+ else: # Proto field is unknown.
+ assert self.allow_unknown_extension
+ _SkipFieldContents(tokenizer)
+
+ # For historical reasons, fields may optionally be separated by commas or
+ # semicolons.
+ if not tokenizer.TryConsume(','):
+ tokenizer.TryConsume(';')
+
+ def _ConsumeAnyTypeUrl(self, tokenizer):
+ """Consumes a google.protobuf.Any type URL and returns the type name."""
+ # Consume "type.googleapis.com/".
+ tokenizer.ConsumeIdentifier()
+ tokenizer.Consume('.')
+ tokenizer.ConsumeIdentifier()
+ tokenizer.Consume('.')
+ tokenizer.ConsumeIdentifier()
+ tokenizer.Consume('/')
+ # Consume the fully-qualified type name.
+ name = [tokenizer.ConsumeIdentifier()]
+ while tokenizer.TryConsume('.'):
+ name.append(tokenizer.ConsumeIdentifier())
+ return '.'.join(name)
+
+ def _MergeMessageField(self, tokenizer, message, field):
+ """Merges a single scalar field into a message.
+
+ Args:
+ tokenizer: A tokenizer to parse the field value.
+ message: The message of which field is a member.
+ field: The descriptor of the field to be merged.
+
+ Raises:
+ ParseError: In case of text parsing problems.
+ """
+ is_map_entry = _IsMapEntry(field)
+
+ if tokenizer.TryConsume('<'):
+ end_token = '>'
+ else:
+ tokenizer.Consume('{')
+ end_token = '}'
+
+ if (field.message_type.full_name == _ANY_FULL_TYPE_NAME and
+ tokenizer.TryConsume('[')):
+ packed_type_name = self._ConsumeAnyTypeUrl(tokenizer)
+ tokenizer.Consume(']')
+ tokenizer.TryConsume(':')
+ if tokenizer.TryConsume('<'):
+ expanded_any_end_token = '>'
+ else:
+ tokenizer.Consume('{')
+ expanded_any_end_token = '}'
+ if not self.descriptor_pool:
+ raise ParseError('Descriptor pool required to parse expanded Any field')
+ expanded_any_sub_message = _BuildMessageFromTypeName(packed_type_name,
+ self.descriptor_pool)
+ if not expanded_any_sub_message:
+ raise ParseError('Type %s not found in descriptor pool' %
+ packed_type_name)
+ while not tokenizer.TryConsume(expanded_any_end_token):
+ if tokenizer.AtEnd():
+ raise tokenizer.ParseErrorPreviousToken('Expected "%s".' %
+ (expanded_any_end_token,))
+ self._MergeField(tokenizer, expanded_any_sub_message)
+ if field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ any_message = getattr(message, field.name).add()
+ else:
+ any_message = getattr(message, field.name)
+ any_message.Pack(expanded_any_sub_message)
+ elif field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ if field.is_extension:
+ sub_message = message.Extensions[field].add()
+ elif is_map_entry:
+ # pylint: disable=protected-access
+ sub_message = field.message_type._concrete_class()
+ else:
+ sub_message = getattr(message, field.name).add()
+ else:
+ if field.is_extension:
+ sub_message = message.Extensions[field]
+ else:
+ sub_message = getattr(message, field.name)
+ sub_message.SetInParent()
+
+ while not tokenizer.TryConsume(end_token):
+ if tokenizer.AtEnd():
+ raise tokenizer.ParseErrorPreviousToken('Expected "%s".' % (end_token,))
+ self._MergeField(tokenizer, sub_message)
+
+ if is_map_entry:
+ value_cpptype = field.message_type.fields_by_name['value'].cpp_type
+ if value_cpptype == descriptor.FieldDescriptor.CPPTYPE_MESSAGE:
+ value = getattr(message, field.name)[sub_message.key]
+ value.MergeFrom(sub_message.value)
+ else:
+ getattr(message, field.name)[sub_message.key] = sub_message.value
+
+ def _MergeScalarField(self, tokenizer, message, field):
+ """Merges a single scalar field into a message.
+
+ Args:
+ tokenizer: A tokenizer to parse the field value.
+ message: A protocol message to record the data.
+ field: The descriptor of the field to be merged.
+
+ Raises:
+ ParseError: In case of text parsing problems.
+ RuntimeError: On runtime errors.
+ """
+ _ = self.allow_unknown_extension
+ value = None
+
+ if field.type in (descriptor.FieldDescriptor.TYPE_INT32,
+ descriptor.FieldDescriptor.TYPE_SINT32,
+ descriptor.FieldDescriptor.TYPE_SFIXED32):
+ value = _ConsumeInt32(tokenizer)
+ elif field.type in (descriptor.FieldDescriptor.TYPE_INT64,
+ descriptor.FieldDescriptor.TYPE_SINT64,
+ descriptor.FieldDescriptor.TYPE_SFIXED64):
+ value = _ConsumeInt64(tokenizer)
+ elif field.type in (descriptor.FieldDescriptor.TYPE_UINT32,
+ descriptor.FieldDescriptor.TYPE_FIXED32):
+ value = _ConsumeUint32(tokenizer)
+ elif field.type in (descriptor.FieldDescriptor.TYPE_UINT64,
+ descriptor.FieldDescriptor.TYPE_FIXED64):
+ value = _ConsumeUint64(tokenizer)
+ elif field.type in (descriptor.FieldDescriptor.TYPE_FLOAT,
+ descriptor.FieldDescriptor.TYPE_DOUBLE):
+ value = tokenizer.ConsumeFloat()
+ elif field.type == descriptor.FieldDescriptor.TYPE_BOOL:
+ value = tokenizer.ConsumeBool()
+ elif field.type == descriptor.FieldDescriptor.TYPE_STRING:
+ value = tokenizer.ConsumeString()
+ elif field.type == descriptor.FieldDescriptor.TYPE_BYTES:
+ value = tokenizer.ConsumeByteString()
+ elif field.type == descriptor.FieldDescriptor.TYPE_ENUM:
+ value = tokenizer.ConsumeEnum(field)
+ else:
+ raise RuntimeError('Unknown field type %d' % field.type)
+
+ if field.label == descriptor.FieldDescriptor.LABEL_REPEATED:
+ if field.is_extension:
+ message.Extensions[field].append(value)
+ else:
+ getattr(message, field.name).append(value)
+ else:
+ if field.is_extension:
+ if not self._allow_multiple_scalars and message.HasExtension(field):
+ raise tokenizer.ParseErrorPreviousToken(
+ 'Message type "%s" should not have multiple "%s" extensions.' %
+ (message.DESCRIPTOR.full_name, field.full_name))
+ else:
+ message.Extensions[field] = value
+ else:
+ if not self._allow_multiple_scalars and message.HasField(field.name):
+ raise tokenizer.ParseErrorPreviousToken(
+ 'Message type "%s" should not have multiple "%s" fields.' %
+ (message.DESCRIPTOR.full_name, field.name))
+ else:
+ setattr(message, field.name, value)
+
+
+def _SkipFieldContents(tokenizer):
+ """Skips over contents (value or message) of a field.
+
+ Args:
+ tokenizer: A tokenizer to parse the field name and values.
+ """
+ # Try to guess the type of this field.
+ # If this field is not a message, there should be a ":" between the
+ # field name and the field value and also the field value should not
+ # start with "{" or "<" which indicates the beginning of a message body.
+ # If there is no ":" or there is a "{" or "<" after ":", this field has
+ # to be a message or the input is ill-formed.
+ if tokenizer.TryConsume(':') and not tokenizer.LookingAt(
+ '{') and not tokenizer.LookingAt('<'):
+ _SkipFieldValue(tokenizer)
+ else:
+ _SkipFieldMessage(tokenizer)
+
+
+def _SkipField(tokenizer):
+ """Skips over a complete field (name and value/message).
+
+ Args:
+ tokenizer: A tokenizer to parse the field name and values.
+ """
+ if tokenizer.TryConsume('['):
+ # Consume extension name.
+ tokenizer.ConsumeIdentifier()
+ while tokenizer.TryConsume('.'):
+ tokenizer.ConsumeIdentifier()
+ tokenizer.Consume(']')
+ else:
+ tokenizer.ConsumeIdentifier()
+
+ _SkipFieldContents(tokenizer)
+
+ # For historical reasons, fields may optionally be separated by commas or
+ # semicolons.
+ if not tokenizer.TryConsume(','):
+ tokenizer.TryConsume(';')
+
+
+def _SkipFieldMessage(tokenizer):
+ """Skips over a field message.
+
+ Args:
+ tokenizer: A tokenizer to parse the field name and values.
+ """
+
+ if tokenizer.TryConsume('<'):
+ delimiter = '>'
+ else:
+ tokenizer.Consume('{')
+ delimiter = '}'
+
+ while not tokenizer.LookingAt('>') and not tokenizer.LookingAt('}'):
+ _SkipField(tokenizer)
+
+ tokenizer.Consume(delimiter)
+
+
+def _SkipFieldValue(tokenizer):
+ """Skips over a field value.
+
+ Args:
+ tokenizer: A tokenizer to parse the field name and values.
+
+ Raises:
+ ParseError: In case an invalid field value is found.
+ """
+ # String/bytes tokens can come in multiple adjacent string literals.
+ # If we can consume one, consume as many as we can.
+ if tokenizer.TryConsumeByteString():
+ while tokenizer.TryConsumeByteString():
+ pass
+ return
+
+ if (not tokenizer.TryConsumeIdentifier() and
+ not _TryConsumeInt64(tokenizer) and not _TryConsumeUint64(tokenizer) and
+ not tokenizer.TryConsumeFloat()):
+ raise ParseError('Invalid field value: ' + tokenizer.token)
+
+
+class Tokenizer(object):
+ """Protocol buffer text representation tokenizer.
+
+ This class handles the lower level string parsing by splitting it into
+ meaningful tokens.
+
+ It was directly ported from the Java protocol buffer API.
+ """
+
+ _WHITESPACE = re.compile(r'\s+')
+ _COMMENT = re.compile(r'(\s*#.*$)', re.MULTILINE)
+ _WHITESPACE_OR_COMMENT = re.compile(r'(\s|(#.*$))+', re.MULTILINE)
+ _TOKEN = re.compile('|'.join([
+ r'[a-zA-Z_][0-9a-zA-Z_+-]*', # an identifier
+ r'([0-9+-]|(\.[0-9]))[0-9a-zA-Z_.+-]*', # a number
+ ] + [ # quoted str for each quote mark
+ r'{qt}([^{qt}\n\\]|\\.)*({qt}|\\?$)'.format(qt=mark) for mark in _QUOTES
+ ]))
+
+ _IDENTIFIER = re.compile(r'[^\d\W]\w*')
+ _IDENTIFIER_OR_NUMBER = re.compile(r'\w+')
+
+ def __init__(self, lines, skip_comments=True):
+ self._position = 0
+ self._line = -1
+ self._column = 0
+ self._token_start = None
+ self.token = ''
+ self._lines = iter(lines)
+ self._current_line = ''
+ self._previous_line = 0
+ self._previous_column = 0
+ self._more_lines = True
+ self._skip_comments = skip_comments
+ self._whitespace_pattern = (skip_comments and self._WHITESPACE_OR_COMMENT
+ or self._WHITESPACE)
+ self._SkipWhitespace()
+ self.NextToken()
+
+ def LookingAt(self, token):
+ return self.token == token
+
+ def AtEnd(self):
+ """Checks the end of the text was reached.
+
+ Returns:
+ True iff the end was reached.
+ """
+ return not self.token
+
+ def _PopLine(self):
+ while len(self._current_line) <= self._column:
+ try:
+ self._current_line = next(self._lines)
+ except StopIteration:
+ self._current_line = ''
+ self._more_lines = False
+ return
+ else:
+ self._line += 1
+ self._column = 0
+
+ def _SkipWhitespace(self):
+ while True:
+ self._PopLine()
+ match = self._whitespace_pattern.match(self._current_line, self._column)
+ if not match:
+ break
+ length = len(match.group(0))
+ self._column += length
+
+ def TryConsume(self, token):
+ """Tries to consume a given piece of text.
+
+ Args:
+ token: Text to consume.
+
+ Returns:
+ True iff the text was consumed.
+ """
+ if self.token == token:
+ self.NextToken()
+ return True
+ return False
+
+ def Consume(self, token):
+ """Consumes a piece of text.
+
+ Args:
+ token: Text to consume.
+
+ Raises:
+ ParseError: If the text couldn't be consumed.
+ """
+ if not self.TryConsume(token):
+ raise self.ParseError('Expected "%s".' % token)
+
+ def ConsumeComment(self):
+ result = self.token
+ if not self._COMMENT.match(result):
+ raise self.ParseError('Expected comment.')
+ self.NextToken()
+ return result
+
+ def TryConsumeIdentifier(self):
+ try:
+ self.ConsumeIdentifier()
+ return True
+ except ParseError:
+ return False
+
+ def ConsumeIdentifier(self):
+ """Consumes protocol message field identifier.
+
+ Returns:
+ Identifier string.
+
+ Raises:
+ ParseError: If an identifier couldn't be consumed.
+ """
+ result = self.token
+ if not self._IDENTIFIER.match(result):
+ raise self.ParseError('Expected identifier.')
+ self.NextToken()
+ return result
+
+ def TryConsumeIdentifierOrNumber(self):
+ try:
+ self.ConsumeIdentifierOrNumber()
+ return True
+ except ParseError:
+ return False
+
+ def ConsumeIdentifierOrNumber(self):
+ """Consumes protocol message field identifier.
+
+ Returns:
+ Identifier string.
+
+ Raises:
+ ParseError: If an identifier couldn't be consumed.
+ """
+ result = self.token
+ if not self._IDENTIFIER_OR_NUMBER.match(result):
+ raise self.ParseError('Expected identifier or number.')
+ self.NextToken()
+ return result
+
+ def TryConsumeInteger(self):
+ try:
+ # Note: is_long only affects value type, not whether an error is raised.
+ self.ConsumeInteger()
+ return True
+ except ParseError:
+ return False
+
+ def ConsumeInteger(self, is_long=False):
+ """Consumes an integer number.
+
+ Args:
+ is_long: True if the value should be returned as a long integer.
+ Returns:
+ The integer parsed.
+
+ Raises:
+ ParseError: If an integer couldn't be consumed.
+ """
+ try:
+ result = _ParseAbstractInteger(self.token, is_long=is_long)
+ except ValueError as e:
+ raise self.ParseError(str(e))
+ self.NextToken()
+ return result
+
+ def TryConsumeFloat(self):
+ try:
+ self.ConsumeFloat()
+ return True
+ except ParseError:
+ return False
+
+ def ConsumeFloat(self):
+ """Consumes an floating point number.
+
+ Returns:
+ The number parsed.
+
+ Raises:
+ ParseError: If a floating point number couldn't be consumed.
+ """
+ try:
+ result = ParseFloat(self.token)
+ except ValueError as e:
+ raise self.ParseError(str(e))
+ self.NextToken()
+ return result
+
+ def ConsumeBool(self):
+ """Consumes a boolean value.
+
+ Returns:
+ The bool parsed.
+
+ Raises:
+ ParseError: If a boolean value couldn't be consumed.
+ """
+ try:
+ result = ParseBool(self.token)
+ except ValueError as e:
+ raise self.ParseError(str(e))
+ self.NextToken()
+ return result
+
+ def TryConsumeByteString(self):
+ try:
+ self.ConsumeByteString()
+ return True
+ except ParseError:
+ return False
+
+ def ConsumeString(self):
+ """Consumes a string value.
+
+ Returns:
+ The string parsed.
+
+ Raises:
+ ParseError: If a string value couldn't be consumed.
+ """
+ the_bytes = self.ConsumeByteString()
+ try:
+ return six.text_type(the_bytes, 'utf-8')
+ except UnicodeDecodeError as e:
+ raise self._StringParseError(e)
+
+ def ConsumeByteString(self):
+ """Consumes a byte array value.
+
+ Returns:
+ The array parsed (as a string).
+
+ Raises:
+ ParseError: If a byte array value couldn't be consumed.
+ """
+ the_list = [self._ConsumeSingleByteString()]
+ while self.token and self.token[0] in _QUOTES:
+ the_list.append(self._ConsumeSingleByteString())
+ return b''.join(the_list)
+
+ def _ConsumeSingleByteString(self):
+ """Consume one token of a string literal.
+
+ String literals (whether bytes or text) can come in multiple adjacent
+ tokens which are automatically concatenated, like in C or Python. This
+ method only consumes one token.
+
+ Returns:
+ The token parsed.
+ Raises:
+ ParseError: When the wrong format data is found.
+ """
+ text = self.token
+ if len(text) < 1 or text[0] not in _QUOTES:
+ raise self.ParseError('Expected string but found: %r' % (text,))
+
+ if len(text) < 2 or text[-1] != text[0]:
+ raise self.ParseError('String missing ending quote: %r' % (text,))
+
+ try:
+ result = text_encoding.CUnescape(text[1:-1])
+ except ValueError as e:
+ raise self.ParseError(str(e))
+ self.NextToken()
+ return result
+
+ def ConsumeEnum(self, field):
+ try:
+ result = ParseEnum(field, self.token)
+ except ValueError as e:
+ raise self.ParseError(str(e))
+ self.NextToken()
+ return result
+
+ def ParseErrorPreviousToken(self, message):
+ """Creates and *returns* a ParseError for the previously read token.
+
+ Args:
+ message: A message to set for the exception.
+
+ Returns:
+ A ParseError instance.
+ """
+ return ParseError(message, self._previous_line + 1,
+ self._previous_column + 1)
+
+ def ParseError(self, message):
+ """Creates and *returns* a ParseError for the current token."""
+ return ParseError(message, self._line + 1, self._column + 1)
+
+ def _StringParseError(self, e):
+ return self.ParseError('Couldn\'t parse string: ' + str(e))
+
+ def NextToken(self):
+ """Reads the next meaningful token."""
+ self._previous_line = self._line
+ self._previous_column = self._column
+
+ self._column += len(self.token)
+ self._SkipWhitespace()
+
+ if not self._more_lines:
+ self.token = ''
+ return
+
+ match = self._TOKEN.match(self._current_line, self._column)
+ if not match and not self._skip_comments:
+ match = self._COMMENT.match(self._current_line, self._column)
+ if match:
+ token = match.group(0)
+ self.token = token
+ else:
+ self.token = self._current_line[self._column]
+
+# Aliased so it can still be accessed by current visibility violators.
+# TODO(dbarnett): Migrate violators to textformat_tokenizer.
+_Tokenizer = Tokenizer # pylint: disable=invalid-name
+
+
+def _ConsumeInt32(tokenizer):
+ """Consumes a signed 32bit integer number from tokenizer.
+
+ Args:
+ tokenizer: A tokenizer used to parse the number.
+
+ Returns:
+ The integer parsed.
+
+ Raises:
+ ParseError: If a signed 32bit integer couldn't be consumed.
+ """
+ return _ConsumeInteger(tokenizer, is_signed=True, is_long=False)
+
+
+def _ConsumeUint32(tokenizer):
+ """Consumes an unsigned 32bit integer number from tokenizer.
+
+ Args:
+ tokenizer: A tokenizer used to parse the number.
+
+ Returns:
+ The integer parsed.
+
+ Raises:
+ ParseError: If an unsigned 32bit integer couldn't be consumed.
+ """
+ return _ConsumeInteger(tokenizer, is_signed=False, is_long=False)
+
+
+def _TryConsumeInt64(tokenizer):
+ try:
+ _ConsumeInt64(tokenizer)
+ return True
+ except ParseError:
+ return False
+
+
+def _ConsumeInt64(tokenizer):
+ """Consumes a signed 32bit integer number from tokenizer.
+
+ Args:
+ tokenizer: A tokenizer used to parse the number.
+
+ Returns:
+ The integer parsed.
+
+ Raises:
+ ParseError: If a signed 32bit integer couldn't be consumed.
+ """
+ return _ConsumeInteger(tokenizer, is_signed=True, is_long=True)
+
+
+def _TryConsumeUint64(tokenizer):
+ try:
+ _ConsumeUint64(tokenizer)
+ return True
+ except ParseError:
+ return False
+
+
+def _ConsumeUint64(tokenizer):
+ """Consumes an unsigned 64bit integer number from tokenizer.
+
+ Args:
+ tokenizer: A tokenizer used to parse the number.
+
+ Returns:
+ The integer parsed.
+
+ Raises:
+ ParseError: If an unsigned 64bit integer couldn't be consumed.
+ """
+ return _ConsumeInteger(tokenizer, is_signed=False, is_long=True)
+
+
+def _TryConsumeInteger(tokenizer, is_signed=False, is_long=False):
+ try:
+ _ConsumeInteger(tokenizer, is_signed=is_signed, is_long=is_long)
+ return True
+ except ParseError:
+ return False
+
+
+def _ConsumeInteger(tokenizer, is_signed=False, is_long=False):
+ """Consumes an integer number from tokenizer.
+
+ Args:
+ tokenizer: A tokenizer used to parse the number.
+ is_signed: True if a signed integer must be parsed.
+ is_long: True if a long integer must be parsed.
+
+ Returns:
+ The integer parsed.
+
+ Raises:
+ ParseError: If an integer with given characteristics couldn't be consumed.
+ """
+ try:
+ result = ParseInteger(tokenizer.token, is_signed=is_signed, is_long=is_long)
+ except ValueError as e:
+ raise tokenizer.ParseError(str(e))
+ tokenizer.NextToken()
+ return result
+
+
+def ParseInteger(text, is_signed=False, is_long=False):
+ """Parses an integer.
+
+ Args:
+ text: The text to parse.
+ is_signed: True if a signed integer must be parsed.
+ is_long: True if a long integer must be parsed.
+
+ Returns:
+ The integer value.
+
+ Raises:
+ ValueError: Thrown Iff the text is not a valid integer.
+ """
+ # Do the actual parsing. Exception handling is propagated to caller.
+ result = _ParseAbstractInteger(text, is_long=is_long)
+
+ # Check if the integer is sane. Exceptions handled by callers.
+ checker = _INTEGER_CHECKERS[2 * int(is_long) + int(is_signed)]
+ checker.CheckValue(result)
+ return result
+
+
+def _ParseAbstractInteger(text, is_long=False):
+ """Parses an integer without checking size/signedness.
+
+ Args:
+ text: The text to parse.
+ is_long: True if the value should be returned as a long integer.
+
+ Returns:
+ The integer value.
+
+ Raises:
+ ValueError: Thrown Iff the text is not a valid integer.
+ """
+ # Do the actual parsing. Exception handling is propagated to caller.
+ try:
+ # We force 32-bit values to int and 64-bit values to long to make
+ # alternate implementations where the distinction is more significant
+ # (e.g. the C++ implementation) simpler.
+ if is_long:
+ return long(text, 0)
+ else:
+ return int(text, 0)
+ except ValueError:
+ raise ValueError('Couldn\'t parse integer: %s' % text)
+
+
+def ParseFloat(text):
+ """Parse a floating point number.
+
+ Args:
+ text: Text to parse.
+
+ Returns:
+ The number parsed.
+
+ Raises:
+ ValueError: If a floating point number couldn't be parsed.
+ """
+ try:
+ # Assume Python compatible syntax.
+ return float(text)
+ except ValueError:
+ # Check alternative spellings.
+ if _FLOAT_INFINITY.match(text):
+ if text[0] == '-':
+ return float('-inf')
+ else:
+ return float('inf')
+ elif _FLOAT_NAN.match(text):
+ return float('nan')
+ else:
+ # assume '1.0f' format
+ try:
+ return float(text.rstrip('f'))
+ except ValueError:
+ raise ValueError('Couldn\'t parse float: %s' % text)
+
+
+def ParseBool(text):
+ """Parse a boolean value.
+
+ Args:
+ text: Text to parse.
+
+ Returns:
+ Boolean values parsed
+
+ Raises:
+ ValueError: If text is not a valid boolean.
+ """
+ if text in ('true', 't', '1'):
+ return True
+ elif text in ('false', 'f', '0'):
+ return False
+ else:
+ raise ValueError('Expected "true" or "false".')
+
+
+def ParseEnum(field, value):
+ """Parse an enum value.
+
+ The value can be specified by a number (the enum value), or by
+ a string literal (the enum name).
+
+ Args:
+ field: Enum field descriptor.
+ value: String value.
+
+ Returns:
+ Enum value number.
+
+ Raises:
+ ValueError: If the enum value could not be parsed.
+ """
+ enum_descriptor = field.enum_type
+ try:
+ number = int(value, 0)
+ except ValueError:
+ # Identifier.
+ enum_value = enum_descriptor.values_by_name.get(value, None)
+ if enum_value is None:
+ raise ValueError('Enum type "%s" has no value named %s.' %
+ (enum_descriptor.full_name, value))
+ else:
+ # Numeric value.
+ enum_value = enum_descriptor.values_by_number.get(number, None)
+ if enum_value is None:
+ raise ValueError('Enum type "%s" has no value with number %d.' %
+ (enum_descriptor.full_name, number))
+ return enum_value.number
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/any.cc b/third_party/protobuf/3.0.0/src/google/protobuf/any.cc
new file mode 100644
index 0000000000..f7b1d31061
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/any.cc
@@ -0,0 +1,114 @@
+// 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.
+
+#include <google/protobuf/any.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+namespace {
+string GetTypeUrl(const Descriptor* message,
+ const string& type_url_prefix) {
+ if (!type_url_prefix.empty() &&
+ type_url_prefix[type_url_prefix.size() - 1] == '/') {
+ return type_url_prefix + message->full_name();
+ } else {
+ return type_url_prefix + "/" + message->full_name();
+ }
+}
+} // namespace
+
+const char kAnyFullTypeName[] = "google.protobuf.Any";
+const char kTypeGoogleApisComPrefix[] = "type.googleapis.com/";
+const char kTypeGoogleProdComPrefix[] = "type.googleprod.com/";
+
+AnyMetadata::AnyMetadata(UrlType* type_url, ValueType* value)
+ : type_url_(type_url), value_(value) {
+}
+
+void AnyMetadata::PackFrom(const Message& message) {
+ PackFrom(message, kTypeGoogleApisComPrefix);
+}
+
+void AnyMetadata::PackFrom(const Message& message,
+ const string& type_url_prefix) {
+ type_url_->SetNoArena(&::google::protobuf::internal::GetEmptyString(),
+ GetTypeUrl(message.GetDescriptor(), type_url_prefix));
+ message.SerializeToString(value_->MutableNoArena(
+ &::google::protobuf::internal::GetEmptyStringAlreadyInited()));
+}
+
+bool AnyMetadata::UnpackTo(Message* message) const {
+ if (!InternalIs(message->GetDescriptor())) {
+ return false;
+ }
+ return message->ParseFromString(
+ value_->GetNoArena(&::google::protobuf::internal::GetEmptyString()));
+}
+
+bool AnyMetadata::InternalIs(const Descriptor* descriptor) const {
+ const string type_url = type_url_->GetNoArena(
+ &::google::protobuf::internal::GetEmptyString());
+ string full_name;
+ if (!ParseAnyTypeUrl(type_url, &full_name)) {
+ return false;
+ }
+ return full_name == descriptor->full_name();
+}
+
+bool ParseAnyTypeUrl(const string& type_url, string* full_type_name) {
+ size_t pos = type_url.find_last_of("/");
+ if (pos == string::npos || pos + 1 == type_url.size()) {
+ return false;
+ }
+ *full_type_name = type_url.substr(pos + 1);
+ return true;
+}
+
+
+bool GetAnyFieldDescriptors(const Message& message,
+ const FieldDescriptor** type_url_field,
+ const FieldDescriptor** value_field) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ if (descriptor->full_name() != kAnyFullTypeName) {
+ return false;
+ }
+ *type_url_field = descriptor->FindFieldByNumber(1);
+ *value_field = descriptor->FindFieldByNumber(2);
+ return (*type_url_field != NULL &&
+ (*type_url_field)->type() == FieldDescriptor::TYPE_STRING &&
+ *value_field != NULL &&
+ (*value_field)->type() == FieldDescriptor::TYPE_BYTES);
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/any.h b/third_party/protobuf/3.0.0/src/google/protobuf/any.h
new file mode 100644
index 0000000000..04e541667f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/any.h
@@ -0,0 +1,107 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_ANY_H__
+#define GOOGLE_PROTOBUF_ANY_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/arenastring.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Helper class used to implement google::protobuf::Any.
+class LIBPROTOBUF_EXPORT AnyMetadata {
+ typedef ArenaStringPtr UrlType;
+ typedef ArenaStringPtr ValueType;
+ public:
+ // AnyMetadata does not take ownership of "type_url" and "value".
+ AnyMetadata(UrlType* type_url, ValueType* value);
+
+ // Packs a message using the default type URL prefix: "type.googleapis.com".
+ // The resulted type URL will be "type.googleapis.com/<message_full_name>".
+ void PackFrom(const Message& message);
+ // Packs a message using the given type URL prefix. The type URL will be
+ // constructed by concatenating the message type's full name to the prefix
+ // with an optional "/" separator if the prefix doesn't already end up "/".
+ // For example, both PackFrom(message, "type.googleapis.com") and
+ // PackFrom(message, "type.googleapis.com/") yield the same result type
+ // URL: "type.googleapis.com/<message_full_name>".
+ void PackFrom(const Message& message, const string& type_url_prefix);
+
+ // Unpacks the payload into the given message. Returns false if the message's
+ // type doesn't match the type specified in the type URL (i.e., the full
+ // name after the last "/" of the type URL doesn't match the message's actaul
+ // full name) or parsing the payload has failed.
+ bool UnpackTo(Message* message) const;
+
+ // Checks whether the type specified in the type URL matches the given type.
+ // A type is consdiered matching if its full name matches the full name after
+ // the last "/" in the type URL.
+ template<typename T>
+ bool Is() const {
+ return InternalIs(T::default_instance().GetDescriptor());
+ }
+
+ private:
+ bool InternalIs(const Descriptor* message) const;
+
+ UrlType* type_url_;
+ ValueType* value_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(AnyMetadata);
+};
+
+extern const char kAnyFullTypeName[]; // "google.protobuf.Any".
+extern const char kTypeGoogleApisComPrefix[]; // "type.googleapis.com/".
+extern const char kTypeGoogleProdComPrefix[]; // "type.googleprod.com/".
+
+// Get the proto type name from Any::type_url value. For example, passing
+// "type.googleapis.com/rpc.QueryOrigin" will return "rpc.QueryOrigin" in
+// *full_type_name. Returns false if type_url does not start with
+// "type.googleapis.com" or "type.googleprod.com".
+bool ParseAnyTypeUrl(const string& type_url, string* full_type_name);
+
+// See if message is of type google.protobuf.Any, if so, return the descriptors
+// for "type_url" and "value" fields.
+bool GetAnyFieldDescriptors(const Message& message,
+ const FieldDescriptor** type_url_field,
+ const FieldDescriptor** value_field);
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_ANY_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/any.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/any.pb.cc
new file mode 100644
index 0000000000..ccccc9c12b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/any.pb.cc
@@ -0,0 +1,496 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/any.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/any.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* Any_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Any_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fany_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fany_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fany_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/any.proto");
+ GOOGLE_CHECK(file != NULL);
+ Any_descriptor_ = file->message_type(0);
+ static const int Any_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Any, type_url_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Any, value_),
+ };
+ Any_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Any_descriptor_,
+ Any::default_instance_,
+ Any_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Any),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Any, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Any, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fany_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Any_descriptor_, &Any::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fany_2eproto() {
+ delete Any::default_instance_;
+ delete Any_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fany_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fany_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n\031google/protobuf/any.proto\022\017google.prot"
+ "obuf\"&\n\003Any\022\020\n\010type_url\030\001 \001(\t\022\r\n\005value\030\002"
+ " \001(\014Br\n\023com.google.protobufB\010AnyProtoP\001Z"
+ "%github.com/golang/protobuf/ptypes/any\240\001"
+ "\001\242\002\003GPB\252\002\036Google.Protobuf.WellKnownTypes"
+ "b\006proto3", 208);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/any.proto", &protobuf_RegisterTypes);
+ Any::default_instance_ = new Any();
+ Any::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fany_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fany_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fany_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fany_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fany_2eproto_;
+
+// ===================================================================
+
+void Any::PackFrom(const ::google::protobuf::Message& message) {
+ _any_metadata_.PackFrom(message);
+}
+
+void Any::PackFrom(const ::google::protobuf::Message& message,
+ const ::std::string& type_url_prefix) {
+ _any_metadata_.PackFrom(message, type_url_prefix);
+}
+
+bool Any::UnpackTo(::google::protobuf::Message* message) const {
+ return _any_metadata_.UnpackTo(message);
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Any::kTypeUrlFieldNumber;
+const int Any::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Any::Any()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL), _any_metadata_(&type_url_, &value_) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Any)
+}
+
+void Any::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Any::Any(const Any& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL),
+ _any_metadata_(&type_url_, &value_) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Any)
+}
+
+void Any::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ type_url_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+Any::~Any() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Any)
+ SharedDtor();
+}
+
+void Any::SharedDtor() {
+ type_url_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void Any::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Any::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Any_descriptor_;
+}
+
+const Any& Any::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fany_2eproto();
+ return *default_instance_;
+}
+
+Any* Any::default_instance_ = NULL;
+
+Any* Any::New(::google::protobuf::Arena* arena) const {
+ Any* n = new Any;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Any::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Any)
+ type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+bool Any::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Any)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string type_url = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_type_url()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->type_url().data(), this->type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Any.type_url"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_value;
+ break;
+ }
+
+ // optional bytes value = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadBytes(
+ input, this->mutable_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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Any)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Any)
+ return false;
+#undef DO_
+}
+
+void Any::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Any)
+ // optional string type_url = 1;
+ if (this->type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->type_url().data(), this->type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Any.type_url");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->type_url(), output);
+ }
+
+ // optional bytes value = 2;
+ if (this->value().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteBytesMaybeAliased(
+ 2, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Any)
+}
+
+::google::protobuf::uint8* Any::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Any)
+ // optional string type_url = 1;
+ if (this->type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->type_url().data(), this->type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Any.type_url");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->type_url(), target);
+ }
+
+ // optional bytes value = 2;
+ if (this->value().size() > 0) {
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteBytesToArray(
+ 2, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Any)
+ return target;
+}
+
+int Any::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Any)
+ int total_size = 0;
+
+ // optional string type_url = 1;
+ if (this->type_url().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->type_url());
+ }
+
+ // optional bytes value = 2;
+ if (this->value().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::BytesSize(
+ this->value());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Any::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Any)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Any* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Any>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Any)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Any)
+ MergeFrom(*source);
+ }
+}
+
+void Any::MergeFrom(const Any& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Any)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.type_url().size() > 0) {
+
+ type_url_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.type_url_);
+ }
+ if (from.value().size() > 0) {
+
+ value_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.value_);
+ }
+}
+
+void Any::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Any)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Any::CopyFrom(const Any& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Any)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Any::IsInitialized() const {
+
+ return true;
+}
+
+void Any::Swap(Any* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Any::InternalSwap(Any* other) {
+ type_url_.Swap(&other->type_url_);
+ value_.Swap(&other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Any::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Any_descriptor_;
+ metadata.reflection = Any_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Any
+
+// optional string type_url = 1;
+void Any::clear_type_url() {
+ type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Any::type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Any.type_url)
+ return type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Any::set_type_url(const ::std::string& value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Any.type_url)
+}
+ void Any::set_type_url(const char* value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Any.type_url)
+}
+ void Any::set_type_url(const char* value, size_t size) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Any.type_url)
+}
+ ::std::string* Any::mutable_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Any.type_url)
+ return type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Any::release_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Any.type_url)
+
+ return type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Any::set_allocated_type_url(::std::string* type_url) {
+ if (type_url != NULL) {
+
+ } else {
+
+ }
+ type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Any.type_url)
+}
+
+// optional bytes value = 2;
+void Any::clear_value() {
+ value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Any::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Any.value)
+ return value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Any::set_value(const ::std::string& value) {
+
+ value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Any.value)
+}
+ void Any::set_value(const char* value) {
+
+ value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Any.value)
+}
+ void Any::set_value(const void* value, size_t size) {
+
+ value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Any.value)
+}
+ ::std::string* Any::mutable_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Any.value)
+ return value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Any::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Any.value)
+
+ return value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Any::set_allocated_value(::std::string* value) {
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Any.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/any.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/any.pb.h
new file mode 100644
index 0000000000..d8cbee2d02
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/any.pb.h
@@ -0,0 +1,258 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/any.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fany_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fany_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/any.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fany_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fany_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fany_2eproto();
+
+class Any;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT Any : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Any) */ {
+ public:
+ Any();
+ virtual ~Any();
+
+ Any(const Any& from);
+
+ inline Any& operator=(const Any& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Any& default_instance();
+
+ // implements Any -----------------------------------------------
+
+ void PackFrom(const ::google::protobuf::Message& message);
+ void PackFrom(const ::google::protobuf::Message& message,
+ const ::std::string& type_url_prefix);
+ bool UnpackTo(::google::protobuf::Message* message) const;
+ template<typename T> bool Is() const {
+ return _any_metadata_.Is<T>();
+ }
+
+ void Swap(Any* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Any* New() const { return New(NULL); }
+
+ Any* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Any& from);
+ void MergeFrom(const Any& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Any* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string type_url = 1;
+ void clear_type_url();
+ static const int kTypeUrlFieldNumber = 1;
+ const ::std::string& type_url() const;
+ void set_type_url(const ::std::string& value);
+ void set_type_url(const char* value);
+ void set_type_url(const char* value, size_t size);
+ ::std::string* mutable_type_url();
+ ::std::string* release_type_url();
+ void set_allocated_type_url(::std::string* type_url);
+
+ // optional bytes value = 2;
+ void clear_value();
+ static const int kValueFieldNumber = 2;
+ const ::std::string& value() const;
+ void set_value(const ::std::string& value);
+ void set_value(const char* value);
+ void set_value(const void* value, size_t size);
+ ::std::string* mutable_value();
+ ::std::string* release_value();
+ void set_allocated_value(::std::string* value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Any)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr type_url_;
+ ::google::protobuf::internal::ArenaStringPtr value_;
+ mutable int _cached_size_;
+ ::google::protobuf::internal::AnyMetadata _any_metadata_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fany_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fany_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fany_2eproto();
+
+ void InitAsDefaultInstance();
+ static Any* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// Any
+
+// optional string type_url = 1;
+inline void Any::clear_type_url() {
+ type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Any::type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Any.type_url)
+ return type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Any::set_type_url(const ::std::string& value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Any.type_url)
+}
+inline void Any::set_type_url(const char* value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Any.type_url)
+}
+inline void Any::set_type_url(const char* value, size_t size) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Any.type_url)
+}
+inline ::std::string* Any::mutable_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Any.type_url)
+ return type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Any::release_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Any.type_url)
+
+ return type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Any::set_allocated_type_url(::std::string* type_url) {
+ if (type_url != NULL) {
+
+ } else {
+
+ }
+ type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Any.type_url)
+}
+
+// optional bytes value = 2;
+inline void Any::clear_value() {
+ value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Any::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Any.value)
+ return value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Any::set_value(const ::std::string& value) {
+
+ value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Any.value)
+}
+inline void Any::set_value(const char* value) {
+
+ value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Any.value)
+}
+inline void Any::set_value(const void* value, size_t size) {
+
+ value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Any.value)
+}
+inline ::std::string* Any::mutable_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Any.value)
+ return value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Any::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Any.value)
+
+ return value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Any::set_allocated_value(::std::string* value) {
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Any.value)
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fany_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/any.proto b/third_party/protobuf/3.0.0/src/google/protobuf/any.proto
new file mode 100644
index 0000000000..81dcf46ccf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/any.proto
@@ -0,0 +1,140 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option go_package = "github.com/golang/protobuf/ptypes/any";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "AnyProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+// `Any` contains an arbitrary serialized protocol buffer message along with a
+// URL that describes the type of the serialized message.
+//
+// Protobuf library provides support to pack/unpack Any values in the form
+// of utility functions or additional generated methods of the Any type.
+//
+// Example 1: Pack and unpack a message in C++.
+//
+// Foo foo = ...;
+// Any any;
+// any.PackFrom(foo);
+// ...
+// if (any.UnpackTo(&foo)) {
+// ...
+// }
+//
+// Example 2: Pack and unpack a message in Java.
+//
+// Foo foo = ...;
+// Any any = Any.pack(foo);
+// ...
+// if (any.is(Foo.class)) {
+// foo = any.unpack(Foo.class);
+// }
+//
+// Example 3: Pack and unpack a message in Python.
+//
+// foo = Foo(...)
+// any = Any()
+// any.Pack(foo)
+// ...
+// if any.Is(Foo.DESCRIPTOR):
+// any.Unpack(foo)
+// ...
+//
+// The pack methods provided by protobuf library will by default use
+// 'type.googleapis.com/full.type.name' as the type URL and the unpack
+// methods only use the fully qualified type name after the last '/'
+// in the type URL, for example "foo.bar.com/x/y.z" will yield type
+// name "y.z".
+//
+//
+// JSON
+// ====
+// The JSON representation of an `Any` value uses the regular
+// representation of the deserialized, embedded message, with an
+// additional field `@type` which contains the type URL. Example:
+//
+// package google.profile;
+// message Person {
+// string first_name = 1;
+// string last_name = 2;
+// }
+//
+// {
+// "@type": "type.googleapis.com/google.profile.Person",
+// "firstName": <string>,
+// "lastName": <string>
+// }
+//
+// If the embedded message type is well-known and has a custom JSON
+// representation, that representation will be embedded adding a field
+// `value` which holds the custom JSON in addition to the `@type`
+// field. Example (for message [google.protobuf.Duration][]):
+//
+// {
+// "@type": "type.googleapis.com/google.protobuf.Duration",
+// "value": "1.212s"
+// }
+//
+message Any {
+ // A URL/resource name whose content describes the type of the
+ // serialized protocol buffer message.
+ //
+ // For URLs which use the scheme `http`, `https`, or no scheme, the
+ // following restrictions and interpretations apply:
+ //
+ // * If no scheme is provided, `https` is assumed.
+ // * The last segment of the URL's path must represent the fully
+ // qualified name of the type (as in `path/google.protobuf.Duration`).
+ // The name should be in a canonical form (e.g., leading "." is
+ // not accepted).
+ // * An HTTP GET on the URL must yield a [google.protobuf.Type][]
+ // value in binary format, or produce an error.
+ // * Applications are allowed to cache lookup results based on the
+ // URL, or have them precompiled into a binary to avoid any
+ // lookup. Therefore, binary compatibility needs to be preserved
+ // on changes to types. (Use versioned type names to manage
+ // breaking changes.)
+ //
+ // Schemes other than `http`, `https` (or the empty scheme) might be
+ // used with implementation specific semantics.
+ //
+ string type_url = 1;
+
+ // Must be a valid serialized protocol buffer of the above specified type.
+ bytes value = 2;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/any_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/any_test.cc
new file mode 100644
index 0000000000..1bfaa63d87
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/any_test.cc
@@ -0,0 +1,89 @@
+// 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.
+
+#include <google/protobuf/any_test.pb.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+
+TEST(AnyTest, TestPackAndUnpack) {
+ protobuf_unittest::TestAny submessage;
+ submessage.set_int32_value(12345);
+ protobuf_unittest::TestAny message;
+ message.mutable_any_value()->PackFrom(submessage);
+
+ string data = message.SerializeAsString();
+
+ ASSERT_TRUE(message.ParseFromString(data));
+ EXPECT_TRUE(message.has_any_value());
+ ASSERT_TRUE(message.any_value().UnpackTo(&submessage));
+ EXPECT_EQ(12345, submessage.int32_value());
+}
+
+TEST(AnyTest, TestPackAndUnpackAny) {
+ // We can pack a Any message inside another Any message.
+ protobuf_unittest::TestAny submessage;
+ submessage.set_int32_value(12345);
+ google::protobuf::Any any;
+ any.PackFrom(submessage);
+ protobuf_unittest::TestAny message;
+ message.mutable_any_value()->PackFrom(any);
+
+ string data = message.SerializeAsString();
+
+ ASSERT_TRUE(message.ParseFromString(data));
+ EXPECT_TRUE(message.has_any_value());
+ ASSERT_TRUE(message.any_value().UnpackTo(&any));
+ ASSERT_TRUE(any.UnpackTo(&submessage));
+ EXPECT_EQ(12345, submessage.int32_value());
+}
+
+TEST(AnyTest, TestIs) {
+ protobuf_unittest::TestAny submessage;
+ submessage.set_int32_value(12345);
+ google::protobuf::Any any;
+ any.PackFrom(submessage);
+ ASSERT_TRUE(any.ParseFromString(any.SerializeAsString()));
+ EXPECT_TRUE(any.Is<protobuf_unittest::TestAny>());
+ EXPECT_FALSE(any.Is<google::protobuf::Any>());
+
+ protobuf_unittest::TestAny message;
+ message.mutable_any_value()->PackFrom(any);
+ ASSERT_TRUE(message.ParseFromString(message.SerializeAsString()));
+ EXPECT_FALSE(message.any_value().Is<protobuf_unittest::TestAny>());
+ EXPECT_TRUE(message.any_value().Is<google::protobuf::Any>());
+}
+
+} // namespace
+} // namespace protobuf
+
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/any_test.proto b/third_party/protobuf/3.0.0/src/google/protobuf/any_test.proto
new file mode 100644
index 0000000000..0c5b30ba3e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/any_test.proto
@@ -0,0 +1,41 @@
+// 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.
+
+syntax = "proto3";
+
+package protobuf_unittest;
+
+import "google/protobuf/any.proto";
+
+message TestAny {
+ int32 int32_value = 1;
+ google.protobuf.Any any_value = 2;
+ repeated google.protobuf.Any repeated_any_value = 3;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/api.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/api.pb.cc
new file mode 100644
index 0000000000..cfb3078691
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/api.pb.cc
@@ -0,0 +1,2028 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/api.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/api.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* Api_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Api_reflection_ = NULL;
+const ::google::protobuf::Descriptor* Method_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Method_reflection_ = NULL;
+const ::google::protobuf::Descriptor* Mixin_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Mixin_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fapi_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fapi_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/api.proto");
+ GOOGLE_CHECK(file != NULL);
+ Api_descriptor_ = file->message_type(0);
+ static const int Api_offsets_[7] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, methods_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, version_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, source_context_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, mixins_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, syntax_),
+ };
+ Api_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Api_descriptor_,
+ Api::default_instance_,
+ Api_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Api),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Api, _is_default_instance_));
+ Method_descriptor_ = file->message_type(1);
+ static const int Method_offsets_[7] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, request_type_url_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, request_streaming_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, response_type_url_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, response_streaming_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, syntax_),
+ };
+ Method_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Method_descriptor_,
+ Method::default_instance_,
+ Method_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Method),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Method, _is_default_instance_));
+ Mixin_descriptor_ = file->message_type(2);
+ static const int Mixin_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Mixin, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Mixin, root_),
+ };
+ Mixin_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Mixin_descriptor_,
+ Mixin::default_instance_,
+ Mixin_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Mixin),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Mixin, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Mixin, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fapi_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Api_descriptor_, &Api::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Method_descriptor_, &Method::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Mixin_descriptor_, &Mixin::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fapi_2eproto() {
+ delete Api::default_instance_;
+ delete Api_reflection_;
+ delete Method::default_instance_;
+ delete Method_reflection_;
+ delete Mixin::default_instance_;
+ delete Mixin_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+ ::google::protobuf::protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n\031google/protobuf/api.proto\022\017google.prot"
+ "obuf\032$google/protobuf/source_context.pro"
+ "to\032\032google/protobuf/type.proto\"\201\002\n\003Api\022\014"
+ "\n\004name\030\001 \001(\t\022(\n\007methods\030\002 \003(\0132\027.google.p"
+ "rotobuf.Method\022(\n\007options\030\003 \003(\0132\027.google"
+ ".protobuf.Option\022\017\n\007version\030\004 \001(\t\0226\n\016sou"
+ "rce_context\030\005 \001(\0132\036.google.protobuf.Sour"
+ "ceContext\022&\n\006mixins\030\006 \003(\0132\026.google.proto"
+ "buf.Mixin\022\'\n\006syntax\030\007 \001(\0162\027.google.proto"
+ "buf.Syntax\"\325\001\n\006Method\022\014\n\004name\030\001 \001(\t\022\030\n\020r"
+ "equest_type_url\030\002 \001(\t\022\031\n\021request_streami"
+ "ng\030\003 \001(\010\022\031\n\021response_type_url\030\004 \001(\t\022\032\n\022r"
+ "esponse_streaming\030\005 \001(\010\022(\n\007options\030\006 \003(\013"
+ "2\027.google.protobuf.Option\022\'\n\006syntax\030\007 \001("
+ "\0162\027.google.protobuf.Syntax\"#\n\005Mixin\022\014\n\004n"
+ "ame\030\001 \001(\t\022\014\n\004root\030\002 \001(\tBK\n\023com.google.pr"
+ "otobufB\010ApiProtoP\001\240\001\001\242\002\003GPB\252\002\036Google.Pro"
+ "tobuf.WellKnownTypesb\006proto3", 708);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/api.proto", &protobuf_RegisterTypes);
+ Api::default_instance_ = new Api();
+ Method::default_instance_ = new Method();
+ Mixin::default_instance_ = new Mixin();
+ Api::default_instance_->InitAsDefaultInstance();
+ Method::default_instance_->InitAsDefaultInstance();
+ Mixin::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fapi_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fapi_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fapi_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fapi_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Api::kNameFieldNumber;
+const int Api::kMethodsFieldNumber;
+const int Api::kOptionsFieldNumber;
+const int Api::kVersionFieldNumber;
+const int Api::kSourceContextFieldNumber;
+const int Api::kMixinsFieldNumber;
+const int Api::kSyntaxFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Api::Api()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Api)
+}
+
+void Api::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+ source_context_ = const_cast< ::google::protobuf::SourceContext*>(&::google::protobuf::SourceContext::default_instance());
+}
+
+Api::Api(const Api& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Api)
+}
+
+void Api::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ version_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ source_context_ = NULL;
+ syntax_ = 0;
+}
+
+Api::~Api() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Api)
+ SharedDtor();
+}
+
+void Api::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ version_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete source_context_;
+ }
+}
+
+void Api::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Api::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Api_descriptor_;
+}
+
+const Api& Api::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ return *default_instance_;
+}
+
+Api* Api::default_instance_ = NULL;
+
+Api* Api::New(::google::protobuf::Arena* arena) const {
+ Api* n = new Api;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Api::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Api)
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ version_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+ syntax_ = 0;
+ methods_.Clear();
+ options_.Clear();
+ mixins_.Clear();
+}
+
+bool Api::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Api)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Api.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_methods;
+ break;
+ }
+
+ // repeated .google.protobuf.Method methods = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_methods:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_methods:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_methods()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_loop_methods;
+ if (input->ExpectTag(26)) goto parse_loop_options;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ case 3: {
+ if (tag == 26) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_loop_options;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(34)) goto parse_version;
+ break;
+ }
+
+ // optional string version = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_version:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_version()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->version().data(), this->version().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Api.version"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(42)) goto parse_source_context;
+ break;
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ case 5: {
+ if (tag == 42) {
+ parse_source_context:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_source_context()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_mixins;
+ break;
+ }
+
+ // repeated .google.protobuf.Mixin mixins = 6;
+ case 6: {
+ if (tag == 50) {
+ parse_mixins:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_mixins:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_mixins()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_loop_mixins;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(56)) goto parse_syntax;
+ break;
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ case 7: {
+ if (tag == 56) {
+ parse_syntax:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ set_syntax(static_cast< ::google::protobuf::Syntax >(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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Api)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Api)
+ return false;
+#undef DO_
+}
+
+void Api::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Api)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Api.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // repeated .google.protobuf.Method methods = 2;
+ for (unsigned int i = 0, n = this->methods_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, this->methods(i), output);
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 3, this->options(i), output);
+ }
+
+ // optional string version = 4;
+ if (this->version().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->version().data(), this->version().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Api.version");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 4, this->version(), output);
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ if (this->has_source_context()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 5, *this->source_context_, output);
+ }
+
+ // repeated .google.protobuf.Mixin mixins = 6;
+ for (unsigned int i = 0, n = this->mixins_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 6, this->mixins(i), output);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ if (this->syntax() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 7, this->syntax(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Api)
+}
+
+::google::protobuf::uint8* Api::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Api)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Api.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // repeated .google.protobuf.Method methods = 2;
+ for (unsigned int i = 0, n = this->methods_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, this->methods(i), false, target);
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 3, this->options(i), false, target);
+ }
+
+ // optional string version = 4;
+ if (this->version().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->version().data(), this->version().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Api.version");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 4, this->version(), target);
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ if (this->has_source_context()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 5, *this->source_context_, false, target);
+ }
+
+ // repeated .google.protobuf.Mixin mixins = 6;
+ for (unsigned int i = 0, n = this->mixins_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 6, this->mixins(i), false, target);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ if (this->syntax() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 7, this->syntax(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Api)
+ return target;
+}
+
+int Api::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Api)
+ int total_size = 0;
+
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional string version = 4;
+ if (this->version().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->version());
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ if (this->has_source_context()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->source_context_);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ if (this->syntax() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->syntax());
+ }
+
+ // repeated .google.protobuf.Method methods = 2;
+ total_size += 1 * this->methods_size();
+ for (int i = 0; i < this->methods_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->methods(i));
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ total_size += 1 * this->options_size();
+ for (int i = 0; i < this->options_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->options(i));
+ }
+
+ // repeated .google.protobuf.Mixin mixins = 6;
+ total_size += 1 * this->mixins_size();
+ for (int i = 0; i < this->mixins_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->mixins(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Api::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Api)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Api* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Api>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Api)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Api)
+ MergeFrom(*source);
+ }
+}
+
+void Api::MergeFrom(const Api& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Api)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ methods_.MergeFrom(from.methods_);
+ options_.MergeFrom(from.options_);
+ mixins_.MergeFrom(from.mixins_);
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.version().size() > 0) {
+
+ version_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.version_);
+ }
+ if (from.has_source_context()) {
+ mutable_source_context()->::google::protobuf::SourceContext::MergeFrom(from.source_context());
+ }
+ if (from.syntax() != 0) {
+ set_syntax(from.syntax());
+ }
+}
+
+void Api::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Api)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Api::CopyFrom(const Api& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Api)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Api::IsInitialized() const {
+
+ return true;
+}
+
+void Api::Swap(Api* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Api::InternalSwap(Api* other) {
+ name_.Swap(&other->name_);
+ methods_.UnsafeArenaSwap(&other->methods_);
+ options_.UnsafeArenaSwap(&other->options_);
+ version_.Swap(&other->version_);
+ std::swap(source_context_, other->source_context_);
+ mixins_.UnsafeArenaSwap(&other->mixins_);
+ std::swap(syntax_, other->syntax_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Api::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Api_descriptor_;
+ metadata.reflection = Api_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Api
+
+// optional string name = 1;
+void Api::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Api::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Api::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Api.name)
+}
+ void Api::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Api.name)
+}
+ void Api::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Api.name)
+}
+ ::std::string* Api::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Api::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Api.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Api::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Api.name)
+}
+
+// repeated .google.protobuf.Method methods = 2;
+int Api::methods_size() const {
+ return methods_.size();
+}
+void Api::clear_methods() {
+ methods_.Clear();
+}
+const ::google::protobuf::Method& Api::methods(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.methods)
+ return methods_.Get(index);
+}
+::google::protobuf::Method* Api::mutable_methods(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.methods)
+ return methods_.Mutable(index);
+}
+::google::protobuf::Method* Api::add_methods() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Api.methods)
+ return methods_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Method >*
+Api::mutable_methods() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Api.methods)
+ return &methods_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Method >&
+Api::methods() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Api.methods)
+ return methods_;
+}
+
+// repeated .google.protobuf.Option options = 3;
+int Api::options_size() const {
+ return options_.size();
+}
+void Api::clear_options() {
+ options_.Clear();
+}
+const ::google::protobuf::Option& Api::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.options)
+ return options_.Get(index);
+}
+::google::protobuf::Option* Api::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.options)
+ return options_.Mutable(index);
+}
+::google::protobuf::Option* Api::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Api.options)
+ return options_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Api::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Api.options)
+ return &options_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Api::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Api.options)
+ return options_;
+}
+
+// optional string version = 4;
+void Api::clear_version() {
+ version_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Api::version() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.version)
+ return version_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Api::set_version(const ::std::string& value) {
+
+ version_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Api.version)
+}
+ void Api::set_version(const char* value) {
+
+ version_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Api.version)
+}
+ void Api::set_version(const char* value, size_t size) {
+
+ version_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Api.version)
+}
+ ::std::string* Api::mutable_version() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.version)
+ return version_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Api::release_version() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Api.version)
+
+ return version_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Api::set_allocated_version(::std::string* version) {
+ if (version != NULL) {
+
+ } else {
+
+ }
+ version_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), version);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Api.version)
+}
+
+// optional .google.protobuf.SourceContext source_context = 5;
+bool Api::has_source_context() const {
+ return !_is_default_instance_ && source_context_ != NULL;
+}
+void Api::clear_source_context() {
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+}
+const ::google::protobuf::SourceContext& Api::source_context() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.source_context)
+ return source_context_ != NULL ? *source_context_ : *default_instance_->source_context_;
+}
+::google::protobuf::SourceContext* Api::mutable_source_context() {
+
+ if (source_context_ == NULL) {
+ source_context_ = new ::google::protobuf::SourceContext;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.source_context)
+ return source_context_;
+}
+::google::protobuf::SourceContext* Api::release_source_context() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Api.source_context)
+
+ ::google::protobuf::SourceContext* temp = source_context_;
+ source_context_ = NULL;
+ return temp;
+}
+void Api::set_allocated_source_context(::google::protobuf::SourceContext* source_context) {
+ delete source_context_;
+ source_context_ = source_context;
+ if (source_context) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Api.source_context)
+}
+
+// repeated .google.protobuf.Mixin mixins = 6;
+int Api::mixins_size() const {
+ return mixins_.size();
+}
+void Api::clear_mixins() {
+ mixins_.Clear();
+}
+const ::google::protobuf::Mixin& Api::mixins(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.mixins)
+ return mixins_.Get(index);
+}
+::google::protobuf::Mixin* Api::mutable_mixins(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.mixins)
+ return mixins_.Mutable(index);
+}
+::google::protobuf::Mixin* Api::add_mixins() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Api.mixins)
+ return mixins_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Mixin >*
+Api::mutable_mixins() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Api.mixins)
+ return &mixins_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Mixin >&
+Api::mixins() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Api.mixins)
+ return mixins_;
+}
+
+// optional .google.protobuf.Syntax syntax = 7;
+void Api::clear_syntax() {
+ syntax_ = 0;
+}
+ ::google::protobuf::Syntax Api::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+ void Api::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Api.syntax)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Method::kNameFieldNumber;
+const int Method::kRequestTypeUrlFieldNumber;
+const int Method::kRequestStreamingFieldNumber;
+const int Method::kResponseTypeUrlFieldNumber;
+const int Method::kResponseStreamingFieldNumber;
+const int Method::kOptionsFieldNumber;
+const int Method::kSyntaxFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Method::Method()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Method)
+}
+
+void Method::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Method::Method(const Method& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Method)
+}
+
+void Method::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ request_type_url_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ request_streaming_ = false;
+ response_type_url_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ response_streaming_ = false;
+ syntax_ = 0;
+}
+
+Method::~Method() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Method)
+ SharedDtor();
+}
+
+void Method::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ request_type_url_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ response_type_url_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void Method::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Method::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Method_descriptor_;
+}
+
+const Method& Method::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ return *default_instance_;
+}
+
+Method* Method::default_instance_ = NULL;
+
+Method* Method::New(::google::protobuf::Arena* arena) const {
+ Method* n = new Method;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Method::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Method)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(Method, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<Method*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(request_streaming_, syntax_);
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ request_type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ response_type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ options_.Clear();
+}
+
+bool Method::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Method)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Method.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_request_type_url;
+ break;
+ }
+
+ // optional string request_type_url = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_request_type_url:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_request_type_url()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->request_type_url().data(), this->request_type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Method.request_type_url"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(24)) goto parse_request_streaming;
+ break;
+ }
+
+ // optional bool request_streaming = 3;
+ case 3: {
+ if (tag == 24) {
+ parse_request_streaming:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &request_streaming_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(34)) goto parse_response_type_url;
+ break;
+ }
+
+ // optional string response_type_url = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_response_type_url:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_response_type_url()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->response_type_url().data(), this->response_type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Method.response_type_url"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(40)) goto parse_response_streaming;
+ break;
+ }
+
+ // optional bool response_streaming = 5;
+ case 5: {
+ if (tag == 40) {
+ parse_response_streaming:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &response_streaming_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_options;
+ break;
+ }
+
+ // repeated .google.protobuf.Option options = 6;
+ case 6: {
+ if (tag == 50) {
+ parse_options:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_loop_options;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(56)) goto parse_syntax;
+ break;
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ case 7: {
+ if (tag == 56) {
+ parse_syntax:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ set_syntax(static_cast< ::google::protobuf::Syntax >(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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Method)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Method)
+ return false;
+#undef DO_
+}
+
+void Method::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Method)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Method.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional string request_type_url = 2;
+ if (this->request_type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->request_type_url().data(), this->request_type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Method.request_type_url");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->request_type_url(), output);
+ }
+
+ // optional bool request_streaming = 3;
+ if (this->request_streaming() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(3, this->request_streaming(), output);
+ }
+
+ // optional string response_type_url = 4;
+ if (this->response_type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->response_type_url().data(), this->response_type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Method.response_type_url");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 4, this->response_type_url(), output);
+ }
+
+ // optional bool response_streaming = 5;
+ if (this->response_streaming() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(5, this->response_streaming(), output);
+ }
+
+ // repeated .google.protobuf.Option options = 6;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 6, this->options(i), output);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ if (this->syntax() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 7, this->syntax(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Method)
+}
+
+::google::protobuf::uint8* Method::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Method)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Method.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional string request_type_url = 2;
+ if (this->request_type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->request_type_url().data(), this->request_type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Method.request_type_url");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->request_type_url(), target);
+ }
+
+ // optional bool request_streaming = 3;
+ if (this->request_streaming() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(3, this->request_streaming(), target);
+ }
+
+ // optional string response_type_url = 4;
+ if (this->response_type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->response_type_url().data(), this->response_type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Method.response_type_url");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 4, this->response_type_url(), target);
+ }
+
+ // optional bool response_streaming = 5;
+ if (this->response_streaming() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(5, this->response_streaming(), target);
+ }
+
+ // repeated .google.protobuf.Option options = 6;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 6, this->options(i), false, target);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ if (this->syntax() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 7, this->syntax(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Method)
+ return target;
+}
+
+int Method::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Method)
+ int total_size = 0;
+
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional string request_type_url = 2;
+ if (this->request_type_url().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->request_type_url());
+ }
+
+ // optional bool request_streaming = 3;
+ if (this->request_streaming() != 0) {
+ total_size += 1 + 1;
+ }
+
+ // optional string response_type_url = 4;
+ if (this->response_type_url().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->response_type_url());
+ }
+
+ // optional bool response_streaming = 5;
+ if (this->response_streaming() != 0) {
+ total_size += 1 + 1;
+ }
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ if (this->syntax() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->syntax());
+ }
+
+ // repeated .google.protobuf.Option options = 6;
+ total_size += 1 * this->options_size();
+ for (int i = 0; i < this->options_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->options(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Method::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Method)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Method* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Method>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Method)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Method)
+ MergeFrom(*source);
+ }
+}
+
+void Method::MergeFrom(const Method& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Method)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ options_.MergeFrom(from.options_);
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.request_type_url().size() > 0) {
+
+ request_type_url_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.request_type_url_);
+ }
+ if (from.request_streaming() != 0) {
+ set_request_streaming(from.request_streaming());
+ }
+ if (from.response_type_url().size() > 0) {
+
+ response_type_url_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.response_type_url_);
+ }
+ if (from.response_streaming() != 0) {
+ set_response_streaming(from.response_streaming());
+ }
+ if (from.syntax() != 0) {
+ set_syntax(from.syntax());
+ }
+}
+
+void Method::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Method)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Method::CopyFrom(const Method& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Method)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Method::IsInitialized() const {
+
+ return true;
+}
+
+void Method::Swap(Method* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Method::InternalSwap(Method* other) {
+ name_.Swap(&other->name_);
+ request_type_url_.Swap(&other->request_type_url_);
+ std::swap(request_streaming_, other->request_streaming_);
+ response_type_url_.Swap(&other->response_type_url_);
+ std::swap(response_streaming_, other->response_streaming_);
+ options_.UnsafeArenaSwap(&other->options_);
+ std::swap(syntax_, other->syntax_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Method::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Method_descriptor_;
+ metadata.reflection = Method_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Method
+
+// optional string name = 1;
+void Method::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Method::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Method::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.name)
+}
+ void Method::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Method.name)
+}
+ void Method::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Method.name)
+}
+ ::std::string* Method::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Method::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Method.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Method::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Method.name)
+}
+
+// optional string request_type_url = 2;
+void Method::clear_request_type_url() {
+ request_type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Method::request_type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.request_type_url)
+ return request_type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Method::set_request_type_url(const ::std::string& value) {
+
+ request_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.request_type_url)
+}
+ void Method::set_request_type_url(const char* value) {
+
+ request_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Method.request_type_url)
+}
+ void Method::set_request_type_url(const char* value, size_t size) {
+
+ request_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Method.request_type_url)
+}
+ ::std::string* Method::mutable_request_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.request_type_url)
+ return request_type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Method::release_request_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Method.request_type_url)
+
+ return request_type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Method::set_allocated_request_type_url(::std::string* request_type_url) {
+ if (request_type_url != NULL) {
+
+ } else {
+
+ }
+ request_type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), request_type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Method.request_type_url)
+}
+
+// optional bool request_streaming = 3;
+void Method::clear_request_streaming() {
+ request_streaming_ = false;
+}
+ bool Method::request_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.request_streaming)
+ return request_streaming_;
+}
+ void Method::set_request_streaming(bool value) {
+
+ request_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.request_streaming)
+}
+
+// optional string response_type_url = 4;
+void Method::clear_response_type_url() {
+ response_type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Method::response_type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.response_type_url)
+ return response_type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Method::set_response_type_url(const ::std::string& value) {
+
+ response_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.response_type_url)
+}
+ void Method::set_response_type_url(const char* value) {
+
+ response_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Method.response_type_url)
+}
+ void Method::set_response_type_url(const char* value, size_t size) {
+
+ response_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Method.response_type_url)
+}
+ ::std::string* Method::mutable_response_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.response_type_url)
+ return response_type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Method::release_response_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Method.response_type_url)
+
+ return response_type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Method::set_allocated_response_type_url(::std::string* response_type_url) {
+ if (response_type_url != NULL) {
+
+ } else {
+
+ }
+ response_type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), response_type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Method.response_type_url)
+}
+
+// optional bool response_streaming = 5;
+void Method::clear_response_streaming() {
+ response_streaming_ = false;
+}
+ bool Method::response_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.response_streaming)
+ return response_streaming_;
+}
+ void Method::set_response_streaming(bool value) {
+
+ response_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.response_streaming)
+}
+
+// repeated .google.protobuf.Option options = 6;
+int Method::options_size() const {
+ return options_.size();
+}
+void Method::clear_options() {
+ options_.Clear();
+}
+const ::google::protobuf::Option& Method::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.options)
+ return options_.Get(index);
+}
+::google::protobuf::Option* Method::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.options)
+ return options_.Mutable(index);
+}
+::google::protobuf::Option* Method::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Method.options)
+ return options_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Method::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Method.options)
+ return &options_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Method::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Method.options)
+ return options_;
+}
+
+// optional .google.protobuf.Syntax syntax = 7;
+void Method::clear_syntax() {
+ syntax_ = 0;
+}
+ ::google::protobuf::Syntax Method::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+ void Method::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.syntax)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Mixin::kNameFieldNumber;
+const int Mixin::kRootFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Mixin::Mixin()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Mixin)
+}
+
+void Mixin::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Mixin::Mixin(const Mixin& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Mixin)
+}
+
+void Mixin::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ root_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+Mixin::~Mixin() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Mixin)
+ SharedDtor();
+}
+
+void Mixin::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ root_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void Mixin::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Mixin::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Mixin_descriptor_;
+}
+
+const Mixin& Mixin::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ return *default_instance_;
+}
+
+Mixin* Mixin::default_instance_ = NULL;
+
+Mixin* Mixin::New(::google::protobuf::Arena* arena) const {
+ Mixin* n = new Mixin;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Mixin::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Mixin)
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ root_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+bool Mixin::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Mixin)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Mixin.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_root;
+ break;
+ }
+
+ // optional string root = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_root:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_root()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->root().data(), this->root().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Mixin.root"));
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Mixin)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Mixin)
+ return false;
+#undef DO_
+}
+
+void Mixin::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Mixin)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Mixin.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional string root = 2;
+ if (this->root().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->root().data(), this->root().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Mixin.root");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->root(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Mixin)
+}
+
+::google::protobuf::uint8* Mixin::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Mixin)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Mixin.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional string root = 2;
+ if (this->root().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->root().data(), this->root().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Mixin.root");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->root(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Mixin)
+ return target;
+}
+
+int Mixin::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Mixin)
+ int total_size = 0;
+
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional string root = 2;
+ if (this->root().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->root());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Mixin::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Mixin)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Mixin* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Mixin>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Mixin)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Mixin)
+ MergeFrom(*source);
+ }
+}
+
+void Mixin::MergeFrom(const Mixin& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Mixin)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.root().size() > 0) {
+
+ root_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.root_);
+ }
+}
+
+void Mixin::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Mixin)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Mixin::CopyFrom(const Mixin& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Mixin)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Mixin::IsInitialized() const {
+
+ return true;
+}
+
+void Mixin::Swap(Mixin* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Mixin::InternalSwap(Mixin* other) {
+ name_.Swap(&other->name_);
+ root_.Swap(&other->root_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Mixin::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Mixin_descriptor_;
+ metadata.reflection = Mixin_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Mixin
+
+// optional string name = 1;
+void Mixin::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Mixin::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Mixin.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Mixin::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Mixin.name)
+}
+ void Mixin::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Mixin.name)
+}
+ void Mixin::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Mixin.name)
+}
+ ::std::string* Mixin::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Mixin.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Mixin::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Mixin.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Mixin::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Mixin.name)
+}
+
+// optional string root = 2;
+void Mixin::clear_root() {
+ root_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Mixin::root() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Mixin.root)
+ return root_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Mixin::set_root(const ::std::string& value) {
+
+ root_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Mixin.root)
+}
+ void Mixin::set_root(const char* value) {
+
+ root_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Mixin.root)
+}
+ void Mixin::set_root(const char* value, size_t size) {
+
+ root_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Mixin.root)
+}
+ ::std::string* Mixin::mutable_root() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Mixin.root)
+ return root_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Mixin::release_root() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Mixin.root)
+
+ return root_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Mixin::set_allocated_root(::std::string* root) {
+ if (root != NULL) {
+
+ } else {
+
+ }
+ root_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), root);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Mixin.root)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/api.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/api.pb.h
new file mode 100644
index 0000000000..c9ec923a83
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/api.pb.h
@@ -0,0 +1,996 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/api.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fapi_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fapi_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/source_context.pb.h>
+#include <google/protobuf/type.pb.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fapi_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fapi_2eproto();
+
+class Api;
+class Method;
+class Mixin;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT Api : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Api) */ {
+ public:
+ Api();
+ virtual ~Api();
+
+ Api(const Api& from);
+
+ inline Api& operator=(const Api& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Api& default_instance();
+
+ void Swap(Api* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Api* New() const { return New(NULL); }
+
+ Api* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Api& from);
+ void MergeFrom(const Api& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Api* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // repeated .google.protobuf.Method methods = 2;
+ int methods_size() const;
+ void clear_methods();
+ static const int kMethodsFieldNumber = 2;
+ const ::google::protobuf::Method& methods(int index) const;
+ ::google::protobuf::Method* mutable_methods(int index);
+ ::google::protobuf::Method* add_methods();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Method >*
+ mutable_methods();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Method >&
+ methods() const;
+
+ // repeated .google.protobuf.Option options = 3;
+ int options_size() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 3;
+ const ::google::protobuf::Option& options(int index) const;
+ ::google::protobuf::Option* mutable_options(int index);
+ ::google::protobuf::Option* add_options();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+ mutable_options();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+ options() const;
+
+ // optional string version = 4;
+ void clear_version();
+ static const int kVersionFieldNumber = 4;
+ const ::std::string& version() const;
+ void set_version(const ::std::string& value);
+ void set_version(const char* value);
+ void set_version(const char* value, size_t size);
+ ::std::string* mutable_version();
+ ::std::string* release_version();
+ void set_allocated_version(::std::string* version);
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ bool has_source_context() const;
+ void clear_source_context();
+ static const int kSourceContextFieldNumber = 5;
+ const ::google::protobuf::SourceContext& source_context() const;
+ ::google::protobuf::SourceContext* mutable_source_context();
+ ::google::protobuf::SourceContext* release_source_context();
+ void set_allocated_source_context(::google::protobuf::SourceContext* source_context);
+
+ // repeated .google.protobuf.Mixin mixins = 6;
+ int mixins_size() const;
+ void clear_mixins();
+ static const int kMixinsFieldNumber = 6;
+ const ::google::protobuf::Mixin& mixins(int index) const;
+ ::google::protobuf::Mixin* mutable_mixins(int index);
+ ::google::protobuf::Mixin* add_mixins();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Mixin >*
+ mutable_mixins();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Mixin >&
+ mixins() const;
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ void clear_syntax();
+ static const int kSyntaxFieldNumber = 7;
+ ::google::protobuf::Syntax syntax() const;
+ void set_syntax(::google::protobuf::Syntax value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Api)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Method > methods_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option > options_;
+ ::google::protobuf::internal::ArenaStringPtr version_;
+ ::google::protobuf::SourceContext* source_context_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Mixin > mixins_;
+ int syntax_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fapi_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fapi_2eproto();
+
+ void InitAsDefaultInstance();
+ static Api* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Method : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Method) */ {
+ public:
+ Method();
+ virtual ~Method();
+
+ Method(const Method& from);
+
+ inline Method& operator=(const Method& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Method& default_instance();
+
+ void Swap(Method* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Method* New() const { return New(NULL); }
+
+ Method* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Method& from);
+ void MergeFrom(const Method& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Method* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional string request_type_url = 2;
+ void clear_request_type_url();
+ static const int kRequestTypeUrlFieldNumber = 2;
+ const ::std::string& request_type_url() const;
+ void set_request_type_url(const ::std::string& value);
+ void set_request_type_url(const char* value);
+ void set_request_type_url(const char* value, size_t size);
+ ::std::string* mutable_request_type_url();
+ ::std::string* release_request_type_url();
+ void set_allocated_request_type_url(::std::string* request_type_url);
+
+ // optional bool request_streaming = 3;
+ void clear_request_streaming();
+ static const int kRequestStreamingFieldNumber = 3;
+ bool request_streaming() const;
+ void set_request_streaming(bool value);
+
+ // optional string response_type_url = 4;
+ void clear_response_type_url();
+ static const int kResponseTypeUrlFieldNumber = 4;
+ const ::std::string& response_type_url() const;
+ void set_response_type_url(const ::std::string& value);
+ void set_response_type_url(const char* value);
+ void set_response_type_url(const char* value, size_t size);
+ ::std::string* mutable_response_type_url();
+ ::std::string* release_response_type_url();
+ void set_allocated_response_type_url(::std::string* response_type_url);
+
+ // optional bool response_streaming = 5;
+ void clear_response_streaming();
+ static const int kResponseStreamingFieldNumber = 5;
+ bool response_streaming() const;
+ void set_response_streaming(bool value);
+
+ // repeated .google.protobuf.Option options = 6;
+ int options_size() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 6;
+ const ::google::protobuf::Option& options(int index) const;
+ ::google::protobuf::Option* mutable_options(int index);
+ ::google::protobuf::Option* add_options();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+ mutable_options();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+ options() const;
+
+ // optional .google.protobuf.Syntax syntax = 7;
+ void clear_syntax();
+ static const int kSyntaxFieldNumber = 7;
+ ::google::protobuf::Syntax syntax() const;
+ void set_syntax(::google::protobuf::Syntax value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Method)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::internal::ArenaStringPtr request_type_url_;
+ ::google::protobuf::internal::ArenaStringPtr response_type_url_;
+ bool request_streaming_;
+ bool response_streaming_;
+ int syntax_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option > options_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fapi_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fapi_2eproto();
+
+ void InitAsDefaultInstance();
+ static Method* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Mixin : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Mixin) */ {
+ public:
+ Mixin();
+ virtual ~Mixin();
+
+ Mixin(const Mixin& from);
+
+ inline Mixin& operator=(const Mixin& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Mixin& default_instance();
+
+ void Swap(Mixin* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Mixin* New() const { return New(NULL); }
+
+ Mixin* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Mixin& from);
+ void MergeFrom(const Mixin& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Mixin* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional string root = 2;
+ void clear_root();
+ static const int kRootFieldNumber = 2;
+ const ::std::string& root() const;
+ void set_root(const ::std::string& value);
+ void set_root(const char* value);
+ void set_root(const char* value, size_t size);
+ ::std::string* mutable_root();
+ ::std::string* release_root();
+ void set_allocated_root(::std::string* root);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Mixin)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::internal::ArenaStringPtr root_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fapi_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fapi_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fapi_2eproto();
+
+ void InitAsDefaultInstance();
+ static Mixin* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// Api
+
+// optional string name = 1;
+inline void Api::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Api::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Api::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Api.name)
+}
+inline void Api::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Api.name)
+}
+inline void Api::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Api.name)
+}
+inline ::std::string* Api::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Api::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Api.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Api::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Api.name)
+}
+
+// repeated .google.protobuf.Method methods = 2;
+inline int Api::methods_size() const {
+ return methods_.size();
+}
+inline void Api::clear_methods() {
+ methods_.Clear();
+}
+inline const ::google::protobuf::Method& Api::methods(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.methods)
+ return methods_.Get(index);
+}
+inline ::google::protobuf::Method* Api::mutable_methods(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.methods)
+ return methods_.Mutable(index);
+}
+inline ::google::protobuf::Method* Api::add_methods() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Api.methods)
+ return methods_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Method >*
+Api::mutable_methods() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Api.methods)
+ return &methods_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Method >&
+Api::methods() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Api.methods)
+ return methods_;
+}
+
+// repeated .google.protobuf.Option options = 3;
+inline int Api::options_size() const {
+ return options_.size();
+}
+inline void Api::clear_options() {
+ options_.Clear();
+}
+inline const ::google::protobuf::Option& Api::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.options)
+ return options_.Get(index);
+}
+inline ::google::protobuf::Option* Api::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.options)
+ return options_.Mutable(index);
+}
+inline ::google::protobuf::Option* Api::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Api.options)
+ return options_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Api::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Api.options)
+ return &options_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Api::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Api.options)
+ return options_;
+}
+
+// optional string version = 4;
+inline void Api::clear_version() {
+ version_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Api::version() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.version)
+ return version_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Api::set_version(const ::std::string& value) {
+
+ version_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Api.version)
+}
+inline void Api::set_version(const char* value) {
+
+ version_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Api.version)
+}
+inline void Api::set_version(const char* value, size_t size) {
+
+ version_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Api.version)
+}
+inline ::std::string* Api::mutable_version() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.version)
+ return version_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Api::release_version() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Api.version)
+
+ return version_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Api::set_allocated_version(::std::string* version) {
+ if (version != NULL) {
+
+ } else {
+
+ }
+ version_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), version);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Api.version)
+}
+
+// optional .google.protobuf.SourceContext source_context = 5;
+inline bool Api::has_source_context() const {
+ return !_is_default_instance_ && source_context_ != NULL;
+}
+inline void Api::clear_source_context() {
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+}
+inline const ::google::protobuf::SourceContext& Api::source_context() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.source_context)
+ return source_context_ != NULL ? *source_context_ : *default_instance_->source_context_;
+}
+inline ::google::protobuf::SourceContext* Api::mutable_source_context() {
+
+ if (source_context_ == NULL) {
+ source_context_ = new ::google::protobuf::SourceContext;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.source_context)
+ return source_context_;
+}
+inline ::google::protobuf::SourceContext* Api::release_source_context() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Api.source_context)
+
+ ::google::protobuf::SourceContext* temp = source_context_;
+ source_context_ = NULL;
+ return temp;
+}
+inline void Api::set_allocated_source_context(::google::protobuf::SourceContext* source_context) {
+ delete source_context_;
+ source_context_ = source_context;
+ if (source_context) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Api.source_context)
+}
+
+// repeated .google.protobuf.Mixin mixins = 6;
+inline int Api::mixins_size() const {
+ return mixins_.size();
+}
+inline void Api::clear_mixins() {
+ mixins_.Clear();
+}
+inline const ::google::protobuf::Mixin& Api::mixins(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.mixins)
+ return mixins_.Get(index);
+}
+inline ::google::protobuf::Mixin* Api::mutable_mixins(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Api.mixins)
+ return mixins_.Mutable(index);
+}
+inline ::google::protobuf::Mixin* Api::add_mixins() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Api.mixins)
+ return mixins_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Mixin >*
+Api::mutable_mixins() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Api.mixins)
+ return &mixins_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Mixin >&
+Api::mixins() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Api.mixins)
+ return mixins_;
+}
+
+// optional .google.protobuf.Syntax syntax = 7;
+inline void Api::clear_syntax() {
+ syntax_ = 0;
+}
+inline ::google::protobuf::Syntax Api::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Api.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+inline void Api::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Api.syntax)
+}
+
+// -------------------------------------------------------------------
+
+// Method
+
+// optional string name = 1;
+inline void Method::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Method::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Method::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.name)
+}
+inline void Method::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Method.name)
+}
+inline void Method::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Method.name)
+}
+inline ::std::string* Method::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Method::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Method.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Method::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Method.name)
+}
+
+// optional string request_type_url = 2;
+inline void Method::clear_request_type_url() {
+ request_type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Method::request_type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.request_type_url)
+ return request_type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Method::set_request_type_url(const ::std::string& value) {
+
+ request_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.request_type_url)
+}
+inline void Method::set_request_type_url(const char* value) {
+
+ request_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Method.request_type_url)
+}
+inline void Method::set_request_type_url(const char* value, size_t size) {
+
+ request_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Method.request_type_url)
+}
+inline ::std::string* Method::mutable_request_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.request_type_url)
+ return request_type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Method::release_request_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Method.request_type_url)
+
+ return request_type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Method::set_allocated_request_type_url(::std::string* request_type_url) {
+ if (request_type_url != NULL) {
+
+ } else {
+
+ }
+ request_type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), request_type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Method.request_type_url)
+}
+
+// optional bool request_streaming = 3;
+inline void Method::clear_request_streaming() {
+ request_streaming_ = false;
+}
+inline bool Method::request_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.request_streaming)
+ return request_streaming_;
+}
+inline void Method::set_request_streaming(bool value) {
+
+ request_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.request_streaming)
+}
+
+// optional string response_type_url = 4;
+inline void Method::clear_response_type_url() {
+ response_type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Method::response_type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.response_type_url)
+ return response_type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Method::set_response_type_url(const ::std::string& value) {
+
+ response_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.response_type_url)
+}
+inline void Method::set_response_type_url(const char* value) {
+
+ response_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Method.response_type_url)
+}
+inline void Method::set_response_type_url(const char* value, size_t size) {
+
+ response_type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Method.response_type_url)
+}
+inline ::std::string* Method::mutable_response_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.response_type_url)
+ return response_type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Method::release_response_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Method.response_type_url)
+
+ return response_type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Method::set_allocated_response_type_url(::std::string* response_type_url) {
+ if (response_type_url != NULL) {
+
+ } else {
+
+ }
+ response_type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), response_type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Method.response_type_url)
+}
+
+// optional bool response_streaming = 5;
+inline void Method::clear_response_streaming() {
+ response_streaming_ = false;
+}
+inline bool Method::response_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.response_streaming)
+ return response_streaming_;
+}
+inline void Method::set_response_streaming(bool value) {
+
+ response_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.response_streaming)
+}
+
+// repeated .google.protobuf.Option options = 6;
+inline int Method::options_size() const {
+ return options_.size();
+}
+inline void Method::clear_options() {
+ options_.Clear();
+}
+inline const ::google::protobuf::Option& Method::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.options)
+ return options_.Get(index);
+}
+inline ::google::protobuf::Option* Method::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Method.options)
+ return options_.Mutable(index);
+}
+inline ::google::protobuf::Option* Method::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Method.options)
+ return options_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Method::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Method.options)
+ return &options_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Method::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Method.options)
+ return options_;
+}
+
+// optional .google.protobuf.Syntax syntax = 7;
+inline void Method::clear_syntax() {
+ syntax_ = 0;
+}
+inline ::google::protobuf::Syntax Method::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Method.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+inline void Method::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Method.syntax)
+}
+
+// -------------------------------------------------------------------
+
+// Mixin
+
+// optional string name = 1;
+inline void Mixin::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Mixin::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Mixin.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Mixin::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Mixin.name)
+}
+inline void Mixin::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Mixin.name)
+}
+inline void Mixin::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Mixin.name)
+}
+inline ::std::string* Mixin::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Mixin.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Mixin::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Mixin.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Mixin::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Mixin.name)
+}
+
+// optional string root = 2;
+inline void Mixin::clear_root() {
+ root_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Mixin::root() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Mixin.root)
+ return root_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Mixin::set_root(const ::std::string& value) {
+
+ root_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Mixin.root)
+}
+inline void Mixin::set_root(const char* value) {
+
+ root_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Mixin.root)
+}
+inline void Mixin::set_root(const char* value, size_t size) {
+
+ root_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Mixin.root)
+}
+inline ::std::string* Mixin::mutable_root() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Mixin.root)
+ return root_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Mixin::release_root() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Mixin.root)
+
+ return root_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Mixin::set_allocated_root(::std::string* root) {
+ if (root != NULL) {
+
+ } else {
+
+ }
+ root_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), root);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Mixin.root)
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fapi_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/api.proto b/third_party/protobuf/3.0.0/src/google/protobuf/api.proto
new file mode 100644
index 0000000000..dbe87b8f54
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/api.proto
@@ -0,0 +1,202 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+import "google/protobuf/source_context.proto";
+import "google/protobuf/type.proto";
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "ApiProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+// Api is a light-weight descriptor for a protocol buffer service.
+message Api {
+
+ // The fully qualified name of this api, including package name
+ // followed by the api's simple name.
+ string name = 1;
+
+ // The methods of this api, in unspecified order.
+ repeated Method methods = 2;
+
+ // Any metadata attached to the API.
+ repeated Option options = 3;
+
+ // A version string for this api. If specified, must have the form
+ // `major-version.minor-version`, as in `1.10`. If the minor version
+ // is omitted, it defaults to zero. If the entire version field is
+ // empty, the major version is derived from the package name, as
+ // outlined below. If the field is not empty, the version in the
+ // package name will be verified to be consistent with what is
+ // provided here.
+ //
+ // The versioning schema uses [semantic
+ // versioning](http://semver.org) where the major version number
+ // indicates a breaking change and the minor version an additive,
+ // non-breaking change. Both version numbers are signals to users
+ // what to expect from different versions, and should be carefully
+ // chosen based on the product plan.
+ //
+ // The major version is also reflected in the package name of the
+ // API, which must end in `v<major-version>`, as in
+ // `google.feature.v1`. For major versions 0 and 1, the suffix can
+ // be omitted. Zero major versions must only be used for
+ // experimental, none-GA apis.
+ //
+ //
+ string version = 4;
+
+ // Source context for the protocol buffer service represented by this
+ // message.
+ SourceContext source_context = 5;
+
+ // Included APIs. See [Mixin][].
+ repeated Mixin mixins = 6;
+
+ // The source syntax of the service.
+ Syntax syntax = 7;
+}
+
+// Method represents a method of an api.
+message Method {
+
+ // The simple name of this method.
+ string name = 1;
+
+ // A URL of the input message type.
+ string request_type_url = 2;
+
+ // If true, the request is streamed.
+ bool request_streaming = 3;
+
+ // The URL of the output message type.
+ string response_type_url = 4;
+
+ // If true, the response is streamed.
+ bool response_streaming = 5;
+
+ // Any metadata attached to the method.
+ repeated Option options = 6;
+
+ // The source syntax of this method.
+ Syntax syntax = 7;
+}
+
+// Declares an API to be included in this API. The including API must
+// redeclare all the methods from the included API, but documentation
+// and options are inherited as follows:
+//
+// - If after comment and whitespace stripping, the documentation
+// string of the redeclared method is empty, it will be inherited
+// from the original method.
+//
+// - Each annotation belonging to the service config (http,
+// visibility) which is not set in the redeclared method will be
+// inherited.
+//
+// - If an http annotation is inherited, the path pattern will be
+// modified as follows. Any version prefix will be replaced by the
+// version of the including API plus the [root][] path if specified.
+//
+// Example of a simple mixin:
+//
+// package google.acl.v1;
+// service AccessControl {
+// // Get the underlying ACL object.
+// rpc GetAcl(GetAclRequest) returns (Acl) {
+// option (google.api.http).get = "/v1/{resource=**}:getAcl";
+// }
+// }
+//
+// package google.storage.v2;
+// service Storage {
+// rpc GetAcl(GetAclRequest) returns (Acl);
+//
+// // Get a data record.
+// rpc GetData(GetDataRequest) returns (Data) {
+// option (google.api.http).get = "/v2/{resource=**}";
+// }
+// }
+//
+// Example of a mixin configuration:
+//
+// apis:
+// - name: google.storage.v2.Storage
+// mixins:
+// - name: google.acl.v1.AccessControl
+//
+// The mixin construct implies that all methods in `AccessControl` are
+// also declared with same name and request/response types in
+// `Storage`. A documentation generator or annotation processor will
+// see the effective `Storage.GetAcl` method after inherting
+// documentation and annotations as follows:
+//
+// service Storage {
+// // Get the underlying ACL object.
+// rpc GetAcl(GetAclRequest) returns (Acl) {
+// option (google.api.http).get = "/v2/{resource=**}:getAcl";
+// }
+// ...
+// }
+//
+// Note how the version in the path pattern changed from `v1` to `v2`.
+//
+// If the `root` field in the mixin is specified, it should be a
+// relative path under which inherited HTTP paths are placed. Example:
+//
+// apis:
+// - name: google.storage.v2.Storage
+// mixins:
+// - name: google.acl.v1.AccessControl
+// root: acls
+//
+// This implies the following inherited HTTP annotation:
+//
+// service Storage {
+// // Get the underlying ACL object.
+// rpc GetAcl(GetAclRequest) returns (Acl) {
+// option (google.api.http).get = "/v2/acls/{resource=**}:getAcl";
+// }
+// ...
+// }
+message Mixin {
+ // The fully qualified name of the API which is included.
+ string name = 1;
+
+ // If non-empty specifies a path under which inherited HTTP paths
+ // are rooted.
+ string root = 2;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arena.cc b/third_party/protobuf/3.0.0/src/google/protobuf/arena.cc
new file mode 100755
index 0000000000..78e20946c3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arena.cc
@@ -0,0 +1,314 @@
+// 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.
+
+#include <google/protobuf/arena.h>
+
+
+#ifdef ADDRESS_SANITIZER
+#include <sanitizer/asan_interface.h>
+#endif
+
+namespace google {
+namespace protobuf {
+
+
+google::protobuf::internal::SequenceNumber Arena::lifecycle_id_generator_;
+#if defined(GOOGLE_PROTOBUF_NO_THREADLOCAL)
+Arena::ThreadCache& Arena::thread_cache() {
+ static internal::ThreadLocalStorage<ThreadCache>* thread_cache_ =
+ new internal::ThreadLocalStorage<ThreadCache>();
+ return *thread_cache_->Get();
+}
+#elif defined(PROTOBUF_USE_DLLS)
+Arena::ThreadCache& Arena::thread_cache() {
+ static GOOGLE_THREAD_LOCAL ThreadCache thread_cache_ = { -1, NULL };
+ return thread_cache_;
+}
+#else
+GOOGLE_THREAD_LOCAL Arena::ThreadCache Arena::thread_cache_ = { -1, NULL };
+#endif
+
+void Arena::Init() {
+ lifecycle_id_ = lifecycle_id_generator_.GetNext();
+ blocks_ = 0;
+ hint_ = 0;
+ owns_first_block_ = true;
+ cleanup_list_ = 0;
+
+ if (options_.initial_block != NULL && options_.initial_block_size > 0) {
+ GOOGLE_CHECK_GE(options_.initial_block_size, sizeof(Block))
+ << ": Initial block size too small for header.";
+
+ // Add first unowned block to list.
+ Block* first_block = reinterpret_cast<Block*>(options_.initial_block);
+ first_block->size = options_.initial_block_size;
+ first_block->pos = kHeaderSize;
+ first_block->next = NULL;
+ // Thread which calls Init() owns the first block. This allows the
+ // single-threaded case to allocate on the first block without taking any
+ // locks.
+ first_block->owner = &thread_cache();
+ SetThreadCacheBlock(first_block);
+ AddBlockInternal(first_block);
+ owns_first_block_ = false;
+ }
+
+ // Call the initialization hook
+ if (options_.on_arena_init != NULL) {
+ hooks_cookie_ = options_.on_arena_init(this);
+ } else {
+ hooks_cookie_ = NULL;
+ }
+}
+
+Arena::~Arena() {
+ uint64 space_allocated = ResetInternal();
+
+ // Call the destruction hook
+ if (options_.on_arena_destruction != NULL) {
+ options_.on_arena_destruction(this, hooks_cookie_, space_allocated);
+ }
+}
+
+uint64 Arena::Reset() {
+ // Invalidate any ThreadCaches pointing to any blocks we just destroyed.
+ lifecycle_id_ = lifecycle_id_generator_.GetNext();
+ return ResetInternal();
+}
+
+uint64 Arena::ResetInternal() {
+ CleanupList();
+ uint64 space_allocated = FreeBlocks();
+
+ // Call the reset hook
+ if (options_.on_arena_reset != NULL) {
+ options_.on_arena_reset(this, hooks_cookie_, space_allocated);
+ }
+
+ return space_allocated;
+}
+
+Arena::Block* Arena::NewBlock(void* me, Block* my_last_block, size_t n,
+ size_t start_block_size, size_t max_block_size) {
+ size_t size;
+ if (my_last_block != NULL) {
+ // Double the current block size, up to a limit.
+ size = 2 * (my_last_block->size);
+ if (size > max_block_size) size = max_block_size;
+ } else {
+ size = start_block_size;
+ }
+ if (n > size - kHeaderSize) {
+ // TODO(sanjay): Check if n + kHeaderSize would overflow
+ size = kHeaderSize + n;
+ }
+
+ Block* b = reinterpret_cast<Block*>(options_.block_alloc(size));
+ b->pos = kHeaderSize + n;
+ b->size = size;
+ b->owner = me;
+#ifdef ADDRESS_SANITIZER
+ // Poison the rest of the block for ASAN. It was unpoisoned by the underlying
+ // malloc but it's not yet usable until we return it as part of an allocation.
+ ASAN_POISON_MEMORY_REGION(
+ reinterpret_cast<char*>(b) + b->pos, b->size - b->pos);
+#endif
+ return b;
+}
+
+void Arena::AddBlock(Block* b) {
+ MutexLock l(&blocks_lock_);
+ AddBlockInternal(b);
+}
+
+void Arena::AddBlockInternal(Block* b) {
+ b->next = reinterpret_cast<Block*>(google::protobuf::internal::NoBarrier_Load(&blocks_));
+ google::protobuf::internal::Release_Store(&blocks_, reinterpret_cast<google::protobuf::internal::AtomicWord>(b));
+ if (b->avail() != 0) {
+ // Direct future allocations to this block.
+ google::protobuf::internal::Release_Store(&hint_, reinterpret_cast<google::protobuf::internal::AtomicWord>(b));
+ }
+}
+
+void Arena::AddListNode(void* elem, void (*cleanup)(void*)) {
+ Node* node = reinterpret_cast<Node*>(AllocateAligned(sizeof(Node)));
+ node->elem = elem;
+ node->cleanup = cleanup;
+ node->next = reinterpret_cast<Node*>(
+ google::protobuf::internal::NoBarrier_AtomicExchange(&cleanup_list_,
+ reinterpret_cast<google::protobuf::internal::AtomicWord>(node)));
+}
+
+void* Arena::AllocateAligned(const std::type_info* allocated, size_t n) {
+ // Align n to next multiple of 8 (from Hacker's Delight, Chapter 3.)
+ n = (n + 7) & -8;
+
+ // Monitor allocation if needed.
+ if (GOOGLE_PREDICT_FALSE(hooks_cookie_ != NULL) &&
+ options_.on_arena_allocation != NULL) {
+ options_.on_arena_allocation(allocated, n, hooks_cookie_);
+ }
+
+ // If this thread already owns a block in this arena then try to use that.
+ // This fast path optimizes the case where multiple threads allocate from the
+ // same arena.
+ if (thread_cache().last_lifecycle_id_seen == lifecycle_id_ &&
+ thread_cache().last_block_used_ != NULL) {
+ if (thread_cache().last_block_used_->avail() < n) {
+ return SlowAlloc(n);
+ }
+ return AllocFromBlock(thread_cache().last_block_used_, n);
+ }
+
+ // Check whether we own the last accessed block on this arena.
+ // This fast path optimizes the case where a single thread uses multiple
+ // arenas.
+ void* me = &thread_cache();
+ Block* b = reinterpret_cast<Block*>(google::protobuf::internal::Acquire_Load(&hint_));
+ if (!b || b->owner != me || b->avail() < n) {
+ return SlowAlloc(n);
+ }
+ return AllocFromBlock(b, n);
+}
+
+void* Arena::AllocFromBlock(Block* b, size_t n) {
+ size_t p = b->pos;
+ b->pos = p + n;
+#ifdef ADDRESS_SANITIZER
+ ASAN_UNPOISON_MEMORY_REGION(reinterpret_cast<char*>(b) + p, n);
+#endif
+ return reinterpret_cast<char*>(b) + p;
+}
+
+void* Arena::SlowAlloc(size_t n) {
+ void* me = &thread_cache();
+ Block* b = FindBlock(me); // Find block owned by me.
+ // See if allocation fits in my latest block.
+ if (b != NULL && b->avail() >= n) {
+ SetThreadCacheBlock(b);
+ google::protobuf::internal::NoBarrier_Store(&hint_, reinterpret_cast<google::protobuf::internal::AtomicWord>(b));
+ return AllocFromBlock(b, n);
+ }
+ b = NewBlock(me, b, n, options_.start_block_size, options_.max_block_size);
+ AddBlock(b);
+ SetThreadCacheBlock(b);
+ return reinterpret_cast<char*>(b) + kHeaderSize;
+}
+
+uint64 Arena::SpaceAllocated() const {
+ uint64 space_allocated = 0;
+ Block* b = reinterpret_cast<Block*>(google::protobuf::internal::NoBarrier_Load(&blocks_));
+ while (b != NULL) {
+ space_allocated += (b->size);
+ b = b->next;
+ }
+ return space_allocated;
+}
+
+uint64 Arena::SpaceUsed() const {
+ uint64 space_used = 0;
+ Block* b = reinterpret_cast<Block*>(google::protobuf::internal::NoBarrier_Load(&blocks_));
+ while (b != NULL) {
+ space_used += (b->pos - kHeaderSize);
+ b = b->next;
+ }
+ return space_used;
+}
+
+pair<uint64, uint64> Arena::SpaceAllocatedAndUsed() const {
+ uint64 allocated = 0;
+ uint64 used = 0;
+
+ Block* b = reinterpret_cast<Block*>(google::protobuf::internal::NoBarrier_Load(&blocks_));
+ while (b != NULL) {
+ allocated += b->size;
+ used += (b->pos - kHeaderSize);
+ b = b->next;
+ }
+ return std::make_pair(allocated, used);
+}
+
+uint64 Arena::FreeBlocks() {
+ uint64 space_allocated = 0;
+ Block* b = reinterpret_cast<Block*>(google::protobuf::internal::NoBarrier_Load(&blocks_));
+ Block* first_block = NULL;
+ while (b != NULL) {
+ space_allocated += (b->size);
+ Block* next = b->next;
+ if (next != NULL) {
+ options_.block_dealloc(b, b->size);
+ } else {
+ if (owns_first_block_) {
+ options_.block_dealloc(b, b->size);
+ } else {
+ // User passed in the first block, skip free'ing the memory.
+ first_block = b;
+ }
+ }
+ b = next;
+ }
+ blocks_ = 0;
+ hint_ = 0;
+ if (!owns_first_block_) {
+ // Make the first block that was passed in through ArenaOptions
+ // available for reuse.
+ first_block->pos = kHeaderSize;
+ // Thread which calls Reset() owns the first block. This allows the
+ // single-threaded case to allocate on the first block without taking any
+ // locks.
+ first_block->owner = &thread_cache();
+ SetThreadCacheBlock(first_block);
+ AddBlockInternal(first_block);
+ }
+ return space_allocated;
+}
+
+void Arena::CleanupList() {
+ Node* head =
+ reinterpret_cast<Node*>(google::protobuf::internal::NoBarrier_Load(&cleanup_list_));
+ while (head != NULL) {
+ head->cleanup(head->elem);
+ head = head->next;
+ }
+ cleanup_list_ = 0;
+}
+
+Arena::Block* Arena::FindBlock(void* me) {
+ // TODO(sanjay): We might want to keep a separate list with one
+ // entry per thread.
+ Block* b = reinterpret_cast<Block*>(google::protobuf::internal::Acquire_Load(&blocks_));
+ while (b != NULL && b->owner != me) {
+ b = b->next;
+ }
+ return b;
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arena.h b/third_party/protobuf/3.0.0/src/google/protobuf/arena.h
new file mode 100644
index 0000000000..58b1e126d5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arena.h
@@ -0,0 +1,925 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_ARENA_H__
+#define GOOGLE_PROTOBUF_ARENA_H__
+
+#include <limits>
+#ifdef max
+#undef max // Visual Studio defines this macro
+#endif
+#if __cplusplus >= 201103L
+#include <google/protobuf/stubs/type_traits.h>
+#endif
+#if defined(_MSC_VER) && !_HAS_EXCEPTIONS
+// Work around bugs in MSVC <typeinfo> header when _HAS_EXCEPTIONS=0.
+#include <exception>
+#include <typeinfo>
+namespace std {
+using type_info = ::type_info;
+}
+#else
+#include <typeinfo>
+#endif
+
+#include <google/protobuf/stubs/atomic_sequence_num.h>
+#include <google/protobuf/stubs/atomicops.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/mutex.h>
+#include <google/protobuf/stubs/type_traits.h>
+
+
+namespace google {
+namespace protobuf {
+
+class Arena; // defined below
+class Message; // message.h
+
+namespace internal {
+class ArenaString; // arenastring.h
+class LazyField; // lazy_field.h
+
+template<typename Type>
+class GenericTypeHandler; // repeated_field.h
+
+// Templated cleanup methods.
+template<typename T> void arena_destruct_object(void* object) {
+ reinterpret_cast<T*>(object)->~T();
+}
+template<typename T> void arena_delete_object(void* object) {
+ delete reinterpret_cast<T*>(object);
+}
+inline void arena_free(void* object, size_t /* size */) {
+ free(object);
+}
+
+} // namespace internal
+
+// ArenaOptions provides optional additional parameters to arena construction
+// that control its block-allocation behavior.
+struct ArenaOptions {
+ // This defines the size of the first block requested from the system malloc.
+ // Subsequent block sizes will increase in a geometric series up to a maximum.
+ size_t start_block_size;
+
+ // This defines the maximum block size requested from system malloc (unless an
+ // individual arena allocation request occurs with a size larger than this
+ // maximum). Requested block sizes increase up to this value, then remain
+ // here.
+ size_t max_block_size;
+
+ // An initial block of memory for the arena to use, or NULL for none. If
+ // provided, the block must live at least as long as the arena itself. The
+ // creator of the Arena retains ownership of the block after the Arena is
+ // destroyed.
+ char* initial_block;
+
+ // The size of the initial block, if provided.
+ size_t initial_block_size;
+
+ // A function pointer to an alloc method that returns memory blocks of size
+ // requested. By default, it contains a ptr to the malloc function.
+ //
+ // NOTE: block_alloc and dealloc functions are expected to behave like
+ // malloc and free, including Asan poisoning.
+ void* (*block_alloc)(size_t);
+ // A function pointer to a dealloc method that takes ownership of the blocks
+ // from the arena. By default, it contains a ptr to a wrapper function that
+ // calls free.
+ void (*block_dealloc)(void*, size_t);
+
+ // Hooks for adding external functionality such as user-specific metrics
+ // collection, specific debugging abilities, etc.
+ // Init hook may return a pointer to a cookie to be stored in the arena.
+ // reset and destruction hooks will then be called with the same cookie
+ // pointer. This allows us to save an external object per arena instance and
+ // use it on the other hooks (Note: It is just as legal for init to return
+ // NULL and not use the cookie feature).
+ // on_arena_reset and on_arena_destruction also receive the space used in
+ // the arena just before the reset.
+ void* (*on_arena_init)(Arena* arena);
+ void (*on_arena_reset)(Arena* arena, void* cookie, uint64 space_used);
+ void (*on_arena_destruction)(Arena* arena, void* cookie, uint64 space_used);
+
+ // type_info is promised to be static - its lifetime extends to
+ // match program's lifetime (It is given by typeid operator).
+ // Note: typeid(void) will be passed as allocated_type every time we
+ // intentionally want to avoid monitoring an allocation. (i.e. internal
+ // allocations for managing the arena)
+ void (*on_arena_allocation)(const std::type_info* allocated_type,
+ uint64 alloc_size, void* cookie);
+
+ ArenaOptions()
+ : start_block_size(kDefaultStartBlockSize),
+ max_block_size(kDefaultMaxBlockSize),
+ initial_block(NULL),
+ initial_block_size(0),
+ block_alloc(&malloc),
+ block_dealloc(&internal::arena_free),
+ on_arena_init(NULL),
+ on_arena_reset(NULL),
+ on_arena_destruction(NULL),
+ on_arena_allocation(NULL) {}
+
+ private:
+ // Constants define default starting block size and max block size for
+ // arena allocator behavior -- see descriptions above.
+ static const size_t kDefaultStartBlockSize = 256;
+ static const size_t kDefaultMaxBlockSize = 8192;
+};
+
+// Support for non-RTTI environments. (The metrics hooks API uses type
+// information.)
+#ifndef GOOGLE_PROTOBUF_NO_RTTI
+#define RTTI_TYPE_ID(type) (&typeid(type))
+#else
+#define RTTI_TYPE_ID(type) (NULL)
+#endif
+
+// Arena allocator. Arena allocation replaces ordinary (heap-based) allocation
+// with new/delete, and improves performance by aggregating allocations into
+// larger blocks and freeing allocations all at once. Protocol messages are
+// allocated on an arena by using Arena::CreateMessage<T>(Arena*), below, and
+// are automatically freed when the arena is destroyed.
+//
+// This is a thread-safe implementation: multiple threads may allocate from the
+// arena concurrently. Destruction is not thread-safe and the destructing
+// thread must synchronize with users of the arena first.
+//
+// An arena provides two allocation interfaces: CreateMessage<T>, which works
+// for arena-enabled proto2 message types as well as other types that satisfy
+// the appropriate protocol (described below), and Create<T>, which works for
+// any arbitrary type T. CreateMessage<T> is better when the type T supports it,
+// because this interface (i) passes the arena pointer to the created object so
+// that its sub-objects and internal allocations can use the arena too, and (ii)
+// elides the object's destructor call when possible. Create<T> does not place
+// any special requirements on the type T, and will invoke the object's
+// destructor when the arena is destroyed.
+//
+// The arena message allocation protocol, required by CreateMessage<T>, is as
+// follows:
+//
+// - The type T must have (at least) two constructors: a constructor with no
+// arguments, called when a T is allocated on the heap; and a constructor with
+// a google::protobuf::Arena* argument, called when a T is allocated on an arena. If the
+// second constructor is called with a NULL arena pointer, it must be
+// equivalent to invoking the first (no-argument) constructor.
+//
+// - The type T must have a particular type trait: a nested type
+// |InternalArenaConstructable_|. This is usually a typedef to |void|. If no
+// such type trait exists, then the instantiation CreateMessage<T> will fail
+// to compile.
+//
+// - The type T *may* have the type trait |DestructorSkippable_|. If this type
+// trait is present in the type, then its destructor will not be called if and
+// only if it was passed a non-NULL arena pointer. If this type trait is not
+// present on the type, then its destructor is always called when the
+// containing arena is destroyed.
+//
+// - One- and two-user-argument forms of CreateMessage<T>() also exist that
+// forward these constructor arguments to T's constructor: for example,
+// CreateMessage<T>(Arena*, arg1, arg2) forwards to a constructor T(Arena*,
+// arg1, arg2).
+//
+// This protocol is implemented by all arena-enabled proto2 message classes as
+// well as RepeatedPtrField.
+
+#if __cplusplus >= 201103L
+class LIBPROTOBUF_EXPORT Arena final {
+#else
+class LIBPROTOBUF_EXPORT Arena {
+#endif
+ public:
+ // Arena constructor taking custom options. See ArenaOptions below for
+ // descriptions of the options available.
+ explicit Arena(const ArenaOptions& options) : options_(options) {
+ Init();
+ }
+
+ // Default constructor with sensible default options, tuned for average
+ // use-cases.
+ Arena() {
+ Init();
+ }
+
+ // Destructor deletes all owned heap allocated objects, and destructs objects
+ // that have non-trivial destructors, except for proto2 message objects whose
+ // destructors can be skipped. Also, frees all blocks except the initial block
+ // if it was passed in.
+ ~Arena();
+
+ // API to create proto2 message objects on the arena. If the arena passed in
+ // is NULL, then a heap allocated object is returned. Type T must be a message
+ // defined in a .proto file with cc_enable_arenas set to true, otherwise a
+ // compilation error will occur.
+ //
+ // RepeatedField and RepeatedPtrField may also be instantiated directly on an
+ // arena with this method.
+ //
+ // This function also accepts any type T that satisfies the arena message
+ // allocation protocol, documented above.
+ template <typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* CreateMessage(::google::protobuf::Arena* arena) {
+ if (arena == NULL) {
+ return new T;
+ } else {
+ return arena->CreateMessageInternal<T>(static_cast<T*>(0));
+ }
+ }
+
+ // One-argument form of CreateMessage. This is useful for constructing objects
+ // that implement the arena message construction protocol described above but
+ // take additional constructor arguments.
+ template <typename T, typename Arg> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* CreateMessage(::google::protobuf::Arena* arena, const Arg& arg) {
+ if (arena == NULL) {
+ return new T(NULL, arg);
+ } else {
+ return arena->CreateMessageInternal<T>(static_cast<T*>(0),
+ arg);
+ }
+ }
+
+ // Two-argument form of CreateMessage. This is useful for constructing objects
+ // that implement the arena message construction protocol described above but
+ // take additional constructor arguments.
+ template <typename T, typename Arg1, typename Arg2> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* CreateMessage(::google::protobuf::Arena* arena,
+ const Arg1& arg1,
+ const Arg2& arg2) {
+ if (arena == NULL) {
+ return new T(NULL, arg1, arg2);
+ } else {
+ return arena->CreateMessageInternal<T>(static_cast<T*>(0),
+ arg1, arg2);
+ }
+ }
+
+ // API to create any objects on the arena. Note that only the object will
+ // be created on the arena; the underlying ptrs (in case of a proto2 message)
+ // will be still heap allocated. Proto messages should usually be allocated
+ // with CreateMessage<T>() instead.
+ //
+ // Note that even if T satisfies the arena message construction protocol
+ // (InternalArenaConstructable_ trait and optional DestructorSkippable_
+ // trait), as described above, this function does not follow the protocol;
+ // instead, it treats T as a black-box type, just as if it did not have these
+ // traits. Specifically, T's constructor arguments will always be only those
+ // passed to Create<T>() -- no additional arena pointer is implicitly added.
+ // Furthermore, the destructor will always be called at arena destruction time
+ // (unless the destructor is trivial). Hence, from T's point of view, it is as
+ // if the object were allocated on the heap (except that the underlying memory
+ // is obtained from the arena).
+ template <typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* Create(::google::protobuf::Arena* arena) {
+ if (arena == NULL) {
+ return new T();
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value);
+ }
+ }
+
+ // Version of the above with one constructor argument for the created object.
+ template <typename T, typename Arg> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* Create(::google::protobuf::Arena* arena, const Arg& arg) {
+ if (arena == NULL) {
+ return new T(arg);
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg);
+ }
+ }
+
+ // Version of the above with two constructor arguments for the created object.
+ template <typename T, typename Arg1, typename Arg2> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* Create(::google::protobuf::Arena* arena, const Arg1& arg1, const Arg2& arg2) {
+ if (arena == NULL) {
+ return new T(arg1, arg2);
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg1, arg2);
+ }
+ }
+
+ // Version of the above with three constructor arguments for the created
+ // object.
+ template <typename T, typename Arg1, typename Arg2, typename Arg3>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static T* Create(::google::protobuf::Arena* arena,
+ const Arg1& arg1, const Arg2& arg2,
+ const Arg3& arg3) {
+ if (arena == NULL) {
+ return new T(arg1, arg2, arg3);
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg1, arg2, arg3);
+ }
+ }
+
+ // Version of the above with four constructor arguments for the created
+ // object.
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static T* Create(::google::protobuf::Arena* arena,
+ const Arg1& arg1, const Arg2& arg2,
+ const Arg3& arg3, const Arg4& arg4) {
+ if (arena == NULL) {
+ return new T(arg1, arg2, arg3, arg4);
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg1, arg2, arg3, arg4);
+ }
+ }
+
+ // Version of the above with five constructor arguments for the created
+ // object.
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static T* Create(::google::protobuf::Arena* arena,
+ const Arg1& arg1, const Arg2& arg2,
+ const Arg3& arg3, const Arg4& arg4,
+ const Arg5& arg5) {
+ if (arena == NULL) {
+ return new T(arg1, arg2, arg3, arg4, arg5);
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg1, arg2, arg3, arg4, arg5);
+ }
+ }
+
+ // Version of the above with six constructor arguments for the created
+ // object.
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5, typename Arg6>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static T* Create(::google::protobuf::Arena* arena,
+ const Arg1& arg1, const Arg2& arg2,
+ const Arg3& arg3, const Arg4& arg4,
+ const Arg5& arg5, const Arg6& arg6) {
+ if (arena == NULL) {
+ return new T(arg1, arg2, arg3, arg4, arg5, arg6);
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg1, arg2, arg3, arg4, arg5, arg6);
+ }
+ }
+
+ // Version of the above with seven constructor arguments for the created
+ // object.
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5, typename Arg6, typename Arg7>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static T* Create(::google::protobuf::Arena* arena,
+ const Arg1& arg1, const Arg2& arg2,
+ const Arg3& arg3, const Arg4& arg4,
+ const Arg5& arg5, const Arg6& arg6,
+ const Arg7& arg7) {
+ if (arena == NULL) {
+ return new T(arg1, arg2, arg3, arg4, arg5, arg6, arg7);
+ } else {
+ return arena->CreateInternal<T>(google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg1, arg2, arg3, arg4, arg5, arg6, arg7);
+ }
+ }
+
+ // Version of the above with eight constructor arguments for the created
+ // object.
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5, typename Arg6, typename Arg7,
+ typename Arg8>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static T* Create(::google::protobuf::Arena* arena,
+ const Arg1& arg1, const Arg2& arg2,
+ const Arg3& arg3, const Arg4& arg4,
+ const Arg5& arg5, const Arg6& arg6,
+ const Arg7& arg7, const Arg8& arg8) {
+ if (arena == NULL) {
+ return new T(arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8);
+ } else {
+ return arena->CreateInternal<T>(
+ google::protobuf::internal::has_trivial_destructor<T>::value,
+ arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8);
+ }
+ }
+
+ // Create an array of object type T on the arena *without* invoking the
+ // constructor of T. If `arena` is null, then the return value should be freed
+ // with `delete[] x;` (or `::operator delete[](x);`).
+ // To ensure safe uses, this function checks at compile time
+ // (when compiled as C++11) that T is trivially default-constructible and
+ // trivially destructible.
+ template <typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* CreateArray(::google::protobuf::Arena* arena, size_t num_elements) {
+ GOOGLE_CHECK_LE(num_elements,
+ std::numeric_limits<size_t>::max() / sizeof(T))
+ << "Requested size is too large to fit into size_t.";
+ if (arena == NULL) {
+ return static_cast<T*>(::operator new[](num_elements * sizeof(T)));
+ } else {
+ return arena->CreateInternalRawArray<T>(num_elements);
+ }
+ }
+
+ // Returns the total space used by the arena, which is the sums of the sizes
+ // of the underlying blocks. The total space used may not include the new
+ // blocks that are allocated by this arena from other threads concurrently
+ // with the call to this method.
+ GOOGLE_ATTRIBUTE_NOINLINE uint64 SpaceAllocated() const;
+ // As above, but does not include any free space in underlying blocks.
+ GOOGLE_ATTRIBUTE_NOINLINE uint64 SpaceUsed() const;
+
+ // Combines SpaceAllocated and SpaceUsed. Returns a pair of
+ // <space_allocated, space_used>.
+ GOOGLE_ATTRIBUTE_NOINLINE pair<uint64, uint64> SpaceAllocatedAndUsed() const;
+
+ // Frees all storage allocated by this arena after calling destructors
+ // registered with OwnDestructor() and freeing objects registered with Own().
+ // Any objects allocated on this arena are unusable after this call. It also
+ // returns the total space used by the arena which is the sums of the sizes
+ // of the allocated blocks. This method is not thread-safe.
+ GOOGLE_ATTRIBUTE_NOINLINE uint64 Reset();
+
+ // Adds |object| to a list of heap-allocated objects to be freed with |delete|
+ // when the arena is destroyed or reset.
+ template <typename T> GOOGLE_ATTRIBUTE_NOINLINE
+ void Own(T* object) {
+ OwnInternal(object, google::protobuf::internal::is_convertible<T*, ::google::protobuf::Message*>());
+ }
+
+ // Adds |object| to a list of objects whose destructors will be manually
+ // called when the arena is destroyed or reset. This differs from Own() in
+ // that it does not free the underlying memory with |delete|; hence, it is
+ // normally only used for objects that are placement-newed into
+ // arena-allocated memory.
+ template <typename T> GOOGLE_ATTRIBUTE_NOINLINE
+ void OwnDestructor(T* object) {
+ if (object != NULL) {
+ AddListNode(object, &internal::arena_destruct_object<T>);
+ }
+ }
+
+ // Adds a custom member function on an object to the list of destructors that
+ // will be manually called when the arena is destroyed or reset. This differs
+ // from OwnDestructor() in that any member function may be specified, not only
+ // the class destructor.
+ GOOGLE_ATTRIBUTE_NOINLINE void OwnCustomDestructor(void* object,
+ void (*destruct)(void*)) {
+ AddListNode(object, destruct);
+ }
+
+ // Retrieves the arena associated with |value| if |value| is an arena-capable
+ // message, or NULL otherwise. This differs from value->GetArena() in that the
+ // latter is a virtual call, while this method is a templated call that
+ // resolves at compile-time.
+ template<typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static ::google::protobuf::Arena* GetArena(const T* value) {
+ return GetArenaInternal(value, static_cast<T*>(0));
+ }
+
+ private:
+ struct InternalIsArenaConstructableHelper {
+ template<typename U>
+ static char ArenaConstructable(
+ const typename U::InternalArenaConstructable_*);
+ template<typename U>
+ static double ArenaConstructable(...);
+ };
+
+ public:
+ // Helper typetrait that indicates support for arenas in a type T at compile
+ // time. This is public only to allow construction of higher-level templated
+ // utilities. is_arena_constructable<T>::value is true if the message type T
+ // has arena support enabled, and false otherwise.
+ //
+ // This is inside Arena because only Arena has the friend relationships
+ // necessary to see the underlying generated code traits.
+ template <typename T>
+ struct is_arena_constructable
+ : public google::protobuf::internal::integral_constant<
+ bool, sizeof(InternalIsArenaConstructableHelper::ArenaConstructable<
+ const T>(static_cast<const T*>(0))) == sizeof(char)> {
+ };
+
+ private:
+ // Blocks are variable length malloc-ed objects. The following structure
+ // describes the common header for all blocks.
+ struct Block {
+ void* owner; // &ThreadCache of thread that owns this block, or
+ // &this->owner if not yet owned by a thread.
+ Block* next; // Next block in arena (may have different owner)
+ // ((char*) &block) + pos is next available byte. It is always
+ // aligned at a multiple of 8 bytes.
+ size_t pos;
+ size_t size; // total size of the block.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE size_t avail() const { return size - pos; }
+ // data follows
+ };
+
+ template<typename Type> friend class ::google::protobuf::internal::GenericTypeHandler;
+ friend class MockArena; // For unit-testing.
+ friend class internal::ArenaString; // For AllocateAligned.
+ friend class internal::LazyField; // For CreateMaybeMessage.
+
+ struct ThreadCache {
+ // The ThreadCache is considered valid as long as this matches the
+ // lifecycle_id of the arena being used.
+ int64 last_lifecycle_id_seen;
+ Block* last_block_used_;
+ };
+
+ static const size_t kHeaderSize = sizeof(Block);
+ static google::protobuf::internal::SequenceNumber lifecycle_id_generator_;
+#if defined(GOOGLE_PROTOBUF_NO_THREADLOCAL)
+ // Android ndk does not support GOOGLE_THREAD_LOCAL keyword so we use a custom thread
+ // local storage class we implemented.
+ // iOS also does not support the GOOGLE_THREAD_LOCAL keyword.
+ static ThreadCache& thread_cache();
+#elif defined(PROTOBUF_USE_DLLS)
+ // Thread local variables cannot be exposed through DLL interface but we can
+ // wrap them in static functions.
+ static ThreadCache& thread_cache();
+#else
+ static GOOGLE_THREAD_LOCAL ThreadCache thread_cache_;
+ static ThreadCache& thread_cache() { return thread_cache_; }
+#endif
+
+ // SFINAE for skipping addition to delete list for a message type when created
+ // with CreateMessage. This is mainly to skip proto2/proto1 message objects
+ // with cc_enable_arenas=true from being part of the delete list. Also, note,
+ // compiler will optimize out the branch in CreateInternal<T>.
+ template<typename T>
+ static inline bool SkipDeleteList(typename T::DestructorSkippable_*) {
+ return true;
+ }
+
+ // For message objects that don't have the DestructorSkippable_ trait, we
+ // always add to the delete list.
+ template<typename T>
+ static inline bool SkipDeleteList(...) {
+ return google::protobuf::internal::has_trivial_destructor<T>::value;
+ }
+
+ private:
+ struct InternalIsDestructorSkippableHelper {
+ template<typename U>
+ static char DestructorSkippable(
+ const typename U::DestructorSkippable_*);
+ template<typename U>
+ static double DestructorSkippable(...);
+ };
+
+ public:
+ // Helper typetrait that indicates whether the desctructor of type T should be
+ // called when arena is destroyed at compile time. This is only to allow
+ // construction of higher-level templated utilities.
+ // is_destructor_skippable<T>::value is true if the destructor of the message
+ // type T should not be called when arena is destroyed or false otherwise.
+ // This is inside Arena because only Arena has the friend relationships
+ // necessary to see the underlying generated code traits.
+ template<typename T>
+ struct is_destructor_skippable
+ : public google::protobuf::internal::integral_constant<
+ bool,
+ sizeof(InternalIsDestructorSkippableHelper::DestructorSkippable<
+ const T>(static_cast<const T*>(0))) == sizeof(char) ||
+ google::protobuf::internal::has_trivial_destructor<T>::value> {};
+
+ // CreateMessage<T> requires that T supports arenas, but this private method
+ // works whether or not T supports arenas. These are not exposed to user code
+ // as it can cause confusing API usages, and end up having double free in
+ // user code. These are used only internally from LazyField and Repeated
+ // fields, since they are designed to work in all mode combinations.
+ template<typename Msg> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static Msg* CreateMaybeMessage(
+ Arena* arena, typename Msg::InternalArenaConstructable_*) {
+ return CreateMessage<Msg>(arena);
+ }
+
+ template<typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static T* CreateMaybeMessage(Arena* arena, ...) {
+ return Create<T>(arena);
+ }
+
+ // Just allocate the required size for the given type assuming the
+ // type has a trivial constructor.
+ template<typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ T* CreateInternalRawArray(size_t num_elements) {
+ GOOGLE_CHECK_LE(num_elements,
+ std::numeric_limits<size_t>::max() / sizeof(T))
+ << "Requested size is too large to fit into size_t.";
+ return static_cast<T*>(
+ AllocateAligned(RTTI_TYPE_ID(T), sizeof(T) * num_elements));
+ }
+
+ template <typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ T* CreateInternal(bool skip_explicit_ownership) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T))) T();
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ T* CreateInternal(bool skip_explicit_ownership, const Arg& arg) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T))) T(arg);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg1, typename Arg2> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ T* CreateInternal(
+ bool skip_explicit_ownership, const Arg1& arg1, const Arg2& arg2) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T))) T(arg1, arg2);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg1, typename Arg2, typename Arg3>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE T* CreateInternal(bool skip_explicit_ownership,
+ const Arg1& arg1,
+ const Arg2& arg2,
+ const Arg3& arg3) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T)))
+ T(arg1, arg2, arg3);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE T* CreateInternal(bool skip_explicit_ownership,
+ const Arg1& arg1,
+ const Arg2& arg2,
+ const Arg3& arg3,
+ const Arg4& arg4) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T)))
+ T(arg1, arg2, arg3, arg4);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE T* CreateInternal(bool skip_explicit_ownership,
+ const Arg1& arg1,
+ const Arg2& arg2,
+ const Arg3& arg3,
+ const Arg4& arg4,
+ const Arg5& arg5) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T)))
+ T(arg1, arg2, arg3, arg4, arg5);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5, typename Arg6>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE T* CreateInternal(bool skip_explicit_ownership,
+ const Arg1& arg1,
+ const Arg2& arg2,
+ const Arg3& arg3,
+ const Arg4& arg4,
+ const Arg5& arg5,
+ const Arg6& arg6) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T)))
+ T(arg1, arg2, arg3, arg4, arg5, arg6);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5, typename Arg6, typename Arg7>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE T* CreateInternal(bool skip_explicit_ownership,
+ const Arg1& arg1,
+ const Arg2& arg2,
+ const Arg3& arg3,
+ const Arg4& arg4,
+ const Arg5& arg5,
+ const Arg6& arg6,
+ const Arg7& arg7) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T)))
+ T(arg1, arg2, arg3, arg4, arg5, arg6, arg7);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T, typename Arg1, typename Arg2, typename Arg3,
+ typename Arg4, typename Arg5, typename Arg6, typename Arg7,
+ typename Arg8>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE T* CreateInternal(bool skip_explicit_ownership,
+ const Arg1& arg1,
+ const Arg2& arg2,
+ const Arg3& arg3,
+ const Arg4& arg4,
+ const Arg5& arg5,
+ const Arg6& arg6,
+ const Arg7& arg7,
+ const Arg8& arg8) {
+ T* t = new (AllocateAligned(RTTI_TYPE_ID(T), sizeof(T)))
+ T(arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8);
+ if (!skip_explicit_ownership) {
+ AddListNode(t, &internal::arena_destruct_object<T>);
+ }
+ return t;
+ }
+
+ template <typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ T* CreateMessageInternal(typename T::InternalArenaConstructable_*) {
+ return CreateInternal<T, Arena*>(SkipDeleteList<T>(static_cast<T*>(0)),
+ this);
+ }
+
+ template <typename T, typename Arg> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ T* CreateMessageInternal(typename T::InternalArenaConstructable_*,
+ const Arg& arg) {
+ return CreateInternal<T, Arena*>(SkipDeleteList<T>(static_cast<T*>(0)),
+ this, arg);
+ }
+
+ template <typename T, typename Arg1, typename Arg2> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ T* CreateMessageInternal(typename T::InternalArenaConstructable_*,
+ const Arg1& arg1, const Arg2& arg2) {
+ return CreateInternal<T, Arena*>(SkipDeleteList<T>(static_cast<T*>(0)),
+ this, arg1, arg2);
+ }
+
+ // CreateInArenaStorage is used to implement map field. Without it,
+ // google::protobuf::Map need to call generated message's protected arena constructor,
+ // which needs to declare google::protobuf::Map as friend of generated message.
+ template <typename T>
+ static void CreateInArenaStorage(T* ptr, Arena* arena) {
+ CreateInArenaStorageInternal(ptr, arena,
+ typename is_arena_constructable<T>::type());
+ RegisterDestructorInternal(ptr, arena,
+ typename is_destructor_skippable<T>::type());
+ }
+
+ template <typename T>
+ static void CreateInArenaStorageInternal(
+ T* ptr, Arena* arena, google::protobuf::internal::true_type) {
+ new (ptr) T(arena);
+ }
+ template <typename T>
+ static void CreateInArenaStorageInternal(
+ T* ptr, Arena* arena, google::protobuf::internal::false_type) {
+ new (ptr) T();
+ }
+
+ template <typename T>
+ static void RegisterDestructorInternal(
+ T* ptr, Arena* arena, google::protobuf::internal::true_type) {}
+ template <typename T>
+ static void RegisterDestructorInternal(
+ T* ptr, Arena* arena, google::protobuf::internal::false_type) {
+ arena->OwnDestructor(ptr);
+ }
+
+ // These implement Own(), which registers an object for deletion (destructor
+ // call and operator delete()). The second parameter has type 'true_type' if T
+ // is a subtype of ::google::protobuf::Message and 'false_type' otherwise. Collapsing
+ // all template instantiations to one for generic Message reduces code size,
+ // using the virtual destructor instead.
+ template<typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ void OwnInternal(T* object, google::protobuf::internal::true_type) {
+ if (object != NULL) {
+ AddListNode(object, &internal::arena_delete_object< ::google::protobuf::Message >);
+ }
+ }
+ template<typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ void OwnInternal(T* object, google::protobuf::internal::false_type) {
+ if (object != NULL) {
+ AddListNode(object, &internal::arena_delete_object<T>);
+ }
+ }
+
+ // Implementation for GetArena(). Only message objects with
+ // InternalArenaConstructable_ tags can be associated with an arena, and such
+ // objects must implement a GetArenaNoVirtual() method.
+ template<typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static ::google::protobuf::Arena* GetArenaInternal(
+ const T* value, typename T::InternalArenaConstructable_*) {
+ return value->GetArenaNoVirtual();
+ }
+
+ template<typename T> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static ::google::protobuf::Arena* GetArenaInternal(const T* value, ...) {
+ return NULL;
+ }
+
+ // Allocate and also optionally call on_arena_allocation callback with the
+ // allocated type info when the hooks are in place in ArenaOptions and
+ // the cookie is not null.
+ void* AllocateAligned(const std::type_info* allocated, size_t n);
+
+ // Allocate an internal allocation, avoiding optional typed monitoring.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE void* AllocateAligned(size_t n) {
+ return AllocateAligned(NULL, n);
+ }
+
+ void Init();
+
+ // Free all blocks and return the total space used which is the sums of sizes
+ // of the all the allocated blocks.
+ uint64 FreeBlocks();
+
+ // Add object pointer and cleanup function pointer to the list.
+ // TODO(rohananil, cfallin): We could pass in a sub-arena into this method
+ // to avoid polluting blocks of this arena with list nodes. This would help in
+ // mixed mode (where many protobufs have cc_enable_arenas=false), and is an
+ // alternative to a chunked linked-list, but with extra overhead of *next.
+ void AddListNode(void* elem, void (*cleanup)(void*));
+ // Delete or Destruct all objects owned by the arena.
+ void CleanupList();
+ uint64 ResetInternal();
+
+ inline void SetThreadCacheBlock(Block* block) {
+ thread_cache().last_block_used_ = block;
+ thread_cache().last_lifecycle_id_seen = lifecycle_id_;
+ }
+
+ int64 lifecycle_id_; // Unique for each arena. Changes on Reset().
+
+ google::protobuf::internal::AtomicWord blocks_; // Head of linked list of all allocated blocks
+ google::protobuf::internal::AtomicWord hint_; // Fast thread-local block access
+
+ // Node contains the ptr of the object to be cleaned up and the associated
+ // cleanup function ptr.
+ struct Node {
+ void* elem; // Pointer to the object to be cleaned up.
+ void (*cleanup)(void*); // Function pointer to the destructor or deleter.
+ Node* next; // Next node in the list.
+ };
+
+ google::protobuf::internal::AtomicWord cleanup_list_; // Head of a linked list of nodes containing object
+ // ptrs and cleanup methods.
+
+ bool owns_first_block_; // Indicates that arena owns the first block
+ Mutex blocks_lock_;
+
+ void AddBlock(Block* b);
+ // Access must be synchronized, either by blocks_lock_ or by being called from
+ // Init()/Reset().
+ void AddBlockInternal(Block* b);
+ void* SlowAlloc(size_t n);
+ Block* FindBlock(void* me);
+ Block* NewBlock(void* me, Block* my_last_block, size_t n,
+ size_t start_block_size, size_t max_block_size);
+ static void* AllocFromBlock(Block* b, size_t n);
+ template <typename Key, typename T>
+ friend class Map;
+
+ // The arena may save a cookie it receives from the external on_init hook
+ // and then use it when calling the on_reset and on_destruction hooks.
+ void* hooks_cookie_;
+
+ ArenaOptions options_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Arena);
+};
+
+// Defined above for supporting environments without RTTI.
+#undef RTTI_TYPE_ID
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_ARENA_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arena_nc.cc b/third_party/protobuf/3.0.0/src/google/protobuf/arena_nc.cc
new file mode 100644
index 0000000000..f2f084274a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arena_nc.cc
@@ -0,0 +1,45 @@
+// 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.
+
+// Negative compilation test for arena usage.
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/unittest.pb.h>
+
+#ifdef TEST_ARENA_PRIVATE_CONSTRUCTOR
+
+namespace google {
+void ArenaPrivateConstructor() {
+ google::protobuf::Arena arena;
+ protobuf_unittest::TestAllTypes message(&arena);
+}
+
+#endif
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arena_nc_test.py b/third_party/protobuf/3.0.0/src/google/protobuf/arena_nc_test.py
new file mode 100644
index 0000000000..56a7dd05aa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arena_nc_test.py
@@ -0,0 +1,61 @@
+#! /usr/bin/env python
+#
+# 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.
+
+"""Negative compilation unit tests for arena API."""
+
+import unittest
+
+from google3.testing.pybase import fake_target_util
+from google3.testing.pybase import unittest
+
+
+class ArenaNcTest(unittest.TestCase):
+
+ def testCompilerErrors(self):
+ """Runs a list of tests to verify compiler error messages."""
+
+ # Defines a list of test specs, where each element is a tuple
+ # (test name, list of regexes for matching the compiler errors).
+ test_specs = [
+ ('ARENA_PRIVATE_CONSTRUCTOR',
+ [r'calling a protected constructor']),
+ ('SANITY', None)]
+
+ fake_target_util.AssertCcCompilerErrors(
+ self, # The current test case.
+ 'google3/google/protobuf/arena_nc', # The fake target file.
+ 'arena_nc.o', # The sub-target to build.
+ test_specs # List of test specifications.
+ )
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.cc
new file mode 100644
index 0000000000..df9c5bd6b4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.cc
@@ -0,0 +1,50 @@
+// 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.
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/arena_test_util.h>
+
+
+#define EXPECT_EQ GOOGLE_CHECK_EQ
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+NoHeapChecker::~NoHeapChecker() {
+ capture_alloc.Unhook();
+ EXPECT_EQ(0, capture_alloc.alloc_count());
+ EXPECT_EQ(0, capture_alloc.free_count());
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.h
new file mode 100644
index 0000000000..690cc706ee
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arena_test_util.h
@@ -0,0 +1,60 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_ARENA_TEST_UTIL_H__
+#define GOOGLE_PROTOBUF_ARENA_TEST_UTIL_H__
+
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+class NoHeapChecker {
+ public:
+ NoHeapChecker() {
+ capture_alloc.Hook();
+ }
+ ~NoHeapChecker();
+ private:
+ class NewDeleteCapture {
+ public:
+ // TOOD(xiaofeng): Implement this for opensource protobuf.
+ void Hook() {}
+ void Unhook() {}
+ int alloc_count() { return 0; }
+ int free_count() { return 0; }
+ } capture_alloc;
+};
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_ARENA_TEST_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arena_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/arena_unittest.cc
new file mode 100644
index 0000000000..5f33e93987
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arena_unittest.cc
@@ -0,0 +1,1353 @@
+// 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.
+
+#include <google/protobuf/arena.h>
+
+#include <algorithm>
+#include <cstring>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <typeinfo>
+#include <vector>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/arena_test_util.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_arena.pb.h>
+#include <google/protobuf/unittest_no_arena.pb.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/message_lite.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/wire_format_lite.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <gtest/gtest.h>
+
+
+namespace google {
+using proto2_arena_unittest::ArenaMessage;
+using protobuf_unittest::TestAllTypes;
+using protobuf_unittest::TestAllExtensions;
+using protobuf_unittest::TestOneof2;
+using protobuf_unittest::TestEmptyMessage;
+
+namespace protobuf {
+namespace {
+
+class Notifier {
+ public:
+ Notifier() : count_(0) {}
+ void Notify() {
+ count_++;
+ }
+ int GetCount() {
+ return count_;
+ }
+
+ private:
+ int count_;
+};
+
+class SimpleDataType {
+ public:
+ SimpleDataType() : notifier_(NULL) {}
+ void SetNotifier(Notifier* notifier) {
+ notifier_ = notifier;
+ }
+ virtual ~SimpleDataType() {
+ if (notifier_ != NULL) {
+ notifier_->Notify();
+ }
+ };
+ private:
+ Notifier* notifier_;
+};
+
+// A simple class that does not allow copying and so cannot be used as a
+// parameter type without "const &".
+class PleaseDontCopyMe {
+ public:
+ explicit PleaseDontCopyMe(int value) : value_(value) {}
+
+ int value() const { return value_; }
+
+ private:
+ int value_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PleaseDontCopyMe);
+};
+
+// A class that takes four different types as constructor arguments.
+class MustBeConstructedWithOneThroughFour {
+ public:
+ MustBeConstructedWithOneThroughFour(
+ int one, const char* two, const string& three,
+ const PleaseDontCopyMe* four)
+ : one_(one), two_(two), three_(three), four_(four) {}
+
+ int one_;
+ const char* const two_;
+ string three_;
+ const PleaseDontCopyMe* four_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MustBeConstructedWithOneThroughFour);
+};
+
+// A class that takes eight different types as constructor arguments.
+class MustBeConstructedWithOneThroughEight {
+ public:
+ MustBeConstructedWithOneThroughEight(
+ int one, const char* two, const string& three,
+ const PleaseDontCopyMe* four, int five, const char* six,
+ const string& seven, const string& eight)
+ : one_(one), two_(two), three_(three), four_(four), five_(five),
+ six_(six), seven_(seven), eight_(eight) {}
+
+ int one_;
+ const char* const two_;
+ string three_;
+ const PleaseDontCopyMe* four_;
+ int five_;
+ const char* const six_;
+ string seven_;
+ string eight_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MustBeConstructedWithOneThroughEight);
+};
+
+} // namespace
+
+TEST(ArenaTest, ArenaConstructable) {
+ EXPECT_TRUE(Arena::is_arena_constructable<TestAllTypes>::type::value);
+ EXPECT_TRUE(Arena::is_arena_constructable<const TestAllTypes>::type::value);
+ EXPECT_FALSE(Arena::is_arena_constructable<Arena>::type::value);
+}
+
+TEST(ArenaTest, BasicCreate) {
+ Arena arena;
+ EXPECT_TRUE(Arena::Create<int32>(&arena) != NULL);
+ EXPECT_TRUE(Arena::Create<int64>(&arena) != NULL);
+ EXPECT_TRUE(Arena::Create<float>(&arena) != NULL);
+ EXPECT_TRUE(Arena::Create<double>(&arena) != NULL);
+ EXPECT_TRUE(Arena::Create<string>(&arena) != NULL);
+ arena.Own(new int32);
+ arena.Own(new int64);
+ arena.Own(new float);
+ arena.Own(new double);
+ arena.Own(new string);
+ arena.Own<int>(NULL);
+ Notifier notifier;
+ SimpleDataType* data = Arena::Create<SimpleDataType>(&arena);
+ data->SetNotifier(&notifier);
+ data = new SimpleDataType;
+ data->SetNotifier(&notifier);
+ arena.Own(data);
+ arena.Reset();
+ EXPECT_EQ(2, notifier.GetCount());
+}
+
+TEST(ArenaTest, CreateWithFourConstructorArguments) {
+ Arena arena;
+ const string three("3");
+ const PleaseDontCopyMe four(4);
+ const MustBeConstructedWithOneThroughFour* new_object =
+ Arena::Create<MustBeConstructedWithOneThroughFour>(
+ &arena, 1, "2", three, &four);
+ EXPECT_TRUE(new_object != NULL);
+ ASSERT_EQ(1, new_object->one_);
+ ASSERT_STREQ("2", new_object->two_);
+ ASSERT_EQ("3", new_object->three_);
+ ASSERT_EQ(4, new_object->four_->value());
+}
+
+TEST(ArenaTest, CreateWithEightConstructorArguments) {
+ Arena arena;
+ const string three("3");
+ const PleaseDontCopyMe four(4);
+ const string seven("7");
+ const string eight("8");
+ const MustBeConstructedWithOneThroughEight* new_object =
+ Arena::Create<MustBeConstructedWithOneThroughEight>(
+ &arena, 1, "2", three, &four, 5, "6", seven, eight);
+ EXPECT_TRUE(new_object != NULL);
+ ASSERT_EQ(1, new_object->one_);
+ ASSERT_STREQ("2", new_object->two_);
+ ASSERT_EQ("3", new_object->three_);
+ ASSERT_EQ(4, new_object->four_->value());
+ ASSERT_EQ(5, new_object->five_);
+ ASSERT_STREQ("6", new_object->six_);
+ ASSERT_EQ("7", new_object->seven_);
+ ASSERT_EQ("8", new_object->eight_);
+}
+
+TEST(ArenaTest, InitialBlockTooSmall) {
+ // Construct a small (64 byte) initial block of memory to be used by the
+ // arena allocator; then, allocate an object which will not fit in the
+ // initial block.
+ std::vector<char> arena_block(64);
+ ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena(options);
+
+ char* p = ::google::protobuf::Arena::CreateArray<char>(&arena, 96);
+ uintptr_t allocation = reinterpret_cast<uintptr_t>(p);
+
+ // Ensure that the arena allocator did not return memory pointing into the
+ // initial block of memory.
+ uintptr_t arena_start = reinterpret_cast<uintptr_t>(&arena_block[0]);
+ uintptr_t arena_end = arena_start + arena_block.size();
+ EXPECT_FALSE(allocation >= arena_start && allocation < arena_end);
+
+ // Write to the memory we allocated; this should (but is not guaranteed to)
+ // trigger a check for heap corruption if the object was allocated from the
+ // initially-provided block.
+ memset(p, '\0', 96);
+}
+
+TEST(ArenaTest, Parsing) {
+ TestAllTypes original;
+ TestUtil::SetAllFields(&original);
+
+ // Test memory leak.
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->ParseFromString(original.SerializeAsString());
+ TestUtil::ExpectAllFieldsSet(*arena_message);
+
+ // Test that string fields have null terminator bytes (earlier bug).
+ EXPECT_EQ(strlen(original.optional_string().c_str()),
+ strlen(arena_message->optional_string().c_str()));
+}
+
+TEST(ArenaTest, UnknownFields) {
+ TestAllTypes original;
+ TestUtil::SetAllFields(&original);
+
+ // Test basic parsing into (populating) and reading out of unknown fields on
+ // an arena.
+ Arena arena;
+ TestEmptyMessage* arena_message =
+ Arena::CreateMessage<TestEmptyMessage>(&arena);
+ arena_message->ParseFromString(original.SerializeAsString());
+
+ TestAllTypes copied;
+ copied.ParseFromString(arena_message->SerializeAsString());
+ TestUtil::ExpectAllFieldsSet(copied);
+
+ // Exercise UFS manual manipulation (setters).
+ arena_message = Arena::CreateMessage<TestEmptyMessage>(&arena);
+ arena_message->mutable_unknown_fields()->AddVarint(
+ TestAllTypes::kOptionalInt32FieldNumber, 42);
+ copied.Clear();
+ copied.ParseFromString(arena_message->SerializeAsString());
+ EXPECT_TRUE(copied.has_optional_int32());
+ EXPECT_EQ(42, copied.optional_int32());
+
+ // Exercise UFS swap path.
+ TestEmptyMessage* arena_message_2 =
+ Arena::CreateMessage<TestEmptyMessage>(&arena);
+ arena_message_2->Swap(arena_message);
+ copied.Clear();
+ copied.ParseFromString(arena_message_2->SerializeAsString());
+ EXPECT_TRUE(copied.has_optional_int32());
+ EXPECT_EQ(42, copied.optional_int32());
+
+ // Test field manipulation.
+ TestEmptyMessage* arena_message_3 =
+ Arena::CreateMessage<TestEmptyMessage>(&arena);
+ arena_message_3->mutable_unknown_fields()->AddVarint(1000, 42);
+ arena_message_3->mutable_unknown_fields()->AddFixed32(1001, 42);
+ arena_message_3->mutable_unknown_fields()->AddFixed64(1002, 42);
+ arena_message_3->mutable_unknown_fields()->AddLengthDelimited(1003);
+ arena_message_3->mutable_unknown_fields()->DeleteSubrange(0, 2);
+ arena_message_3->mutable_unknown_fields()->DeleteByNumber(1002);
+ arena_message_3->mutable_unknown_fields()->DeleteByNumber(1003);
+ EXPECT_TRUE(arena_message_3->unknown_fields().empty());
+}
+
+TEST(ArenaTest, Swap) {
+ Arena arena1;
+ Arena arena2;
+ TestAllTypes* arena1_message;
+ TestAllTypes* arena2_message;
+
+ // Case 1: Swap(), no UFS on either message, both messages on different
+ // arenas. Arena pointers should remain the same after swap.
+ arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ arena1_message->Swap(arena2_message);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(&arena2, arena2_message->GetArena());
+
+ // Case 2: Swap(), UFS on one message, both messages on different arenas.
+ arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ arena1_message->mutable_unknown_fields()->AddVarint(1, 42);
+ arena1_message->Swap(arena2_message);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(&arena2, arena2_message->GetArena());
+ EXPECT_EQ(0, arena1_message->unknown_fields().field_count());
+ EXPECT_EQ(1, arena2_message->unknown_fields().field_count());
+ EXPECT_EQ(42, arena2_message->unknown_fields().field(0).varint());
+
+ // Case 3: Swap(), UFS on both messages, both messages on different arenas.
+ arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ arena1_message->mutable_unknown_fields()->AddVarint(1, 42);
+ arena2_message->mutable_unknown_fields()->AddVarint(2, 84);
+ arena1_message->Swap(arena2_message);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(&arena2, arena2_message->GetArena());
+ EXPECT_EQ(1, arena1_message->unknown_fields().field_count());
+ EXPECT_EQ(1, arena2_message->unknown_fields().field_count());
+ EXPECT_EQ(84, arena1_message->unknown_fields().field(0).varint());
+ EXPECT_EQ(42, arena2_message->unknown_fields().field(0).varint());
+}
+
+TEST(ArenaTest, ReflectionSwapFields) {
+ Arena arena1;
+ Arena arena2;
+ TestAllTypes* arena1_message;
+ TestAllTypes* arena2_message;
+
+ // Case 1: messages on different arenas, only one message is set.
+ arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ TestUtil::SetAllFields(arena1_message);
+ const Reflection* reflection = arena1_message->GetReflection();
+ std::vector<const FieldDescriptor*> fields;
+ reflection->ListFields(*arena1_message, &fields);
+ reflection->SwapFields(arena1_message, arena2_message, fields);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(&arena2, arena2_message->GetArena());
+ string output;
+ arena1_message->SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+ TestUtil::ExpectAllFieldsSet(*arena2_message);
+ reflection->SwapFields(arena1_message, arena2_message, fields);
+ arena2_message->SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+ TestUtil::ExpectAllFieldsSet(*arena1_message);
+
+ // Case 2: messages on different arenas, both messages are set.
+ arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ TestUtil::SetAllFields(arena1_message);
+ TestUtil::SetAllFields(arena2_message);
+ reflection->SwapFields(arena1_message, arena2_message, fields);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(&arena2, arena2_message->GetArena());
+ TestUtil::ExpectAllFieldsSet(*arena1_message);
+ TestUtil::ExpectAllFieldsSet(*arena2_message);
+
+ // Case 3: messages on different arenas with different lifetimes.
+ arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ {
+ Arena arena3;
+ TestAllTypes* arena3_message = Arena::CreateMessage<TestAllTypes>(&arena3);
+ TestUtil::SetAllFields(arena3_message);
+ reflection->SwapFields(arena1_message, arena3_message, fields);
+ }
+ TestUtil::ExpectAllFieldsSet(*arena1_message);
+
+ // Case 4: one message on arena, the other on heap.
+ arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ TestAllTypes message;
+ TestUtil::SetAllFields(arena1_message);
+ reflection->SwapFields(arena1_message, &message, fields);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(NULL, message.GetArena());
+ arena1_message->SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+ TestUtil::ExpectAllFieldsSet(message);
+}
+
+TEST(ArenaTest, SetAllocatedMessage) {
+ Arena arena;
+ TestAllTypes *arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ TestAllTypes::NestedMessage* nested = new TestAllTypes::NestedMessage;
+ nested->set_bb(118);
+ arena_message->set_allocated_optional_nested_message(nested);
+ EXPECT_EQ(118, arena_message->optional_nested_message().bb());
+
+ protobuf_unittest_no_arena::TestNoArenaMessage no_arena_message;
+ EXPECT_FALSE(no_arena_message.has_arena_message());
+ no_arena_message.set_allocated_arena_message(NULL);
+ EXPECT_FALSE(no_arena_message.has_arena_message());
+ no_arena_message.set_allocated_arena_message(new ArenaMessage);
+ EXPECT_TRUE(no_arena_message.has_arena_message());
+}
+
+TEST(ArenaTest, ReleaseMessage) {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->mutable_optional_nested_message()->set_bb(118);
+ google::protobuf::scoped_ptr<TestAllTypes::NestedMessage> nested(
+ arena_message->release_optional_nested_message());
+ EXPECT_EQ(118, nested->bb());
+
+ TestAllTypes::NestedMessage* released_null =
+ arena_message->release_optional_nested_message();
+ EXPECT_EQ(NULL, released_null);
+}
+
+TEST(ArenaTest, SetAllocatedString) {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ string* allocated_str = new string("hello");
+ arena_message->set_allocated_optional_string(allocated_str);
+ EXPECT_EQ("hello", arena_message->optional_string());
+}
+
+TEST(ArenaTest, ReleaseString) {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->set_optional_string("hello");
+ google::protobuf::scoped_ptr<string> released_str(
+ arena_message->release_optional_string());
+ EXPECT_EQ("hello", *released_str);
+
+ // Test default value.
+}
+
+
+TEST(ArenaTest, SwapBetweenArenasWithAllFieldsSet) {
+ Arena arena1;
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ {
+ Arena arena2;
+ TestAllTypes* arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ TestUtil::SetAllFields(arena2_message);
+ arena2_message->Swap(arena1_message);
+ string output;
+ arena2_message->SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+ }
+ TestUtil::ExpectAllFieldsSet(*arena1_message);
+}
+
+TEST(ArenaTest, SwapBetweenArenaAndNonArenaWithAllFieldsSet) {
+ TestAllTypes non_arena_message;
+ TestUtil::SetAllFields(&non_arena_message);
+ {
+ Arena arena2;
+ TestAllTypes* arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ TestUtil::SetAllFields(arena2_message);
+ arena2_message->Swap(&non_arena_message);
+ TestUtil::ExpectAllFieldsSet(*arena2_message);
+ TestUtil::ExpectAllFieldsSet(non_arena_message);
+ }
+}
+
+TEST(ArenaTest, UnsafeArenaSwap) {
+ Arena shared_arena;
+ TestAllTypes* message1 = Arena::CreateMessage<TestAllTypes>(&shared_arena);
+ TestAllTypes* message2 = Arena::CreateMessage<TestAllTypes>(&shared_arena);
+ TestUtil::SetAllFields(message1);
+ message1->UnsafeArenaSwap(message2);
+ TestUtil::ExpectAllFieldsSet(*message2);
+}
+
+TEST(ArenaTest, SwapBetweenArenasUsingReflection) {
+ Arena arena1;
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ {
+ Arena arena2;
+ TestAllTypes* arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ TestUtil::SetAllFields(arena2_message);
+ const Reflection* r = arena2_message->GetReflection();
+ r->Swap(arena1_message, arena2_message);
+ string output;
+ arena2_message->SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+ }
+ TestUtil::ExpectAllFieldsSet(*arena1_message);
+}
+
+TEST(ArenaTest, SwapBetweenArenaAndNonArenaUsingReflection) {
+ TestAllTypes non_arena_message;
+ TestUtil::SetAllFields(&non_arena_message);
+ {
+ Arena arena2;
+ TestAllTypes* arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ TestUtil::SetAllFields(arena2_message);
+ const Reflection* r = arena2_message->GetReflection();
+ r->Swap(&non_arena_message, arena2_message);
+ TestUtil::ExpectAllFieldsSet(*arena2_message);
+ TestUtil::ExpectAllFieldsSet(non_arena_message);
+ }
+}
+
+TEST(ArenaTest, ReleaseFromArenaMessageMakesCopy) {
+ TestAllTypes::NestedMessage* nested_msg = NULL;
+ string* nested_string = NULL;
+ {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->mutable_optional_nested_message()->set_bb(42);
+ *arena_message->mutable_optional_string() = "Hello";
+ nested_msg = arena_message->release_optional_nested_message();
+ nested_string = arena_message->release_optional_string();
+ }
+ EXPECT_EQ(42, nested_msg->bb());
+ EXPECT_EQ("Hello", *nested_string);
+ delete nested_msg;
+ delete nested_string;
+}
+
+#ifndef GOOGLE_PROTOBUF_NO_RTTI
+TEST(ArenaTest, ReleaseFromArenaMessageUsingReflectionMakesCopy) {
+ TestAllTypes::NestedMessage* nested_msg = NULL;
+ // Note: no string: reflection API only supports releasing submessages.
+ {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->mutable_optional_nested_message()->set_bb(42);
+ const Reflection* r = arena_message->GetReflection();
+ const FieldDescriptor* f = arena_message->GetDescriptor()->FindFieldByName(
+ "optional_nested_message");
+ nested_msg = static_cast<TestAllTypes::NestedMessage*>(
+ r->ReleaseMessage(arena_message, f));
+ }
+ EXPECT_EQ(42, nested_msg->bb());
+ delete nested_msg;
+}
+#endif // !GOOGLE_PROTOBUF_NO_RTTI
+
+TEST(ArenaTest, UnsafeArenaReleaseDoesNotMakeCopy) {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ TestAllTypes::NestedMessage* nested_msg = NULL;
+ TestAllTypes::NestedMessage* orig_nested_msg = NULL;
+ string* nested_string = NULL;
+ string* orig_nested_string = NULL;
+ arena_message->mutable_optional_nested_message()->set_bb(42);
+ *arena_message->mutable_optional_string() = "Hello";
+ orig_nested_msg = arena_message->mutable_optional_nested_message();
+ orig_nested_string = arena_message->mutable_optional_string();
+ nested_msg = arena_message->unsafe_arena_release_optional_nested_message();
+ nested_string = arena_message->unsafe_arena_release_optional_string();
+
+ EXPECT_EQ(orig_nested_msg, nested_msg);
+ EXPECT_EQ(orig_nested_string, nested_string);
+ // Released pointers still on arena; no 'delete' calls needed here.
+}
+
+TEST(ArenaTest, SetAllocatedAcrossArenas) {
+ Arena arena1;
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ TestAllTypes::NestedMessage* heap_submessage =
+ new TestAllTypes::NestedMessage();
+ heap_submessage->set_bb(42);
+ arena1_message->set_allocated_optional_nested_message(heap_submessage);
+ // Should keep same object and add to arena's Own()-list.
+ EXPECT_EQ(heap_submessage,
+ arena1_message->mutable_optional_nested_message());
+ {
+ Arena arena2;
+ TestAllTypes::NestedMessage* arena2_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena2);
+ arena2_submessage->set_bb(42);
+ arena1_message->set_allocated_optional_nested_message(arena2_submessage);
+ EXPECT_NE(arena2_submessage,
+ arena1_message->mutable_optional_nested_message());
+ }
+
+ TestAllTypes::NestedMessage* arena1_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena1);
+ arena1_submessage->set_bb(42);
+ TestAllTypes* heap_message = new TestAllTypes;
+ heap_message->set_allocated_optional_nested_message(arena1_submessage);
+ EXPECT_NE(arena1_submessage,
+ heap_message->mutable_optional_nested_message());
+ delete heap_message;
+}
+
+TEST(ArenaTest, SetAllocatedAcrossArenasWithReflection) {
+ // Same as above, with reflection.
+ Arena arena1;
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ const Reflection* r = arena1_message->GetReflection();
+ const Descriptor* d = arena1_message->GetDescriptor();
+ const FieldDescriptor* msg_field = d->FindFieldByName(
+ "optional_nested_message");
+ TestAllTypes::NestedMessage* heap_submessage =
+ new TestAllTypes::NestedMessage();
+ heap_submessage->set_bb(42);
+ r->SetAllocatedMessage(arena1_message, heap_submessage, msg_field);
+ // Should keep same object and add to arena's Own()-list.
+ EXPECT_EQ(heap_submessage,
+ arena1_message->mutable_optional_nested_message());
+ {
+ Arena arena2;
+ TestAllTypes::NestedMessage* arena2_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena2);
+ arena2_submessage->set_bb(42);
+ r->SetAllocatedMessage(arena1_message, arena2_submessage, msg_field);
+ EXPECT_NE(arena2_submessage,
+ arena1_message->mutable_optional_nested_message());
+ }
+
+ TestAllTypes::NestedMessage* arena1_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena1);
+ arena1_submessage->set_bb(42);
+ TestAllTypes* heap_message = new TestAllTypes;
+ r->SetAllocatedMessage(heap_message, arena1_submessage, msg_field);
+ EXPECT_NE(arena1_submessage,
+ heap_message->mutable_optional_nested_message());
+ delete heap_message;
+}
+
+TEST(ArenaTest, AddAllocatedWithReflection) {
+ Arena arena1;
+ ArenaMessage* arena1_message = Arena::CreateMessage<ArenaMessage>(&arena1);
+ const Reflection* r = arena1_message->GetReflection();
+ const Descriptor* d = arena1_message->GetDescriptor();
+ const FieldDescriptor* fd =
+ d->FindFieldByName("repeated_import_no_arena_message");
+ // Message with cc_enable_arenas = false;
+ r->AddMessage(arena1_message, fd);
+ r->AddMessage(arena1_message, fd);
+ r->AddMessage(arena1_message, fd);
+ EXPECT_EQ(3, r->FieldSize(*arena1_message, fd));
+ // Message with cc_enable_arenas = true;
+ fd = d->FindFieldByName("repeated_nested_message");
+ r->AddMessage(arena1_message, fd);
+ r->AddMessage(arena1_message, fd);
+ r->AddMessage(arena1_message, fd);
+ EXPECT_EQ(3, r->FieldSize(*arena1_message, fd));
+}
+
+TEST(ArenaTest, RepeatedPtrFieldAddClearedTest) {
+ {
+ RepeatedPtrField<TestAllTypes> repeated_field;
+ EXPECT_TRUE(repeated_field.empty());
+ EXPECT_EQ(0, repeated_field.size());
+ // Ownership is passed to repeated_field.
+ TestAllTypes* cleared = new TestAllTypes();
+ repeated_field.AddCleared(cleared);
+ EXPECT_TRUE(repeated_field.empty());
+ EXPECT_EQ(0, repeated_field.size());
+ }
+ {
+ RepeatedPtrField<TestAllTypes> repeated_field;
+ EXPECT_TRUE(repeated_field.empty());
+ EXPECT_EQ(0, repeated_field.size());
+ // Ownership is passed to repeated_field.
+ TestAllTypes* cleared = new TestAllTypes();
+ repeated_field.AddAllocated(cleared);
+ EXPECT_FALSE(repeated_field.empty());
+ EXPECT_EQ(1, repeated_field.size());
+ }
+}
+
+TEST(ArenaTest, AddAllocatedToRepeatedField) {
+ // Heap->arena case.
+ Arena arena1;
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ for (int i = 0; i < 10; i++) {
+ TestAllTypes::NestedMessage* heap_submessage =
+ new TestAllTypes::NestedMessage();
+ heap_submessage->set_bb(42);
+ arena1_message->mutable_repeated_nested_message()->
+ AddAllocated(heap_submessage);
+ // Should not copy object -- will use arena_->Own().
+ EXPECT_EQ(heap_submessage,
+ &arena1_message->repeated_nested_message(i));
+ EXPECT_EQ(42, arena1_message->repeated_nested_message(i).bb());
+ }
+
+ // Arena1->Arena2 case.
+ arena1_message->Clear();
+ for (int i = 0; i < 10; i++) {
+ Arena arena2;
+ TestAllTypes::NestedMessage* arena2_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena2);
+ arena2_submessage->set_bb(42);
+ arena1_message->mutable_repeated_nested_message()->
+ AddAllocated(arena2_submessage);
+ // Should copy object.
+ EXPECT_NE(arena2_submessage,
+ &arena1_message->repeated_nested_message(i));
+ EXPECT_EQ(42, arena1_message->repeated_nested_message(i).bb());
+ }
+
+ // Arena->heap case.
+ TestAllTypes* heap_message = new TestAllTypes();
+ for (int i = 0; i < 10; i++) {
+ Arena arena2;
+ TestAllTypes::NestedMessage* arena2_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena2);
+ arena2_submessage->set_bb(42);
+ heap_message->mutable_repeated_nested_message()->
+ AddAllocated(arena2_submessage);
+ // Should copy object.
+ EXPECT_NE(arena2_submessage,
+ &heap_message->repeated_nested_message(i));
+ EXPECT_EQ(42, heap_message->repeated_nested_message(i).bb());
+ }
+ delete heap_message;
+
+ // Heap-arena case for strings (which are not arena-allocated).
+ arena1_message->Clear();
+ for (int i = 0; i < 10; i++) {
+ string* s = new string("Test");
+ arena1_message->mutable_repeated_string()->
+ AddAllocated(s);
+ // Should not copy.
+ EXPECT_EQ(s, &arena1_message->repeated_string(i));
+ EXPECT_EQ("Test", arena1_message->repeated_string(i));
+ }
+}
+
+TEST(ArenaTest, AddAllocatedToRepeatedFieldViaReflection) {
+ // Heap->arena case.
+ Arena arena1;
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ const Reflection* r = arena1_message->GetReflection();
+ const Descriptor* d = arena1_message->GetDescriptor();
+ const FieldDescriptor* fd =
+ d->FindFieldByName("repeated_nested_message");
+ for (int i = 0; i < 10; i++) {
+ TestAllTypes::NestedMessage* heap_submessage =
+ new TestAllTypes::NestedMessage;
+ heap_submessage->set_bb(42);
+ r->AddAllocatedMessage(arena1_message, fd, heap_submessage);
+ // Should not copy object -- will use arena_->Own().
+ EXPECT_EQ(heap_submessage,
+ &arena1_message->repeated_nested_message(i));
+ EXPECT_EQ(42, arena1_message->repeated_nested_message(i).bb());
+ }
+
+ // Arena1->Arena2 case.
+ arena1_message->Clear();
+ for (int i = 0; i < 10; i++) {
+ Arena arena2;
+ TestAllTypes::NestedMessage* arena2_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena2);
+ arena2_submessage->set_bb(42);
+ r->AddAllocatedMessage(arena1_message, fd, arena2_submessage);
+ // Should copy object.
+ EXPECT_NE(arena2_submessage,
+ &arena1_message->repeated_nested_message(i));
+ EXPECT_EQ(42, arena1_message->repeated_nested_message(i).bb());
+ }
+
+ // Arena->heap case.
+ TestAllTypes* heap_message = new TestAllTypes;
+ for (int i = 0; i < 10; i++) {
+ Arena arena2;
+ TestAllTypes::NestedMessage* arena2_submessage =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena2);
+ arena2_submessage->set_bb(42);
+ r->AddAllocatedMessage(heap_message, fd, arena2_submessage);
+ // Should copy object.
+ EXPECT_NE(arena2_submessage,
+ &heap_message->repeated_nested_message(i));
+ EXPECT_EQ(42, heap_message->repeated_nested_message(i).bb());
+ }
+ delete heap_message;
+}
+
+TEST(ArenaTest, ReleaseLastRepeatedField) {
+ // Release from arena-allocated repeated field and ensure that returned object
+ // is heap-allocated.
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ for (int i = 0; i < 10; i++) {
+ TestAllTypes::NestedMessage* nested =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena);
+ nested->set_bb(42);
+ arena_message->mutable_repeated_nested_message()->AddAllocated(nested);
+ }
+
+ for (int i = 0; i < 10; i++) {
+ const TestAllTypes::NestedMessage *orig_submessage =
+ &arena_message->repeated_nested_message(10 - 1 - i); // last element
+ TestAllTypes::NestedMessage *released =
+ arena_message->mutable_repeated_nested_message()->ReleaseLast();
+ EXPECT_NE(released, orig_submessage);
+ EXPECT_EQ(42, released->bb());
+ delete released;
+ }
+
+ // Test UnsafeArenaReleaseLast().
+ for (int i = 0; i < 10; i++) {
+ TestAllTypes::NestedMessage* nested =
+ Arena::CreateMessage<TestAllTypes::NestedMessage>(&arena);
+ nested->set_bb(42);
+ arena_message->mutable_repeated_nested_message()->AddAllocated(nested);
+ }
+
+ for (int i = 0; i < 10; i++) {
+ const TestAllTypes::NestedMessage *orig_submessage =
+ &arena_message->repeated_nested_message(10 - 1 - i); // last element
+ TestAllTypes::NestedMessage *released =
+ arena_message->mutable_repeated_nested_message()->
+ UnsafeArenaReleaseLast();
+ EXPECT_EQ(released, orig_submessage);
+ EXPECT_EQ(42, released->bb());
+ // no delete -- |released| is on the arena.
+ }
+
+ // Test string case as well. ReleaseLast() in this case must copy the string,
+ // even though it was originally heap-allocated and its pointer was simply
+ // appended to the repeated field's internal vector, because the string was
+ // placed on the arena's destructor list and cannot be removed from that list
+ // (so the arena permanently owns the original instance).
+ arena_message->Clear();
+ for (int i = 0; i < 10; i++) {
+ string* s = new string("Test");
+ arena_message->mutable_repeated_string()->AddAllocated(s);
+ }
+ for (int i = 0; i < 10; i++) {
+ const string* orig_element = &arena_message->repeated_string(10 - 1 - i);
+ string* released = arena_message->mutable_repeated_string()->ReleaseLast();
+ EXPECT_NE(released, orig_element);
+ EXPECT_EQ("Test", *released);
+ delete released;
+ }
+}
+
+TEST(ArenaTest, UnsafeArenaReleaseAdd) {
+ // Use unsafe_arena_release() and unsafe_arena_set_allocated() to transfer an
+ // arena-allocated string from one message to another.
+ Arena arena;
+ TestAllTypes* message1 = Arena::CreateMessage<TestAllTypes>(&arena);
+ TestAllTypes* message2 = Arena::CreateMessage<TestAllTypes>(&arena);
+ string* arena_string = Arena::Create<string>(&arena);
+ *arena_string = "Test content";
+
+ message1->unsafe_arena_set_allocated_optional_string(arena_string);
+ EXPECT_EQ(arena_string, message1->mutable_optional_string());
+ message2->unsafe_arena_set_allocated_optional_string(
+ message1->unsafe_arena_release_optional_string());
+ EXPECT_EQ(arena_string, message2->mutable_optional_string());
+}
+
+TEST(ArenaTest, UnsafeArenaAddAllocated) {
+ Arena arena;
+ TestAllTypes* message = Arena::CreateMessage<TestAllTypes>(&arena);
+ for (int i = 0; i < 10; i++) {
+ string* arena_string = Arena::Create<string>(&arena);
+ message->mutable_repeated_string()->UnsafeArenaAddAllocated(arena_string);
+ EXPECT_EQ(arena_string, message->mutable_repeated_string(i));
+ }
+}
+
+TEST(ArenaTest, UnsafeArenaRelease) {
+ Arena arena;
+ TestAllTypes* message = Arena::CreateMessage<TestAllTypes>(&arena);
+
+ string* s = new string("test string");
+ message->unsafe_arena_set_allocated_optional_string(s);
+ EXPECT_TRUE(message->has_optional_string());
+ EXPECT_EQ("test string", message->optional_string());
+ s = message->unsafe_arena_release_optional_string();
+ EXPECT_FALSE(message->has_optional_string());
+ delete s;
+
+ s = new string("test string");
+ message->unsafe_arena_set_allocated_oneof_string(s);
+ EXPECT_TRUE(message->has_oneof_string());
+ EXPECT_EQ("test string", message->oneof_string());
+ s = message->unsafe_arena_release_oneof_string();
+ EXPECT_FALSE(message->has_oneof_string());
+ delete s;
+}
+
+TEST(ArenaTest, ArenaOneofReflection) {
+ Arena arena;
+ TestAllTypes* message = Arena::CreateMessage<TestAllTypes>(&arena);
+ const Descriptor* desc = message->GetDescriptor();
+ const Reflection* refl = message->GetReflection();
+
+ const FieldDescriptor* string_field = desc->FindFieldByName(
+ "oneof_string");
+ const FieldDescriptor* msg_field = desc->FindFieldByName(
+ "oneof_nested_message");
+ const OneofDescriptor* oneof = desc->FindOneofByName(
+ "oneof_field");
+
+ refl->SetString(message, string_field, "Test value");
+ EXPECT_TRUE(refl->HasOneof(*message, oneof));
+ refl->ClearOneof(message, oneof);
+ EXPECT_FALSE(refl->HasOneof(*message, oneof));
+
+ Message* submsg = refl->MutableMessage(message, msg_field);
+ EXPECT_TRUE(refl->HasOneof(*message, oneof));
+ refl->ClearOneof(message, oneof);
+ EXPECT_FALSE(refl->HasOneof(*message, oneof));
+ refl->MutableMessage(message, msg_field);
+ EXPECT_TRUE(refl->HasOneof(*message, oneof));
+ submsg = refl->ReleaseMessage(message, msg_field);
+ EXPECT_FALSE(refl->HasOneof(*message, oneof));
+ EXPECT_TRUE(submsg->GetArena() == NULL);
+ delete submsg;
+}
+
+namespace {
+void TestSwapRepeatedField(Arena* arena1, Arena* arena2) {
+ // Test "safe" (copying) semantics for direct Swap() on RepeatedPtrField
+ // between arenas.
+ RepeatedPtrField<TestAllTypes> field1(arena1);
+ RepeatedPtrField<TestAllTypes> field2(arena2);
+ for (int i = 0; i < 10; i++) {
+ TestAllTypes* t = Arena::CreateMessage<TestAllTypes>(arena1);
+ t->set_optional_string("field1");
+ t->set_optional_int32(i);
+ if (arena1 != NULL) {
+ field1.UnsafeArenaAddAllocated(t);
+ } else {
+ field1.AddAllocated(t);
+ }
+ }
+ for (int i = 0; i < 5; i++) {
+ TestAllTypes* t = Arena::CreateMessage<TestAllTypes>(arena2);
+ t->set_optional_string("field2");
+ t->set_optional_int32(i);
+ if (arena2 != NULL) {
+ field2.UnsafeArenaAddAllocated(t);
+ } else {
+ field2.AddAllocated(t);
+ }
+ }
+ field1.Swap(&field2);
+ EXPECT_EQ(5, field1.size());
+ EXPECT_EQ(10, field2.size());
+ EXPECT_TRUE(string("field1") == field2.Get(0).optional_string());
+ EXPECT_TRUE(string("field2") == field1.Get(0).optional_string());
+ // Ensure that fields retained their original order:
+ for (int i = 0; i < field1.size(); i++) {
+ EXPECT_EQ(i, field1.Get(i).optional_int32());
+ }
+ for (int i = 0; i < field2.size(); i++) {
+ EXPECT_EQ(i, field2.Get(i).optional_int32());
+ }
+}
+} // namespace
+
+TEST(ArenaTest, SwapRepeatedField) {
+ Arena arena;
+ TestSwapRepeatedField(&arena, &arena);
+}
+
+TEST(ArenaTest, SwapRepeatedFieldWithDifferentArenas) {
+ Arena arena1;
+ Arena arena2;
+ TestSwapRepeatedField(&arena1, &arena2);
+}
+
+TEST(ArenaTest, SwapRepeatedFieldWithNoArenaOnRightHandSide) {
+ Arena arena;
+ TestSwapRepeatedField(&arena, NULL);
+}
+
+TEST(ArenaTest, SwapRepeatedFieldWithNoArenaOnLeftHandSide) {
+ Arena arena;
+ TestSwapRepeatedField(NULL, &arena);
+}
+
+TEST(ArenaTest, ExtensionsOnArena) {
+ Arena arena;
+ // Ensure no leaks.
+ TestAllExtensions* message_ext =
+ Arena::CreateMessage<TestAllExtensions>(&arena);
+ message_ext->SetExtension(
+ protobuf_unittest::optional_int32_extension, 42);
+ message_ext->SetExtension(
+ protobuf_unittest::optional_string_extension, string("test"));
+ message_ext->MutableExtension(
+ protobuf_unittest::optional_nested_message_extension)->set_bb(42);
+}
+
+TEST(ArenaTest, RepeatedFieldOnArena) {
+ // Preallocate an initial arena block to avoid mallocs during hooked region.
+ std::vector<char> arena_block(1024 * 1024);
+ ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena(options);
+
+ {
+ internal::NoHeapChecker no_heap;
+
+ // Fill some repeated fields on the arena to test for leaks. Also verify no
+ // memory allocations.
+ RepeatedField<int32> repeated_int32(&arena);
+ RepeatedPtrField<TestAllTypes> repeated_message(&arena);
+ for (int i = 0; i < 100; i++) {
+ repeated_int32.Add(42);
+ repeated_message.Add()->set_optional_int32(42);
+ EXPECT_EQ(&arena, repeated_message.Get(0).GetArena());
+ const TestAllTypes* msg_in_repeated_field = &repeated_message.Get(0);
+ TestAllTypes* msg = repeated_message.UnsafeArenaReleaseLast();
+ EXPECT_EQ(msg_in_repeated_field, msg);
+ }
+
+ // UnsafeArenaExtractSubrange (i) should not leak and (ii) should return
+ // on-arena pointers.
+ for (int i = 0; i < 10; i++) {
+ repeated_message.Add()->set_optional_int32(42);
+ }
+ TestAllTypes* extracted_messages[5];
+ repeated_message.UnsafeArenaExtractSubrange(0, 5, extracted_messages);
+ EXPECT_EQ(&arena, repeated_message.Get(0).GetArena());
+ EXPECT_EQ(5, repeated_message.size());
+ }
+
+ // Now, outside the scope of the NoHeapChecker, test ExtractSubrange's copying
+ // semantics.
+ {
+ RepeatedPtrField<TestAllTypes> repeated_message(&arena);
+ for (int i = 0; i < 100; i++) {
+ repeated_message.Add()->set_optional_int32(42);
+ }
+
+ TestAllTypes* extracted_messages[5];
+ // ExtractSubrange should copy to the heap.
+ repeated_message.ExtractSubrange(0, 5, extracted_messages);
+ EXPECT_EQ(NULL, extracted_messages[0]->GetArena());
+ // We need to free the heap-allocated messages to prevent a leak.
+ for (int i = 0; i < 5; i++) {
+ delete extracted_messages[i];
+ extracted_messages[i] = NULL;
+ }
+ }
+
+ // Now check that we can create RepeatedFields/RepeatedPtrFields themselves on
+ // the arena. They have the necessary type traits so that they can behave like
+ // messages in this way. This is useful for higher-level generic templated
+ // code that may allocate messages or repeated fields of messages on an arena.
+ {
+ RepeatedPtrField<TestAllTypes>* repeated_ptr_on_arena =
+ Arena::CreateMessage< RepeatedPtrField<TestAllTypes> >(&arena);
+ for (int i = 0; i < 10; i++) {
+ // Add some elements and let the leak-checker ensure that everything is
+ // freed.
+ repeated_ptr_on_arena->Add();
+ }
+
+ RepeatedField<int>* repeated_int_on_arena =
+ Arena::CreateMessage< RepeatedField<int> >(&arena);
+ for (int i = 0; i < 100; i++) {
+ repeated_int_on_arena->Add(i);
+ }
+
+ }
+
+ arena.Reset();
+}
+
+
+#ifndef GOOGLE_PROTOBUF_NO_RTTI
+TEST(ArenaTest, MutableMessageReflection) {
+ Arena arena;
+ TestAllTypes* message = Arena::CreateMessage<TestAllTypes>(&arena);
+ const Reflection* r = message->GetReflection();
+ const Descriptor* d = message->GetDescriptor();
+ const FieldDescriptor* field = d->FindFieldByName("optional_nested_message");
+ TestAllTypes::NestedMessage* submessage =
+ static_cast<TestAllTypes::NestedMessage*>(
+ r->MutableMessage(message, field));
+ TestAllTypes::NestedMessage* submessage_expected =
+ message->mutable_optional_nested_message();
+
+ EXPECT_EQ(submessage_expected, submessage);
+ EXPECT_EQ(&arena, submessage->GetArena());
+
+ const FieldDescriptor* oneof_field = d->FindFieldByName("oneof_nested_message");
+ submessage = static_cast<TestAllTypes::NestedMessage*>(
+ r->MutableMessage(message, oneof_field));
+ submessage_expected = message->mutable_oneof_nested_message();
+
+ EXPECT_EQ(submessage_expected, submessage);
+ EXPECT_EQ(&arena, submessage->GetArena());
+}
+#endif // !GOOGLE_PROTOBUF_NO_RTTI
+
+
+namespace {
+
+void FillArenaAwareFields(TestAllTypes* message) {
+ string test_string = "hello world";
+ message->set_optional_int32(42);
+ message->set_optional_string(test_string);
+ message->set_optional_bytes(test_string);
+ message->mutable_optional_nested_message()->set_bb(42);
+
+ message->set_oneof_uint32(42);
+ message->mutable_oneof_nested_message()->set_bb(42);
+ message->set_oneof_string(test_string);
+ message->set_oneof_bytes(test_string);
+
+ message->add_repeated_int32(42);
+ // No repeated string: not yet arena-aware.
+ message->add_repeated_nested_message()->set_bb(42);
+ message->mutable_optional_lazy_message()->set_bb(42);
+}
+
+}
+
+// Test: no allocations occur on heap while touching all supported field types.
+TEST(ArenaTest, NoHeapAllocationsTest) {
+ // Allocate a large initial block to avoid mallocs during hooked test.
+ std::vector<char> arena_block(128 * 1024);
+ ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena(options);
+
+ {
+
+ TestAllTypes* message = Arena::CreateMessage<TestAllTypes>(&arena);
+ FillArenaAwareFields(message);
+ }
+
+ arena.Reset();
+}
+
+#ifndef GOOGLE_PROTOBUF_NO_RTTI
+// Test construction on an arena via generic MessageLite interface. We should be
+// able to successfully deserialize on the arena without incurring heap
+// allocations, i.e., everything should still be arena-allocation-aware.
+TEST(ArenaTest, MessageLiteOnArena) {
+ std::vector<char> arena_block(128 * 1024);
+ ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena(options);
+ const google::protobuf::MessageLite* prototype = &TestAllTypes::default_instance();
+
+ TestAllTypes initial_message;
+ FillArenaAwareFields(&initial_message);
+ string serialized;
+ initial_message.SerializeToString(&serialized);
+
+ {
+
+ google::protobuf::MessageLite* generic_message = prototype->New(&arena);
+ EXPECT_TRUE(generic_message != NULL);
+ EXPECT_EQ(&arena, generic_message->GetArena());
+ EXPECT_TRUE(generic_message->ParseFromString(serialized));
+ TestAllTypes* deserialized = static_cast<TestAllTypes*>(generic_message);
+ EXPECT_EQ(42, deserialized->optional_int32());
+ }
+
+ arena.Reset();
+}
+#endif // !GOOGLE_PROTOBUF_NO_RTTI
+
+
+// RepeatedField should support non-POD types, and invoke constructors and
+// destructors appropriately, because it's used this way by lots of other code
+// (even if this was not its original intent).
+TEST(ArenaTest, RepeatedFieldWithNonPODType) {
+ {
+ RepeatedField<string> field_on_heap;
+ for (int i = 0; i < 100; i++) {
+ *field_on_heap.Add() = "test string long enough to exceed inline buffer";
+ }
+ }
+ {
+ Arena arena;
+ RepeatedField<string> field_on_arena(&arena);
+ for (int i = 0; i < 100; i++) {
+ *field_on_arena.Add() = "test string long enough to exceed inline buffer";
+ }
+ }
+}
+
+// Align n to next multiple of 8
+namespace {
+uint64 Align8(uint64 n) { return (n + 7) & -8; }
+} // namespace
+
+TEST(ArenaTest, SpaceAllocated_and_Used) {
+ ArenaOptions options;
+ options.start_block_size = 256;
+ options.max_block_size = 8192;
+ Arena arena_1(options);
+ EXPECT_EQ(0, arena_1.SpaceAllocated());
+ EXPECT_EQ(0, arena_1.SpaceUsed());
+ EXPECT_EQ(0, arena_1.Reset());
+ ::google::protobuf::Arena::CreateArray<char>(&arena_1, 320);
+ // Arena will allocate slightly more than 320 for the block headers.
+ EXPECT_LE(320, arena_1.SpaceAllocated());
+ EXPECT_EQ(Align8(320), arena_1.SpaceUsed());
+ EXPECT_LE(320, arena_1.Reset());
+
+ // Test with initial block.
+ std::vector<char> arena_block(1024);
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena_2(options);
+ EXPECT_EQ(1024, arena_2.SpaceAllocated());
+ EXPECT_EQ(0, arena_2.SpaceUsed());
+ EXPECT_EQ(1024, arena_2.Reset());
+ ::google::protobuf::Arena::CreateArray<char>(&arena_2, 55);
+ EXPECT_EQ(1024, arena_2.SpaceAllocated());
+ EXPECT_EQ(Align8(55), arena_2.SpaceUsed());
+ EXPECT_EQ(1024, arena_2.Reset());
+
+ // Reset options to test doubling policy explicitly.
+ options.initial_block = NULL;
+ options.initial_block_size = 0;
+ Arena arena_3(options);
+ EXPECT_EQ(0, arena_3.SpaceUsed());
+ ::google::protobuf::Arena::CreateArray<char>(&arena_3, 190);
+ EXPECT_EQ(256, arena_3.SpaceAllocated());
+ EXPECT_EQ(Align8(190), arena_3.SpaceUsed());
+ ::google::protobuf::Arena::CreateArray<char>(&arena_3, 70);
+ EXPECT_EQ(256 + 512, arena_3.SpaceAllocated());
+ EXPECT_EQ(Align8(190) + Align8(70), arena_3.SpaceUsed());
+ EXPECT_EQ(256 + 512, arena_3.Reset());
+}
+
+TEST(ArenaTest, Alignment) {
+ ::google::protobuf::Arena arena;
+ for (int i = 0; i < 200; i++) {
+ void* p = ::google::protobuf::Arena::CreateArray<char>(&arena, i);
+ GOOGLE_CHECK_EQ(reinterpret_cast<uintptr_t>(p) % 8, 0) << i << ": " << p;
+ }
+}
+
+TEST(ArenaTest, GetArenaShouldReturnTheArenaForArenaAllocatedMessages) {
+ ::google::protobuf::Arena arena;
+ ArenaMessage* message = Arena::CreateMessage<ArenaMessage>(&arena);
+ const ArenaMessage* const_pointer_to_message = message;
+ EXPECT_EQ(&arena, Arena::GetArena(message));
+ EXPECT_EQ(&arena, Arena::GetArena(const_pointer_to_message));
+}
+
+TEST(ArenaTest, GetArenaShouldReturnNullForNonArenaAllocatedMessages) {
+ ArenaMessage message;
+ const ArenaMessage* const_pointer_to_message = &message;
+ EXPECT_EQ(NULL, Arena::GetArena(&message));
+ EXPECT_EQ(NULL, Arena::GetArena(const_pointer_to_message));
+}
+
+TEST(ArenaTest, UnsafeSetAllocatedOnArena) {
+ ::google::protobuf::Arena arena;
+ TestAllTypes* message = Arena::CreateMessage<TestAllTypes>(&arena);
+ EXPECT_FALSE(message->has_optional_string());
+
+ string owned_string = "test with long enough content to heap-allocate";
+ message->unsafe_arena_set_allocated_optional_string(&owned_string);
+ EXPECT_TRUE(message->has_optional_string());
+
+ message->unsafe_arena_set_allocated_optional_string(NULL);
+ EXPECT_FALSE(message->has_optional_string());
+}
+
+// A helper utility class to only contain static hook functions, some
+// counters to be used to verify the counters have been called and a cookie
+// value to be verified.
+class ArenaHooksTestUtil {
+ public:
+ static void* on_init(::google::protobuf::Arena* arena) {
+ ++num_init;
+ int* cookie = new int(kCookieValue);
+ return static_cast<void*>(cookie);
+ }
+
+ static void on_allocation(const std::type_info* /*unused*/, uint64 alloc_size,
+ void* cookie) {
+ ++num_allocations;
+ int cookie_value = *static_cast<int*>(cookie);
+ EXPECT_EQ(kCookieValue, cookie_value);
+ }
+
+ static void on_reset(::google::protobuf::Arena* arena, void* cookie,
+ uint64 space_used) {
+ ++num_reset;
+ int cookie_value = *static_cast<int*>(cookie);
+ EXPECT_EQ(kCookieValue, cookie_value);
+ }
+
+ static void on_destruction(::google::protobuf::Arena* arena, void* cookie,
+ uint64 space_used) {
+ ++num_destruct;
+ int cookie_value = *static_cast<int*>(cookie);
+ EXPECT_EQ(kCookieValue, cookie_value);
+ delete static_cast<int*>(cookie);
+ }
+
+ static const int kCookieValue = 999;
+ static uint32 num_init;
+ static uint32 num_allocations;
+ static uint32 num_reset;
+ static uint32 num_destruct;
+};
+uint32 ArenaHooksTestUtil::num_init = 0;
+uint32 ArenaHooksTestUtil::num_allocations = 0;
+uint32 ArenaHooksTestUtil::num_reset = 0;
+uint32 ArenaHooksTestUtil::num_destruct = 0;
+const int ArenaHooksTestUtil::kCookieValue;
+
+// Test the hooks are correctly called and that the cookie is passed.
+TEST(ArenaTest, ArenaHooksSanity) {
+ ::google::protobuf::ArenaOptions options;
+ options.on_arena_init = ArenaHooksTestUtil::on_init;
+ options.on_arena_allocation = ArenaHooksTestUtil::on_allocation;
+ options.on_arena_reset = ArenaHooksTestUtil::on_reset;
+ options.on_arena_destruction = ArenaHooksTestUtil::on_destruction;
+
+ // Scope for defining the arena
+ {
+ ::google::protobuf::Arena arena(options);
+ EXPECT_EQ(1, ArenaHooksTestUtil::num_init);
+ EXPECT_EQ(0, ArenaHooksTestUtil::num_allocations);
+ ::google::protobuf::Arena::Create<uint64>(&arena);
+ if (google::protobuf::internal::has_trivial_destructor<uint64>::value) {
+ EXPECT_EQ(1, ArenaHooksTestUtil::num_allocations);
+ } else {
+ EXPECT_EQ(2, ArenaHooksTestUtil::num_allocations);
+ }
+ arena.Reset();
+ arena.Reset();
+ EXPECT_EQ(2, ArenaHooksTestUtil::num_reset);
+ }
+ EXPECT_EQ(3, ArenaHooksTestUtil::num_reset);
+ EXPECT_EQ(1, ArenaHooksTestUtil::num_destruct);
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arenastring.cc b/third_party/protobuf/3.0.0/src/google/protobuf/arenastring.cc
new file mode 100644
index 0000000000..cce61d74de
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arenastring.cc
@@ -0,0 +1,53 @@
+// 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.
+
+// The ArenaString implementation is not included in the open-source release. Do
+// not include this file in the distribution.
+
+#include <google/protobuf/arenastring.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+
+void ArenaStringPtr::AssignWithDefault(const ::std::string* default_value,
+ ArenaStringPtr value) {
+ const ::std::string* me = *UnsafeRawStringPointer();
+ const ::std::string* other = *value.UnsafeRawStringPointer();
+ // If the pointers are the same then do nothing.
+ if (me != other) {
+ SetNoArena(default_value, value.GetNoArena(default_value));
+ }
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arenastring.h b/third_party/protobuf/3.0.0/src/google/protobuf/arenastring.h
new file mode 100755
index 0000000000..590ffce9ac
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arenastring.h
@@ -0,0 +1,314 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_ARENASTRING_H__
+#define GOOGLE_PROTOBUF_ARENASTRING_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/fastmem.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/generated_message_util.h>
+
+
+
+// This is the implementation of arena string fields written for the open-source
+// release. The ArenaStringPtr struct below is an internal implementation class
+// and *should not be used* by user code. It is used to collect string
+// operations together into one place and abstract away the underlying
+// string-field pointer representation, so that (for example) an alternate
+// implementation that knew more about ::std::string's internals could integrate more
+// closely with the arena allocator.
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+struct LIBPROTOBUF_EXPORT ArenaStringPtr {
+ inline void Set(const ::std::string* default_value,
+ const ::std::string& value, ::google::protobuf::Arena* arena) {
+ if (ptr_ == default_value) {
+ CreateInstance(arena, &value);
+ } else {
+ *ptr_ = value;
+ }
+ }
+
+ // Basic accessors.
+ inline const ::std::string& Get(const ::std::string* /* default_value */) const {
+ return *ptr_;
+ }
+
+ inline ::std::string* Mutable(const ::std::string* default_value,
+ ::google::protobuf::Arena* arena) {
+ if (ptr_ == default_value) {
+ CreateInstance(arena, default_value);
+ }
+ return ptr_;
+ }
+
+ // Release returns a ::std::string* instance that is heap-allocated and is not
+ // Own()'d by any arena. If the field was not set, it returns NULL. The caller
+ // retains ownership. Clears this field back to NULL state. Used to implement
+ // release_<field>() methods on generated classes.
+ inline ::std::string* Release(const ::std::string* default_value,
+ ::google::protobuf::Arena* arena) {
+ if (ptr_ == default_value) {
+ return NULL;
+ }
+ ::std::string* released = NULL;
+ if (arena != NULL) {
+ // ptr_ is owned by the arena -- we need to return a copy.
+ released = new ::std::string(*ptr_);
+ } else {
+ released = ptr_;
+ }
+ ptr_ = const_cast< ::std::string* >(default_value);
+ return released;
+ }
+
+ // UnsafeArenaRelease returns a ::std::string*, but it may be arena-owned (i.e.
+ // have its destructor already registered) if arena != NULL. If the field was
+ // not set, this returns NULL. This method clears this field back to NULL
+ // state. Used to implement unsafe_arena_release_<field>() methods on
+ // generated classes.
+ inline ::std::string* UnsafeArenaRelease(const ::std::string* default_value,
+ ::google::protobuf::Arena* /* arena */) {
+ if (ptr_ == default_value) {
+ return NULL;
+ }
+ ::std::string* released = ptr_;
+ ptr_ = const_cast< ::std::string* >(default_value);
+ return released;
+ }
+
+ // Takes a string that is heap-allocated, and takes ownership. The string's
+ // destructor is registered with the arena. Used to implement
+ // set_allocated_<field> in generated classes.
+ inline void SetAllocated(const ::std::string* default_value,
+ ::std::string* value, ::google::protobuf::Arena* arena) {
+ if (arena == NULL && ptr_ != default_value) {
+ Destroy(default_value, arena);
+ }
+ if (value != NULL) {
+ ptr_ = value;
+ if (arena != NULL) {
+ arena->Own(value);
+ }
+ } else {
+ ptr_ = const_cast< ::std::string* >(default_value);
+ }
+ }
+
+ // Takes a string that has lifetime equal to the arena's lifetime. The arena
+ // must be non-null. It is safe only to pass this method a value returned by
+ // UnsafeArenaRelease() on another field of a message in the same arena. Used
+ // to implement unsafe_arena_set_allocated_<field> in generated classes.
+ inline void UnsafeArenaSetAllocated(const ::std::string* default_value,
+ ::std::string* value,
+ ::google::protobuf::Arena* /* arena */) {
+ if (value != NULL) {
+ ptr_ = value;
+ } else {
+ ptr_ = const_cast< ::std::string* >(default_value);
+ }
+ }
+
+ // Swaps internal pointers. Arena-safety semantics: this is guarded by the
+ // logic in Swap()/UnsafeArenaSwap() at the message level, so this method is
+ // 'unsafe' if called directly.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE void Swap(ArenaStringPtr* other) {
+ std::swap(ptr_, other->ptr_);
+ }
+
+ // Frees storage (if not on an arena) and sets field to default value.
+ inline void Destroy(const ::std::string* default_value,
+ ::google::protobuf::Arena* arena) {
+ if (arena == NULL && ptr_ != default_value) {
+ delete ptr_;
+ }
+ ptr_ = const_cast< ::std::string* >(default_value);
+ }
+
+ // Clears content, but keeps allocated string if arena != NULL, to avoid the
+ // overhead of heap operations. After this returns, the content (as seen by
+ // the user) will always be the empty string. Assumes that |default_value|
+ // is an empty string.
+ inline void ClearToEmpty(const ::std::string* default_value,
+ ::google::protobuf::Arena* /* arena */) {
+ if (ptr_ == default_value) {
+ // Already set to default (which is empty) -- do nothing.
+ } else {
+ ptr_->clear();
+ }
+ }
+
+ // Clears content, but keeps allocated string if arena != NULL, to avoid the
+ // overhead of heap operations. After this returns, the content (as seen by
+ // the user) will always be equal to |default_value|.
+ inline void ClearToDefault(const ::std::string* default_value,
+ ::google::protobuf::Arena* /* arena */) {
+ if (ptr_ == default_value) {
+ // Already set to default -- do nothing.
+ } else {
+ // Have another allocated string -- rather than throwing this away and
+ // resetting ptr_ to the canonical default string instance, we just reuse
+ // this instance.
+ *ptr_ = *default_value;
+ }
+ }
+
+ // Called from generated code / reflection runtime only. Resets value to point
+ // to a default string pointer, with the semantics that this ArenaStringPtr
+ // does not own the pointed-to memory. Disregards initial value of ptr_ (so
+ // this is the *ONLY* safe method to call after construction or when
+ // reinitializing after becoming the active field in a oneof union).
+ inline void UnsafeSetDefault(const ::std::string* default_value) {
+ // Casting away 'const' is safe here: accessors ensure that ptr_ is only
+ // returned as a const if it is equal to default_value.
+ ptr_ = const_cast< ::std::string* >(default_value);
+ }
+
+ // The 'NoArena' variants of methods below assume arena == NULL and are
+ // optimized to provide very little overhead relative to a raw string pointer
+ // (while still being in-memory compatible with other code that assumes
+ // ArenaStringPtr). Note the invariant that a class instance that has only
+ // ever been mutated by NoArena methods must *only* be in the String state
+ // (i.e., tag bits are not used), *NEVER* ArenaString. This allows all
+ // tagged-pointer manipulations to be avoided.
+ inline void SetNoArena(const ::std::string* default_value,
+ const ::std::string& value) {
+ if (ptr_ == default_value) {
+ CreateInstanceNoArena(&value);
+ } else {
+ *ptr_ = value;
+ }
+ }
+
+ void AssignWithDefault(const ::std::string* default_value, ArenaStringPtr value);
+
+ inline const ::std::string& GetNoArena(const ::std::string* /* default_value */) const {
+ return *ptr_;
+ }
+
+ inline ::std::string* MutableNoArena(const ::std::string* default_value) {
+ if (ptr_ == default_value) {
+ CreateInstanceNoArena(default_value);
+ }
+ return ptr_;
+ }
+
+ inline ::std::string* ReleaseNoArena(const ::std::string* default_value) {
+ if (ptr_ == default_value) {
+ return NULL;
+ } else {
+ ::std::string* released = ptr_;
+ ptr_ = const_cast< ::std::string* >(default_value);
+ return released;
+ }
+ }
+
+ inline void SetAllocatedNoArena(const ::std::string* default_value,
+ ::std::string* value) {
+ if (ptr_ != default_value) {
+ delete ptr_;
+ }
+ if (value != NULL) {
+ ptr_ = value;
+ } else {
+ ptr_ = const_cast< ::std::string* >(default_value);
+ }
+ }
+
+ inline void DestroyNoArena(const ::std::string* default_value) {
+ if (ptr_ != default_value) {
+ delete ptr_;
+ }
+ ptr_ = NULL;
+ }
+
+ inline void ClearToEmptyNoArena(const ::std::string* default_value) {
+ if (ptr_ == default_value) {
+ // Nothing: already equal to default (which is the empty string).
+ } else {
+ ptr_->clear();
+ }
+ }
+
+ inline void ClearToDefaultNoArena(const ::std::string* default_value) {
+ if (ptr_ == default_value) {
+ // Nothing: already set to default.
+ } else {
+ // Reuse existing allocated instance.
+ *ptr_ = *default_value;
+ }
+ }
+
+ // Internal accessor used only at parse time to provide direct access to the
+ // raw pointer from the shared parse routine (in the non-arenas case). The
+ // parse routine does the string allocation in order to save code size in the
+ // generated parsing code.
+ inline ::std::string** UnsafeRawStringPointer() {
+ return &ptr_;
+ }
+
+ private:
+ ::std::string* ptr_;
+
+ GOOGLE_ATTRIBUTE_NOINLINE void CreateInstance(::google::protobuf::Arena* arena,
+ const ::std::string* initial_value) {
+ // Assumes ptr_ is not NULL.
+ if (initial_value != NULL) {
+ ptr_ = new ::std::string(*initial_value);
+ } else {
+ ptr_ = new ::std::string();
+ }
+ if (arena != NULL) {
+ arena->Own(ptr_);
+ }
+ }
+ GOOGLE_ATTRIBUTE_NOINLINE void CreateInstanceNoArena(const ::std::string* initial_value) {
+ if (initial_value != NULL) {
+ ptr_ = new ::std::string(*initial_value);
+ } else {
+ ptr_ = new ::std::string();
+ }
+ }
+};
+
+} // namespace internal
+} // namespace protobuf
+
+
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_ARENASTRING_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/arenastring_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/arenastring_unittest.cc
new file mode 100644
index 0000000000..ea405d7d3e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/arenastring_unittest.cc
@@ -0,0 +1,110 @@
+// 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.
+
+// Based on mvels@'s frankenstring.
+
+#include <google/protobuf/arenastring.h>
+
+#include <string>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <cstdlib>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <gtest/gtest.h>
+
+namespace google {
+using google::protobuf::internal::ArenaString;
+using google::protobuf::internal::ArenaStringPtr;
+
+namespace protobuf {
+
+
+static string WrapString(const char* value) {
+ return value;
+}
+
+// Test ArenaStringPtr with arena == NULL.
+TEST(ArenaStringPtrTest, ArenaStringPtrOnHeap) {
+ ArenaStringPtr field;
+ ::std::string default_value = "default";
+ field.UnsafeSetDefault(&default_value);
+ EXPECT_EQ(string("default"), field.Get(&default_value));
+ field.Set(&default_value, WrapString("Test short"), NULL);
+ EXPECT_EQ(string("Test short"), field.Get(&default_value));
+ field.Set(&default_value, WrapString("Test long long long long value"), NULL);
+ EXPECT_EQ(string("Test long long long long value"), field.Get(&default_value));
+ field.Set(&default_value, string(""), NULL);
+ field.Destroy(&default_value, NULL);
+
+ ArenaStringPtr field2;
+ field2.UnsafeSetDefault(&default_value);
+ ::std::string* mut = field2.Mutable(&default_value, NULL);
+ EXPECT_EQ(mut, field2.Mutable(&default_value, NULL));
+ EXPECT_EQ(mut, &field2.Get(&default_value));
+ EXPECT_NE(&default_value, mut);
+ EXPECT_EQ(string("default"), *mut);
+ *mut = "Test long long long long value"; // ensure string allocates storage
+ EXPECT_EQ(string("Test long long long long value"), field2.Get(&default_value));
+ field2.Destroy(&default_value, NULL);
+}
+
+TEST(ArenaStringPtrTest, ArenaStringPtrOnArena) {
+ google::protobuf::Arena arena;
+ ArenaStringPtr field;
+ ::std::string default_value = "default";
+ field.UnsafeSetDefault(&default_value);
+ EXPECT_EQ(string("default"), field.Get(&default_value));
+ field.Set(&default_value, WrapString("Test short"), &arena);
+ EXPECT_EQ(string("Test short"), field.Get(&default_value));
+ field.Set(&default_value, WrapString("Test long long long long value"), &arena);
+ EXPECT_EQ(string("Test long long long long value"),
+ field.Get(&default_value));
+ field.Set(&default_value, string(""), &arena);
+ field.Destroy(&default_value, &arena);
+
+ ArenaStringPtr field2;
+ field2.UnsafeSetDefault(&default_value);
+ ::std::string* mut = field2.Mutable(&default_value, &arena);
+ EXPECT_EQ(mut, field2.Mutable(&default_value, &arena));
+ EXPECT_EQ(mut, &field2.Get(&default_value));
+ EXPECT_NE(&default_value, mut);
+ EXPECT_EQ(string("default"), *mut);
+ *mut = "Test long long long long value"; // ensure string allocates storage
+ EXPECT_EQ(string("Test long long long long value"),
+ field2.Get(&default_value));
+ field2.Destroy(&default_value, &arena);
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.cc
new file mode 100644
index 0000000000..473eb4e6fb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.cc
@@ -0,0 +1,85 @@
+// 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.
+
+#include <google/protobuf/compiler/code_generator.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+CodeGenerator::~CodeGenerator() {}
+GeneratorContext::~GeneratorContext() {}
+
+io::ZeroCopyOutputStream*
+GeneratorContext::OpenForAppend(const string& filename) {
+ return NULL;
+}
+
+io::ZeroCopyOutputStream* GeneratorContext::OpenForInsert(
+ const string& filename, const string& insertion_point) {
+ GOOGLE_LOG(FATAL) << "This GeneratorContext does not support insertion.";
+ return NULL; // make compiler happy
+}
+
+void GeneratorContext::ListParsedFiles(
+ vector<const FileDescriptor*>* output) {
+ GOOGLE_LOG(FATAL) << "This GeneratorContext does not support ListParsedFiles";
+}
+
+// Parses a set of comma-delimited name/value pairs.
+void ParseGeneratorParameter(const string& text,
+ vector<pair<string, string> >* output) {
+ vector<string> parts = Split(text, ",", true);
+
+ for (int i = 0; i < parts.size(); i++) {
+ string::size_type equals_pos = parts[i].find_first_of('=');
+ pair<string, string> value;
+ if (equals_pos == string::npos) {
+ value.first = parts[i];
+ value.second = "";
+ } else {
+ value.first = parts[i].substr(0, equals_pos);
+ value.second = parts[i].substr(equals_pos + 1);
+ }
+ output->push_back(value);
+ }
+}
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.h
new file mode 100644
index 0000000000..b989f15132
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/code_generator.h
@@ -0,0 +1,176 @@
+// 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.
+//
+// Defines the abstract interface implemented by each of the language-specific
+// code generators.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CODE_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_CODE_GENERATOR_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <string>
+#include <vector>
+#include <utility>
+
+namespace google {
+namespace protobuf {
+
+namespace io { class ZeroCopyOutputStream; }
+class FileDescriptor;
+
+namespace compiler {
+
+// Defined in this file.
+class CodeGenerator;
+class GeneratorContext;
+
+// The abstract interface to a class which generates code implementing a
+// particular proto file in a particular language. A number of these may
+// be registered with CommandLineInterface to support various languages.
+class LIBPROTOC_EXPORT CodeGenerator {
+ public:
+ inline CodeGenerator() {}
+ virtual ~CodeGenerator();
+
+ // Generates code for the given proto file, generating one or more files in
+ // the given output directory.
+ //
+ // A parameter to be passed to the generator can be specified on the
+ // command line. This is intended to be used by Java and similar languages
+ // to specify which specific class from the proto file is to be generated,
+ // though it could have other uses as well. It is empty if no parameter was
+ // given.
+ //
+ // Returns true if successful. Otherwise, sets *error to a description of
+ // the problem (e.g. "invalid parameter") and returns false.
+ virtual bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const = 0;
+
+ // Generates code for all given proto files, generating one or more files in
+ // the given output directory.
+ //
+ // This method should be called instead of |Generate()| when
+ // |HasGenerateAll()| returns |true|. It is used to emulate legacy semantics
+ // when more than one `.proto` file is specified on one compiler invocation.
+ //
+ // WARNING: Please do not use unless legacy semantics force the code generator
+ // to produce a single output file for all input files, or otherwise require
+ // an examination of all input files first. The canonical code generator
+ // design produces one output file per input .proto file, and we do not wish
+ // to encourage alternate designs.
+ //
+ // A parameter is given as passed on the command line, as in |Generate()|
+ // above.
+ //
+ // Returns true if successful. Otherwise, sets *error to a description of
+ // the problem (e.g. "invalid parameter") and returns false.
+ virtual bool GenerateAll(const vector<const FileDescriptor*>& files,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const {
+ *error = "Unimplemented GenerateAll() method.";
+ return false;
+ }
+
+ // Returns true if the code generator expects to receive all FileDescriptors
+ // at once (via |GenerateAll()|), rather than one at a time (via
+ // |Generate()|). This is required to implement legacy semantics.
+ virtual bool HasGenerateAll() const { return false; }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CodeGenerator);
+};
+
+// CodeGenerators generate one or more files in a given directory. This
+// abstract interface represents the directory to which the CodeGenerator is
+// to write and other information about the context in which the Generator
+// runs.
+class LIBPROTOC_EXPORT GeneratorContext {
+ public:
+ inline GeneratorContext() {}
+ virtual ~GeneratorContext();
+
+ // Opens the given file, truncating it if it exists, and returns a
+ // ZeroCopyOutputStream that writes to the file. The caller takes ownership
+ // of the returned object. This method never fails (a dummy stream will be
+ // returned instead).
+ //
+ // The filename given should be relative to the root of the source tree.
+ // E.g. the C++ generator, when generating code for "foo/bar.proto", will
+ // generate the files "foo/bar.pb.h" and "foo/bar.pb.cc"; note that
+ // "foo/" is included in these filenames. The filename is not allowed to
+ // contain "." or ".." components.
+ virtual io::ZeroCopyOutputStream* Open(const string& filename) = 0;
+
+ // Similar to Open() but the output will be appended to the file if exists
+ virtual io::ZeroCopyOutputStream* OpenForAppend(const string& filename);
+
+ // Creates a ZeroCopyOutputStream which will insert code into the given file
+ // at the given insertion point. See plugin.proto (plugin.pb.h) for more
+ // information on insertion points. The default implementation
+ // assert-fails -- it exists only for backwards-compatibility.
+ //
+ // WARNING: This feature is currently EXPERIMENTAL and is subject to change.
+ virtual io::ZeroCopyOutputStream* OpenForInsert(
+ const string& filename, const string& insertion_point);
+
+ // Returns a vector of FileDescriptors for all the files being compiled
+ // in this run. Useful for languages, such as Go, that treat files
+ // differently when compiled as a set rather than individually.
+ virtual void ListParsedFiles(vector<const FileDescriptor*>* output);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(GeneratorContext);
+};
+
+// The type GeneratorContext was once called OutputDirectory. This typedef
+// provides backward compatibility.
+typedef GeneratorContext OutputDirectory;
+
+// Several code generators treat the parameter argument as holding a
+// list of options separated by commas. This helper function parses
+// a set of comma-delimited name/value pairs: e.g.,
+// "foo=bar,baz,qux=corge"
+// parses to the pairs:
+// ("foo", "bar"), ("baz", ""), ("qux", "corge")
+extern void ParseGeneratorParameter(const string&,
+ vector<pair<string, string> >*);
+
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CODE_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.cc
new file mode 100644
index 0000000000..bb781b0a63
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.cc
@@ -0,0 +1,1887 @@
+// 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.
+
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/stubs/platform_macros.h>
+
+#include <stdio.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#ifdef _MSC_VER
+#include <io.h>
+#include <direct.h>
+#else
+#include <unistd.h>
+#endif
+#include <errno.h>
+#include <fstream>
+#include <iostream>
+#include <ctype.h>
+
+#include <limits.h> //For PATH_MAX
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#ifdef __APPLE__
+#include <mach-o/dyld.h>
+#endif
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/compiler/importer.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.pb.h>
+#include <google/protobuf/compiler/subprocess.h>
+#include <google/protobuf/compiler/zip_writer.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+#if defined(_WIN32)
+#define mkdir(name, mode) mkdir(name)
+#ifndef W_OK
+#define W_OK 02 // not defined by MSVC for whatever reason
+#endif
+#ifndef F_OK
+#define F_OK 00 // not defined by MSVC for whatever reason
+#endif
+#ifndef STDIN_FILENO
+#define STDIN_FILENO 0
+#endif
+#ifndef STDOUT_FILENO
+#define STDOUT_FILENO 1
+#endif
+#endif
+
+#ifndef O_BINARY
+#ifdef _O_BINARY
+#define O_BINARY _O_BINARY
+#else
+#define O_BINARY 0 // If this isn't defined, the platform doesn't need it.
+#endif
+#endif
+
+namespace {
+#if defined(_WIN32) && !defined(__CYGWIN__)
+static const char* kPathSeparator = ";";
+#else
+static const char* kPathSeparator = ":";
+#endif
+
+// Returns true if the text looks like a Windows-style absolute path, starting
+// with a drive letter. Example: "C:\foo". TODO(kenton): Share this with
+// copy in importer.cc?
+static bool IsWindowsAbsolutePath(const string& text) {
+#if defined(_WIN32) || defined(__CYGWIN__)
+ return text.size() >= 3 && text[1] == ':' &&
+ isalpha(text[0]) &&
+ (text[2] == '/' || text[2] == '\\') &&
+ text.find_last_of(':') == 1;
+#else
+ return false;
+#endif
+}
+
+void SetFdToTextMode(int fd) {
+#ifdef _WIN32
+ if (_setmode(fd, _O_TEXT) == -1) {
+ // This should never happen, I think.
+ GOOGLE_LOG(WARNING) << "_setmode(" << fd << ", _O_TEXT): " << strerror(errno);
+ }
+#endif
+ // (Text and binary are the same on non-Windows platforms.)
+}
+
+void SetFdToBinaryMode(int fd) {
+#ifdef _WIN32
+ if (_setmode(fd, _O_BINARY) == -1) {
+ // This should never happen, I think.
+ GOOGLE_LOG(WARNING) << "_setmode(" << fd << ", _O_BINARY): " << strerror(errno);
+ }
+#endif
+ // (Text and binary are the same on non-Windows platforms.)
+}
+
+void AddTrailingSlash(string* path) {
+ if (!path->empty() && path->at(path->size() - 1) != '/') {
+ path->push_back('/');
+ }
+}
+
+bool VerifyDirectoryExists(const string& path) {
+ if (path.empty()) return true;
+
+ if (access(path.c_str(), F_OK) == -1) {
+ std::cerr << path << ": " << strerror(errno) << std::endl;
+ return false;
+ } else {
+ return true;
+ }
+}
+
+// Try to create the parent directory of the given file, creating the parent's
+// parent if necessary, and so on. The full file name is actually
+// (prefix + filename), but we assume |prefix| already exists and only create
+// directories listed in |filename|.
+bool TryCreateParentDirectory(const string& prefix, const string& filename) {
+ // Recursively create parent directories to the output file.
+ vector<string> parts = Split(filename, "/", true);
+ string path_so_far = prefix;
+ for (int i = 0; i < parts.size() - 1; i++) {
+ path_so_far += parts[i];
+ if (mkdir(path_so_far.c_str(), 0777) != 0) {
+ if (errno != EEXIST) {
+ std::cerr << filename << ": while trying to create directory "
+ << path_so_far << ": " << strerror(errno) << std::endl;
+ return false;
+ }
+ }
+ path_so_far += '/';
+ }
+
+ return true;
+}
+
+// Get the absolute path of this protoc binary.
+bool GetProtocAbsolutePath(string* path) {
+#ifdef _WIN32
+ char buffer[MAX_PATH];
+ int len = GetModuleFileNameA(NULL, buffer, MAX_PATH);
+#elif __APPLE__
+ char buffer[PATH_MAX];
+ int len = 0;
+
+ char dirtybuffer[PATH_MAX];
+ uint32_t size = sizeof(dirtybuffer);
+ if (_NSGetExecutablePath(dirtybuffer, &size) == 0) {
+ realpath(dirtybuffer, buffer);
+ len = strlen(buffer);
+ }
+#else
+ char buffer[PATH_MAX];
+ int len = readlink("/proc/self/exe", buffer, PATH_MAX);
+#endif
+ if (len > 0) {
+ path->assign(buffer, len);
+ return true;
+ } else {
+ return false;
+ }
+}
+
+// Whether a path is where google/protobuf/descriptor.proto and other well-known
+// type protos are installed.
+bool IsInstalledProtoPath(const string& path) {
+ // Checking the descriptor.proto file should be good enough.
+ string file_path = path + "/google/protobuf/descriptor.proto";
+ return access(file_path.c_str(), F_OK) != -1;
+}
+
+// Add the paths where google/protobuf/descritor.proto and other well-known
+// type protos are installed.
+void AddDefaultProtoPaths(vector<pair<string, string> >* paths) {
+ // TODO(xiaofeng): The code currently only checks relative paths of where
+ // the protoc binary is installed. We probably should make it handle more
+ // cases than that.
+ string path;
+ if (!GetProtocAbsolutePath(&path)) {
+ return;
+ }
+ // Strip the binary name.
+ size_t pos = path.find_last_of("/\\");
+ if (pos == string::npos || pos == 0) {
+ return;
+ }
+ path = path.substr(0, pos);
+ // Check the binary's directory.
+ if (IsInstalledProtoPath(path)) {
+ paths->push_back(pair<string, string>("", path));
+ return;
+ }
+ // Check if there is an include subdirectory.
+ if (IsInstalledProtoPath(path + "/include")) {
+ paths->push_back(pair<string, string>("", path + "/include"));
+ return;
+ }
+ // Check if the upper level directory has an "include" subdirectory.
+ pos = path.find_last_of("/\\");
+ if (pos == string::npos || pos == 0) {
+ return;
+ }
+ path = path.substr(0, pos);
+ if (IsInstalledProtoPath(path + "/include")) {
+ paths->push_back(pair<string, string>("", path + "/include"));
+ return;
+ }
+}
+} // namespace
+
+// A MultiFileErrorCollector that prints errors to stderr.
+class CommandLineInterface::ErrorPrinter : public MultiFileErrorCollector,
+ public io::ErrorCollector {
+ public:
+ ErrorPrinter(ErrorFormat format, DiskSourceTree *tree = NULL)
+ : format_(format), tree_(tree) {}
+ ~ErrorPrinter() {}
+
+ // implements MultiFileErrorCollector ------------------------------
+ void AddError(const string& filename, int line, int column,
+ const string& message) {
+ AddErrorOrWarning(filename, line, column, message, "error", std::cerr);
+ }
+
+ void AddWarning(const string& filename, int line, int column,
+ const string& message) {
+ AddErrorOrWarning(filename, line, column, message, "warning", std::clog);
+ }
+
+ // implements io::ErrorCollector -----------------------------------
+ void AddError(int line, int column, const string& message) {
+ AddError("input", line, column, message);
+ }
+
+ void AddWarning(int line, int column, const string& message) {
+ AddErrorOrWarning("input", line, column, message, "warning", std::clog);
+ }
+
+ private:
+ void AddErrorOrWarning(
+ const string& filename, int line, int column,
+ const string& message, const string& type, ostream& out) {
+ // Print full path when running under MSVS
+ string dfile;
+ if (format_ == CommandLineInterface::ERROR_FORMAT_MSVS &&
+ tree_ != NULL &&
+ tree_->VirtualFileToDiskFile(filename, &dfile)) {
+ out << dfile;
+ } else {
+ out << filename;
+ }
+
+ // Users typically expect 1-based line/column numbers, so we add 1
+ // to each here.
+ if (line != -1) {
+ // Allow for both GCC- and Visual-Studio-compatible output.
+ switch (format_) {
+ case CommandLineInterface::ERROR_FORMAT_GCC:
+ out << ":" << (line + 1) << ":" << (column + 1);
+ break;
+ case CommandLineInterface::ERROR_FORMAT_MSVS:
+ out << "(" << (line + 1) << ") : "
+ << type << " in column=" << (column + 1);
+ break;
+ }
+ }
+
+ if (type == "warning") {
+ out << ": warning: " << message << std::endl;
+ } else {
+ out << ": " << message << std::endl;
+ }
+ }
+
+ const ErrorFormat format_;
+ DiskSourceTree *tree_;
+};
+
+// -------------------------------------------------------------------
+
+// A GeneratorContext implementation that buffers files in memory, then dumps
+// them all to disk on demand.
+class CommandLineInterface::GeneratorContextImpl : public GeneratorContext {
+ public:
+ GeneratorContextImpl(const vector<const FileDescriptor*>& parsed_files);
+ ~GeneratorContextImpl();
+
+ // Write all files in the directory to disk at the given output location,
+ // which must end in a '/'.
+ bool WriteAllToDisk(const string& prefix);
+
+ // Write the contents of this directory to a ZIP-format archive with the
+ // given name.
+ bool WriteAllToZip(const string& filename);
+
+ // Add a boilerplate META-INF/MANIFEST.MF file as required by the Java JAR
+ // format, unless one has already been written.
+ void AddJarManifest();
+
+ // Get name of all output files.
+ void GetOutputFilenames(vector<string>* output_filenames);
+
+ // implements GeneratorContext --------------------------------------
+ io::ZeroCopyOutputStream* Open(const string& filename);
+ io::ZeroCopyOutputStream* OpenForAppend(const string& filename);
+ io::ZeroCopyOutputStream* OpenForInsert(
+ const string& filename, const string& insertion_point);
+ void ListParsedFiles(vector<const FileDescriptor*>* output) {
+ *output = parsed_files_;
+ }
+
+ private:
+ friend class MemoryOutputStream;
+
+ // map instead of hash_map so that files are written in order (good when
+ // writing zips).
+ map<string, string*> files_;
+ const vector<const FileDescriptor*>& parsed_files_;
+ bool had_error_;
+};
+
+class CommandLineInterface::MemoryOutputStream
+ : public io::ZeroCopyOutputStream {
+ public:
+ MemoryOutputStream(GeneratorContextImpl* directory, const string& filename,
+ bool append_mode);
+ MemoryOutputStream(GeneratorContextImpl* directory, const string& filename,
+ const string& insertion_point);
+ virtual ~MemoryOutputStream();
+
+ // implements ZeroCopyOutputStream ---------------------------------
+ virtual bool Next(void** data, int* size) { return inner_->Next(data, size); }
+ virtual void BackUp(int count) { inner_->BackUp(count); }
+ virtual int64 ByteCount() const { return inner_->ByteCount(); }
+
+ private:
+ // Where to insert the string when it's done.
+ GeneratorContextImpl* directory_;
+ string filename_;
+ string insertion_point_;
+
+ // The string we're building.
+ string data_;
+
+ // Whether we should append the output stream to the existing file.
+ bool append_mode_;
+
+ // StringOutputStream writing to data_.
+ google::protobuf::scoped_ptr<io::StringOutputStream> inner_;
+};
+
+// -------------------------------------------------------------------
+
+CommandLineInterface::GeneratorContextImpl::GeneratorContextImpl(
+ const vector<const FileDescriptor*>& parsed_files)
+ : parsed_files_(parsed_files),
+ had_error_(false) {
+}
+
+CommandLineInterface::GeneratorContextImpl::~GeneratorContextImpl() {
+ STLDeleteValues(&files_);
+}
+
+bool CommandLineInterface::GeneratorContextImpl::WriteAllToDisk(
+ const string& prefix) {
+ if (had_error_) {
+ return false;
+ }
+
+ if (!VerifyDirectoryExists(prefix)) {
+ return false;
+ }
+
+ for (map<string, string*>::const_iterator iter = files_.begin();
+ iter != files_.end(); ++iter) {
+ const string& relative_filename = iter->first;
+ const char* data = iter->second->data();
+ int size = iter->second->size();
+
+ if (!TryCreateParentDirectory(prefix, relative_filename)) {
+ return false;
+ }
+ string filename = prefix + relative_filename;
+
+ // Create the output file.
+ int file_descriptor;
+ do {
+ file_descriptor =
+ open(filename.c_str(), O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0666);
+ } while (file_descriptor < 0 && errno == EINTR);
+
+ if (file_descriptor < 0) {
+ int error = errno;
+ std::cerr << filename << ": " << strerror(error);
+ return false;
+ }
+
+ // Write the file.
+ while (size > 0) {
+ int write_result;
+ do {
+ write_result = write(file_descriptor, data, size);
+ } while (write_result < 0 && errno == EINTR);
+
+ if (write_result <= 0) {
+ // Write error.
+
+ // FIXME(kenton): According to the man page, if write() returns zero,
+ // there was no error; write() simply did not write anything. It's
+ // unclear under what circumstances this might happen, but presumably
+ // errno won't be set in this case. I am confused as to how such an
+ // event should be handled. For now I'm treating it as an error,
+ // since retrying seems like it could lead to an infinite loop. I
+ // suspect this never actually happens anyway.
+
+ if (write_result < 0) {
+ int error = errno;
+ std::cerr << filename << ": write: " << strerror(error);
+ } else {
+ std::cerr << filename << ": write() returned zero?" << std::endl;
+ }
+ return false;
+ }
+
+ data += write_result;
+ size -= write_result;
+ }
+
+ if (close(file_descriptor) != 0) {
+ int error = errno;
+ std::cerr << filename << ": close: " << strerror(error);
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool CommandLineInterface::GeneratorContextImpl::WriteAllToZip(
+ const string& filename) {
+ if (had_error_) {
+ return false;
+ }
+
+ // Create the output file.
+ int file_descriptor;
+ do {
+ file_descriptor =
+ open(filename.c_str(), O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0666);
+ } while (file_descriptor < 0 && errno == EINTR);
+
+ if (file_descriptor < 0) {
+ int error = errno;
+ std::cerr << filename << ": " << strerror(error);
+ return false;
+ }
+
+ // Create the ZipWriter
+ io::FileOutputStream stream(file_descriptor);
+ ZipWriter zip_writer(&stream);
+
+ for (map<string, string*>::const_iterator iter = files_.begin();
+ iter != files_.end(); ++iter) {
+ zip_writer.Write(iter->first, *iter->second);
+ }
+
+ zip_writer.WriteDirectory();
+
+ if (stream.GetErrno() != 0) {
+ std::cerr << filename << ": " << strerror(stream.GetErrno()) << std::endl;
+ }
+
+ if (!stream.Close()) {
+ std::cerr << filename << ": " << strerror(stream.GetErrno()) << std::endl;
+ }
+
+ return true;
+}
+
+void CommandLineInterface::GeneratorContextImpl::AddJarManifest() {
+ string** map_slot = &files_["META-INF/MANIFEST.MF"];
+ if (*map_slot == NULL) {
+ *map_slot = new string(
+ "Manifest-Version: 1.0\n"
+ "Created-By: 1.6.0 (protoc)\n"
+ "\n");
+ }
+}
+
+void CommandLineInterface::GeneratorContextImpl::GetOutputFilenames(
+ vector<string>* output_filenames) {
+ for (map<string, string*>::iterator iter = files_.begin();
+ iter != files_.end(); ++iter) {
+ output_filenames->push_back(iter->first);
+ }
+}
+
+io::ZeroCopyOutputStream* CommandLineInterface::GeneratorContextImpl::Open(
+ const string& filename) {
+ return new MemoryOutputStream(this, filename, false);
+}
+
+io::ZeroCopyOutputStream*
+CommandLineInterface::GeneratorContextImpl::OpenForAppend(
+ const string& filename) {
+ return new MemoryOutputStream(this, filename, true);
+}
+
+io::ZeroCopyOutputStream*
+CommandLineInterface::GeneratorContextImpl::OpenForInsert(
+ const string& filename, const string& insertion_point) {
+ return new MemoryOutputStream(this, filename, insertion_point);
+}
+
+// -------------------------------------------------------------------
+
+CommandLineInterface::MemoryOutputStream::MemoryOutputStream(
+ GeneratorContextImpl* directory, const string& filename, bool append_mode)
+ : directory_(directory),
+ filename_(filename),
+ append_mode_(append_mode),
+ inner_(new io::StringOutputStream(&data_)) {
+}
+
+CommandLineInterface::MemoryOutputStream::MemoryOutputStream(
+ GeneratorContextImpl* directory, const string& filename,
+ const string& insertion_point)
+ : directory_(directory),
+ filename_(filename),
+ insertion_point_(insertion_point),
+ inner_(new io::StringOutputStream(&data_)) {
+}
+
+CommandLineInterface::MemoryOutputStream::~MemoryOutputStream() {
+ // Make sure all data has been written.
+ inner_.reset();
+
+ // Insert into the directory.
+ string** map_slot = &directory_->files_[filename_];
+
+ if (insertion_point_.empty()) {
+ // This was just a regular Open().
+ if (*map_slot != NULL) {
+ if (append_mode_) {
+ (*map_slot)->append(data_);
+ } else {
+ std::cerr << filename_ << ": Tried to write the same file twice."
+ << std::endl;
+ directory_->had_error_ = true;
+ }
+ return;
+ }
+
+ *map_slot = new string;
+ (*map_slot)->swap(data_);
+ } else {
+ // This was an OpenForInsert().
+
+ // If the data doesn't end with a clean line break, add one.
+ if (!data_.empty() && data_[data_.size() - 1] != '\n') {
+ data_.push_back('\n');
+ }
+
+ // Find the file we are going to insert into.
+ if (*map_slot == NULL) {
+ std::cerr << filename_
+ << ": Tried to insert into file that doesn't exist."
+ << std::endl;
+ directory_->had_error_ = true;
+ return;
+ }
+ string* target = *map_slot;
+
+ // Find the insertion point.
+ string magic_string = strings::Substitute(
+ "@@protoc_insertion_point($0)", insertion_point_);
+ string::size_type pos = target->find(magic_string);
+
+ if (pos == string::npos) {
+ std::cerr << filename_ << ": insertion point \"" << insertion_point_
+ << "\" not found." << std::endl;
+ directory_->had_error_ = true;
+ return;
+ }
+
+ if ((pos > 3) && (target->substr(pos - 3, 2) == "/*")) {
+ // Support for inline "/* @@protoc_insertion_point() */"
+ pos = pos - 3;
+ } else {
+ // Seek backwards to the beginning of the line, which is where we will
+ // insert the data. Note that this has the effect of pushing the
+ // insertion point down, so the data is inserted before it. This is
+ // intentional because it means that multiple insertions at the same point
+ // will end up in the expected order in the final output.
+ pos = target->find_last_of('\n', pos);
+ if (pos == string::npos) {
+ // Insertion point is on the first line.
+ pos = 0;
+ } else {
+ // Advance to character after '\n'.
+ ++pos;
+ }
+ }
+
+ // Extract indent.
+ string indent_(*target, pos, target->find_first_not_of(" \t", pos) - pos);
+
+ if (indent_.empty()) {
+ // No indent. This makes things easier.
+ target->insert(pos, data_);
+ } else {
+ // Calculate how much space we need.
+ int indent_size = 0;
+ for (int i = 0; i < data_.size(); i++) {
+ if (data_[i] == '\n') indent_size += indent_.size();
+ }
+
+ // Make a hole for it.
+ target->insert(pos, data_.size() + indent_size, '\0');
+
+ // Now copy in the data.
+ string::size_type data_pos = 0;
+ char* target_ptr = string_as_array(target) + pos;
+ while (data_pos < data_.size()) {
+ // Copy indent.
+ memcpy(target_ptr, indent_.data(), indent_.size());
+ target_ptr += indent_.size();
+
+ // Copy line from data_.
+ // We already guaranteed that data_ ends with a newline (above), so this
+ // search can't fail.
+ string::size_type line_length =
+ data_.find_first_of('\n', data_pos) + 1 - data_pos;
+ memcpy(target_ptr, data_.data() + data_pos, line_length);
+ target_ptr += line_length;
+ data_pos += line_length;
+ }
+
+ GOOGLE_CHECK_EQ(target_ptr,
+ string_as_array(target) + pos + data_.size() + indent_size);
+ }
+ }
+}
+
+// ===================================================================
+
+CommandLineInterface::CommandLineInterface()
+ : mode_(MODE_COMPILE),
+ print_mode_(PRINT_NONE),
+ error_format_(ERROR_FORMAT_GCC),
+ imports_in_descriptor_set_(false),
+ source_info_in_descriptor_set_(false),
+ disallow_services_(false),
+ inputs_are_proto_path_relative_(false) {}
+CommandLineInterface::~CommandLineInterface() {}
+
+void CommandLineInterface::RegisterGenerator(const string& flag_name,
+ CodeGenerator* generator,
+ const string& help_text) {
+ GeneratorInfo info;
+ info.flag_name = flag_name;
+ info.generator = generator;
+ info.help_text = help_text;
+ generators_by_flag_name_[flag_name] = info;
+}
+
+void CommandLineInterface::RegisterGenerator(const string& flag_name,
+ const string& option_flag_name,
+ CodeGenerator* generator,
+ const string& help_text) {
+ GeneratorInfo info;
+ info.flag_name = flag_name;
+ info.option_flag_name = option_flag_name;
+ info.generator = generator;
+ info.help_text = help_text;
+ generators_by_flag_name_[flag_name] = info;
+ generators_by_option_name_[option_flag_name] = info;
+}
+
+void CommandLineInterface::AllowPlugins(const string& exe_name_prefix) {
+ plugin_prefix_ = exe_name_prefix;
+}
+
+int CommandLineInterface::Run(int argc, const char* const argv[]) {
+ Clear();
+ switch (ParseArguments(argc, argv)) {
+ case PARSE_ARGUMENT_DONE_AND_EXIT:
+ return 0;
+ case PARSE_ARGUMENT_FAIL:
+ return 1;
+ case PARSE_ARGUMENT_DONE_AND_CONTINUE:
+ break;
+ }
+
+ AddDefaultProtoPaths(&proto_path_);
+
+ // Set up the source tree.
+ DiskSourceTree source_tree;
+ for (int i = 0; i < proto_path_.size(); i++) {
+ source_tree.MapPath(proto_path_[i].first, proto_path_[i].second);
+ }
+
+ // Map input files to virtual paths if necessary.
+ if (!inputs_are_proto_path_relative_) {
+ if (!MakeInputsBeProtoPathRelative(&source_tree)) {
+ return 1;
+ }
+ }
+
+ // Allocate the Importer.
+ ErrorPrinter error_collector(error_format_, &source_tree);
+ Importer importer(&source_tree, &error_collector);
+
+ vector<const FileDescriptor*> parsed_files;
+
+ // Parse each file.
+ for (int i = 0; i < input_files_.size(); i++) {
+ // Import the file.
+ importer.AddUnusedImportTrackFile(input_files_[i]);
+ const FileDescriptor* parsed_file = importer.Import(input_files_[i]);
+ importer.ClearUnusedImportTrackFiles();
+ if (parsed_file == NULL) return 1;
+ parsed_files.push_back(parsed_file);
+
+ // Enforce --disallow_services.
+ if (disallow_services_ && parsed_file->service_count() > 0) {
+ cerr << parsed_file->name() << ": This file contains services, but "
+ "--disallow_services was used." << endl;
+ return 1;
+ }
+ }
+
+ // We construct a separate GeneratorContext for each output location. Note
+ // that two code generators may output to the same location, in which case
+ // they should share a single GeneratorContext so that OpenForInsert() works.
+ GeneratorContextMap output_directories;
+
+ // Generate output.
+ if (mode_ == MODE_COMPILE) {
+ for (int i = 0; i < output_directives_.size(); i++) {
+ string output_location = output_directives_[i].output_location;
+ if (!HasSuffixString(output_location, ".zip") &&
+ !HasSuffixString(output_location, ".jar")) {
+ AddTrailingSlash(&output_location);
+ }
+ GeneratorContextImpl** map_slot = &output_directories[output_location];
+
+ if (*map_slot == NULL) {
+ // First time we've seen this output location.
+ *map_slot = new GeneratorContextImpl(parsed_files);
+ }
+
+ if (!GenerateOutput(parsed_files, output_directives_[i], *map_slot)) {
+ STLDeleteValues(&output_directories);
+ return 1;
+ }
+ }
+ }
+
+ // Write all output to disk.
+ for (GeneratorContextMap::iterator iter = output_directories.begin();
+ iter != output_directories.end(); ++iter) {
+ const string& location = iter->first;
+ GeneratorContextImpl* directory = iter->second;
+ if (HasSuffixString(location, "/")) {
+ if (!directory->WriteAllToDisk(location)) {
+ STLDeleteValues(&output_directories);
+ return 1;
+ }
+ } else {
+ if (HasSuffixString(location, ".jar")) {
+ directory->AddJarManifest();
+ }
+
+ if (!directory->WriteAllToZip(location)) {
+ STLDeleteValues(&output_directories);
+ return 1;
+ }
+ }
+ }
+
+ if (!dependency_out_name_.empty()) {
+ if (!GenerateDependencyManifestFile(parsed_files, output_directories,
+ &source_tree)) {
+ return 1;
+ }
+ }
+
+ STLDeleteValues(&output_directories);
+
+ if (!descriptor_set_name_.empty()) {
+ if (!WriteDescriptorSet(parsed_files)) {
+ return 1;
+ }
+ }
+
+ if (mode_ == MODE_ENCODE || mode_ == MODE_DECODE) {
+ if (codec_type_.empty()) {
+ // HACK: Define an EmptyMessage type to use for decoding.
+ DescriptorPool pool;
+ FileDescriptorProto file;
+ file.set_name("empty_message.proto");
+ file.add_message_type()->set_name("EmptyMessage");
+ GOOGLE_CHECK(pool.BuildFile(file) != NULL);
+ codec_type_ = "EmptyMessage";
+ if (!EncodeOrDecode(&pool)) {
+ return 1;
+ }
+ } else {
+ if (!EncodeOrDecode(importer.pool())) {
+ return 1;
+ }
+ }
+ }
+
+ if (mode_ == MODE_PRINT) {
+ switch (print_mode_) {
+ case PRINT_FREE_FIELDS:
+ for (int i = 0; i < parsed_files.size(); ++i) {
+ const FileDescriptor* fd = parsed_files[i];
+ for (int j = 0; j < fd->message_type_count(); ++j) {
+ PrintFreeFieldNumbers(fd->message_type(j));
+ }
+ }
+ break;
+ case PRINT_NONE:
+ GOOGLE_LOG(ERROR) << "If the code reaches here, it usually means a bug of "
+ "flag parsing in the CommonadLineInterface.";
+ return 1;
+
+ // Do not add a default case.
+ }
+ }
+
+ return 0;
+}
+
+void CommandLineInterface::Clear() {
+ // Clear all members that are set by Run(). Note that we must not clear
+ // members which are set by other methods before Run() is called.
+ executable_name_.clear();
+ proto_path_.clear();
+ input_files_.clear();
+ output_directives_.clear();
+ codec_type_.clear();
+ descriptor_set_name_.clear();
+ dependency_out_name_.clear();
+
+ mode_ = MODE_COMPILE;
+ print_mode_ = PRINT_NONE;
+ imports_in_descriptor_set_ = false;
+ source_info_in_descriptor_set_ = false;
+ disallow_services_ = false;
+}
+
+bool CommandLineInterface::MakeInputsBeProtoPathRelative(
+ DiskSourceTree* source_tree) {
+ for (int i = 0; i < input_files_.size(); i++) {
+ string virtual_file, shadowing_disk_file;
+ switch (source_tree->DiskFileToVirtualFile(
+ input_files_[i], &virtual_file, &shadowing_disk_file)) {
+ case DiskSourceTree::SUCCESS:
+ input_files_[i] = virtual_file;
+ break;
+ case DiskSourceTree::SHADOWED:
+ std::cerr << input_files_[i]
+ << ": Input is shadowed in the --proto_path by \""
+ << shadowing_disk_file
+ << "\". Either use the latter file as your input or reorder "
+ "the --proto_path so that the former file's location "
+ "comes first." << std::endl;
+ return false;
+ case DiskSourceTree::CANNOT_OPEN:
+ std::cerr << input_files_[i] << ": " << strerror(errno) << std::endl;
+ return false;
+ case DiskSourceTree::NO_MAPPING:
+ // First check if the file exists at all.
+ if (access(input_files_[i].c_str(), F_OK) < 0) {
+ // File does not even exist.
+ std::cerr << input_files_[i] << ": " << strerror(ENOENT) << std::endl;
+ } else {
+ std::cerr
+ << input_files_[i]
+ << ": File does not reside within any path "
+ "specified using --proto_path (or -I). You must specify a "
+ "--proto_path which encompasses this file. Note that the "
+ "proto_path must be an exact prefix of the .proto file "
+ "names -- protoc is too dumb to figure out when two paths "
+ "(e.g. absolute and relative) are equivalent (it's harder "
+ "than you think)." << std::endl;
+ }
+ return false;
+ }
+ }
+
+ return true;
+}
+
+
+CommandLineInterface::ParseArgumentStatus
+CommandLineInterface::ParseArguments(int argc, const char* const argv[]) {
+ executable_name_ = argv[0];
+
+ vector<string> arguments;
+ for (int i = 1; i < argc; ++i) {
+ arguments.push_back(argv[i]);
+ }
+
+ // Iterate through all arguments and parse them.
+ for (int i = 0; i < arguments.size(); ++i) {
+ string name, value;
+
+ if (ParseArgument(arguments[i].c_str(), &name, &value)) {
+ // Returned true => Use the next argument as the flag value.
+ if (i + 1 == arguments.size() || arguments[i + 1][0] == '-') {
+ std::cerr << "Missing value for flag: " << name << std::endl;
+ if (name == "--decode") {
+ std::cerr << "To decode an unknown message, use --decode_raw."
+ << std::endl;
+ }
+ return PARSE_ARGUMENT_FAIL;
+ } else {
+ ++i;
+ value = arguments[i];
+ }
+ }
+
+ ParseArgumentStatus status = InterpretArgument(name, value);
+ if (status != PARSE_ARGUMENT_DONE_AND_CONTINUE)
+ return status;
+ }
+
+ // If no --proto_path was given, use the current working directory.
+ if (proto_path_.empty()) {
+ // Don't use make_pair as the old/default standard library on Solaris
+ // doesn't support it without explicit template parameters, which are
+ // incompatible with C++0x's make_pair.
+ proto_path_.push_back(pair<string, string>("", "."));
+ }
+
+ // Check some errror cases.
+ bool decoding_raw = (mode_ == MODE_DECODE) && codec_type_.empty();
+ if (decoding_raw && !input_files_.empty()) {
+ std::cerr << "When using --decode_raw, no input files should be given."
+ << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ } else if (!decoding_raw && input_files_.empty()) {
+ std::cerr << "Missing input file." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (mode_ == MODE_COMPILE && output_directives_.empty() &&
+ descriptor_set_name_.empty()) {
+ std::cerr << "Missing output directives." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (mode_ != MODE_COMPILE && !dependency_out_name_.empty()) {
+ std::cerr << "Can only use --dependency_out=FILE when generating code."
+ << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (!dependency_out_name_.empty() && input_files_.size() > 1) {
+ std::cerr
+ << "Can only process one input file when using --dependency_out=FILE."
+ << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (imports_in_descriptor_set_ && descriptor_set_name_.empty()) {
+ std::cerr << "--include_imports only makes sense when combined with "
+ "--descriptor_set_out." << std::endl;
+ }
+ if (source_info_in_descriptor_set_ && descriptor_set_name_.empty()) {
+ std::cerr << "--include_source_info only makes sense when combined with "
+ "--descriptor_set_out." << std::endl;
+ }
+
+ return PARSE_ARGUMENT_DONE_AND_CONTINUE;
+}
+
+bool CommandLineInterface::ParseArgument(const char* arg,
+ string* name, string* value) {
+ bool parsed_value = false;
+
+ if (arg[0] != '-') {
+ // Not a flag.
+ name->clear();
+ parsed_value = true;
+ *value = arg;
+ } else if (arg[1] == '-') {
+ // Two dashes: Multi-character name, with '=' separating name and
+ // value.
+ const char* equals_pos = strchr(arg, '=');
+ if (equals_pos != NULL) {
+ *name = string(arg, equals_pos - arg);
+ *value = equals_pos + 1;
+ parsed_value = true;
+ } else {
+ *name = arg;
+ }
+ } else {
+ // One dash: One-character name, all subsequent characters are the
+ // value.
+ if (arg[1] == '\0') {
+ // arg is just "-". We treat this as an input file, except that at
+ // present this will just lead to a "file not found" error.
+ name->clear();
+ *value = arg;
+ parsed_value = true;
+ } else {
+ *name = string(arg, 2);
+ *value = arg + 2;
+ parsed_value = !value->empty();
+ }
+ }
+
+ // Need to return true iff the next arg should be used as the value for this
+ // one, false otherwise.
+
+ if (parsed_value) {
+ // We already parsed a value for this flag.
+ return false;
+ }
+
+ if (*name == "-h" || *name == "--help" ||
+ *name == "--disallow_services" ||
+ *name == "--include_imports" ||
+ *name == "--include_source_info" ||
+ *name == "--version" ||
+ *name == "--decode_raw" ||
+ *name == "--print_free_field_numbers") {
+ // HACK: These are the only flags that don't take a value.
+ // They probably should not be hard-coded like this but for now it's
+ // not worth doing better.
+ return false;
+ }
+
+ // Next argument is the flag value.
+ return true;
+}
+
+CommandLineInterface::ParseArgumentStatus
+CommandLineInterface::InterpretArgument(const string& name,
+ const string& value) {
+ if (name.empty()) {
+ // Not a flag. Just a filename.
+ if (value.empty()) {
+ std::cerr
+ << "You seem to have passed an empty string as one of the "
+ "arguments to " << executable_name_
+ << ". This is actually "
+ "sort of hard to do. Congrats. Unfortunately it is not valid "
+ "input so the program is going to die now." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+
+ input_files_.push_back(value);
+
+ } else if (name == "-I" || name == "--proto_path") {
+ // Java's -classpath (and some other languages) delimits path components
+ // with colons. Let's accept that syntax too just to make things more
+ // intuitive.
+ vector<string> parts = Split(
+ value, kPathSeparator, true);
+
+ for (int i = 0; i < parts.size(); i++) {
+ string virtual_path;
+ string disk_path;
+
+ string::size_type equals_pos = parts[i].find_first_of('=');
+ if (equals_pos == string::npos) {
+ virtual_path = "";
+ disk_path = parts[i];
+ } else {
+ virtual_path = parts[i].substr(0, equals_pos);
+ disk_path = parts[i].substr(equals_pos + 1);
+ }
+
+ if (disk_path.empty()) {
+ std::cerr
+ << "--proto_path passed empty directory name. (Use \".\" for "
+ "current directory.)" << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+
+ // Make sure disk path exists, warn otherwise.
+ if (access(disk_path.c_str(), F_OK) < 0) {
+ // Try the original path; it may have just happed to have a '=' in it.
+ if (access(parts[i].c_str(), F_OK) < 0) {
+ cerr << disk_path << ": warning: directory does not exist." << endl;
+ } else {
+ virtual_path = "";
+ disk_path = parts[i];
+ }
+ }
+
+ // Don't use make_pair as the old/default standard library on Solaris
+ // doesn't support it without explicit template parameters, which are
+ // incompatible with C++0x's make_pair.
+ proto_path_.push_back(pair<string, string>(virtual_path, disk_path));
+ }
+
+ } else if (name == "-o" || name == "--descriptor_set_out") {
+ if (!descriptor_set_name_.empty()) {
+ std::cerr << name << " may only be passed once." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (value.empty()) {
+ std::cerr << name << " requires a non-empty value." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (mode_ != MODE_COMPILE) {
+ std::cerr
+ << "Cannot use --encode or --decode and generate descriptors at the "
+ "same time." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ descriptor_set_name_ = value;
+
+ } else if (name == "--dependency_out") {
+ if (!dependency_out_name_.empty()) {
+ std::cerr << name << " may only be passed once." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (value.empty()) {
+ std::cerr << name << " requires a non-empty value." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ dependency_out_name_ = value;
+
+ } else if (name == "--include_imports") {
+ if (imports_in_descriptor_set_) {
+ std::cerr << name << " may only be passed once." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ imports_in_descriptor_set_ = true;
+
+ } else if (name == "--include_source_info") {
+ if (source_info_in_descriptor_set_) {
+ std::cerr << name << " may only be passed once." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ source_info_in_descriptor_set_ = true;
+
+ } else if (name == "-h" || name == "--help") {
+ PrintHelpText();
+ return PARSE_ARGUMENT_DONE_AND_EXIT; // Exit without running compiler.
+
+ } else if (name == "--version") {
+ if (!version_info_.empty()) {
+ std::cout << version_info_ << std::endl;
+ }
+ cout << "libprotoc "
+ << protobuf::internal::VersionString(GOOGLE_PROTOBUF_VERSION)
+ << endl;
+ return PARSE_ARGUMENT_DONE_AND_EXIT; // Exit without running compiler.
+
+ } else if (name == "--disallow_services") {
+ disallow_services_ = true;
+
+ } else if (name == "--encode" || name == "--decode" ||
+ name == "--decode_raw") {
+ if (mode_ != MODE_COMPILE) {
+ std::cerr << "Only one of --encode and --decode can be specified."
+ << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (!output_directives_.empty() || !descriptor_set_name_.empty()) {
+ std::cerr << "Cannot use " << name
+ << " and generate code or descriptors at the same time."
+ << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+
+ mode_ = (name == "--encode") ? MODE_ENCODE : MODE_DECODE;
+
+ if (value.empty() && name != "--decode_raw") {
+ std::cerr << "Type name for " << name << " cannot be blank." << std::endl;
+ if (name == "--decode") {
+ std::cerr << "To decode an unknown message, use --decode_raw."
+ << std::endl;
+ }
+ return PARSE_ARGUMENT_FAIL;
+ } else if (!value.empty() && name == "--decode_raw") {
+ std::cerr << "--decode_raw does not take a parameter." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+
+ codec_type_ = value;
+
+ } else if (name == "--error_format") {
+ if (value == "gcc") {
+ error_format_ = ERROR_FORMAT_GCC;
+ } else if (value == "msvs") {
+ error_format_ = ERROR_FORMAT_MSVS;
+ } else {
+ std::cerr << "Unknown error format: " << value << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+
+ } else if (name == "--plugin") {
+ if (plugin_prefix_.empty()) {
+ std::cerr << "This compiler does not support plugins." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+
+ string plugin_name;
+ string path;
+
+ string::size_type equals_pos = value.find_first_of('=');
+ if (equals_pos == string::npos) {
+ // Use the basename of the file.
+ string::size_type slash_pos = value.find_last_of('/');
+ if (slash_pos == string::npos) {
+ plugin_name = value;
+ } else {
+ plugin_name = value.substr(slash_pos + 1);
+ }
+ path = value;
+ } else {
+ plugin_name = value.substr(0, equals_pos);
+ path = value.substr(equals_pos + 1);
+ }
+
+ plugins_[plugin_name] = path;
+
+ } else if (name == "--print_free_field_numbers") {
+ if (mode_ != MODE_COMPILE) {
+ std::cerr << "Cannot use " << name
+ << " and use --encode, --decode or print "
+ << "other info at the same time." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ if (!output_directives_.empty() || !descriptor_set_name_.empty()) {
+ std::cerr << "Cannot use " << name
+ << " and generate code or descriptors at the same time."
+ << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+ mode_ = MODE_PRINT;
+ print_mode_ = PRINT_FREE_FIELDS;
+ } else {
+ // Some other flag. Look it up in the generators list.
+ const GeneratorInfo* generator_info =
+ FindOrNull(generators_by_flag_name_, name);
+ if (generator_info == NULL &&
+ (plugin_prefix_.empty() || !HasSuffixString(name, "_out"))) {
+ // Check if it's a generator option flag.
+ generator_info = FindOrNull(generators_by_option_name_, name);
+ if (generator_info == NULL) {
+ std::cerr << "Unknown flag: " << name << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ } else {
+ string* parameters = &generator_parameters_[generator_info->flag_name];
+ if (!parameters->empty()) {
+ parameters->append(",");
+ }
+ parameters->append(value);
+ }
+ } else {
+ // It's an output flag. Add it to the output directives.
+ if (mode_ != MODE_COMPILE) {
+ std::cerr << "Cannot use --encode, --decode or print .proto info and "
+ "generate code at the same time." << std::endl;
+ return PARSE_ARGUMENT_FAIL;
+ }
+
+ OutputDirective directive;
+ directive.name = name;
+ if (generator_info == NULL) {
+ directive.generator = NULL;
+ } else {
+ directive.generator = generator_info->generator;
+ }
+
+ // Split value at ':' to separate the generator parameter from the
+ // filename. However, avoid doing this if the colon is part of a valid
+ // Windows-style absolute path.
+ string::size_type colon_pos = value.find_first_of(':');
+ if (colon_pos == string::npos || IsWindowsAbsolutePath(value)) {
+ directive.output_location = value;
+ } else {
+ directive.parameter = value.substr(0, colon_pos);
+ directive.output_location = value.substr(colon_pos + 1);
+ }
+
+ output_directives_.push_back(directive);
+ }
+ }
+
+ return PARSE_ARGUMENT_DONE_AND_CONTINUE;
+}
+
+void CommandLineInterface::PrintHelpText() {
+ // Sorry for indentation here; line wrapping would be uglier.
+ std::cerr <<
+"Usage: " << executable_name_ << " [OPTION] PROTO_FILES\n"
+"Parse PROTO_FILES and generate output based on the options given:\n"
+" -IPATH, --proto_path=PATH Specify the directory in which to search for\n"
+" imports. May be specified multiple times;\n"
+" directories will be searched in order. If not\n"
+" given, the current working directory is used.\n"
+" --version Show version info and exit.\n"
+" -h, --help Show this text and exit.\n"
+" --encode=MESSAGE_TYPE Read a text-format message of the given type\n"
+" from standard input and write it in binary\n"
+" to standard output. The message type must\n"
+" be defined in PROTO_FILES or their imports.\n"
+" --decode=MESSAGE_TYPE Read a binary message of the given type from\n"
+" standard input and write it in text format\n"
+" to standard output. The message type must\n"
+" be defined in PROTO_FILES or their imports.\n"
+" --decode_raw Read an arbitrary protocol message from\n"
+" standard input and write the raw tag/value\n"
+" pairs in text format to standard output. No\n"
+" PROTO_FILES should be given when using this\n"
+" flag.\n"
+" -oFILE, Writes a FileDescriptorSet (a protocol buffer,\n"
+" --descriptor_set_out=FILE defined in descriptor.proto) containing all of\n"
+" the input files to FILE.\n"
+" --include_imports When using --descriptor_set_out, also include\n"
+" all dependencies of the input files in the\n"
+" set, so that the set is self-contained.\n"
+" --include_source_info When using --descriptor_set_out, do not strip\n"
+" SourceCodeInfo from the FileDescriptorProto.\n"
+" This results in vastly larger descriptors that\n"
+" include information about the original\n"
+" location of each decl in the source file as\n"
+" well as surrounding comments.\n"
+" --dependency_out=FILE Write a dependency output file in the format\n"
+" expected by make. This writes the transitive\n"
+" set of input file paths to FILE\n"
+" --error_format=FORMAT Set the format in which to print errors.\n"
+" FORMAT may be 'gcc' (the default) or 'msvs'\n"
+" (Microsoft Visual Studio format).\n"
+" --print_free_field_numbers Print the free field numbers of the messages\n"
+" defined in the given proto files. Groups share\n"
+" the same field number space with the parent \n"
+" message. Extension ranges are counted as \n"
+" occupied fields numbers.\n"
+ << std::endl;
+ if (!plugin_prefix_.empty()) {
+ std::cerr <<
+" --plugin=EXECUTABLE Specifies a plugin executable to use.\n"
+" Normally, protoc searches the PATH for\n"
+" plugins, but you may specify additional\n"
+" executables not in the path using this flag.\n"
+" Additionally, EXECUTABLE may be of the form\n"
+" NAME=PATH, in which case the given plugin name\n"
+" is mapped to the given executable even if\n"
+" the executable's own name differs." << std::endl;
+ }
+
+ for (GeneratorMap::iterator iter = generators_by_flag_name_.begin();
+ iter != generators_by_flag_name_.end(); ++iter) {
+ // FIXME(kenton): If the text is long enough it will wrap, which is ugly,
+ // but fixing this nicely (e.g. splitting on spaces) is probably more
+ // trouble than it's worth.
+ std::cerr << " " << iter->first << "=OUT_DIR "
+ << string(19 - iter->first.size(), ' ') // Spaces for alignment.
+ << iter->second.help_text << std::endl;
+ }
+}
+
+bool CommandLineInterface::GenerateOutput(
+ const vector<const FileDescriptor*>& parsed_files,
+ const OutputDirective& output_directive,
+ GeneratorContext* generator_context) {
+ // Call the generator.
+ string error;
+ if (output_directive.generator == NULL) {
+ // This is a plugin.
+ GOOGLE_CHECK(HasPrefixString(output_directive.name, "--") &&
+ HasSuffixString(output_directive.name, "_out"))
+ << "Bad name for plugin generator: " << output_directive.name;
+
+ // Strip the "--" and "_out" and add the plugin prefix.
+ string plugin_name = plugin_prefix_ + "gen-" +
+ output_directive.name.substr(2, output_directive.name.size() - 6);
+
+ if (!GeneratePluginOutput(parsed_files, plugin_name,
+ output_directive.parameter,
+ generator_context, &error)) {
+ std::cerr << output_directive.name << ": " << error << std::endl;
+ return false;
+ }
+ } else {
+ // Regular generator.
+ string parameters = output_directive.parameter;
+ if (!generator_parameters_[output_directive.name].empty()) {
+ if (!parameters.empty()) {
+ parameters.append(",");
+ }
+ parameters.append(generator_parameters_[output_directive.name]);
+ }
+ if (output_directive.generator->HasGenerateAll()) {
+ if (!output_directive.generator->GenerateAll(
+ parsed_files, parameters, generator_context, &error)) {
+ // Generator returned an error.
+ std::cerr << output_directive.name << ": "
+ << ": " << error << std::endl;
+ return false;
+ }
+ } else {
+ for (int i = 0; i < parsed_files.size(); i++) {
+ if (!output_directive.generator->Generate(parsed_files[i], parameters,
+ generator_context, &error)) {
+ // Generator returned an error.
+ std::cerr << output_directive.name << ": " << parsed_files[i]->name()
+ << ": " << error << std::endl;
+ return false;
+ }
+ }
+ }
+ }
+
+ return true;
+}
+
+bool CommandLineInterface::GenerateDependencyManifestFile(
+ const vector<const FileDescriptor*>& parsed_files,
+ const GeneratorContextMap& output_directories,
+ DiskSourceTree* source_tree) {
+ FileDescriptorSet file_set;
+
+ set<const FileDescriptor*> already_seen;
+ for (int i = 0; i < parsed_files.size(); i++) {
+ GetTransitiveDependencies(parsed_files[i],
+ false,
+ false,
+ &already_seen,
+ file_set.mutable_file());
+ }
+
+ vector<string> output_filenames;
+ for (GeneratorContextMap::const_iterator iter = output_directories.begin();
+ iter != output_directories.end(); ++iter) {
+ const string& location = iter->first;
+ GeneratorContextImpl* directory = iter->second;
+ vector<string> relative_output_filenames;
+ directory->GetOutputFilenames(&relative_output_filenames);
+ for (int i = 0; i < relative_output_filenames.size(); i++) {
+ string output_filename = location + relative_output_filenames[i];
+ if (output_filename.compare(0, 2, "./") == 0) {
+ output_filename = output_filename.substr(2);
+ }
+ output_filenames.push_back(output_filename);
+ }
+ }
+
+ int fd;
+ do {
+ fd = open(dependency_out_name_.c_str(),
+ O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0666);
+ } while (fd < 0 && errno == EINTR);
+
+ if (fd < 0) {
+ perror(dependency_out_name_.c_str());
+ return false;
+ }
+
+ io::FileOutputStream out(fd);
+ io::Printer printer(&out, '$');
+
+ for (int i = 0; i < output_filenames.size(); i++) {
+ printer.Print(output_filenames[i].c_str());
+ if (i == output_filenames.size() - 1) {
+ printer.Print(":");
+ } else {
+ printer.Print(" \\\n");
+ }
+ }
+
+ for (int i = 0; i < file_set.file_size(); i++) {
+ const FileDescriptorProto& file = file_set.file(i);
+ const string& virtual_file = file.name();
+ string disk_file;
+ if (source_tree &&
+ source_tree->VirtualFileToDiskFile(virtual_file, &disk_file)) {
+ printer.Print(" $disk_file$", "disk_file", disk_file);
+ if (i < file_set.file_size() - 1) printer.Print("\\\n");
+ } else {
+ std::cerr << "Unable to identify path for file " << virtual_file
+ << std::endl;
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool CommandLineInterface::GeneratePluginOutput(
+ const vector<const FileDescriptor*>& parsed_files,
+ const string& plugin_name,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) {
+ CodeGeneratorRequest request;
+ CodeGeneratorResponse response;
+
+ // Build the request.
+ if (!parameter.empty()) {
+ request.set_parameter(parameter);
+ }
+
+ set<const FileDescriptor*> already_seen;
+ for (int i = 0; i < parsed_files.size(); i++) {
+ request.add_file_to_generate(parsed_files[i]->name());
+ GetTransitiveDependencies(parsed_files[i],
+ true, // Include json_name for plugins.
+ true, // Include source code info.
+ &already_seen, request.mutable_proto_file());
+ }
+
+ // Invoke the plugin.
+ Subprocess subprocess;
+
+ if (plugins_.count(plugin_name) > 0) {
+ subprocess.Start(plugins_[plugin_name], Subprocess::EXACT_NAME);
+ } else {
+ subprocess.Start(plugin_name, Subprocess::SEARCH_PATH);
+ }
+
+ string communicate_error;
+ if (!subprocess.Communicate(request, &response, &communicate_error)) {
+ *error = strings::Substitute("$0: $1", plugin_name, communicate_error);
+ return false;
+ }
+
+ // Write the files. We do this even if there was a generator error in order
+ // to match the behavior of a compiled-in generator.
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> current_output;
+ for (int i = 0; i < response.file_size(); i++) {
+ const CodeGeneratorResponse::File& output_file = response.file(i);
+
+ if (!output_file.insertion_point().empty()) {
+ // Open a file for insert.
+ // We reset current_output to NULL first so that the old file is closed
+ // before the new one is opened.
+ current_output.reset();
+ current_output.reset(generator_context->OpenForInsert(
+ output_file.name(), output_file.insertion_point()));
+ } else if (!output_file.name().empty()) {
+ // Starting a new file. Open it.
+ // We reset current_output to NULL first so that the old file is closed
+ // before the new one is opened.
+ current_output.reset();
+ current_output.reset(generator_context->Open(output_file.name()));
+ } else if (current_output == NULL) {
+ *error = strings::Substitute(
+ "$0: First file chunk returned by plugin did not specify a file name.",
+ plugin_name);
+ return false;
+ }
+
+ // Use CodedOutputStream for convenience; otherwise we'd need to provide
+ // our own buffer-copying loop.
+ io::CodedOutputStream writer(current_output.get());
+ writer.WriteString(output_file.content());
+ }
+
+ // Check for errors.
+ if (!response.error().empty()) {
+ // Generator returned an error.
+ *error = response.error();
+ return false;
+ }
+
+ return true;
+}
+
+bool CommandLineInterface::EncodeOrDecode(const DescriptorPool* pool) {
+ // Look up the type.
+ const Descriptor* type = pool->FindMessageTypeByName(codec_type_);
+ if (type == NULL) {
+ std::cerr << "Type not defined: " << codec_type_ << std::endl;
+ return false;
+ }
+
+ DynamicMessageFactory dynamic_factory(pool);
+ google::protobuf::scoped_ptr<Message> message(dynamic_factory.GetPrototype(type)->New());
+
+ if (mode_ == MODE_ENCODE) {
+ SetFdToTextMode(STDIN_FILENO);
+ SetFdToBinaryMode(STDOUT_FILENO);
+ } else {
+ SetFdToBinaryMode(STDIN_FILENO);
+ SetFdToTextMode(STDOUT_FILENO);
+ }
+
+ io::FileInputStream in(STDIN_FILENO);
+ io::FileOutputStream out(STDOUT_FILENO);
+
+ if (mode_ == MODE_ENCODE) {
+ // Input is text.
+ ErrorPrinter error_collector(error_format_);
+ TextFormat::Parser parser;
+ parser.RecordErrorsTo(&error_collector);
+ parser.AllowPartialMessage(true);
+
+ if (!parser.Parse(&in, message.get())) {
+ std::cerr << "Failed to parse input." << std::endl;
+ return false;
+ }
+ } else {
+ // Input is binary.
+ if (!message->ParsePartialFromZeroCopyStream(&in)) {
+ std::cerr << "Failed to parse input." << std::endl;
+ return false;
+ }
+ }
+
+ if (!message->IsInitialized()) {
+ std::cerr << "warning: Input message is missing required fields: "
+ << message->InitializationErrorString() << std::endl;
+ }
+
+ if (mode_ == MODE_ENCODE) {
+ // Output is binary.
+ if (!message->SerializePartialToZeroCopyStream(&out)) {
+ std::cerr << "output: I/O error." << std::endl;
+ return false;
+ }
+ } else {
+ // Output is text.
+ if (!TextFormat::Print(*message, &out)) {
+ std::cerr << "output: I/O error." << std::endl;
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool CommandLineInterface::WriteDescriptorSet(
+ const vector<const FileDescriptor*> parsed_files) {
+ FileDescriptorSet file_set;
+
+ if (imports_in_descriptor_set_) {
+ set<const FileDescriptor*> already_seen;
+ for (int i = 0; i < parsed_files.size(); i++) {
+ GetTransitiveDependencies(parsed_files[i],
+ true, // Include json_name
+ source_info_in_descriptor_set_,
+ &already_seen, file_set.mutable_file());
+ }
+ } else {
+ set<const FileDescriptor*> already_seen;
+ for (int i = 0; i < parsed_files.size(); i++) {
+ if (!already_seen.insert(parsed_files[i]).second) {
+ continue;
+ }
+ FileDescriptorProto* file_proto = file_set.add_file();
+ parsed_files[i]->CopyTo(file_proto);
+ parsed_files[i]->CopyJsonNameTo(file_proto);
+ if (source_info_in_descriptor_set_) {
+ parsed_files[i]->CopySourceCodeInfoTo(file_proto);
+ }
+ }
+ }
+
+ int fd;
+ do {
+ fd = open(descriptor_set_name_.c_str(),
+ O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0666);
+ } while (fd < 0 && errno == EINTR);
+
+ if (fd < 0) {
+ perror(descriptor_set_name_.c_str());
+ return false;
+ }
+
+ io::FileOutputStream out(fd);
+ if (!file_set.SerializeToZeroCopyStream(&out)) {
+ std::cerr << descriptor_set_name_ << ": " << strerror(out.GetErrno())
+ << std::endl;
+ out.Close();
+ return false;
+ }
+ if (!out.Close()) {
+ std::cerr << descriptor_set_name_ << ": " << strerror(out.GetErrno())
+ << std::endl;
+ return false;
+ }
+
+ return true;
+}
+
+void CommandLineInterface::GetTransitiveDependencies(
+ const FileDescriptor* file,
+ bool include_json_name,
+ bool include_source_code_info,
+ set<const FileDescriptor*>* already_seen,
+ RepeatedPtrField<FileDescriptorProto>* output) {
+ if (!already_seen->insert(file).second) {
+ // Already saw this file. Skip.
+ return;
+ }
+
+ // Add all dependencies.
+ for (int i = 0; i < file->dependency_count(); i++) {
+ GetTransitiveDependencies(file->dependency(i),
+ include_json_name,
+ include_source_code_info,
+ already_seen, output);
+ }
+
+ // Add this file.
+ FileDescriptorProto* new_descriptor = output->Add();
+ file->CopyTo(new_descriptor);
+ if (include_json_name) {
+ file->CopyJsonNameTo(new_descriptor);
+ }
+ if (include_source_code_info) {
+ file->CopySourceCodeInfoTo(new_descriptor);
+ }
+}
+
+namespace {
+
+// Utility function for PrintFreeFieldNumbers.
+// Stores occupied ranges into the ranges parameter, and next level of sub
+// message types into the nested_messages parameter. The FieldRange is left
+// inclusive, right exclusive. i.e. [a, b).
+//
+// Nested Messages:
+// Note that it only stores the nested message type, iff the nested type is
+// either a direct child of the given descriptor, or the nested type is a
+// decendent of the given descriptor and all the nodes between the
+// nested type and the given descriptor are group types. e.g.
+//
+// message Foo {
+// message Bar {
+// message NestedBar {}
+// }
+// group Baz = 1 {
+// group NestedBazGroup = 2 {
+// message Quz {
+// message NestedQuz {}
+// }
+// }
+// message NestedBaz {}
+// }
+// }
+//
+// In this case, Bar, Quz and NestedBaz will be added into the nested types.
+// Since free field numbers of group types will not be printed, this makes sure
+// the nested message types in groups will not be dropped. The nested_messages
+// parameter will contain the direct children (when groups are ignored in the
+// tree) of the given descriptor for the caller to traverse. The declaration
+// order of the nested messages is also preserved.
+typedef pair<int, int> FieldRange;
+void GatherOccupiedFieldRanges(const Descriptor* descriptor,
+ set<FieldRange>* ranges,
+ vector<const Descriptor*>* nested_messages) {
+ set<const Descriptor*> groups;
+ for (int i = 0; i < descriptor->field_count(); ++i) {
+ const FieldDescriptor* fd = descriptor->field(i);
+ ranges->insert(FieldRange(fd->number(), fd->number() + 1));
+ if (fd->type() == FieldDescriptor::TYPE_GROUP) {
+ groups.insert(fd->message_type());
+ }
+ }
+ for (int i = 0; i < descriptor->extension_range_count(); ++i) {
+ ranges->insert(FieldRange(descriptor->extension_range(i)->start,
+ descriptor->extension_range(i)->end));
+ }
+ for (int i = 0; i < descriptor->reserved_range_count(); ++i) {
+ ranges->insert(FieldRange(descriptor->reserved_range(i)->start,
+ descriptor->reserved_range(i)->end));
+ }
+ // Handle the nested messages/groups in declaration order to make it
+ // post-order strict.
+ for (int i = 0; i < descriptor->nested_type_count(); ++i) {
+ const Descriptor* nested_desc = descriptor->nested_type(i);
+ if (groups.find(nested_desc) != groups.end()) {
+ GatherOccupiedFieldRanges(nested_desc, ranges, nested_messages);
+ } else {
+ nested_messages->push_back(nested_desc);
+ }
+ }
+}
+
+// Utility function for PrintFreeFieldNumbers.
+// Actually prints the formatted free field numbers for given message name and
+// occupied ranges.
+void FormatFreeFieldNumbers(const string& name,
+ const set<FieldRange>& ranges) {
+ string output;
+ StringAppendF(&output, "%-35s free:", name.c_str());
+ int next_free_number = 1;
+ for (set<FieldRange>::const_iterator i = ranges.begin();
+ i != ranges.end(); ++i) {
+ // This happens when groups re-use parent field numbers, in which
+ // case we skip the FieldRange entirely.
+ if (next_free_number >= i->second) continue;
+
+ if (next_free_number < i->first) {
+ if (next_free_number + 1 == i->first) {
+ // Singleton
+ StringAppendF(&output, " %d", next_free_number);
+ } else {
+ // Range
+ StringAppendF(&output, " %d-%d", next_free_number, i->first - 1);
+ }
+ }
+ next_free_number = i->second;
+ }
+ if (next_free_number <= FieldDescriptor::kMaxNumber) {
+ StringAppendF(&output, " %d-INF", next_free_number);
+ }
+ std::cout << output << std::endl;
+}
+
+} // namespace
+
+void CommandLineInterface::PrintFreeFieldNumbers(
+ const Descriptor* descriptor) {
+ set<FieldRange> ranges;
+ vector<const Descriptor*> nested_messages;
+ GatherOccupiedFieldRanges(descriptor, &ranges, &nested_messages);
+
+ for (int i = 0; i < nested_messages.size(); ++i) {
+ PrintFreeFieldNumbers(nested_messages[i]);
+ }
+ FormatFreeFieldNumbers(descriptor->full_name(), ranges);
+}
+
+
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.h
new file mode 100644
index 0000000000..d1377666d3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface.h
@@ -0,0 +1,394 @@
+// 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.
+//
+// Implements the Protocol Compiler front-end such that it may be reused by
+// custom compilers written to support other languages.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_COMMAND_LINE_INTERFACE_H__
+#define GOOGLE_PROTOBUF_COMPILER_COMMAND_LINE_INTERFACE_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/hash.h>
+#include <string>
+#include <vector>
+#include <map>
+#include <set>
+#include <utility>
+
+namespace google {
+namespace protobuf {
+
+class Descriptor; // descriptor.h
+class DescriptorPool; // descriptor.h
+class FileDescriptor; // descriptor.h
+class FileDescriptorProto; // descriptor.pb.h
+template<typename T> class RepeatedPtrField; // repeated_field.h
+
+namespace compiler {
+
+class CodeGenerator; // code_generator.h
+class GeneratorContext; // code_generator.h
+class DiskSourceTree; // importer.h
+
+// This class implements the command-line interface to the protocol compiler.
+// It is designed to make it very easy to create a custom protocol compiler
+// supporting the languages of your choice. For example, if you wanted to
+// create a custom protocol compiler binary which includes both the regular
+// C++ support plus support for your own custom output "Foo", you would
+// write a class "FooGenerator" which implements the CodeGenerator interface,
+// then write a main() procedure like this:
+//
+// int main(int argc, char* argv[]) {
+// google::protobuf::compiler::CommandLineInterface cli;
+//
+// // Support generation of C++ source and headers.
+// google::protobuf::compiler::cpp::CppGenerator cpp_generator;
+// cli.RegisterGenerator("--cpp_out", &cpp_generator,
+// "Generate C++ source and header.");
+//
+// // Support generation of Foo code.
+// FooGenerator foo_generator;
+// cli.RegisterGenerator("--foo_out", &foo_generator,
+// "Generate Foo file.");
+//
+// return cli.Run(argc, argv);
+// }
+//
+// The compiler is invoked with syntax like:
+// protoc --cpp_out=outdir --foo_out=outdir --proto_path=src src/foo.proto
+//
+// For a full description of the command-line syntax, invoke it with --help.
+class LIBPROTOC_EXPORT CommandLineInterface {
+ public:
+ CommandLineInterface();
+ ~CommandLineInterface();
+
+ // Register a code generator for a language.
+ //
+ // Parameters:
+ // * flag_name: The command-line flag used to specify an output file of
+ // this type. The name must start with a '-'. If the name is longer
+ // than one letter, it must start with two '-'s.
+ // * generator: The CodeGenerator which will be called to generate files
+ // of this type.
+ // * help_text: Text describing this flag in the --help output.
+ //
+ // Some generators accept extra parameters. You can specify this parameter
+ // on the command-line by placing it before the output directory, separated
+ // by a colon:
+ // protoc --foo_out=enable_bar:outdir
+ // The text before the colon is passed to CodeGenerator::Generate() as the
+ // "parameter".
+ void RegisterGenerator(const string& flag_name,
+ CodeGenerator* generator,
+ const string& help_text);
+
+ // Register a code generator for a language.
+ // Besides flag_name you can specify another option_flag_name that could be
+ // used to pass extra parameters to the registered code generator.
+ // Suppose you have registered a generator by calling:
+ // command_line_interface.RegisterGenerator("--foo_out", "--foo_opt", ...)
+ // Then you could invoke the compiler with a command like:
+ // protoc --foo_out=enable_bar:outdir --foo_opt=enable_baz
+ // This will pass "enable_bar,enable_baz" as the parameter to the generator.
+ void RegisterGenerator(const string& flag_name,
+ const string& option_flag_name,
+ CodeGenerator* generator,
+ const string& help_text);
+
+ // Enables "plugins". In this mode, if a command-line flag ends with "_out"
+ // but does not match any registered generator, the compiler will attempt to
+ // find a "plugin" to implement the generator. Plugins are just executables.
+ // They should live somewhere in the PATH.
+ //
+ // The compiler determines the executable name to search for by concatenating
+ // exe_name_prefix with the unrecognized flag name, removing "_out". So, for
+ // example, if exe_name_prefix is "protoc-" and you pass the flag --foo_out,
+ // the compiler will try to run the program "protoc-foo".
+ //
+ // The plugin program should implement the following usage:
+ // plugin [--out=OUTDIR] [--parameter=PARAMETER] PROTO_FILES < DESCRIPTORS
+ // --out indicates the output directory (as passed to the --foo_out
+ // parameter); if omitted, the current directory should be used. --parameter
+ // gives the generator parameter, if any was provided. The PROTO_FILES list
+ // the .proto files which were given on the compiler command-line; these are
+ // the files for which the plugin is expected to generate output code.
+ // Finally, DESCRIPTORS is an encoded FileDescriptorSet (as defined in
+ // descriptor.proto). This is piped to the plugin's stdin. The set will
+ // include descriptors for all the files listed in PROTO_FILES as well as
+ // all files that they import. The plugin MUST NOT attempt to read the
+ // PROTO_FILES directly -- it must use the FileDescriptorSet.
+ //
+ // The plugin should generate whatever files are necessary, as code generators
+ // normally do. It should write the names of all files it generates to
+ // stdout. The names should be relative to the output directory, NOT absolute
+ // names or relative to the current directory. If any errors occur, error
+ // messages should be written to stderr. If an error is fatal, the plugin
+ // should exit with a non-zero exit code.
+ void AllowPlugins(const string& exe_name_prefix);
+
+ // Run the Protocol Compiler with the given command-line parameters.
+ // Returns the error code which should be returned by main().
+ //
+ // It may not be safe to call Run() in a multi-threaded environment because
+ // it calls strerror(). I'm not sure why you'd want to do this anyway.
+ int Run(int argc, const char* const argv[]);
+
+ // Call SetInputsAreCwdRelative(true) if the input files given on the command
+ // line should be interpreted relative to the proto import path specified
+ // using --proto_path or -I flags. Otherwise, input file names will be
+ // interpreted relative to the current working directory (or as absolute
+ // paths if they start with '/'), though they must still reside inside
+ // a directory given by --proto_path or the compiler will fail. The latter
+ // mode is generally more intuitive and easier to use, especially e.g. when
+ // defining implicit rules in Makefiles.
+ void SetInputsAreProtoPathRelative(bool enable) {
+ inputs_are_proto_path_relative_ = enable;
+ }
+
+ // Provides some text which will be printed when the --version flag is
+ // used. The version of libprotoc will also be printed on the next line
+ // after this text.
+ void SetVersionInfo(const string& text) {
+ version_info_ = text;
+ }
+
+
+ private:
+ // -----------------------------------------------------------------
+
+ class ErrorPrinter;
+ class GeneratorContextImpl;
+ class MemoryOutputStream;
+ typedef hash_map<string, GeneratorContextImpl*> GeneratorContextMap;
+
+ // Clear state from previous Run().
+ void Clear();
+
+ // Remaps each file in input_files_ so that it is relative to one of the
+ // directories in proto_path_. Returns false if an error occurred. This
+ // is only used if inputs_are_proto_path_relative_ is false.
+ bool MakeInputsBeProtoPathRelative(
+ DiskSourceTree* source_tree);
+
+ // Return status for ParseArguments() and InterpretArgument().
+ enum ParseArgumentStatus {
+ PARSE_ARGUMENT_DONE_AND_CONTINUE,
+ PARSE_ARGUMENT_DONE_AND_EXIT,
+ PARSE_ARGUMENT_FAIL
+ };
+
+ // Parse all command-line arguments.
+ ParseArgumentStatus ParseArguments(int argc, const char* const argv[]);
+
+
+ // Parses a command-line argument into a name/value pair. Returns
+ // true if the next argument in the argv should be used as the value,
+ // false otherwise.
+ //
+ // Examples:
+ // "-Isrc/protos" ->
+ // name = "-I", value = "src/protos"
+ // "--cpp_out=src/foo.pb2.cc" ->
+ // name = "--cpp_out", value = "src/foo.pb2.cc"
+ // "foo.proto" ->
+ // name = "", value = "foo.proto"
+ bool ParseArgument(const char* arg, string* name, string* value);
+
+ // Interprets arguments parsed with ParseArgument.
+ ParseArgumentStatus InterpretArgument(const string& name,
+ const string& value);
+
+ // Print the --help text to stderr.
+ void PrintHelpText();
+
+ // Generate the given output file from the given input.
+ struct OutputDirective; // see below
+ bool GenerateOutput(const vector<const FileDescriptor*>& parsed_files,
+ const OutputDirective& output_directive,
+ GeneratorContext* generator_context);
+ bool GeneratePluginOutput(const vector<const FileDescriptor*>& parsed_files,
+ const string& plugin_name,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error);
+
+ // Implements --encode and --decode.
+ bool EncodeOrDecode(const DescriptorPool* pool);
+
+ // Implements the --descriptor_set_out option.
+ bool WriteDescriptorSet(const vector<const FileDescriptor*> parsed_files);
+
+ // Implements the --dependency_out option
+ bool GenerateDependencyManifestFile(
+ const vector<const FileDescriptor*>& parsed_files,
+ const GeneratorContextMap& output_directories,
+ DiskSourceTree* source_tree);
+
+ // Get all transitive dependencies of the given file (including the file
+ // itself), adding them to the given list of FileDescriptorProtos. The
+ // protos will be ordered such that every file is listed before any file that
+ // depends on it, so that you can call DescriptorPool::BuildFile() on them
+ // in order. Any files in *already_seen will not be added, and each file
+ // added will be inserted into *already_seen. If include_source_code_info is
+ // true then include the source code information in the FileDescriptorProtos.
+ // If include_json_name is true, populate the json_name field of
+ // FieldDescriptorProto for all fields.
+ static void GetTransitiveDependencies(
+ const FileDescriptor* file,
+ bool include_json_name,
+ bool include_source_code_info,
+ set<const FileDescriptor*>* already_seen,
+ RepeatedPtrField<FileDescriptorProto>* output);
+
+ // Implements the --print_free_field_numbers. This function prints free field
+ // numbers into stdout for the message and it's nested message types in
+ // post-order, i.e. nested types first. Printed range are left-right
+ // inclusive, i.e. [a, b].
+ //
+ // Groups:
+ // For historical reasons, groups are considered to share the same
+ // field number space with the parent message, thus it will not print free
+ // field numbers for groups. The field numbers used in the groups are
+ // excluded in the free field numbers of the parent message.
+ //
+ // Extension Ranges:
+ // Extension ranges are considered ocuppied field numbers and they will not be
+ // listed as free numbers in the output.
+ void PrintFreeFieldNumbers(const Descriptor* descriptor);
+
+ // -----------------------------------------------------------------
+
+ // The name of the executable as invoked (i.e. argv[0]).
+ string executable_name_;
+
+ // Version info set with SetVersionInfo().
+ string version_info_;
+
+ // Registered generators.
+ struct GeneratorInfo {
+ string flag_name;
+ string option_flag_name;
+ CodeGenerator* generator;
+ string help_text;
+ };
+ typedef map<string, GeneratorInfo> GeneratorMap;
+ GeneratorMap generators_by_flag_name_;
+ GeneratorMap generators_by_option_name_;
+ // A map from generator names to the parameters specified using the option
+ // flag. For example, if the user invokes the compiler with:
+ // protoc --foo_out=outputdir --foo_opt=enable_bar ...
+ // Then there will be an entry ("--foo_out", "enable_bar") in this map.
+ map<string, string> generator_parameters_;
+
+ // See AllowPlugins(). If this is empty, plugins aren't allowed.
+ string plugin_prefix_;
+
+ // Maps specific plugin names to files. When executing a plugin, this map
+ // is searched first to find the plugin executable. If not found here, the
+ // PATH (or other OS-specific search strategy) is searched.
+ map<string, string> plugins_;
+
+ // Stuff parsed from command line.
+ enum Mode {
+ MODE_COMPILE, // Normal mode: parse .proto files and compile them.
+ MODE_ENCODE, // --encode: read text from stdin, write binary to stdout.
+ MODE_DECODE, // --decode: read binary from stdin, write text to stdout.
+ MODE_PRINT, // Print mode: print info of the given .proto files and exit.
+ };
+
+ Mode mode_;
+
+ enum PrintMode {
+ PRINT_NONE, // Not in MODE_PRINT
+ PRINT_FREE_FIELDS, // --print_free_fields
+ };
+
+ PrintMode print_mode_;
+
+ enum ErrorFormat {
+ ERROR_FORMAT_GCC, // GCC error output format (default).
+ ERROR_FORMAT_MSVS // Visual Studio output (--error_format=msvs).
+ };
+
+ ErrorFormat error_format_;
+
+ vector<pair<string, string> > proto_path_; // Search path for proto files.
+ vector<string> input_files_; // Names of the input proto files.
+
+ // output_directives_ lists all the files we are supposed to output and what
+ // generator to use for each.
+ struct OutputDirective {
+ string name; // E.g. "--foo_out"
+ CodeGenerator* generator; // NULL for plugins
+ string parameter;
+ string output_location;
+ };
+ vector<OutputDirective> output_directives_;
+
+ // When using --encode or --decode, this names the type we are encoding or
+ // decoding. (Empty string indicates --decode_raw.)
+ string codec_type_;
+
+ // If --descriptor_set_out was given, this is the filename to which the
+ // FileDescriptorSet should be written. Otherwise, empty.
+ string descriptor_set_name_;
+
+ // If --dependency_out was given, this is the path to the file where the
+ // dependency file will be written. Otherwise, empty.
+ string dependency_out_name_;
+
+ // True if --include_imports was given, meaning that we should
+ // write all transitive dependencies to the DescriptorSet. Otherwise, only
+ // the .proto files listed on the command-line are added.
+ bool imports_in_descriptor_set_;
+
+ // True if --include_source_info was given, meaning that we should not strip
+ // SourceCodeInfo from the DescriptorSet.
+ bool source_info_in_descriptor_set_;
+
+ // Was the --disallow_services flag used?
+ bool disallow_services_;
+
+ // See SetInputsAreProtoPathRelative().
+ bool inputs_are_proto_path_relative_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CommandLineInterface);
+};
+
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_COMMAND_LINE_INTERFACE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface_unittest.cc
new file mode 100644
index 0000000000..0ebf9b6a2c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/command_line_interface_unittest.cc
@@ -0,0 +1,1849 @@
+// 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.
+
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#ifdef _MSC_VER
+#include <io.h>
+#else
+#include <unistd.h>
+#endif
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/compiler/mock_code_generator.h>
+#include <google/protobuf/compiler/subprocess.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+// Disable the whole test when we use tcmalloc for "draconian" heap checks, in
+// which case tcmalloc will print warnings that fail the plugin tests.
+#if !GOOGLE_PROTOBUF_HEAP_CHECK_DRACONIAN
+
+#if defined(_WIN32)
+#ifndef STDIN_FILENO
+#define STDIN_FILENO 0
+#endif
+#ifndef STDOUT_FILENO
+#define STDOUT_FILENO 1
+#endif
+#ifndef F_OK
+#define F_OK 00 // not defined by MSVC for whatever reason
+#endif
+#endif
+
+namespace {
+
+bool FileExists(const string& path) {
+ return File::Exists(path);
+}
+
+class CommandLineInterfaceTest : public testing::Test {
+ protected:
+ virtual void SetUp();
+ virtual void TearDown();
+
+ // Runs the CommandLineInterface with the given command line. The
+ // command is automatically split on spaces, and the string "$tmpdir"
+ // is replaced with TestTempDir().
+ void Run(const string& command);
+
+ // -----------------------------------------------------------------
+ // Methods to set up the test (called before Run()).
+
+ class NullCodeGenerator;
+
+ // Normally plugins are allowed for all tests. Call this to explicitly
+ // disable them.
+ void DisallowPlugins() { disallow_plugins_ = true; }
+
+ // Create a temp file within temp_directory_ with the given name.
+ // The containing directory is also created if necessary.
+ void CreateTempFile(const string& name, const string& contents);
+
+ // Create a subdirectory within temp_directory_.
+ void CreateTempDir(const string& name);
+
+#ifdef PROTOBUF_OPENSOURCE
+ // Change working directory to temp directory.
+ void SwitchToTempDirectory() {
+ File::ChangeWorkingDirectory(temp_directory_);
+ }
+#else // !PROTOBUF_OPENSOURCE
+ // TODO(teboring): Figure out how to change and get working directory in
+ // google3.
+#endif // !PROTOBUF_OPENSOURCE
+
+ void SetInputsAreProtoPathRelative(bool enable) {
+ cli_.SetInputsAreProtoPathRelative(enable);
+ }
+
+ // -----------------------------------------------------------------
+ // Methods to check the test results (called after Run()).
+
+ // Checks that no text was written to stderr during Run(), and Run()
+ // returned 0.
+ void ExpectNoErrors();
+
+ // Checks that Run() returned non-zero and the stderr output is exactly
+ // the text given. expected_test may contain references to "$tmpdir",
+ // which will be replaced by the temporary directory path.
+ void ExpectErrorText(const string& expected_text);
+
+ // Checks that Run() returned non-zero and the stderr contains the given
+ // substring.
+ void ExpectErrorSubstring(const string& expected_substring);
+
+ // Like ExpectErrorSubstring, but checks that Run() returned zero.
+ void ExpectErrorSubstringWithZeroReturnCode(
+ const string& expected_substring);
+
+ // Checks that the captured stdout is the same as the expected_text.
+ void ExpectCapturedStdout(const string& expected_text);
+
+ // Returns true if ExpectErrorSubstring(expected_substring) would pass, but
+ // does not fail otherwise.
+ bool HasAlternateErrorSubstring(const string& expected_substring);
+
+ // Checks that MockCodeGenerator::Generate() was called in the given
+ // context (or the generator in test_plugin.cc, which produces the same
+ // output). That is, this tests if the generator with the given name
+ // was called with the given parameter and proto file and produced the
+ // given output file. This is checked by reading the output file and
+ // checking that it contains the content that MockCodeGenerator would
+ // generate given these inputs. message_name is the name of the first
+ // message that appeared in the proto file; this is just to make extra
+ // sure that the correct file was parsed.
+ void ExpectGenerated(const string& generator_name,
+ const string& parameter,
+ const string& proto_name,
+ const string& message_name);
+ void ExpectGenerated(const string& generator_name,
+ const string& parameter,
+ const string& proto_name,
+ const string& message_name,
+ const string& output_directory);
+ void ExpectGeneratedWithMultipleInputs(const string& generator_name,
+ const string& all_proto_names,
+ const string& proto_name,
+ const string& message_name);
+ void ExpectGeneratedWithInsertions(const string& generator_name,
+ const string& parameter,
+ const string& insertions,
+ const string& proto_name,
+ const string& message_name);
+
+ void ExpectNullCodeGeneratorCalled(const string& parameter);
+
+ void ReadDescriptorSet(const string& filename,
+ FileDescriptorSet* descriptor_set);
+
+ void ExpectFileContent(const string& filename,
+ const string& content);
+
+ private:
+ // The object we are testing.
+ CommandLineInterface cli_;
+
+ // Was DisallowPlugins() called?
+ bool disallow_plugins_;
+
+ // We create a directory within TestTempDir() in order to add extra
+ // protection against accidentally deleting user files (since we recursively
+ // delete this directory during the test). This is the full path of that
+ // directory.
+ string temp_directory_;
+
+ // The result of Run().
+ int return_code_;
+
+ // The captured stderr output.
+ string error_text_;
+
+ // The captured stdout.
+ string captured_stdout_;
+
+ // Pointers which need to be deleted later.
+ vector<CodeGenerator*> mock_generators_to_delete_;
+
+ NullCodeGenerator* null_generator_;
+};
+
+class CommandLineInterfaceTest::NullCodeGenerator : public CodeGenerator {
+ public:
+ NullCodeGenerator() : called_(false) {}
+ ~NullCodeGenerator() {}
+
+ mutable bool called_;
+ mutable string parameter_;
+
+ // implements CodeGenerator ----------------------------------------
+ bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ called_ = true;
+ parameter_ = parameter;
+ return true;
+ }
+};
+
+// ===================================================================
+
+void CommandLineInterfaceTest::SetUp() {
+ // Most of these tests were written before this option was added, so we
+ // run with the option on (which used to be the only way) except in certain
+ // tests where we turn it off.
+ cli_.SetInputsAreProtoPathRelative(true);
+
+ temp_directory_ = TestTempDir() + "/proto2_cli_test_temp";
+
+ // If the temp directory already exists, it must be left over from a
+ // previous run. Delete it.
+ if (FileExists(temp_directory_)) {
+ File::DeleteRecursively(temp_directory_, NULL, NULL);
+ }
+
+ // Create the temp directory.
+ GOOGLE_CHECK_OK(File::CreateDir(temp_directory_, 0777));
+
+ // Register generators.
+ CodeGenerator* generator = new MockCodeGenerator("test_generator");
+ mock_generators_to_delete_.push_back(generator);
+ cli_.RegisterGenerator("--test_out", "--test_opt", generator, "Test output.");
+ cli_.RegisterGenerator("-t", generator, "Test output.");
+
+ generator = new MockCodeGenerator("alt_generator");
+ mock_generators_to_delete_.push_back(generator);
+ cli_.RegisterGenerator("--alt_out", generator, "Alt output.");
+
+ generator = null_generator_ = new NullCodeGenerator();
+ mock_generators_to_delete_.push_back(generator);
+ cli_.RegisterGenerator("--null_out", generator, "Null output.");
+
+ disallow_plugins_ = false;
+}
+
+void CommandLineInterfaceTest::TearDown() {
+ // Delete the temp directory.
+ if (FileExists(temp_directory_)) {
+ File::DeleteRecursively(temp_directory_, NULL, NULL);
+ }
+
+ // Delete all the MockCodeGenerators.
+ for (int i = 0; i < mock_generators_to_delete_.size(); i++) {
+ delete mock_generators_to_delete_[i];
+ }
+ mock_generators_to_delete_.clear();
+}
+
+void CommandLineInterfaceTest::Run(const string& command) {
+ vector<string> args = Split(command, " ", true);
+
+ if (!disallow_plugins_) {
+ cli_.AllowPlugins("prefix-");
+#ifndef GOOGLE_THIRD_PARTY_PROTOBUF
+ string plugin_path;
+#ifdef GOOGLE_PROTOBUF_TEST_PLUGIN_PATH
+ plugin_path = GOOGLE_PROTOBUF_TEST_PLUGIN_PATH;
+#else
+ const char* possible_paths[] = {
+ // When building with shared libraries, libtool hides the real executable
+ // in .libs and puts a fake wrapper in the current directory.
+ // Unfortunately, due to an apparent bug on Cygwin/MinGW, if one program
+ // wrapped in this way (e.g. protobuf-tests.exe) tries to execute another
+ // program wrapped in this way (e.g. test_plugin.exe), the latter fails
+ // with error code 127 and no explanation message. Presumably the problem
+ // is that the wrapper for protobuf-tests.exe set some environment
+ // variables that confuse the wrapper for test_plugin.exe. Luckily, it
+ // turns out that if we simply invoke the wrapped test_plugin.exe
+ // directly, it works -- I guess the environment variables set by the
+ // protobuf-tests.exe wrapper happen to be correct for it too. So we do
+ // that.
+ ".libs/test_plugin.exe", // Win32 w/autotool (Cygwin / MinGW)
+ "test_plugin.exe", // Other Win32 (MSVC)
+ "test_plugin", // Unix
+ };
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(possible_paths); i++) {
+ if (access(possible_paths[i], F_OK) == 0) {
+ plugin_path = possible_paths[i];
+ break;
+ }
+ }
+#endif
+
+ if (plugin_path.empty()) {
+#else
+ string plugin_path = "third_party/protobuf/test_plugin";
+
+ if (access(plugin_path.c_str(), F_OK) != 0) {
+#endif // GOOGLE_THIRD_PARTY_PROTOBUF
+ GOOGLE_LOG(ERROR)
+ << "Plugin executable not found. Plugin tests are likely to fail.";
+ } else {
+ args.push_back("--plugin=prefix-gen-plug=" + plugin_path);
+ }
+ }
+
+ google::protobuf::scoped_array<const char * > argv(new const char* [args.size()]);
+
+ for (int i = 0; i < args.size(); i++) {
+ args[i] = StringReplace(args[i], "$tmpdir", temp_directory_, true);
+ argv[i] = args[i].c_str();
+ }
+
+ // TODO(jieluo): Cygwin doesn't work well if we try to capture stderr and
+ // stdout at the same time. Need to figure out why and add this capture back
+ // for Cygwin.
+#if !defined(__CYGWIN__)
+ CaptureTestStdout();
+#endif
+ CaptureTestStderr();
+
+ return_code_ = cli_.Run(args.size(), argv.get());
+
+ error_text_ = GetCapturedTestStderr();
+#if !defined(__CYGWIN__)
+ captured_stdout_ = GetCapturedTestStdout();
+#endif
+}
+
+// -------------------------------------------------------------------
+
+void CommandLineInterfaceTest::CreateTempFile(
+ const string& name,
+ const string& contents) {
+ // Create parent directory, if necessary.
+ string::size_type slash_pos = name.find_last_of('/');
+ if (slash_pos != string::npos) {
+ string dir = name.substr(0, slash_pos);
+ if (!FileExists(temp_directory_ + "/" + dir)) {
+ GOOGLE_CHECK_OK(File::RecursivelyCreateDir(temp_directory_ + "/" + dir,
+ 0777));
+ }
+ }
+
+ // Write file.
+ string full_name = temp_directory_ + "/" + name;
+ GOOGLE_CHECK_OK(File::SetContents(
+ full_name, StringReplace(contents, "$tmpdir", temp_directory_, true),
+ true));
+}
+
+void CommandLineInterfaceTest::CreateTempDir(const string& name) {
+ GOOGLE_CHECK_OK(File::RecursivelyCreateDir(temp_directory_ + "/" + name,
+ 0777));
+}
+
+// -------------------------------------------------------------------
+
+void CommandLineInterfaceTest::ExpectNoErrors() {
+ EXPECT_EQ(0, return_code_);
+ EXPECT_EQ("", error_text_);
+}
+
+void CommandLineInterfaceTest::ExpectErrorText(const string& expected_text) {
+ EXPECT_NE(0, return_code_);
+ EXPECT_EQ(StringReplace(expected_text, "$tmpdir", temp_directory_, true),
+ error_text_);
+}
+
+void CommandLineInterfaceTest::ExpectErrorSubstring(
+ const string& expected_substring) {
+ EXPECT_NE(0, return_code_);
+ EXPECT_PRED_FORMAT2(testing::IsSubstring, expected_substring, error_text_);
+}
+
+void CommandLineInterfaceTest::ExpectErrorSubstringWithZeroReturnCode(
+ const string& expected_substring) {
+ EXPECT_EQ(0, return_code_);
+ EXPECT_PRED_FORMAT2(testing::IsSubstring, expected_substring, error_text_);
+}
+
+bool CommandLineInterfaceTest::HasAlternateErrorSubstring(
+ const string& expected_substring) {
+ EXPECT_NE(0, return_code_);
+ return error_text_.find(expected_substring) != string::npos;
+}
+
+void CommandLineInterfaceTest::ExpectGenerated(
+ const string& generator_name,
+ const string& parameter,
+ const string& proto_name,
+ const string& message_name) {
+ MockCodeGenerator::ExpectGenerated(
+ generator_name, parameter, "", proto_name, message_name, proto_name,
+ temp_directory_);
+}
+
+void CommandLineInterfaceTest::ExpectGenerated(
+ const string& generator_name,
+ const string& parameter,
+ const string& proto_name,
+ const string& message_name,
+ const string& output_directory) {
+ MockCodeGenerator::ExpectGenerated(
+ generator_name, parameter, "", proto_name, message_name, proto_name,
+ temp_directory_ + "/" + output_directory);
+}
+
+void CommandLineInterfaceTest::ExpectGeneratedWithMultipleInputs(
+ const string& generator_name,
+ const string& all_proto_names,
+ const string& proto_name,
+ const string& message_name) {
+ MockCodeGenerator::ExpectGenerated(
+ generator_name, "", "", proto_name, message_name,
+ all_proto_names,
+ temp_directory_);
+}
+
+void CommandLineInterfaceTest::ExpectGeneratedWithInsertions(
+ const string& generator_name,
+ const string& parameter,
+ const string& insertions,
+ const string& proto_name,
+ const string& message_name) {
+ MockCodeGenerator::ExpectGenerated(
+ generator_name, parameter, insertions, proto_name, message_name,
+ proto_name, temp_directory_);
+}
+
+void CommandLineInterfaceTest::ExpectNullCodeGeneratorCalled(
+ const string& parameter) {
+ EXPECT_TRUE(null_generator_->called_);
+ EXPECT_EQ(parameter, null_generator_->parameter_);
+}
+
+void CommandLineInterfaceTest::ReadDescriptorSet(
+ const string& filename, FileDescriptorSet* descriptor_set) {
+ string path = temp_directory_ + "/" + filename;
+ string file_contents;
+ GOOGLE_CHECK_OK(File::GetContents(path, &file_contents, true));
+
+ if (!descriptor_set->ParseFromString(file_contents)) {
+ FAIL() << "Could not parse file contents: " << path;
+ }
+}
+
+void CommandLineInterfaceTest::ExpectCapturedStdout(
+ const string& expected_text) {
+ EXPECT_EQ(expected_text, captured_stdout_);
+}
+
+
+void CommandLineInterfaceTest::ExpectFileContent(
+ const string& filename, const string& content) {
+ string path = temp_directory_ + "/" + filename;
+ string file_contents;
+ GOOGLE_CHECK_OK(File::GetContents(path, &file_contents, true));
+
+ EXPECT_EQ(StringReplace(content, "$tmpdir", temp_directory_, true),
+ file_contents);
+}
+
+// ===================================================================
+
+TEST_F(CommandLineInterfaceTest, BasicOutput) {
+ // Test that the common case works.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, BasicPlugin) {
+ // Test that basic plugins work.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --plug_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_plugin", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorAndPlugin) {
+ // Invoke a generator and a plugin at the same time.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir --plug_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+ ExpectGenerated("test_plugin", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, MultipleInputs) {
+ // Test parsing multiple input files.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "message Bar {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir --plug_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto bar.proto");
+
+ ExpectNoErrors();
+ ExpectGeneratedWithMultipleInputs("test_generator", "foo.proto,bar.proto",
+ "foo.proto", "Foo");
+ ExpectGeneratedWithMultipleInputs("test_generator", "foo.proto,bar.proto",
+ "bar.proto", "Bar");
+ ExpectGeneratedWithMultipleInputs("test_plugin", "foo.proto,bar.proto",
+ "foo.proto", "Foo");
+ ExpectGeneratedWithMultipleInputs("test_plugin", "foo.proto,bar.proto",
+ "bar.proto", "Bar");
+}
+
+TEST_F(CommandLineInterfaceTest, MultipleInputsWithImport) {
+ // Test parsing multiple input files with an import of a separate file.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"baz.proto\";\n"
+ "message Bar {\n"
+ " optional Baz a = 1;\n"
+ "}\n");
+ CreateTempFile("baz.proto",
+ "syntax = \"proto2\";\n"
+ "message Baz {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir --plug_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto bar.proto");
+
+ ExpectNoErrors();
+ ExpectGeneratedWithMultipleInputs("test_generator", "foo.proto,bar.proto",
+ "foo.proto", "Foo");
+ ExpectGeneratedWithMultipleInputs("test_generator", "foo.proto,bar.proto",
+ "bar.proto", "Bar");
+ ExpectGeneratedWithMultipleInputs("test_plugin", "foo.proto,bar.proto",
+ "foo.proto", "Foo");
+ ExpectGeneratedWithMultipleInputs("test_plugin", "foo.proto,bar.proto",
+ "bar.proto", "Bar");
+}
+
+TEST_F(CommandLineInterfaceTest, CreateDirectory) {
+ // Test that when we output to a sub-directory, it is created.
+
+ CreateTempFile("bar/baz/foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempDir("out");
+ CreateTempDir("plugout");
+
+ Run("protocol_compiler --test_out=$tmpdir/out --plug_out=$tmpdir/plugout "
+ "--proto_path=$tmpdir bar/baz/foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "bar/baz/foo.proto", "Foo", "out");
+ ExpectGenerated("test_plugin", "", "bar/baz/foo.proto", "Foo", "plugout");
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorParameters) {
+ // Test that generator parameters are correctly parsed from the command line.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=TestParameter:$tmpdir "
+ "--plug_out=TestPluginParameter:$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "TestParameter", "foo.proto", "Foo");
+ ExpectGenerated("test_plugin", "TestPluginParameter", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, ExtraGeneratorParameters) {
+ // Test that generator parameters specified with the option flag are
+ // correctly passed to the code generator.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ // Create the "a" and "b" sub-directories.
+ CreateTempDir("a");
+ CreateTempDir("b");
+
+ Run("protocol_compiler "
+ "--test_opt=foo1 "
+ "--test_out=bar:$tmpdir/a "
+ "--test_opt=foo2 "
+ "--test_out=baz:$tmpdir/b "
+ "--test_opt=foo3 "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated(
+ "test_generator", "bar,foo1,foo2,foo3", "foo.proto", "Foo", "a");
+ ExpectGenerated(
+ "test_generator", "baz,foo1,foo2,foo3", "foo.proto", "Foo", "b");
+}
+
+TEST_F(CommandLineInterfaceTest, Insert) {
+ // Test running a generator that inserts code into another's output.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler "
+ "--test_out=TestParameter:$tmpdir "
+ "--plug_out=TestPluginParameter:$tmpdir "
+ "--test_out=insert=test_generator,test_plugin:$tmpdir "
+ "--plug_out=insert=test_generator,test_plugin:$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGeneratedWithInsertions(
+ "test_generator", "TestParameter", "test_generator,test_plugin",
+ "foo.proto", "Foo");
+ ExpectGeneratedWithInsertions(
+ "test_plugin", "TestPluginParameter", "test_generator,test_plugin",
+ "foo.proto", "Foo");
+}
+
+#if defined(_WIN32)
+
+TEST_F(CommandLineInterfaceTest, WindowsOutputPath) {
+ // Test that the output path can be a Windows-style path.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n");
+
+ Run("protocol_compiler --null_out=C:\\ "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectNullCodeGeneratorCalled("");
+}
+
+TEST_F(CommandLineInterfaceTest, WindowsOutputPathAndParameter) {
+ // Test that we can have a windows-style output path and a parameter.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n");
+
+ Run("protocol_compiler --null_out=bar:C:\\ "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectNullCodeGeneratorCalled("bar");
+}
+
+TEST_F(CommandLineInterfaceTest, TrailingBackslash) {
+ // Test that the directories can end in backslashes. Some users claim this
+ // doesn't work on their system.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir\\ "
+ "--proto_path=$tmpdir\\ foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+#endif // defined(_WIN32) || defined(__CYGWIN__)
+
+TEST_F(CommandLineInterfaceTest, PathLookup) {
+ // Test that specifying multiple directories in the proto search path works.
+
+ CreateTempFile("b/bar.proto",
+ "syntax = \"proto2\";\n"
+ "message Bar {}\n");
+ CreateTempFile("a/foo.proto",
+ "syntax = \"proto2\";\n"
+ "import \"bar.proto\";\n"
+ "message Foo {\n"
+ " optional Bar a = 1;\n"
+ "}\n");
+ CreateTempFile("b/foo.proto", "this should not be parsed\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir/a --proto_path=$tmpdir/b foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, ColonDelimitedPath) {
+ // Same as PathLookup, but we provide the proto_path in a single flag.
+
+ CreateTempFile("b/bar.proto",
+ "syntax = \"proto2\";\n"
+ "message Bar {}\n");
+ CreateTempFile("a/foo.proto",
+ "syntax = \"proto2\";\n"
+ "import \"bar.proto\";\n"
+ "message Foo {\n"
+ " optional Bar a = 1;\n"
+ "}\n");
+ CreateTempFile("b/foo.proto", "this should not be parsed\n");
+
+#undef PATH_SEPARATOR
+#if defined(_WIN32)
+#define PATH_SEPARATOR ";"
+#else
+#define PATH_SEPARATOR ":"
+#endif
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir/a" PATH_SEPARATOR "$tmpdir/b foo.proto");
+
+#undef PATH_SEPARATOR
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, NonRootMapping) {
+ // Test setting up a search path mapping a directory to a non-root location.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=bar=$tmpdir bar/foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "bar/foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, PathWithEqualsSign) {
+ // Test setting up a search path which happens to have '=' in it.
+
+ CreateTempDir("with=sign");
+ CreateTempFile("with=sign/foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir/with=sign foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, MultipleGenerators) {
+ // Test that we can have multiple generators and use both in one invocation,
+ // each with a different output directory.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ // Create the "a" and "b" sub-directories.
+ CreateTempDir("a");
+ CreateTempDir("b");
+
+ Run("protocol_compiler "
+ "--test_out=$tmpdir/a "
+ "--alt_out=$tmpdir/b "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo", "a");
+ ExpectGenerated("alt_generator", "", "foo.proto", "Foo", "b");
+}
+
+TEST_F(CommandLineInterfaceTest, DisallowServicesNoServices) {
+ // Test that --disallow_services doesn't cause a problem when there are no
+ // services.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --disallow_services --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, DisallowServicesHasService) {
+ // Test that --disallow_services produces an error when there are services.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n"
+ "service Bar {}\n");
+
+ Run("protocol_compiler --disallow_services --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring("foo.proto: This file contains services");
+}
+
+TEST_F(CommandLineInterfaceTest, AllowServicesHasService) {
+ // Test that services work fine as long as --disallow_services is not used.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n"
+ "service Bar {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, CwdRelativeInputs) {
+ // Test that we can accept working-directory-relative input files.
+
+ SetInputsAreProtoPathRelative(false);
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir $tmpdir/foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, WriteDescriptorSet) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --descriptor_set_out=$tmpdir/descriptor_set "
+ "--proto_path=$tmpdir bar.proto");
+
+ ExpectNoErrors();
+
+ FileDescriptorSet descriptor_set;
+ ReadDescriptorSet("descriptor_set", &descriptor_set);
+ if (HasFatalFailure()) return;
+ EXPECT_EQ(1, descriptor_set.file_size());
+ EXPECT_EQ("bar.proto", descriptor_set.file(0).name());
+ // Descriptor set should not have source code info.
+ EXPECT_FALSE(descriptor_set.file(0).has_source_code_info());
+ // Descriptor set should have json_name.
+ EXPECT_EQ("Bar", descriptor_set.file(0).message_type(0).name());
+ EXPECT_EQ("foo", descriptor_set.file(0).message_type(0).field(0).name());
+ EXPECT_TRUE(descriptor_set.file(0).message_type(0).field(0).has_json_name());
+}
+
+TEST_F(CommandLineInterfaceTest, WriteDescriptorSetWithDuplicates) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+ CreateTempFile("baz.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Baz {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --descriptor_set_out=$tmpdir/descriptor_set "
+ "--proto_path=$tmpdir bar.proto foo.proto bar.proto baz.proto");
+
+ ExpectNoErrors();
+
+ FileDescriptorSet descriptor_set;
+ ReadDescriptorSet("descriptor_set", &descriptor_set);
+ if (HasFatalFailure()) return;
+ EXPECT_EQ(3, descriptor_set.file_size());
+ EXPECT_EQ("bar.proto", descriptor_set.file(0).name());
+ EXPECT_EQ("foo.proto", descriptor_set.file(1).name());
+ EXPECT_EQ("baz.proto", descriptor_set.file(2).name());
+ // Descriptor set should not have source code info.
+ EXPECT_FALSE(descriptor_set.file(0).has_source_code_info());
+ // Descriptor set should have json_name.
+ EXPECT_EQ("Bar", descriptor_set.file(0).message_type(0).name());
+ EXPECT_EQ("foo", descriptor_set.file(0).message_type(0).field(0).name());
+ EXPECT_TRUE(descriptor_set.file(0).message_type(0).field(0).has_json_name());
+}
+
+TEST_F(CommandLineInterfaceTest, WriteDescriptorSetWithSourceInfo) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --descriptor_set_out=$tmpdir/descriptor_set "
+ "--include_source_info --proto_path=$tmpdir bar.proto");
+
+ ExpectNoErrors();
+
+ FileDescriptorSet descriptor_set;
+ ReadDescriptorSet("descriptor_set", &descriptor_set);
+ if (HasFatalFailure()) return;
+ EXPECT_EQ(1, descriptor_set.file_size());
+ EXPECT_EQ("bar.proto", descriptor_set.file(0).name());
+ // Source code info included.
+ EXPECT_TRUE(descriptor_set.file(0).has_source_code_info());
+}
+
+TEST_F(CommandLineInterfaceTest, WriteTransitiveDescriptorSet) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --descriptor_set_out=$tmpdir/descriptor_set "
+ "--include_imports --proto_path=$tmpdir bar.proto");
+
+ ExpectNoErrors();
+
+ FileDescriptorSet descriptor_set;
+ ReadDescriptorSet("descriptor_set", &descriptor_set);
+ if (HasFatalFailure()) return;
+ EXPECT_EQ(2, descriptor_set.file_size());
+ if (descriptor_set.file(0).name() == "bar.proto") {
+ std::swap(descriptor_set.mutable_file()->mutable_data()[0],
+ descriptor_set.mutable_file()->mutable_data()[1]);
+ }
+ EXPECT_EQ("foo.proto", descriptor_set.file(0).name());
+ EXPECT_EQ("bar.proto", descriptor_set.file(1).name());
+ // Descriptor set should not have source code info.
+ EXPECT_FALSE(descriptor_set.file(0).has_source_code_info());
+ EXPECT_FALSE(descriptor_set.file(1).has_source_code_info());
+}
+
+TEST_F(CommandLineInterfaceTest, WriteTransitiveDescriptorSetWithSourceInfo) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --descriptor_set_out=$tmpdir/descriptor_set "
+ "--include_imports --include_source_info --proto_path=$tmpdir bar.proto");
+
+ ExpectNoErrors();
+
+ FileDescriptorSet descriptor_set;
+ ReadDescriptorSet("descriptor_set", &descriptor_set);
+ if (HasFatalFailure()) return;
+ EXPECT_EQ(2, descriptor_set.file_size());
+ if (descriptor_set.file(0).name() == "bar.proto") {
+ std::swap(descriptor_set.mutable_file()->mutable_data()[0],
+ descriptor_set.mutable_file()->mutable_data()[1]);
+ }
+ EXPECT_EQ("foo.proto", descriptor_set.file(0).name());
+ EXPECT_EQ("bar.proto", descriptor_set.file(1).name());
+ // Source code info included.
+ EXPECT_TRUE(descriptor_set.file(0).has_source_code_info());
+ EXPECT_TRUE(descriptor_set.file(1).has_source_code_info());
+}
+
+#ifdef _WIN32
+// TODO(teboring): Figure out how to write test on windows.
+#else
+TEST_F(CommandLineInterfaceTest, WriteDependencyManifestFileGivenTwoInputs) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --dependency_out=$tmpdir/manifest "
+ "--test_out=$tmpdir --proto_path=$tmpdir bar.proto foo.proto");
+
+ ExpectErrorText(
+ "Can only process one input file when using --dependency_out=FILE.\n");
+}
+
+#ifdef PROTOBUF_OPENSOURCE
+TEST_F(CommandLineInterfaceTest, WriteDependencyManifestFile) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ string current_working_directory = getcwd(NULL, 0);
+ SwitchToTempDirectory();
+
+ Run("protocol_compiler --dependency_out=manifest --test_out=. "
+ "bar.proto");
+
+ ExpectNoErrors();
+
+ ExpectFileContent("manifest",
+ "bar.proto.MockCodeGenerator.test_generator: "
+ "foo.proto\\\n bar.proto");
+
+ File::ChangeWorkingDirectory(current_working_directory);
+}
+#else // !PROTOBUF_OPENSOURCE
+// TODO(teboring): Figure out how to change and get working directory in
+// google3.
+#endif // !PROTOBUF_OPENSOURCE
+
+TEST_F(CommandLineInterfaceTest, WriteDependencyManifestFileForAbsolutePath) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "import \"foo.proto\";\n"
+ "message Bar {\n"
+ " optional Foo foo = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --dependency_out=$tmpdir/manifest "
+ "--test_out=$tmpdir --proto_path=$tmpdir bar.proto");
+
+ ExpectNoErrors();
+
+ ExpectFileContent("manifest",
+ "$tmpdir/bar.proto.MockCodeGenerator.test_generator: "
+ "$tmpdir/foo.proto\\\n $tmpdir/bar.proto");
+}
+#endif // !_WIN32
+
+
+// -------------------------------------------------------------------
+
+TEST_F(CommandLineInterfaceTest, ParseErrors) {
+ // Test that parse errors are reported.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "badsyntax\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorText(
+ "foo.proto:2:1: Expected top-level statement (e.g. \"message\").\n");
+}
+
+TEST_F(CommandLineInterfaceTest, ParseErrorsMultipleFiles) {
+ // Test that parse errors are reported from multiple files.
+
+ // We set up files such that foo.proto actually depends on bar.proto in
+ // two ways: Directly and through baz.proto. bar.proto's errors should
+ // only be reported once.
+ CreateTempFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "badsyntax\n");
+ CreateTempFile("baz.proto",
+ "syntax = \"proto2\";\n"
+ "import \"bar.proto\";\n");
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "import \"bar.proto\";\n"
+ "import \"baz.proto\";\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorText(
+ "bar.proto:2:1: Expected top-level statement (e.g. \"message\").\n"
+ "baz.proto: Import \"bar.proto\" was not found or had errors.\n"
+ "foo.proto: Import \"bar.proto\" was not found or had errors.\n"
+ "foo.proto: Import \"baz.proto\" was not found or had errors.\n");
+}
+
+TEST_F(CommandLineInterfaceTest, InputNotFoundError) {
+ // Test what happens if the input file is not found.
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorText(
+ "foo.proto: File not found.\n");
+}
+
+TEST_F(CommandLineInterfaceTest, CwdRelativeInputNotFoundError) {
+ // Test what happens when a working-directory-relative input file is not
+ // found.
+
+ SetInputsAreProtoPathRelative(false);
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir $tmpdir/foo.proto");
+
+ ExpectErrorText(
+ "$tmpdir/foo.proto: No such file or directory\n");
+}
+
+TEST_F(CommandLineInterfaceTest, CwdRelativeInputNotMappedError) {
+ // Test what happens when a working-directory-relative input file is not
+ // mapped to a virtual path.
+
+ SetInputsAreProtoPathRelative(false);
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ // Create a directory called "bar" so that we can point --proto_path at it.
+ CreateTempFile("bar/dummy", "");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir/bar $tmpdir/foo.proto");
+
+ ExpectErrorText(
+ "$tmpdir/foo.proto: File does not reside within any path "
+ "specified using --proto_path (or -I). You must specify a "
+ "--proto_path which encompasses this file. Note that the "
+ "proto_path must be an exact prefix of the .proto file "
+ "names -- protoc is too dumb to figure out when two paths "
+ "(e.g. absolute and relative) are equivalent (it's harder "
+ "than you think).\n");
+}
+
+TEST_F(CommandLineInterfaceTest, CwdRelativeInputNotFoundAndNotMappedError) {
+ // Check what happens if the input file is not found *and* is not mapped
+ // in the proto_path.
+
+ SetInputsAreProtoPathRelative(false);
+
+ // Create a directory called "bar" so that we can point --proto_path at it.
+ CreateTempFile("bar/dummy", "");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir/bar $tmpdir/foo.proto");
+
+ ExpectErrorText(
+ "$tmpdir/foo.proto: No such file or directory\n");
+}
+
+TEST_F(CommandLineInterfaceTest, CwdRelativeInputShadowedError) {
+ // Test what happens when a working-directory-relative input file is shadowed
+ // by another file in the virtual path.
+
+ SetInputsAreProtoPathRelative(false);
+
+ CreateTempFile("foo/foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+ CreateTempFile("bar/foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Bar {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir/foo --proto_path=$tmpdir/bar "
+ "$tmpdir/bar/foo.proto");
+
+ ExpectErrorText(
+ "$tmpdir/bar/foo.proto: Input is shadowed in the --proto_path "
+ "by \"$tmpdir/foo/foo.proto\". Either use the latter "
+ "file as your input or reorder the --proto_path so that the "
+ "former file's location comes first.\n");
+}
+
+TEST_F(CommandLineInterfaceTest, ProtoPathNotFoundError) {
+ // Test what happens if the input file is not found.
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir/foo foo.proto");
+
+ ExpectErrorText(
+ "$tmpdir/foo: warning: directory does not exist.\n"
+ "foo.proto: File not found.\n");
+}
+
+TEST_F(CommandLineInterfaceTest, MissingInputError) {
+ // Test that we get an error if no inputs are given.
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir");
+
+ ExpectErrorText("Missing input file.\n");
+}
+
+TEST_F(CommandLineInterfaceTest, MissingOutputError) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --proto_path=$tmpdir foo.proto");
+
+ ExpectErrorText("Missing output directives.\n");
+}
+
+TEST_F(CommandLineInterfaceTest, OutputWriteError) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ string output_file =
+ MockCodeGenerator::GetOutputFileName("test_generator", "foo.proto");
+
+ // Create a directory blocking our output location.
+ CreateTempDir(output_file);
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ // MockCodeGenerator no longer detects an error because we actually write to
+ // an in-memory location first, then dump to disk at the end. This is no
+ // big deal.
+ // ExpectErrorSubstring("MockCodeGenerator detected write error.");
+
+#if defined(_WIN32) && !defined(__CYGWIN__)
+ // Windows with MSVCRT.dll produces EPERM instead of EISDIR.
+ if (HasAlternateErrorSubstring(output_file + ": Permission denied")) {
+ return;
+ }
+#endif
+
+ ExpectErrorSubstring(output_file + ": Is a directory");
+}
+
+TEST_F(CommandLineInterfaceTest, PluginOutputWriteError) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ string output_file =
+ MockCodeGenerator::GetOutputFileName("test_plugin", "foo.proto");
+
+ // Create a directory blocking our output location.
+ CreateTempDir(output_file);
+
+ Run("protocol_compiler --plug_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+#if defined(_WIN32) && !defined(__CYGWIN__)
+ // Windows with MSVCRT.dll produces EPERM instead of EISDIR.
+ if (HasAlternateErrorSubstring(output_file + ": Permission denied")) {
+ return;
+ }
+#endif
+
+ ExpectErrorSubstring(output_file + ": Is a directory");
+}
+
+TEST_F(CommandLineInterfaceTest, OutputDirectoryNotFoundError) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir/nosuchdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring("nosuchdir/: No such file or directory");
+}
+
+TEST_F(CommandLineInterfaceTest, PluginOutputDirectoryNotFoundError) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --plug_out=$tmpdir/nosuchdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring("nosuchdir/: No such file or directory");
+}
+
+TEST_F(CommandLineInterfaceTest, OutputDirectoryIsFileError) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir/foo.proto "
+ "--proto_path=$tmpdir foo.proto");
+
+#if defined(_WIN32) && !defined(__CYGWIN__)
+ // Windows with MSVCRT.dll produces EINVAL instead of ENOTDIR.
+ if (HasAlternateErrorSubstring("foo.proto/: Invalid argument")) {
+ return;
+ }
+#endif
+
+ ExpectErrorSubstring("foo.proto/: Not a directory");
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorError) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message MockCodeGenerator_Error {}\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring(
+ "--test_out: foo.proto: Saw message type MockCodeGenerator_Error.");
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorPluginError) {
+ // Test a generator plugin that returns an error.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message MockCodeGenerator_Error {}\n");
+
+ Run("protocol_compiler --plug_out=TestParameter:$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring(
+ "--plug_out: foo.proto: Saw message type MockCodeGenerator_Error.");
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorPluginFail) {
+ // Test a generator plugin that exits with an error code.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message MockCodeGenerator_Exit {}\n");
+
+ Run("protocol_compiler --plug_out=TestParameter:$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring("Saw message type MockCodeGenerator_Exit.");
+ ExpectErrorSubstring(
+ "--plug_out: prefix-gen-plug: Plugin failed with status code 123.");
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorPluginCrash) {
+ // Test a generator plugin that crashes.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message MockCodeGenerator_Abort {}\n");
+
+ Run("protocol_compiler --plug_out=TestParameter:$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring("Saw message type MockCodeGenerator_Abort.");
+
+#ifdef _WIN32
+ // Windows doesn't have signals. It looks like abort()ing causes the process
+ // to exit with status code 3, but let's not depend on the exact number here.
+ ExpectErrorSubstring(
+ "--plug_out: prefix-gen-plug: Plugin failed with status code");
+#else
+ // Don't depend on the exact signal number.
+ ExpectErrorSubstring(
+ "--plug_out: prefix-gen-plug: Plugin killed by signal");
+#endif
+}
+
+TEST_F(CommandLineInterfaceTest, PluginReceivesSourceCodeInfo) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message MockCodeGenerator_HasSourceCodeInfo {}\n");
+
+ Run("protocol_compiler --plug_out=$tmpdir --proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring(
+ "Saw message type MockCodeGenerator_HasSourceCodeInfo: 1.");
+}
+
+TEST_F(CommandLineInterfaceTest, PluginReceivesJsonName) {
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message MockCodeGenerator_HasJsonName {\n"
+ " optional int32 value = 1;\n"
+ "}\n");
+
+ Run("protocol_compiler --plug_out=$tmpdir --proto_path=$tmpdir foo.proto");
+
+ ExpectErrorSubstring("Saw json_name: 1");
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorPluginNotFound) {
+ // Test what happens if the plugin isn't found.
+
+ CreateTempFile("error.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --badplug_out=TestParameter:$tmpdir "
+ "--plugin=prefix-gen-badplug=no_such_file "
+ "--proto_path=$tmpdir error.proto");
+
+#ifdef _WIN32
+ ExpectErrorSubstring("--badplug_out: prefix-gen-badplug: " +
+ Subprocess::Win32ErrorMessage(ERROR_FILE_NOT_FOUND));
+#else
+ // Error written to stdout by child process after exec() fails.
+ ExpectErrorSubstring(
+ "no_such_file: program not found or is not executable");
+
+ // Error written by parent process when child fails.
+ ExpectErrorSubstring(
+ "--badplug_out: prefix-gen-badplug: Plugin failed with status code 1.");
+#endif
+}
+
+TEST_F(CommandLineInterfaceTest, GeneratorPluginNotAllowed) {
+ // Test what happens if plugins aren't allowed.
+
+ CreateTempFile("error.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ DisallowPlugins();
+ Run("protocol_compiler --plug_out=TestParameter:$tmpdir "
+ "--proto_path=$tmpdir error.proto");
+
+ ExpectErrorSubstring("Unknown flag: --plug_out");
+}
+
+TEST_F(CommandLineInterfaceTest, HelpText) {
+ Run("test_exec_name --help");
+
+ ExpectErrorSubstringWithZeroReturnCode("Usage: test_exec_name ");
+ ExpectErrorSubstringWithZeroReturnCode("--test_out=OUT_DIR");
+ ExpectErrorSubstringWithZeroReturnCode("Test output.");
+ ExpectErrorSubstringWithZeroReturnCode("--alt_out=OUT_DIR");
+ ExpectErrorSubstringWithZeroReturnCode("Alt output.");
+}
+
+TEST_F(CommandLineInterfaceTest, GccFormatErrors) {
+ // Test --error_format=gcc (which is the default, but we want to verify
+ // that it can be set explicitly).
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "badsyntax\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir --error_format=gcc foo.proto");
+
+ ExpectErrorText(
+ "foo.proto:2:1: Expected top-level statement (e.g. \"message\").\n");
+}
+
+TEST_F(CommandLineInterfaceTest, MsvsFormatErrors) {
+ // Test --error_format=msvs
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "badsyntax\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir --error_format=msvs foo.proto");
+
+ ExpectErrorText(
+ "$tmpdir/foo.proto(2) : error in column=1: Expected top-level statement "
+ "(e.g. \"message\").\n");
+}
+
+TEST_F(CommandLineInterfaceTest, InvalidErrorFormat) {
+ // Test --error_format=msvs
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "badsyntax\n");
+
+ Run("protocol_compiler --test_out=$tmpdir "
+ "--proto_path=$tmpdir --error_format=invalid foo.proto");
+
+ ExpectErrorText(
+ "Unknown error format: invalid\n");
+}
+
+// -------------------------------------------------------------------
+// Flag parsing tests
+
+TEST_F(CommandLineInterfaceTest, ParseSingleCharacterFlag) {
+ // Test that a single-character flag works.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler -t$tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, ParseSpaceDelimitedValue) {
+ // Test that separating the flag value with a space works.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler --test_out $tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, ParseSingleCharacterSpaceDelimitedValue) {
+ // Test that separating the flag value with a space works for
+ // single-character flags.
+
+ CreateTempFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ Run("protocol_compiler -t $tmpdir "
+ "--proto_path=$tmpdir foo.proto");
+
+ ExpectNoErrors();
+ ExpectGenerated("test_generator", "", "foo.proto", "Foo");
+}
+
+TEST_F(CommandLineInterfaceTest, MissingValueError) {
+ // Test that we get an error if a flag is missing its value.
+
+ Run("protocol_compiler --test_out --proto_path=$tmpdir foo.proto");
+
+ ExpectErrorText("Missing value for flag: --test_out\n");
+}
+
+TEST_F(CommandLineInterfaceTest, MissingValueAtEndError) {
+ // Test that we get an error if the last argument is a flag requiring a
+ // value.
+
+ Run("protocol_compiler --test_out");
+
+ ExpectErrorText("Missing value for flag: --test_out\n");
+}
+
+TEST_F(CommandLineInterfaceTest, PrintFreeFieldNumbers) {
+ CreateTempFile(
+ "foo.proto",
+ "syntax = \"proto2\";\n"
+ "package foo;\n"
+ "message Foo {\n"
+ " optional int32 a = 2;\n"
+ " optional string b = 4;\n"
+ " optional string c = 5;\n"
+ " optional int64 d = 8;\n"
+ " optional double e = 10;\n"
+ "}\n");
+ CreateTempFile(
+ "bar.proto",
+ "syntax = \"proto2\";\n"
+ "message Bar {\n"
+ " optional int32 a = 2;\n"
+ " extensions 4 to 5;\n"
+ " optional int64 d = 8;\n"
+ " extensions 10;\n"
+ "}\n");
+ CreateTempFile(
+ "baz.proto",
+ "syntax = \"proto2\";\n"
+ "message Baz {\n"
+ " optional int32 a = 2;\n"
+ " optional int64 d = 8;\n"
+ " extensions 15 to max;\n" // unordered.
+ " extensions 13;\n"
+ " extensions 10 to 12;\n"
+ " extensions 5;\n"
+ " extensions 4;\n"
+ "}\n");
+ CreateTempFile(
+ "quz.proto",
+ "syntax = \"proto2\";\n"
+ "message Quz {\n"
+ " message Foo {}\n" // nested message
+ " optional int32 a = 2;\n"
+ " optional group C = 4 {\n"
+ " optional int32 d = 5;\n"
+ " }\n"
+ " extensions 8 to 10;\n"
+ " optional group E = 11 {\n"
+ " optional int32 f = 9;\n" // explicitly reuse extension range 8-10
+ " optional group G = 15 {\n" // nested group
+ " message Foo {}\n" // nested message inside nested group
+ " }\n"
+ " }\n"
+ "}\n");
+
+ Run("protocol_compiler --print_free_field_numbers --proto_path=$tmpdir "
+ "foo.proto bar.proto baz.proto quz.proto");
+
+ ExpectNoErrors();
+
+ // TODO(jieluo): Cygwin doesn't work well if we try to capture stderr and
+ // stdout at the same time. Need to figure out why and add this test back
+ // for Cygwin.
+#if !defined(__CYGWIN__)
+ ExpectCapturedStdout(
+ "foo.Foo free: 1 3 6-7 9 11-INF\n"
+ "Bar free: 1 3 6-7 9 11-INF\n"
+ "Baz free: 1 3 6-7 9 14\n"
+ "Quz.Foo free: 1-INF\n"
+ "Quz.E.G.Foo free: 1-INF\n"
+ "Quz free: 1 3 6-7 12-14 16-INF\n");
+#endif
+}
+
+// ===================================================================
+
+// Test for --encode and --decode. Note that it would be easier to do this
+// test as a shell script, but we'd like to be able to run the test on
+// platforms that don't have a Bourne-compatible shell available (especially
+// Windows/MSVC).
+class EncodeDecodeTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ duped_stdin_ = dup(STDIN_FILENO);
+ }
+
+ virtual void TearDown() {
+ dup2(duped_stdin_, STDIN_FILENO);
+ close(duped_stdin_);
+ }
+
+ void RedirectStdinFromText(const string& input) {
+ string filename = TestTempDir() + "/test_stdin";
+ GOOGLE_CHECK_OK(File::SetContents(filename, input, true));
+ GOOGLE_CHECK(RedirectStdinFromFile(filename));
+ }
+
+ bool RedirectStdinFromFile(const string& filename) {
+ int fd = open(filename.c_str(), O_RDONLY);
+ if (fd < 0) return false;
+ dup2(fd, STDIN_FILENO);
+ close(fd);
+ return true;
+ }
+
+ // Remove '\r' characters from text.
+ string StripCR(const string& text) {
+ string result;
+
+ for (int i = 0; i < text.size(); i++) {
+ if (text[i] != '\r') {
+ result.push_back(text[i]);
+ }
+ }
+
+ return result;
+ }
+
+ enum Type { TEXT, BINARY };
+ enum ReturnCode { SUCCESS, ERROR };
+
+ bool Run(const string& command) {
+ vector<string> args;
+ args.push_back("protoc");
+ SplitStringUsing(command, " ", &args);
+ args.push_back("--proto_path=" + TestSourceDir());
+
+ google::protobuf::scoped_array<const char * > argv(new const char* [args.size()]);
+ for (int i = 0; i < args.size(); i++) {
+ argv[i] = args[i].c_str();
+ }
+
+ CommandLineInterface cli;
+ cli.SetInputsAreProtoPathRelative(true);
+
+ CaptureTestStdout();
+ CaptureTestStderr();
+
+ int result = cli.Run(args.size(), argv.get());
+
+ captured_stdout_ = GetCapturedTestStdout();
+ captured_stderr_ = GetCapturedTestStderr();
+
+ return result == 0;
+ }
+
+ void ExpectStdoutMatchesBinaryFile(const string& filename) {
+ string expected_output;
+ GOOGLE_CHECK_OK(File::GetContents(filename, &expected_output, true));
+
+ // Don't use EXPECT_EQ because we don't want to print raw binary data to
+ // stdout on failure.
+ EXPECT_TRUE(captured_stdout_ == expected_output);
+ }
+
+ void ExpectStdoutMatchesTextFile(const string& filename) {
+ string expected_output;
+ GOOGLE_CHECK_OK(File::GetContents(filename, &expected_output, true));
+
+ ExpectStdoutMatchesText(expected_output);
+ }
+
+ void ExpectStdoutMatchesText(const string& expected_text) {
+ EXPECT_EQ(StripCR(expected_text), StripCR(captured_stdout_));
+ }
+
+ void ExpectStderrMatchesText(const string& expected_text) {
+ EXPECT_EQ(StripCR(expected_text), StripCR(captured_stderr_));
+ }
+
+ private:
+ int duped_stdin_;
+ string captured_stdout_;
+ string captured_stderr_;
+};
+
+TEST_F(EncodeDecodeTest, Encode) {
+ RedirectStdinFromFile(TestSourceDir() + "/google/protobuf/"
+ "testdata/text_format_unittest_data_oneof_implemented.txt");
+ EXPECT_TRUE(Run("google/protobuf/unittest.proto "
+ "--encode=protobuf_unittest.TestAllTypes"));
+ ExpectStdoutMatchesBinaryFile(TestSourceDir() +
+ "/google/protobuf/testdata/golden_message_oneof_implemented");
+ ExpectStderrMatchesText("");
+}
+
+TEST_F(EncodeDecodeTest, Decode) {
+ RedirectStdinFromFile(TestSourceDir() +
+ "/google/protobuf/testdata/golden_message_oneof_implemented");
+ EXPECT_TRUE(Run("google/protobuf/unittest.proto "
+ "--decode=protobuf_unittest.TestAllTypes"));
+ ExpectStdoutMatchesTextFile(TestSourceDir() +
+ "/google/protobuf/"
+ "testdata/text_format_unittest_data_oneof_implemented.txt");
+ ExpectStderrMatchesText("");
+}
+
+TEST_F(EncodeDecodeTest, Partial) {
+ RedirectStdinFromText("");
+ EXPECT_TRUE(Run("google/protobuf/unittest.proto "
+ "--encode=protobuf_unittest.TestRequired"));
+ ExpectStdoutMatchesText("");
+ ExpectStderrMatchesText(
+ "warning: Input message is missing required fields: a, b, c\n");
+}
+
+TEST_F(EncodeDecodeTest, DecodeRaw) {
+ protobuf_unittest::TestAllTypes message;
+ message.set_optional_int32(123);
+ message.set_optional_string("foo");
+ string data;
+ message.SerializeToString(&data);
+
+ RedirectStdinFromText(data);
+ EXPECT_TRUE(Run("--decode_raw"));
+ ExpectStdoutMatchesText("1: 123\n"
+ "14: \"foo\"\n");
+ ExpectStderrMatchesText("");
+}
+
+TEST_F(EncodeDecodeTest, UnknownType) {
+ EXPECT_FALSE(Run("google/protobuf/unittest.proto "
+ "--encode=NoSuchType"));
+ ExpectStdoutMatchesText("");
+ ExpectStderrMatchesText("Type not defined: NoSuchType\n");
+}
+
+TEST_F(EncodeDecodeTest, ProtoParseError) {
+ EXPECT_FALSE(Run("google/protobuf/no_such_file.proto "
+ "--encode=NoSuchType"));
+ ExpectStdoutMatchesText("");
+ ExpectStderrMatchesText(
+ "google/protobuf/no_such_file.proto: File not found.\n");
+}
+
+} // anonymous namespace
+
+#endif // !GOOGLE_PROTOBUF_HEAP_CHECK_DRACONIAN
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_bootstrap_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_bootstrap_unittest.cc
new file mode 100644
index 0000000000..77451ab1bf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_bootstrap_unittest.cc
@@ -0,0 +1,159 @@
+// 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 test insures that google/protobuf/descriptor.pb.{h,cc} match exactly
+// what would be generated by the protocol compiler. These files are not
+// generated automatically at build time because they are compiled into the
+// protocol compiler itself. So, if they were auto-generated, you'd have a
+// chicken-and-egg problem.
+//
+// If this test fails, run the script
+// "generate_descriptor_proto.sh" and add
+// descriptor.pb.{h,cc} to your changelist.
+
+#include <map>
+
+#include <google/protobuf/compiler/cpp/cpp_generator.h>
+#include <google/protobuf/compiler/importer.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/stl_util.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+namespace {
+
+class MockErrorCollector : public MultiFileErrorCollector {
+ public:
+ MockErrorCollector() {}
+ ~MockErrorCollector() {}
+
+ string text_;
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(const string& filename, int line, int column,
+ const string& message) {
+ strings::SubstituteAndAppend(&text_, "$0:$1:$2: $3\n",
+ filename, line, column, message);
+ }
+};
+
+class MockGeneratorContext : public GeneratorContext {
+ public:
+ MockGeneratorContext() {}
+ ~MockGeneratorContext() {
+ STLDeleteValues(&files_);
+ }
+
+ void ExpectFileMatches(const string& virtual_filename,
+ const string& physical_filename) {
+ string* expected_contents = FindPtrOrNull(files_, virtual_filename);
+ ASSERT_TRUE(expected_contents != NULL)
+ << "Generator failed to generate file: " << virtual_filename;
+
+ string actual_contents;
+ GOOGLE_CHECK_OK(
+ File::GetContents(TestSourceDir() + "/" + physical_filename,
+ &actual_contents, true));
+ EXPECT_TRUE(actual_contents == *expected_contents)
+ << physical_filename << " needs to be regenerated. Please run "
+ "google/protobuf/compiler/release_compiler.sh and "
+ "generate_descriptor_proto.sh. Then add this file "
+ "to your CL.";
+ }
+
+ // implements GeneratorContext --------------------------------------
+
+ virtual io::ZeroCopyOutputStream* Open(const string& filename) {
+ string** map_slot = &files_[filename];
+ delete *map_slot;
+ *map_slot = new string;
+
+ return new io::StringOutputStream(*map_slot);
+ }
+
+ private:
+ map<string, string*> files_;
+};
+
+TEST(BootstrapTest, GeneratedDescriptorMatches) {
+ MockErrorCollector error_collector;
+ DiskSourceTree source_tree;
+ source_tree.MapPath("", TestSourceDir());
+ Importer importer(&source_tree, &error_collector);
+ const FileDescriptor* proto_file =
+ importer.Import("google/protobuf/descriptor.proto");
+ const FileDescriptor* plugin_proto_file =
+ importer.Import("google/protobuf/compiler/plugin.proto");
+ EXPECT_EQ("", error_collector.text_);
+ ASSERT_TRUE(proto_file != NULL);
+ ASSERT_TRUE(plugin_proto_file != NULL);
+
+ CppGenerator generator;
+ MockGeneratorContext context;
+ string error;
+ string parameter = "dllexport_decl=LIBPROTOBUF_EXPORT";
+ ASSERT_TRUE(generator.Generate(proto_file, parameter,
+ &context, &error));
+ parameter = "dllexport_decl=LIBPROTOC_EXPORT";
+ ASSERT_TRUE(generator.Generate(plugin_proto_file, parameter,
+ &context, &error));
+
+ context.ExpectFileMatches("google/protobuf/descriptor.pb.h",
+ "google/protobuf/descriptor.pb.h");
+ context.ExpectFileMatches("google/protobuf/descriptor.pb.cc",
+ "google/protobuf/descriptor.pb.cc");
+ context.ExpectFileMatches("google/protobuf/compiler/plugin.pb.h",
+ "google/protobuf/compiler/plugin.pb.h");
+ context.ExpectFileMatches("google/protobuf/compiler/plugin.pb.cc",
+ "google/protobuf/compiler/plugin.pb.cc");
+}
+
+} // namespace
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.cc
new file mode 100644
index 0000000000..62b7ed4e47
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.cc
@@ -0,0 +1,319 @@
+// 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.
+
+#include <map>
+
+#include <google/protobuf/compiler/cpp/cpp_enum.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+namespace {
+// The GOOGLE_ARRAYSIZE constant is the max enum value plus 1. If the max enum value
+// is ::google::protobuf::kint32max, GOOGLE_ARRAYSIZE will overflow. In such cases we should omit the
+// generation of the GOOGLE_ARRAYSIZE constant.
+bool ShouldGenerateArraySize(const EnumDescriptor* descriptor) {
+ int32 max_value = descriptor->value(0)->number();
+ for (int i = 0; i < descriptor->value_count(); i++) {
+ if (descriptor->value(i)->number() > max_value) {
+ max_value = descriptor->value(i)->number();
+ }
+ }
+ return max_value != ::google::protobuf::kint32max;
+}
+} // namespace
+
+EnumGenerator::EnumGenerator(const EnumDescriptor* descriptor,
+ const Options& options)
+ : descriptor_(descriptor),
+ classname_(ClassName(descriptor, false)),
+ options_(options),
+ generate_array_size_(ShouldGenerateArraySize(descriptor)) {
+}
+
+EnumGenerator::~EnumGenerator() {}
+
+void EnumGenerator::FillForwardDeclaration(
+ map<string, const EnumDescriptor*>* enum_names) {
+ if (!options_.proto_h) {
+ return;
+ }
+ (*enum_names)[classname_] = descriptor_;
+}
+
+void EnumGenerator::GenerateDefinition(io::Printer* printer) {
+ map<string, string> vars;
+ vars["classname"] = classname_;
+ vars["short_name"] = descriptor_->name();
+ vars["enumbase"] = classname_ + (options_.proto_h ? " : int" : "");
+
+ printer->Print(vars, "enum $enumbase$ {\n");
+ printer->Annotate("enumbase", descriptor_);
+ printer->Indent();
+
+ const EnumValueDescriptor* min_value = descriptor_->value(0);
+ const EnumValueDescriptor* max_value = descriptor_->value(0);
+
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ vars["name"] = EnumValueName(descriptor_->value(i));
+ // In C++, an value of -2147483648 gets interpreted as the negative of
+ // 2147483648, and since 2147483648 can't fit in an integer, this produces a
+ // compiler warning. This works around that issue.
+ vars["number"] = Int32ToString(descriptor_->value(i)->number());
+ vars["prefix"] = (descriptor_->containing_type() == NULL) ?
+ "" : classname_ + "_";
+ vars["deprecation"] = descriptor_->value(i)->options().deprecated() ?
+ " PROTOBUF_DEPRECATED" : "";
+
+ if (i > 0) printer->Print(",\n");
+ printer->Print(vars, "$prefix$$name$$deprecation$ = $number$");
+
+ if (descriptor_->value(i)->number() < min_value->number()) {
+ min_value = descriptor_->value(i);
+ }
+ if (descriptor_->value(i)->number() > max_value->number()) {
+ max_value = descriptor_->value(i);
+ }
+ }
+
+ if (HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ // For new enum semantics: generate min and max sentinel values equal to
+ // INT32_MIN and INT32_MAX
+ if (descriptor_->value_count() > 0) printer->Print(",\n");
+ printer->Print(vars,
+ "$classname$_$prefix$INT_MIN_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32min,\n"
+ "$classname$_$prefix$INT_MAX_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32max");
+ }
+
+ printer->Outdent();
+ printer->Print("\n};\n");
+
+ vars["min_name"] = EnumValueName(min_value);
+ vars["max_name"] = EnumValueName(max_value);
+
+ if (options_.dllexport_decl.empty()) {
+ vars["dllexport"] = "";
+ } else {
+ vars["dllexport"] = options_.dllexport_decl + " ";
+ }
+
+ printer->Print(vars,
+ "$dllexport$bool $classname$_IsValid(int value);\n"
+ "const $classname$ $prefix$$short_name$_MIN = $prefix$$min_name$;\n"
+ "const $classname$ $prefix$$short_name$_MAX = $prefix$$max_name$;\n");
+
+ if (generate_array_size_) {
+ printer->Print(vars,
+ "const int $prefix$$short_name$_ARRAYSIZE = "
+ "$prefix$$short_name$_MAX + 1;\n\n");
+ }
+
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(vars,
+ "$dllexport$const ::google::protobuf::EnumDescriptor* $classname$_descriptor();\n");
+ // The _Name and _Parse methods
+ printer->Print(
+ vars,
+ "inline const ::std::string& $classname$_Name($classname$ value) {\n"
+ " return ::google::protobuf::internal::NameOfEnum(\n"
+ " $classname$_descriptor(), value);\n"
+ "}\n");
+ printer->Print(vars,
+ "inline bool $classname$_Parse(\n"
+ " const ::std::string& name, $classname$* value) {\n"
+ " return ::google::protobuf::internal::ParseNamedEnum<$classname$>(\n"
+ " $classname$_descriptor(), name, value);\n"
+ "}\n");
+ }
+}
+
+void EnumGenerator::
+GenerateGetEnumDescriptorSpecializations(io::Printer* printer) {
+ printer->Print(
+ "template <> struct is_proto_enum< $classname$> : ::google::protobuf::internal::true_type "
+ "{};\n",
+ "classname", ClassName(descriptor_, true));
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(
+ "template <>\n"
+ "inline const EnumDescriptor* GetEnumDescriptor< $classname$>() {\n"
+ " return $classname$_descriptor();\n"
+ "}\n",
+ "classname", ClassName(descriptor_, true));
+ }
+}
+
+void EnumGenerator::GenerateSymbolImports(io::Printer* printer) {
+ map<string, string> vars;
+ vars["nested_name"] = descriptor_->name();
+ vars["classname"] = classname_;
+ vars["constexpr"] = options_.proto_h ? "constexpr " : "";
+ printer->Print(vars, "typedef $classname$ $nested_name$;\n");
+
+ for (int j = 0; j < descriptor_->value_count(); j++) {
+ vars["tag"] = EnumValueName(descriptor_->value(j));
+ vars["deprecated_attr"] = descriptor_->value(j)->options().deprecated() ?
+ "GOOGLE_PROTOBUF_DEPRECATED_ATTR " : "";
+ printer->Print(vars,
+ "$deprecated_attr$static $constexpr$const $nested_name$ $tag$ =\n"
+ " $classname$_$tag$;\n");
+ }
+
+ printer->Print(vars,
+ "static inline bool $nested_name$_IsValid(int value) {\n"
+ " return $classname$_IsValid(value);\n"
+ "}\n"
+ "static const $nested_name$ $nested_name$_MIN =\n"
+ " $classname$_$nested_name$_MIN;\n"
+ "static const $nested_name$ $nested_name$_MAX =\n"
+ " $classname$_$nested_name$_MAX;\n");
+ if (generate_array_size_) {
+ printer->Print(vars,
+ "static const int $nested_name$_ARRAYSIZE =\n"
+ " $classname$_$nested_name$_ARRAYSIZE;\n");
+ }
+
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(vars,
+ "static inline const ::google::protobuf::EnumDescriptor*\n"
+ "$nested_name$_descriptor() {\n"
+ " return $classname$_descriptor();\n"
+ "}\n");
+ printer->Print(vars,
+ "static inline const ::std::string& "
+ "$nested_name$_Name($nested_name$ value) {"
+ "\n"
+ " return $classname$_Name(value);\n"
+ "}\n");
+ printer->Print(vars,
+ "static inline bool $nested_name$_Parse(const ::std::string& name,\n"
+ " $nested_name$* value) {\n"
+ " return $classname$_Parse(name, value);\n"
+ "}\n");
+ }
+}
+
+void EnumGenerator::GenerateDescriptorInitializer(
+ io::Printer* printer, int index) {
+ map<string, string> vars;
+ vars["classname"] = classname_;
+ vars["index"] = SimpleItoa(index);
+
+ if (descriptor_->containing_type() == NULL) {
+ printer->Print(vars,
+ "$classname$_descriptor_ = file->enum_type($index$);\n");
+ } else {
+ vars["parent"] = ClassName(descriptor_->containing_type(), false);
+ printer->Print(vars,
+ "$classname$_descriptor_ = $parent$_descriptor_->enum_type($index$);\n");
+ }
+}
+
+void EnumGenerator::GenerateMethods(io::Printer* printer) {
+ map<string, string> vars;
+ vars["classname"] = classname_;
+ vars["constexpr"] = options_.proto_h ? "constexpr " : "";
+
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(vars,
+ "const ::google::protobuf::EnumDescriptor* $classname$_descriptor() {\n"
+ " protobuf_AssignDescriptorsOnce();\n"
+ " return $classname$_descriptor_;\n"
+ "}\n");
+ }
+
+ printer->Print(vars,
+ "bool $classname$_IsValid(int value) {\n"
+ " switch(value) {\n");
+
+ // Multiple values may have the same number. Make sure we only cover
+ // each number once by first constructing a set containing all valid
+ // numbers, then printing a case statement for each element.
+
+ set<int> numbers;
+ for (int j = 0; j < descriptor_->value_count(); j++) {
+ const EnumValueDescriptor* value = descriptor_->value(j);
+ numbers.insert(value->number());
+ }
+
+ for (set<int>::iterator iter = numbers.begin();
+ iter != numbers.end(); ++iter) {
+ printer->Print(
+ " case $number$:\n",
+ "number", Int32ToString(*iter));
+ }
+
+ printer->Print(vars,
+ " return true;\n"
+ " default:\n"
+ " return false;\n"
+ " }\n"
+ "}\n"
+ "\n");
+
+ if (descriptor_->containing_type() != NULL) {
+ // We need to "define" the static constants which were declared in the
+ // header, to give the linker a place to put them. Or at least the C++
+ // standard says we have to. MSVC actually insists that we do _not_ define
+ // them again in the .cc file, prior to VC++ 2015.
+ printer->Print("#if !defined(_MSC_VER) || _MSC_VER >= 1900\n");
+
+ vars["parent"] = ClassName(descriptor_->containing_type(), false);
+ vars["nested_name"] = descriptor_->name();
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ vars["value"] = EnumValueName(descriptor_->value(i));
+ printer->Print(vars,
+ "$constexpr$const $classname$ $parent$::$value$;\n");
+ }
+ printer->Print(vars,
+ "const $classname$ $parent$::$nested_name$_MIN;\n"
+ "const $classname$ $parent$::$nested_name$_MAX;\n");
+ if (generate_array_size_) {
+ printer->Print(vars,
+ "const int $parent$::$nested_name$_ARRAYSIZE;\n");
+ }
+
+ printer->Print("#endif // !defined(_MSC_VER) || _MSC_VER >= 1900\n");
+ }
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.h
new file mode 100644
index 0000000000..90edf0017d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum.h
@@ -0,0 +1,111 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_ENUM_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_ENUM_H__
+
+#include <map>
+#include <set>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_options.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class EnumGenerator {
+ public:
+ // See generator.cc for the meaning of dllexport_decl.
+ EnumGenerator(const EnumDescriptor* descriptor, const Options& options);
+ ~EnumGenerator();
+
+ // Header stuff.
+
+ // Fills the name to use when declaring the enum. This is for use when
+ // generating other .proto.h files. This code should be placed within the
+ // enum's package namespace, but NOT within any class, even for nested
+ // enums. A given key in enum_names will map from an enum class name to the
+ // EnumDescriptor that was responsible for its inclusion in the map. This can
+ // be used to associate the descriptor with the code generated for it.
+ void FillForwardDeclaration(map<string, const EnumDescriptor*>* enum_names);
+
+ // Generate header code defining the enum. This code should be placed
+ // within the enum's package namespace, but NOT within any class, even for
+ // nested enums.
+ void GenerateDefinition(io::Printer* printer);
+
+ // Generate specialization of GetEnumDescriptor<MyEnum>().
+ // Precondition: in ::google::protobuf namespace.
+ void GenerateGetEnumDescriptorSpecializations(io::Printer* printer);
+
+ // For enums nested within a message, generate code to import all the enum's
+ // symbols (e.g. the enum type name, all its values, etc.) into the class's
+ // namespace. This should be placed inside the class definition in the
+ // header.
+ void GenerateSymbolImports(io::Printer* printer);
+
+ // Source file stuff.
+
+ // Generate code that initializes the global variable storing the enum's
+ // descriptor.
+ void GenerateDescriptorInitializer(io::Printer* printer, int index);
+
+ // Generate non-inline methods related to the enum, such as IsValidValue().
+ // Goes in the .cc file.
+ void GenerateMethods(io::Printer* printer);
+
+ private:
+ const EnumDescriptor* descriptor_;
+ const string classname_;
+ const Options& options_;
+ // whether to generate the *_ARRAYSIZE constant.
+ const bool generate_array_size_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_ENUM_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.cc
new file mode 100644
index 0000000000..ffd815293f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.cc
@@ -0,0 +1,507 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_enum_field.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+namespace {
+
+void SetEnumVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables,
+ const Options& options) {
+ SetCommonFieldVariables(descriptor, variables, options);
+ const EnumValueDescriptor* default_value = descriptor->default_value_enum();
+ (*variables)["type"] = ClassName(descriptor->enum_type(), true);
+ (*variables)["default"] = Int32ToString(default_value->number());
+ (*variables)["full_name"] = descriptor->full_name();
+}
+
+} // namespace
+
+// ===================================================================
+
+EnumFieldGenerator::EnumFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : FieldGenerator(options), descriptor_(descriptor) {
+ SetEnumVariables(descriptor, &variables_, options);
+}
+
+EnumFieldGenerator::~EnumFieldGenerator() {}
+
+void EnumFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_, "int $name$_;\n");
+}
+
+void EnumFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$deprecated_attr$$type$ $name$() const;\n"
+ "$deprecated_attr$void set_$name$($type$ value);\n");
+}
+
+void EnumFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ $type$ $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return static_cast< $type$ >($name$_);\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$($type$ value) {\n");
+ if (!HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables,
+ " assert($type$_IsValid(value));\n");
+ }
+ printer->Print(variables,
+ " $set_hasbit$\n"
+ " $name$_ = value;\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n");
+}
+
+void EnumFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+}
+
+void EnumFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_, "set_$name$(from.$name$());\n");
+}
+
+void EnumFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "std::swap($name$_, other->$name$_);\n");
+}
+
+void EnumFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+}
+
+void EnumFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ printer->Print(variables_,
+ "int value;\n"
+ "DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<\n"
+ " int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(\n"
+ " input, &value)));\n");
+ if (HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables_,
+ "set_$name$(static_cast< $type$ >(value));\n");
+ } else {
+ printer->Print(variables_,
+ "if ($type$_IsValid(value)) {\n"
+ " set_$name$(static_cast< $type$ >(value));\n");
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ "} else {\n"
+ " mutable_unknown_fields()->AddVarint($number$, value);\n");
+ } else {
+ printer->Print(
+ "} else {\n"
+ " unknown_fields_stream.WriteVarint32($tag$);\n"
+ " unknown_fields_stream.WriteVarint32(value);\n",
+ "tag", SimpleItoa(internal::WireFormat::MakeTag(descriptor_)));
+ }
+ printer->Print(variables_,
+ "}\n");
+ }
+}
+
+void EnumFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ printer->Print(variables_,
+ "::google::protobuf::internal::WireFormatLite::WriteEnum(\n"
+ " $number$, this->$name$(), output);\n");
+}
+
+void EnumFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ printer->Print(variables_,
+ "target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(\n"
+ " $number$, this->$name$(), target);\n");
+}
+
+void EnumFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "total_size += $tag_size$ +\n"
+ " ::google::protobuf::internal::WireFormatLite::EnumSize(this->$name$());\n");
+}
+
+// ===================================================================
+
+EnumOneofFieldGenerator::
+EnumOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : EnumFieldGenerator(descriptor, options) {
+ SetCommonOneofFieldVariables(descriptor, &variables_);
+}
+
+EnumOneofFieldGenerator::~EnumOneofFieldGenerator() {}
+
+void EnumOneofFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ $type$ $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " if (has_$name$()) {\n"
+ " return static_cast< $type$ >($oneof_prefix$$name$_);\n"
+ " }\n"
+ " return static_cast< $type$ >($default$);\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$($type$ value) {\n");
+ if (!HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables,
+ " assert($type$_IsValid(value));\n");
+ }
+ printer->Print(variables,
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " }\n"
+ " $oneof_prefix$$name$_ = value;\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n");
+}
+
+void EnumOneofFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$oneof_prefix$$name$_ = $default$;\n");
+}
+
+void EnumOneofFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ // Don't print any swapping code. Swapping the union will swap this field.
+}
+
+void EnumOneofFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ " $classname$_default_oneof_instance_->$name$_ = $default$;\n");
+}
+
+// ===================================================================
+
+RepeatedEnumFieldGenerator::RepeatedEnumFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : FieldGenerator(options), descriptor_(descriptor) {
+ SetEnumVariables(descriptor, &variables_, options);
+}
+
+RepeatedEnumFieldGenerator::~RepeatedEnumFieldGenerator() {}
+
+void RepeatedEnumFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "::google::protobuf::RepeatedField<int> $name$_;\n");
+ if (descriptor_->is_packed() &&
+ HasGeneratedMethods(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ "mutable int _$name$_cached_byte_size_;\n");
+ }
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$deprecated_attr$$type$ $name$(int index) const;\n"
+ "$deprecated_attr$void set_$name$(int index, $type$ value);\n"
+ "$deprecated_attr$void add_$name$($type$ value);\n");
+ printer->Print(variables_,
+ "$deprecated_attr$const ::google::protobuf::RepeatedField<int>& $name$() const;\n"
+ "$deprecated_attr$::google::protobuf::RepeatedField<int>* mutable_$name$();\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ $type$ $classname$::$name$(int index) const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return static_cast< $type$ >($name$_.Get(index));\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(int index, $type$ value) {\n");
+ if (!HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables,
+ " assert($type$_IsValid(value));\n");
+ }
+ printer->Print(variables,
+ " $name$_.Set(index, value);\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::add_$name$($type$ value) {\n");
+ if (!HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables,
+ " assert($type$_IsValid(value));\n");
+ }
+ printer->Print(variables,
+ " $name$_.Add(value);\n"
+ " // @@protoc_insertion_point(field_add:$full_name$)\n"
+ "}\n");
+ printer->Print(variables,
+ "$inline$ const ::google::protobuf::RepeatedField<int>&\n"
+ "$classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_list:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "$inline$ ::google::protobuf::RepeatedField<int>*\n"
+ "$classname$::mutable_$name$() {\n"
+ " // @@protoc_insertion_point(field_mutable_list:$full_name$)\n"
+ " return &$name$_;\n"
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.Clear();\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.MergeFrom(from.$name$_);\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.UnsafeArenaSwap(&other->$name$_);\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ // Not needed for repeated fields.
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ // Don't use ReadRepeatedPrimitive here so that the enum can be validated.
+ printer->Print(variables_,
+ "int value;\n"
+ "DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<\n"
+ " int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(\n"
+ " input, &value)));\n");
+ if (HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables_,
+ "add_$name$(static_cast< $type$ >(value));\n");
+ } else {
+ printer->Print(variables_,
+ "if ($type$_IsValid(value)) {\n"
+ " add_$name$(static_cast< $type$ >(value));\n");
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ "} else {\n"
+ " mutable_unknown_fields()->AddVarint($number$, value);\n");
+ } else {
+ printer->Print(
+ "} else {\n"
+ " unknown_fields_stream.WriteVarint32(tag);\n"
+ " unknown_fields_stream.WriteVarint32(value);\n");
+ }
+ printer->Print("}\n");
+ }
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateMergeFromCodedStreamWithPacking(io::Printer* printer) const {
+ if (!descriptor_->is_packed()) {
+ // This path is rarely executed, so we use a non-inlined implementation.
+ if (HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables_,
+ "DO_((::google::protobuf::internal::"
+ "WireFormatLite::ReadPackedEnumPreserveUnknowns(\n"
+ " input,\n"
+ " $number$,\n"
+ " NULL,\n"
+ " NULL,\n"
+ " this->mutable_$name$())));\n");
+ } else if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ "DO_((::google::protobuf::internal::WireFormat::ReadPackedEnumPreserveUnknowns(\n"
+ " input,\n"
+ " $number$,\n"
+ " $type$_IsValid,\n"
+ " mutable_unknown_fields(),\n"
+ " this->mutable_$name$())));\n");
+ } else {
+ printer->Print(variables_,
+ "DO_((::google::protobuf::internal::"
+ "WireFormatLite::ReadPackedEnumPreserveUnknowns(\n"
+ " input,\n"
+ " $number$,\n"
+ " $type$_IsValid,\n"
+ " &unknown_fields_stream,\n"
+ " this->mutable_$name$())));\n");
+ }
+ } else {
+ printer->Print(variables_,
+ "::google::protobuf::uint32 length;\n"
+ "DO_(input->ReadVarint32(&length));\n"
+ "::google::protobuf::io::CodedInputStream::Limit limit = "
+ "input->PushLimit(length);\n"
+ "while (input->BytesUntilLimit() > 0) {\n"
+ " int value;\n"
+ " DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<\n"
+ " int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(\n"
+ " input, &value)));\n");
+ if (HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ printer->Print(variables_,
+ " add_$name$(static_cast< $type$ >(value));\n");
+ } else {
+ printer->Print(variables_,
+ " if ($type$_IsValid(value)) {\n"
+ " add_$name$(static_cast< $type$ >(value));\n"
+ " } else {\n");
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ " mutable_unknown_fields()->AddVarint($number$, value);\n");
+ } else {
+ printer->Print(variables_,
+ " unknown_fields_stream.WriteVarint32(tag);\n"
+ " unknown_fields_stream.WriteVarint32(value);\n");
+ }
+ printer->Print(
+ " }\n");
+ }
+ printer->Print(variables_,
+ "}\n"
+ "input->PopLimit(limit);\n");
+ }
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ if (descriptor_->is_packed()) {
+ // Write the tag and the size.
+ printer->Print(variables_,
+ "if (this->$name$_size() > 0) {\n"
+ " ::google::protobuf::internal::WireFormatLite::WriteTag(\n"
+ " $number$,\n"
+ " ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED,\n"
+ " output);\n"
+ " output->WriteVarint32(_$name$_cached_byte_size_);\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n");
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ " ::google::protobuf::internal::WireFormatLite::WriteEnumNoTag(\n"
+ " this->$name$(i), output);\n");
+ } else {
+ printer->Print(variables_,
+ " ::google::protobuf::internal::WireFormatLite::WriteEnum(\n"
+ " $number$, this->$name$(i), output);\n");
+ }
+ printer->Print("}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ if (descriptor_->is_packed()) {
+ // Write the tag and the size.
+ printer->Print(variables_,
+ "if (this->$name$_size() > 0) {\n"
+ " target = ::google::protobuf::internal::WireFormatLite::WriteTagToArray(\n"
+ " $number$,\n"
+ " ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED,\n"
+ " target);\n"
+ " target = ::google::protobuf::io::CodedOutputStream::WriteVarint32ToArray("
+ " _$name$_cached_byte_size_, target);\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n");
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ " target = ::google::protobuf::internal::WireFormatLite::WriteEnumNoTagToArray(\n"
+ " this->$name$(i), target);\n");
+ } else {
+ printer->Print(variables_,
+ " target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(\n"
+ " $number$, this->$name$(i), target);\n");
+ }
+ printer->Print("}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "{\n"
+ " int data_size = 0;\n");
+ printer->Indent();
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n"
+ " data_size += ::google::protobuf::internal::WireFormatLite::EnumSize(\n"
+ " this->$name$(i));\n"
+ "}\n");
+
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ "if (data_size > 0) {\n"
+ " total_size += $tag_size$ +\n"
+ " ::google::protobuf::internal::WireFormatLite::Int32Size(data_size);\n"
+ "}\n"
+ "GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();\n"
+ "_$name$_cached_byte_size_ = data_size;\n"
+ "GOOGLE_SAFE_CONCURRENT_WRITES_END();\n"
+ "total_size += data_size;\n");
+ } else {
+ printer->Print(variables_,
+ "total_size += $tag_size$ * this->$name$_size() + data_size;\n");
+ }
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.h
new file mode 100644
index 0000000000..fe21c57574
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_enum_field.h
@@ -0,0 +1,124 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_ENUM_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_ENUM_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class EnumFieldGenerator : public FieldGenerator {
+ public:
+ EnumFieldGenerator(const FieldDescriptor* descriptor, const Options& options);
+ ~EnumFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumFieldGenerator);
+};
+
+class EnumOneofFieldGenerator : public EnumFieldGenerator {
+ public:
+ EnumOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~EnumOneofFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumOneofFieldGenerator);
+};
+
+class RepeatedEnumFieldGenerator : public FieldGenerator {
+ public:
+ RepeatedEnumFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~RepeatedEnumFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateMergeFromCodedStreamWithPacking(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedEnumFieldGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_ENUM_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.cc
new file mode 100644
index 0000000000..c42f162794
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.cc
@@ -0,0 +1,210 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_extension.h>
+#include <map>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+namespace {
+
+// Returns the fully-qualified class name of the message that this field
+// extends. This function is used in the Google-internal code to handle some
+// legacy cases.
+string ExtendeeClassName(const FieldDescriptor* descriptor) {
+ const Descriptor* extendee = descriptor->containing_type();
+ return ClassName(extendee, true);
+}
+
+} // anonymous namespace
+
+ExtensionGenerator::ExtensionGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : descriptor_(descriptor),
+ options_(options) {
+ // Construct type_traits_.
+ if (descriptor_->is_repeated()) {
+ type_traits_ = "Repeated";
+ }
+
+ switch (descriptor_->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_ENUM:
+ type_traits_.append("EnumTypeTraits< ");
+ type_traits_.append(ClassName(descriptor_->enum_type(), true));
+ type_traits_.append(", ");
+ type_traits_.append(ClassName(descriptor_->enum_type(), true));
+ type_traits_.append("_IsValid>");
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ type_traits_.append("StringTypeTraits");
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ type_traits_.append("MessageTypeTraits< ");
+ type_traits_.append(ClassName(descriptor_->message_type(), true));
+ type_traits_.append(" >");
+ break;
+ default:
+ type_traits_.append("PrimitiveTypeTraits< ");
+ type_traits_.append(PrimitiveTypeName(descriptor_->cpp_type()));
+ type_traits_.append(" >");
+ break;
+ }
+}
+
+ExtensionGenerator::~ExtensionGenerator() {}
+
+void ExtensionGenerator::GenerateDeclaration(io::Printer* printer) {
+ map<string, string> vars;
+ vars["extendee" ] = ExtendeeClassName(descriptor_);
+ vars["number" ] = SimpleItoa(descriptor_->number());
+ vars["type_traits" ] = type_traits_;
+ vars["name" ] = descriptor_->name();
+ vars["field_type" ] = SimpleItoa(static_cast<int>(descriptor_->type()));
+ vars["packed" ] = descriptor_->options().packed() ? "true" : "false";
+ vars["constant_name"] = FieldConstantName(descriptor_);
+
+ // If this is a class member, it needs to be declared "static". Otherwise,
+ // it needs to be "extern". In the latter case, it also needs the DLL
+ // export/import specifier.
+ if (descriptor_->extension_scope() == NULL) {
+ vars["qualifier"] = "extern";
+ if (!options_.dllexport_decl.empty()) {
+ vars["qualifier"] = options_.dllexport_decl + " " + vars["qualifier"];
+ }
+ } else {
+ vars["qualifier"] = "static";
+ }
+
+ printer->Print(vars,
+ "static const int $constant_name$ = $number$;\n"
+ "$qualifier$ ::google::protobuf::internal::ExtensionIdentifier< $extendee$,\n"
+ " ::google::protobuf::internal::$type_traits$, $field_type$, $packed$ >\n"
+ " $name$;\n"
+ );
+
+}
+
+void ExtensionGenerator::GenerateDefinition(io::Printer* printer) {
+ // If this is a class member, it needs to be declared in its class scope.
+ string scope = (descriptor_->extension_scope() == NULL) ? "" :
+ ClassName(descriptor_->extension_scope(), false) + "::";
+ string name = scope + descriptor_->name();
+
+ map<string, string> vars;
+ vars["extendee" ] = ExtendeeClassName(descriptor_);
+ vars["type_traits" ] = type_traits_;
+ vars["name" ] = name;
+ vars["constant_name"] = FieldConstantName(descriptor_);
+ vars["default" ] = DefaultValue(descriptor_);
+ vars["field_type" ] = SimpleItoa(static_cast<int>(descriptor_->type()));
+ vars["packed" ] = descriptor_->options().packed() ? "true" : "false";
+ vars["scope" ] = scope;
+
+ if (descriptor_->cpp_type() == FieldDescriptor::CPPTYPE_STRING) {
+ // We need to declare a global string which will contain the default value.
+ // We cannot declare it at class scope because that would require exposing
+ // it in the header which would be annoying for other reasons. So we
+ // replace :: with _ in the name and declare it as a global.
+ string global_name = StringReplace(name, "::", "_", true);
+ vars["global_name"] = global_name;
+ printer->Print(vars,
+ "const ::std::string $global_name$_default($default$);\n");
+
+ // Update the default to refer to the string global.
+ vars["default"] = global_name + "_default";
+ }
+
+ // Likewise, class members need to declare the field constant variable.
+ if (descriptor_->extension_scope() != NULL) {
+ printer->Print(vars,
+ "#if !defined(_MSC_VER) || _MSC_VER >= 1900\n"
+ "const int $scope$$constant_name$;\n"
+ "#endif\n");
+ }
+
+ printer->Print(vars,
+ "::google::protobuf::internal::ExtensionIdentifier< $extendee$,\n"
+ " ::google::protobuf::internal::$type_traits$, $field_type$, $packed$ >\n"
+ " $name$($constant_name$, $default$);\n");
+}
+
+void ExtensionGenerator::GenerateRegistration(io::Printer* printer) {
+ map<string, string> vars;
+ vars["extendee" ] = ExtendeeClassName(descriptor_);
+ vars["number" ] = SimpleItoa(descriptor_->number());
+ vars["field_type" ] = SimpleItoa(static_cast<int>(descriptor_->type()));
+ vars["is_repeated"] = descriptor_->is_repeated() ? "true" : "false";
+ vars["is_packed" ] = (descriptor_->is_repeated() &&
+ descriptor_->options().packed())
+ ? "true" : "false";
+
+ switch (descriptor_->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_ENUM:
+ printer->Print(vars,
+ "::google::protobuf::internal::ExtensionSet::RegisterEnumExtension(\n"
+ " &$extendee$::default_instance(),\n"
+ " $number$, $field_type$, $is_repeated$, $is_packed$,\n");
+ printer->Print(
+ " &$type$_IsValid);\n",
+ "type", ClassName(descriptor_->enum_type(), true));
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ printer->Print(vars,
+ "::google::protobuf::internal::ExtensionSet::RegisterMessageExtension(\n"
+ " &$extendee$::default_instance(),\n"
+ " $number$, $field_type$, $is_repeated$, $is_packed$,\n");
+ printer->Print(
+ " &$type$::default_instance());\n",
+ "type", ClassName(descriptor_->message_type(), true));
+ break;
+ default:
+ printer->Print(vars,
+ "::google::protobuf::internal::ExtensionSet::RegisterExtension(\n"
+ " &$extendee$::default_instance(),\n"
+ " $number$, $field_type$, $is_repeated$, $is_packed$);\n");
+ break;
+ }
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.h
new file mode 100644
index 0000000000..1c1caf1f90
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_extension.h
@@ -0,0 +1,86 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_EXTENSION_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_EXTENSION_H__
+
+#include <string>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/cpp/cpp_options.h>
+
+namespace google {
+namespace protobuf {
+ class FieldDescriptor; // descriptor.h
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+// Generates code for an extension, which may be within the scope of some
+// message or may be at file scope. This is much simpler than FieldGenerator
+// since extensions are just simple identifiers with interesting types.
+class ExtensionGenerator {
+ public:
+ // See generator.cc for the meaning of dllexport_decl.
+ explicit ExtensionGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~ExtensionGenerator();
+
+ // Header stuff.
+ void GenerateDeclaration(io::Printer* printer);
+
+ // Source file stuff.
+ void GenerateDefinition(io::Printer* printer);
+
+ // Generate code to register the extension.
+ void GenerateRegistration(io::Printer* printer);
+
+ private:
+ const FieldDescriptor* descriptor_;
+ string type_traits_;
+ Options options_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.cc
new file mode 100644
index 0000000000..e2033c1acd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.cc
@@ -0,0 +1,201 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/compiler/cpp/cpp_primitive_field.h>
+#include <google/protobuf/compiler/cpp/cpp_string_field.h>
+#include <google/protobuf/compiler/cpp/cpp_enum_field.h>
+#include <google/protobuf/compiler/cpp/cpp_map_field.h>
+#include <google/protobuf/compiler/cpp/cpp_message_field.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+using internal::WireFormat;
+
+void SetCommonFieldVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables,
+ const Options& options) {
+ (*variables)["name"] = FieldName(descriptor);
+ (*variables)["index"] = SimpleItoa(descriptor->index());
+ (*variables)["number"] = SimpleItoa(descriptor->number());
+ (*variables)["classname"] = ClassName(FieldScope(descriptor), false);
+ (*variables)["declared_type"] = DeclaredTypeMethodName(descriptor->type());
+
+ // non_null_ptr_to_name is usable only if has_$name$ is true. It yields a
+ // pointer that will not be NULL. Subclasses of FieldGenerator may set
+ // (*variables)["non_null_ptr_to_name"] differently.
+ (*variables)["non_null_ptr_to_name"] =
+ StrCat("&this->", FieldName(descriptor), "()");
+
+ (*variables)["tag_size"] = SimpleItoa(
+ WireFormat::TagSize(descriptor->number(), descriptor->type()));
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? " PROTOBUF_DEPRECATED" : "";
+ (*variables)["deprecated_attr"] = descriptor->options().deprecated()
+ ? "GOOGLE_PROTOBUF_DEPRECATED_ATTR " : "";
+
+ (*variables)["cppget"] = "Get";
+
+ if (HasFieldPresence(descriptor->file())) {
+ (*variables)["set_hasbit"] =
+ "set_has_" + FieldName(descriptor) + "();";
+ (*variables)["clear_hasbit"] =
+ "clear_has_" + FieldName(descriptor) + "();";
+ } else {
+ (*variables)["set_hasbit"] = "";
+ (*variables)["clear_hasbit"] = "";
+ }
+
+ // By default, empty string, so that generic code used for both oneofs and
+ // singular fields can be written.
+ (*variables)["oneof_prefix"] = "";
+}
+
+void SetCommonOneofFieldVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables) {
+ const string prefix = descriptor->containing_oneof()->name() + "_.";
+ (*variables)["oneof_prefix"] = prefix;
+ (*variables)["oneof_name"] = descriptor->containing_oneof()->name();
+ (*variables)["non_null_ptr_to_name"] =
+ StrCat(prefix, (*variables)["name"], "_");
+}
+
+FieldGenerator::~FieldGenerator() {}
+
+void FieldGenerator::
+GenerateMergeFromCodedStreamWithPacking(io::Printer* printer) const {
+ // Reaching here indicates a bug. Cases are:
+ // - This FieldGenerator should support packing, but this method should be
+ // overridden.
+ // - This FieldGenerator doesn't support packing, and this method should
+ // never have been called.
+ GOOGLE_LOG(FATAL) << "GenerateMergeFromCodedStreamWithPacking() "
+ << "called on field generator that does not support packing.";
+
+}
+
+FieldGeneratorMap::FieldGeneratorMap(const Descriptor* descriptor,
+ const Options& options)
+ : descriptor_(descriptor),
+ options_(options),
+ field_generators_(
+ new google::protobuf::scoped_ptr<FieldGenerator>[descriptor->field_count()]) {
+ // Construct all the FieldGenerators.
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ field_generators_[i].reset(MakeGenerator(descriptor->field(i), options));
+ }
+}
+
+FieldGenerator* FieldGeneratorMap::MakeGenerator(const FieldDescriptor* field,
+ const Options& options) {
+ if (field->is_repeated()) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (field->is_map()) {
+ return new MapFieldGenerator(field, options);
+ } else {
+ return new RepeatedMessageFieldGenerator(field, options);
+ }
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // RepeatedStringFieldGenerator handles unknown ctypes.
+ case FieldOptions::STRING:
+ return new RepeatedStringFieldGenerator(field, options);
+ }
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return new RepeatedEnumFieldGenerator(field, options);
+ default:
+ return new RepeatedPrimitiveFieldGenerator(field, options);
+ }
+ } else if (field->containing_oneof()) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return new MessageOneofFieldGenerator(field, options);
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // StringOneofFieldGenerator handles unknown ctypes.
+ case FieldOptions::STRING:
+ return new StringOneofFieldGenerator(field, options);
+ }
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return new EnumOneofFieldGenerator(field, options);
+ default:
+ return new PrimitiveOneofFieldGenerator(field, options);
+ }
+ } else {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return new MessageFieldGenerator(field, options);
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // StringFieldGenerator handles unknown ctypes.
+ case FieldOptions::STRING:
+ return new StringFieldGenerator(field, options);
+ }
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return new EnumFieldGenerator(field, options);
+ default:
+ return new PrimitiveFieldGenerator(field, options);
+ }
+ }
+}
+
+FieldGeneratorMap::~FieldGeneratorMap() {}
+
+const FieldGenerator& FieldGeneratorMap::get(
+ const FieldDescriptor* field) const {
+ GOOGLE_CHECK_EQ(field->containing_type(), descriptor_);
+ return *field_generators_[field->index()];
+}
+
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.h
new file mode 100644
index 0000000000..3b01252780
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_field.h
@@ -0,0 +1,229 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_FIELD_H__
+
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/compiler/cpp/cpp_options.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+// Helper function: set variables in the map that are the same for all
+// field code generators.
+// ['name', 'index', 'number', 'classname', 'declared_type', 'tag_size',
+// 'deprecation'].
+void SetCommonFieldVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables,
+ const Options& options);
+
+void SetCommonOneofFieldVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables);
+
+class FieldGenerator {
+ public:
+ explicit FieldGenerator(const Options& options) : options_(options) {}
+ virtual ~FieldGenerator();
+
+ // Generate lines of code declaring members fields of the message class
+ // needed to represent this field. These are placed inside the message
+ // class.
+ virtual void GeneratePrivateMembers(io::Printer* printer) const = 0;
+
+ // Generate static default variable for this field. These are placed inside
+ // the message class. Most field types don't need this, so the default
+ // implementation is empty.
+ virtual void GenerateStaticMembers(io::Printer* /*printer*/) const {}
+
+ // Generate prototypes for accessors that will manipulate imported
+ // messages inline. These are for .proto.h headers.
+ //
+ // In .proto.h mode, the headers of imports are not #included. However,
+ // functions that manipulate the imported message types need access to
+ // the class definition of the imported message, meaning that the headers
+ // must be #included. To get around this, functions that manipulate
+ // imported message objects are defined as dependent functions in a base
+ // template class. By making them dependent template functions, the
+ // function templates will not be instantiated until they are called, so
+ // we can defer to those translation units to #include the necessary
+ // generated headers.
+ //
+ // See:
+ // http://en.cppreference.com/w/cpp/language/class_template#Implicit_instantiation
+ //
+ // Most field types don't need this, so the default implementation is empty.
+ virtual void GenerateDependentAccessorDeclarations(
+ io::Printer* printer) const {}
+
+ // Generate prototypes for all of the accessor functions related to this
+ // field. These are placed inside the class definition.
+ virtual void GenerateAccessorDeclarations(io::Printer* printer) const = 0;
+
+ // Generate inline definitions of depenent accessor functions for this field.
+ // These are placed inside the header after all class definitions.
+ virtual void GenerateDependentInlineAccessorDefinitions(
+ io::Printer* printer) const {}
+
+ // Generate inline definitions of accessor functions for this field.
+ // These are placed inside the header after all class definitions.
+ // In non-.proto.h mode, this generates dependent accessor functions as well.
+ virtual void GenerateInlineAccessorDefinitions(
+ io::Printer* printer, bool is_inline) const = 0;
+
+ // Generate definitions of accessors that aren't inlined. These are
+ // placed somewhere in the .cc file.
+ // Most field types don't need this, so the default implementation is empty.
+ virtual void GenerateNonInlineAccessorDefinitions(
+ io::Printer* /*printer*/) const {}
+
+ // Generate lines of code (statements, not declarations) which clear the
+ // field. This is used to define the clear_$name$() method as well as
+ // the Clear() method for the whole message.
+ virtual void GenerateClearingCode(io::Printer* printer) const = 0;
+
+ // Generate lines of code (statements, not declarations) which merges the
+ // contents of the field from the current message to the target message,
+ // which is stored in the generated code variable "from".
+ // This is used to fill in the MergeFrom method for the whole message.
+ // Details of this usage can be found in message.cc under the
+ // GenerateMergeFrom method.
+ virtual void GenerateMergingCode(io::Printer* printer) const = 0;
+
+ // Generate lines of code (statements, not declarations) which swaps
+ // this field and the corresponding field of another message, which
+ // is stored in the generated code variable "other". This is used to
+ // define the Swap method. Details of usage can be found in
+ // message.cc under the GenerateSwap method.
+ virtual void GenerateSwappingCode(io::Printer* printer) const = 0;
+
+ // Generate initialization code for private members declared by
+ // GeneratePrivateMembers(). These go into the message class's SharedCtor()
+ // method, invoked by each of the generated constructors.
+ virtual void GenerateConstructorCode(io::Printer* printer) const = 0;
+
+ // Generate any code that needs to go in the class's SharedDtor() method,
+ // invoked by the destructor.
+ // Most field types don't need this, so the default implementation is empty.
+ virtual void GenerateDestructorCode(io::Printer* /*printer*/) const {}
+
+ // Generate a manual destructor invocation for use when the message is on an
+ // arena. The code that this method generates will be executed inside a
+ // shared-for-the-whole-message-class method registered with OwnDestructor().
+ // The method should return |true| if it generated any code that requires a
+ // call; this allows the message generator to eliminate the OwnDestructor()
+ // registration if no fields require it.
+ virtual bool GenerateArenaDestructorCode(io::Printer* printer) const {
+ return false;
+ }
+
+ // Generate code that allocates the fields's default instance.
+ virtual void GenerateDefaultInstanceAllocator(io::Printer* /*printer*/)
+ const {}
+
+ // Generate code that should be run when ShutdownProtobufLibrary() is called,
+ // to delete all dynamically-allocated objects.
+ virtual void GenerateShutdownCode(io::Printer* /*printer*/) const {}
+
+ // Generate lines to decode this field, which will be placed inside the
+ // message's MergeFromCodedStream() method.
+ virtual void GenerateMergeFromCodedStream(io::Printer* printer) const = 0;
+
+ // Generate lines to decode this field from a packed value, which will be
+ // placed inside the message's MergeFromCodedStream() method.
+ virtual void GenerateMergeFromCodedStreamWithPacking(io::Printer* printer)
+ const;
+
+ // Generate lines to serialize this field, which are placed within the
+ // message's SerializeWithCachedSizes() method.
+ virtual void GenerateSerializeWithCachedSizes(io::Printer* printer) const = 0;
+
+ // Generate lines to serialize this field directly to the array "target",
+ // which are placed within the message's SerializeWithCachedSizesToArray()
+ // method. This must also advance "target" past the written bytes.
+ virtual void GenerateSerializeWithCachedSizesToArray(
+ io::Printer* printer) const = 0;
+
+ // Generate lines to compute the serialized size of this field, which
+ // are placed in the message's ByteSize() method.
+ virtual void GenerateByteSize(io::Printer* printer) const = 0;
+
+ protected:
+ const Options& options_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGenerator);
+};
+
+// Convenience class which constructs FieldGenerators for a Descriptor.
+class FieldGeneratorMap {
+ public:
+ FieldGeneratorMap(const Descriptor* descriptor, const Options& options);
+ ~FieldGeneratorMap();
+
+ const FieldGenerator& get(const FieldDescriptor* field) const;
+
+ private:
+ const Descriptor* descriptor_;
+ const Options& options_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<FieldGenerator> > field_generators_;
+
+ static FieldGenerator* MakeGenerator(const FieldDescriptor* field,
+ const Options& options);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGeneratorMap);
+};
+
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.cc
new file mode 100644
index 0000000000..b3eca660d3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.cc
@@ -0,0 +1,1058 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_file.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <set>
+
+#include <google/protobuf/compiler/cpp/cpp_enum.h>
+#include <google/protobuf/compiler/cpp/cpp_service.h>
+#include <google/protobuf/compiler/cpp/cpp_extension.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/compiler/cpp/cpp_message.h>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+// ===================================================================
+
+FileGenerator::FileGenerator(const FileDescriptor* file, const Options& options)
+ : file_(file),
+ options_(options),
+ message_generators_(
+ new google::protobuf::scoped_ptr<MessageGenerator>[file->message_type_count()]),
+ enum_generators_(
+ new google::protobuf::scoped_ptr<EnumGenerator>[file->enum_type_count()]),
+ service_generators_(
+ new google::protobuf::scoped_ptr<ServiceGenerator>[file->service_count()]),
+ extension_generators_(
+ new google::protobuf::scoped_ptr<ExtensionGenerator>[file->extension_count()]) {
+
+ for (int i = 0; i < file->message_type_count(); i++) {
+ message_generators_[i].reset(
+ new MessageGenerator(file->message_type(i), options));
+ }
+
+ for (int i = 0; i < file->enum_type_count(); i++) {
+ enum_generators_[i].reset(
+ new EnumGenerator(file->enum_type(i), options));
+ }
+
+ for (int i = 0; i < file->service_count(); i++) {
+ service_generators_[i].reset(
+ new ServiceGenerator(file->service(i), options));
+ }
+
+ for (int i = 0; i < file->extension_count(); i++) {
+ extension_generators_[i].reset(
+ new ExtensionGenerator(file->extension(i), options));
+ }
+
+ SplitStringUsing(file_->package(), ".", &package_parts_);
+}
+
+FileGenerator::~FileGenerator() {}
+
+void FileGenerator::GenerateProtoHeader(io::Printer* printer,
+ const string& info_path) {
+ if (!options_.proto_h) {
+ return;
+ }
+
+ string filename_identifier = FilenameIdentifier(file_->name());
+ GenerateTopHeaderGuard(printer, filename_identifier);
+
+
+ GenerateLibraryIncludes(printer);
+
+ for (int i = 0; i < file_->public_dependency_count(); i++) {
+ const FileDescriptor* dep = file_->public_dependency(i);
+ const char* extension = ".proto.h";
+ string dependency = StripProto(dep->name()) + extension;
+ printer->Print(
+ "#include \"$dependency$\" // IWYU pragma: export\n",
+ "dependency", dependency);
+ }
+
+ GenerateMetadataPragma(printer, info_path);
+
+ printer->Print(
+ "// @@protoc_insertion_point(includes)\n");
+
+
+ GenerateForwardDeclarations(printer);
+
+ // Open namespace.
+ GenerateNamespaceOpeners(printer);
+
+ GenerateGlobalStateFunctionDeclarations(printer);
+
+ printer->Print("\n");
+
+ GenerateEnumDefinitions(printer);
+
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+
+ GenerateMessageDefinitions(printer);
+
+ printer->Print("\n");
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+
+ GenerateServiceDefinitions(printer);
+
+ GenerateExtensionIdentifiers(printer);
+
+ printer->Print("\n");
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+
+ GenerateInlineFunctionDefinitions(printer);
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(namespace_scope)\n"
+ "\n");
+
+ // Close up namespace.
+ GenerateNamespaceClosers(printer);
+
+ // We need to specialize some templates in the ::google::protobuf namespace:
+ GenerateProto2NamespaceEnumSpecializations(printer);
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(global_scope)\n"
+ "\n");
+
+ GenerateBottomHeaderGuard(printer, filename_identifier);
+}
+
+void FileGenerator::GeneratePBHeader(io::Printer* printer,
+ const string& info_path) {
+ string filename_identifier =
+ FilenameIdentifier(file_->name() + (options_.proto_h ? ".pb.h" : ""));
+ GenerateTopHeaderGuard(printer, filename_identifier);
+
+ if (options_.proto_h) {
+ printer->Print("#include \"$basename$.proto.h\" // IWYU pragma: export\n",
+ "basename", StripProto(file_->name()));
+ } else {
+ GenerateLibraryIncludes(printer);
+ }
+ GenerateDependencyIncludes(printer);
+ GenerateMetadataPragma(printer, info_path);
+
+ printer->Print(
+ "// @@protoc_insertion_point(includes)\n");
+
+
+
+ // Open namespace.
+ GenerateNamespaceOpeners(printer);
+
+ if (!options_.proto_h) {
+ GenerateGlobalStateFunctionDeclarations(printer);
+ GenerateMessageForwardDeclarations(printer);
+
+ printer->Print("\n");
+
+ GenerateEnumDefinitions(printer);
+
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+
+ GenerateMessageDefinitions(printer);
+
+ printer->Print("\n");
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+
+ GenerateServiceDefinitions(printer);
+
+ GenerateExtensionIdentifiers(printer);
+
+ printer->Print("\n");
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+
+ GenerateInlineFunctionDefinitions(printer);
+ }
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(namespace_scope)\n");
+
+ // Close up namespace.
+ GenerateNamespaceClosers(printer);
+
+ if (!options_.proto_h) {
+ // We need to specialize some templates in the ::google::protobuf namespace:
+ GenerateProto2NamespaceEnumSpecializations(printer);
+ }
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(global_scope)\n"
+ "\n");
+
+ GenerateBottomHeaderGuard(printer, filename_identifier);
+}
+
+void FileGenerator::GenerateSource(io::Printer* printer) {
+ const bool use_system_include = IsWellKnownMessage(file_);
+ string header =
+ StripProto(file_->name()) + (options_.proto_h ? ".proto.h" : ".pb.h");
+ printer->Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "// source: $filename$\n"
+ "\n"
+ // The generated code calls accessors that might be deprecated. We don't
+ // want the compiler to warn in generated code.
+ "#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION\n"
+ "#include $left$$header$$right$\n"
+ "\n"
+ "#include <algorithm>\n" // for swap()
+ "\n"
+ "#include <google/protobuf/stubs/common.h>\n"
+ "#include <google/protobuf/stubs/port.h>\n"
+ "#include <google/protobuf/stubs/once.h>\n"
+ "#include <google/protobuf/io/coded_stream.h>\n"
+ "#include <google/protobuf/wire_format_lite_inl.h>\n",
+ "filename", file_->name(),
+ "header", header,
+ "left", use_system_include ? "<" : "\"",
+ "right", use_system_include ? ">" : "\"");
+
+ // Unknown fields implementation in lite mode uses StringOutputStream
+ if (!UseUnknownFieldSet(file_, options_) && file_->message_type_count() > 0) {
+ printer->Print(
+ "#include <google/protobuf/io/zero_copy_stream_impl_lite.h>\n");
+ }
+
+ if (HasDescriptorMethods(file_, options_)) {
+ printer->Print(
+ "#include <google/protobuf/descriptor.h>\n"
+ "#include <google/protobuf/generated_message_reflection.h>\n"
+ "#include <google/protobuf/reflection_ops.h>\n"
+ "#include <google/protobuf/wire_format.h>\n");
+ }
+
+ if (options_.proto_h) {
+ // Use the smaller .proto.h files.
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ const FileDescriptor* dep = file_->dependency(i);
+ const char* extension = ".proto.h";
+ string dependency = StripProto(dep->name()) + extension;
+ printer->Print(
+ "#include \"$dependency$\"\n",
+ "dependency", dependency);
+ }
+ }
+
+ printer->Print(
+ "// @@protoc_insertion_point(includes)\n");
+
+ GenerateNamespaceOpeners(printer);
+
+ if (HasDescriptorMethods(file_, options_)) {
+ printer->Print(
+ "\n"
+ "namespace {\n"
+ "\n");
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateDescriptorDeclarations(printer);
+ }
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ printer->Print(
+ "const ::google::protobuf::EnumDescriptor* $name$_descriptor_ = NULL;\n",
+ "name", ClassName(file_->enum_type(i), false));
+ }
+
+ if (HasGenericServices(file_, options_)) {
+ for (int i = 0; i < file_->service_count(); i++) {
+ printer->Print(
+ "const ::google::protobuf::ServiceDescriptor* $name$_descriptor_ = NULL;\n",
+ "name", file_->service(i)->name());
+ }
+ }
+
+ printer->Print(
+ "\n"
+ "} // namespace\n"
+ "\n");
+ }
+
+ // Define our externally-visible BuildDescriptors() function. (For the lite
+ // library, all this does is initialize default instances.)
+ GenerateBuildDescriptors(printer);
+
+ // Generate enums.
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateMethods(printer);
+ }
+
+ // Generate classes.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ printer->Print("\n");
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+ message_generators_[i]->GenerateClassMethods(printer);
+
+ printer->Print("#if PROTOBUF_INLINE_NOT_IN_HEADERS\n");
+ // Generate class inline methods.
+ message_generators_[i]->GenerateInlineMethods(printer,
+ /* is_inline = */ false);
+ printer->Print("#endif // PROTOBUF_INLINE_NOT_IN_HEADERS\n");
+ }
+
+ if (HasGenericServices(file_, options_)) {
+ // Generate services.
+ for (int i = 0; i < file_->service_count(); i++) {
+ if (i == 0) printer->Print("\n");
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+ service_generators_[i]->GenerateImplementation(printer);
+ }
+ }
+
+ // Define extensions.
+ for (int i = 0; i < file_->extension_count(); i++) {
+ extension_generators_[i]->GenerateDefinition(printer);
+ }
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(namespace_scope)\n");
+
+ GenerateNamespaceClosers(printer);
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(global_scope)\n");
+}
+
+class FileGenerator::ForwardDeclarations {
+ public:
+ ~ForwardDeclarations() {
+ for (map<string, ForwardDeclarations *>::iterator it = namespaces_.begin(),
+ end = namespaces_.end();
+ it != end; ++it) {
+ delete it->second;
+ }
+ namespaces_.clear();
+ }
+
+ ForwardDeclarations* AddOrGetNamespace(const string& ns_name) {
+ ForwardDeclarations*& ns = namespaces_[ns_name];
+ if (ns == NULL) {
+ ns = new ForwardDeclarations;
+ }
+ return ns;
+ }
+
+ map<string, const Descriptor*>& classes() { return classes_; }
+ map<string, const EnumDescriptor*>& enums() { return enums_; }
+
+ void Print(io::Printer* printer) const {
+ for (map<string, const EnumDescriptor *>::const_iterator
+ it = enums_.begin(),
+ end = enums_.end();
+ it != end; ++it) {
+ printer->Print("enum $enumname$ : int;\n", "enumname", it->first);
+ printer->Annotate("enumname", it->second);
+ printer->Print("bool $enumname$_IsValid(int value);\n", "enumname",
+ it->first);
+ }
+ for (map<string, const Descriptor *>::const_iterator it = classes_.begin(),
+ end = classes_.end();
+ it != end; ++it) {
+ printer->Print("class $classname$;\n", "classname", it->first);
+ printer->Annotate("classname", it->second);
+ }
+ for (map<string, ForwardDeclarations *>::const_iterator
+ it = namespaces_.begin(),
+ end = namespaces_.end();
+ it != end; ++it) {
+ printer->Print("namespace $nsname$ {\n",
+ "nsname", it->first);
+ it->second->Print(printer);
+ printer->Print("} // namespace $nsname$\n",
+ "nsname", it->first);
+ }
+ }
+
+
+ private:
+ map<string, ForwardDeclarations*> namespaces_;
+ map<string, const Descriptor*> classes_;
+ map<string, const EnumDescriptor*> enums_;
+};
+
+void FileGenerator::GenerateBuildDescriptors(io::Printer* printer) {
+ // AddDescriptors() is a file-level procedure which adds the encoded
+ // FileDescriptorProto for this .proto file to the global DescriptorPool for
+ // generated files (DescriptorPool::generated_pool()). It either runs at
+ // static initialization time (by default) or when default_instance() is
+ // called for the first time (in LITE_RUNTIME mode with
+ // GOOGLE_PROTOBUF_NO_STATIC_INITIALIZER flag enabled). This procedure also
+ // constructs default instances and registers extensions.
+ //
+ // Its sibling, AssignDescriptors(), actually pulls the compiled
+ // FileDescriptor from the DescriptorPool and uses it to populate all of
+ // the global variables which store pointers to the descriptor objects.
+ // It also constructs the reflection objects. It is called the first time
+ // anyone calls descriptor() or GetReflection() on one of the types defined
+ // in the file.
+
+ // In optimize_for = LITE_RUNTIME mode, we don't generate AssignDescriptors()
+ // and we only use AddDescriptors() to allocate default instances.
+ if (HasDescriptorMethods(file_, options_)) {
+ printer->Print(
+ "\n"
+ "void $assigndescriptorsname$() GOOGLE_ATTRIBUTE_COLD;\n"
+ "void $assigndescriptorsname$() {\n",
+ "assigndescriptorsname", GlobalAssignDescriptorsName(file_->name()));
+ printer->Indent();
+
+ // Make sure the file has found its way into the pool. If a descriptor
+ // is requested *during* static init then AddDescriptors() may not have
+ // been called yet, so we call it manually. Note that it's fine if
+ // AddDescriptors() is called multiple times.
+ printer->Print(
+ "$adddescriptorsname$();\n",
+ "adddescriptorsname", GlobalAddDescriptorsName(file_->name()));
+
+ // Get the file's descriptor from the pool.
+ printer->Print(
+ "const ::google::protobuf::FileDescriptor* file =\n"
+ " ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(\n"
+ " \"$filename$\");\n"
+ // Note that this GOOGLE_CHECK is necessary to prevent a warning about "file"
+ // being unused when compiling an empty .proto file.
+ "GOOGLE_CHECK(file != NULL);\n",
+ "filename", file_->name());
+
+ // Go through all the stuff defined in this file and generated code to
+ // assign the global descriptor pointers based on the file descriptor.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateDescriptorInitializer(printer, i);
+ }
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateDescriptorInitializer(printer, i);
+ }
+ if (HasGenericServices(file_, options_)) {
+ for (int i = 0; i < file_->service_count(); i++) {
+ service_generators_[i]->GenerateDescriptorInitializer(printer, i);
+ }
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+
+ // ---------------------------------------------------------------
+
+ // protobuf_AssignDescriptorsOnce(): The first time it is called, calls
+ // AssignDescriptors(). All later times, waits for the first call to
+ // complete and then returns.
+ printer->Print(
+ "namespace {\n"
+ "\n"
+ "GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);\n"
+ "inline void protobuf_AssignDescriptorsOnce() {\n"
+ " ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,\n"
+ " &$assigndescriptorsname$);\n"
+ "}\n"
+ "\n",
+ "assigndescriptorsname", GlobalAssignDescriptorsName(file_->name()));
+
+ // protobuf_RegisterTypes(): Calls
+ // MessageFactory::InternalRegisterGeneratedType() for each message type.
+ printer->Print(
+ "void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;\n"
+ "void protobuf_RegisterTypes(const ::std::string&) {\n"
+ " protobuf_AssignDescriptorsOnce();\n");
+ printer->Indent();
+
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateTypeRegistrations(printer);
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n"
+ "} // namespace\n");
+ }
+
+ // -----------------------------------------------------------------
+
+ // ShutdownFile(): Deletes descriptors, default instances, etc. on shutdown.
+ printer->Print(
+ "\n"
+ "void $shutdownfilename$() {\n",
+ "shutdownfilename", GlobalShutdownFileName(file_->name()));
+ printer->Indent();
+
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateShutdownCode(printer);
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n\n");
+
+ // -----------------------------------------------------------------
+
+ // Now generate the AddDescriptors() function.
+ PrintHandlingOptionalStaticInitializers(
+ file_, options_, printer,
+ // With static initializers.
+ // Note that we don't need any special synchronization in the following
+ // code
+ // because it is called at static init time before any threads exist.
+ "void $adddescriptorsname$() GOOGLE_ATTRIBUTE_COLD;\n"
+ "void $adddescriptorsname$() {\n"
+ " static bool already_here = false;\n"
+ " if (already_here) return;\n"
+ " already_here = true;\n"
+ " GOOGLE_PROTOBUF_VERIFY_VERSION;\n"
+ "\n",
+ // Without.
+ "void $adddescriptorsname$_impl() {\n"
+ " GOOGLE_PROTOBUF_VERIFY_VERSION;\n"
+ "\n",
+ // Vars.
+ "adddescriptorsname", GlobalAddDescriptorsName(file_->name()));
+
+ printer->Indent();
+
+ // Call the AddDescriptors() methods for all of our dependencies, to make
+ // sure they get added first.
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ const FileDescriptor* dependency = file_->dependency(i);
+ // Print the namespace prefix for the dependency.
+ string add_desc_name = QualifiedFileLevelSymbol(
+ dependency->package(), GlobalAddDescriptorsName(dependency->name()));
+ // Call its AddDescriptors function.
+ printer->Print(
+ "$name$();\n",
+ "name", add_desc_name);
+ }
+
+ if (HasDescriptorMethods(file_, options_)) {
+ // Embed the descriptor. We simply serialize the entire FileDescriptorProto
+ // and embed it as a string literal, which is parsed and built into real
+ // descriptors at initialization time.
+ FileDescriptorProto file_proto;
+ file_->CopyTo(&file_proto);
+ string file_data;
+ file_proto.SerializeToString(&file_data);
+
+#ifdef _MSC_VER
+ bool breakdown_large_file = true;
+#else
+ bool breakdown_large_file = false;
+#endif
+ // Workaround for MSVC: "Error C1091: compiler limit: string exceeds 65535
+ // bytes in length". Declare a static array of characters rather than use a
+ // string literal.
+ if (breakdown_large_file && file_data.size() > 65535) {
+ // This has to be explicitly marked as a signed char because the generated
+ // code puts negative values in the array, and sometimes plain char is
+ // unsigned. That implicit narrowing conversion is not allowed in C++11.
+ // <http://stackoverflow.com/questions/4434140/narrowing-conversions-in-c0x-is-it-just-me-or-does-this-sound-like-a-breakin>
+ // has details on why.
+ printer->Print(
+ "static const signed char descriptor[] = {\n");
+ printer->Indent();
+
+ // Only write 25 bytes per line.
+ static const int kBytesPerLine = 25;
+ for (int i = 0; i < file_data.size();) {
+ for (int j = 0; j < kBytesPerLine && i < file_data.size(); ++i, ++j) {
+ printer->Print(
+ "$char$, ",
+ "char", SimpleItoa(file_data[i]));
+ }
+ printer->Print(
+ "\n");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "};\n");
+
+ printer->Print(
+ "::google::protobuf::DescriptorPool::InternalAddGeneratedFile(descriptor, $size$);\n",
+ "size", SimpleItoa(file_data.size()));
+
+ } else {
+ printer->Print(
+ "::google::protobuf::DescriptorPool::InternalAddGeneratedFile(");
+
+ // Only write 40 bytes per line.
+ static const int kBytesPerLine = 40;
+ for (int i = 0; i < file_data.size(); i += kBytesPerLine) {
+ printer->Print("\n \"$data$\"",
+ "data",
+ EscapeTrigraphs(
+ CEscape(file_data.substr(i, kBytesPerLine))));
+ }
+ printer->Print(
+ ", $size$);\n",
+ "size", SimpleItoa(file_data.size()));
+ }
+
+ // Call MessageFactory::InternalRegisterGeneratedFile().
+ printer->Print(
+ "::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(\n"
+ " \"$filename$\", &protobuf_RegisterTypes);\n",
+ "filename", file_->name());
+ }
+
+ // Allocate and initialize default instances. This can't be done lazily
+ // since default instances are returned by simple accessors and are used with
+ // extensions. Speaking of which, we also register extensions at this time.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateDefaultInstanceAllocator(printer);
+ }
+ for (int i = 0; i < file_->extension_count(); i++) {
+ extension_generators_[i]->GenerateRegistration(printer);
+ }
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateDefaultInstanceInitializer(printer);
+ }
+
+ printer->Print(
+ "::google::protobuf::internal::OnShutdown(&$shutdownfilename$);\n",
+ "shutdownfilename", GlobalShutdownFileName(file_->name()));
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+
+ PrintHandlingOptionalStaticInitializers(
+ file_, options_, printer,
+ // With static initializers.
+ "// Force AddDescriptors() to be called at static initialization time.\n"
+ "struct StaticDescriptorInitializer_$filename$ {\n"
+ " StaticDescriptorInitializer_$filename$() {\n"
+ " $adddescriptorsname$();\n"
+ " }\n"
+ "} static_descriptor_initializer_$filename$_;\n",
+ // Without.
+ "GOOGLE_PROTOBUF_DECLARE_ONCE($adddescriptorsname$_once_);\n"
+ "void $adddescriptorsname$() {\n"
+ " ::google::protobuf::GoogleOnceInit(&$adddescriptorsname$_once_,\n"
+ " &$adddescriptorsname$_impl);\n"
+ "}\n",
+ // Vars.
+ "adddescriptorsname", GlobalAddDescriptorsName(file_->name()), "filename",
+ FilenameIdentifier(file_->name()));
+}
+
+void FileGenerator::GenerateNamespaceOpeners(io::Printer* printer) {
+ if (package_parts_.size() > 0) printer->Print("\n");
+
+ for (int i = 0; i < package_parts_.size(); i++) {
+ printer->Print("namespace $part$ {\n",
+ "part", package_parts_[i]);
+ }
+}
+
+void FileGenerator::GenerateNamespaceClosers(io::Printer* printer) {
+ if (package_parts_.size() > 0) printer->Print("\n");
+
+ for (int i = package_parts_.size() - 1; i >= 0; i--) {
+ printer->Print("} // namespace $part$\n",
+ "part", package_parts_[i]);
+ }
+}
+
+void FileGenerator::GenerateForwardDeclarations(io::Printer* printer) {
+ ForwardDeclarations decls;
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ FileGenerator dependency(file_->dependency(i), options_);
+ dependency.FillForwardDeclarations(&decls);
+ }
+ FillForwardDeclarations(&decls);
+ decls.Print(printer);
+}
+
+void FileGenerator::FillForwardDeclarations(ForwardDeclarations* decls) {
+ for (int i = 0; i < file_->public_dependency_count(); i++) {
+ FileGenerator dependency(file_->public_dependency(i), options_);
+ dependency.FillForwardDeclarations(decls);
+ }
+ for (int i = 0; i < package_parts_.size(); i++) {
+ decls = decls->AddOrGetNamespace(package_parts_[i]);
+ }
+ // Generate enum definitions.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->FillEnumForwardDeclarations(&decls->enums());
+ }
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ enum_generators_[i]->FillForwardDeclaration(&decls->enums());
+ }
+ // Generate forward declarations of classes.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->FillMessageForwardDeclarations(
+ &decls->classes());
+ }
+}
+
+void FileGenerator::GenerateTopHeaderGuard(io::Printer* printer,
+ const string& filename_identifier) {
+ // Generate top of header.
+ printer->Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "// source: $filename$\n"
+ "\n"
+ "#ifndef PROTOBUF_$filename_identifier$__INCLUDED\n"
+ "#define PROTOBUF_$filename_identifier$__INCLUDED\n"
+ "\n"
+ "#include <string>\n",
+ "filename", file_->name(), "filename_identifier", filename_identifier);
+ printer->Print("\n");
+}
+
+void FileGenerator::GenerateBottomHeaderGuard(
+ io::Printer* printer, const string& filename_identifier) {
+ printer->Print(
+ "#endif // PROTOBUF_$filename_identifier$__INCLUDED\n",
+ "filename_identifier", filename_identifier);
+}
+
+void FileGenerator::GenerateLibraryIncludes(io::Printer* printer) {
+
+ printer->Print(
+ "#include <google/protobuf/stubs/common.h>\n"
+ "\n");
+
+ // Verify the protobuf library header version is compatible with the protoc
+ // version before going any further.
+ printer->Print(
+ "#if GOOGLE_PROTOBUF_VERSION < $min_header_version$\n"
+ "#error This file was generated by a newer version of protoc which is\n"
+ "#error incompatible with your Protocol Buffer headers. Please update\n"
+ "#error your headers.\n"
+ "#endif\n"
+ "#if $protoc_version$ < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION\n"
+ "#error This file was generated by an older version of protoc which is\n"
+ "#error incompatible with your Protocol Buffer headers. Please\n"
+ "#error regenerate this file with a newer version of protoc.\n"
+ "#endif\n"
+ "\n",
+ "min_header_version",
+ SimpleItoa(protobuf::internal::kMinHeaderVersionForProtoc),
+ "protoc_version", SimpleItoa(GOOGLE_PROTOBUF_VERSION));
+
+ // OK, it's now safe to #include other files.
+ printer->Print(
+ "#include <google/protobuf/arena.h>\n"
+ "#include <google/protobuf/arenastring.h>\n"
+ "#include <google/protobuf/generated_message_util.h>\n");
+ if (UseUnknownFieldSet(file_, options_)) {
+ printer->Print(
+ "#include <google/protobuf/metadata.h>\n");
+ }
+ if (file_->message_type_count() > 0) {
+ if (HasDescriptorMethods(file_, options_)) {
+ printer->Print(
+ "#include <google/protobuf/message.h>\n");
+ } else {
+ printer->Print(
+ "#include <google/protobuf/message_lite.h>\n");
+ }
+ }
+ printer->Print(
+ "#include <google/protobuf/repeated_field.h>\n"
+ "#include <google/protobuf/extension_set.h>\n");
+ if (HasMapFields(file_)) {
+ printer->Print(
+ "#include <google/protobuf/map.h>\n");
+ if (HasDescriptorMethods(file_, options_)) {
+ printer->Print(
+ "#include <google/protobuf/map_field_inl.h>\n");
+ } else {
+ printer->Print(
+ "#include <google/protobuf/map_field_lite.h>\n");
+ }
+ }
+
+ if (HasEnumDefinitions(file_)) {
+ if (HasDescriptorMethods(file_, options_)) {
+ printer->Print(
+ "#include <google/protobuf/generated_enum_reflection.h>\n");
+ } else {
+ printer->Print(
+ "#include <google/protobuf/generated_enum_util.h>\n");
+ }
+ }
+
+ if (HasGenericServices(file_, options_)) {
+ printer->Print(
+ "#include <google/protobuf/service.h>\n");
+ }
+
+ if (UseUnknownFieldSet(file_, options_) && file_->message_type_count() > 0) {
+ printer->Print(
+ "#include <google/protobuf/unknown_field_set.h>\n");
+ }
+
+
+ if (IsAnyMessage(file_)) {
+ printer->Print(
+ "#include <google/protobuf/any.h>\n");
+ }
+}
+
+void FileGenerator::GenerateMetadataPragma(io::Printer* printer,
+ const string& info_path) {
+ if (!info_path.empty() && !options_.annotation_pragma_name.empty() &&
+ !options_.annotation_guard_name.empty()) {
+ printer->Print(
+ "#ifdef $guard$\n"
+ "#pragma $pragma$ \"$info_path$\"\n"
+ "#endif // $guard$\n",
+ "guard", options_.annotation_guard_name, "pragma",
+ options_.annotation_pragma_name, "info_path", info_path);
+ }
+}
+
+void FileGenerator::GenerateDependencyIncludes(io::Printer* printer) {
+ set<string> public_import_names;
+ for (int i = 0; i < file_->public_dependency_count(); i++) {
+ public_import_names.insert(file_->public_dependency(i)->name());
+ }
+
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ const bool use_system_include = IsWellKnownMessage(file_->dependency(i));
+ const string& name = file_->dependency(i)->name();
+ bool public_import = (public_import_names.count(name) != 0);
+
+
+ printer->Print(
+ "#include $left$$dependency$.pb.h$right$$iwyu$\n",
+ "dependency", StripProto(name),
+ "iwyu", (public_import) ? " // IWYU pragma: export" : "",
+ "left", use_system_include ? "<" : "\"",
+ "right", use_system_include ? ">" : "\"");
+ }
+}
+
+void FileGenerator::GenerateGlobalStateFunctionDeclarations(
+ io::Printer* printer) {
+ // Forward-declare the AddDescriptors, AssignDescriptors, and ShutdownFile
+ // functions, so that we can declare them to be friends of each class.
+ printer->Print(
+ "\n"
+ "// Internal implementation detail -- do not call these.\n"
+ "void $dllexport_decl$$adddescriptorsname$();\n",
+ "adddescriptorsname", GlobalAddDescriptorsName(file_->name()),
+ "dllexport_decl",
+ options_.dllexport_decl.empty() ? "" : options_.dllexport_decl + " ");
+
+ printer->Print(
+ // Note that we don't put dllexport_decl on these because they are only
+ // called by the .pb.cc file in which they are defined.
+ "void $assigndescriptorsname$();\n"
+ "void $shutdownfilename$();\n"
+ "\n",
+ "assigndescriptorsname", GlobalAssignDescriptorsName(file_->name()),
+ "shutdownfilename", GlobalShutdownFileName(file_->name()));
+}
+
+void FileGenerator::GenerateMessageForwardDeclarations(io::Printer* printer) {
+ map<string, const Descriptor*> classes;
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->FillMessageForwardDeclarations(&classes);
+ }
+ for (map<string, const Descriptor *>::const_iterator it = classes.begin(),
+ end = classes.end();
+ it != end; ++it) {
+ printer->Print("class $classname$;\n", "classname", it->first);
+ printer->Annotate("classname", it->second);
+ }
+}
+
+void FileGenerator::GenerateMessageDefinitions(io::Printer* printer) {
+ // Generate class definitions.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ if (i > 0) {
+ printer->Print("\n");
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+ message_generators_[i]->GenerateClassDefinition(printer);
+ }
+}
+
+void FileGenerator::GenerateEnumDefinitions(io::Printer* printer) {
+ // Generate enum definitions.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateEnumDefinitions(printer);
+ }
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateDefinition(printer);
+ }
+}
+
+void FileGenerator::GenerateServiceDefinitions(io::Printer* printer) {
+ if (HasGenericServices(file_, options_)) {
+ // Generate service definitions.
+ for (int i = 0; i < file_->service_count(); i++) {
+ if (i > 0) {
+ printer->Print("\n");
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+ service_generators_[i]->GenerateDeclarations(printer);
+ }
+
+ printer->Print("\n");
+ printer->Print(kThickSeparator);
+ printer->Print("\n");
+ }
+}
+
+void FileGenerator::GenerateExtensionIdentifiers(io::Printer* printer) {
+ // Declare extension identifiers.
+ for (int i = 0; i < file_->extension_count(); i++) {
+ extension_generators_[i]->GenerateDeclaration(printer);
+ }
+}
+
+void FileGenerator::GenerateInlineFunctionDefinitions(io::Printer* printer) {
+ // An aside about inline functions in .proto.h mode:
+ //
+ // The PROTOBUF_INLINE_NOT_IN_HEADERS symbol controls conditionally
+ // moving much of the inline functions to the .pb.cc file, which can be a
+ // significant performance benefit for compilation time, at the expense
+ // of non-inline function calls.
+ //
+ // However, in .proto.h mode, the definition of the internal dependent
+ // base class must remain in the header, and can never be out-lined. The
+ // dependent base class also needs access to has-bit manipuation
+ // functions, so the has-bit functions must be unconditionally inlined in
+ // proto_h mode.
+ //
+ // This gives us three flavors of functions:
+ //
+ // 1. Functions on the message not used by the internal dependent base
+ // class: in .proto.h mode, only some functions are defined on the
+ // message class; others are defined on the dependent base class.
+ // These are guarded and can be out-lined. These are generated by
+ // GenerateInlineMethods, and include has_* bit functions in
+ // non-proto_h mode.
+ //
+ // 2. Functions on the internal dependent base class: these functions
+ // are dependent on a template parameter, so they always need to
+ // remain in the header.
+ //
+ // 3. Functions on the message that are used by the dependent base: the
+ // dependent base class down casts itself to the message
+ // implementation class to access these functions (the has_* bit
+ // manipulation functions). Unlike #1, these functions must
+ // unconditionally remain in the header. These are emitted by
+ // GenerateDependentInlineMethods, even though they are not actually
+ // dependent.
+
+ printer->Print("#if !PROTOBUF_INLINE_NOT_IN_HEADERS\n");
+ // Generate class inline methods.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ if (i > 0) {
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+ message_generators_[i]->GenerateInlineMethods(printer,
+ /* is_inline = */ true);
+ }
+ printer->Print("#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS\n");
+
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ if (i > 0) {
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+ // Methods of the dependent base class must always be inline in the header.
+ message_generators_[i]->GenerateDependentInlineMethods(printer);
+ }
+}
+
+void FileGenerator::GenerateProto2NamespaceEnumSpecializations(
+ io::Printer* printer) {
+ // Emit GetEnumDescriptor specializations into google::protobuf namespace:
+ if (HasEnumDefinitions(file_)) {
+ // The SWIG conditional is to avoid a null-pointer dereference
+ // (bug 1984964) in swig-1.3.21 resulting from the following syntax:
+ // namespace X { void Y<Z::W>(); }
+ // which appears in GetEnumDescriptor() specializations.
+ printer->Print(
+ "\n"
+ "#ifndef SWIG\n"
+ "namespace google {\nnamespace protobuf {\n"
+ "\n");
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateGetEnumDescriptorSpecializations(printer);
+ }
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateGetEnumDescriptorSpecializations(printer);
+ }
+ printer->Print(
+ "\n"
+ "} // namespace protobuf\n} // namespace google\n"
+ "#endif // SWIG\n");
+ }
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.h
new file mode 100644
index 0000000000..5dcf692bcd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_file.h
@@ -0,0 +1,164 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_FILE_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_FILE_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+#include <google/protobuf/compiler/cpp/cpp_options.h>
+
+namespace google {
+namespace protobuf {
+ class FileDescriptor; // descriptor.h
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class EnumGenerator; // enum.h
+class MessageGenerator; // message.h
+class ServiceGenerator; // service.h
+class ExtensionGenerator; // extension.h
+
+class FileGenerator {
+ public:
+ // See generator.cc for the meaning of dllexport_decl.
+ FileGenerator(const FileDescriptor* file, const Options& options);
+ ~FileGenerator();
+
+ // info_path, if non-empty, should be the path (relative to printer's output)
+ // to the metadata file describing this proto header.
+ void GenerateProtoHeader(io::Printer* printer,
+ const string& info_path);
+ // info_path, if non-empty, should be the path (relative to printer's output)
+ // to the metadata file describing this PB header.
+ void GeneratePBHeader(io::Printer* printer,
+ const string& info_path);
+ void GenerateSource(io::Printer* printer);
+
+ private:
+ // Internal type used by GenerateForwardDeclarations (defined in file.cc).
+ class ForwardDeclarations;
+
+ // Generate the BuildDescriptors() procedure, which builds all descriptors
+ // for types defined in the file.
+ void GenerateBuildDescriptors(io::Printer* printer);
+
+ void GenerateNamespaceOpeners(io::Printer* printer);
+ void GenerateNamespaceClosers(io::Printer* printer);
+
+ // For other imports, generates their forward-declarations.
+ void GenerateForwardDeclarations(io::Printer* printer);
+
+ // Internal helper used by GenerateForwardDeclarations: fills 'decls'
+ // with all necessary forward-declarations for this file and its
+ // transient depednencies.
+ void FillForwardDeclarations(ForwardDeclarations* decls);
+
+ // Generates top or bottom of a header file.
+ void GenerateTopHeaderGuard(io::Printer* printer,
+ const string& filename_identifier);
+ void GenerateBottomHeaderGuard(io::Printer* printer,
+ const string& filename_identifier);
+
+ // Generates #include directives.
+ void GenerateLibraryIncludes(io::Printer* printer);
+ void GenerateDependencyIncludes(io::Printer* printer);
+
+ // Generate a pragma to pull in metadata using the given info_path (if
+ // non-empty). info_path should be relative to printer's output.
+ void GenerateMetadataPragma(io::Printer* printer, const string& info_path);
+
+ // Generates a couple of different pieces before definitions:
+ void GenerateGlobalStateFunctionDeclarations(io::Printer* printer);
+
+ // Generates types for classes.
+ void GenerateMessageDefinitions(io::Printer* printer);
+
+ // Generates forward-declarations for just this file's classes. This is
+ // used for .pb.h headers, but not in proto_h mode.
+ void GenerateMessageForwardDeclarations(io::Printer* printer);
+
+ // Fills in types for forward declarations. This is used internally, and
+ // also by other FileGenerators to determine imports' declarations.
+ void FillMessageForwardDeclarations(ForwardDeclarations* decls);
+ void FillMessageDefinitions(ForwardDeclarations* decls);
+
+ // Generates enum definitions.
+ void GenerateEnumForwardDeclarations(io::Printer* printer);
+ void FillEnumForwardDeclarations(ForwardDeclarations* decls);
+ void GenerateEnumDefinitions(io::Printer* printer);
+
+ // Generates generic service definitions.
+ void GenerateServiceDefinitions(io::Printer* printer);
+
+ // Generates extension identifiers.
+ void GenerateExtensionIdentifiers(io::Printer* printer);
+
+ // Generates inline function defintions.
+ void GenerateInlineFunctionDefinitions(io::Printer* printer);
+
+ void GenerateProto2NamespaceEnumSpecializations(io::Printer* printer);
+
+ const FileDescriptor* file_;
+ const Options options_;
+
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<MessageGenerator> > message_generators_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<EnumGenerator> > enum_generators_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<ServiceGenerator> > service_generators_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<ExtensionGenerator> > extension_generators_;
+
+ // E.g. if the package is foo.bar, package_parts_ is {"foo", "bar"}.
+ vector<string> package_parts_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_FILE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.cc
new file mode 100644
index 0000000000..31d189c255
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.cc
@@ -0,0 +1,168 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_generator.h>
+
+#include <vector>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <utility>
+
+#include <google/protobuf/compiler/cpp/cpp_file.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+CppGenerator::CppGenerator() {}
+CppGenerator::~CppGenerator() {}
+
+bool CppGenerator::Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const {
+ vector<pair<string, string> > options;
+ ParseGeneratorParameter(parameter, &options);
+
+ // -----------------------------------------------------------------
+ // parse generator options
+
+ // TODO(kenton): If we ever have more options, we may want to create a
+ // class that encapsulates them which we can pass down to all the
+ // generator classes. Currently we pass dllexport_decl down to all of
+ // them via the constructors, but we don't want to have to add another
+ // constructor parameter for every option.
+
+ // If the dllexport_decl option is passed to the compiler, we need to write
+ // it in front of every symbol that should be exported if this .proto is
+ // compiled into a Windows DLL. E.g., if the user invokes the protocol
+ // compiler as:
+ // protoc --cpp_out=dllexport_decl=FOO_EXPORT:outdir foo.proto
+ // then we'll define classes like this:
+ // class FOO_EXPORT Foo {
+ // ...
+ // }
+ // FOO_EXPORT is a macro which should expand to __declspec(dllexport) or
+ // __declspec(dllimport) depending on what is being compiled.
+ //
+ Options file_options;
+
+ for (int i = 0; i < options.size(); i++) {
+ if (options[i].first == "dllexport_decl") {
+ file_options.dllexport_decl = options[i].second;
+ } else if (options[i].first == "safe_boundary_check") {
+ file_options.safe_boundary_check = true;
+ } else if (options[i].first == "annotate_headers") {
+ file_options.annotate_headers = true;
+ } else if (options[i].first == "annotation_pragma_name") {
+ file_options.annotation_pragma_name = options[i].second;
+ } else if (options[i].first == "annotation_guard_name") {
+ file_options.annotation_guard_name = options[i].second;
+ } else if (options[i].first == "lite") {
+ file_options.enforce_lite = true;
+ } else {
+ *error = "Unknown generator option: " + options[i].first;
+ return false;
+ }
+ }
+
+ // -----------------------------------------------------------------
+
+
+ string basename = StripProto(file->name());
+
+ FileGenerator file_generator(file, file_options);
+
+ // Generate header(s).
+ if (file_options.proto_h) {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ generator_context->Open(basename + ".proto.h"));
+ GeneratedCodeInfo annotations;
+ io::AnnotationProtoCollector<GeneratedCodeInfo> annotation_collector(
+ &annotations);
+ string info_path = basename + ".proto.h.meta";
+ io::Printer printer(output.get(), '$', file_options.annotate_headers
+ ? &annotation_collector
+ : NULL);
+ file_generator.GenerateProtoHeader(
+ &printer, file_options.annotate_headers ? info_path : "");
+ if (file_options.annotate_headers) {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> info_output(
+ generator_context->Open(info_path));
+ annotations.SerializeToZeroCopyStream(info_output.get());
+ }
+ }
+
+ basename.append(".pb");
+ {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ generator_context->Open(basename + ".h"));
+ GeneratedCodeInfo annotations;
+ io::AnnotationProtoCollector<GeneratedCodeInfo> annotation_collector(
+ &annotations);
+ string info_path = basename + ".h.meta";
+ io::Printer printer(output.get(), '$', file_options.annotate_headers
+ ? &annotation_collector
+ : NULL);
+ file_generator.GeneratePBHeader(
+ &printer, file_options.annotate_headers ? info_path : "");
+ if (file_options.annotate_headers) {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> info_output(
+ generator_context->Open(info_path));
+ annotations.SerializeToZeroCopyStream(info_output.get());
+ }
+ }
+
+ // Generate cc file.
+ {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ generator_context->Open(basename + ".cc"));
+ io::Printer printer(output.get(), '$');
+ file_generator.GenerateSource(&printer);
+ }
+
+ return true;
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.h
new file mode 100644
index 0000000000..3d517cf4a5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_generator.h
@@ -0,0 +1,72 @@
+// 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.
+//
+// Generates C++ code for a given .proto file.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_GENERATOR_H__
+
+#include <string>
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+// CodeGenerator implementation which generates a C++ source file and
+// header. If you create your own protocol compiler binary and you want
+// it to support C++ output, you can do so by registering an instance of this
+// CodeGenerator with the CommandLineInterface in your main() function.
+class LIBPROTOC_EXPORT CppGenerator : public CodeGenerator {
+ public:
+ CppGenerator();
+ ~CppGenerator();
+
+ // implements CodeGenerator ----------------------------------------
+ bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CppGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.cc
new file mode 100644
index 0000000000..2ad4d36a58
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.cc
@@ -0,0 +1,704 @@
+// 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.
+
+#include <limits>
+#include <map>
+#include <vector>
+#include <google/protobuf/stubs/hash.h>
+
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+namespace {
+
+static const char kAnyMessageName[] = "Any";
+static const char kAnyProtoFile[] = "google/protobuf/any.proto";
+static const char kGoogleProtobufPrefix[] = "google/protobuf/";
+
+string DotsToUnderscores(const string& name) {
+ return StringReplace(name, ".", "_", true);
+}
+
+string DotsToColons(const string& name) {
+ return StringReplace(name, ".", "::", true);
+}
+
+const char* const kKeywordList[] = {
+ "alignas", "alignof", "and", "and_eq", "asm", "auto", "bitand", "bitor",
+ "bool", "break", "case", "catch", "char", "class", "compl", "const",
+ "constexpr", "const_cast", "continue", "decltype", "default", "delete", "do",
+ "double", "dynamic_cast", "else", "enum", "explicit", "export", "extern",
+ "false", "float", "for", "friend", "goto", "if", "inline", "int", "long",
+ "mutable", "namespace", "new", "noexcept", "not", "not_eq", "NULL",
+ "operator", "or", "or_eq", "private", "protected", "public", "register",
+ "reinterpret_cast", "return", "short", "signed", "sizeof", "static",
+ "static_assert", "static_cast", "struct", "switch", "template", "this",
+ "thread_local", "throw", "true", "try", "typedef", "typeid", "typename",
+ "union", "unsigned", "using", "virtual", "void", "volatile", "wchar_t",
+ "while", "xor", "xor_eq"
+};
+
+hash_set<string> MakeKeywordsMap() {
+ hash_set<string> result;
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(kKeywordList); i++) {
+ result.insert(kKeywordList[i]);
+ }
+ return result;
+}
+
+hash_set<string> kKeywords = MakeKeywordsMap();
+
+// Returns whether the provided descriptor has an extension. This includes its
+// nested types.
+bool HasExtension(const Descriptor* descriptor) {
+ if (descriptor->extension_count() > 0) {
+ return true;
+ }
+ for (int i = 0; i < descriptor->nested_type_count(); ++i) {
+ if (HasExtension(descriptor->nested_type(i))) {
+ return true;
+ }
+ }
+ return false;
+}
+
+} // namespace
+
+string UnderscoresToCamelCase(const string& input, bool cap_next_letter) {
+ string result;
+ // Note: I distrust ctype.h due to locales.
+ for (int i = 0; i < input.size(); i++) {
+ if ('a' <= input[i] && input[i] <= 'z') {
+ if (cap_next_letter) {
+ result += input[i] + ('A' - 'a');
+ } else {
+ result += input[i];
+ }
+ cap_next_letter = false;
+ } else if ('A' <= input[i] && input[i] <= 'Z') {
+ // Capital letters are left as-is.
+ result += input[i];
+ cap_next_letter = false;
+ } else if ('0' <= input[i] && input[i] <= '9') {
+ result += input[i];
+ cap_next_letter = true;
+ } else {
+ cap_next_letter = true;
+ }
+ }
+ return result;
+}
+
+const char kThickSeparator[] =
+ "// ===================================================================\n";
+const char kThinSeparator[] =
+ "// -------------------------------------------------------------------\n";
+
+string ClassName(const Descriptor* descriptor, bool qualified) {
+
+ // Find "outer", the descriptor of the top-level message in which
+ // "descriptor" is embedded.
+ const Descriptor* outer = descriptor;
+ while (outer->containing_type() != NULL) outer = outer->containing_type();
+
+ const string& outer_name = outer->full_name();
+ string inner_name = descriptor->full_name().substr(outer_name.size());
+
+ if (qualified) {
+ return "::" + DotsToColons(outer_name) + DotsToUnderscores(inner_name);
+ } else {
+ return outer->name() + DotsToUnderscores(inner_name);
+ }
+}
+
+string ClassName(const EnumDescriptor* enum_descriptor, bool qualified) {
+ if (enum_descriptor->containing_type() == NULL) {
+ if (qualified) {
+ return "::" + DotsToColons(enum_descriptor->full_name());
+ } else {
+ return enum_descriptor->name();
+ }
+ } else {
+ string result = ClassName(enum_descriptor->containing_type(), qualified);
+ result += '_';
+ result += enum_descriptor->name();
+ return result;
+ }
+}
+
+
+string DependentBaseClassTemplateName(const Descriptor* descriptor) {
+ return ClassName(descriptor, false) + "_InternalBase";
+}
+
+string SuperClassName(const Descriptor* descriptor, const Options& options) {
+ return HasDescriptorMethods(descriptor->file(), options)
+ ? "::google::protobuf::Message"
+ : "::google::protobuf::MessageLite";
+}
+
+string DependentBaseDownCast() {
+ return "reinterpret_cast<T*>(this)->";
+}
+
+string DependentBaseConstDownCast() {
+ return "reinterpret_cast<const T*>(this)->";
+}
+
+string FieldName(const FieldDescriptor* field) {
+ string result = field->name();
+ LowerString(&result);
+ if (kKeywords.count(result) > 0) {
+ result.append("_");
+ }
+ return result;
+}
+
+string EnumValueName(const EnumValueDescriptor* enum_value) {
+ string result = enum_value->name();
+ if (kKeywords.count(result) > 0) {
+ result.append("_");
+ }
+ return result;
+}
+
+string FieldConstantName(const FieldDescriptor *field) {
+ string field_name = UnderscoresToCamelCase(field->name(), true);
+ string result = "k" + field_name + "FieldNumber";
+
+ if (!field->is_extension() &&
+ field->containing_type()->FindFieldByCamelcaseName(
+ field->camelcase_name()) != field) {
+ // This field's camelcase name is not unique. As a hack, add the field
+ // number to the constant name. This makes the constant rather useless,
+ // but what can we do?
+ result += "_" + SimpleItoa(field->number());
+ }
+
+ return result;
+}
+
+bool IsFieldDependent(const FieldDescriptor* field) {
+ if (field->containing_oneof() != NULL &&
+ field->cpp_type() == FieldDescriptor::CPPTYPE_STRING) {
+ return true;
+ }
+ if (field->is_map()) {
+ const Descriptor* map_descriptor = field->message_type();
+ for (int i = 0; i < map_descriptor->field_count(); i++) {
+ if (IsFieldDependent(map_descriptor->field(i))) {
+ return true;
+ }
+ }
+ return false;
+ }
+ if (field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ return false;
+ }
+ if (field->containing_oneof() != NULL) {
+ // Oneof fields will always be dependent.
+ //
+ // This is a unique case for field codegen. Field generators are
+ // responsible for generating all the field-specific accessor
+ // functions, except for the clear_*() function; instead, field
+ // generators produce inline clearing code.
+ //
+ // For non-oneof fields, the Message class uses the inline clearing
+ // code to define the field's clear_*() function, as well as in the
+ // destructor. For oneof fields, the Message class generates a much
+ // more complicated clear_*() function, which clears only the oneof
+ // member that is set, in addition to clearing methods for each of the
+ // oneof members individually.
+ //
+ // Since oneofs do not have their own generator class, the Message code
+ // generation logic would be significantly complicated in order to
+ // split dependent and non-dependent manipulation logic based on
+ // whether the oneof truly needs to be dependent; so, for oneof fields,
+ // we just assume it (and its constituents) should be manipulated by a
+ // dependent base class function.
+ //
+ // This is less precise than how dependent message-typed fields are
+ // handled, but the cost is limited to only the generated code for the
+ // oneof field, which seems like an acceptable tradeoff.
+ return true;
+ }
+ if (field->file() == field->message_type()->file()) {
+ return false;
+ }
+ return true;
+}
+
+string DependentTypeName(const FieldDescriptor* field) {
+ return "InternalBase_" + field->name() + "_T";
+}
+
+string FieldMessageTypeName(const FieldDescriptor* field) {
+ // Note: The Google-internal version of Protocol Buffers uses this function
+ // as a hook point for hacks to support legacy code.
+ return ClassName(field->message_type(), true);
+}
+
+string StripProto(const string& filename) {
+ if (HasSuffixString(filename, ".protodevel")) {
+ return StripSuffixString(filename, ".protodevel");
+ } else {
+ return StripSuffixString(filename, ".proto");
+ }
+}
+
+const char* PrimitiveTypeName(FieldDescriptor::CppType type) {
+ switch (type) {
+ case FieldDescriptor::CPPTYPE_INT32 : return "::google::protobuf::int32";
+ case FieldDescriptor::CPPTYPE_INT64 : return "::google::protobuf::int64";
+ case FieldDescriptor::CPPTYPE_UINT32 : return "::google::protobuf::uint32";
+ case FieldDescriptor::CPPTYPE_UINT64 : return "::google::protobuf::uint64";
+ case FieldDescriptor::CPPTYPE_DOUBLE : return "double";
+ case FieldDescriptor::CPPTYPE_FLOAT : return "float";
+ case FieldDescriptor::CPPTYPE_BOOL : return "bool";
+ case FieldDescriptor::CPPTYPE_ENUM : return "int";
+ case FieldDescriptor::CPPTYPE_STRING : return "::std::string";
+ case FieldDescriptor::CPPTYPE_MESSAGE: return NULL;
+
+ // No default because we want the compiler to complain if any new
+ // CppTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+const char* DeclaredTypeMethodName(FieldDescriptor::Type type) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32 : return "Int32";
+ case FieldDescriptor::TYPE_INT64 : return "Int64";
+ case FieldDescriptor::TYPE_UINT32 : return "UInt32";
+ case FieldDescriptor::TYPE_UINT64 : return "UInt64";
+ case FieldDescriptor::TYPE_SINT32 : return "SInt32";
+ case FieldDescriptor::TYPE_SINT64 : return "SInt64";
+ case FieldDescriptor::TYPE_FIXED32 : return "Fixed32";
+ case FieldDescriptor::TYPE_FIXED64 : return "Fixed64";
+ case FieldDescriptor::TYPE_SFIXED32: return "SFixed32";
+ case FieldDescriptor::TYPE_SFIXED64: return "SFixed64";
+ case FieldDescriptor::TYPE_FLOAT : return "Float";
+ case FieldDescriptor::TYPE_DOUBLE : return "Double";
+
+ case FieldDescriptor::TYPE_BOOL : return "Bool";
+ case FieldDescriptor::TYPE_ENUM : return "Enum";
+
+ case FieldDescriptor::TYPE_STRING : return "String";
+ case FieldDescriptor::TYPE_BYTES : return "Bytes";
+ case FieldDescriptor::TYPE_GROUP : return "Group";
+ case FieldDescriptor::TYPE_MESSAGE : return "Message";
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return "";
+}
+
+string Int32ToString(int number) {
+ // gcc rejects the decimal form of kint32min.
+ if (number == kint32min) {
+ GOOGLE_COMPILE_ASSERT(kint32min == (~0x7fffffff), kint32min_value_error);
+ return "(~0x7fffffff)";
+ } else {
+ return SimpleItoa(number);
+ }
+}
+
+string Int64ToString(int64 number) {
+ // gcc rejects the decimal form of kint64min
+ if (number == kint64min) {
+ // Make sure we are in a 2's complement system.
+ GOOGLE_COMPILE_ASSERT(kint64min == GOOGLE_LONGLONG(~0x7fffffffffffffff),
+ kint64min_value_error);
+ return "GOOGLE_LONGLONG(~0x7fffffffffffffff)";
+ }
+ return "GOOGLE_LONGLONG(" + SimpleItoa(number) + ")";
+}
+
+string DefaultValue(const FieldDescriptor* field) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return Int32ToString(field->default_value_int32());
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return SimpleItoa(field->default_value_uint32()) + "u";
+ case FieldDescriptor::CPPTYPE_INT64:
+ return Int64ToString(field->default_value_int64());
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return "GOOGLE_ULONGLONG(" + SimpleItoa(field->default_value_uint64())+ ")";
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value = field->default_value_double();
+ if (value == numeric_limits<double>::infinity()) {
+ return "::google::protobuf::internal::Infinity()";
+ } else if (value == -numeric_limits<double>::infinity()) {
+ return "-::google::protobuf::internal::Infinity()";
+ } else if (value != value) {
+ return "::google::protobuf::internal::NaN()";
+ } else {
+ return SimpleDtoa(value);
+ }
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ {
+ float value = field->default_value_float();
+ if (value == numeric_limits<float>::infinity()) {
+ return "static_cast<float>(::google::protobuf::internal::Infinity())";
+ } else if (value == -numeric_limits<float>::infinity()) {
+ return "static_cast<float>(-::google::protobuf::internal::Infinity())";
+ } else if (value != value) {
+ return "static_cast<float>(::google::protobuf::internal::NaN())";
+ } else {
+ string float_value = SimpleFtoa(value);
+ // If floating point value contains a period (.) or an exponent
+ // (either E or e), then append suffix 'f' to make it a float
+ // literal.
+ if (float_value.find_first_of(".eE") != string::npos) {
+ float_value.push_back('f');
+ }
+ return float_value;
+ }
+ }
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field->default_value_bool() ? "true" : "false";
+ case FieldDescriptor::CPPTYPE_ENUM:
+ // Lazy: Generate a static_cast because we don't have a helper function
+ // that constructs the full name of an enum value.
+ return strings::Substitute(
+ "static_cast< $0 >($1)",
+ ClassName(field->enum_type(), true),
+ Int32ToString(field->default_value_enum()->number()));
+ case FieldDescriptor::CPPTYPE_STRING:
+ return "\"" + EscapeTrigraphs(
+ CEscape(field->default_value_string())) +
+ "\"";
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return FieldMessageTypeName(field) + "::default_instance()";
+ }
+ // Can't actually get here; make compiler happy. (We could add a default
+ // case above but then we wouldn't get the nice compiler warning when a
+ // new type is added.)
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return "";
+}
+
+// Convert a file name into a valid identifier.
+string FilenameIdentifier(const string& filename) {
+ string result;
+ for (int i = 0; i < filename.size(); i++) {
+ if (ascii_isalnum(filename[i])) {
+ result.push_back(filename[i]);
+ } else {
+ // Not alphanumeric. To avoid any possibility of name conflicts we
+ // use the hex code for the character.
+ StrAppend(&result, "_", strings::Hex(static_cast<uint8>(filename[i])));
+ }
+ }
+ return result;
+}
+
+// Return the name of the AddDescriptors() function for a given file.
+string GlobalAddDescriptorsName(const string& filename) {
+ return "protobuf_AddDesc_" + FilenameIdentifier(filename);
+}
+
+// Return the name of the AssignDescriptors() function for a given file.
+string GlobalAssignDescriptorsName(const string& filename) {
+ return "protobuf_AssignDesc_" + FilenameIdentifier(filename);
+}
+
+// Return the name of the ShutdownFile() function for a given file.
+string GlobalShutdownFileName(const string& filename) {
+ return "protobuf_ShutdownFile_" + FilenameIdentifier(filename);
+}
+
+// Return the qualified C++ name for a file level symbol.
+string QualifiedFileLevelSymbol(const string& package, const string& name) {
+ if (package.empty()) {
+ return StrCat("::", name);
+ }
+ return StrCat("::", DotsToColons(package), "::", name);
+}
+
+// Escape C++ trigraphs by escaping question marks to \?
+string EscapeTrigraphs(const string& to_escape) {
+ return StringReplace(to_escape, "?", "\\?", true);
+}
+
+// Escaped function name to eliminate naming conflict.
+string SafeFunctionName(const Descriptor* descriptor,
+ const FieldDescriptor* field,
+ const string& prefix) {
+ // Do not use FieldName() since it will escape keywords.
+ string name = field->name();
+ LowerString(&name);
+ string function_name = prefix + name;
+ if (descriptor->FindFieldByName(function_name)) {
+ // Single underscore will also make it conflicting with the private data
+ // member. We use double underscore to escape function names.
+ function_name.append("__");
+ } else if (kKeywords.count(name) > 0) {
+ // If the field name is a keyword, we append the underscore back to keep it
+ // consistent with other function names.
+ function_name.append("_");
+ }
+ return function_name;
+}
+
+bool StaticInitializersForced(const FileDescriptor* file,
+ const Options& options) {
+ if (HasDescriptorMethods(file, options) || file->extension_count() > 0) {
+ return true;
+ }
+ for (int i = 0; i < file->message_type_count(); ++i) {
+ if (HasExtension(file->message_type(i))) {
+ return true;
+ }
+ }
+ return false;
+}
+
+void PrintHandlingOptionalStaticInitializers(
+ const FileDescriptor* file, const Options& options, io::Printer* printer,
+ const char* with_static_init, const char* without_static_init,
+ const char* var1, const string& val1, const char* var2,
+ const string& val2) {
+ map<string, string> vars;
+ if (var1) {
+ vars[var1] = val1;
+ }
+ if (var2) {
+ vars[var2] = val2;
+ }
+ PrintHandlingOptionalStaticInitializers(
+ vars, file, options, printer, with_static_init, without_static_init);
+}
+
+void PrintHandlingOptionalStaticInitializers(const map<string, string>& vars,
+ const FileDescriptor* file,
+ const Options& options,
+ io::Printer* printer,
+ const char* with_static_init,
+ const char* without_static_init) {
+ if (StaticInitializersForced(file, options)) {
+ printer->Print(vars, with_static_init);
+ } else {
+ printer->Print(vars, (string(
+ "#ifdef GOOGLE_PROTOBUF_NO_STATIC_INITIALIZER\n") +
+ without_static_init +
+ "#else\n" +
+ with_static_init +
+ "#endif\n").c_str());
+ }
+}
+
+
+static bool HasMapFields(const Descriptor* descriptor) {
+ for (int i = 0; i < descriptor->field_count(); ++i) {
+ if (descriptor->field(i)->is_map()) {
+ return true;
+ }
+ }
+ for (int i = 0; i < descriptor->nested_type_count(); ++i) {
+ if (HasMapFields(descriptor->nested_type(i))) return true;
+ }
+ return false;
+}
+
+bool HasMapFields(const FileDescriptor* file) {
+ for (int i = 0; i < file->message_type_count(); ++i) {
+ if (HasMapFields(file->message_type(i))) return true;
+ }
+ return false;
+}
+
+static bool HasEnumDefinitions(const Descriptor* message_type) {
+ if (message_type->enum_type_count() > 0) return true;
+ for (int i = 0; i < message_type->nested_type_count(); ++i) {
+ if (HasEnumDefinitions(message_type->nested_type(i))) return true;
+ }
+ return false;
+}
+
+bool HasEnumDefinitions(const FileDescriptor* file) {
+ if (file->enum_type_count() > 0) return true;
+ for (int i = 0; i < file->message_type_count(); ++i) {
+ if (HasEnumDefinitions(file->message_type(i))) return true;
+ }
+ return false;
+}
+
+bool IsStringOrMessage(const FieldDescriptor* field) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ case FieldDescriptor::CPPTYPE_INT64:
+ case FieldDescriptor::CPPTYPE_UINT32:
+ case FieldDescriptor::CPPTYPE_UINT64:
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ case FieldDescriptor::CPPTYPE_BOOL:
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return false;
+ case FieldDescriptor::CPPTYPE_STRING:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return true;
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return false;
+}
+
+FieldOptions::CType EffectiveStringCType(const FieldDescriptor* field) {
+ GOOGLE_DCHECK(field->cpp_type() == FieldDescriptor::CPPTYPE_STRING);
+ // Open-source protobuf release only supports STRING ctype.
+ return FieldOptions::STRING;
+
+}
+
+bool IsAnyMessage(const FileDescriptor* descriptor) {
+ return descriptor->name() == kAnyProtoFile;
+}
+
+bool IsAnyMessage(const Descriptor* descriptor) {
+ return descriptor->name() == kAnyMessageName &&
+ descriptor->file()->name() == kAnyProtoFile;
+}
+
+bool IsWellKnownMessage(const FileDescriptor* descriptor) {
+ return !descriptor->name().compare(0, 16, kGoogleProtobufPrefix);
+}
+
+enum Utf8CheckMode {
+ STRICT = 0, // Parsing will fail if non UTF-8 data is in string fields.
+ VERIFY = 1, // Only log an error but parsing will succeed.
+ NONE = 2, // No UTF-8 check.
+};
+
+// Which level of UTF-8 enforcemant is placed on this file.
+static Utf8CheckMode GetUtf8CheckMode(const FieldDescriptor* field,
+ const Options& options) {
+ if (field->file()->syntax() == FileDescriptor::SYNTAX_PROTO3) {
+ return STRICT;
+ } else if (GetOptimizeFor(field->file(), options) !=
+ FileOptions::LITE_RUNTIME) {
+ return VERIFY;
+ } else {
+ return NONE;
+ }
+}
+
+static void GenerateUtf8CheckCode(const FieldDescriptor* field,
+ const Options& options, bool for_parse,
+ const map<string, string>& variables,
+ const char* parameters,
+ const char* strict_function,
+ const char* verify_function,
+ io::Printer* printer) {
+ switch (GetUtf8CheckMode(field, options)) {
+ case STRICT: {
+ if (for_parse) {
+ printer->Print("DO_(");
+ }
+ printer->Print(
+ "::google::protobuf::internal::WireFormatLite::$function$(\n",
+ "function", strict_function);
+ printer->Indent();
+ printer->Print(variables, parameters);
+ if (for_parse) {
+ printer->Print("::google::protobuf::internal::WireFormatLite::PARSE,\n");
+ } else {
+ printer->Print("::google::protobuf::internal::WireFormatLite::SERIALIZE,\n");
+ }
+ printer->Print("\"$full_name$\")", "full_name", field->full_name());
+ if (for_parse) {
+ printer->Print(")");
+ }
+ printer->Print(";\n");
+ printer->Outdent();
+ break;
+ }
+ case VERIFY: {
+ printer->Print(
+ "::google::protobuf::internal::WireFormat::$function$(\n",
+ "function", verify_function);
+ printer->Indent();
+ printer->Print(variables, parameters);
+ if (for_parse) {
+ printer->Print("::google::protobuf::internal::WireFormat::PARSE,\n");
+ } else {
+ printer->Print("::google::protobuf::internal::WireFormat::SERIALIZE,\n");
+ }
+ printer->Print("\"$full_name$\");\n", "full_name", field->full_name());
+ printer->Outdent();
+ break;
+ }
+ case NONE:
+ break;
+ }
+}
+
+void GenerateUtf8CheckCodeForString(const FieldDescriptor* field,
+ const Options& options, bool for_parse,
+ const map<string, string>& variables,
+ const char* parameters,
+ io::Printer* printer) {
+ GenerateUtf8CheckCode(field, options, for_parse, variables, parameters,
+ "VerifyUtf8String", "VerifyUTF8StringNamedField",
+ printer);
+}
+
+void GenerateUtf8CheckCodeForCord(const FieldDescriptor* field,
+ const Options& options, bool for_parse,
+ const map<string, string>& variables,
+ const char* parameters,
+ io::Printer* printer) {
+ GenerateUtf8CheckCode(field, options, for_parse, variables, parameters,
+ "VerifyUtf8Cord", "VerifyUTF8CordNamedField", printer);
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.h
new file mode 100644
index 0000000000..018acfcad0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_helpers.h
@@ -0,0 +1,306 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_HELPERS_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_HELPERS_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_options.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+
+namespace io {
+class Printer;
+}
+
+namespace compiler {
+namespace cpp {
+
+// Commonly-used separator comments. Thick is a line of '=', thin is a line
+// of '-'.
+extern const char kThickSeparator[];
+extern const char kThinSeparator[];
+
+// Returns the non-nested type name for the given type. If "qualified" is
+// true, prefix the type with the full namespace. For example, if you had:
+// package foo.bar;
+// message Baz { message Qux {} }
+// Then the qualified ClassName for Qux would be:
+// ::foo::bar::Baz_Qux
+// While the non-qualified version would be:
+// Baz_Qux
+string ClassName(const Descriptor* descriptor, bool qualified);
+string ClassName(const EnumDescriptor* enum_descriptor, bool qualified);
+
+// Name of the CRTP class template (for use with proto_h).
+// This is a class name, like "ProtoName_InternalBase".
+string DependentBaseClassTemplateName(const Descriptor* descriptor);
+
+// Name of the base class: either the dependent base class (for use with
+// proto_h) or google::protobuf::Message.
+string SuperClassName(const Descriptor* descriptor, const Options& options);
+
+// Returns a string that down-casts from the dependent base class to the
+// derived class.
+string DependentBaseDownCast();
+string DependentBaseConstDownCast();
+
+// Get the (unqualified) name that should be used for this field in C++ code.
+// The name is coerced to lower-case to emulate proto1 behavior. People
+// should be using lowercase-with-underscores style for proto field names
+// anyway, so normally this just returns field->name().
+string FieldName(const FieldDescriptor* field);
+
+// Get the sanitized name that should be used for the given enum in C++ code.
+string EnumValueName(const EnumValueDescriptor* enum_value);
+
+// Get the unqualified name that should be used for a field's field
+// number constant.
+string FieldConstantName(const FieldDescriptor *field);
+
+// Returns the scope where the field was defined (for extensions, this is
+// different from the message type to which the field applies).
+inline const Descriptor* FieldScope(const FieldDescriptor* field) {
+ return field->is_extension() ?
+ field->extension_scope() : field->containing_type();
+}
+
+// Returns true if the given 'field_descriptor' has a message type that is
+// a dependency of the file where the field is defined (i.e., the field
+// type is defined in a different file than the message holding the field).
+//
+// This only applies to Message-typed fields. Enum-typed fields may refer
+// to an enum in a dependency; however, enums are specified and
+// forward-declared with an enum-base, so the definition is not required to
+// manipulate the field value.
+bool IsFieldDependent(const FieldDescriptor* field_descriptor);
+
+// Returns the name that should be used for forcing dependent lookup from a
+// dependent base class.
+string DependentTypeName(const FieldDescriptor* field);
+
+// Returns the fully-qualified type name field->message_type(). Usually this
+// is just ClassName(field->message_type(), true);
+string FieldMessageTypeName(const FieldDescriptor* field);
+
+// Strips ".proto" or ".protodevel" from the end of a filename.
+LIBPROTOC_EXPORT string StripProto(const string& filename);
+
+// Get the C++ type name for a primitive type (e.g. "double", "::google::protobuf::int32", etc.).
+// Note: non-built-in type names will be qualified, meaning they will start
+// with a ::. If you are using the type as a template parameter, you will
+// need to insure there is a space between the < and the ::, because the
+// ridiculous C++ standard defines "<:" to be a synonym for "[".
+const char* PrimitiveTypeName(FieldDescriptor::CppType type);
+
+// Get the declared type name in CamelCase format, as is used e.g. for the
+// methods of WireFormat. For example, TYPE_INT32 becomes "Int32".
+const char* DeclaredTypeMethodName(FieldDescriptor::Type type);
+
+// Return the code that evaluates to the number when compiled.
+string Int32ToString(int number);
+
+// Return the code that evaluates to the number when compiled.
+string Int64ToString(int64 number);
+
+// Get code that evaluates to the field's default value.
+string DefaultValue(const FieldDescriptor* field);
+
+// Convert a file name into a valid identifier.
+string FilenameIdentifier(const string& filename);
+
+// Return the name of the AddDescriptors() function for a given file.
+string GlobalAddDescriptorsName(const string& filename);
+
+// Return the name of the AssignDescriptors() function for a given file.
+string GlobalAssignDescriptorsName(const string& filename);
+
+// Return the qualified C++ name for a file level symbol.
+string QualifiedFileLevelSymbol(const string& package, const string& name);
+
+// Return the name of the ShutdownFile() function for a given file.
+string GlobalShutdownFileName(const string& filename);
+
+// Escape C++ trigraphs by escaping question marks to \?
+string EscapeTrigraphs(const string& to_escape);
+
+// Escaped function name to eliminate naming conflict.
+string SafeFunctionName(const Descriptor* descriptor,
+ const FieldDescriptor* field,
+ const string& prefix);
+
+// Returns true if unknown fields are preseved after parsing.
+inline bool PreserveUnknownFields(const Descriptor* message) {
+ return message->file()->syntax() != FileDescriptor::SYNTAX_PROTO3;
+}
+
+// Returns the optimize mode for <file>, respecting <options.enforce_lite>.
+::google::protobuf::FileOptions_OptimizeMode GetOptimizeFor(
+ const FileDescriptor* file, const Options& options);
+
+// If PreserveUnknownFields() is true, determines whether unknown
+// fields will be stored in an UnknownFieldSet or a string.
+// If PreserveUnknownFields() is false, this method will not be
+// used.
+inline bool UseUnknownFieldSet(const FileDescriptor* file,
+ const Options& options) {
+ return GetOptimizeFor(file, options) != FileOptions::LITE_RUNTIME;
+}
+
+
+// Does the file have any map fields, necessitating the file to include
+// map_field_inl.h and map.h.
+bool HasMapFields(const FileDescriptor* file);
+
+// Does this file have any enum type definitions?
+bool HasEnumDefinitions(const FileDescriptor* file);
+
+// Does this file have generated parsing, serialization, and other
+// standard methods for which reflection-based fallback implementations exist?
+inline bool HasGeneratedMethods(const FileDescriptor* file,
+ const Options& options) {
+ return GetOptimizeFor(file, options) != FileOptions::CODE_SIZE;
+}
+
+// Do message classes in this file have descriptor and reflection methods?
+inline bool HasDescriptorMethods(const FileDescriptor* file,
+ const Options& options) {
+ return GetOptimizeFor(file, options) != FileOptions::LITE_RUNTIME;
+}
+
+// Should we generate generic services for this file?
+inline bool HasGenericServices(const FileDescriptor* file,
+ const Options& options) {
+ return file->service_count() > 0 &&
+ GetOptimizeFor(file, options) != FileOptions::LITE_RUNTIME &&
+ file->options().cc_generic_services();
+}
+
+// Should we generate a separate, super-optimized code path for serializing to
+// flat arrays? We don't do this in Lite mode because we'd rather reduce code
+// size.
+inline bool HasFastArraySerialization(const FileDescriptor* file,
+ const Options& options) {
+ return GetOptimizeFor(file, options) == FileOptions::SPEED;
+}
+
+// Returns whether we have to generate code with static initializers.
+bool StaticInitializersForced(const FileDescriptor* file,
+ const Options& options);
+
+// Prints 'with_static_init' if static initializers have to be used for the
+// provided file. Otherwise emits both 'with_static_init' and
+// 'without_static_init' using #ifdef.
+void PrintHandlingOptionalStaticInitializers(
+ const FileDescriptor* file, const Options& options, io::Printer* printer,
+ const char* with_static_init, const char* without_static_init,
+ const char* var1 = NULL, const string& val1 = "", const char* var2 = NULL,
+ const string& val2 = "");
+
+void PrintHandlingOptionalStaticInitializers(const map<string, string>& vars,
+ const FileDescriptor* file,
+ const Options& options,
+ io::Printer* printer,
+ const char* with_static_init,
+ const char* without_static_init);
+
+
+inline bool IsMapEntryMessage(const Descriptor* descriptor) {
+ return descriptor->options().map_entry();
+}
+
+// Returns true if the field's CPPTYPE is string or message.
+bool IsStringOrMessage(const FieldDescriptor* field);
+
+// For a string field, returns the effective ctype. If the actual ctype is
+// not supported, returns the default of STRING.
+FieldOptions::CType EffectiveStringCType(const FieldDescriptor* field);
+
+string UnderscoresToCamelCase(const string& input, bool cap_next_letter);
+
+inline bool HasFieldPresence(const FileDescriptor* file) {
+ return file->syntax() != FileDescriptor::SYNTAX_PROTO3;
+}
+
+// Returns true if 'enum' semantics are such that unknown values are preserved
+// in the enum field itself, rather than going to the UnknownFieldSet.
+inline bool HasPreservingUnknownEnumSemantics(const FileDescriptor* file) {
+ return file->syntax() == FileDescriptor::SYNTAX_PROTO3;
+}
+
+inline bool SupportsArenas(const FileDescriptor* file) {
+ return file->options().cc_enable_arenas();
+}
+
+inline bool SupportsArenas(const Descriptor* desc) {
+ return SupportsArenas(desc->file());
+}
+
+inline bool SupportsArenas(const FieldDescriptor* field) {
+ return SupportsArenas(field->file());
+}
+
+bool IsAnyMessage(const FileDescriptor* descriptor);
+bool IsAnyMessage(const Descriptor* descriptor);
+
+bool IsWellKnownMessage(const FileDescriptor* descriptor);
+
+void GenerateUtf8CheckCodeForString(const FieldDescriptor* field,
+ const Options& options, bool for_parse,
+ const map<string, string>& variables,
+ const char* parameters,
+ io::Printer* printer);
+
+void GenerateUtf8CheckCodeForCord(const FieldDescriptor* field,
+ const Options& options, bool for_parse,
+ const map<string, string>& variables,
+ const char* parameters, io::Printer* printer);
+
+inline ::google::protobuf::FileOptions_OptimizeMode GetOptimizeFor(
+ const FileDescriptor* file, const Options& options) {
+ return options.enforce_lite
+ ? FileOptions::LITE_RUNTIME
+ : file->options().optimize_for();
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_HELPERS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.cc
new file mode 100644
index 0000000000..0588e34ecd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.cc
@@ -0,0 +1,437 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_map_field.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+bool IsProto3Field(const FieldDescriptor* field_descriptor) {
+ const FileDescriptor* file_descriptor = field_descriptor->file();
+ return file_descriptor->syntax() == FileDescriptor::SYNTAX_PROTO3;
+}
+
+void SetMessageVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables,
+ const Options& options) {
+ SetCommonFieldVariables(descriptor, variables, options);
+ (*variables)["type"] = FieldMessageTypeName(descriptor);
+ (*variables)["stream_writer"] =
+ (*variables)["declared_type"] +
+ (HasFastArraySerialization(descriptor->message_type()->file(), options)
+ ? "MaybeToArray"
+ : "");
+ (*variables)["full_name"] = descriptor->full_name();
+
+ const FieldDescriptor* key =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* val =
+ descriptor->message_type()->FindFieldByName("value");
+ (*variables)["key_cpp"] = PrimitiveTypeName(key->cpp_type());
+ switch (val->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ (*variables)["val_cpp"] = FieldMessageTypeName(val);
+ (*variables)["wrapper"] = "EntryWrapper";
+ break;
+ case FieldDescriptor::CPPTYPE_ENUM:
+ (*variables)["val_cpp"] = ClassName(val->enum_type(), true);
+ (*variables)["wrapper"] = "EnumEntryWrapper";
+ break;
+ default:
+ (*variables)["val_cpp"] = PrimitiveTypeName(val->cpp_type());
+ (*variables)["wrapper"] = "EntryWrapper";
+ }
+ (*variables)["key_wire_type"] =
+ "::google::protobuf::internal::WireFormatLite::TYPE_" +
+ ToUpper(DeclaredTypeMethodName(key->type()));
+ (*variables)["val_wire_type"] =
+ "::google::protobuf::internal::WireFormatLite::TYPE_" +
+ ToUpper(DeclaredTypeMethodName(val->type()));
+ (*variables)["map_classname"] = ClassName(descriptor->message_type(), false);
+ (*variables)["number"] = SimpleItoa(descriptor->number());
+ (*variables)["tag"] = SimpleItoa(internal::WireFormat::MakeTag(descriptor));
+
+ if (HasDescriptorMethods(descriptor->file(), options)) {
+ (*variables)["lite"] = "";
+ } else {
+ (*variables)["lite"] = "Lite";
+ }
+
+ if (!IsProto3Field(descriptor) &&
+ val->type() == FieldDescriptor::TYPE_ENUM) {
+ const EnumValueDescriptor* default_value = val->default_value_enum();
+ (*variables)["default_enum_value"] = Int32ToString(default_value->number());
+ } else {
+ (*variables)["default_enum_value"] = "0";
+ }
+}
+
+MapFieldGenerator::MapFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : FieldGenerator(options),
+ descriptor_(descriptor),
+ dependent_field_(options.proto_h && IsFieldDependent(descriptor)) {
+ SetMessageVariables(descriptor, &variables_, options);
+}
+
+MapFieldGenerator::~MapFieldGenerator() {}
+
+void MapFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "typedef ::google::protobuf::internal::MapEntryLite<\n"
+ " $key_cpp$, $val_cpp$,\n"
+ " $key_wire_type$,\n"
+ " $val_wire_type$,\n"
+ " $default_enum_value$ >\n"
+ " $map_classname$;\n"
+ "::google::protobuf::internal::MapField$lite$<\n"
+ " $key_cpp$, $val_cpp$,\n"
+ " $key_wire_type$,\n"
+ " $val_wire_type$,\n"
+ " $default_enum_value$ > $name$_;\n");
+}
+
+void MapFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$deprecated_attr$const ::google::protobuf::Map< $key_cpp$, $val_cpp$ >&\n"
+ " $name$() const;\n"
+ "$deprecated_attr$::google::protobuf::Map< $key_cpp$, $val_cpp$ >*\n"
+ " mutable_$name$();\n");
+}
+
+void MapFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ const ::google::protobuf::Map< $key_cpp$, $val_cpp$ >&\n"
+ "$classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_map:$full_name$)\n"
+ " return $name$_.GetMap();\n"
+ "}\n"
+ "$inline$ ::google::protobuf::Map< $key_cpp$, $val_cpp$ >*\n"
+ "$classname$::mutable_$name$() {\n"
+ " // @@protoc_insertion_point(field_mutable_map:$full_name$)\n"
+ " return $name$_.MutableMap();\n"
+ "}\n");
+}
+
+void MapFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ variables["this_message"] = dependent_field_ ? DependentBaseDownCast() : "";
+ printer->Print(variables, "$this_message$$name$_.Clear();\n");
+}
+
+void MapFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.MergeFrom(from.$name$_);\n");
+}
+
+void MapFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.Swap(&other->$name$_);\n");
+}
+
+void MapFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ "$name$_.SetAssignDescriptorCallback(\n"
+ " protobuf_AssignDescriptorsOnce);\n"
+ "$name$_.SetEntryDescriptor(\n"
+ " &$type$_descriptor_);\n");
+ }
+}
+
+void MapFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ const FieldDescriptor* key_field =
+ descriptor_->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_field =
+ descriptor_->message_type()->FindFieldByName("value");
+ bool using_entry = false;
+ string key;
+ string value;
+ if (IsProto3Field(descriptor_) ||
+ value_field->type() != FieldDescriptor::TYPE_ENUM) {
+ printer->Print(variables_,
+ "$map_classname$::Parser< ::google::protobuf::internal::MapField$lite$<\n"
+ " $key_cpp$, $val_cpp$,\n"
+ " $key_wire_type$,\n"
+ " $val_wire_type$,\n"
+ " $default_enum_value$ >,\n"
+ " ::google::protobuf::Map< $key_cpp$, $val_cpp$ > >"
+ " parser(&$name$_);\n"
+ "DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(\n"
+ " input, &parser));\n");
+ key = "parser.key()";
+ value = "parser.value()";
+ } else {
+ using_entry = true;
+ key = "entry->key()";
+ value = "entry->value()";
+ printer->Print(variables_,
+ "::google::protobuf::scoped_ptr<$map_classname$> entry($name$_.NewEntry());\n");
+ printer->Print(variables_,
+ "{\n"
+ " ::std::string data;\n"
+ " DO_(::google::protobuf::internal::WireFormatLite::ReadString(input, &data));\n"
+ " DO_(entry->ParseFromString(data));\n"
+ " if ($val_cpp$_IsValid(*entry->mutable_value())) {\n"
+ " (*mutable_$name$())[entry->key()] =\n"
+ " static_cast< $val_cpp$ >(*entry->mutable_value());\n"
+ " } else {\n");
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ " mutable_unknown_fields()"
+ "->AddLengthDelimited($number$, data);\n");
+ } else {
+ printer->Print(variables_,
+ " unknown_fields_stream.WriteVarint32($tag$);\n"
+ " unknown_fields_stream.WriteVarint32(data.size());\n"
+ " unknown_fields_stream.WriteString(data);\n");
+ }
+
+ printer->Print(variables_,
+ " }\n"
+ "}\n");
+ }
+
+ if (key_field->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ key_field, options_, true, variables_,
+ StrCat(key, ".data(), ", key, ".length(),\n").data(), printer);
+ }
+ if (value_field->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(value_field, options_, true, variables_,
+ StrCat(value, ".data(), ", value, ".length(),\n").data(), printer);
+ }
+
+ // If entry is allocated by arena, its desctructor should be avoided.
+ if (using_entry && SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ "if (entry->GetArena() != NULL) entry.release();\n");
+ }
+}
+
+static void GenerateSerializationLoop(io::Printer* printer,
+ const map<string, string>& variables,
+ bool supports_arenas,
+ const string& utf8_check,
+ const string& loop_header,
+ const string& ptr,
+ bool loop_via_iterators) {
+ printer->Print(variables,
+ StrCat("::google::protobuf::scoped_ptr<$map_classname$> entry;\n",
+ loop_header, " {\n").c_str());
+ printer->Indent();
+
+ printer->Print(variables, StrCat(
+ "entry.reset($name$_.New$wrapper$(\n"
+ " ", ptr, "->first, ", ptr, "->second));\n"
+ "$write_entry$;\n").c_str());
+
+ // If entry is allocated by arena, its desctructor should be avoided.
+ if (supports_arenas) {
+ printer->Print(
+ "if (entry->GetArena() != NULL) {\n"
+ " entry.release();\n"
+ "}\n");
+ }
+
+ if (!utf8_check.empty()) {
+ // If loop_via_iterators is true then ptr is actually an iterator, and we
+ // create a pointer by prefixing it with "&*".
+ printer->Print(
+ StrCat(utf8_check, "(", (loop_via_iterators ? "&*" : ""), ptr, ");\n")
+ .c_str());
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+}
+
+void MapFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ variables["write_entry"] = "::google::protobuf::internal::WireFormatLite::Write" +
+ variables["stream_writer"] + "(\n " +
+ variables["number"] + ", *entry, output)";
+ variables["deterministic"] = "output->IsSerializationDeterminstic()";
+ GenerateSerializeWithCachedSizes(printer, variables);
+}
+
+void MapFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ variables["write_entry"] =
+ "target = ::google::protobuf::internal::WireFormatLite::\n"
+ " InternalWrite" + variables["declared_type"] +
+ "NoVirtualToArray(\n " + variables["number"] +
+ ", *entry, deterministic, target);\n";
+ variables["deterministic"] = "deterministic";
+ GenerateSerializeWithCachedSizes(printer, variables);
+}
+
+void MapFieldGenerator::GenerateSerializeWithCachedSizes(
+ io::Printer* printer, const map<string, string>& variables) const {
+ printer->Print(variables,
+ "if (!this->$name$().empty()) {\n");
+ printer->Indent();
+ const FieldDescriptor* key_field =
+ descriptor_->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_field =
+ descriptor_->message_type()->FindFieldByName("value");
+ const bool string_key = key_field->type() == FieldDescriptor::TYPE_STRING;
+ const bool string_value = value_field->type() == FieldDescriptor::TYPE_STRING;
+
+ printer->Print(variables,
+ "typedef ::google::protobuf::Map< $key_cpp$, $val_cpp$ >::const_pointer\n"
+ " ConstPtr;\n");
+ if (string_key) {
+ printer->Print(variables,
+ "typedef ConstPtr SortItem;\n"
+ "typedef ::google::protobuf::internal::"
+ "CompareByDerefFirst<SortItem> Less;\n");
+ } else {
+ printer->Print(variables,
+ "typedef ::google::protobuf::internal::SortItem< $key_cpp$, ConstPtr > "
+ "SortItem;\n"
+ "typedef ::google::protobuf::internal::CompareByFirstField<SortItem> Less;\n");
+ }
+ string utf8_check;
+ if (string_key || string_value) {
+ printer->Print(
+ "struct Utf8Check {\n"
+ " static void Check(ConstPtr p) {\n");
+ printer->Indent();
+ printer->Indent();
+ if (string_key) {
+ GenerateUtf8CheckCodeForString(key_field, options_, false, variables,
+ "p->first.data(), p->first.length(),\n",
+ printer);
+ }
+ if (string_value) {
+ GenerateUtf8CheckCodeForString(value_field, options_, false, variables,
+ "p->second.data(), p->second.length(),\n",
+ printer);
+ }
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n"
+ "};\n");
+ utf8_check = "Utf8Check::Check";
+ }
+
+ printer->Print(variables,
+ "\n"
+ "if ($deterministic$ &&\n"
+ " this->$name$().size() > 1) {\n"
+ " ::google::protobuf::scoped_array<SortItem> items(\n"
+ " new SortItem[this->$name$().size()]);\n"
+ " typedef ::google::protobuf::Map< $key_cpp$, $val_cpp$ >::size_type size_type;\n"
+ " size_type n = 0;\n"
+ " for (::google::protobuf::Map< $key_cpp$, $val_cpp$ >::const_iterator\n"
+ " it = this->$name$().begin();\n"
+ " it != this->$name$().end(); ++it, ++n) {\n"
+ " items[n] = SortItem(&*it);\n"
+ " }\n"
+ " ::std::sort(&items[0], &items[n], Less());\n");
+ printer->Indent();
+ GenerateSerializationLoop(printer, variables, SupportsArenas(descriptor_),
+ utf8_check, "for (size_type i = 0; i < n; i++)",
+ string_key ? "items[i]" : "items[i].second", false);
+ printer->Outdent();
+ printer->Print(
+ "} else {\n");
+ printer->Indent();
+ GenerateSerializationLoop(
+ printer, variables, SupportsArenas(descriptor_), utf8_check,
+ "for (::google::protobuf::Map< $key_cpp$, $val_cpp$ >::const_iterator\n"
+ " it = this->$name$().begin();\n"
+ " it != this->$name$().end(); ++it)",
+ "it", true);
+ printer->Outdent();
+ printer->Print("}\n");
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MapFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "total_size += $tag_size$ * this->$name$_size();\n"
+ "{\n"
+ " ::google::protobuf::scoped_ptr<$map_classname$> entry;\n"
+ " for (::google::protobuf::Map< $key_cpp$, $val_cpp$ >::const_iterator\n"
+ " it = this->$name$().begin();\n"
+ " it != this->$name$().end(); ++it) {\n");
+
+ // If entry is allocated by arena, its desctructor should be avoided.
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ " if (entry.get() != NULL && entry->GetArena() != NULL) {\n"
+ " entry.release();\n"
+ " }\n");
+ }
+
+ printer->Print(variables_,
+ " entry.reset($name$_.New$wrapper$(it->first, it->second));\n"
+ " total_size += ::google::protobuf::internal::WireFormatLite::\n"
+ " $declared_type$SizeNoVirtual(*entry);\n"
+ " }\n");
+
+ // If entry is allocated by arena, its desctructor should be avoided.
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ " if (entry.get() != NULL && entry->GetArena() != NULL) {\n"
+ " entry.release();\n"
+ " }\n");
+ }
+
+ printer->Print("}\n");
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.h
new file mode 100644
index 0000000000..2930fe59e9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_map_field.h
@@ -0,0 +1,80 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_MAP_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_MAP_FIELD_H__
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/cpp/cpp_message_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class MapFieldGenerator : public FieldGenerator {
+ public:
+ MapFieldGenerator(const FieldDescriptor* descriptor, const Options& options);
+ ~MapFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ private:
+ // A helper for GenerateSerializeWithCachedSizes{,ToArray}.
+ void GenerateSerializeWithCachedSizes(
+ io::Printer* printer, const map<string, string>& variables) const;
+
+ const FieldDescriptor* descriptor_;
+ const bool dependent_field_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MapFieldGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_MAP_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.cc
new file mode 100644
index 0000000000..405a5fed55
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.cc
@@ -0,0 +1,3819 @@
+// 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.
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <utility>
+#include <vector>
+#include <google/protobuf/compiler/cpp/cpp_message.h>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+#include <google/protobuf/compiler/cpp/cpp_enum.h>
+#include <google/protobuf/compiler/cpp/cpp_extension.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/descriptor.pb.h>
+
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+template <class T>
+void PrintFieldComment(io::Printer* printer, const T* field) {
+ // Print the field's (or oneof's) proto-syntax definition as a comment.
+ // We don't want to print group bodies so we cut off after the first
+ // line.
+ DebugStringOptions options;
+ options.elide_group_body = true;
+ options.elide_oneof_body = true;
+ string def = field->DebugStringWithOptions(options);
+ printer->Print("// $def$\n",
+ "def", def.substr(0, def.find_first_of('\n')));
+}
+
+struct FieldOrderingByNumber {
+ inline bool operator()(const FieldDescriptor* a,
+ const FieldDescriptor* b) const {
+ return a->number() < b->number();
+ }
+};
+
+// Sort the fields of the given Descriptor by number into a new[]'d array
+// and return it.
+const FieldDescriptor** SortFieldsByNumber(const Descriptor* descriptor) {
+ const FieldDescriptor** fields =
+ new const FieldDescriptor*[descriptor->field_count()];
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ fields[i] = descriptor->field(i);
+ }
+ std::sort(fields, fields + descriptor->field_count(),
+ FieldOrderingByNumber());
+ return fields;
+}
+
+// Functor for sorting extension ranges by their "start" field number.
+struct ExtensionRangeSorter {
+ bool operator()(const Descriptor::ExtensionRange* left,
+ const Descriptor::ExtensionRange* right) const {
+ return left->start < right->start;
+ }
+};
+
+// Returns true if the "required" restriction check should be ignored for the
+// given field.
+inline static bool ShouldIgnoreRequiredFieldCheck(const FieldDescriptor* field,
+ const Options& options) {
+ return false;
+}
+
+// Returns true if the message type has any required fields. If it doesn't,
+// we can optimize out calls to its IsInitialized() method.
+//
+// already_seen is used to avoid checking the same type multiple times
+// (and also to protect against recursion).
+static bool HasRequiredFields(const Descriptor* type, const Options& options,
+ hash_set<const Descriptor*>* already_seen) {
+ if (already_seen->count(type) > 0) {
+ // Since the first occurrence of a required field causes the whole
+ // function to return true, we can assume that if the type is already
+ // in the cache it didn't have any required fields.
+ return false;
+ }
+ already_seen->insert(type);
+
+ // If the type has extensions, an extension with message type could contain
+ // required fields, so we have to be conservative and assume such an
+ // extension exists.
+ if (type->extension_range_count() > 0) return true;
+
+ for (int i = 0; i < type->field_count(); i++) {
+ const FieldDescriptor* field = type->field(i);
+ if (field->is_required()) {
+ return true;
+ }
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ !ShouldIgnoreRequiredFieldCheck(field, options)) {
+ if (HasRequiredFields(field->message_type(), options, already_seen)) {
+ return true;
+ }
+ }
+ }
+
+ return false;
+}
+
+static bool HasRequiredFields(const Descriptor* type, const Options& options) {
+ hash_set<const Descriptor*> already_seen;
+ return HasRequiredFields(type, options, &already_seen);
+}
+
+// This returns an estimate of the compiler's alignment for the field. This
+// can't guarantee to be correct because the generated code could be compiled on
+// different systems with different alignment rules. The estimates below assume
+// 64-bit pointers.
+int EstimateAlignmentSize(const FieldDescriptor* field) {
+ if (field == NULL) return 0;
+ if (field->is_repeated()) return 8;
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return 1;
+
+ case FieldDescriptor::CPPTYPE_INT32:
+ case FieldDescriptor::CPPTYPE_UINT32:
+ case FieldDescriptor::CPPTYPE_ENUM:
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return 4;
+
+ case FieldDescriptor::CPPTYPE_INT64:
+ case FieldDescriptor::CPPTYPE_UINT64:
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ case FieldDescriptor::CPPTYPE_STRING:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return 8;
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return -1; // Make compiler happy.
+}
+
+// FieldGroup is just a helper for OptimizePadding below. It holds a vector of
+// fields that are grouped together because they have compatible alignment, and
+// a preferred location in the final field ordering.
+class FieldGroup {
+ public:
+ FieldGroup()
+ : preferred_location_(0) {}
+
+ // A group with a single field.
+ FieldGroup(float preferred_location, const FieldDescriptor* field)
+ : preferred_location_(preferred_location),
+ fields_(1, field) {}
+
+ // Append the fields in 'other' to this group.
+ void Append(const FieldGroup& other) {
+ if (other.fields_.empty()) {
+ return;
+ }
+ // Preferred location is the average among all the fields, so we weight by
+ // the number of fields on each FieldGroup object.
+ preferred_location_ =
+ (preferred_location_ * fields_.size() +
+ (other.preferred_location_ * other.fields_.size())) /
+ (fields_.size() + other.fields_.size());
+ fields_.insert(fields_.end(), other.fields_.begin(), other.fields_.end());
+ }
+
+ void SetPreferredLocation(float location) { preferred_location_ = location; }
+ const vector<const FieldDescriptor*>& fields() const { return fields_; }
+
+ // FieldGroup objects sort by their preferred location.
+ bool operator<(const FieldGroup& other) const {
+ return preferred_location_ < other.preferred_location_;
+ }
+
+ private:
+ // "preferred_location_" is an estimate of where this group should go in the
+ // final list of fields. We compute this by taking the average index of each
+ // field in this group in the original ordering of fields. This is very
+ // approximate, but should put this group close to where its member fields
+ // originally went.
+ float preferred_location_;
+ vector<const FieldDescriptor*> fields_;
+ // We rely on the default copy constructor and operator= so this type can be
+ // used in a vector.
+};
+
+// Reorder 'fields' so that if the fields are output into a c++ class in the new
+// order, the alignment padding is minimized. We try to do this while keeping
+// each field as close as possible to its original position so that we don't
+// reduce cache locality much for function that access each field in order.
+void OptimizePadding(vector<const FieldDescriptor*>* fields) {
+ // First divide fields into those that align to 1 byte, 4 bytes or 8 bytes.
+ vector<FieldGroup> aligned_to_1, aligned_to_4, aligned_to_8;
+ for (int i = 0; i < fields->size(); ++i) {
+ switch (EstimateAlignmentSize((*fields)[i])) {
+ case 1: aligned_to_1.push_back(FieldGroup(i, (*fields)[i])); break;
+ case 4: aligned_to_4.push_back(FieldGroup(i, (*fields)[i])); break;
+ case 8: aligned_to_8.push_back(FieldGroup(i, (*fields)[i])); break;
+ default:
+ GOOGLE_LOG(FATAL) << "Unknown alignment size.";
+ }
+ }
+
+ // Now group fields aligned to 1 byte into sets of 4, and treat those like a
+ // single field aligned to 4 bytes.
+ for (int i = 0; i < aligned_to_1.size(); i += 4) {
+ FieldGroup field_group;
+ for (int j = i; j < aligned_to_1.size() && j < i + 4; ++j) {
+ field_group.Append(aligned_to_1[j]);
+ }
+ aligned_to_4.push_back(field_group);
+ }
+ // Sort by preferred location to keep fields as close to their original
+ // location as possible. Using stable_sort ensures that the output is
+ // consistent across runs.
+ std::stable_sort(aligned_to_4.begin(), aligned_to_4.end());
+
+ // Now group fields aligned to 4 bytes (or the 4-field groups created above)
+ // into pairs, and treat those like a single field aligned to 8 bytes.
+ for (int i = 0; i < aligned_to_4.size(); i += 2) {
+ FieldGroup field_group;
+ for (int j = i; j < aligned_to_4.size() && j < i + 2; ++j) {
+ field_group.Append(aligned_to_4[j]);
+ }
+ if (i == aligned_to_4.size() - 1) {
+ // Move incomplete 4-byte block to the end.
+ field_group.SetPreferredLocation(fields->size() + 1);
+ }
+ aligned_to_8.push_back(field_group);
+ }
+ // Sort by preferred location.
+ std::stable_sort(aligned_to_8.begin(), aligned_to_8.end());
+
+ // Now pull out all the FieldDescriptors in order.
+ fields->clear();
+ for (int i = 0; i < aligned_to_8.size(); ++i) {
+ fields->insert(fields->end(),
+ aligned_to_8[i].fields().begin(),
+ aligned_to_8[i].fields().end());
+ }
+}
+
+string MessageTypeProtoName(const FieldDescriptor* field) {
+ return field->message_type()->full_name();
+}
+
+// Emits an if-statement with a condition that evaluates to true if |field| is
+// considered non-default (will be sent over the wire), for message types
+// without true field presence. Should only be called if
+// !HasFieldPresence(message_descriptor).
+bool EmitFieldNonDefaultCondition(io::Printer* printer,
+ const string& prefix,
+ const FieldDescriptor* field) {
+ // Merge and serialize semantics: primitive fields are merged/serialized only
+ // if non-zero (numeric) or non-empty (string).
+ if (!field->is_repeated() && !field->containing_oneof()) {
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_STRING) {
+ printer->Print(
+ "if ($prefix$$name$().size() > 0) {\n",
+ "prefix", prefix,
+ "name", FieldName(field));
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Message fields still have has_$name$() methods.
+ printer->Print(
+ "if ($prefix$has_$name$()) {\n",
+ "prefix", prefix,
+ "name", FieldName(field));
+ } else {
+ printer->Print(
+ "if ($prefix$$name$() != 0) {\n",
+ "prefix", prefix,
+ "name", FieldName(field));
+ }
+ printer->Indent();
+ return true;
+ } else if (field->containing_oneof()) {
+ printer->Print(
+ "if (has_$name$()) {\n",
+ "name", FieldName(field));
+ printer->Indent();
+ return true;
+ }
+ return false;
+}
+
+// Does the given field have a has_$name$() method?
+bool HasHasMethod(const FieldDescriptor* field) {
+ if (HasFieldPresence(field->file())) {
+ // In proto1/proto2, every field has a has_$name$() method.
+ return true;
+ }
+ // For message types without true field presence, only fields with a message
+ // type have a has_$name$() method.
+ return field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE;
+}
+
+// Collects map entry message type information.
+void CollectMapInfo(const Descriptor* descriptor,
+ map<string, string>* variables) {
+ GOOGLE_CHECK(IsMapEntryMessage(descriptor));
+ const FieldDescriptor* key = descriptor->FindFieldByName("key");
+ const FieldDescriptor* val = descriptor->FindFieldByName("value");
+ (*variables)["key"] = PrimitiveTypeName(key->cpp_type());
+ switch (val->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ (*variables)["val"] = FieldMessageTypeName(val);
+ break;
+ case FieldDescriptor::CPPTYPE_ENUM:
+ (*variables)["val"] = ClassName(val->enum_type(), true);
+ break;
+ default:
+ (*variables)["val"] = PrimitiveTypeName(val->cpp_type());
+ }
+ (*variables)["key_wire_type"] =
+ "::google::protobuf::internal::WireFormatLite::TYPE_" +
+ ToUpper(DeclaredTypeMethodName(key->type()));
+ (*variables)["val_wire_type"] =
+ "::google::protobuf::internal::WireFormatLite::TYPE_" +
+ ToUpper(DeclaredTypeMethodName(val->type()));
+}
+
+// Does the given field have a private (internal helper only) has_$name$()
+// method?
+bool HasPrivateHasMethod(const FieldDescriptor* field) {
+ // Only for oneofs in message types with no field presence. has_$name$(),
+ // based on the oneof case, is still useful internally for generated code.
+ return (!HasFieldPresence(field->file()) &&
+ field->containing_oneof() != NULL);
+}
+
+} // anonymous namespace
+
+// ===================================================================
+
+MessageGenerator::MessageGenerator(const Descriptor* descriptor,
+ const Options& options)
+ : descriptor_(descriptor),
+ classname_(ClassName(descriptor, false)),
+ options_(options),
+ field_generators_(descriptor, options),
+ nested_generators_(new google::protobuf::scoped_ptr<
+ MessageGenerator>[descriptor->nested_type_count()]),
+ enum_generators_(
+ new google::protobuf::scoped_ptr<EnumGenerator>[descriptor->enum_type_count()]),
+ extension_generators_(new google::protobuf::scoped_ptr<
+ ExtensionGenerator>[descriptor->extension_count()]),
+ use_dependent_base_(false) {
+
+ for (int i = 0; i < descriptor->nested_type_count(); i++) {
+ nested_generators_[i].reset(
+ new MessageGenerator(descriptor->nested_type(i), options));
+ }
+
+ for (int i = 0; i < descriptor->enum_type_count(); i++) {
+ enum_generators_[i].reset(
+ new EnumGenerator(descriptor->enum_type(i), options));
+ }
+
+ for (int i = 0; i < descriptor->extension_count(); i++) {
+ extension_generators_[i].reset(
+ new ExtensionGenerator(descriptor->extension(i), options));
+ }
+
+ num_required_fields_ = 0;
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ if (descriptor->field(i)->is_required()) {
+ ++num_required_fields_;
+ }
+ if (options.proto_h && IsFieldDependent(descriptor->field(i))) {
+ use_dependent_base_ = true;
+ }
+ }
+ if (options.proto_h && descriptor->oneof_decl_count() > 0) {
+ // Always make oneofs dependent.
+ use_dependent_base_ = true;
+ }
+}
+
+MessageGenerator::~MessageGenerator() {}
+
+void MessageGenerator::
+FillMessageForwardDeclarations(map<string, const Descriptor*>* class_names) {
+ (*class_names)[classname_] = descriptor_;
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // map entry message doesn't need forward declaration. Since map entry
+ // message cannot be a top level class, we just need to avoid calling
+ // GenerateForwardDeclaration here.
+ if (IsMapEntryMessage(descriptor_->nested_type(i))) continue;
+ nested_generators_[i]->FillMessageForwardDeclarations(class_names);
+ }
+}
+
+void MessageGenerator::
+FillEnumForwardDeclarations(map<string, const EnumDescriptor*>* enum_names) {
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ nested_generators_[i]->FillEnumForwardDeclarations(enum_names);
+ }
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ enum_generators_[i]->FillForwardDeclaration(enum_names);
+ }
+}
+
+void MessageGenerator::
+GenerateEnumDefinitions(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ nested_generators_[i]->GenerateEnumDefinitions(printer);
+ }
+
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateDefinition(printer);
+ }
+}
+
+void MessageGenerator::
+GenerateGetEnumDescriptorSpecializations(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ nested_generators_[i]->GenerateGetEnumDescriptorSpecializations(printer);
+ }
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateGetEnumDescriptorSpecializations(printer);
+ }
+}
+
+void MessageGenerator::
+GenerateDependentFieldAccessorDeclarations(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ PrintFieldComment(printer, field);
+
+ map<string, string> vars;
+ SetCommonFieldVariables(field, &vars, options_);
+
+ if (use_dependent_base_ && IsFieldDependent(field)) {
+ // If the message is dependent, the inline clear_*() method will need
+ // to delete the message type, so it must be in the dependent base
+ // class. (See also GenerateFieldAccessorDeclarations.)
+ printer->Print(vars, "$deprecated_attr$void clear_$name$();\n");
+ }
+ // Generate type-specific accessor declarations.
+ field_generators_.get(field).GenerateDependentAccessorDeclarations(printer);
+ printer->Print("\n");
+ }
+}
+
+void MessageGenerator::
+GenerateFieldAccessorDeclarations(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ PrintFieldComment(printer, field);
+
+ map<string, string> vars;
+ SetCommonFieldVariables(field, &vars, options_);
+ vars["constant_name"] = FieldConstantName(field);
+
+ bool dependent_field = use_dependent_base_ && IsFieldDependent(field);
+ if (dependent_field &&
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ !field->is_map()) {
+ // If this field is dependent, the dependent base class determines
+ // the message type from the derived class (which is a template
+ // parameter). This typedef is for that:
+ printer->Print(
+ "private:\n"
+ "typedef $field_type$ $dependent_type$;\n"
+ "public:\n",
+ "field_type", FieldMessageTypeName(field),
+ "dependent_type", DependentTypeName(field));
+ }
+
+ if (field->is_repeated()) {
+ printer->Print(vars, "$deprecated_attr$int $name$_size() const;\n");
+ } else if (HasHasMethod(field)) {
+ printer->Print(vars, "$deprecated_attr$bool has_$name$() const;\n");
+ } else if (HasPrivateHasMethod(field)) {
+ printer->Print(vars,
+ "private:\n"
+ "bool has_$name$() const;\n"
+ "public:\n");
+ }
+
+ if (!dependent_field) {
+ // If this field is dependent, then its clear_() method is in the
+ // depenent base class. (See also GenerateDependentAccessorDeclarations.)
+ printer->Print(vars, "$deprecated_attr$void clear_$name$();\n");
+ }
+ printer->Print(vars,
+ "$deprecated_attr$static const int $constant_name$ = "
+ "$number$;\n");
+
+ // Generate type-specific accessor declarations.
+ field_generators_.get(field).GenerateAccessorDeclarations(printer);
+
+ printer->Print("\n");
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ // Generate accessors for extensions. We just call a macro located in
+ // extension_set.h since the accessors about 80 lines of static code.
+ printer->Print(
+ "GOOGLE_PROTOBUF_EXTENSION_ACCESSORS($classname$)\n",
+ "classname", classname_);
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "$camel_oneof_name$Case $oneof_name$_case() const;\n",
+ "camel_oneof_name",
+ UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), true),
+ "oneof_name", descriptor_->oneof_decl(i)->name());
+ }
+}
+
+void MessageGenerator::
+GenerateDependentFieldAccessorDefinitions(io::Printer* printer) {
+ if (!use_dependent_base_) return;
+
+ printer->Print("// $classname$\n\n", "classname",
+ DependentBaseClassTemplateName(descriptor_));
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ PrintFieldComment(printer, field);
+
+ // These functions are not really dependent: they are part of the
+ // (non-dependent) derived class. However, they need to live outside
+ // any #ifdef guards, so we treat them as if they were dependent.
+ //
+ // See the comment in FileGenerator::GenerateInlineFunctionDefinitions
+ // for a more complete explanation.
+ if (use_dependent_base_ && IsFieldDependent(field)) {
+ map<string, string> vars;
+ SetCommonFieldVariables(field, &vars, options_);
+ vars["inline"] = "inline ";
+ if (field->containing_oneof()) {
+ vars["field_name"] = UnderscoresToCamelCase(field->name(), true);
+ vars["oneof_name"] = field->containing_oneof()->name();
+ vars["oneof_index"] = SimpleItoa(field->containing_oneof()->index());
+ GenerateOneofMemberHasBits(field, vars, printer);
+ } else if (!field->is_repeated()) {
+ // There will be no header guard, so this always has to be inline.
+ GenerateSingularFieldHasBits(field, vars, printer);
+ }
+ // vars needed for clear_(), which is in the dependent base:
+ // (See also GenerateDependentFieldAccessorDeclarations.)
+ vars["tmpl"] = "template<class T>\n";
+ vars["dependent_classname"] =
+ DependentBaseClassTemplateName(descriptor_) + "<T>";
+ vars["this_message"] = DependentBaseDownCast();
+ vars["this_const_message"] = DependentBaseConstDownCast();
+ GenerateFieldClear(field, vars, printer);
+ }
+
+ // Generate type-specific accessors.
+ field_generators_.get(field)
+ .GenerateDependentInlineAccessorDefinitions(printer);
+
+ printer->Print("\n");
+ }
+
+ // Generate has_$name$() and clear_has_$name$() functions for oneofs
+ // Similar to other has-bits, these must always be in the header if we
+ // are using a dependent base class.
+ GenerateOneofHasBits(printer, true /* is_inline */);
+}
+
+void MessageGenerator::
+GenerateSingularFieldHasBits(const FieldDescriptor* field,
+ map<string, string> vars,
+ io::Printer* printer) {
+ if (HasFieldPresence(descriptor_->file())) {
+ // N.B.: without field presence, we do not use has-bits or generate
+ // has_$name$() methods.
+ vars["has_array_index"] = SimpleItoa(field->index() / 32);
+ vars["has_mask"] = StrCat(strings::Hex(1u << (field->index() % 32),
+ strings::ZERO_PAD_8));
+ printer->Print(vars,
+ "$inline$"
+ "bool $classname$::has_$name$() const {\n"
+ " return (_has_bits_[$has_array_index$] & 0x$has_mask$u) != 0;\n"
+ "}\n"
+ "$inline$"
+ "void $classname$::set_has_$name$() {\n"
+ " _has_bits_[$has_array_index$] |= 0x$has_mask$u;\n"
+ "}\n"
+ "$inline$"
+ "void $classname$::clear_has_$name$() {\n"
+ " _has_bits_[$has_array_index$] &= ~0x$has_mask$u;\n"
+ "}\n");
+ } else {
+ // Message fields have a has_$name$() method.
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ bool is_lazy = false;
+ if (is_lazy) {
+ printer->Print(vars,
+ "$inline$"
+ "bool $classname$::has_$name$() const {\n"
+ " return !$name$_.IsCleared();\n"
+ "}\n");
+ } else {
+ printer->Print(vars,
+ "$inline$"
+ "bool $classname$::has_$name$() const {\n"
+ " return !_is_default_instance_ && $name$_ != NULL;\n"
+ "}\n");
+ }
+ }
+ }
+}
+
+void MessageGenerator::
+GenerateOneofHasBits(io::Printer* printer, bool is_inline) {
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ map<string, string> vars;
+ vars["oneof_name"] = descriptor_->oneof_decl(i)->name();
+ vars["oneof_index"] = SimpleItoa(descriptor_->oneof_decl(i)->index());
+ vars["cap_oneof_name"] =
+ ToUpper(descriptor_->oneof_decl(i)->name());
+ vars["classname"] = classname_;
+ vars["inline"] = (is_inline ? "inline " : "");
+ printer->Print(
+ vars,
+ "$inline$"
+ "bool $classname$::has_$oneof_name$() const {\n"
+ " return $oneof_name$_case() != $cap_oneof_name$_NOT_SET;\n"
+ "}\n"
+ "$inline$"
+ "void $classname$::clear_has_$oneof_name$() {\n"
+ " _oneof_case_[$oneof_index$] = $cap_oneof_name$_NOT_SET;\n"
+ "}\n");
+ }
+}
+
+void MessageGenerator::
+GenerateOneofMemberHasBits(const FieldDescriptor* field,
+ const map<string, string>& vars,
+ io::Printer* printer) {
+ // Singular field in a oneof
+ // N.B.: Without field presence, we do not use has-bits or generate
+ // has_$name$() methods, but oneofs still have set_has_$name$().
+ // Oneofs also have has_$name$() but only as a private helper
+ // method, so that generated code is slightly cleaner (vs. comparing
+ // _oneof_case_[index] against a constant everywhere).
+ printer->Print(vars,
+ "$inline$"
+ "bool $classname$::has_$name$() const {\n"
+ " return $oneof_name$_case() == k$field_name$;\n"
+ "}\n");
+ printer->Print(vars,
+ "$inline$"
+ "void $classname$::set_has_$name$() {\n"
+ " _oneof_case_[$oneof_index$] = k$field_name$;\n"
+ "}\n");
+}
+
+void MessageGenerator::
+GenerateFieldClear(const FieldDescriptor* field,
+ const map<string, string>& vars,
+ io::Printer* printer) {
+ // Generate clear_$name$() (See GenerateFieldAccessorDeclarations and
+ // GenerateDependentFieldAccessorDeclarations, $dependent_classname$ is
+ // set by the Generate*Definitions functions.)
+ printer->Print(vars,
+ "$tmpl$"
+ "$inline$"
+ "void $dependent_classname$::clear_$name$() {\n");
+
+ printer->Indent();
+
+ if (field->containing_oneof()) {
+ // Clear this field only if it is the active field in this oneof,
+ // otherwise ignore
+ printer->Print(vars,
+ "if ($this_message$has_$name$()) {\n");
+ printer->Indent();
+ field_generators_.get(field)
+ .GenerateClearingCode(printer);
+ printer->Print(vars,
+ "$this_message$clear_has_$oneof_name$();\n");
+ printer->Outdent();
+ printer->Print("}\n");
+ } else {
+ field_generators_.get(field)
+ .GenerateClearingCode(printer);
+ if (HasFieldPresence(descriptor_->file())) {
+ if (!field->is_repeated()) {
+ printer->Print(vars,
+ "$this_message$clear_has_$name$();\n");
+ }
+ }
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MessageGenerator::
+GenerateFieldAccessorDefinitions(io::Printer* printer, bool is_inline) {
+ printer->Print("// $classname$\n\n", "classname", classname_);
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ PrintFieldComment(printer, field);
+
+ map<string, string> vars;
+ SetCommonFieldVariables(field, &vars, options_);
+ vars["inline"] = is_inline ? "inline " : "";
+ if (use_dependent_base_ && IsFieldDependent(field)) {
+ vars["tmpl"] = "template<class T>\n";
+ vars["dependent_classname"] =
+ DependentBaseClassTemplateName(descriptor_) + "<T>";
+ vars["this_message"] = "reinterpret_cast<T*>(this)->";
+ vars["this_const_message"] = "reinterpret_cast<const T*>(this)->";
+ } else {
+ vars["tmpl"] = "";
+ vars["dependent_classname"] = vars["classname"];
+ vars["this_message"] = "";
+ vars["this_const_message"] = "";
+ }
+
+ // Generate has_$name$() or $name$_size().
+ if (field->is_repeated()) {
+ printer->Print(vars,
+ "$inline$"
+ "int $classname$::$name$_size() const {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ } else if (field->containing_oneof()) {
+ vars["field_name"] = UnderscoresToCamelCase(field->name(), true);
+ vars["oneof_name"] = field->containing_oneof()->name();
+ vars["oneof_index"] = SimpleItoa(field->containing_oneof()->index());
+ if (!use_dependent_base_ || !IsFieldDependent(field)) {
+ GenerateOneofMemberHasBits(field, vars, printer);
+ }
+ } else {
+ // Singular field.
+ if (!use_dependent_base_ || !IsFieldDependent(field)) {
+ GenerateSingularFieldHasBits(field, vars, printer);
+ }
+ }
+
+ if (!use_dependent_base_ || !IsFieldDependent(field)) {
+ GenerateFieldClear(field, vars, printer);
+ }
+
+ // Generate type-specific accessors.
+ field_generators_.get(field).GenerateInlineAccessorDefinitions(printer,
+ is_inline);
+
+ printer->Print("\n");
+ }
+
+ if (!use_dependent_base_) {
+ // Generate has_$name$() and clear_has_$name$() functions for oneofs
+ // If we aren't using a dependent base, they can be with the other functions
+ // that are #ifdef-guarded.
+ GenerateOneofHasBits(printer, is_inline);
+ }
+}
+
+// Helper for the code that emits the Clear() method.
+static bool CanClearByZeroing(const FieldDescriptor* field) {
+ if (field->is_repeated() || field->is_extension()) return false;
+ switch (field->cpp_type()) {
+ case internal::WireFormatLite::CPPTYPE_ENUM:
+ return field->default_value_enum()->number() == 0;
+ case internal::WireFormatLite::CPPTYPE_INT32:
+ return field->default_value_int32() == 0;
+ case internal::WireFormatLite::CPPTYPE_INT64:
+ return field->default_value_int64() == 0;
+ case internal::WireFormatLite::CPPTYPE_UINT32:
+ return field->default_value_uint32() == 0;
+ case internal::WireFormatLite::CPPTYPE_UINT64:
+ return field->default_value_uint64() == 0;
+ case internal::WireFormatLite::CPPTYPE_FLOAT:
+ return field->default_value_float() == 0;
+ case internal::WireFormatLite::CPPTYPE_DOUBLE:
+ return field->default_value_double() == 0;
+ case internal::WireFormatLite::CPPTYPE_BOOL:
+ return field->default_value_bool() == false;
+ default:
+ return false;
+ }
+}
+
+void MessageGenerator::
+GenerateDependentBaseClassDefinition(io::Printer* printer) {
+ if (!use_dependent_base_) {
+ return;
+ }
+
+ map<string, string> vars;
+ vars["classname"] = DependentBaseClassTemplateName(descriptor_);
+ vars["full_name"] = descriptor_->full_name();
+ vars["superclass"] = SuperClassName(descriptor_, options_);
+
+ printer->Print(vars,
+ "template <class T>\n"
+ "class $classname$ : public $superclass$ "
+ "/* @@protoc_insertion_point(dep_base_class_definition:$full_name$) */ {\n"
+ " public:\n");
+ printer->Indent();
+
+ printer->Print(vars,
+ "$classname$() {}\n"
+ "virtual ~$classname$() {}\n"
+ "\n");
+
+ // Generate dependent accessor methods for all fields.
+ GenerateDependentFieldAccessorDeclarations(printer);
+
+ printer->Outdent();
+ printer->Print("};\n");
+}
+
+void MessageGenerator::
+GenerateClassDefinition(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // map entry message doesn't need class definition. Since map entry message
+ // cannot be a top level class, we just need to avoid calling
+ // GenerateClassDefinition here.
+ if (IsMapEntryMessage(descriptor_->nested_type(i))) continue;
+ nested_generators_[i]->GenerateClassDefinition(printer);
+ printer->Print("\n");
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+
+ if (use_dependent_base_) {
+ GenerateDependentBaseClassDefinition(printer);
+ printer->Print("\n");
+ }
+
+ map<string, string> vars;
+ vars["classname"] = classname_;
+ vars["full_name"] = descriptor_->full_name();
+ vars["field_count"] = SimpleItoa(descriptor_->field_count());
+ vars["oneof_decl_count"] = SimpleItoa(descriptor_->oneof_decl_count());
+ if (options_.dllexport_decl.empty()) {
+ vars["dllexport"] = "";
+ } else {
+ vars["dllexport"] = options_.dllexport_decl + " ";
+ }
+ if (use_dependent_base_) {
+ vars["superclass"] =
+ DependentBaseClassTemplateName(descriptor_) + "<" + classname_ + ">";
+ } else {
+ vars["superclass"] = SuperClassName(descriptor_, options_);
+ }
+ printer->Print(vars,
+ "class $dllexport$$classname$ : public $superclass$ "
+ "/* @@protoc_insertion_point(class_definition:$full_name$) */ "
+ "{\n");
+ printer->Annotate("classname", descriptor_);
+ if (use_dependent_base_) {
+ printer->Print(vars, " friend class $superclass$;\n");
+ }
+ printer->Print(" public:\n");
+ printer->Indent();
+
+ printer->Print(vars,
+ "$classname$();\n"
+ "virtual ~$classname$();\n"
+ "\n"
+ "$classname$(const $classname$& from);\n"
+ "\n"
+ "inline $classname$& operator=(const $classname$& from) {\n"
+ " CopyFrom(from);\n"
+ " return *this;\n"
+ "}\n"
+ "\n");
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {\n"
+ " return _internal_metadata_.unknown_fields();\n"
+ "}\n"
+ "\n"
+ "inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {\n"
+ " return _internal_metadata_.mutable_unknown_fields();\n"
+ "}\n"
+ "\n");
+ } else {
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(
+ "inline const ::std::string& unknown_fields() const {\n"
+ " return _unknown_fields_.Get(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited());\n"
+ "}\n"
+ "\n"
+ "inline ::std::string* mutable_unknown_fields() {\n"
+ " return _unknown_fields_.Mutable(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited(),\n"
+ " GetArenaNoVirtual());\n"
+ "}\n"
+ "\n");
+ } else {
+ printer->Print(
+ "inline const ::std::string& unknown_fields() const {\n"
+ " return _unknown_fields_.GetNoArena(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited());\n"
+ "}\n"
+ "\n"
+ "inline ::std::string* mutable_unknown_fields() {\n"
+ " return _unknown_fields_.MutableNoArena(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited());\n"
+ "}\n"
+ "\n");
+ }
+ }
+ }
+
+ // N.B.: We exclude GetArena() when arena support is disabled, falling back on
+ // MessageLite's implementation which returns NULL rather than generating our
+ // own method which returns NULL, in order to reduce code size.
+ if (SupportsArenas(descriptor_)) {
+ // virtual method version of GetArenaNoVirtual(), required for generic dispatch given a
+ // MessageLite* (e.g., in RepeatedField::AddAllocated()).
+ printer->Print(
+ "inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }\n"
+ "inline void* GetMaybeArenaPointer() const {\n"
+ " return MaybeArenaPtr();\n"
+ "}\n");
+ }
+
+ // Only generate this member if it's not disabled.
+ if (HasDescriptorMethods(descriptor_->file(), options_) &&
+ !descriptor_->options().no_standard_descriptor_accessor()) {
+ printer->Print(vars,
+ "static const ::google::protobuf::Descriptor* descriptor();\n");
+ }
+
+ printer->Print(vars,
+ "static const $classname$& default_instance();\n"
+ "\n");
+
+ // Generate enum values for every field in oneofs. One list is generated for
+ // each oneof with an additional *_NOT_SET value.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "enum $camel_oneof_name$Case {\n",
+ "camel_oneof_name",
+ UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), true));
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ printer->Print(
+ "k$field_name$ = $field_number$,\n",
+ "field_name",
+ UnderscoresToCamelCase(
+ descriptor_->oneof_decl(i)->field(j)->name(), true),
+ "field_number",
+ SimpleItoa(descriptor_->oneof_decl(i)->field(j)->number()));
+ }
+ printer->Print(
+ "$cap_oneof_name$_NOT_SET = 0,\n",
+ "cap_oneof_name",
+ ToUpper(descriptor_->oneof_decl(i)->name()));
+ printer->Outdent();
+ printer->Print(
+ "};\n"
+ "\n");
+ }
+
+ if (!StaticInitializersForced(descriptor_->file(), options_)) {
+ printer->Print(vars,
+ "#ifdef GOOGLE_PROTOBUF_NO_STATIC_INITIALIZER\n"
+ "// Returns the internal default instance pointer. This function can\n"
+ "// return NULL thus should not be used by the user. This is intended\n"
+ "// for Protobuf internal code. Please use default_instance() declared\n"
+ "// above instead.\n"
+ "static inline const $classname$* internal_default_instance() {\n"
+ " return default_instance_;\n"
+ "}\n"
+ "#endif\n"
+ "\n");
+ }
+
+
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(vars,
+ "void UnsafeArenaSwap($classname$* other);\n");
+ }
+
+ if (IsAnyMessage(descriptor_)) {
+ printer->Print(vars,
+ "// implements Any -----------------------------------------------\n"
+ "\n"
+ "void PackFrom(const ::google::protobuf::Message& message);\n"
+ "void PackFrom(const ::google::protobuf::Message& message,\n"
+ " const ::std::string& type_url_prefix);\n"
+ "bool UnpackTo(::google::protobuf::Message* message) const;\n"
+ "template<typename T> bool Is() const {\n"
+ " return _any_metadata_.Is<T>();\n"
+ "}\n"
+ "\n");
+ }
+
+ printer->Print(vars,
+ "void Swap($classname$* other);\n"
+ "\n"
+ "// implements Message ----------------------------------------------\n"
+ "\n"
+ "inline $classname$* New() const { return New(NULL); }\n"
+ "\n"
+ "$classname$* New(::google::protobuf::Arena* arena) const;\n");
+
+ if (HasGeneratedMethods(descriptor_->file(), options_)) {
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(vars,
+ "void CopyFrom(const ::google::protobuf::Message& from);\n"
+ "void MergeFrom(const ::google::protobuf::Message& from);\n");
+ } else {
+ printer->Print(vars,
+ "void CheckTypeAndMergeFrom(const ::google::protobuf::MessageLite& from);\n");
+ }
+
+ printer->Print(vars,
+ "void CopyFrom(const $classname$& from);\n"
+ "void MergeFrom(const $classname$& from);\n"
+ "void Clear();\n"
+ "bool IsInitialized() const;\n"
+ "\n"
+ "int ByteSize() const;\n"
+ "bool MergePartialFromCodedStream(\n"
+ " ::google::protobuf::io::CodedInputStream* input);\n"
+ "void SerializeWithCachedSizes(\n"
+ " ::google::protobuf::io::CodedOutputStream* output) const;\n");
+ // DiscardUnknownFields() is implemented in message.cc using reflections. We
+ // need to implement this function in generated code for messages.
+ if (!UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "void DiscardUnknownFields();\n");
+ }
+ if (HasFastArraySerialization(descriptor_->file(), options_)) {
+ printer->Print(
+ "::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(\n"
+ " bool deterministic, ::google::protobuf::uint8* output) const;\n"
+ "::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {\n"
+ " return InternalSerializeWithCachedSizesToArray(false, output);\n"
+ "}\n");
+ }
+ }
+
+ // Check all FieldDescriptors including those in oneofs to estimate
+ // whether ::std::string is likely to be used, and depending on that
+ // estimate, set uses_string_ to true or false. That contols
+ // whether to force initialization of empty_string_ in SharedCtor().
+ // It's often advantageous to do so to keep "is empty_string_
+ // inited?" code from appearing all over the place.
+ vector<const FieldDescriptor*> descriptors;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ descriptors.push_back(descriptor_->field(i));
+ }
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ descriptors.push_back(descriptor_->oneof_decl(i)->field(j));
+ }
+ }
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ const Descriptor* nested_type = descriptor_->nested_type(i);
+ if (IsMapEntryMessage(nested_type)) {
+ descriptors.push_back(nested_type->FindFieldByName("key"));
+ descriptors.push_back(nested_type->FindFieldByName("value"));
+ }
+ }
+ uses_string_ = false;
+ if (PreserveUnknownFields(descriptor_) &&
+ !UseUnknownFieldSet(descriptor_->file(), options_)) {
+ uses_string_ = true;
+ }
+ for (int i = 0; i < descriptors.size(); i++) {
+ const FieldDescriptor* field = descriptors[i];
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_STRING) {
+ switch (field->options().ctype()) {
+ default: uses_string_ = true; break;
+ }
+ }
+ }
+
+ printer->Print(
+ "int GetCachedSize() const { return _cached_size_; }\n"
+ "private:\n"
+ "void SharedCtor();\n"
+ "void SharedDtor();\n"
+ "void SetCachedSize(int size) const;\n"
+ "void InternalSwap($classname$* other);\n",
+ "classname", classname_);
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(
+ "protected:\n"
+ "explicit $classname$(::google::protobuf::Arena* arena);\n"
+ "private:\n"
+ "static void ArenaDtor(void* object);\n"
+ "inline void RegisterArenaDtor(::google::protobuf::Arena* arena);\n",
+ "classname", classname_);
+ }
+
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "private:\n"
+ "inline ::google::protobuf::Arena* GetArenaNoVirtual() const {\n"
+ " return _internal_metadata_.arena();\n"
+ "}\n"
+ "inline void* MaybeArenaPtr() const {\n"
+ " return _internal_metadata_.raw_arena_ptr();\n"
+ "}\n"
+ "public:\n"
+ "\n");
+ } else {
+ printer->Print(
+ "private:\n"
+ "inline ::google::protobuf::Arena* GetArenaNoVirtual() const {\n"
+ " return _arena_ptr_;\n"
+ "}\n"
+ "inline ::google::protobuf::Arena* MaybeArenaPtr() const {\n"
+ " return _arena_ptr_;\n"
+ "}\n"
+ "public:\n"
+ "\n");
+ }
+
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(
+ "::google::protobuf::Metadata GetMetadata() const;\n"
+ "\n");
+ } else {
+ printer->Print(
+ "::std::string GetTypeName() const;\n"
+ "\n");
+ }
+
+ printer->Print(
+ "// nested types ----------------------------------------------------\n"
+ "\n");
+
+ // Import all nested message classes into this class's scope with typedefs.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ const Descriptor* nested_type = descriptor_->nested_type(i);
+ if (!IsMapEntryMessage(nested_type)) {
+ printer->Print("typedef $nested_full_name$ $nested_name$;\n",
+ "nested_name", nested_type->name(),
+ "nested_full_name", ClassName(nested_type, false));
+ }
+ }
+
+ if (descriptor_->nested_type_count() > 0) {
+ printer->Print("\n");
+ }
+
+ // Import all nested enums and their values into this class's scope with
+ // typedefs and constants.
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateSymbolImports(printer);
+ printer->Print("\n");
+ }
+
+ printer->Print(
+ "// accessors -------------------------------------------------------\n"
+ "\n");
+
+ // Generate accessor methods for all fields.
+ GenerateFieldAccessorDeclarations(printer);
+
+ // Declare extension identifiers.
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ extension_generators_[i]->GenerateDeclaration(printer);
+ }
+
+
+ printer->Print(
+ "// @@protoc_insertion_point(class_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ // Generate private members.
+ printer->Outdent();
+ printer->Print(" private:\n");
+ printer->Indent();
+
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->is_repeated()) {
+ // set_has_***() generated in all proto1/2 code and in oneofs (only) for
+ // messages without true field presence.
+ if (HasFieldPresence(descriptor_->file()) ||
+ descriptor_->field(i)->containing_oneof()) {
+ printer->Print(
+ "inline void set_has_$name$();\n",
+ "name", FieldName(descriptor_->field(i)));
+ }
+ // clear_has_***() generated only for non-oneof fields
+ // in proto1/2.
+ if (!descriptor_->field(i)->containing_oneof() &&
+ HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ "inline void clear_has_$name$();\n",
+ "name", FieldName(descriptor_->field(i)));
+ }
+ }
+ }
+ printer->Print("\n");
+
+ // Generate oneof function declarations
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "inline bool has_$oneof_name$() const;\n"
+ "void clear_$oneof_name$();\n"
+ "inline void clear_has_$oneof_name$();\n\n",
+ "oneof_name", descriptor_->oneof_decl(i)->name());
+ }
+
+ if (HasGeneratedMethods(descriptor_->file(), options_) &&
+ !descriptor_->options().message_set_wire_format() &&
+ num_required_fields_ > 1) {
+ printer->Print(
+ "// helper for ByteSize()\n"
+ "int RequiredFieldsByteSizeFallback() const;\n\n");
+ }
+
+ // Prepare decls for _cached_size_ and _has_bits_. Their position in the
+ // output will be determined later.
+
+ bool need_to_emit_cached_size = true;
+ // TODO(kenton): Make _cached_size_ an atomic<int> when C++ supports it.
+ const string cached_size_decl = "mutable int _cached_size_;\n";
+
+ // TODO(jieluo) - Optimize _has_bits_ for repeated and oneof fields.
+ size_t sizeof_has_bits = (descriptor_->field_count() + 31) / 32 * 4;
+ if (descriptor_->field_count() == 0) {
+ // Zero-size arrays aren't technically allowed, and MSVC in particular
+ // doesn't like them. We still need to declare these arrays to make
+ // other code compile. Since this is an uncommon case, we'll just declare
+ // them with size 1 and waste some space. Oh well.
+ sizeof_has_bits = 4;
+ }
+ const string has_bits_decl = sizeof_has_bits == 0 ? "" :
+ "::google::protobuf::uint32 _has_bits_[" + SimpleItoa(sizeof_has_bits / 4) + "];\n";
+
+
+ // To minimize padding, data members are divided into three sections:
+ // (1) members assumed to align to 8 bytes
+ // (2) members corresponding to message fields, re-ordered to optimize
+ // alignment.
+ // (3) members assumed to align to 4 bytes.
+
+ // Members assumed to align to 8 bytes:
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "::google::protobuf::internal::ExtensionSet _extensions_;\n"
+ "\n");
+ }
+
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;\n");
+ } else {
+ printer->Print(
+ "::google::protobuf::internal::ArenaStringPtr _unknown_fields_;\n"
+ "::google::protobuf::Arena* _arena_ptr_;\n"
+ "\n");
+ }
+
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(
+ "friend class ::google::protobuf::Arena;\n"
+ "typedef void InternalArenaConstructable_;\n"
+ "typedef void DestructorSkippable_;\n");
+ }
+
+ if (HasFieldPresence(descriptor_->file())) {
+ // _has_bits_ is frequently accessed, so to reduce code size and improve
+ // speed, it should be close to the start of the object. But, try not to
+ // waste space:_has_bits_ by itself always makes sense if its size is a
+ // multiple of 8, but, otherwise, maybe _has_bits_ and cached_size_ together
+ // will work well.
+ printer->Print(has_bits_decl.c_str());
+ if ((sizeof_has_bits % 8) != 0) {
+ printer->Print(cached_size_decl.c_str());
+ need_to_emit_cached_size = false;
+ }
+ } else {
+ // Without field presence, we need another way to disambiguate the default
+ // instance, because the default instance's submessage fields (if any) store
+ // pointers to the default instances of the submessages even when they
+ // aren't present. Alternatives to this approach might be to (i) use a
+ // tagged pointer on all message fields, setting a tag bit for "not really
+ // present, just default instance"; or (ii) comparing |this| against the
+ // return value from GeneratedMessageFactory::GetPrototype() in all
+ // has_$field$() calls. However, both of these options are much more
+ // expensive (in code size and CPU overhead) than just checking a field in
+ // the message. Long-term, the best solution would be to rearchitect the
+ // default instance design not to store pointers to submessage default
+ // instances, and have reflection get those some other way; but that change
+ // would have too much impact on proto2.
+ printer->Print(
+ "bool _is_default_instance_;\n");
+ }
+
+ // Field members:
+
+ // List fields which doesn't belong to any oneof
+ vector<const FieldDescriptor*> fields;
+ hash_map<string, int> fieldname_to_chunk;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ fields.push_back(field);
+ fieldname_to_chunk[FieldName(field)] = i / 8;
+ }
+ }
+ OptimizePadding(&fields);
+ // Emit some private and static members
+ runs_of_fields_ = vector< vector<string> >(1);
+ for (int i = 0; i < fields.size(); ++i) {
+ const FieldDescriptor* field = fields[i];
+ const FieldGenerator& generator = field_generators_.get(field);
+ generator.GenerateStaticMembers(printer);
+ generator.GeneratePrivateMembers(printer);
+ if (CanClearByZeroing(field)) {
+ const string& fieldname = FieldName(field);
+ if (!runs_of_fields_.back().empty() &&
+ (fieldname_to_chunk[runs_of_fields_.back().back()] !=
+ fieldname_to_chunk[fieldname])) {
+ runs_of_fields_.push_back(vector<string>());
+ }
+ runs_of_fields_.back().push_back(fieldname);
+ } else if (!runs_of_fields_.back().empty()) {
+ runs_of_fields_.push_back(vector<string>());
+ }
+ }
+
+ // For each oneof generate a union
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "union $camel_oneof_name$Union {\n"
+ // explicit empty constructor is needed when union contains
+ // ArenaStringPtr members for string fields.
+ " $camel_oneof_name$Union() {}\n",
+ "camel_oneof_name",
+ UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), true));
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ field_generators_.get(descriptor_->oneof_decl(i)->
+ field(j)).GeneratePrivateMembers(printer);
+ }
+ printer->Outdent();
+ printer->Print(
+ "} $oneof_name$_;\n",
+ "oneof_name", descriptor_->oneof_decl(i)->name());
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ field_generators_.get(descriptor_->oneof_decl(i)->
+ field(j)).GenerateStaticMembers(printer);
+ }
+ }
+
+ // Members assumed to align to 4 bytes:
+
+ if (need_to_emit_cached_size) {
+ printer->Print(cached_size_decl.c_str());
+ need_to_emit_cached_size = false;
+ }
+
+ // Generate _oneof_case_.
+ if (descriptor_->oneof_decl_count() > 0) {
+ printer->Print(vars,
+ "::google::protobuf::uint32 _oneof_case_[$oneof_decl_count$];\n"
+ "\n");
+ }
+
+ // Generate _any_metadata_ for the Any type.
+ if (IsAnyMessage(descriptor_)) {
+ printer->Print(vars,
+ "::google::protobuf::internal::AnyMetadata _any_metadata_;\n");
+ }
+
+ // Declare AddDescriptors(), BuildDescriptors(), and ShutdownFile() as
+ // friends so that they can access private static variables like
+ // default_instance_ and reflection_.
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ "friend void $dllexport_decl$ $adddescriptorsname$();\n",
+ // Without.
+ "friend void $dllexport_decl$ $adddescriptorsname$_impl();\n",
+ // Vars.
+ "dllexport_decl", options_.dllexport_decl, "adddescriptorsname",
+ GlobalAddDescriptorsName(descriptor_->file()->name()));
+
+ printer->Print(
+ "friend void $assigndescriptorsname$();\n"
+ "friend void $shutdownfilename$();\n"
+ "\n",
+ "assigndescriptorsname",
+ GlobalAssignDescriptorsName(descriptor_->file()->name()),
+ "shutdownfilename", GlobalShutdownFileName(descriptor_->file()->name()));
+
+ printer->Print(
+ "void InitAsDefaultInstance();\n"
+ "static $classname$* default_instance_;\n",
+ "classname", classname_);
+
+ printer->Outdent();
+ printer->Print(vars, "};");
+ GOOGLE_DCHECK(!need_to_emit_cached_size);
+}
+
+void MessageGenerator::
+GenerateDependentInlineMethods(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // map entry message doesn't need inline methods. Since map entry message
+ // cannot be a top level class, we just need to avoid calling
+ // GenerateInlineMethods here.
+ if (IsMapEntryMessage(descriptor_->nested_type(i))) continue;
+ nested_generators_[i]->GenerateDependentInlineMethods(printer);
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+
+ GenerateDependentFieldAccessorDefinitions(printer);
+}
+
+void MessageGenerator::
+GenerateInlineMethods(io::Printer* printer, bool is_inline) {
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // map entry message doesn't need inline methods. Since map entry message
+ // cannot be a top level class, we just need to avoid calling
+ // GenerateInlineMethods here.
+ if (IsMapEntryMessage(descriptor_->nested_type(i))) continue;
+ nested_generators_[i]->GenerateInlineMethods(printer, is_inline);
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+
+ GenerateFieldAccessorDefinitions(printer, is_inline);
+
+ // Generate oneof_case() functions.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ map<string, string> vars;
+ vars["class_name"] = classname_;
+ vars["camel_oneof_name"] = UnderscoresToCamelCase(
+ descriptor_->oneof_decl(i)->name(), true);
+ vars["oneof_name"] = descriptor_->oneof_decl(i)->name();
+ vars["oneof_index"] = SimpleItoa(descriptor_->oneof_decl(i)->index());
+ vars["inline"] = is_inline ? "inline " : "";
+ printer->Print(
+ vars,
+ "$inline$"
+ "$class_name$::$camel_oneof_name$Case $class_name$::"
+ "$oneof_name$_case() const {\n"
+ " return $class_name$::$camel_oneof_name$Case("
+ "_oneof_case_[$oneof_index$]);\n"
+ "}\n");
+ }
+}
+
+void MessageGenerator::
+GenerateDescriptorDeclarations(io::Printer* printer) {
+ if (!IsMapEntryMessage(descriptor_)) {
+ printer->Print(
+ "const ::google::protobuf::Descriptor* $name$_descriptor_ = NULL;\n"
+ "const ::google::protobuf::internal::GeneratedMessageReflection*\n"
+ " $name$_reflection_ = NULL;\n",
+ "name", classname_);
+ } else {
+ printer->Print(
+ "const ::google::protobuf::Descriptor* $name$_descriptor_ = NULL;\n",
+ "name", classname_);
+ }
+
+ // Generate oneof default instance for reflection usage.
+ if (descriptor_->oneof_decl_count() > 0) {
+ printer->Print("struct $name$OneofInstance {\n",
+ "name", classname_);
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(" ");
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE ||
+ (field->cpp_type() == FieldDescriptor::CPPTYPE_STRING &&
+ EffectiveStringCType(field) != FieldOptions::STRING)) {
+ printer->Print("const ");
+ }
+ field_generators_.get(field).GeneratePrivateMembers(printer);
+ }
+ }
+
+ printer->Print("}* $name$_default_oneof_instance_ = NULL;\n",
+ "name", classname_);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ nested_generators_[i]->GenerateDescriptorDeclarations(printer);
+ }
+
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ printer->Print(
+ "const ::google::protobuf::EnumDescriptor* $name$_descriptor_ = NULL;\n",
+ "name", ClassName(descriptor_->enum_type(i), false));
+ }
+}
+
+void MessageGenerator::
+GenerateDescriptorInitializer(io::Printer* printer, int index) {
+ // TODO(kenton): Passing the index to this method is redundant; just use
+ // descriptor_->index() instead.
+ map<string, string> vars;
+ vars["classname"] = classname_;
+ vars["index"] = SimpleItoa(index);
+
+ // Obtain the descriptor from the parent's descriptor.
+ if (descriptor_->containing_type() == NULL) {
+ printer->Print(vars,
+ "$classname$_descriptor_ = file->message_type($index$);\n");
+ } else {
+ vars["parent"] = ClassName(descriptor_->containing_type(), false);
+ printer->Print(vars,
+ "$classname$_descriptor_ = "
+ "$parent$_descriptor_->nested_type($index$);\n");
+ }
+
+ if (IsMapEntryMessage(descriptor_)) return;
+
+ // Generate the offsets.
+ GenerateOffsets(printer);
+
+ const bool pass_pool_and_factory = false;
+ vars["fn"] = pass_pool_and_factory ?
+ "new ::google::protobuf::internal::GeneratedMessageReflection" :
+ "::google::protobuf::internal::GeneratedMessageReflection"
+ "::NewGeneratedMessageReflection";
+ // Construct the reflection object.
+ printer->Print(vars,
+ "$classname$_reflection_ =\n"
+ " $fn$(\n"
+ " $classname$_descriptor_,\n"
+ " $classname$::default_instance_,\n"
+ " $classname$_offsets_,\n");
+ if (!HasFieldPresence(descriptor_->file())) {
+ // If we don't have field presence, then _has_bits_ does not exist.
+ printer->Print(vars,
+ " -1,\n");
+ } else {
+ printer->Print(vars,
+ " GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET($classname$, _has_bits_[0]),\n");
+ }
+
+ // Unknown field offset: either points to the unknown field set if embedded
+ // directly, or indicates that the unknown field set is stored as part of the
+ // internal metadata if not.
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(vars,
+ " -1,\n");
+ } else {
+ printer->Print(vars,
+ " GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET("
+ "$classname$, _unknown_fields_),\n");
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(vars,
+ " GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET("
+ "$classname$, _extensions_),\n");
+ } else {
+ // No extensions.
+ printer->Print(vars,
+ " -1,\n");
+ }
+
+ if (descriptor_->oneof_decl_count() > 0) {
+ printer->Print(vars,
+ " $classname$_default_oneof_instance_,\n"
+ " GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET("
+ "$classname$, _oneof_case_[0]),\n");
+ }
+
+ if (pass_pool_and_factory) {
+ printer->Print(
+ " ::google::protobuf::DescriptorPool::generated_pool(),\n");
+ printer->Print(vars,
+ " ::google::protobuf::MessageFactory::generated_factory(),\n");
+ }
+
+ printer->Print(vars,
+ " sizeof($classname$),\n");
+
+ // Arena offset: either an offset to the metadata struct that contains the
+ // arena pointer and unknown field set (in a space-efficient way) if we use
+ // that implementation strategy, or an offset directly to the arena pointer if
+ // not (because e.g. we don't have an unknown field set).
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(vars,
+ " GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET("
+ "$classname$, _internal_metadata_),\n");
+ } else {
+ printer->Print(vars,
+ " GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET("
+ "$classname$, _arena_),\n");
+ }
+
+ // is_default_instance_ offset.
+ if (HasFieldPresence(descriptor_->file())) {
+ printer->Print(vars,
+ " -1);\n");
+ } else {
+ printer->Print(vars,
+ " GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET("
+ "$classname$, _is_default_instance_));\n");
+ }
+
+ // Handle nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ nested_generators_[i]->GenerateDescriptorInitializer(printer, i);
+ }
+
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateDescriptorInitializer(printer, i);
+ }
+}
+
+void MessageGenerator::
+GenerateTypeRegistrations(io::Printer* printer) {
+ // Register this message type with the message factory.
+ if (!IsMapEntryMessage(descriptor_)) {
+ printer->Print(
+ "::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(\n"
+ " $classname$_descriptor_, &$classname$::default_instance());\n",
+ "classname", classname_);
+ }
+ else {
+ map<string, string> vars;
+ CollectMapInfo(descriptor_, &vars);
+ vars["classname"] = classname_;
+
+ const FieldDescriptor* val = descriptor_->FindFieldByName("value");
+ if (descriptor_->file()->syntax() == FileDescriptor::SYNTAX_PROTO2 &&
+ val->type() == FieldDescriptor::TYPE_ENUM) {
+ const EnumValueDescriptor* default_value = val->default_value_enum();
+ vars["default_enum_value"] = Int32ToString(default_value->number());
+ } else {
+ vars["default_enum_value"] = "0";
+ }
+
+ printer->Print(vars,
+ "::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(\n"
+ " $classname$_descriptor_,\n"
+ " ::google::protobuf::internal::MapEntry<\n"
+ " $key$,\n"
+ " $val$,\n"
+ " $key_wire_type$,\n"
+ " $val_wire_type$,\n"
+ " $default_enum_value$>::CreateDefaultInstance(\n"
+ " $classname$_descriptor_));\n");
+ }
+
+ // Handle nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ nested_generators_[i]->GenerateTypeRegistrations(printer);
+ }
+}
+
+void MessageGenerator::
+GenerateDefaultInstanceAllocator(io::Printer* printer) {
+ // Construct the default instances of all fields, as they will be used
+ // when creating the default instance of the entire message.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateDefaultInstanceAllocator(printer);
+ }
+
+ if (IsMapEntryMessage(descriptor_)) return;
+
+ // Construct the default instance. We can't call InitAsDefaultInstance() yet
+ // because we need to make sure all default instances that this one might
+ // depend on are constructed first.
+ printer->Print(
+ "$classname$::default_instance_ = new $classname$();\n",
+ "classname", classname_);
+
+ if ((descriptor_->oneof_decl_count() > 0) &&
+ HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(
+ "$classname$_default_oneof_instance_ = new $classname$OneofInstance();\n",
+ "classname", classname_);
+ }
+
+ // Handle nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ nested_generators_[i]->GenerateDefaultInstanceAllocator(printer);
+ }
+
+}
+
+void MessageGenerator::
+GenerateDefaultInstanceInitializer(io::Printer* printer) {
+ printer->Print(
+ "$classname$::default_instance_->InitAsDefaultInstance();\n",
+ "classname", classname_);
+
+ // Register extensions.
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ extension_generators_[i]->GenerateRegistration(printer);
+ }
+
+ // Handle nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // map entry message doesn't need to initialize default instance manually.
+ // Since map entry message cannot be a top level class, we just need to
+ // avoid calling DefaultInstanceInitializer here.
+ if (IsMapEntryMessage(descriptor_->nested_type(i))) continue;
+ nested_generators_[i]->GenerateDefaultInstanceInitializer(printer);
+ }
+}
+
+void MessageGenerator::
+GenerateShutdownCode(io::Printer* printer) {
+ printer->Print(
+ "delete $classname$::default_instance_;\n",
+ "classname", classname_);
+
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ if (descriptor_->oneof_decl_count() > 0) {
+ printer->Print(
+ "delete $classname$_default_oneof_instance_;\n",
+ "classname", classname_);
+ }
+ printer->Print(
+ "delete $classname$_reflection_;\n",
+ "classname", classname_);
+ }
+
+ // Handle default instances of fields.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateShutdownCode(printer);
+ }
+
+ // Handle nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ if (IsMapEntryMessage(descriptor_->nested_type(i))) continue;
+ nested_generators_[i]->GenerateShutdownCode(printer);
+ }
+}
+
+void MessageGenerator::
+GenerateClassMethods(io::Printer* printer) {
+ // mutable_unknown_fields wrapper function for LazyStringOutputStream
+ // callback.
+ if (PreserveUnknownFields(descriptor_) &&
+ !UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "static ::std::string* MutableUnknownFieldsFor$classname$(\n"
+ " $classname$* ptr) {\n"
+ " return ptr->mutable_unknown_fields();\n"
+ "}\n"
+ "\n",
+ "classname", classname_);
+ }
+ if (IsAnyMessage(descriptor_)) {
+ printer->Print(
+ "void $classname$::PackFrom(const ::google::protobuf::Message& message) {\n"
+ " _any_metadata_.PackFrom(message);\n"
+ "}\n"
+ "\n"
+ "void $classname$::PackFrom(const ::google::protobuf::Message& message,\n"
+ " const ::std::string& type_url_prefix) {\n"
+ " _any_metadata_.PackFrom(message, type_url_prefix);\n"
+ "}\n"
+ "\n"
+ "bool $classname$::UnpackTo(::google::protobuf::Message* message) const {\n"
+ " return _any_metadata_.UnpackTo(message);\n"
+ "}\n"
+ "\n",
+ "classname", classname_);
+ }
+
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ enum_generators_[i]->GenerateMethods(printer);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // map entry message doesn't need class methods. Since map entry message
+ // cannot be a top level class, we just need to avoid calling
+ // GenerateClassMethods here.
+ if (IsMapEntryMessage(descriptor_->nested_type(i))) continue;
+ nested_generators_[i]->GenerateClassMethods(printer);
+ printer->Print("\n");
+ printer->Print(kThinSeparator);
+ printer->Print("\n");
+ }
+
+ // Generate non-inline field definitions.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateNonInlineAccessorDefinitions(printer);
+ }
+
+ // Generate field number constants.
+ printer->Print("#if !defined(_MSC_VER) || _MSC_VER >= 1900\n");
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor *field = descriptor_->field(i);
+ printer->Print(
+ "const int $classname$::$constant_name$;\n",
+ "classname", ClassName(FieldScope(field), false),
+ "constant_name", FieldConstantName(field));
+ }
+ printer->Print(
+ "#endif // !defined(_MSC_VER) || _MSC_VER >= 1900\n"
+ "\n");
+
+ // Define extension identifiers.
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ extension_generators_[i]->GenerateDefinition(printer);
+ }
+
+ GenerateStructors(printer);
+ printer->Print("\n");
+
+ if (descriptor_->oneof_decl_count() > 0) {
+ GenerateOneofClear(printer);
+ printer->Print("\n");
+ }
+
+ if (HasGeneratedMethods(descriptor_->file(), options_)) {
+ GenerateClear(printer);
+ printer->Print("\n");
+
+ GenerateMergeFromCodedStream(printer);
+ printer->Print("\n");
+
+ GenerateSerializeWithCachedSizes(printer);
+ printer->Print("\n");
+
+ if (HasFastArraySerialization(descriptor_->file(), options_)) {
+ GenerateSerializeWithCachedSizesToArray(printer);
+ printer->Print("\n");
+ }
+
+ GenerateByteSize(printer);
+ printer->Print("\n");
+
+ GenerateMergeFrom(printer);
+ printer->Print("\n");
+
+ GenerateCopyFrom(printer);
+ printer->Print("\n");
+
+ GenerateIsInitialized(printer);
+ printer->Print("\n");
+ }
+
+ GenerateSwap(printer);
+ printer->Print("\n");
+
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ printer->Print(
+ "::google::protobuf::Metadata $classname$::GetMetadata() const {\n"
+ " protobuf_AssignDescriptorsOnce();\n"
+ " ::google::protobuf::Metadata metadata;\n"
+ " metadata.descriptor = $classname$_descriptor_;\n"
+ " metadata.reflection = $classname$_reflection_;\n"
+ " return metadata;\n"
+ "}\n"
+ "\n",
+ "classname", classname_);
+ } else {
+ printer->Print(
+ "::std::string $classname$::GetTypeName() const {\n"
+ " return \"$type_name$\";\n"
+ "}\n"
+ "\n",
+ "classname", classname_,
+ "type_name", descriptor_->full_name());
+ }
+
+}
+
+void MessageGenerator::
+GenerateOffsets(io::Printer* printer) {
+ printer->Print("static const int $classname$_offsets_[$field_count$] = {\n",
+ "classname", classname_, "field_count",
+ SimpleItoa(std::max(1, descriptor_->field_count() +
+ descriptor_->oneof_decl_count())));
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (field->containing_oneof()) {
+ printer->Print(
+ "PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET("
+ "$classname$_default_oneof_instance_, $name$_),\n",
+ "classname", classname_,
+ "name", FieldName(field));
+ } else {
+ printer->Print(
+ "GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET($classname$, "
+ "$name$_),\n",
+ "classname", classname_,
+ "name", FieldName(field));
+ }
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ const OneofDescriptor* oneof = descriptor_->oneof_decl(i);
+ printer->Print(
+ "GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET($classname$, $name$_),\n",
+ "classname", classname_,
+ "name", oneof->name());
+ }
+
+ printer->Outdent();
+ printer->Print("};\n");
+}
+
+void MessageGenerator::
+GenerateSharedConstructorCode(io::Printer* printer) {
+ printer->Print(
+ "void $classname$::SharedCtor() {\n",
+ "classname", classname_);
+ printer->Indent();
+
+ if (!HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ " _is_default_instance_ = false;\n");
+ }
+
+ printer->Print(StrCat(
+ uses_string_ ? "::google::protobuf::internal::GetEmptyString();\n" : "",
+ "_cached_size_ = 0;\n").c_str());
+
+ if (PreserveUnknownFields(descriptor_) &&
+ !UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "_unknown_fields_.UnsafeSetDefault(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited());\n");
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateConstructorCode(printer);
+ }
+ }
+
+ if (HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ "::memset(_has_bits_, 0, sizeof(_has_bits_));\n");
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "clear_has_$oneof_name$();\n",
+ "oneof_name", descriptor_->oneof_decl(i)->name());
+ }
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+void MessageGenerator::
+GenerateSharedDestructorCode(io::Printer* printer) {
+ printer->Print(
+ "void $classname$::SharedDtor() {\n",
+ "classname", classname_);
+ printer->Indent();
+ if (SupportsArenas(descriptor_)) {
+ // Do nothing when the message is allocated in an arena.
+ printer->Print(
+ "if (GetArenaNoVirtual() != NULL) {\n"
+ " return;\n"
+ "}\n"
+ "\n");
+ }
+
+ // Write the desctructor for _unknown_fields_ in lite runtime.
+ if (PreserveUnknownFields(descriptor_) &&
+ !UseUnknownFieldSet(descriptor_->file(), options_)) {
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(
+ "_unknown_fields_.Destroy(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited(),\n"
+ " GetArenaNoVirtual());\n");
+ } else {
+ printer->Print(
+ "_unknown_fields_.DestroyNoArena(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited());\n");
+ }
+ }
+
+ // Write the destructors for each field except oneof members.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateDestructorCode(printer);
+ }
+ }
+
+ // Generate code to destruct oneofs. Clearing should do the work.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "if (has_$oneof_name$()) {\n"
+ " clear_$oneof_name$();\n"
+ "}\n",
+ "oneof_name", descriptor_->oneof_decl(i)->name());
+ }
+
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ "if (this != default_instance_) {\n",
+ // Without.
+ "if (this != &default_instance()) {\n");
+
+ // We need to delete all embedded messages.
+ // TODO(kenton): If we make unset messages point at default instances
+ // instead of NULL, then it would make sense to move this code into
+ // MessageFieldGenerator::GenerateDestructorCode().
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ if (!field->is_repeated() &&
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Skip oneof members
+ if (!field->containing_oneof()) {
+ printer->Print(
+ " delete $name$_;\n",
+ "name", FieldName(field));
+ }
+ }
+ }
+
+ printer->Outdent();
+ printer->Print(
+ " }\n"
+ "}\n"
+ "\n");
+}
+
+void MessageGenerator::
+GenerateArenaDestructorCode(io::Printer* printer) {
+ // Generate the ArenaDtor() method. Track whether any fields actually produced
+ // code that needs to be called.
+ printer->Print(
+ "void $classname$::ArenaDtor(void* object) {\n",
+ "classname", classname_);
+ printer->Indent();
+
+ // This code is placed inside a static method, rather than an ordinary one,
+ // since that simplifies Arena's destructor list (ordinary function pointers
+ // rather than member function pointers). _this is the object being
+ // destructed.
+ printer->Print(
+ "$classname$* _this = reinterpret_cast< $classname$* >(object);\n"
+ // avoid an "unused variable" warning in case no fields have dtor code.
+ "(void)_this;\n",
+ "classname", classname_);
+
+ bool need_registration = false;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (field_generators_.get(descriptor_->field(i))
+ .GenerateArenaDestructorCode(printer)) {
+ need_registration = true;
+ }
+ }
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+
+ if (need_registration) {
+ printer->Print(
+ "inline void $classname$::RegisterArenaDtor(::google::protobuf::Arena* arena) {\n"
+ " if (arena != NULL) {\n"
+ " arena->OwnCustomDestructor(this, &$classname$::ArenaDtor);\n"
+ " }\n"
+ "}\n",
+ "classname", classname_);
+ } else {
+ printer->Print(
+ "void $classname$::RegisterArenaDtor(::google::protobuf::Arena* arena) {\n"
+ "}\n",
+ "classname", classname_);
+ }
+}
+
+void MessageGenerator::
+GenerateStructors(io::Printer* printer) {
+ string superclass;
+ if (use_dependent_base_) {
+ superclass =
+ DependentBaseClassTemplateName(descriptor_) + "<" + classname_ + ">";
+ } else {
+ superclass = SuperClassName(descriptor_, options_);
+ }
+ string initializer_with_arena = superclass + "()";
+
+ if (descriptor_->extension_range_count() > 0) {
+ initializer_with_arena += ",\n _extensions_(arena)";
+ }
+
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ initializer_with_arena += ",\n _internal_metadata_(arena)";
+ } else {
+ initializer_with_arena += ",\n _arena_ptr_(arena)";
+ }
+
+ // Initialize member variables with arena constructor.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ bool has_arena_constructor = descriptor_->field(i)->is_repeated();
+ if (has_arena_constructor) {
+ initializer_with_arena += string(",\n ") +
+ FieldName(descriptor_->field(i)) + string("_(arena)");
+ }
+ }
+
+ if (IsAnyMessage(descriptor_)) {
+ initializer_with_arena += ",\n _any_metadata_(&type_url, &value_)";
+ }
+
+ string initializer_null;
+ initializer_null = (UseUnknownFieldSet(descriptor_->file(), options_) ?
+ ", _internal_metadata_(NULL)" : ", _arena_ptr_(NULL)");
+ if (IsAnyMessage(descriptor_)) {
+ initializer_null += ", _any_metadata_(&type_url_, &value_)";
+ }
+
+ printer->Print(
+ "$classname$::$classname$()\n"
+ " : $superclass$()$initializer$ {\n"
+ " SharedCtor();\n"
+ " // @@protoc_insertion_point(constructor:$full_name$)\n"
+ "}\n",
+ "classname", classname_,
+ "superclass", superclass,
+ "full_name", descriptor_->full_name(),
+ "initializer", initializer_null);
+
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(
+ "\n"
+ "$classname$::$classname$(::google::protobuf::Arena* arena)\n"
+ " : $initializer$ {\n"
+ " SharedCtor();\n"
+ " RegisterArenaDtor(arena);\n"
+ " // @@protoc_insertion_point(arena_constructor:$full_name$)\n"
+ "}\n",
+ "initializer", initializer_with_arena,
+ "classname", classname_,
+ "superclass", superclass,
+ "full_name", descriptor_->full_name());
+ }
+
+ printer->Print(
+ "\n"
+ "void $classname$::InitAsDefaultInstance() {\n",
+ "classname", classname_);
+
+ if (!HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ " _is_default_instance_ = true;\n");
+ }
+
+ // The default instance needs all of its embedded message pointers
+ // cross-linked to other default instances. We can't do this initialization
+ // in the constructor because some other default instances may not have been
+ // constructed yet at that time.
+ // TODO(kenton): Maybe all message fields (even for non-default messages)
+ // should be initialized to point at default instances rather than NULL?
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ if (!field->is_repeated() &&
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ (field->containing_oneof() == NULL ||
+ HasDescriptorMethods(descriptor_->file(), options_))) {
+ string name;
+ if (field->containing_oneof()) {
+ name = classname_ + "_default_oneof_instance_->";
+ }
+ name += FieldName(field);
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ " $name$_ = const_cast< $type$*>(&$type$::default_instance());\n",
+ // Without.
+ " $name$_ = const_cast< $type$*>(\n"
+ " $type$::internal_default_instance());\n",
+ // Vars.
+ "name", name, "type", FieldMessageTypeName(field));
+ } else if (field->containing_oneof() &&
+ HasDescriptorMethods(descriptor_->file(), options_)) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateConstructorCode(printer);
+ }
+ }
+ printer->Print(
+ "}\n"
+ "\n");
+
+ // Generate the copy constructor.
+ printer->Print(
+ "$classname$::$classname$(const $classname$& from)\n"
+ " : $superclass$()",
+ "classname", classname_,
+ "superclass", superclass,
+ "full_name", descriptor_->full_name());
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ ",\n _internal_metadata_(NULL)");
+ } else if (!UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(",\n _arena_ptr_(NULL)");
+ }
+ if (IsAnyMessage(descriptor_)) {
+ printer->Print(",\n _any_metadata_(&type_url_, &value_)");
+ }
+ printer->Print(" {\n");
+ printer->Print(
+ " SharedCtor();\n"
+ " MergeFrom(from);\n"
+ " // @@protoc_insertion_point(copy_constructor:$full_name$)\n"
+ "}\n"
+ "\n",
+ "classname", classname_,
+ "superclass", superclass,
+ "full_name", descriptor_->full_name());
+
+ // Generate the shared constructor code.
+ GenerateSharedConstructorCode(printer);
+
+ // Generate the destructor.
+ printer->Print(
+ "$classname$::~$classname$() {\n"
+ " // @@protoc_insertion_point(destructor:$full_name$)\n"
+ " SharedDtor();\n"
+ "}\n"
+ "\n",
+ "classname", classname_,
+ "full_name", descriptor_->full_name());
+
+ // Generate the shared destructor code.
+ GenerateSharedDestructorCode(printer);
+
+ // Generate the arena-specific destructor code.
+ if (SupportsArenas(descriptor_)) {
+ GenerateArenaDestructorCode(printer);
+ }
+
+ // Generate SetCachedSize.
+ printer->Print(
+ "void $classname$::SetCachedSize(int size) const {\n"
+ " GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();\n"
+ " _cached_size_ = size;\n"
+ " GOOGLE_SAFE_CONCURRENT_WRITES_END();\n"
+ "}\n",
+ "classname", classname_);
+
+ // Only generate this member if it's not disabled.
+ if (HasDescriptorMethods(descriptor_->file(), options_) &&
+ !descriptor_->options().no_standard_descriptor_accessor()) {
+ printer->Print(
+ "const ::google::protobuf::Descriptor* $classname$::descriptor() {\n"
+ " protobuf_AssignDescriptorsOnce();\n"
+ " return $classname$_descriptor_;\n"
+ "}\n"
+ "\n",
+ "classname", classname_,
+ "adddescriptorsname",
+ GlobalAddDescriptorsName(descriptor_->file()->name()));
+ }
+
+ printer->Print(
+ "const $classname$& $classname$::default_instance() {\n",
+ "classname", classname_);
+
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ " if (default_instance_ == NULL) $adddescriptorsname$();\n",
+ // Without.
+ " $adddescriptorsname$();\n",
+ // Vars.
+ "adddescriptorsname",
+ GlobalAddDescriptorsName(descriptor_->file()->name()));
+
+ printer->Print(
+ " return *default_instance_;\n"
+ "}\n"
+ "\n"
+ "$classname$* $classname$::default_instance_ = NULL;\n"
+ "\n",
+ "classname", classname_);
+
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(
+ "$classname$* $classname$::New(::google::protobuf::Arena* arena) const {\n"
+ " return ::google::protobuf::Arena::CreateMessage<$classname$>(arena);\n"
+ "}\n",
+ "classname", classname_);
+ } else {
+ printer->Print(
+ "$classname$* $classname$::New(::google::protobuf::Arena* arena) const {\n"
+ " $classname$* n = new $classname$;\n"
+ " if (arena != NULL) {\n"
+ " arena->Own(n);\n"
+ " }\n"
+ " return n;\n"
+ "}\n",
+ "classname", classname_);
+ }
+
+}
+
+// Return the number of bits set in n, a non-negative integer.
+static int popcnt(uint32 n) {
+ int result = 0;
+ while (n != 0) {
+ result += (n & 1);
+ n = n / 2;
+ }
+ return result;
+}
+
+void MessageGenerator::
+GenerateClear(io::Printer* printer) {
+ printer->Print(
+ "void $classname$::Clear() {\n"
+ "// @@protoc_insertion_point(message_clear_start:$full_name$)\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ printer->Indent();
+
+ // Step 1: Extensions
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print("_extensions_.Clear();\n");
+ }
+
+ // Step 2: Everything but extensions, repeateds, unions.
+ // These are handled in chunks of 8. The first chunk is
+ // the non-extensions-non-repeateds-non-unions in
+ // descriptor_->field(0), descriptor_->field(1), ... descriptor_->field(7),
+ // and the second chunk is the same for
+ // descriptor_->field(8), descriptor_->field(9), ... descriptor_->field(15),
+ // etc.
+ set<int> step2_indices;
+ hash_map<string, int> fieldname_to_chunk;
+ hash_map<int, string> memsets_for_chunk;
+ hash_map<int, int> memset_field_count_for_chunk;
+ hash_set<string> handled; // fields that appear anywhere in memsets_for_chunk
+ hash_map<int, uint32> fields_mask_for_chunk;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (!field->is_repeated() && !field->containing_oneof()) {
+ step2_indices.insert(i);
+ int chunk = i / 8;
+ fieldname_to_chunk[FieldName(field)] = chunk;
+ fields_mask_for_chunk[chunk] |= static_cast<uint32>(1) << (i % 32);
+ }
+ }
+
+ // Step 2a: Greedily seek runs of fields that can be cleared by memset-to-0.
+ // The generated code uses two macros to help it clear runs of fields:
+ // ZR_HELPER_(f1) - ZR_HELPER_(f0) computes the difference, in bytes, of the
+ // positions of two fields in the Message.
+ // ZR_ zeroes a non-empty range of fields via memset.
+ const char* macros =
+ "#if defined(__clang__)\n"
+ "#define ZR_HELPER_(f) \\\n"
+ " _Pragma(\"clang diagnostic push\") \\\n"
+ " _Pragma(\"clang diagnostic ignored \\\"-Winvalid-offsetof\\\"\") \\\n"
+ " __builtin_offsetof($classname$, f) \\\n"
+ " _Pragma(\"clang diagnostic pop\")\n"
+ "#else\n"
+ "#define ZR_HELPER_(f) reinterpret_cast<char*>(\\\n"
+ " &reinterpret_cast<$classname$*>(16)->f)\n"
+ "#endif\n\n"
+ "#define ZR_(first, last) do {\\\n"
+ " ::memset(&first, 0,\\\n"
+ " ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\\\n"
+ "} while (0)\n\n";
+ for (int i = 0; i < runs_of_fields_.size(); i++) {
+ const vector<string>& run = runs_of_fields_[i];
+ if (run.size() < 2) continue;
+ const string& first_field_name = run[0];
+ const string& last_field_name = run.back();
+ int chunk = fieldname_to_chunk[run[0]];
+ memsets_for_chunk[chunk].append(
+ "ZR_(" + first_field_name + "_, " + last_field_name + "_);\n");
+ for (int j = 0; j < run.size(); j++) {
+ GOOGLE_DCHECK_EQ(chunk, fieldname_to_chunk[run[j]]);
+ handled.insert(run[j]);
+ }
+ memset_field_count_for_chunk[chunk] += run.size();
+ }
+ const bool macros_are_needed = handled.size() > 0;
+ if (macros_are_needed) {
+ printer->Outdent();
+ printer->Print(macros,
+ "classname", classname_);
+ printer->Indent();
+ }
+ // Step 2b: Finish step 2, ignoring fields handled in step 2a.
+ int last_index = -1;
+ bool chunk_block_in_progress = false;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (step2_indices.count(i) == 0) continue;
+ const FieldDescriptor* field = descriptor_->field(i);
+ const string fieldname = FieldName(field);
+ if (i / 8 != last_index / 8 || last_index < 0) {
+ // End previous chunk, if there was one.
+ if (chunk_block_in_progress) {
+ printer->Outdent();
+ printer->Print("}\n");
+ chunk_block_in_progress = false;
+ }
+ // Start chunk.
+ const string& memsets = memsets_for_chunk[i / 8];
+ uint32 mask = fields_mask_for_chunk[i / 8];
+ int count = popcnt(mask);
+ GOOGLE_DCHECK_GE(count, 1);
+ if (count == 1 ||
+ (count <= 4 && count == memset_field_count_for_chunk[i / 8])) {
+ // No "if" here because the chunk is trivial.
+ } else {
+ if (HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ "if (_has_bits_[$index$ / 32] & $mask$u) {\n",
+ "index", SimpleItoa(i / 8 * 8),
+ "mask", SimpleItoa(mask));
+ printer->Indent();
+ chunk_block_in_progress = true;
+ }
+ }
+ printer->Print(memsets.c_str());
+ }
+ last_index = i;
+ if (handled.count(fieldname) > 0) continue;
+
+ // It's faster to just overwrite primitive types, but we should
+ // only clear strings and messages if they were set.
+ // TODO(kenton): Let the CppFieldGenerator decide this somehow.
+ bool should_check_bit =
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE ||
+ field->cpp_type() == FieldDescriptor::CPPTYPE_STRING;
+
+ bool have_enclosing_if = false;
+ if (should_check_bit &&
+ // If no field presence, then always clear strings/messages as well.
+ HasFieldPresence(descriptor_->file())) {
+ printer->Print("if (has_$name$()) {\n", "name", fieldname);
+ printer->Indent();
+ have_enclosing_if = true;
+ }
+
+ if (use_dependent_base_ && IsFieldDependent(field)) {
+ printer->Print("clear_$name$();\n", "name", fieldname);
+ } else {
+ field_generators_.get(field).GenerateClearingCode(printer);
+ }
+
+ if (have_enclosing_if) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ }
+
+ if (chunk_block_in_progress) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ if (macros_are_needed) {
+ printer->Outdent();
+ printer->Print("\n#undef ZR_HELPER_\n#undef ZR_\n\n");
+ printer->Indent();
+ }
+
+ // Step 3: Repeated fields don't use _has_bits_; emit code to clear them here.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ if (field->is_repeated()) {
+ if (use_dependent_base_ && IsFieldDependent(field)) {
+ printer->Print("clear_$name$();\n", "name", FieldName(field));
+ } else {
+ field_generators_.get(field).GenerateClearingCode(printer);
+ }
+ }
+ }
+
+ // Step 4: Unions.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "clear_$oneof_name$();\n",
+ "oneof_name", descriptor_->oneof_decl(i)->name());
+ }
+
+ if (HasFieldPresence(descriptor_->file())) {
+ // Step 5: Everything else.
+ printer->Print(
+ "::memset(_has_bits_, 0, sizeof(_has_bits_));\n");
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "if (_internal_metadata_.have_unknown_fields()) {\n"
+ " mutable_unknown_fields()->Clear();\n"
+ "}\n");
+ } else {
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(
+ "_unknown_fields_.ClearToEmpty(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited(),\n"
+ " GetArenaNoVirtual());\n");
+ } else {
+ printer->Print(
+ "_unknown_fields_.ClearToEmptyNoArena(\n"
+ " &::google::protobuf::internal::GetEmptyStringAlreadyInited());\n");
+ }
+ }
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MessageGenerator::
+GenerateOneofClear(io::Printer* printer) {
+ // Generated function clears the active field and union case (e.g. foo_case_).
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ map<string, string> oneof_vars;
+ oneof_vars["classname"] = classname_;
+ oneof_vars["oneofname"] = descriptor_->oneof_decl(i)->name();
+ oneof_vars["full_name"] = descriptor_->full_name();
+ string message_class;
+
+ printer->Print(oneof_vars,
+ "void $classname$::clear_$oneofname$() {\n"
+ "// @@protoc_insertion_point(one_of_clear_start:"
+ "$full_name$)\n");
+ printer->Indent();
+ printer->Print(oneof_vars,
+ "switch($oneofname$_case()) {\n");
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "case k$field_name$: {\n",
+ "field_name", UnderscoresToCamelCase(field->name(), true));
+ printer->Indent();
+ // We clear only allocated objects in oneofs
+ if (!IsStringOrMessage(field)) {
+ printer->Print(
+ "// No need to clear\n");
+ } else {
+ field_generators_.get(field).GenerateClearingCode(printer);
+ }
+ printer->Print(
+ "break;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+ printer->Print(
+ "case $cap_oneof_name$_NOT_SET: {\n"
+ " break;\n"
+ "}\n",
+ "cap_oneof_name",
+ ToUpper(descriptor_->oneof_decl(i)->name()));
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "_oneof_case_[$oneof_index$] = $cap_oneof_name$_NOT_SET;\n",
+ "oneof_index", SimpleItoa(i),
+ "cap_oneof_name",
+ ToUpper(descriptor_->oneof_decl(i)->name()));
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+ }
+}
+
+void MessageGenerator::
+GenerateSwap(io::Printer* printer) {
+ if (SupportsArenas(descriptor_)) {
+ // Generate the Swap member function. This is a lightweight wrapper around
+ // UnsafeArenaSwap() / MergeFrom() with temporaries, depending on the memory
+ // ownership situation: swapping across arenas or between an arena and a
+ // heap requires copying.
+ printer->Print(
+ "void $classname$::Swap($classname$* other) {\n"
+ " if (other == this) return;\n"
+ " if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {\n"
+ " InternalSwap(other);\n"
+ " } else {\n"
+ " $classname$ temp;\n"
+ " temp.MergeFrom(*this);\n"
+ " CopyFrom(*other);\n"
+ " other->CopyFrom(temp);\n"
+ " }\n"
+ "}\n"
+ "void $classname$::UnsafeArenaSwap($classname$* other) {\n"
+ " if (other == this) return;\n"
+ " GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());\n"
+ " InternalSwap(other);\n"
+ "}\n",
+ "classname", classname_);
+ } else {
+ printer->Print(
+ "void $classname$::Swap($classname$* other) {\n"
+ " if (other == this) return;\n"
+ " InternalSwap(other);\n"
+ "}\n",
+ "classname", classname_);
+ }
+
+ // Generate the UnsafeArenaSwap member function.
+ printer->Print("void $classname$::InternalSwap($classname$* other) {\n",
+ "classname", classname_);
+ printer->Indent();
+
+ if (HasGeneratedMethods(descriptor_->file(), options_)) {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ field_generators_.get(field).GenerateSwappingCode(printer);
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "std::swap($oneof_name$_, other->$oneof_name$_);\n"
+ "std::swap(_oneof_case_[$i$], other->_oneof_case_[$i$]);\n",
+ "oneof_name", descriptor_->oneof_decl(i)->name(),
+ "i", SimpleItoa(i));
+ }
+
+ if (HasFieldPresence(descriptor_->file())) {
+ for (int i = 0; i < (descriptor_->field_count() + 31) / 32; ++i) {
+ printer->Print("std::swap(_has_bits_[$i$], other->_has_bits_[$i$]);\n",
+ "i", SimpleItoa(i));
+ }
+ }
+
+ // Ignore PreserveUnknownFields here - always swap internal_metadata as it
+ // may contain more than just unknown fields.
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "_internal_metadata_.Swap(&other->_internal_metadata_);\n");
+ } else {
+ printer->Print("_unknown_fields_.Swap(&other->_unknown_fields_);\n");
+ }
+
+ printer->Print("std::swap(_cached_size_, other->_cached_size_);\n");
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print("_extensions_.Swap(&other->_extensions_);\n");
+ }
+ } else {
+ printer->Print("GetReflection()->Swap(this, other);");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MessageGenerator::
+GenerateMergeFrom(io::Printer* printer) {
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ // Generate the generalized MergeFrom (aka that which takes in the Message
+ // base class as a parameter).
+ printer->Print(
+ "void $classname$::MergeFrom(const ::google::protobuf::Message& from) {\n"
+ "// @@protoc_insertion_point(generalized_merge_from_start:"
+ "$full_name$)\n"
+ " if (GOOGLE_PREDICT_FALSE(&from == this)) {\n"
+ " ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);\n"
+ " }\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ printer->Indent();
+
+ // Cast the message to the proper type. If we find that the message is
+ // *not* of the proper type, we can still call Merge via the reflection
+ // system, as the GOOGLE_CHECK above ensured that we have the same descriptor
+ // for each message.
+ printer->Print(
+ "const $classname$* source = \n"
+ " ::google::protobuf::internal::DynamicCastToGenerated<const $classname$>(\n"
+ " &from);\n"
+ "if (source == NULL) {\n"
+ "// @@protoc_insertion_point(generalized_merge_from_cast_fail:"
+ "$full_name$)\n"
+ " ::google::protobuf::internal::ReflectionOps::Merge(from, this);\n"
+ "} else {\n"
+ "// @@protoc_insertion_point(generalized_merge_from_cast_success:"
+ "$full_name$)\n"
+ " MergeFrom(*source);\n"
+ "}\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+ } else {
+ // Generate CheckTypeAndMergeFrom().
+ printer->Print(
+ "void $classname$::CheckTypeAndMergeFrom(\n"
+ " const ::google::protobuf::MessageLite& from) {\n"
+ " MergeFrom(*::google::protobuf::down_cast<const $classname$*>(&from));\n"
+ "}\n"
+ "\n",
+ "classname", classname_);
+ }
+
+ // Generate the class-specific MergeFrom, which avoids the GOOGLE_CHECK and cast.
+ printer->Print(
+ "void $classname$::MergeFrom(const $classname$& from) {\n"
+ "// @@protoc_insertion_point(class_specific_merge_from_start:"
+ "$full_name$)\n"
+ " if (GOOGLE_PREDICT_FALSE(&from == this)) {\n"
+ " ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);\n"
+ " }\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ printer->Indent();
+
+ // Merge Repeated fields. These fields do not require a
+ // check as we can simply iterate over them.
+ for (int i = 0; i < descriptor_->field_count(); ++i) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ if (field->is_repeated()) {
+ field_generators_.get(field).GenerateMergingCode(printer);
+ }
+ }
+
+ // Merge oneof fields. Oneof field requires oneof case check.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
+ printer->Print(
+ "switch (from.$oneofname$_case()) {\n",
+ "oneofname", descriptor_->oneof_decl(i)->name());
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "case k$field_name$: {\n",
+ "field_name", UnderscoresToCamelCase(field->name(), true));
+ printer->Indent();
+ field_generators_.get(field).GenerateMergingCode(printer);
+ printer->Print(
+ "break;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+ printer->Print(
+ "case $cap_oneof_name$_NOT_SET: {\n"
+ " break;\n"
+ "}\n",
+ "cap_oneof_name",
+ ToUpper(descriptor_->oneof_decl(i)->name()));
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+
+ // Merge Optional and Required fields (after a _has_bit check).
+ int last_index = -1;
+
+ for (int i = 0; i < descriptor_->field_count(); ++i) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ if (!field->is_repeated() && !field->containing_oneof()) {
+ if (HasFieldPresence(descriptor_->file())) {
+ // See above in GenerateClear for an explanation of this.
+ if (i / 8 != last_index / 8 || last_index < 0) {
+ if (last_index >= 0) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ printer->Print(
+ "if (from._has_bits_[$index$ / 32] & "
+ "(0xffu << ($index$ % 32))) {\n",
+ "index", SimpleItoa(field->index()));
+ printer->Indent();
+ }
+ }
+
+ last_index = i;
+
+ bool have_enclosing_if = false;
+ if (HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ "if (from.has_$name$()) {\n",
+ "name", FieldName(field));
+ printer->Indent();
+ have_enclosing_if = true;
+ } else {
+ // Merge semantics without true field presence: primitive fields are
+ // merged only if non-zero (numeric) or non-empty (string).
+ have_enclosing_if = EmitFieldNonDefaultCondition(
+ printer, "from.", field);
+ }
+
+ field_generators_.get(field).GenerateMergingCode(printer);
+
+ if (have_enclosing_if) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ }
+ }
+
+ if (HasFieldPresence(descriptor_->file()) &&
+ last_index >= 0) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print("_extensions_.MergeFrom(from._extensions_);\n");
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "if (from._internal_metadata_.have_unknown_fields()) {\n"
+ " mutable_unknown_fields()->MergeFrom(from.unknown_fields());\n"
+ "}\n");
+ } else {
+ printer->Print(
+ "if (!from.unknown_fields().empty()) {\n"
+ " mutable_unknown_fields()->append(from.unknown_fields());\n"
+ "}\n");
+ }
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MessageGenerator::
+GenerateCopyFrom(io::Printer* printer) {
+ if (HasDescriptorMethods(descriptor_->file(), options_)) {
+ // Generate the generalized CopyFrom (aka that which takes in the Message
+ // base class as a parameter).
+ printer->Print(
+ "void $classname$::CopyFrom(const ::google::protobuf::Message& from) {\n"
+ "// @@protoc_insertion_point(generalized_copy_from_start:"
+ "$full_name$)\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ printer->Indent();
+
+ printer->Print(
+ "if (&from == this) return;\n"
+ "Clear();\n"
+ "MergeFrom(from);\n");
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+ }
+
+ // Generate the class-specific CopyFrom.
+ printer->Print(
+ "void $classname$::CopyFrom(const $classname$& from) {\n"
+ "// @@protoc_insertion_point(class_specific_copy_from_start:"
+ "$full_name$)\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ printer->Indent();
+
+ printer->Print(
+ "if (&from == this) return;\n"
+ "Clear();\n"
+ "MergeFrom(from);\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MessageGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) {
+ if (descriptor_->options().message_set_wire_format()) {
+ // Special-case MessageSet.
+ printer->Print(
+ "bool $classname$::MergePartialFromCodedStream(\n"
+ " ::google::protobuf::io::CodedInputStream* input) {\n",
+ "classname", classname_);
+
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ " return _extensions_.ParseMessageSet(input, default_instance_,\n"
+ " mutable_unknown_fields());\n",
+ // Without.
+ " return _extensions_.ParseMessageSet(input, &default_instance(),\n"
+ " mutable_unknown_fields());\n",
+ // Vars.
+ "classname", classname_);
+
+ printer->Print(
+ "}\n");
+ return;
+ }
+
+ printer->Print(
+ "bool $classname$::MergePartialFromCodedStream(\n"
+ " ::google::protobuf::io::CodedInputStream* input) {\n"
+ "#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure\n"
+ " ::google::protobuf::uint32 tag;\n",
+ "classname", classname_);
+
+ if (PreserveUnknownFields(descriptor_) &&
+ !UseUnknownFieldSet(descriptor_->file(), options_)) {
+ // Use LazyStringOutputString to avoid initializing unknown fields string
+ // unless it is actually needed. For the same reason, disable eager refresh
+ // on the CodedOutputStream.
+ printer->Print(
+ " ::google::protobuf::io::LazyStringOutputStream unknown_fields_string(\n"
+ " ::google::protobuf::internal::NewPermanentCallback(\n"
+ " &MutableUnknownFieldsFor$classname$, this));\n"
+ " ::google::protobuf::io::CodedOutputStream unknown_fields_stream(\n"
+ " &unknown_fields_string, false);\n",
+ "classname", classname_);
+ }
+
+ printer->Print(
+ " // @@protoc_insertion_point(parse_start:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Indent();
+ printer->Print("for (;;) {\n");
+ printer->Indent();
+
+ google::protobuf::scoped_array<const FieldDescriptor * > ordered_fields(
+ SortFieldsByNumber(descriptor_));
+ uint32 maxtag = descriptor_->field_count() == 0 ? 0 :
+ WireFormat::MakeTag(ordered_fields[descriptor_->field_count() - 1]);
+ const int kCutoff0 = 127; // fits in 1-byte varint
+ const int kCutoff1 = (127 << 7) + 127; // fits in 2-byte varint
+ printer->Print("::std::pair< ::google::protobuf::uint32, bool> p = "
+ "input->ReadTagWithCutoff($max$);\n"
+ "tag = p.first;\n"
+ "if (!p.second) goto handle_unusual;\n",
+ "max", SimpleItoa(maxtag <= kCutoff0 ? kCutoff0 :
+ (maxtag <= kCutoff1 ? kCutoff1 :
+ maxtag)));
+ if (descriptor_->field_count() > 0) {
+ // We don't even want to print the switch() if we have no fields because
+ // MSVC dislikes switch() statements that contain only a default value.
+
+ // Note: If we just switched on the tag rather than the field number, we
+ // could avoid the need for the if() to check the wire type at the beginning
+ // of each case. However, this is actually a bit slower in practice as it
+ // creates a jump table that is 8x larger and sparser, and meanwhile the
+ // if()s are highly predictable.
+ printer->Print("switch (::google::protobuf::internal::WireFormatLite::"
+ "GetTagFieldNumber(tag)) {\n");
+
+ printer->Indent();
+
+ // Find repeated messages and groups now, to simplify what follows.
+ hash_set<int> fields_with_parse_loop;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = ordered_fields[i];
+ if (field->is_repeated() &&
+ (field->type() == FieldDescriptor::TYPE_MESSAGE ||
+ field->type() == FieldDescriptor::TYPE_GROUP)) {
+ fields_with_parse_loop.insert(i);
+ }
+ }
+
+ // need_label is true if we generated "goto parse_$name$" while handling the
+ // previous field.
+ bool need_label = false;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = ordered_fields[i];
+ const bool loops = fields_with_parse_loop.count(i) > 0;
+ const bool next_field_loops = fields_with_parse_loop.count(i + 1) > 0;
+
+ PrintFieldComment(printer, field);
+
+ printer->Print(
+ "case $number$: {\n",
+ "number", SimpleItoa(field->number()));
+ printer->Indent();
+ const FieldGenerator& field_generator = field_generators_.get(field);
+
+ // Emit code to parse the common, expected case.
+ printer->Print("if (tag == $commontag$) {\n",
+ "commontag", SimpleItoa(WireFormat::MakeTag(field)));
+
+ if (need_label ||
+ (field->is_repeated() && !field->is_packed() && !loops)) {
+ printer->Print(
+ " parse_$name$:\n",
+ "name", field->name());
+ }
+ if (loops) {
+ printer->Print(
+ " DO_(input->IncrementRecursionDepth());\n"
+ " parse_loop_$name$:\n",
+ "name", field->name());
+ }
+
+ printer->Indent();
+ if (field->is_packed()) {
+ field_generator.GenerateMergeFromCodedStreamWithPacking(printer);
+ } else {
+ field_generator.GenerateMergeFromCodedStream(printer);
+ }
+ printer->Outdent();
+
+ // Emit code to parse unexpectedly packed or unpacked values.
+ if (field->is_packed()) {
+ internal::WireFormatLite::WireType wiretype =
+ WireFormat::WireTypeForFieldType(field->type());
+ printer->Print("} else if (tag == $uncommontag$) {\n",
+ "uncommontag", SimpleItoa(
+ internal::WireFormatLite::MakeTag(
+ field->number(), wiretype)));
+ printer->Indent();
+ field_generator.GenerateMergeFromCodedStream(printer);
+ printer->Outdent();
+ } else if (field->is_packable() && !field->is_packed()) {
+ internal::WireFormatLite::WireType wiretype =
+ internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED;
+ printer->Print("} else if (tag == $uncommontag$) {\n",
+ "uncommontag", SimpleItoa(
+ internal::WireFormatLite::MakeTag(
+ field->number(), wiretype)));
+ printer->Indent();
+ field_generator.GenerateMergeFromCodedStreamWithPacking(printer);
+ printer->Outdent();
+ }
+
+ printer->Print(
+ "} else {\n"
+ " goto handle_unusual;\n"
+ "}\n");
+
+ // switch() is slow since it can't be predicted well. Insert some if()s
+ // here that attempt to predict the next tag.
+ // For non-packed repeated fields, expect the same tag again.
+ if (loops) {
+ printer->Print(
+ "if (input->ExpectTag($tag$)) goto parse_loop_$name$;\n",
+ "tag", SimpleItoa(WireFormat::MakeTag(field)),
+ "name", field->name());
+ } else if (field->is_repeated() && !field->is_packed()) {
+ printer->Print(
+ "if (input->ExpectTag($tag$)) goto parse_$name$;\n",
+ "tag", SimpleItoa(WireFormat::MakeTag(field)),
+ "name", field->name());
+ }
+
+ // Have we emitted "if (input->ExpectTag($next_tag$)) ..." yet?
+ bool emitted_goto_next_tag = false;
+
+ // For repeated messages/groups, we need to decrement recursion depth,
+ // unless the next tag is also for a repeated message/group.
+ if (loops) {
+ if (next_field_loops) {
+ const FieldDescriptor* next_field = ordered_fields[i + 1];
+ printer->Print(
+ "if (input->ExpectTag($next_tag$)) goto parse_loop_$next_name$;\n",
+ "next_tag", SimpleItoa(WireFormat::MakeTag(next_field)),
+ "next_name", next_field->name());
+ emitted_goto_next_tag = true;
+ }
+ printer->Print(
+ "input->UnsafeDecrementRecursionDepth();\n");
+ }
+
+ // If there are more fields, expect the next one.
+ need_label = false;
+ if (!emitted_goto_next_tag) {
+ if (i + 1 == descriptor_->field_count()) {
+ // Expect EOF.
+ // TODO(kenton): Expect group end-tag?
+ printer->Print(
+ "if (input->ExpectAtEnd()) goto success;\n");
+ } else {
+ const FieldDescriptor* next_field = ordered_fields[i + 1];
+ printer->Print(
+ "if (input->ExpectTag($next_tag$)) goto parse_$next_name$;\n",
+ "next_tag", SimpleItoa(WireFormat::MakeTag(next_field)),
+ "next_name", next_field->name());
+ need_label = true;
+ }
+ }
+
+ printer->Print(
+ "break;\n");
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+ }
+
+ printer->Print("default: {\n");
+ printer->Indent();
+ }
+
+ printer->Outdent();
+ printer->Print("handle_unusual:\n");
+ printer->Indent();
+ // If tag is 0 or an end-group tag then this must be the end of the message.
+ printer->Print(
+ "if (tag == 0 ||\n"
+ " ::google::protobuf::internal::WireFormatLite::GetTagWireType(tag) ==\n"
+ " ::google::protobuf::internal::WireFormatLite::WIRETYPE_END_GROUP) {\n"
+ " goto success;\n"
+ "}\n");
+
+ // Handle extension ranges.
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "if (");
+ for (int i = 0; i < descriptor_->extension_range_count(); i++) {
+ const Descriptor::ExtensionRange* range =
+ descriptor_->extension_range(i);
+ if (i > 0) printer->Print(" ||\n ");
+
+ uint32 start_tag = WireFormatLite::MakeTag(
+ range->start, static_cast<WireFormatLite::WireType>(0));
+ uint32 end_tag = WireFormatLite::MakeTag(
+ range->end, static_cast<WireFormatLite::WireType>(0));
+
+ if (range->end > FieldDescriptor::kMaxNumber) {
+ printer->Print(
+ "($start$u <= tag)",
+ "start", SimpleItoa(start_tag));
+ } else {
+ printer->Print(
+ "($start$u <= tag && tag < $end$u)",
+ "start", SimpleItoa(start_tag),
+ "end", SimpleItoa(end_tag));
+ }
+ }
+ printer->Print(") {\n");
+ if (PreserveUnknownFields(descriptor_)) {
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ " DO_(_extensions_.ParseField(tag, input, default_instance_,\n"
+ " mutable_unknown_fields()));\n",
+ // Without.
+ " DO_(_extensions_.ParseField(tag, input, &default_instance(),\n"
+ " mutable_unknown_fields()));\n");
+ } else {
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ " DO_(_extensions_.ParseField(tag, input, default_instance_,\n"
+ " &unknown_fields_stream));\n",
+ // Without.
+ " DO_(_extensions_.ParseField(tag, input, &default_instance(),\n"
+ " &unknown_fields_stream));\n");
+ }
+ } else {
+ PrintHandlingOptionalStaticInitializers(
+ descriptor_->file(), options_, printer,
+ // With static initializers.
+ " DO_(_extensions_.ParseField(tag, input, default_instance_);\n",
+ // Without.
+ " DO_(_extensions_.ParseField(tag, input, &default_instance());\n");
+ }
+ printer->Print(
+ " continue;\n"
+ "}\n");
+ }
+
+ // We really don't recognize this tag. Skip it.
+ if (PreserveUnknownFields(descriptor_)) {
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "DO_(::google::protobuf::internal::WireFormat::SkipField(\n"
+ " input, tag, mutable_unknown_fields()));\n");
+ } else {
+ printer->Print(
+ "DO_(::google::protobuf::internal::WireFormatLite::SkipField(\n"
+ " input, tag, &unknown_fields_stream));\n");
+ }
+ } else {
+ printer->Print(
+ "DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));\n");
+ }
+
+ if (descriptor_->field_count() > 0) {
+ printer->Print("break;\n");
+ printer->Outdent();
+ printer->Print("}\n"); // default:
+ printer->Outdent();
+ printer->Print("}\n"); // switch
+ }
+
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n" // for (;;)
+ "success:\n"
+ " // @@protoc_insertion_point(parse_success:$full_name$)\n"
+ " return true;\n"
+ "failure:\n"
+ " // @@protoc_insertion_point(parse_failure:$full_name$)\n"
+ " return false;\n"
+ "#undef DO_\n"
+ "}\n", "full_name", descriptor_->full_name());
+}
+
+void MessageGenerator::GenerateSerializeOneField(
+ io::Printer* printer, const FieldDescriptor* field, bool to_array) {
+ PrintFieldComment(printer, field);
+
+ bool have_enclosing_if = false;
+ if (!field->is_repeated() && HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ "if (has_$name$()) {\n",
+ "name", FieldName(field));
+ printer->Indent();
+ have_enclosing_if = true;
+ } else if (!HasFieldPresence(descriptor_->file())) {
+ have_enclosing_if = EmitFieldNonDefaultCondition(printer, "this->", field);
+ }
+
+ if (to_array) {
+ field_generators_.get(field).GenerateSerializeWithCachedSizesToArray(
+ printer);
+ } else {
+ field_generators_.get(field).GenerateSerializeWithCachedSizes(printer);
+ }
+
+ if (have_enclosing_if) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ printer->Print("\n");
+}
+
+void MessageGenerator::GenerateSerializeOneExtensionRange(
+ io::Printer* printer, const Descriptor::ExtensionRange* range,
+ bool to_array) {
+ map<string, string> vars;
+ vars["start"] = SimpleItoa(range->start);
+ vars["end"] = SimpleItoa(range->end);
+ printer->Print(vars,
+ "// Extension range [$start$, $end$)\n");
+ if (to_array) {
+ printer->Print(vars,
+ "target = _extensions_.InternalSerializeWithCachedSizesToArray(\n"
+ " $start$, $end$, false, target);\n\n");
+ } else {
+ printer->Print(vars,
+ "_extensions_.SerializeWithCachedSizes(\n"
+ " $start$, $end$, output);\n\n");
+ }
+}
+
+void MessageGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) {
+ if (descriptor_->options().message_set_wire_format()) {
+ // Special-case MessageSet.
+ printer->Print(
+ "void $classname$::SerializeWithCachedSizes(\n"
+ " ::google::protobuf::io::CodedOutputStream* output) const {\n"
+ " _extensions_.SerializeMessageSetWithCachedSizes(output);\n",
+ "classname", classname_);
+ GOOGLE_CHECK(UseUnknownFieldSet(descriptor_->file(), options_));
+ printer->Print(
+ " ::google::protobuf::internal::WireFormat::SerializeUnknownMessageSetItems(\n"
+ " unknown_fields(), output);\n");
+ printer->Print(
+ "}\n");
+ return;
+ }
+
+ printer->Print(
+ "void $classname$::SerializeWithCachedSizes(\n"
+ " ::google::protobuf::io::CodedOutputStream* output) const {\n",
+ "classname", classname_);
+ printer->Indent();
+
+ printer->Print(
+ "// @@protoc_insertion_point(serialize_start:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ GenerateSerializeWithCachedSizesBody(printer, false);
+
+ printer->Print(
+ "// @@protoc_insertion_point(serialize_end:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+}
+
+void MessageGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) {
+ if (descriptor_->options().message_set_wire_format()) {
+ // Special-case MessageSet.
+ printer->Print(
+ "::google::protobuf::uint8* $classname$::InternalSerializeWithCachedSizesToArray(\n"
+ " bool deterministic, ::google::protobuf::uint8* target) const {\n"
+ " target = _extensions_."
+ "InternalSerializeMessageSetWithCachedSizesToArray(\n"
+ " deterministic, target);\n",
+ "classname", classname_);
+ GOOGLE_CHECK(UseUnknownFieldSet(descriptor_->file(), options_));
+ printer->Print(
+ " target = ::google::protobuf::internal::WireFormat::\n"
+ " SerializeUnknownMessageSetItemsToArray(\n"
+ " unknown_fields(), target);\n");
+ printer->Print(
+ " return target;\n"
+ "}\n");
+ return;
+ }
+
+ printer->Print(
+ "::google::protobuf::uint8* $classname$::InternalSerializeWithCachedSizesToArray(\n"
+ " bool deterministic, ::google::protobuf::uint8* target) const {\n",
+ "classname", classname_);
+ printer->Indent();
+
+ printer->Print(
+ "// @@protoc_insertion_point(serialize_to_array_start:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ GenerateSerializeWithCachedSizesBody(printer, true);
+
+ printer->Print(
+ "// @@protoc_insertion_point(serialize_to_array_end:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print(
+ " return target;\n"
+ "}\n");
+}
+
+void MessageGenerator::
+GenerateSerializeWithCachedSizesBody(io::Printer* printer, bool to_array) {
+ google::protobuf::scoped_array<const FieldDescriptor * > ordered_fields(
+ SortFieldsByNumber(descriptor_));
+
+ vector<const Descriptor::ExtensionRange*> sorted_extensions;
+ for (int i = 0; i < descriptor_->extension_range_count(); ++i) {
+ sorted_extensions.push_back(descriptor_->extension_range(i));
+ }
+ std::sort(sorted_extensions.begin(), sorted_extensions.end(),
+ ExtensionRangeSorter());
+
+ // Merge the fields and the extension ranges, both sorted by field number.
+ int i, j;
+ for (i = 0, j = 0;
+ i < descriptor_->field_count() || j < sorted_extensions.size();
+ ) {
+ if (i == descriptor_->field_count()) {
+ GenerateSerializeOneExtensionRange(printer,
+ sorted_extensions[j++],
+ to_array);
+ } else if (j == sorted_extensions.size()) {
+ GenerateSerializeOneField(printer, ordered_fields[i++], to_array);
+ } else if (ordered_fields[i]->number() < sorted_extensions[j]->start) {
+ GenerateSerializeOneField(printer, ordered_fields[i++], to_array);
+ } else {
+ GenerateSerializeOneExtensionRange(printer,
+ sorted_extensions[j++],
+ to_array);
+ }
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print("if (_internal_metadata_.have_unknown_fields()) {\n");
+ printer->Indent();
+ if (to_array) {
+ printer->Print(
+ "target = "
+ "::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(\n"
+ " unknown_fields(), target);\n");
+ } else {
+ printer->Print(
+ "::google::protobuf::internal::WireFormat::SerializeUnknownFields(\n"
+ " unknown_fields(), output);\n");
+ }
+ printer->Outdent();
+
+ printer->Print(
+ "}\n");
+ } else {
+ printer->Print(
+ "output->WriteRaw(unknown_fields().data(),\n"
+ " static_cast<int>(unknown_fields().size()));\n");
+ }
+ }
+}
+
+static vector<uint32> RequiredFieldsBitMask(const Descriptor* desc) {
+ vector<uint32> result;
+ uint32 mask = 0;
+ for (int i = 0; i < desc->field_count(); i++) {
+ if (i > 0 && i % 32 == 0) {
+ result.push_back(mask);
+ mask = 0;
+ }
+ if (desc->field(i)->is_required()) {
+ mask |= (1 << (i & 31));
+ }
+ }
+ if (mask != 0) {
+ result.push_back(mask);
+ }
+ return result;
+}
+
+// Create an expression that evaluates to
+// "for all i, (_has_bits_[i] & masks[i]) == masks[i]"
+// masks is allowed to be shorter than _has_bits_, but at least one element of
+// masks must be non-zero.
+static string ConditionalToCheckBitmasks(const vector<uint32>& masks) {
+ vector<string> parts;
+ for (int i = 0; i < masks.size(); i++) {
+ if (masks[i] == 0) continue;
+ string m = StrCat("0x", strings::Hex(masks[i], strings::ZERO_PAD_8));
+ // Each xor evaluates to 0 if the expected bits are present.
+ parts.push_back(StrCat("((_has_bits_[", i, "] & ", m, ") ^ ", m, ")"));
+ }
+ GOOGLE_CHECK(!parts.empty());
+ // If we have multiple parts, each expected to be 0, then bitwise-or them.
+ string result = parts.size() == 1 ? parts[0] :
+ StrCat("(", Join(parts, "\n | "), ")");
+ return result + " == 0";
+}
+
+void MessageGenerator::
+GenerateByteSize(io::Printer* printer) {
+ if (descriptor_->options().message_set_wire_format()) {
+ // Special-case MessageSet.
+ printer->Print(
+ "int $classname$::ByteSize() const {\n"
+ "// @@protoc_insertion_point(message_set_byte_size_start:$full_name$)\n"
+ " int total_size = _extensions_.MessageSetByteSize();\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ GOOGLE_CHECK(UseUnknownFieldSet(descriptor_->file(), options_));
+ printer->Print(
+ "if (_internal_metadata_.have_unknown_fields()) {\n"
+ " total_size += ::google::protobuf::internal::WireFormat::\n"
+ " ComputeUnknownMessageSetItemsSize(unknown_fields());\n"
+ "}\n");
+ printer->Print(
+ " GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();\n"
+ " _cached_size_ = total_size;\n"
+ " GOOGLE_SAFE_CONCURRENT_WRITES_END();\n"
+ " return total_size;\n"
+ "}\n");
+ return;
+ }
+
+ if (num_required_fields_ > 1 && HasFieldPresence(descriptor_->file())) {
+ // Emit a function (rarely used, we hope) that handles the required fields
+ // by checking for each one individually.
+ printer->Print(
+ "int $classname$::RequiredFieldsByteSizeFallback() const {\n"
+ "// @@protoc_insertion_point(required_fields_byte_size_fallback_start:"
+ "$full_name$)\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ printer->Indent();
+ printer->Print("int total_size = 0;\n");
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (field->is_required()) {
+ printer->Print("\n"
+ "if (has_$name$()) {\n",
+ "name", FieldName(field));
+ printer->Indent();
+ PrintFieldComment(printer, field);
+ field_generators_.get(field).GenerateByteSize(printer);
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ }
+ printer->Print("\n"
+ "return total_size;\n");
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+
+ printer->Print(
+ "int $classname$::ByteSize() const {\n"
+ "// @@protoc_insertion_point(message_byte_size_start:$full_name$)\n",
+ "classname", classname_, "full_name", descriptor_->full_name());
+ printer->Indent();
+ printer->Print(
+ "int total_size = 0;\n"
+ "\n");
+
+ // Handle required fields (if any). We expect all of them to be
+ // present, so emit one conditional that checks for that. If they are all
+ // present then the fast path executes; otherwise the slow path executes.
+ if (num_required_fields_ > 1 && HasFieldPresence(descriptor_->file())) {
+ // The fast path works if all required fields are present.
+ vector<uint32> masks_for_has_bits = RequiredFieldsBitMask(descriptor_);
+ printer->Print((string("if (") +
+ ConditionalToCheckBitmasks(masks_for_has_bits) +
+ ") { // All required fields are present.\n").c_str());
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (!field->is_required()) continue;
+ PrintFieldComment(printer, field);
+ field_generators_.get(field).GenerateByteSize(printer);
+ printer->Print("\n");
+ }
+ printer->Outdent();
+ printer->Print("} else {\n" // the slow path
+ " total_size += RequiredFieldsByteSizeFallback();\n"
+ "}\n");
+ } else {
+ // num_required_fields_ <= 1: no need to be tricky
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (!field->is_required()) continue;
+ PrintFieldComment(printer, field);
+ printer->Print("if (has_$name$()) {\n",
+ "name", FieldName(field));
+ printer->Indent();
+ field_generators_.get(field).GenerateByteSize(printer);
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ }
+
+ // Handle optional fields (worry below about repeateds, oneofs, etc.).
+ // These are handled in chunks of 8. The first chunk is
+ // the non-requireds-non-repeateds-non-unions-non-extensions in
+ // descriptor_->field(0), descriptor_->field(1), ... descriptor_->field(7),
+ // and the second chunk is the same for
+ // descriptor_->field(8), descriptor_->field(9), ... descriptor_->field(15),
+ // etc.
+ hash_map<int, uint32> fields_mask_for_chunk;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (!field->is_required() && !field->is_repeated() &&
+ !field->containing_oneof()) {
+ fields_mask_for_chunk[i / 8] |= static_cast<uint32>(1) << (i % 32);
+ }
+ }
+
+ int last_index = -1;
+ bool chunk_block_in_progress = false;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (!field->is_required() && !field->is_repeated() &&
+ !field->containing_oneof()) {
+ // See above in GenerateClear for an explanation of this.
+ // TODO(kenton): Share code? Unclear how to do so without
+ // over-engineering.
+ if (i / 8 != last_index / 8 || last_index < 0) {
+ // End previous chunk, if there was one.
+ if (chunk_block_in_progress) {
+ printer->Outdent();
+ printer->Print("}\n");
+ chunk_block_in_progress = false;
+ }
+ // Start chunk.
+ uint32 mask = fields_mask_for_chunk[i / 8];
+ int count = popcnt(mask);
+ GOOGLE_DCHECK_GE(count, 1);
+ if (count == 1) {
+ // No "if" here because the chunk is trivial.
+ } else {
+ if (HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ "if (_has_bits_[$index$ / 32] & $mask$u) {\n",
+ "index", SimpleItoa(i),
+ "mask", SimpleItoa(mask));
+ printer->Indent();
+ chunk_block_in_progress = true;
+ }
+ }
+ }
+ last_index = i;
+
+ PrintFieldComment(printer, field);
+
+ bool have_enclosing_if = false;
+ if (HasFieldPresence(descriptor_->file())) {
+ printer->Print(
+ "if (has_$name$()) {\n",
+ "name", FieldName(field));
+ printer->Indent();
+ have_enclosing_if = true;
+ } else {
+ // Without field presence: field is serialized only if it has a
+ // non-default value.
+ have_enclosing_if = EmitFieldNonDefaultCondition(
+ printer, "this->", field);
+ }
+
+ field_generators_.get(field).GenerateByteSize(printer);
+
+ if (have_enclosing_if) {
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+ }
+ }
+ }
+
+ if (chunk_block_in_progress) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+
+ // Repeated fields don't use _has_bits_ so we count them in a separate
+ // pass.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ if (field->is_repeated()) {
+ PrintFieldComment(printer, field);
+ field_generators_.get(field).GenerateByteSize(printer);
+ printer->Print("\n");
+ }
+ }
+
+ // Fields inside a oneof don't use _has_bits_ so we count them in a separate
+ // pass.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "switch ($oneofname$_case()) {\n",
+ "oneofname", descriptor_->oneof_decl(i)->name());
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ PrintFieldComment(printer, field);
+ printer->Print(
+ "case k$field_name$: {\n",
+ "field_name", UnderscoresToCamelCase(field->name(), true));
+ printer->Indent();
+ field_generators_.get(field).GenerateByteSize(printer);
+ printer->Print(
+ "break;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+ printer->Print(
+ "case $cap_oneof_name$_NOT_SET: {\n"
+ " break;\n"
+ "}\n",
+ "cap_oneof_name",
+ ToUpper(descriptor_->oneof_decl(i)->name()));
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "total_size += _extensions_.ByteSize();\n"
+ "\n");
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (UseUnknownFieldSet(descriptor_->file(), options_)) {
+ printer->Print(
+ "if (_internal_metadata_.have_unknown_fields()) {\n"
+ " total_size +=\n"
+ " ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(\n"
+ " unknown_fields());\n"
+ "}\n");
+ } else {
+ printer->Print(
+ "total_size += unknown_fields().size();\n"
+ "\n");
+ }
+ }
+
+ // We update _cached_size_ even though this is a const method. In theory,
+ // this is not thread-compatible, because concurrent writes have undefined
+ // results. In practice, since any concurrent writes will be writing the
+ // exact same value, it works on all common processors. In a future version
+ // of C++, _cached_size_ should be made into an atomic<int>.
+ printer->Print(
+ "GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();\n"
+ "_cached_size_ = total_size;\n"
+ "GOOGLE_SAFE_CONCURRENT_WRITES_END();\n"
+ "return total_size;\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MessageGenerator::
+GenerateIsInitialized(io::Printer* printer) {
+ printer->Print(
+ "bool $classname$::IsInitialized() const {\n",
+ "classname", classname_);
+ printer->Indent();
+
+ if (HasFieldPresence(descriptor_->file())) {
+ // Check that all required fields in this message are set. We can do this
+ // most efficiently by checking 32 "has bits" at a time.
+ int has_bits_array_size = (descriptor_->field_count() + 31) / 32;
+ for (int i = 0; i < has_bits_array_size; i++) {
+ uint32 mask = 0;
+ for (int bit = 0; bit < 32; bit++) {
+ int index = i * 32 + bit;
+ if (index >= descriptor_->field_count()) break;
+ const FieldDescriptor* field = descriptor_->field(index);
+
+ if (field->is_required()) {
+ mask |= 1 << bit;
+ }
+ }
+
+ if (mask != 0) {
+ printer->Print(
+ "if ((_has_bits_[$i$] & 0x$mask$) != 0x$mask$) return false;\n",
+ "i", SimpleItoa(i),
+ "mask", StrCat(strings::Hex(mask, strings::ZERO_PAD_8)));
+ }
+ }
+ }
+
+ // Now check that all embedded messages are initialized.
+ printer->Print("\n");
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ !ShouldIgnoreRequiredFieldCheck(field, options_) &&
+ HasRequiredFields(field->message_type(), options_)) {
+ if (field->is_repeated()) {
+ printer->Print(
+ "if (!::google::protobuf::internal::AllAreInitialized(this->$name$()))"
+ " return false;\n",
+ "name", FieldName(field));
+ } else {
+ if (field->options().weak() || !field->containing_oneof()) {
+ // For weak fields, use the data member (::google::protobuf::Message*) instead
+ // of the getter to avoid a link dependency on the weak message type
+ // which is only forward declared.
+ printer->Print(
+ "if (has_$name$()) {\n"
+ " if (!this->$name$_->IsInitialized()) return false;\n"
+ "}\n",
+ "name", FieldName(field));
+ } else {
+ printer->Print(
+ "if (has_$name$()) {\n"
+ " if (!this->$name$().IsInitialized()) return false;\n"
+ "}\n",
+ "name", FieldName(field));
+ }
+ }
+ }
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "\n"
+ "if (!_extensions_.IsInitialized()) return false;");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ " return true;\n"
+ "}\n");
+}
+
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.h
new file mode 100644
index 0000000000..b1e3fe21dd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message.h
@@ -0,0 +1,208 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_MESSAGE_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_MESSAGE_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <set>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+#include <google/protobuf/compiler/cpp/cpp_options.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class EnumGenerator; // enum.h
+class ExtensionGenerator; // extension.h
+
+class MessageGenerator {
+ public:
+ // See generator.cc for the meaning of dllexport_decl.
+ MessageGenerator(const Descriptor* descriptor, const Options& options);
+ ~MessageGenerator();
+
+ // Header stuff.
+
+ // Return names for forward declarations of this class and all its nested
+ // types. A given key in {class,enum}_names will map from a class name to the
+ // descriptor that was responsible for its inclusion in the map. This can be
+ // used to associate the descriptor with the code generated for it.
+ void FillMessageForwardDeclarations(
+ map<string, const Descriptor*>* class_names);
+ void FillEnumForwardDeclarations(
+ map<string, const EnumDescriptor*>* enum_names);
+
+ // Generate definitions of all nested enums (must come before class
+ // definitions because those classes use the enums definitions).
+ void GenerateEnumDefinitions(io::Printer* printer);
+
+ // Generate specializations of GetEnumDescriptor<MyEnum>().
+ // Precondition: in ::google::protobuf namespace.
+ void GenerateGetEnumDescriptorSpecializations(io::Printer* printer);
+
+ // Generate definitions for this class and all its nested types.
+ void GenerateClassDefinition(io::Printer* printer);
+
+ // Generate definitions of inline methods (placed at the end of the header
+ // file).
+ void GenerateInlineMethods(io::Printer* printer, bool is_inline);
+
+ // Dependent methods are always inline.
+ void GenerateDependentInlineMethods(io::Printer* printer);
+
+ // Source file stuff.
+
+ // Generate code which declares all the global descriptor pointers which
+ // will be initialized by the methods below.
+ void GenerateDescriptorDeclarations(io::Printer* printer);
+
+ // Generate code that initializes the global variable storing the message's
+ // descriptor.
+ void GenerateDescriptorInitializer(io::Printer* printer, int index);
+
+ // Generate code that calls MessageFactory::InternalRegisterGeneratedMessage()
+ // for all types.
+ void GenerateTypeRegistrations(io::Printer* printer);
+
+ // Generates code that allocates the message's default instance.
+ void GenerateDefaultInstanceAllocator(io::Printer* printer);
+
+ // Generates code that initializes the message's default instance. This
+ // is separate from allocating because all default instances must be
+ // allocated before any can be initialized.
+ void GenerateDefaultInstanceInitializer(io::Printer* printer);
+
+ // Generates code that should be run when ShutdownProtobufLibrary() is called,
+ // to delete all dynamically-allocated objects.
+ void GenerateShutdownCode(io::Printer* printer);
+
+ // Generate all non-inline methods for this class.
+ void GenerateClassMethods(io::Printer* printer);
+
+ private:
+ // Generate declarations and definitions of accessors for fields.
+ void GenerateDependentBaseClassDefinition(io::Printer* printer);
+ void GenerateDependentFieldAccessorDeclarations(io::Printer* printer);
+ void GenerateFieldAccessorDeclarations(io::Printer* printer);
+ void GenerateDependentFieldAccessorDefinitions(io::Printer* printer);
+ void GenerateFieldAccessorDefinitions(io::Printer* printer, bool is_inline);
+
+ // Generate the field offsets array.
+ void GenerateOffsets(io::Printer* printer);
+
+ // Generate constructors and destructor.
+ void GenerateStructors(io::Printer* printer);
+
+ // The compiler typically generates multiple copies of each constructor and
+ // destructor: http://gcc.gnu.org/bugs.html#nonbugs_cxx
+ // Placing common code in a separate method reduces the generated code size.
+ //
+ // Generate the shared constructor code.
+ void GenerateSharedConstructorCode(io::Printer* printer);
+ // Generate the shared destructor code.
+ void GenerateSharedDestructorCode(io::Printer* printer);
+ // Generate the arena-specific destructor code.
+ void GenerateArenaDestructorCode(io::Printer* printer);
+
+ // Generate standard Message methods.
+ void GenerateClear(io::Printer* printer);
+ void GenerateOneofClear(io::Printer* printer);
+ void GenerateMergeFromCodedStream(io::Printer* printer);
+ void GenerateSerializeWithCachedSizes(io::Printer* printer);
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer);
+ void GenerateSerializeWithCachedSizesBody(io::Printer* printer,
+ bool to_array);
+ void GenerateByteSize(io::Printer* printer);
+ void GenerateMergeFrom(io::Printer* printer);
+ void GenerateCopyFrom(io::Printer* printer);
+ void GenerateSwap(io::Printer* printer);
+ void GenerateIsInitialized(io::Printer* printer);
+
+ // Helpers for GenerateSerializeWithCachedSizes().
+ void GenerateSerializeOneField(io::Printer* printer,
+ const FieldDescriptor* field,
+ bool unbounded);
+ void GenerateSerializeOneExtensionRange(
+ io::Printer* printer, const Descriptor::ExtensionRange* range,
+ bool unbounded);
+
+
+ // Generates has_foo() functions and variables for singular field has-bits.
+ void GenerateSingularFieldHasBits(const FieldDescriptor* field,
+ map<string, string> vars,
+ io::Printer* printer);
+ // Generates has_foo() functions and variables for oneof field has-bits.
+ void GenerateOneofHasBits(io::Printer* printer, bool is_inline);
+ // Generates has_foo_bar() functions for oneof members.
+ void GenerateOneofMemberHasBits(const FieldDescriptor* field,
+ const map<string, string>& vars,
+ io::Printer* printer);
+ // Generates the clear_foo() method for a field.
+ void GenerateFieldClear(const FieldDescriptor* field,
+ const map<string, string>& vars,
+ io::Printer* printer);
+
+ const Descriptor* descriptor_;
+ string classname_;
+ Options options_;
+ FieldGeneratorMap field_generators_;
+ vector< vector<string> > runs_of_fields_; // that might be trivially cleared
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<MessageGenerator> > nested_generators_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<EnumGenerator> > enum_generators_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<ExtensionGenerator> > extension_generators_;
+ int num_required_fields_;
+ bool uses_string_;
+ bool use_dependent_base_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.cc
new file mode 100644
index 0000000000..d021035d05
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.cc
@@ -0,0 +1,1055 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_message_field.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+namespace {
+
+void SetMessageVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables,
+ const Options& options) {
+ SetCommonFieldVariables(descriptor, variables, options);
+ (*variables)["type"] = FieldMessageTypeName(descriptor);
+ if (descriptor->options().weak() || !descriptor->containing_oneof()) {
+ (*variables)["non_null_ptr_to_name"] =
+ StrCat("this->", (*variables)["name"], "_");
+ }
+ (*variables)["stream_writer"] =
+ (*variables)["declared_type"] +
+ (HasFastArraySerialization(descriptor->message_type()->file(), options)
+ ? "MaybeToArray"
+ : "");
+ // NOTE: Escaped here to unblock proto1->proto2 migration.
+ // TODO(liujisi): Extend this to apply for other conflicting methods.
+ (*variables)["release_name"] =
+ SafeFunctionName(descriptor->containing_type(),
+ descriptor, "release_");
+ (*variables)["full_name"] = descriptor->full_name();
+ if (options.proto_h && IsFieldDependent(descriptor)) {
+ (*variables)["dependent_type"] = "T::" + DependentTypeName(descriptor);
+ (*variables)["dependent_typename"] =
+ "typename T::" + DependentTypeName(descriptor);
+ } else {
+ (*variables)["dependent_type"] = FieldMessageTypeName(descriptor);
+ (*variables)["dependent_typename"] = FieldMessageTypeName(descriptor);
+ }
+}
+
+} // namespace
+
+// ===================================================================
+
+MessageFieldGenerator::MessageFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : FieldGenerator(options),
+ descriptor_(descriptor),
+ dependent_field_(options.proto_h && IsFieldDependent(descriptor)) {
+ SetMessageVariables(descriptor, &variables_, options);
+}
+
+MessageFieldGenerator::~MessageFieldGenerator() {}
+
+void MessageFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_, "$type$* $name$_;\n");
+}
+
+void MessageFieldGenerator::
+GenerateGetterDeclaration(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$deprecated_attr$const $type$& $name$() const;\n");
+}
+
+void MessageFieldGenerator::
+GenerateDependentAccessorDeclarations(io::Printer* printer) const {
+ if (!dependent_field_) {
+ return;
+ }
+ // Arena manipulation code is out-of-line in the derived message class.
+ printer->Print(variables_,
+ "$deprecated_attr$$type$* mutable_$name$();\n"
+ "$deprecated_attr$$type$* $release_name$();\n"
+ "$deprecated_attr$void set_allocated_$name$($type$* $name$);\n");
+}
+
+void MessageFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ "private:\n"
+ "void _slow_mutable_$name$();\n");
+ if (SupportsArenas(descriptor_->message_type())) {
+ printer->Print(variables_,
+ "void _slow_set_allocated_$name$(\n"
+ " ::google::protobuf::Arena* message_arena, $type$** $name$);\n");
+ }
+ printer->Print(variables_,
+ "$type$* _slow_$release_name$();\n"
+ "public:\n");
+ }
+ GenerateGetterDeclaration(printer);
+ if (!dependent_field_) {
+ printer->Print(variables_,
+ "$deprecated_attr$$type$* mutable_$name$();\n"
+ "$deprecated_attr$$type$* $release_name$();\n"
+ "$deprecated_attr$void set_allocated_$name$($type$* $name$);\n");
+ }
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ "$deprecated_attr$$type$* unsafe_arena_release_$name$();\n"
+ "$deprecated_attr$void unsafe_arena_set_allocated_$name$(\n"
+ " $type$* $name$);\n");
+ }
+}
+
+void MessageFieldGenerator::GenerateNonInlineAccessorDefinitions(
+ io::Printer* printer) const {
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ "void $classname$::_slow_mutable_$name$() {\n");
+ if (SupportsArenas(descriptor_->message_type())) {
+ printer->Print(variables_,
+ " $name$_ = ::google::protobuf::Arena::CreateMessage< $type$ >(\n"
+ " GetArenaNoVirtual());\n");
+ } else {
+ printer->Print(variables_,
+ " $name$_ = ::google::protobuf::Arena::Create< $type$ >(\n"
+ " GetArenaNoVirtual());\n");
+ }
+ printer->Print(variables_,
+ "}\n"
+ "$type$* $classname$::_slow_$release_name$() {\n"
+ " if ($name$_ == NULL) {\n"
+ " return NULL;\n"
+ " } else {\n"
+ " $type$* temp = new $type$;\n"
+ " temp->MergeFrom(*$name$_);\n"
+ " $name$_ = NULL;\n"
+ " return temp;\n"
+ " }\n"
+ "}\n"
+ "$type$* $classname$::unsafe_arena_release_$name$() {\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_release:$full_name$)\n"
+ " $clear_hasbit$\n"
+ " $type$* temp = $name$_;\n"
+ " $name$_ = NULL;\n"
+ " return temp;\n"
+ "}\n");
+ if (SupportsArenas(descriptor_->message_type())) {
+ // NOTE: the same logic is mirrored in weak_message_field.cc. Any
+ // arena-related semantics changes should be made in both places.
+ printer->Print(variables_,
+ "void $classname$::_slow_set_allocated_$name$(\n"
+ " ::google::protobuf::Arena* message_arena, $type$** $name$) {\n"
+ " if (message_arena != NULL && \n"
+ " ::google::protobuf::Arena::GetArena(*$name$) == NULL) {\n"
+ " message_arena->Own(*$name$);\n"
+ " } else if (message_arena !=\n"
+ " ::google::protobuf::Arena::GetArena(*$name$)) {\n"
+ " $type$* new_$name$ = \n"
+ " ::google::protobuf::Arena::CreateMessage< $type$ >(\n"
+ " message_arena);\n"
+ " new_$name$->CopyFrom(**$name$);\n"
+ " *$name$ = new_$name$;\n"
+ " }\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "void $classname$::unsafe_arena_set_allocated_$name$(\n"
+ " $type$* $name$) {\n"
+ // If we're not on an arena, free whatever we were holding before.
+ // (If we are on arena, we can just forget the earlier pointer.)
+ " if (GetArenaNoVirtual() == NULL) {\n"
+ " delete $name$_;\n"
+ " }\n"
+ " $name$_ = $name$;\n"
+ " if ($name$) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_set_allocated"
+ ":$full_name$)\n"
+ "}\n");
+ }
+}
+
+void MessageFieldGenerator::
+GenerateDependentInlineAccessorDefinitions(io::Printer* printer) const {
+ if (!dependent_field_) {
+ return;
+ }
+
+ map<string, string> variables(variables_);
+ // For the CRTP base class, all mutation methods are dependent, and so
+ // they must be in the header.
+ variables["dependent_classname"] =
+ DependentBaseClassTemplateName(descriptor_->containing_type()) + "<T>";
+ variables["this_message"] = DependentBaseDownCast();
+ if (!variables["set_hasbit"].empty()) {
+ variables["set_hasbit"] =
+ variables["this_message"] + variables["set_hasbit"];
+ }
+ if (!variables["clear_hasbit"].empty()) {
+ variables["clear_hasbit"] =
+ variables["this_message"] + variables["clear_hasbit"];
+ }
+
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables,
+ "template <class T>\n"
+ "inline $type$* $dependent_classname$::mutable_$name$() {\n"
+ " $set_hasbit$\n"
+ " $dependent_typename$*& $name$_ = $this_message$$name$_;\n"
+ " if ($name$_ == NULL) {\n"
+ " $this_message$_slow_mutable_$name$();\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "template <class T>\n"
+ "inline $type$* $dependent_classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " $dependent_typename$*& $name$_ = $this_message$$name$_;\n"
+ " $clear_hasbit$\n"
+ " if ($this_message$GetArenaNoVirtual() != NULL) {\n"
+ " return $this_message$_slow_$release_name$();\n"
+ " } else {\n"
+ " $dependent_typename$* temp = $name$_;\n"
+ " $name$_ = NULL;\n"
+ " return temp;\n"
+ " }\n"
+ "}\n"
+ "template <class T>\n"
+ "inline void $dependent_classname$::"
+ "set_allocated_$name$($type$* $name$) {\n"
+ " ::google::protobuf::Arena* message_arena = $this_message$GetArenaNoVirtual();\n"
+ " $dependent_typename$*& $name$_ = $this_message$$name$_;\n"
+ " if (message_arena == NULL) {\n"
+ " delete $name$_;\n"
+ " }\n"
+ " if ($name$ != NULL) {\n");
+ if (SupportsArenas(descriptor_->message_type())) {
+ // If we're on an arena and the incoming message is not, simply Own() it
+ // rather than copy to the arena -- either way we need a heap dealloc,
+ // so we might as well defer it. Otherwise, if incoming message is on a
+ // different ownership domain (specific arena, or the heap) than we are,
+ // copy to our arena (or heap, as the case may be).
+ printer->Print(variables,
+ " $this_message$_slow_set_allocated_$name$(message_arena, "
+ "&$name$);\n");
+ } else {
+ printer->Print(variables,
+ " if (message_arena != NULL) {\n"
+ " message_arena->Own($name$);\n"
+ " }\n");
+ }
+ printer->Print(variables,
+ " }\n"
+ " $name$_ = $name$;\n"
+ " if ($name$) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ // TODO(dlj): move insertion points to message class.
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n");
+ } else {
+ printer->Print(variables,
+ "template <class T>\n"
+ "inline $type$* $dependent_classname$::mutable_$name$() {\n"
+ " $set_hasbit$\n"
+ " $dependent_typename$*& $name$_ = $this_message$$name$_;\n"
+ " if ($name$_ == NULL) {\n"
+ " $name$_ = new $dependent_typename$;\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "template <class T>\n"
+ "inline $type$* $dependent_classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " $clear_hasbit$\n"
+ " $dependent_typename$*& $name$_ = $this_message$$name$_;\n"
+ " $dependent_typename$* temp = $name$_;\n"
+ " $name$_ = NULL;\n"
+ " return temp;\n"
+ "}\n"
+ "template <class T>\n"
+ "inline void $dependent_classname$::"
+ "set_allocated_$name$($type$* $name$) {\n"
+ " $dependent_typename$*& $name$_ = $this_message$$name$_;\n"
+ " delete $name$_;\n");
+
+ if (SupportsArenas(descriptor_->message_type())) {
+ printer->Print(variables,
+ " if ($name$ != NULL && static_cast< $dependent_typename$* >($name$)"
+ "->GetArena() != NULL) {\n"
+ " $dependent_typename$* new_$name$ = new $dependent_typename$;\n"
+ " new_$name$->CopyFrom(*$name$);\n"
+ " $name$ = new_$name$;\n"
+ " }\n");
+ }
+
+ printer->Print(variables,
+ " $name$_ = $name$;\n"
+ " if ($name$) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n");
+ }
+}
+
+void MessageFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline " : "";
+ printer->Print(variables,
+ "$inline$const $type$& $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n");
+
+ PrintHandlingOptionalStaticInitializers(
+ variables, descriptor_->file(), options_, printer,
+ // With static initializers.
+ " return $name$_ != NULL ? *$name$_ : *default_instance_->$name$_;\n",
+ // Without.
+ " return $name$_ != NULL ? *$name$_ : *default_instance().$name$_;\n");
+ printer->Print(variables, "}\n");
+
+ if (dependent_field_) {
+ return;
+ }
+
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables,
+ "$inline$"
+ "$type$* $classname$::mutable_$name$() {\n"
+ " $set_hasbit$\n"
+ " if ($name$_ == NULL) {\n"
+ " _slow_mutable_$name$();\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "$inline$"
+ "$type$* $classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " $clear_hasbit$\n"
+ " if (GetArenaNoVirtual() != NULL) {\n"
+ " return _slow_$release_name$();\n"
+ " } else {\n"
+ " $type$* temp = $name$_;\n"
+ " $name$_ = NULL;\n"
+ " return temp;\n"
+ " }\n"
+ "}\n"
+ "$inline$ "
+ "void $classname$::set_allocated_$name$($type$* $name$) {\n"
+ " ::google::protobuf::Arena* message_arena = GetArenaNoVirtual();\n"
+ " if (message_arena == NULL) {\n"
+ " delete $name$_;\n"
+ " }\n"
+ " if ($name$ != NULL) {\n");
+ if (SupportsArenas(descriptor_->message_type())) {
+ // If we're on an arena and the incoming message is not, simply Own() it
+ // rather than copy to the arena -- either way we need a heap dealloc,
+ // so we might as well defer it. Otherwise, if incoming message is on a
+ // different ownership domain (specific arena, or the heap) than we are,
+ // copy to our arena (or heap, as the case may be).
+ printer->Print(variables,
+ " _slow_set_allocated_$name$(message_arena, &$name$);\n");
+ } else {
+ printer->Print(variables,
+ " if (message_arena != NULL) {\n"
+ " message_arena->Own($name$);\n"
+ " }\n");
+ }
+ printer->Print(variables,
+ " }\n"
+ " $name$_ = $name$;\n"
+ " if ($name$) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n");
+ } else {
+ printer->Print(variables,
+ "$inline$"
+ "$type$* $classname$::mutable_$name$() {\n"
+ " $set_hasbit$\n"
+ " if ($name$_ == NULL) {\n"
+ " $name$_ = new $type$;\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "$inline$"
+ "$type$* $classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " $clear_hasbit$\n"
+ " $type$* temp = $name$_;\n"
+ " $name$_ = NULL;\n"
+ " return temp;\n"
+ "}\n"
+ "$inline$"
+ "void $classname$::set_allocated_$name$($type$* $name$) {\n"
+ " delete $name$_;\n");
+
+ if (SupportsArenas(descriptor_->message_type())) {
+ printer->Print(variables,
+ " if ($name$ != NULL && $name$->GetArena() != NULL) {\n"
+ " $type$* new_$name$ = new $type$;\n"
+ " new_$name$->CopyFrom(*$name$);\n"
+ " $name$ = new_$name$;\n"
+ " }\n");
+ }
+
+ printer->Print(variables,
+ " $name$_ = $name$;\n"
+ " if ($name$) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n");
+ }
+}
+
+void MessageFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ variables["this_message"] = dependent_field_ ? DependentBaseDownCast() : "";
+ if (!HasFieldPresence(descriptor_->file())) {
+ // If we don't have has-bits, message presence is indicated only by ptr !=
+ // NULL. Thus on clear, we need to delete the object.
+ printer->Print(variables,
+ "if ($this_message$GetArenaNoVirtual() == NULL && "
+ "$this_message$$name$_ != NULL) delete $this_message$$name$_;\n"
+ "$this_message$$name$_ = NULL;\n");
+ } else {
+ printer->Print(variables,
+ "if ($this_message$$name$_ != NULL) $this_message$$name$_->"
+ "$dependent_type$::Clear();\n");
+ }
+}
+
+void MessageFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "mutable_$name$()->$type$::MergeFrom(from.$name$());\n");
+}
+
+void MessageFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "std::swap($name$_, other->$name$_);\n");
+}
+
+void MessageFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = NULL;\n");
+}
+
+void MessageFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ if (descriptor_->type() == FieldDescriptor::TYPE_MESSAGE) {
+ printer->Print(variables_,
+ "DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(\n"
+ " input, mutable_$name$()));\n");
+ } else {
+ printer->Print(variables_,
+ "DO_(::google::protobuf::internal::WireFormatLite::ReadGroupNoVirtual(\n"
+ " $number$, input, mutable_$name$()));\n");
+ }
+}
+
+void MessageFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ printer->Print(variables_,
+ "::google::protobuf::internal::WireFormatLite::Write$stream_writer$(\n"
+ " $number$, *$non_null_ptr_to_name$, output);\n");
+}
+
+void MessageFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ printer->Print(variables_,
+ "target = ::google::protobuf::internal::WireFormatLite::\n"
+ " InternalWrite$declared_type$NoVirtualToArray(\n"
+ " $number$, *$non_null_ptr_to_name$, false, target);\n");
+}
+
+void MessageFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "total_size += $tag_size$ +\n"
+ " ::google::protobuf::internal::WireFormatLite::$declared_type$SizeNoVirtual(\n"
+ " *$non_null_ptr_to_name$);\n");
+}
+
+// ===================================================================
+
+MessageOneofFieldGenerator::
+MessageOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : MessageFieldGenerator(descriptor, options),
+ dependent_base_(options.proto_h) {
+ SetCommonOneofFieldVariables(descriptor, &variables_);
+}
+
+MessageOneofFieldGenerator::~MessageOneofFieldGenerator() {}
+
+
+void MessageOneofFieldGenerator::
+GenerateDependentAccessorDeclarations(io::Printer* printer) const {
+ // Oneof field getters must be dependent as they call default_instance().
+ // Otherwise, the logic is the same as MessageFields.
+ if (!dependent_field_) {
+ return;
+ }
+ printer->Print(variables_,
+ "$deprecated_attr$const $type$& $name$() const;\n");
+ MessageFieldGenerator::GenerateDependentAccessorDeclarations(printer);
+}
+
+void MessageOneofFieldGenerator::
+GenerateGetterDeclaration(io::Printer* printer) const {
+ // Oneof field getters must be dependent as they call default_instance().
+ // Unlike MessageField, this means there is no (non-dependent) getter to
+ // generate.
+ if (dependent_field_) {
+ return;
+ }
+ printer->Print(variables_,
+ "$deprecated_attr$const $type$& $name$() const;\n");
+}
+
+void MessageOneofFieldGenerator::
+GenerateDependentInlineAccessorDefinitions(io::Printer* printer) const {
+ // For the CRTP base class, all mutation methods are dependent, and so
+ // they must be in the header.
+ if (!dependent_base_) {
+ return;
+ }
+ map<string, string> variables(variables_);
+ variables["inline"] = "inline ";
+ variables["dependent_classname"] =
+ DependentBaseClassTemplateName(descriptor_->containing_type()) + "<T>";
+ variables["this_message"] = "reinterpret_cast<T*>(this)->";
+ // Const message access is needed for the dependent getter.
+ variables["this_const_message"] = "reinterpret_cast<const T*>(this)->";
+ variables["tmpl"] = "template <class T>\n";
+ variables["field_member"] = variables["this_message"] +
+ variables["oneof_prefix"] + variables["name"] +
+ "_";
+ InternalGenerateInlineAccessorDefinitions(variables, printer);
+}
+
+void MessageOneofFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ if (dependent_base_) {
+ return;
+ }
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline " : "";
+ variables["dependent_classname"] = variables["classname"];
+ variables["this_message"] = "";
+ variables["this_const_message"] = "";
+ variables["tmpl"] = "";
+ variables["field_member"] =
+ variables["oneof_prefix"] + variables["name"] + "_";
+ variables["dependent_type"] = variables["type"];
+ InternalGenerateInlineAccessorDefinitions(variables, printer);
+}
+
+void MessageOneofFieldGenerator::
+GenerateNonInlineAccessorDefinitions(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ variables["field_member"] =
+ variables["oneof_prefix"] + variables["name"] + "_";
+
+ //printer->Print(variables,
+}
+
+void MessageOneofFieldGenerator::
+InternalGenerateInlineAccessorDefinitions(const map<string, string>& variables,
+ io::Printer* printer) const {
+ printer->Print(variables,
+ "$tmpl$"
+ "$inline$ "
+ "const $type$& $dependent_classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $this_const_message$has_$name$()\n"
+ " ? *$this_const_message$$oneof_prefix$$name$_\n"
+ " : $dependent_type$::default_instance();\n"
+ "}\n");
+
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables,
+ "$tmpl$"
+ "$inline$"
+ "$type$* $dependent_classname$::mutable_$name$() {\n"
+ " if (!$this_message$has_$name$()) {\n"
+ " $this_message$clear_$oneof_name$();\n"
+ " $this_message$set_has_$name$();\n");
+ if (SupportsArenas(descriptor_->message_type())) {
+ printer->Print(variables,
+ " $field_member$ = \n"
+ " ::google::protobuf::Arena::CreateMessage< $dependent_typename$ >(\n"
+ " $this_message$GetArenaNoVirtual());\n");
+ } else {
+ printer->Print(variables,
+ " $this_message$$oneof_prefix$$name$_ = \n"
+ " ::google::protobuf::Arena::Create< $dependent_typename$ >(\n"
+ " $this_message$GetArenaNoVirtual());\n");
+ }
+ printer->Print(variables,
+ " }\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $field_member$;\n"
+ "}\n"
+ "$tmpl$"
+ "$inline$"
+ "$type$* $dependent_classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " if ($this_message$has_$name$()) {\n"
+ " $this_message$clear_has_$oneof_name$();\n"
+ " if ($this_message$GetArenaNoVirtual() != NULL) {\n"
+ // N.B.: safe to use the underlying field pointer here because we are sure
+ // that it is non-NULL (because has_$name$() returned true).
+ " $dependent_typename$* temp = new $dependent_typename$;\n"
+ " temp->MergeFrom(*$field_member$);\n"
+ " $field_member$ = NULL;\n"
+ " return temp;\n"
+ " } else {\n"
+ " $dependent_typename$* temp = $field_member$;\n"
+ " $field_member$ = NULL;\n"
+ " return temp;\n"
+ " }\n"
+ " } else {\n"
+ " return NULL;\n"
+ " }\n"
+ "}\n"
+ "$tmpl$"
+ "$inline$"
+ "void $dependent_classname$::"
+ "set_allocated_$name$($type$* $name$) {\n"
+ " $this_message$clear_$oneof_name$();\n"
+ " if ($name$) {\n");
+
+ if (SupportsArenas(descriptor_->message_type())) {
+ printer->Print(variables,
+ // If incoming message is on the heap and we are on an arena, just Own()
+ // it (see above). If it's on a different arena than we are or one of us
+ // is on the heap, we make a copy to our arena/heap.
+ " if ($this_message$GetArenaNoVirtual() != NULL &&\n"
+ " ::google::protobuf::Arena::GetArena($name$) == NULL) {\n"
+ " $this_message$GetArenaNoVirtual()->Own($name$);\n"
+ " } else if ($this_message$GetArenaNoVirtual() !=\n"
+ " ::google::protobuf::Arena::GetArena($name$)) {\n"
+ " $dependent_typename$* new_$name$ = \n"
+ " ::google::protobuf::Arena::CreateMessage< $dependent_typename$ >(\n"
+ " $this_message$GetArenaNoVirtual());\n"
+ " new_$name$->CopyFrom(*$name$);\n"
+ " $name$ = new_$name$;\n"
+ " }\n");
+ } else {
+ printer->Print(variables,
+ " if ($this_message$GetArenaNoVirtual() != NULL) {\n"
+ " $this_message$GetArenaNoVirtual()->Own($name$);\n"
+ " }\n");
+ }
+
+ printer->Print(variables,
+ " $this_message$set_has_$name$();\n"
+ " $field_member$ = $name$;\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n"
+ "$inline$ $type$* $classname$::unsafe_arena_release_$name$() {\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_release"
+ ":$full_name$)\n"
+ " if (has_$name$()) {\n"
+ " clear_has_$oneof_name$();\n"
+ " $type$* temp = $oneof_prefix$$name$_;\n"
+ " $oneof_prefix$$name$_ = NULL;\n"
+ " return temp;\n"
+ " } else {\n"
+ " return NULL;\n"
+ " }\n"
+ "}\n"
+ "$inline$ void $classname$::unsafe_arena_set_allocated_$name$"
+ "($type$* $name$) {\n"
+ // We rely on the oneof clear method to free the earlier contents of this
+ // oneof. We can directly use the pointer we're given to set the new
+ // value.
+ " clear_$oneof_name$();\n"
+ " if ($name$) {\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_ = $name$;\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_set_allocated:"
+ "$full_name$)\n"
+ "}\n");
+ } else {
+ printer->Print(variables,
+ "$tmpl$"
+ "$inline$"
+ "$type$* $dependent_classname$::mutable_$name$() {\n"
+ " if (!$this_message$has_$name$()) {\n"
+ " $this_message$clear_$oneof_name$();\n"
+ " $this_message$set_has_$name$();\n"
+ " $field_member$ = new $dependent_typename$;\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $field_member$;\n"
+ "}\n"
+ "$tmpl$"
+ "$inline$"
+ "$type$* $dependent_classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " if ($this_message$has_$name$()) {\n"
+ " $this_message$clear_has_$oneof_name$();\n"
+ " $dependent_typename$* temp = $field_member$;\n"
+ " $field_member$ = NULL;\n"
+ " return temp;\n"
+ " } else {\n"
+ " return NULL;\n"
+ " }\n"
+ "}\n"
+ "$tmpl$"
+ "$inline$"
+ "void $dependent_classname$::"
+ "set_allocated_$name$($type$* $name$) {\n"
+ " $this_message$clear_$oneof_name$();\n"
+ " if ($name$) {\n");
+ if (SupportsArenas(descriptor_->message_type())) {
+ printer->Print(variables,
+ " if (static_cast< $dependent_typename$*>($name$)->"
+ "GetArena() != NULL) {\n"
+ " $dependent_typename$* new_$name$ = new $dependent_typename$;\n"
+ " new_$name$->CopyFrom(*$name$);\n"
+ " $name$ = new_$name$;\n"
+ " }\n");
+ }
+ printer->Print(variables,
+ " $this_message$set_has_$name$();\n"
+ " $field_member$ = $name$;\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n");
+ }
+}
+
+void MessageOneofFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ variables["this_message"] = dependent_field_ ? DependentBaseDownCast() : "";
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables,
+ "if ($this_message$GetArenaNoVirtual() == NULL) {\n"
+ " delete $this_message$$oneof_prefix$$name$_;\n"
+ "}\n");
+ } else {
+ printer->Print(variables,
+ "delete $this_message$$oneof_prefix$$name$_;\n");
+ }
+}
+
+void MessageOneofFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ // Don't print any swapping code. Swapping the union will swap this field.
+}
+
+void MessageOneofFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ // Don't print any constructor code. The field is in a union. We allocate
+ // space only when this field is used.
+}
+
+// ===================================================================
+
+RepeatedMessageFieldGenerator::RepeatedMessageFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : FieldGenerator(options),
+ descriptor_(descriptor),
+ dependent_field_(options.proto_h && IsFieldDependent(descriptor)),
+ dependent_getter_(dependent_field_ && options.safe_boundary_check) {
+ SetMessageVariables(descriptor, &variables_, options);
+}
+
+RepeatedMessageFieldGenerator::~RepeatedMessageFieldGenerator() {}
+
+void RepeatedMessageFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "::google::protobuf::RepeatedPtrField< $type$ > $name$_;\n");
+}
+
+void RepeatedMessageFieldGenerator::
+InternalGenerateTypeDependentAccessorDeclarations(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$deprecated_attr$$type$* mutable_$name$(int index);\n"
+ "$deprecated_attr$$type$* add_$name$();\n");
+ if (dependent_getter_) {
+ printer->Print(variables_,
+ "$deprecated_attr$const ::google::protobuf::RepeatedPtrField< $type$ >&\n"
+ " $name$() const;\n");
+ }
+ printer->Print(variables_,
+ "$deprecated_attr$::google::protobuf::RepeatedPtrField< $type$ >*\n"
+ " mutable_$name$();\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateDependentAccessorDeclarations(io::Printer* printer) const {
+ if (dependent_getter_) {
+ printer->Print(variables_,
+ "$deprecated_attr$const $type$& $name$(int index) const;\n");
+ }
+ if (dependent_field_) {
+ InternalGenerateTypeDependentAccessorDeclarations(printer);
+ }
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ if (!dependent_getter_) {
+ printer->Print(variables_,
+ "$deprecated_attr$const $type$& $name$(int index) const;\n");
+ }
+ if (!dependent_field_) {
+ InternalGenerateTypeDependentAccessorDeclarations(printer);
+ }
+ if (!dependent_getter_) {
+ printer->Print(variables_,
+ "$deprecated_attr$const ::google::protobuf::RepeatedPtrField< $type$ >&\n"
+ " $name$() const;\n");
+ }
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateDependentInlineAccessorDefinitions(io::Printer* printer) const {
+ if (!dependent_field_) {
+ return;
+ }
+ map<string, string> variables(variables_);
+ // For the CRTP base class, all mutation methods are dependent, and so
+ // they must be in the header.
+ variables["dependent_classname"] =
+ DependentBaseClassTemplateName(descriptor_->containing_type()) + "<T>";
+ variables["this_message"] = DependentBaseDownCast();
+ variables["this_const_message"] = DependentBaseConstDownCast();
+
+ if (dependent_getter_) {
+ printer->Print(variables,
+ "template <class T>\n"
+ "inline const $type$& $dependent_classname$::$name$(int index) const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $this_const_message$$name$_.$cppget$(index);\n"
+ "}\n");
+ }
+
+ // Generate per-element accessors:
+ printer->Print(variables,
+ "template <class T>\n"
+ "inline $type$* $dependent_classname$::mutable_$name$(int index) {\n"
+ // TODO(dlj): move insertion points
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $this_message$$name$_.Mutable(index);\n"
+ "}\n"
+ "template <class T>\n"
+ "inline $type$* $dependent_classname$::add_$name$() {\n"
+ " // @@protoc_insertion_point(field_add:$full_name$)\n"
+ " return $this_message$$name$_.Add();\n"
+ "}\n");
+
+
+ if (dependent_getter_) {
+ printer->Print(variables,
+ "template <class T>\n"
+ "inline const ::google::protobuf::RepeatedPtrField< $type$ >&\n"
+ "$dependent_classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_list:$full_name$)\n"
+ " return $this_const_message$$name$_;\n"
+ "}\n");
+ }
+
+ // Generate mutable access to the entire list:
+ printer->Print(variables,
+ "template <class T>\n"
+ "inline ::google::protobuf::RepeatedPtrField< $type$ >*\n"
+ "$dependent_classname$::mutable_$name$() {\n"
+ " // @@protoc_insertion_point(field_mutable_list:$full_name$)\n"
+ " return &$this_message$$name$_;\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline " : "";
+
+ if (!dependent_getter_) {
+ printer->Print(variables,
+ "$inline$"
+ "const $type$& $classname$::$name$(int index) const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $name$_.$cppget$(index);\n"
+ "}\n");
+ }
+
+ if (!dependent_field_) {
+ printer->Print(variables,
+ "$inline$"
+ "$type$* $classname$::mutable_$name$(int index) {\n"
+ // TODO(dlj): move insertion points
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_.Mutable(index);\n"
+ "}\n"
+ "$inline$"
+ "$type$* $classname$::add_$name$() {\n"
+ " // @@protoc_insertion_point(field_add:$full_name$)\n"
+ " return $name$_.Add();\n"
+ "}\n");
+ }
+
+
+ if (!dependent_field_) {
+ printer->Print(variables,
+ "$inline$"
+ "::google::protobuf::RepeatedPtrField< $type$ >*\n"
+ "$classname$::mutable_$name$() {\n"
+ " // @@protoc_insertion_point(field_mutable_list:$full_name$)\n"
+ " return &$name$_;\n"
+ "}\n");
+ }
+ if (!dependent_getter_) {
+ printer->Print(variables,
+ "$inline$"
+ "const ::google::protobuf::RepeatedPtrField< $type$ >&\n"
+ "$classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_list:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n");
+ }
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ variables["this_message"] = dependent_field_ ? DependentBaseDownCast() : "";
+ printer->Print(variables, "$this_message$$name$_.Clear();\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.MergeFrom(from.$name$_);\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.UnsafeArenaSwap(&other->$name$_);\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ // Not needed for repeated fields.
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ if (descriptor_->type() == FieldDescriptor::TYPE_MESSAGE) {
+ printer->Print(variables_,
+ "DO_(::google::protobuf::internal::WireFormatLite::"
+ "ReadMessageNoVirtualNoRecursionDepth(\n"
+ " input, add_$name$()));\n");
+ } else {
+ printer->Print(variables_,
+ "DO_(::google::protobuf::internal::WireFormatLite::"
+ "ReadGroupNoVirtualNoRecursionDepth(\n"
+ " $number$, input, add_$name$()));\n");
+ }
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (unsigned int i = 0, n = this->$name$_size(); i < n; i++) {\n"
+ " ::google::protobuf::internal::WireFormatLite::Write$stream_writer$(\n"
+ " $number$, this->$name$(i), output);\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (unsigned int i = 0, n = this->$name$_size(); i < n; i++) {\n"
+ " target = ::google::protobuf::internal::WireFormatLite::\n"
+ " InternalWrite$declared_type$NoVirtualToArray(\n"
+ " $number$, this->$name$(i), false, target);\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "total_size += $tag_size$ * this->$name$_size();\n"
+ "for (int i = 0; i < this->$name$_size(); i++) {\n"
+ " total_size +=\n"
+ " ::google::protobuf::internal::WireFormatLite::$declared_type$SizeNoVirtual(\n"
+ " this->$name$(i));\n"
+ "}\n");
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.h
new file mode 100644
index 0000000000..d8d9279c97
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_message_field.h
@@ -0,0 +1,150 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_MESSAGE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_MESSAGE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class MessageFieldGenerator : public FieldGenerator {
+ public:
+ MessageFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~MessageFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateDependentAccessorDeclarations(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateDependentInlineAccessorDefinitions(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateNonInlineAccessorDefinitions(io::Printer* printer) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ protected:
+ void GenerateArenaManipulationCode(const map<string, string>& variables,
+ io::Printer* printer) const;
+
+ virtual void GenerateGetterDeclaration(io::Printer* printer) const;
+
+ const FieldDescriptor* descriptor_;
+ const bool dependent_field_;
+ map<string, string> variables_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageFieldGenerator);
+};
+
+class MessageOneofFieldGenerator : public MessageFieldGenerator {
+ public:
+ MessageOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~MessageOneofFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateDependentAccessorDeclarations(io::Printer* printer) const;
+ void GenerateDependentInlineAccessorDefinitions(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateNonInlineAccessorDefinitions(io::Printer* printer) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+
+ protected:
+ void GenerateGetterDeclaration(io::Printer* printer) const;
+
+ private:
+ void InternalGenerateInlineAccessorDefinitions(
+ const map<string, string>& variables, io::Printer* printer) const;
+
+ const bool dependent_base_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageOneofFieldGenerator);
+};
+
+class RepeatedMessageFieldGenerator : public FieldGenerator {
+ public:
+ RepeatedMessageFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~RepeatedMessageFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateDependentAccessorDeclarations(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateDependentInlineAccessorDefinitions(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ private:
+ void InternalGenerateTypeDependentAccessorDeclarations(
+ io::Printer* printer) const;
+
+ const FieldDescriptor* descriptor_;
+ const bool dependent_field_;
+ const bool dependent_getter_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedMessageFieldGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_MESSAGE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_options.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_options.h
new file mode 100644
index 0000000000..ee44fb0abc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_options.h
@@ -0,0 +1,69 @@
+// 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: rennie@google.com (Jeffrey Rennie)
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_OPTIONS_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_OPTIONS_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+// Generator options (see generator.cc for a description of each):
+struct Options {
+ Options()
+ : safe_boundary_check(false),
+ proto_h(false),
+ allow_import_public(true),
+ annotate_headers(false),
+ enforce_lite(false) {}
+
+ string dllexport_decl;
+ bool safe_boundary_check;
+ bool proto_h;
+ bool allow_import_public;
+ bool annotate_headers;
+ bool enforce_lite;
+ string annotation_pragma_name;
+ string annotation_guard_name;
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_OPTIONS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_plugin_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_plugin_unittest.cc
new file mode 100644
index 0000000000..34a41d8232
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_plugin_unittest.cc
@@ -0,0 +1,252 @@
+// 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)
+//
+// TODO(kenton): Share code with the versions of this test in other languages?
+// It seemed like parameterizing it would add more complexity than it is
+// worth.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/cpp/cpp_generator.h>
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/printer.h>
+
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+namespace {
+
+class TestGenerator : public CodeGenerator {
+ public:
+ TestGenerator() {}
+ ~TestGenerator() {}
+
+ virtual bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ TryInsert("test.pb.h", "includes", context);
+ TryInsert("test.pb.h", "namespace_scope", context);
+ TryInsert("test.pb.h", "global_scope", context);
+ TryInsert("test.pb.h", "class_scope:foo.Bar", context);
+ TryInsert("test.pb.h", "class_scope:foo.Bar.Baz", context);
+
+ TryInsert("test.pb.cc", "includes", context);
+ TryInsert("test.pb.cc", "namespace_scope", context);
+ TryInsert("test.pb.cc", "global_scope", context);
+
+ // Check field accessors for an optional int32:
+ TryInsert("test.pb.h", "field_get:foo.Bar.optInt", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.optInt", context);
+
+ // Check field accessors for a repeated int32:
+ TryInsert("test.pb.h", "field_get:foo.Bar.repeatedInt", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.repeatedInt", context);
+
+ // Check field accessors for a required string:
+ TryInsert("test.pb.h", "field_get:foo.Bar.requiredString", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.requiredString", context);
+ TryInsert("test.pb.h", "field_set_char:foo.Bar.requiredString", context);
+ TryInsert("test.pb.h", "field_set_pointer:foo.Bar.requiredString", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.requiredString", context);
+ TryInsert("test.pb.h", "field_set_allocated:foo.Bar.requiredString",
+ context);
+ TryInsert("test.pb.h", "field_set_char:foo.Bar.requiredString", context);
+ TryInsert("test.pb.h", "field_set_pointer:foo.Bar.requiredString", context);
+
+ // Check field accessors for a repeated string:
+ TryInsert("test.pb.h", "field_get:foo.Bar.repeatedString", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.repeatedString", context);
+ TryInsert("test.pb.h", "field_set_char:foo.Bar.repeatedString", context);
+ TryInsert("test.pb.h", "field_set_pointer:foo.Bar.repeatedString", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.repeatedString", context);
+ TryInsert("test.pb.h", "field_set_char:foo.Bar.repeatedString", context);
+ TryInsert("test.pb.h", "field_set_pointer:foo.Bar.repeatedString", context);
+
+ // Check field accessors for an int inside oneof{}:
+ TryInsert("test.pb.h", "field_get:foo.Bar.oneOfInt", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.oneOfInt", context);
+
+ // Check field accessors for a string inside oneof{}:
+ TryInsert("test.pb.h", "field_get:foo.Bar.oneOfString", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.oneOfString", context);
+ TryInsert("test.pb.h", "field_set_char:foo.Bar.oneOfString", context);
+ TryInsert("test.pb.h", "field_set_pointer:foo.Bar.oneOfString", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.oneOfString", context);
+ TryInsert("test.pb.h", "field_set_allocated:foo.Bar.oneOfString", context);
+ TryInsert("test.pb.h", "field_set_char:foo.Bar.oneOfString", context);
+ TryInsert("test.pb.h", "field_set_pointer:foo.Bar.oneOfString", context);
+
+ // Check field accessors for an optional message:
+ TryInsert("test.pb.h", "field_get:foo.Bar.optMessage", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.optMessage", context);
+ TryInsert("test.pb.h", "field_set_allocated:foo.Bar.optMessage", context);
+
+ // Check field accessors for a repeated message:
+ TryInsert("test.pb.h", "field_add:foo.Bar.repeatedMessage", context);
+ TryInsert("test.pb.h", "field_get:foo.Bar.repeatedMessage", context);
+ TryInsert("test.pb.h", "field_list:foo.Bar.repeatedMessage", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.repeatedMessage", context);
+ TryInsert("test.pb.h", "field_mutable_list:foo.Bar.repeatedMessage",
+ context);
+
+ // Check field accessors for a message inside oneof{}:
+ TryInsert("test.pb.h", "field_get:foo.Bar.oneOfMessage", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.oneOfMessage", context);
+ TryInsert("test.pb.h", "field_set_allocated:foo.Bar.oneOfMessage", context);
+
+ // Check field accessors for an optional enum:
+ TryInsert("test.pb.h", "field_get:foo.Bar.optEnum", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.optEnum", context);
+
+ // Check field accessors for a repeated enum:
+ TryInsert("test.pb.h", "field_get:foo.Bar.repeatedEnum", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.repeatedEnum", context);
+ TryInsert("test.pb.h", "field_add:foo.Bar.repeatedEnum", context);
+ TryInsert("test.pb.h", "field_list:foo.Bar.repeatedEnum", context);
+ TryInsert("test.pb.h", "field_mutable_list:foo.Bar.repeatedEnum", context);
+
+ // Check field accessors for an enum inside oneof{}:
+ TryInsert("test.pb.h", "field_get:foo.Bar.oneOfEnum", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.oneOfEnum", context);
+
+ // Check field accessors for a required cord:
+ TryInsert("test.pb.h", "field_get:foo.Bar.requiredCord", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.requiredCord", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.requiredCord", context);
+
+ // Check field accessors for a repeated cord:
+ TryInsert("test.pb.h", "field_get:foo.Bar.repeatedCord", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.repeatedCord", context);
+ TryInsert("test.pb.h", "field_add:foo.Bar.repeatedCord", context);
+ TryInsert("test.pb.h", "field_list:foo.Bar.repeatedCord", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.repeatedCord", context);
+ TryInsert("test.pb.h", "field_mutable_list:foo.Bar.repeatedCord", context);
+
+ // Check field accessors for a cord inside oneof{}:
+ TryInsert("test.pb.h", "field_get:foo.Bar.oneOfCord", context);
+ TryInsert("test.pb.h", "field_set:foo.Bar.oneOfCord", context);
+ TryInsert("test.pb.h", "field_mutable:foo.Bar.oneOfCord", context);
+
+ return true;
+ }
+
+ void TryInsert(const string& filename, const string& insertion_point,
+ GeneratorContext* context) const {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->OpenForInsert(filename, insertion_point));
+ io::Printer printer(output.get(), '$');
+ printer.Print("// inserted $name$\n", "name", insertion_point);
+ }
+};
+
+// This test verifies that all the expected insertion points exist. It does
+// not verify that they are correctly-placed; that would require actually
+// compiling the output which is a bit more than I care to do for this test.
+TEST(CppPluginTest, PluginTest) {
+ GOOGLE_CHECK_OK(File::SetContents(TestTempDir() + "/test.proto",
+ "syntax = \"proto2\";\n"
+ "package foo;\n"
+ "\n"
+ "enum Thud { VALUE = 0; }\n"
+ "\n"
+ "message Bar {\n"
+ " message Baz {}\n"
+ " optional int32 optInt = 1;\n"
+ " repeated int32 repeatedInt = 2;\n"
+ "\n"
+ " required string requiredString = 3;\n"
+ " repeated string repeatedString = 4;\n"
+ "\n"
+ " optional Baz optMessage = 6;\n"
+ " repeated Baz repeatedMessage = 7;\n"
+ "\n"
+ " optional Thud optEnum = 8;\n"
+ " repeated Thud repeatedEnum = 9;\n"
+ "\n"
+ " required string requiredCord = 10 [\n"
+ " ctype = CORD\n"
+ " ];\n"
+ " repeated string repeatedCord = 11 [\n"
+ " ctype = CORD\n"
+ " ];\n"
+ "\n"
+ " oneof Qux {\n"
+ " int64 oneOfInt = 20;\n"
+ " string oneOfString = 21;\n"
+ " Baz oneOfMessage = 22;\n"
+ " Thud oneOfEnum = 23;"
+ " string oneOfCord = 24 [\n"
+ " ctype = CORD\n"
+ " ];\n"
+ " }\n"
+ "}\n",
+ true));
+
+ google::protobuf::compiler::CommandLineInterface cli;
+ cli.SetInputsAreProtoPathRelative(true);
+
+ CppGenerator cpp_generator;
+ TestGenerator test_generator;
+ cli.RegisterGenerator("--cpp_out", &cpp_generator, "");
+ cli.RegisterGenerator("--test_out", &test_generator, "");
+
+ string proto_path = "-I" + TestTempDir();
+ string cpp_out = "--cpp_out=" + TestTempDir();
+ string test_out = "--test_out=" + TestTempDir();
+
+ const char* argv[] = {
+ "protoc",
+ proto_path.c_str(),
+ cpp_out.c_str(),
+ test_out.c_str(),
+ "test.proto"
+ };
+
+ EXPECT_EQ(0, cli.Run(5, argv));
+}
+
+} // namespace
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.cc
new file mode 100644
index 0000000000..650f0381e5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.cc
@@ -0,0 +1,458 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_primitive_field.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+using internal::WireFormatLite;
+
+namespace {
+
+// For encodings with fixed sizes, returns that size in bytes. Otherwise
+// returns -1.
+int FixedSize(FieldDescriptor::Type type) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32 : return -1;
+ case FieldDescriptor::TYPE_INT64 : return -1;
+ case FieldDescriptor::TYPE_UINT32 : return -1;
+ case FieldDescriptor::TYPE_UINT64 : return -1;
+ case FieldDescriptor::TYPE_SINT32 : return -1;
+ case FieldDescriptor::TYPE_SINT64 : return -1;
+ case FieldDescriptor::TYPE_FIXED32 : return WireFormatLite::kFixed32Size;
+ case FieldDescriptor::TYPE_FIXED64 : return WireFormatLite::kFixed64Size;
+ case FieldDescriptor::TYPE_SFIXED32: return WireFormatLite::kSFixed32Size;
+ case FieldDescriptor::TYPE_SFIXED64: return WireFormatLite::kSFixed64Size;
+ case FieldDescriptor::TYPE_FLOAT : return WireFormatLite::kFloatSize;
+ case FieldDescriptor::TYPE_DOUBLE : return WireFormatLite::kDoubleSize;
+
+ case FieldDescriptor::TYPE_BOOL : return WireFormatLite::kBoolSize;
+ case FieldDescriptor::TYPE_ENUM : return -1;
+
+ case FieldDescriptor::TYPE_STRING : return -1;
+ case FieldDescriptor::TYPE_BYTES : return -1;
+ case FieldDescriptor::TYPE_GROUP : return -1;
+ case FieldDescriptor::TYPE_MESSAGE : return -1;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return -1;
+}
+
+void SetPrimitiveVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables,
+ const Options& options) {
+ SetCommonFieldVariables(descriptor, variables, options);
+ (*variables)["type"] = PrimitiveTypeName(descriptor->cpp_type());
+ (*variables)["default"] = DefaultValue(descriptor);
+ (*variables)["tag"] = SimpleItoa(internal::WireFormat::MakeTag(descriptor));
+ int fixed_size = FixedSize(descriptor->type());
+ if (fixed_size != -1) {
+ (*variables)["fixed_size"] = SimpleItoa(fixed_size);
+ }
+ (*variables)["wire_format_field_type"] =
+ "::google::protobuf::internal::WireFormatLite::" + FieldDescriptorProto_Type_Name(
+ static_cast<FieldDescriptorProto_Type>(descriptor->type()));
+ (*variables)["full_name"] = descriptor->full_name();
+}
+
+} // namespace
+
+// ===================================================================
+
+PrimitiveFieldGenerator::PrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : FieldGenerator(options), descriptor_(descriptor) {
+ SetPrimitiveVariables(descriptor, &variables_, options);
+}
+
+PrimitiveFieldGenerator::~PrimitiveFieldGenerator() {}
+
+void PrimitiveFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_, "$type$ $name$_;\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$deprecated_attr$$type$ $name$() const;\n"
+ "$deprecated_attr$void set_$name$($type$ value);\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer, bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ $type$ $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$($type$ value) {\n"
+ " $set_hasbit$\n"
+ " $name$_ = value;\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_, "set_$name$(from.$name$());\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "std::swap($name$_, other->$name$_);\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ printer->Print(variables_,
+ "DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<\n"
+ " $type$, $wire_format_field_type$>(\n"
+ " input, &$name$_)));\n"
+ "$set_hasbit$\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ printer->Print(variables_,
+ "::google::protobuf::internal::WireFormatLite::Write$declared_type$("
+ "$number$, this->$name$(), output);\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ printer->Print(variables_,
+ "target = ::google::protobuf::internal::WireFormatLite::Write$declared_type$ToArray("
+ "$number$, this->$name$(), target);\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ int fixed_size = FixedSize(descriptor_->type());
+ if (fixed_size == -1) {
+ printer->Print(variables_,
+ "total_size += $tag_size$ +\n"
+ " ::google::protobuf::internal::WireFormatLite::$declared_type$Size(\n"
+ " this->$name$());\n");
+ } else {
+ printer->Print(variables_,
+ "total_size += $tag_size$ + $fixed_size$;\n");
+ }
+}
+
+// ===================================================================
+
+PrimitiveOneofFieldGenerator::
+PrimitiveOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : PrimitiveFieldGenerator(descriptor, options) {
+ SetCommonOneofFieldVariables(descriptor, &variables_);
+}
+
+PrimitiveOneofFieldGenerator::~PrimitiveOneofFieldGenerator() {}
+
+void PrimitiveOneofFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer, bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ $type$ $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " if (has_$name$()) {\n"
+ " return $oneof_prefix$$name$_;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$($type$ value) {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " }\n"
+ " $oneof_prefix$$name$_ = value;\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n");
+}
+
+void PrimitiveOneofFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$oneof_prefix$$name$_ = $default$;\n");
+}
+
+void PrimitiveOneofFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ // Don't print any swapping code. Swapping the union will swap this field.
+}
+
+void PrimitiveOneofFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ " $classname$_default_oneof_instance_->$name$_ = $default$;\n");
+}
+
+void PrimitiveOneofFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ printer->Print(variables_,
+ "clear_$oneof_name$();\n"
+ "DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<\n"
+ " $type$, $wire_format_field_type$>(\n"
+ " input, &$oneof_prefix$$name$_)));\n"
+ "set_has_$name$();\n");
+}
+
+// ===================================================================
+
+RepeatedPrimitiveFieldGenerator::RepeatedPrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : FieldGenerator(options), descriptor_(descriptor) {
+ SetPrimitiveVariables(descriptor, &variables_, options);
+
+ if (descriptor->is_packed()) {
+ variables_["packed_reader"] = "ReadPackedPrimitive";
+ variables_["repeated_reader"] = "ReadRepeatedPrimitiveNoInline";
+ } else {
+ variables_["packed_reader"] = "ReadPackedPrimitiveNoInline";
+ variables_["repeated_reader"] = "ReadRepeatedPrimitive";
+ }
+}
+
+RepeatedPrimitiveFieldGenerator::~RepeatedPrimitiveFieldGenerator() {}
+
+void RepeatedPrimitiveFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "::google::protobuf::RepeatedField< $type$ > $name$_;\n");
+ if (descriptor_->is_packed() &&
+ HasGeneratedMethods(descriptor_->file(), options_)) {
+ printer->Print(variables_,
+ "mutable int _$name$_cached_byte_size_;\n");
+ }
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$deprecated_attr$$type$ $name$(int index) const;\n"
+ "$deprecated_attr$void set_$name$(int index, $type$ value);\n"
+ "$deprecated_attr$void add_$name$($type$ value);\n");
+ printer->Print(variables_,
+ "$deprecated_attr$const ::google::protobuf::RepeatedField< $type$ >&\n"
+ " $name$() const;\n"
+ "$deprecated_attr$::google::protobuf::RepeatedField< $type$ >*\n"
+ " mutable_$name$();\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer, bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ $type$ $classname$::$name$(int index) const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $name$_.Get(index);\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(int index, $type$ value) {\n"
+ " $name$_.Set(index, value);\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::add_$name$($type$ value) {\n"
+ " $name$_.Add(value);\n"
+ " // @@protoc_insertion_point(field_add:$full_name$)\n"
+ "}\n");
+ printer->Print(variables,
+ "$inline$ const ::google::protobuf::RepeatedField< $type$ >&\n"
+ "$classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_list:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "$inline$ ::google::protobuf::RepeatedField< $type$ >*\n"
+ "$classname$::mutable_$name$() {\n"
+ " // @@protoc_insertion_point(field_mutable_list:$full_name$)\n"
+ " return &$name$_;\n"
+ "}\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.Clear();\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.MergeFrom(from.$name$_);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.UnsafeArenaSwap(&other->$name$_);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ // Not needed for repeated fields.
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ printer->Print(variables_,
+ "DO_((::google::protobuf::internal::WireFormatLite::$repeated_reader$<\n"
+ " $type$, $wire_format_field_type$>(\n"
+ " $tag_size$, $tag$, input, this->mutable_$name$())));\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateMergeFromCodedStreamWithPacking(io::Printer* printer) const {
+ printer->Print(variables_,
+ "DO_((::google::protobuf::internal::WireFormatLite::$packed_reader$<\n"
+ " $type$, $wire_format_field_type$>(\n"
+ " input, this->mutable_$name$())));\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ if (descriptor_->is_packed()) {
+ // Write the tag and the size.
+ printer->Print(variables_,
+ "if (this->$name$_size() > 0) {\n"
+ " ::google::protobuf::internal::WireFormatLite::WriteTag("
+ "$number$, "
+ "::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED, "
+ "output);\n"
+ " output->WriteVarint32(_$name$_cached_byte_size_);\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n");
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ " ::google::protobuf::internal::WireFormatLite::Write$declared_type$NoTag(\n"
+ " this->$name$(i), output);\n");
+ } else {
+ printer->Print(variables_,
+ " ::google::protobuf::internal::WireFormatLite::Write$declared_type$(\n"
+ " $number$, this->$name$(i), output);\n");
+ }
+ printer->Print("}\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ if (descriptor_->is_packed()) {
+ // Write the tag and the size.
+ printer->Print(variables_,
+ "if (this->$name$_size() > 0) {\n"
+ " target = ::google::protobuf::internal::WireFormatLite::WriteTagToArray(\n"
+ " $number$,\n"
+ " ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED,\n"
+ " target);\n"
+ " target = ::google::protobuf::io::CodedOutputStream::WriteVarint32ToArray(\n"
+ " _$name$_cached_byte_size_, target);\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n");
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ " target = ::google::protobuf::internal::WireFormatLite::\n"
+ " Write$declared_type$NoTagToArray(this->$name$(i), target);\n");
+ } else {
+ printer->Print(variables_,
+ " target = ::google::protobuf::internal::WireFormatLite::\n"
+ " Write$declared_type$ToArray($number$, this->$name$(i), target);\n");
+ }
+ printer->Print("}\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "{\n"
+ " int data_size = 0;\n");
+ printer->Indent();
+ int fixed_size = FixedSize(descriptor_->type());
+ if (fixed_size == -1) {
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n"
+ " data_size += ::google::protobuf::internal::WireFormatLite::\n"
+ " $declared_type$Size(this->$name$(i));\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "data_size = $fixed_size$ * this->$name$_size();\n");
+ }
+
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ "if (data_size > 0) {\n"
+ " total_size += $tag_size$ +\n"
+ " ::google::protobuf::internal::WireFormatLite::Int32Size(data_size);\n"
+ "}\n"
+ "GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();\n"
+ "_$name$_cached_byte_size_ = data_size;\n"
+ "GOOGLE_SAFE_CONCURRENT_WRITES_END();\n"
+ "total_size += data_size;\n");
+ } else {
+ printer->Print(variables_,
+ "total_size += $tag_size$ * this->$name$_size() + data_size;\n");
+ }
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.h
new file mode 100644
index 0000000000..655ebde468
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_primitive_field.h
@@ -0,0 +1,126 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_PRIMITIVE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_PRIMITIVE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class PrimitiveFieldGenerator : public FieldGenerator {
+ public:
+ PrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~PrimitiveFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveFieldGenerator);
+};
+
+class PrimitiveOneofFieldGenerator : public PrimitiveFieldGenerator {
+ public:
+ PrimitiveOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~PrimitiveOneofFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveOneofFieldGenerator);
+};
+
+class RepeatedPrimitiveFieldGenerator : public FieldGenerator {
+ public:
+ RepeatedPrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~RepeatedPrimitiveFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateMergeFromCodedStreamWithPacking(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedPrimitiveFieldGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_PRIMITIVE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.cc
new file mode 100644
index 0000000000..6030f7ce1b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.cc
@@ -0,0 +1,336 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_service.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+ServiceGenerator::ServiceGenerator(const ServiceDescriptor* descriptor,
+ const Options& options)
+ : descriptor_(descriptor) {
+ vars_["classname"] = descriptor_->name();
+ vars_["full_name"] = descriptor_->full_name();
+ if (options.dllexport_decl.empty()) {
+ vars_["dllexport"] = "";
+ } else {
+ vars_["dllexport"] = options.dllexport_decl + " ";
+ }
+}
+
+ServiceGenerator::~ServiceGenerator() {}
+
+void ServiceGenerator::GenerateDeclarations(io::Printer* printer) {
+ // Forward-declare the stub type.
+ printer->Print(vars_,
+ "class $classname$_Stub;\n"
+ "\n");
+
+ GenerateInterface(printer);
+ GenerateStubDefinition(printer);
+}
+
+void ServiceGenerator::GenerateInterface(io::Printer* printer) {
+ printer->Print(vars_,
+ "class $dllexport$$classname$ : public ::google::protobuf::Service {\n"
+ " protected:\n"
+ " // This class should be treated as an abstract interface.\n"
+ " inline $classname$() {};\n"
+ " public:\n"
+ " virtual ~$classname$();\n");
+ printer->Indent();
+
+ printer->Print(vars_,
+ "\n"
+ "typedef $classname$_Stub Stub;\n"
+ "\n"
+ "static const ::google::protobuf::ServiceDescriptor* descriptor();\n"
+ "\n");
+
+ GenerateMethodSignatures(VIRTUAL, printer);
+
+ printer->Print(
+ "\n"
+ "// implements Service ----------------------------------------------\n"
+ "\n"
+ "const ::google::protobuf::ServiceDescriptor* GetDescriptor();\n"
+ "void CallMethod(const ::google::protobuf::MethodDescriptor* method,\n"
+ " ::google::protobuf::RpcController* controller,\n"
+ " const ::google::protobuf::Message* request,\n"
+ " ::google::protobuf::Message* response,\n"
+ " ::google::protobuf::Closure* done);\n"
+ "const ::google::protobuf::Message& GetRequestPrototype(\n"
+ " const ::google::protobuf::MethodDescriptor* method) const;\n"
+ "const ::google::protobuf::Message& GetResponsePrototype(\n"
+ " const ::google::protobuf::MethodDescriptor* method) const;\n");
+
+ printer->Outdent();
+ printer->Print(vars_,
+ "\n"
+ " private:\n"
+ " GOOGLE_DISALLOW_EVIL_CONSTRUCTORS($classname$);\n"
+ "};\n"
+ "\n");
+}
+
+void ServiceGenerator::GenerateStubDefinition(io::Printer* printer) {
+ printer->Print(vars_,
+ "class $dllexport$$classname$_Stub : public $classname$ {\n"
+ " public:\n");
+
+ printer->Indent();
+
+ printer->Print(vars_,
+ "$classname$_Stub(::google::protobuf::RpcChannel* channel);\n"
+ "$classname$_Stub(::google::protobuf::RpcChannel* channel,\n"
+ " ::google::protobuf::Service::ChannelOwnership ownership);\n"
+ "~$classname$_Stub();\n"
+ "\n"
+ "inline ::google::protobuf::RpcChannel* channel() { return channel_; }\n"
+ "\n"
+ "// implements $classname$ ------------------------------------------\n"
+ "\n");
+
+ GenerateMethodSignatures(NON_VIRTUAL, printer);
+
+ printer->Outdent();
+ printer->Print(vars_,
+ " private:\n"
+ " ::google::protobuf::RpcChannel* channel_;\n"
+ " bool owns_channel_;\n"
+ " GOOGLE_DISALLOW_EVIL_CONSTRUCTORS($classname$_Stub);\n"
+ "};\n"
+ "\n");
+}
+
+void ServiceGenerator::GenerateMethodSignatures(
+ VirtualOrNon virtual_or_non, io::Printer* printer) {
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ map<string, string> sub_vars;
+ sub_vars["name"] = method->name();
+ sub_vars["input_type"] = ClassName(method->input_type(), true);
+ sub_vars["output_type"] = ClassName(method->output_type(), true);
+ sub_vars["virtual"] = virtual_or_non == VIRTUAL ? "virtual " : "";
+
+ printer->Print(sub_vars,
+ "$virtual$void $name$(::google::protobuf::RpcController* controller,\n"
+ " const $input_type$* request,\n"
+ " $output_type$* response,\n"
+ " ::google::protobuf::Closure* done);\n");
+ }
+}
+
+// ===================================================================
+
+void ServiceGenerator::GenerateDescriptorInitializer(
+ io::Printer* printer, int index) {
+ map<string, string> vars;
+ vars["classname"] = descriptor_->name();
+ vars["index"] = SimpleItoa(index);
+
+ printer->Print(vars,
+ "$classname$_descriptor_ = file->service($index$);\n");
+}
+
+// ===================================================================
+
+void ServiceGenerator::GenerateImplementation(io::Printer* printer) {
+ printer->Print(vars_,
+ "$classname$::~$classname$() {}\n"
+ "\n"
+ "const ::google::protobuf::ServiceDescriptor* $classname$::descriptor() {\n"
+ " protobuf_AssignDescriptorsOnce();\n"
+ " return $classname$_descriptor_;\n"
+ "}\n"
+ "\n"
+ "const ::google::protobuf::ServiceDescriptor* $classname$::GetDescriptor() {\n"
+ " protobuf_AssignDescriptorsOnce();\n"
+ " return $classname$_descriptor_;\n"
+ "}\n"
+ "\n");
+
+ // Generate methods of the interface.
+ GenerateNotImplementedMethods(printer);
+ GenerateCallMethod(printer);
+ GenerateGetPrototype(REQUEST, printer);
+ GenerateGetPrototype(RESPONSE, printer);
+
+ // Generate stub implementation.
+ printer->Print(vars_,
+ "$classname$_Stub::$classname$_Stub(::google::protobuf::RpcChannel* channel)\n"
+ " : channel_(channel), owns_channel_(false) {}\n"
+ "$classname$_Stub::$classname$_Stub(\n"
+ " ::google::protobuf::RpcChannel* channel,\n"
+ " ::google::protobuf::Service::ChannelOwnership ownership)\n"
+ " : channel_(channel),\n"
+ " owns_channel_(ownership == ::google::protobuf::Service::STUB_OWNS_CHANNEL) {}\n"
+ "$classname$_Stub::~$classname$_Stub() {\n"
+ " if (owns_channel_) delete channel_;\n"
+ "}\n"
+ "\n");
+
+ GenerateStubMethods(printer);
+}
+
+void ServiceGenerator::GenerateNotImplementedMethods(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ map<string, string> sub_vars;
+ sub_vars["classname"] = descriptor_->name();
+ sub_vars["name"] = method->name();
+ sub_vars["index"] = SimpleItoa(i);
+ sub_vars["input_type"] = ClassName(method->input_type(), true);
+ sub_vars["output_type"] = ClassName(method->output_type(), true);
+
+ printer->Print(sub_vars,
+ "void $classname$::$name$(::google::protobuf::RpcController* controller,\n"
+ " const $input_type$*,\n"
+ " $output_type$*,\n"
+ " ::google::protobuf::Closure* done) {\n"
+ " controller->SetFailed(\"Method $name$() not implemented.\");\n"
+ " done->Run();\n"
+ "}\n"
+ "\n");
+ }
+}
+
+void ServiceGenerator::GenerateCallMethod(io::Printer* printer) {
+ printer->Print(vars_,
+ "void $classname$::CallMethod(const ::google::protobuf::MethodDescriptor* method,\n"
+ " ::google::protobuf::RpcController* controller,\n"
+ " const ::google::protobuf::Message* request,\n"
+ " ::google::protobuf::Message* response,\n"
+ " ::google::protobuf::Closure* done) {\n"
+ " GOOGLE_DCHECK_EQ(method->service(), $classname$_descriptor_);\n"
+ " switch(method->index()) {\n");
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ map<string, string> sub_vars;
+ sub_vars["name"] = method->name();
+ sub_vars["index"] = SimpleItoa(i);
+ sub_vars["input_type"] = ClassName(method->input_type(), true);
+ sub_vars["output_type"] = ClassName(method->output_type(), true);
+
+ // Note: down_cast does not work here because it only works on pointers,
+ // not references.
+ printer->Print(sub_vars,
+ " case $index$:\n"
+ " $name$(controller,\n"
+ " ::google::protobuf::down_cast<const $input_type$*>(request),\n"
+ " ::google::protobuf::down_cast< $output_type$*>(response),\n"
+ " done);\n"
+ " break;\n");
+ }
+
+ printer->Print(vars_,
+ " default:\n"
+ " GOOGLE_LOG(FATAL) << \"Bad method index; this should never happen.\";\n"
+ " break;\n"
+ " }\n"
+ "}\n"
+ "\n");
+}
+
+void ServiceGenerator::GenerateGetPrototype(RequestOrResponse which,
+ io::Printer* printer) {
+ if (which == REQUEST) {
+ printer->Print(vars_,
+ "const ::google::protobuf::Message& $classname$::GetRequestPrototype(\n");
+ } else {
+ printer->Print(vars_,
+ "const ::google::protobuf::Message& $classname$::GetResponsePrototype(\n");
+ }
+
+ printer->Print(vars_,
+ " const ::google::protobuf::MethodDescriptor* method) const {\n"
+ " GOOGLE_DCHECK_EQ(method->service(), descriptor());\n"
+ " switch(method->index()) {\n");
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ const Descriptor* type =
+ (which == REQUEST) ? method->input_type() : method->output_type();
+
+ map<string, string> sub_vars;
+ sub_vars["index"] = SimpleItoa(i);
+ sub_vars["type"] = ClassName(type, true);
+
+ printer->Print(sub_vars,
+ " case $index$:\n"
+ " return $type$::default_instance();\n");
+ }
+
+ printer->Print(
+ " default:\n"
+ " GOOGLE_LOG(FATAL) << \"Bad method index; this should never happen.\";\n"
+ " return *::google::protobuf::MessageFactory::generated_factory()\n"
+ " ->GetPrototype(method->$input_or_output$_type());\n"
+ " }\n"
+ "}\n"
+ "\n",
+ "input_or_output", which == REQUEST ? "input" : "output");
+}
+
+void ServiceGenerator::GenerateStubMethods(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ map<string, string> sub_vars;
+ sub_vars["classname"] = descriptor_->name();
+ sub_vars["name"] = method->name();
+ sub_vars["index"] = SimpleItoa(i);
+ sub_vars["input_type"] = ClassName(method->input_type(), true);
+ sub_vars["output_type"] = ClassName(method->output_type(), true);
+
+ printer->Print(sub_vars,
+ "void $classname$_Stub::$name$(::google::protobuf::RpcController* controller,\n"
+ " const $input_type$* request,\n"
+ " $output_type$* response,\n"
+ " ::google::protobuf::Closure* done) {\n"
+ " channel_->CallMethod(descriptor()->method($index$),\n"
+ " controller, request, response, done);\n"
+ "}\n");
+ }
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.h
new file mode 100644
index 0000000000..ede2fd80e6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_service.h
@@ -0,0 +1,118 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_SERVICE_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_SERVICE_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_options.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class ServiceGenerator {
+ public:
+ // See generator.cc for the meaning of dllexport_decl.
+ explicit ServiceGenerator(const ServiceDescriptor* descriptor,
+ const Options& options);
+ ~ServiceGenerator();
+
+ // Header stuff.
+
+ // Generate the class definitions for the service's interface and the
+ // stub implementation.
+ void GenerateDeclarations(io::Printer* printer);
+
+ // Source file stuff.
+
+ // Generate code that initializes the global variable storing the service's
+ // descriptor.
+ void GenerateDescriptorInitializer(io::Printer* printer, int index);
+
+ // Generate implementations of everything declared by GenerateDeclarations().
+ void GenerateImplementation(io::Printer* printer);
+
+ private:
+ enum RequestOrResponse { REQUEST, RESPONSE };
+ enum VirtualOrNon { VIRTUAL, NON_VIRTUAL };
+
+ // Header stuff.
+
+ // Generate the service abstract interface.
+ void GenerateInterface(io::Printer* printer);
+
+ // Generate the stub class definition.
+ void GenerateStubDefinition(io::Printer* printer);
+
+ // Prints signatures for all methods in the
+ void GenerateMethodSignatures(VirtualOrNon virtual_or_non,
+ io::Printer* printer);
+
+ // Source file stuff.
+
+ // Generate the default implementations of the service methods, which
+ // produce a "not implemented" error.
+ void GenerateNotImplementedMethods(io::Printer* printer);
+
+ // Generate the CallMethod() method of the service.
+ void GenerateCallMethod(io::Printer* printer);
+
+ // Generate the Get{Request,Response}Prototype() methods.
+ void GenerateGetPrototype(RequestOrResponse which, io::Printer* printer);
+
+ // Generate the stub's implementations of the service methods.
+ void GenerateStubMethods(io::Printer* printer);
+
+ const ServiceDescriptor* descriptor_;
+ map<string, string> vars_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ServiceGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_SERVICE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.cc
new file mode 100644
index 0000000000..1d7434578c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.cc
@@ -0,0 +1,871 @@
+// 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.
+
+#include <google/protobuf/compiler/cpp/cpp_string_field.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+namespace {
+
+void SetStringVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables,
+ const Options& options) {
+ SetCommonFieldVariables(descriptor, variables, options);
+ (*variables)["default"] = DefaultValue(descriptor);
+ (*variables)["default_length"] =
+ SimpleItoa(descriptor->default_value_string().length());
+ string default_variable_string =
+ descriptor->default_value_string().empty()
+ ? "&::google::protobuf::internal::GetEmptyStringAlreadyInited()"
+ : "_default_" + FieldName(descriptor) + "_";
+ (*variables)["default_variable"] = default_variable_string;
+ (*variables)["default_value_init"] =
+ descriptor->default_value_string().empty()
+ ? "" : "*" + default_variable_string;
+ (*variables)["pointer_type"] =
+ descriptor->type() == FieldDescriptor::TYPE_BYTES ? "void" : "char";
+ // NOTE: Escaped here to unblock proto1->proto2 migration.
+ // TODO(liujisi): Extend this to apply for other conflicting methods.
+ (*variables)["release_name"] =
+ SafeFunctionName(descriptor->containing_type(),
+ descriptor, "release_");
+ (*variables)["full_name"] = descriptor->full_name();
+
+ (*variables)["string_piece"] = "::std::string";
+}
+
+} // namespace
+
+// ===================================================================
+
+StringFieldGenerator::StringFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : FieldGenerator(options), descriptor_(descriptor) {
+ SetStringVariables(descriptor, &variables_, options);
+}
+
+StringFieldGenerator::~StringFieldGenerator() {}
+
+void StringFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ // N.B. that we continue to use |ArenaStringPtr| instead of |string*| for
+ // string fields, even when SupportArenas(descriptor_) == false. Why?
+ // The simple answer is to avoid unmaintainable complexity. The reflection
+ // code assumes ArenaStringPtrs. These are *almost* in-memory-compatible with
+ // string*, except for the pointer tags and related ownership semantics. We
+ // could modify the runtime code to use string* for the not-supporting-arenas
+ // case, but this would require a way to detect which type of class was
+ // generated (adding overhead and complexity to GeneratedMessageReflection)
+ // and littering the runtime code paths with conditionals. It's simpler to
+ // stick with this but use lightweight accessors that assume arena == NULL.
+ // There should be very little overhead anyway because it's just a tagged
+ // pointer in-memory.
+ printer->Print(variables_, "::google::protobuf::internal::ArenaStringPtr $name$_;\n");
+}
+
+void StringFieldGenerator::
+GenerateStaticMembers(io::Printer* printer) const {
+ if (!descriptor_->default_value_string().empty()) {
+ printer->Print(variables_, "static ::std::string* $default_variable$;\n");
+ }
+}
+
+void StringFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ // If we're using StringFieldGenerator for a field with a ctype, it's
+ // because that ctype isn't actually implemented. In particular, this is
+ // true of ctype=CORD and ctype=STRING_PIECE in the open source release.
+ // We aren't releasing Cord because it has too many Google-specific
+ // dependencies and we aren't releasing StringPiece because it's hardly
+ // useful outside of Google and because it would get confusing to have
+ // multiple instances of the StringPiece class in different libraries (PCRE
+ // already includes it for their C++ bindings, which came from Google).
+ //
+ // In any case, we make all the accessors private while still actually
+ // using a string to represent the field internally. This way, we can
+ // guarantee that if we do ever implement the ctype, it won't break any
+ // existing users who might be -- for whatever reason -- already using .proto
+ // files that applied the ctype. The field can still be accessed via the
+ // reflection interface since the reflection interface is independent of
+ // the string's underlying representation.
+
+ bool unknown_ctype =
+ descriptor_->options().ctype() != EffectiveStringCType(descriptor_);
+
+ if (unknown_ctype) {
+ printer->Outdent();
+ printer->Print(
+ " private:\n"
+ " // Hidden due to unknown ctype option.\n");
+ printer->Indent();
+ }
+
+ printer->Print(variables_,
+ "$deprecated_attr$const ::std::string& $name$() const;\n"
+ "$deprecated_attr$void set_$name$(const ::std::string& value);\n"
+ "$deprecated_attr$void set_$name$(const char* value);\n"
+ "$deprecated_attr$void set_$name$(const $pointer_type$* value, size_t size)"
+ ";\n"
+ "$deprecated_attr$::std::string* mutable_$name$();\n"
+ "$deprecated_attr$::std::string* $release_name$();\n"
+ "$deprecated_attr$void set_allocated_$name$(::std::string* $name$);\n");
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ "$deprecated_attr$::std::string* unsafe_arena_release_$name$();\n"
+ "$deprecated_attr$void unsafe_arena_set_allocated_$name$(\n"
+ " ::std::string* $name$);\n");
+ }
+
+
+ if (unknown_ctype) {
+ printer->Outdent();
+ printer->Print(" public:\n");
+ printer->Indent();
+ }
+}
+
+void StringFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables,
+ "$inline$ const ::std::string& $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $name$_.Get($default_variable$);\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const ::std::string& value) {\n"
+ " $set_hasbit$\n"
+ " $name$_.Set($default_variable$, value, GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const char* value) {\n"
+ " $set_hasbit$\n"
+ " $name$_.Set($default_variable$, $string_piece$(value),\n"
+ " GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_set_char:$full_name$)\n"
+ "}\n"
+ "$inline$ "
+ "void $classname$::set_$name$(const $pointer_type$* value,\n"
+ " size_t size) {\n"
+ " $set_hasbit$\n"
+ " $name$_.Set($default_variable$, $string_piece$(\n"
+ " reinterpret_cast<const char*>(value), size), GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_set_pointer:$full_name$)\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::mutable_$name$() {\n"
+ " $set_hasbit$\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_.Mutable($default_variable$, GetArenaNoVirtual());\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " $clear_hasbit$\n"
+ " return $name$_.Release($default_variable$, GetArenaNoVirtual());\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::unsafe_arena_release_$name$() {\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_release:$full_name$)\n"
+ " GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);\n"
+ " $clear_hasbit$\n"
+ " return $name$_.UnsafeArenaRelease($default_variable$,\n"
+ " GetArenaNoVirtual());\n"
+ "}\n"
+ "$inline$ void $classname$::set_allocated_$name$(::std::string* $name$) {\n"
+ " if ($name$ != NULL) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ " $name$_.SetAllocated($default_variable$, $name$,\n"
+ " GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::unsafe_arena_set_allocated_$name$(\n"
+ " ::std::string* $name$) {\n"
+ " GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);\n"
+ " if ($name$ != NULL) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ " $name$_.UnsafeArenaSetAllocated($default_variable$,\n"
+ " $name$, GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_set_allocated:"
+ "$full_name$)\n"
+ "}\n");
+ } else {
+ // No-arena case.
+ printer->Print(variables,
+ "$inline$ const ::std::string& $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $name$_.GetNoArena($default_variable$);\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const ::std::string& value) {\n"
+ " $set_hasbit$\n"
+ " $name$_.SetNoArena($default_variable$, value);\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const char* value) {\n"
+ " $set_hasbit$\n"
+ " $name$_.SetNoArena($default_variable$, $string_piece$(value));\n"
+ " // @@protoc_insertion_point(field_set_char:$full_name$)\n"
+ "}\n"
+ "$inline$ "
+ "void $classname$::set_$name$(const $pointer_type$* value, "
+ "size_t size) {\n"
+ " $set_hasbit$\n"
+ " $name$_.SetNoArena($default_variable$,\n"
+ " $string_piece$(reinterpret_cast<const char*>(value), size));\n"
+ " // @@protoc_insertion_point(field_set_pointer:$full_name$)\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::mutable_$name$() {\n"
+ " $set_hasbit$\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_.MutableNoArena($default_variable$);\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " $clear_hasbit$\n"
+ " return $name$_.ReleaseNoArena($default_variable$);\n"
+ "}\n"
+ "$inline$ void $classname$::set_allocated_$name$(::std::string* $name$) {\n"
+ " if ($name$ != NULL) {\n"
+ " $set_hasbit$\n"
+ " } else {\n"
+ " $clear_hasbit$\n"
+ " }\n"
+ " $name$_.SetAllocatedNoArena($default_variable$, $name$);\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n");
+ }
+}
+
+void StringFieldGenerator::
+GenerateNonInlineAccessorDefinitions(io::Printer* printer) const {
+ if (!descriptor_->default_value_string().empty()) {
+ // Initialized in GenerateDefaultInstanceAllocator.
+ printer->Print(variables_,
+ "::std::string* $classname$::$default_variable$ = NULL;\n");
+ }
+}
+
+void StringFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ // Two-dimension specialization here: supporting arenas or not, and default
+ // value is the empty string or not. Complexity here ensures the minimal
+ // number of branches / amount of extraneous code at runtime (given that the
+ // below methods are inlined one-liners)!
+ if (SupportsArenas(descriptor_)) {
+ if (descriptor_->default_value_string().empty()) {
+ printer->Print(variables_,
+ "$name$_.ClearToEmpty($default_variable$, GetArenaNoVirtual());\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_.ClearToDefault($default_variable$, GetArenaNoVirtual());\n");
+ }
+ } else {
+ if (descriptor_->default_value_string().empty()) {
+ printer->Print(variables_,
+ "$name$_.ClearToEmptyNoArena($default_variable$);\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_.ClearToDefaultNoArena($default_variable$);\n");
+ }
+ }
+}
+
+void StringFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ if (SupportsArenas(descriptor_) || descriptor_->containing_oneof() != NULL) {
+ // TODO(gpike): improve this
+ printer->Print(variables_, "set_$name$(from.$name$());\n");
+ } else {
+ printer->Print(variables_,
+ "$set_hasbit$\n"
+ "$name$_.AssignWithDefault($default_variable$, from.$name$_);\n");
+ }
+}
+
+void StringFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.Swap(&other->$name$_);\n");
+}
+
+void StringFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_.UnsafeSetDefault($default_variable$);\n");
+}
+
+void StringFieldGenerator::
+GenerateDestructorCode(io::Printer* printer) const {
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ "$name$_.Destroy($default_variable$, GetArenaNoVirtual());\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_.DestroyNoArena($default_variable$);\n");
+ }
+}
+
+void StringFieldGenerator::
+GenerateDefaultInstanceAllocator(io::Printer* printer) const {
+ if (!descriptor_->default_value_string().empty()) {
+ printer->Print(variables_,
+ "$classname$::$default_variable$ =\n"
+ " new ::std::string($default$, $default_length$);\n");
+ }
+}
+
+void StringFieldGenerator::
+GenerateShutdownCode(io::Printer* printer) const {
+ if (!descriptor_->default_value_string().empty()) {
+ printer->Print(variables_,
+ "delete $classname$::$default_variable$;\n");
+ }
+}
+
+void StringFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ printer->Print(variables_,
+ "DO_(::google::protobuf::internal::WireFormatLite::Read$declared_type$(\n"
+ " input, this->mutable_$name$()));\n");
+
+ if (descriptor_->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ descriptor_, options_, true, variables_,
+ "this->$name$().data(), this->$name$().length(),\n", printer);
+ }
+}
+
+void StringFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ if (descriptor_->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ descriptor_, options_, false, variables_,
+ "this->$name$().data(), this->$name$().length(),\n", printer);
+ }
+ printer->Print(variables_,
+ "::google::protobuf::internal::WireFormatLite::Write$declared_type$MaybeAliased(\n"
+ " $number$, this->$name$(), output);\n");
+}
+
+void StringFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ if (descriptor_->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ descriptor_, options_, false, variables_,
+ "this->$name$().data(), this->$name$().length(),\n", printer);
+ }
+ printer->Print(variables_,
+ "target =\n"
+ " ::google::protobuf::internal::WireFormatLite::Write$declared_type$ToArray(\n"
+ " $number$, this->$name$(), target);\n");
+}
+
+void StringFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "total_size += $tag_size$ +\n"
+ " ::google::protobuf::internal::WireFormatLite::$declared_type$Size(\n"
+ " this->$name$());\n");
+}
+
+// ===================================================================
+
+StringOneofFieldGenerator::
+StringOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : StringFieldGenerator(descriptor, options),
+ dependent_field_(options.proto_h) {
+ SetCommonOneofFieldVariables(descriptor, &variables_);
+}
+
+StringOneofFieldGenerator::~StringOneofFieldGenerator() {}
+
+void StringOneofFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables,
+ "$inline$ const ::std::string& $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " if (has_$name$()) {\n"
+ " return $oneof_prefix$$name$_.Get($default_variable$);\n"
+ " }\n"
+ " return *$default_variable$;\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const ::std::string& value) {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " $oneof_prefix$$name$_.Set($default_variable$, value,\n"
+ " GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const char* value) {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " $oneof_prefix$$name$_.Set($default_variable$,\n"
+ " $string_piece$(value), GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_set_char:$full_name$)\n"
+ "}\n"
+ "$inline$ "
+ "void $classname$::set_$name$(const $pointer_type$* value,\n"
+ " size_t size) {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " $oneof_prefix$$name$_.Set($default_variable$, $string_piece$(\n"
+ " reinterpret_cast<const char*>(value), size),\n"
+ " GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_set_pointer:$full_name$)\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::mutable_$name$() {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " return $oneof_prefix$$name$_.Mutable($default_variable$,\n"
+ " GetArenaNoVirtual());\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " if (has_$name$()) {\n"
+ " clear_has_$oneof_name$();\n"
+ " return $oneof_prefix$$name$_.Release($default_variable$,\n"
+ " GetArenaNoVirtual());\n"
+ " } else {\n"
+ " return NULL;\n"
+ " }\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::unsafe_arena_release_$name$() {\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_release:$full_name$)\n"
+ " GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);\n"
+ " if (has_$name$()) {\n"
+ " clear_has_$oneof_name$();\n"
+ " return $oneof_prefix$$name$_.UnsafeArenaRelease(\n"
+ " $default_variable$, GetArenaNoVirtual());\n"
+ " } else {\n"
+ " return NULL;\n"
+ " }\n"
+ "}\n"
+ "$inline$ void $classname$::set_allocated_$name$(::std::string* $name$) {\n"
+ " if (!has_$name$()) {\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " clear_$oneof_name$();\n"
+ " if ($name$ != NULL) {\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.SetAllocated($default_variable$, $name$,\n"
+ " GetArenaNoVirtual());\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::unsafe_arena_set_allocated_$name$("
+ "::std::string* $name$) {\n"
+ " GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);\n"
+ " if (!has_$name$()) {\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " clear_$oneof_name$();\n"
+ " if ($name$) {\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeArenaSetAllocated($default_variable$, "
+ "$name$, GetArenaNoVirtual());\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_unsafe_arena_set_allocated:"
+ "$full_name$)\n"
+ "}\n");
+ } else {
+ // No-arena case.
+ printer->Print(variables,
+ "$inline$ const ::std::string& $classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " if (has_$name$()) {\n"
+ " return $oneof_prefix$$name$_.GetNoArena($default_variable$);\n"
+ " }\n"
+ " return *$default_variable$;\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const ::std::string& value) {\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " $oneof_prefix$$name$_.SetNoArena($default_variable$, value);\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(const char* value) {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " $oneof_prefix$$name$_.SetNoArena($default_variable$,\n"
+ " $string_piece$(value));\n"
+ " // @@protoc_insertion_point(field_set_char:$full_name$)\n"
+ "}\n"
+ "$inline$ "
+ "void $classname$::set_$name$(const $pointer_type$* value, size_t size) {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " $oneof_prefix$$name$_.SetNoArena($default_variable$, $string_piece$(\n"
+ " reinterpret_cast<const char*>(value), size));\n"
+ " // @@protoc_insertion_point(field_set_pointer:$full_name$)\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::mutable_$name$() {\n"
+ " if (!has_$name$()) {\n"
+ " clear_$oneof_name$();\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $oneof_prefix$$name$_.MutableNoArena($default_variable$);\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::$release_name$() {\n"
+ " // @@protoc_insertion_point(field_release:$full_name$)\n"
+ " if (has_$name$()) {\n"
+ " clear_has_$oneof_name$();\n"
+ " return $oneof_prefix$$name$_.ReleaseNoArena($default_variable$);\n"
+ " } else {\n"
+ " return NULL;\n"
+ " }\n"
+ "}\n"
+ "$inline$ void $classname$::set_allocated_$name$(::std::string* $name$) {\n"
+ " if (!has_$name$()) {\n"
+ " $oneof_prefix$$name$_.UnsafeSetDefault($default_variable$);\n"
+ " }\n"
+ " clear_$oneof_name$();\n"
+ " if ($name$ != NULL) {\n"
+ " set_has_$name$();\n"
+ " $oneof_prefix$$name$_.SetAllocatedNoArena($default_variable$,\n"
+ " $name$);\n"
+ " }\n"
+ " // @@protoc_insertion_point(field_set_allocated:$full_name$)\n"
+ "}\n");
+ }
+}
+
+void StringOneofFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ map<string, string> variables(variables_);
+ if (dependent_field_) {
+ variables["this_message"] = DependentBaseDownCast();
+ // This clearing code may be in the dependent base class. If the default
+ // value is an empty string, then the $default_variable$ is a global
+ // singleton. If the default is not empty, we need to down-cast to get the
+ // default value's global singleton instance. See SetStringVariables() for
+ // possible values of default_variable.
+ if (!descriptor_->default_value_string().empty()) {
+ variables["default_variable"] =
+ DependentBaseDownCast() + variables["default_variable"];
+ }
+ } else {
+ variables["this_message"] = "";
+ }
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables,
+ "$this_message$$oneof_prefix$$name$_.Destroy($default_variable$,\n"
+ " $this_message$GetArenaNoVirtual());\n");
+ } else {
+ printer->Print(variables,
+ "$this_message$$oneof_prefix$$name$_."
+ "DestroyNoArena($default_variable$);\n");
+ }
+}
+
+void StringOneofFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ // Don't print any swapping code. Swapping the union will swap this field.
+}
+
+void StringOneofFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ " $classname$_default_oneof_instance_->$name$_.UnsafeSetDefault("
+ "$default_variable$);\n");
+}
+
+void StringOneofFieldGenerator::
+GenerateDestructorCode(io::Printer* printer) const {
+ if (SupportsArenas(descriptor_)) {
+ printer->Print(variables_,
+ "if (has_$name$()) {\n"
+ " $oneof_prefix$$name$_.Destroy($default_variable$,\n"
+ " GetArenaNoVirtual());\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "if (has_$name$()) {\n"
+ " $oneof_prefix$$name$_.DestroyNoArena($default_variable$);\n"
+ "}\n");
+ }
+}
+
+void StringOneofFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ printer->Print(variables_,
+ "DO_(::google::protobuf::internal::WireFormatLite::Read$declared_type$(\n"
+ " input, this->mutable_$name$()));\n");
+
+ if (descriptor_->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ descriptor_, options_, true, variables_,
+ "this->$name$().data(), this->$name$().length(),\n", printer);
+ }
+}
+
+
+// ===================================================================
+
+RepeatedStringFieldGenerator::RepeatedStringFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : FieldGenerator(options), descriptor_(descriptor) {
+ SetStringVariables(descriptor, &variables_, options);
+}
+
+RepeatedStringFieldGenerator::~RepeatedStringFieldGenerator() {}
+
+void RepeatedStringFieldGenerator::
+GeneratePrivateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "::google::protobuf::RepeatedPtrField< ::std::string> $name$_;\n");
+}
+
+void RepeatedStringFieldGenerator::
+GenerateAccessorDeclarations(io::Printer* printer) const {
+ // See comment above about unknown ctypes.
+ bool unknown_ctype =
+ descriptor_->options().ctype() != EffectiveStringCType(descriptor_);
+
+ if (unknown_ctype) {
+ printer->Outdent();
+ printer->Print(
+ " private:\n"
+ " // Hidden due to unknown ctype option.\n");
+ printer->Indent();
+ }
+
+ printer->Print(variables_,
+ "$deprecated_attr$const ::std::string& $name$(int index) const;\n"
+ "$deprecated_attr$::std::string* mutable_$name$(int index);\n"
+ "$deprecated_attr$void set_$name$(int index, const ::std::string& value);\n"
+ "$deprecated_attr$void set_$name$(int index, const char* value);\n"
+ ""
+ "$deprecated_attr$void set_$name$("
+ "int index, const $pointer_type$* value, size_t size);\n"
+ "$deprecated_attr$::std::string* add_$name$();\n"
+ "$deprecated_attr$void add_$name$(const ::std::string& value);\n"
+ "$deprecated_attr$void add_$name$(const char* value);\n"
+ "$deprecated_attr$void add_$name$(const $pointer_type$* value, size_t size)"
+ ";\n");
+
+ printer->Print(variables_,
+ "$deprecated_attr$const ::google::protobuf::RepeatedPtrField< ::std::string>& $name$() "
+ "const;\n"
+ "$deprecated_attr$::google::protobuf::RepeatedPtrField< ::std::string>* mutable_$name$()"
+ ";\n");
+
+ if (unknown_ctype) {
+ printer->Outdent();
+ printer->Print(" public:\n");
+ printer->Indent();
+ }
+}
+
+void RepeatedStringFieldGenerator::
+GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const {
+ map<string, string> variables(variables_);
+ variables["inline"] = is_inline ? "inline" : "";
+ printer->Print(variables,
+ "$inline$ const ::std::string& $classname$::$name$(int index) const {\n"
+ " // @@protoc_insertion_point(field_get:$full_name$)\n"
+ " return $name$_.$cppget$(index);\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::mutable_$name$(int index) {\n"
+ " // @@protoc_insertion_point(field_mutable:$full_name$)\n"
+ " return $name$_.Mutable(index);\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(int index, const ::std::string& value) {\n"
+ " // @@protoc_insertion_point(field_set:$full_name$)\n"
+ " $name$_.Mutable(index)->assign(value);\n"
+ "}\n"
+ "$inline$ void $classname$::set_$name$(int index, const char* value) {\n"
+ " $name$_.Mutable(index)->assign(value);\n"
+ " // @@protoc_insertion_point(field_set_char:$full_name$)\n"
+ "}\n"
+ "$inline$ void "
+ "$classname$::set_$name$"
+ "(int index, const $pointer_type$* value, size_t size) {\n"
+ " $name$_.Mutable(index)->assign(\n"
+ " reinterpret_cast<const char*>(value), size);\n"
+ " // @@protoc_insertion_point(field_set_pointer:$full_name$)\n"
+ "}\n"
+ "$inline$ ::std::string* $classname$::add_$name$() {\n"
+ " // @@protoc_insertion_point(field_add_mutable:$full_name$)\n"
+ " return $name$_.Add();\n"
+ "}\n"
+ "$inline$ void $classname$::add_$name$(const ::std::string& value) {\n"
+ " $name$_.Add()->assign(value);\n"
+ " // @@protoc_insertion_point(field_add:$full_name$)\n"
+ "}\n"
+ "$inline$ void $classname$::add_$name$(const char* value) {\n"
+ " $name$_.Add()->assign(value);\n"
+ " // @@protoc_insertion_point(field_add_char:$full_name$)\n"
+ "}\n"
+ "$inline$ void "
+ "$classname$::add_$name$(const $pointer_type$* value, size_t size) {\n"
+ " $name$_.Add()->assign(reinterpret_cast<const char*>(value), size);\n"
+ " // @@protoc_insertion_point(field_add_pointer:$full_name$)\n"
+ "}\n");
+ printer->Print(variables,
+ "$inline$ const ::google::protobuf::RepeatedPtrField< ::std::string>&\n"
+ "$classname$::$name$() const {\n"
+ " // @@protoc_insertion_point(field_list:$full_name$)\n"
+ " return $name$_;\n"
+ "}\n"
+ "$inline$ ::google::protobuf::RepeatedPtrField< ::std::string>*\n"
+ "$classname$::mutable_$name$() {\n"
+ " // @@protoc_insertion_point(field_mutable_list:$full_name$)\n"
+ " return &$name$_;\n"
+ "}\n");
+}
+
+void RepeatedStringFieldGenerator::
+GenerateClearingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.Clear();\n");
+}
+
+void RepeatedStringFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.MergeFrom(from.$name$_);\n");
+}
+
+void RepeatedStringFieldGenerator::
+GenerateSwappingCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.UnsafeArenaSwap(&other->$name$_);\n");
+}
+
+void RepeatedStringFieldGenerator::
+GenerateConstructorCode(io::Printer* printer) const {
+ // Not needed for repeated fields.
+}
+
+void RepeatedStringFieldGenerator::
+GenerateMergeFromCodedStream(io::Printer* printer) const {
+ printer->Print(variables_,
+ "DO_(::google::protobuf::internal::WireFormatLite::Read$declared_type$(\n"
+ " input, this->add_$name$()));\n");
+ if (descriptor_->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ descriptor_, options_, true, variables_,
+ "this->$name$(this->$name$_size() - 1).data(),\n"
+ "this->$name$(this->$name$_size() - 1).length(),\n",
+ printer);
+ }
+}
+
+void RepeatedStringFieldGenerator::
+GenerateSerializeWithCachedSizes(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n");
+ printer->Indent();
+ if (descriptor_->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ descriptor_, options_, false, variables_,
+ "this->$name$(i).data(), this->$name$(i).length(),\n", printer);
+ }
+ printer->Outdent();
+ printer->Print(variables_,
+ " ::google::protobuf::internal::WireFormatLite::Write$declared_type$(\n"
+ " $number$, this->$name$(i), output);\n"
+ "}\n");
+}
+
+void RepeatedStringFieldGenerator::
+GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < this->$name$_size(); i++) {\n");
+ printer->Indent();
+ if (descriptor_->type() == FieldDescriptor::TYPE_STRING) {
+ GenerateUtf8CheckCodeForString(
+ descriptor_, options_, false, variables_,
+ "this->$name$(i).data(), this->$name$(i).length(),\n", printer);
+ }
+ printer->Outdent();
+ printer->Print(variables_,
+ " target = ::google::protobuf::internal::WireFormatLite::\n"
+ " Write$declared_type$ToArray($number$, this->$name$(i), target);\n"
+ "}\n");
+}
+
+void RepeatedStringFieldGenerator::
+GenerateByteSize(io::Printer* printer) const {
+ printer->Print(variables_,
+ "total_size += $tag_size$ * this->$name$_size();\n"
+ "for (int i = 0; i < this->$name$_size(); i++) {\n"
+ " total_size += ::google::protobuf::internal::WireFormatLite::$declared_type$Size(\n"
+ " this->$name$(i));\n"
+ "}\n");
+}
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.h
new file mode 100644
index 0000000000..cb4e8772d0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_string_field.h
@@ -0,0 +1,132 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_STRING_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_STRING_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/cpp/cpp_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+class StringFieldGenerator : public FieldGenerator {
+ public:
+ StringFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~StringFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateStaticMembers(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateNonInlineAccessorDefinitions(io::Printer* printer) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateDestructorCode(io::Printer* printer) const;
+ void GenerateDefaultInstanceAllocator(io::Printer* printer) const;
+ void GenerateShutdownCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StringFieldGenerator);
+};
+
+class StringOneofFieldGenerator : public StringFieldGenerator {
+ public:
+ StringOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~StringOneofFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateDestructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+
+ private:
+ const bool dependent_field_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StringOneofFieldGenerator);
+};
+
+class RepeatedStringFieldGenerator : public FieldGenerator {
+ public:
+ RepeatedStringFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ ~RepeatedStringFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GeneratePrivateMembers(io::Printer* printer) const;
+ void GenerateAccessorDeclarations(io::Printer* printer) const;
+ void GenerateInlineAccessorDefinitions(io::Printer* printer,
+ bool is_inline) const;
+ void GenerateClearingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSwappingCode(io::Printer* printer) const;
+ void GenerateConstructorCode(io::Printer* printer) const;
+ void GenerateMergeFromCodedStream(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizes(io::Printer* printer) const;
+ void GenerateSerializeWithCachedSizesToArray(io::Printer* printer) const;
+ void GenerateByteSize(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedStringFieldGenerator);
+};
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_STRING_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_bad_identifiers.proto b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_bad_identifiers.proto
new file mode 100644
index 0000000000..4e25b2ea8f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_bad_identifiers.proto
@@ -0,0 +1,156 @@
+// 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 tests that various identifiers work as field and type names even
+// though the same identifiers are used internally by the C++ code generator.
+
+syntax = "proto2";
+
+// Some generic_services option(s) added automatically.
+// See: http://go/proto2-generic-services-default
+option cc_generic_services = true; // auto-added
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+package protobuf_unittest;
+
+// Test that fields can have names like "input" and "i" which are also used
+// internally by the code generator for local variables.
+message TestConflictingSymbolNames {
+ message BuildDescriptors {}
+ message TypeTraits {}
+
+ optional int32 input = 1;
+ optional int32 output = 2;
+ optional string length = 3;
+ repeated int32 i = 4;
+ repeated string new_element = 5 [ctype=STRING_PIECE];
+ optional int32 total_size = 6;
+ optional int32 tag = 7;
+
+ enum TestEnum { FOO = 0; }
+ message Data1 { repeated int32 data = 1; }
+ message Data2 { repeated TestEnum data = 1; }
+ message Data3 { repeated string data = 1; }
+ message Data4 { repeated Data4 data = 1; }
+ message Data5 { repeated string data = 1 [ctype=STRING_PIECE]; }
+ message Data6 { repeated string data = 1 [ctype=CORD]; }
+
+ optional int32 source = 8;
+ optional int32 value = 9;
+ optional int32 file = 10;
+ optional int32 from = 11;
+ optional int32 handle_uninterpreted = 12;
+ repeated int32 index = 13;
+ optional int32 controller = 14;
+ optional int32 already_here = 15;
+
+ optional uint32 uint32 = 16;
+ optional uint64 uint64 = 17;
+ optional string string = 18;
+ optional int32 memset = 19;
+ optional int32 int32 = 20;
+ optional int64 int64 = 21;
+
+ optional uint32 cached_size = 22;
+ optional uint32 extensions = 23;
+ optional uint32 bit = 24;
+ optional uint32 bits = 25;
+ optional uint32 offsets = 26;
+ optional uint32 reflection = 27;
+
+ message Cord {}
+ optional string some_cord = 28 [ctype=CORD];
+
+ message StringPiece {}
+ optional string some_string_piece = 29 [ctype=STRING_PIECE];
+
+ // Some keywords.
+ optional uint32 int = 30;
+ optional uint32 friend = 31;
+ optional uint32 class = 37;
+ optional uint32 typedecl = 39;
+ optional uint32 auto = 40;
+
+ // The generator used to #define a macro called "DO" inside the .cc file.
+ message DO {}
+ optional DO do = 32;
+
+ // Some template parameter names for extensions.
+ optional int32 field_type = 33;
+ optional bool is_packed = 34;
+
+ // test conflicting release_$name$. "length" and "do" field in this message
+ // must remain string or message fields to make the test valid.
+ optional string release_length = 35;
+ // A more extreme case, the field name "do" here is a keyword, which will be
+ // escaped to "do_" already. Test there is no conflict even with escaped field
+ // names.
+ optional DO release_do = 36;
+
+ // For clashing local variables in Serialize and ByteSize calculation.
+ optional string target = 38;
+
+ extensions 1000 to max; // NO_PROTO3
+}
+
+message TestConflictingSymbolNamesExtension { // NO_PROTO3
+ extend TestConflictingSymbolNames { // NO_PROTO3
+ repeated int32 repeated_int32_ext = 20423638 [packed=true]; // NO_PROTO3
+ } // NO_PROTO3
+} // NO_PROTO3
+
+message TestConflictingEnumNames { // NO_PROTO3
+ enum NestedConflictingEnum { // NO_PROTO3
+ and = 1; // NO_PROTO3
+ class = 2; // NO_PROTO3
+ int = 3; // NO_PROTO3
+ typedef = 4; // NO_PROTO3
+ XOR = 5; // NO_PROTO3
+ } // NO_PROTO3
+
+ optional NestedConflictingEnum conflicting_enum = 1; // NO_PROTO3
+} // NO_PROTO3
+
+enum ConflictingEnum { // NO_PROTO3
+ NOT_EQ = 1; // NO_PROTO3
+ volatile = 2; // NO_PROTO3
+ return = 3; // NO_PROTO3
+} // NO_PROTO3
+
+message DummyMessage {}
+
+service TestConflictingMethodNames {
+ rpc Closure(DummyMessage) returns (DummyMessage);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_large_enum_value.proto b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_large_enum_value.proto
new file mode 100644
index 0000000000..cb6ca1b151
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_test_large_enum_value.proto
@@ -0,0 +1,43 @@
+// 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.
+
+// Test that proto2 compiler can generate valid code when the enum value
+// is INT_MAX. Note that this is a compile-only test and this proto is not
+// referenced in any C++ code.
+syntax = "proto2";
+
+package protobuf_unittest;
+
+message TestLargeEnumValue {
+ enum EnumWithLargeValue {
+ VALUE_1 = 1;
+ VALUE_MAX = 0x7fffffff;
+ }
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.cc
new file mode 100644
index 0000000000..5d82946d61
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.cc
@@ -0,0 +1,2139 @@
+// 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.
+//
+// To test the code generator, we actually use it to generate code for
+// google/protobuf/unittest.proto, then test that. This means that we
+// are actually testing the parser and other parts of the system at the same
+// time, and that problems in the generator may show up as compile-time errors
+// rather than unittest failures, which may be surprising. However, testing
+// the output of the C++ generator directly would be very hard. We can't very
+// well just check it against golden files since those files would have to be
+// updated for any small change; such a test would be very brittle and probably
+// not very helpful. What we really want to test is that the code compiles
+// correctly and produces the interfaces we expect, which is why this test
+// is written this way.
+
+#include <google/protobuf/compiler/cpp/cpp_unittest.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_optimize_for.pb.h>
+#include <google/protobuf/unittest_embed_optimize_for.pb.h>
+#if !defined(GOOGLE_PROTOBUF_CMAKE_BUILD) && !defined(_MSC_VER)
+// We exclude this large proto from cmake build because it's too large for
+// visual studio to compile (report internal errors).
+#include <google/protobuf/unittest_enormous_descriptor.pb.h>
+#endif
+#include <google/protobuf/unittest_no_generic_services.pb.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/compiler/cpp/cpp_test_bad_identifiers.pb.h>
+#include <google/protobuf/compiler/importer.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/dynamic_message.h>
+
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+
+// Can't use an anonymous namespace here due to brokenness of Tru64 compiler.
+namespace cpp_unittest {
+
+namespace protobuf_unittest = ::protobuf_unittest;
+
+
+class MockErrorCollector : public MultiFileErrorCollector {
+ public:
+ MockErrorCollector() {}
+ ~MockErrorCollector() {}
+
+ string text_;
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(const string& filename, int line, int column,
+ const string& message) {
+ strings::SubstituteAndAppend(&text_, "$0:$1:$2: $3\n",
+ filename, line, column, message);
+ }
+};
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+
+// Test that generated code has proper descriptors:
+// Parse a descriptor directly (using google::protobuf::compiler::Importer) and
+// compare it to the one that was produced by generated code.
+TEST(GeneratedDescriptorTest, IdenticalDescriptors) {
+ const FileDescriptor* generated_descriptor =
+ unittest::TestAllTypes::descriptor()->file();
+
+ // Set up the Importer.
+ MockErrorCollector error_collector;
+ DiskSourceTree source_tree;
+ source_tree.MapPath("", TestSourceDir());
+ Importer importer(&source_tree, &error_collector);
+
+ // Import (parse) unittest.proto.
+ const FileDescriptor* parsed_descriptor =
+ importer.Import("google/protobuf/unittest.proto");
+ EXPECT_EQ("", error_collector.text_);
+ ASSERT_TRUE(parsed_descriptor != NULL);
+
+ // Test that descriptors are generated correctly by converting them to
+ // FileDescriptorProtos and comparing.
+ FileDescriptorProto generated_decsriptor_proto, parsed_descriptor_proto;
+ generated_descriptor->CopyTo(&generated_decsriptor_proto);
+ parsed_descriptor->CopyTo(&parsed_descriptor_proto);
+
+ EXPECT_EQ(parsed_descriptor_proto.DebugString(),
+ generated_decsriptor_proto.DebugString());
+}
+
+#if !defined(GOOGLE_PROTOBUF_CMAKE_BUILD) && !defined(_MSC_VER)
+// Test that generated code has proper descriptors:
+// Touch a descriptor generated from an enormous message to validate special
+// handling for descriptors exceeding the C++ standard's recommended minimum
+// limit for string literal size
+TEST(GeneratedDescriptorTest, EnormousDescriptor) {
+ const Descriptor* generated_descriptor =
+ TestEnormousDescriptor::descriptor();
+
+ EXPECT_TRUE(generated_descriptor != NULL);
+}
+#endif
+
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+
+// ===================================================================
+
+TEST(GeneratedMessageTest, Defaults) {
+ // Check that all default values are set correctly in the initial message.
+ unittest::TestAllTypes message;
+
+ TestUtil::ExpectClear(message);
+
+ // Messages should return pointers to default instances until first use.
+ // (This is not checked by ExpectClear() since it is not actually true after
+ // the fields have been set and then cleared.)
+ EXPECT_EQ(&unittest::TestAllTypes::OptionalGroup::default_instance(),
+ &message.optionalgroup());
+ EXPECT_EQ(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &message.optional_nested_message());
+ EXPECT_EQ(&unittest::ForeignMessage::default_instance(),
+ &message.optional_foreign_message());
+ EXPECT_EQ(&unittest_import::ImportMessage::default_instance(),
+ &message.optional_import_message());
+}
+
+#ifndef PROTOBUF_USE_DLLS
+TEST(GeneratedMessageTest, Int32StringConversion) {
+ EXPECT_EQ("971", Int32ToString(971));
+ EXPECT_EQ("(~0x7fffffff)", Int32ToString(kint32min));
+ EXPECT_EQ("2147483647", Int32ToString(kint32max));
+}
+
+TEST(GeneratedMessageTest, Int64StringConversion) {
+ EXPECT_EQ("GOOGLE_LONGLONG(971)", Int64ToString(971));
+ EXPECT_EQ("GOOGLE_LONGLONG(-2147483648)", Int64ToString(kint32min));
+ EXPECT_EQ("GOOGLE_LONGLONG(~0x7fffffffffffffff)", Int64ToString(kint64min));
+ EXPECT_EQ("GOOGLE_LONGLONG(9223372036854775807)", Int64ToString(kint64max));
+}
+#endif // !PROTOBUF_USE_DLLS
+
+TEST(GeneratedMessageTest, FloatingPointDefaults) {
+ const unittest::TestExtremeDefaultValues& extreme_default =
+ unittest::TestExtremeDefaultValues::default_instance();
+
+ EXPECT_EQ(0.0f, extreme_default.zero_float());
+ EXPECT_EQ(1.0f, extreme_default.one_float());
+ EXPECT_EQ(1.5f, extreme_default.small_float());
+ EXPECT_EQ(-1.0f, extreme_default.negative_one_float());
+ EXPECT_EQ(-1.5f, extreme_default.negative_float());
+ EXPECT_EQ(2.0e8f, extreme_default.large_float());
+ EXPECT_EQ(-8e-28f, extreme_default.small_negative_float());
+ EXPECT_EQ(numeric_limits<double>::infinity(),
+ extreme_default.inf_double());
+ EXPECT_EQ(-numeric_limits<double>::infinity(),
+ extreme_default.neg_inf_double());
+ EXPECT_TRUE(extreme_default.nan_double() != extreme_default.nan_double());
+ EXPECT_EQ(numeric_limits<float>::infinity(),
+ extreme_default.inf_float());
+ EXPECT_EQ(-numeric_limits<float>::infinity(),
+ extreme_default.neg_inf_float());
+ EXPECT_TRUE(extreme_default.nan_float() != extreme_default.nan_float());
+}
+
+TEST(GeneratedMessageTest, Trigraph) {
+ const unittest::TestExtremeDefaultValues& extreme_default =
+ unittest::TestExtremeDefaultValues::default_instance();
+
+ EXPECT_EQ("? ? ?? ?? ??? ?\?/ ?\?-", extreme_default.cpp_trigraph());
+}
+
+TEST(GeneratedMessageTest, ExtremeSmallIntegerDefault) {
+ const unittest::TestExtremeDefaultValues& extreme_default =
+ unittest::TestExtremeDefaultValues::default_instance();
+ EXPECT_EQ(~0x7fffffff, kint32min);
+ EXPECT_EQ(GOOGLE_LONGLONG(~0x7fffffffffffffff), kint64min);
+ EXPECT_EQ(kint32min, extreme_default.really_small_int32());
+ EXPECT_EQ(kint64min, extreme_default.really_small_int64());
+}
+
+TEST(GeneratedMessageTest, Accessors) {
+ // Set every field to a unique value then go back and check all those
+ // values.
+ unittest::TestAllTypes message;
+
+ TestUtil::SetAllFields(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+
+ TestUtil::ModifyRepeatedFields(&message);
+ TestUtil::ExpectRepeatedFieldsModified(message);
+}
+
+TEST(GeneratedMessageTest, MutableStringDefault) {
+ // mutable_foo() for a string should return a string initialized to its
+ // default value.
+ unittest::TestAllTypes message;
+
+ EXPECT_EQ("hello", *message.mutable_default_string());
+
+ // Note that the first time we call mutable_foo(), we get a newly-allocated
+ // string, but if we clear it and call it again, we get the same object again.
+ // We should verify that it has its default value in both cases.
+ message.set_default_string("blah");
+ message.Clear();
+
+ EXPECT_EQ("hello", *message.mutable_default_string());
+}
+
+TEST(GeneratedMessageTest, StringDefaults) {
+ unittest::TestExtremeDefaultValues message;
+ // Check if '\000' can be used in default string value.
+ EXPECT_EQ(string("hel\000lo", 6), message.string_with_zero());
+ EXPECT_EQ(string("wor\000ld", 6), message.bytes_with_zero());
+}
+
+TEST(GeneratedMessageTest, ReleaseString) {
+ // Check that release_foo() starts out NULL, and gives us a value
+ // that we can delete after it's been set.
+ unittest::TestAllTypes message;
+
+ EXPECT_EQ(NULL, message.release_default_string());
+ EXPECT_FALSE(message.has_default_string());
+ EXPECT_EQ("hello", message.default_string());
+
+ message.set_default_string("blah");
+ EXPECT_TRUE(message.has_default_string());
+ google::protobuf::scoped_ptr<string> str(message.release_default_string());
+ EXPECT_FALSE(message.has_default_string());
+ ASSERT_TRUE(str != NULL);
+ EXPECT_EQ("blah", *str);
+
+ EXPECT_EQ(NULL, message.release_default_string());
+ EXPECT_FALSE(message.has_default_string());
+ EXPECT_EQ("hello", message.default_string());
+}
+
+TEST(GeneratedMessageTest, ReleaseMessage) {
+ // Check that release_foo() starts out NULL, and gives us a value
+ // that we can delete after it's been set.
+ unittest::TestAllTypes message;
+
+ EXPECT_EQ(NULL, message.release_optional_nested_message());
+ EXPECT_FALSE(message.has_optional_nested_message());
+
+ message.mutable_optional_nested_message()->set_bb(1);
+ google::protobuf::scoped_ptr<unittest::TestAllTypes::NestedMessage> nest(
+ message.release_optional_nested_message());
+ EXPECT_FALSE(message.has_optional_nested_message());
+ ASSERT_TRUE(nest != NULL);
+ EXPECT_EQ(1, nest->bb());
+
+ EXPECT_EQ(NULL, message.release_optional_nested_message());
+ EXPECT_FALSE(message.has_optional_nested_message());
+}
+
+TEST(GeneratedMessageTest, SetAllocatedString) {
+ // Check that set_allocated_foo() works for strings.
+ unittest::TestAllTypes message;
+
+ EXPECT_FALSE(message.has_optional_string());
+ const string kHello("hello");
+ message.set_optional_string(kHello);
+ EXPECT_TRUE(message.has_optional_string());
+
+ message.set_allocated_optional_string(NULL);
+ EXPECT_FALSE(message.has_optional_string());
+ EXPECT_EQ("", message.optional_string());
+
+ message.set_allocated_optional_string(new string(kHello));
+ EXPECT_TRUE(message.has_optional_string());
+ EXPECT_EQ(kHello, message.optional_string());
+}
+
+TEST(GeneratedMessageTest, SetAllocatedMessage) {
+ // Check that set_allocated_foo() can be called in all cases.
+ unittest::TestAllTypes message;
+
+ EXPECT_FALSE(message.has_optional_nested_message());
+
+ message.mutable_optional_nested_message()->set_bb(1);
+ EXPECT_TRUE(message.has_optional_nested_message());
+
+ message.set_allocated_optional_nested_message(NULL);
+ EXPECT_FALSE(message.has_optional_nested_message());
+ EXPECT_EQ(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &message.optional_nested_message());
+
+ message.mutable_optional_nested_message()->set_bb(1);
+ unittest::TestAllTypes::NestedMessage* nest =
+ message.release_optional_nested_message();
+ ASSERT_TRUE(nest != NULL);
+ EXPECT_FALSE(message.has_optional_nested_message());
+
+ message.set_allocated_optional_nested_message(nest);
+ EXPECT_TRUE(message.has_optional_nested_message());
+ EXPECT_EQ(1, message.optional_nested_message().bb());
+}
+
+TEST(GeneratedMessageTest, Clear) {
+ // Set every field to a unique value, clear the message, then check that
+ // it is cleared.
+ unittest::TestAllTypes message;
+
+ TestUtil::SetAllFields(&message);
+ message.Clear();
+ TestUtil::ExpectClear(message);
+
+ // Unlike with the defaults test, we do NOT expect that requesting embedded
+ // messages will return a pointer to the default instance. Instead, they
+ // should return the objects that were created when mutable_blah() was
+ // called.
+ EXPECT_NE(&unittest::TestAllTypes::OptionalGroup::default_instance(),
+ &message.optionalgroup());
+ EXPECT_NE(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &message.optional_nested_message());
+ EXPECT_NE(&unittest::ForeignMessage::default_instance(),
+ &message.optional_foreign_message());
+ EXPECT_NE(&unittest_import::ImportMessage::default_instance(),
+ &message.optional_import_message());
+}
+
+TEST(GeneratedMessageTest, EmbeddedNullsInBytesCharStar) {
+ unittest::TestAllTypes message;
+
+ const char* value = "\0lalala\0\0";
+ message.set_optional_bytes(value, 9);
+ ASSERT_EQ(9, message.optional_bytes().size());
+ EXPECT_EQ(0, memcmp(value, message.optional_bytes().data(), 9));
+
+ message.add_repeated_bytes(value, 9);
+ ASSERT_EQ(9, message.repeated_bytes(0).size());
+ EXPECT_EQ(0, memcmp(value, message.repeated_bytes(0).data(), 9));
+}
+
+TEST(GeneratedMessageTest, ClearOneField) {
+ // Set every field to a unique value, then clear one value and insure that
+ // only that one value is cleared.
+ unittest::TestAllTypes message;
+
+ TestUtil::SetAllFields(&message);
+ int64 original_value = message.optional_int64();
+
+ // Clear the field and make sure it shows up as cleared.
+ message.clear_optional_int64();
+ EXPECT_FALSE(message.has_optional_int64());
+ EXPECT_EQ(0, message.optional_int64());
+
+ // Other adjacent fields should not be cleared.
+ EXPECT_TRUE(message.has_optional_int32());
+ EXPECT_TRUE(message.has_optional_uint32());
+
+ // Make sure if we set it again, then all fields are set.
+ message.set_optional_int64(original_value);
+ TestUtil::ExpectAllFieldsSet(message);
+}
+
+TEST(GeneratedMessageTest, StringCharStarLength) {
+ // Verify that we can use a char*,length to set one of the string fields.
+ unittest::TestAllTypes message;
+ message.set_optional_string("abcdef", 3);
+ EXPECT_EQ("abc", message.optional_string());
+
+ // Verify that we can use a char*,length to add to a repeated string field.
+ message.add_repeated_string("abcdef", 3);
+ EXPECT_EQ(1, message.repeated_string_size());
+ EXPECT_EQ("abc", message.repeated_string(0));
+
+ // Verify that we can use a char*,length to set a repeated string field.
+ message.set_repeated_string(0, "wxyz", 2);
+ EXPECT_EQ("wx", message.repeated_string(0));
+}
+
+
+TEST(GeneratedMessageTest, CopyFrom) {
+ unittest::TestAllTypes message1, message2;
+
+ TestUtil::SetAllFields(&message1);
+ message2.CopyFrom(message1);
+ TestUtil::ExpectAllFieldsSet(message2);
+
+ // Copying from self should be a no-op.
+ message2.CopyFrom(message2);
+ TestUtil::ExpectAllFieldsSet(message2);
+}
+
+
+TEST(GeneratedMessageTest, SwapWithEmpty) {
+ unittest::TestAllTypes message1, message2;
+ TestUtil::SetAllFields(&message1);
+
+ TestUtil::ExpectAllFieldsSet(message1);
+ TestUtil::ExpectClear(message2);
+ message1.Swap(&message2);
+ TestUtil::ExpectAllFieldsSet(message2);
+ TestUtil::ExpectClear(message1);
+}
+
+TEST(GeneratedMessageTest, SwapWithSelf) {
+ unittest::TestAllTypes message;
+ TestUtil::SetAllFields(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+ message.Swap(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+}
+
+TEST(GeneratedMessageTest, SwapWithOther) {
+ unittest::TestAllTypes message1, message2;
+
+ message1.set_optional_int32(123);
+ message1.set_optional_string("abc");
+ message1.mutable_optional_nested_message()->set_bb(1);
+ message1.set_optional_nested_enum(unittest::TestAllTypes::FOO);
+ message1.add_repeated_int32(1);
+ message1.add_repeated_int32(2);
+ message1.add_repeated_string("a");
+ message1.add_repeated_string("b");
+ message1.add_repeated_nested_message()->set_bb(7);
+ message1.add_repeated_nested_message()->set_bb(8);
+ message1.add_repeated_nested_enum(unittest::TestAllTypes::FOO);
+ message1.add_repeated_nested_enum(unittest::TestAllTypes::BAR);
+
+ message2.set_optional_int32(456);
+ message2.set_optional_string("def");
+ message2.mutable_optional_nested_message()->set_bb(2);
+ message2.set_optional_nested_enum(unittest::TestAllTypes::BAR);
+ message2.add_repeated_int32(3);
+ message2.add_repeated_string("c");
+ message2.add_repeated_nested_message()->set_bb(9);
+ message2.add_repeated_nested_enum(unittest::TestAllTypes::BAZ);
+
+ message1.Swap(&message2);
+
+ EXPECT_EQ(456, message1.optional_int32());
+ EXPECT_EQ("def", message1.optional_string());
+ EXPECT_EQ(2, message1.optional_nested_message().bb());
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message1.optional_nested_enum());
+ ASSERT_EQ(1, message1.repeated_int32_size());
+ EXPECT_EQ(3, message1.repeated_int32(0));
+ ASSERT_EQ(1, message1.repeated_string_size());
+ EXPECT_EQ("c", message1.repeated_string(0));
+ ASSERT_EQ(1, message1.repeated_nested_message_size());
+ EXPECT_EQ(9, message1.repeated_nested_message(0).bb());
+ ASSERT_EQ(1, message1.repeated_nested_enum_size());
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, message1.repeated_nested_enum(0));
+
+ EXPECT_EQ(123, message2.optional_int32());
+ EXPECT_EQ("abc", message2.optional_string());
+ EXPECT_EQ(1, message2.optional_nested_message().bb());
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message2.optional_nested_enum());
+ ASSERT_EQ(2, message2.repeated_int32_size());
+ EXPECT_EQ(1, message2.repeated_int32(0));
+ EXPECT_EQ(2, message2.repeated_int32(1));
+ ASSERT_EQ(2, message2.repeated_string_size());
+ EXPECT_EQ("a", message2.repeated_string(0));
+ EXPECT_EQ("b", message2.repeated_string(1));
+ ASSERT_EQ(2, message2.repeated_nested_message_size());
+ EXPECT_EQ(7, message2.repeated_nested_message(0).bb());
+ EXPECT_EQ(8, message2.repeated_nested_message(1).bb());
+ ASSERT_EQ(2, message2.repeated_nested_enum_size());
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message2.repeated_nested_enum(0));
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message2.repeated_nested_enum(1));
+}
+
+TEST(GeneratedMessageTest, CopyConstructor) {
+ unittest::TestAllTypes message1;
+ TestUtil::SetAllFields(&message1);
+
+ unittest::TestAllTypes message2(message1);
+ TestUtil::ExpectAllFieldsSet(message2);
+}
+
+TEST(GeneratedMessageTest, CopyAssignmentOperator) {
+ unittest::TestAllTypes message1;
+ TestUtil::SetAllFields(&message1);
+
+ unittest::TestAllTypes message2;
+ message2 = message1;
+ TestUtil::ExpectAllFieldsSet(message2);
+
+ // Make sure that self-assignment does something sane.
+ message2.operator=(message2);
+ TestUtil::ExpectAllFieldsSet(message2);
+}
+
+#if !defined(PROTOBUF_TEST_NO_DESCRIPTORS) || \
+ !defined(GOOGLE_PROTOBUF_NO_RTTI)
+TEST(GeneratedMessageTest, UpcastCopyFrom) {
+ // Test the CopyFrom method that takes in the generic const Message&
+ // parameter.
+ unittest::TestAllTypes message1, message2;
+
+ TestUtil::SetAllFields(&message1);
+
+ const Message* source = implicit_cast<const Message*>(&message1);
+ message2.CopyFrom(*source);
+
+ TestUtil::ExpectAllFieldsSet(message2);
+}
+#endif
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+
+TEST(GeneratedMessageTest, DynamicMessageCopyFrom) {
+ // Test copying from a DynamicMessage, which must fall back to using
+ // reflection.
+ unittest::TestAllTypes message2;
+
+ // Construct a new version of the dynamic message via the factory.
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> message1;
+ message1.reset(factory.GetPrototype(
+ unittest::TestAllTypes::descriptor())->New());
+
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+ reflection_tester.SetAllFieldsViaReflection(message1.get());
+
+ message2.CopyFrom(*message1);
+
+ TestUtil::ExpectAllFieldsSet(message2);
+}
+
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+
+TEST(GeneratedMessageTest, NonEmptyMergeFrom) {
+ // Test merging with a non-empty message. Code is a modified form
+ // of that found in google/protobuf/reflection_ops_unittest.cc.
+ unittest::TestAllTypes message1, message2;
+
+ TestUtil::SetAllFields(&message1);
+
+ // This field will test merging into an empty spot.
+ message2.set_optional_int32(message1.optional_int32());
+ message1.clear_optional_int32();
+
+ // This tests overwriting.
+ message2.set_optional_string(message1.optional_string());
+ message1.set_optional_string("something else");
+
+ // This tests concatenating.
+ message2.add_repeated_int32(message1.repeated_int32(1));
+ int32 i = message1.repeated_int32(0);
+ message1.clear_repeated_int32();
+ message1.add_repeated_int32(i);
+
+ message1.MergeFrom(message2);
+
+ TestUtil::ExpectAllFieldsSet(message1);
+}
+
+#if !defined(PROTOBUF_TEST_NO_DESCRIPTORS) || \
+ !defined(GOOGLE_PROTOBUF_NO_RTTI)
+#ifdef PROTOBUF_HAS_DEATH_TEST
+
+TEST(GeneratedMessageTest, MergeFromSelf) {
+ unittest::TestAllTypes message;
+ EXPECT_DEATH(message.MergeFrom(message), "Check failed:.*pb[.]cc");
+ EXPECT_DEATH(message.MergeFrom(implicit_cast<const Message&>(message)),
+ "Check failed:.*pb[.]cc");
+}
+
+#endif // PROTOBUF_HAS_DEATH_TEST
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS || !GOOGLE_PROTOBUF_NO_RTTI
+
+// Test the generated SerializeWithCachedSizesToArray(),
+TEST(GeneratedMessageTest, SerializationToArray) {
+ unittest::TestAllTypes message1, message2;
+ string data;
+ TestUtil::SetAllFields(&message1);
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ TestUtil::ExpectAllFieldsSet(message2);
+
+}
+
+TEST(GeneratedMessageTest, PackedFieldsSerializationToArray) {
+ unittest::TestPackedTypes packed_message1, packed_message2;
+ string packed_data;
+ TestUtil::SetPackedFields(&packed_message1);
+ int packed_size = packed_message1.ByteSize();
+ packed_data.resize(packed_size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&packed_data));
+ uint8* end = packed_message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(packed_size, end - start);
+ EXPECT_TRUE(packed_message2.ParseFromString(packed_data));
+ TestUtil::ExpectPackedFieldsSet(packed_message2);
+}
+
+// Test the generated SerializeWithCachedSizes() by forcing the buffer to write
+// one byte at a time.
+TEST(GeneratedMessageTest, SerializationToStream) {
+ unittest::TestAllTypes message1, message2;
+ TestUtil::SetAllFields(&message1);
+ int size = message1.ByteSize();
+ string data;
+ data.resize(size);
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+ EXPECT_TRUE(message2.ParseFromString(data));
+ TestUtil::ExpectAllFieldsSet(message2);
+
+}
+
+TEST(GeneratedMessageTest, PackedFieldsSerializationToStream) {
+ unittest::TestPackedTypes message1, message2;
+ TestUtil::SetPackedFields(&message1);
+ int size = message1.ByteSize();
+ string data;
+ data.resize(size);
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+ EXPECT_TRUE(message2.ParseFromString(data));
+ TestUtil::ExpectPackedFieldsSet(message2);
+}
+
+
+TEST(GeneratedMessageTest, Required) {
+ // Test that IsInitialized() returns false if required fields are missing.
+ unittest::TestRequired message;
+
+ EXPECT_FALSE(message.IsInitialized());
+ message.set_a(1);
+ EXPECT_FALSE(message.IsInitialized());
+ message.set_b(2);
+ EXPECT_FALSE(message.IsInitialized());
+ message.set_c(3);
+ EXPECT_TRUE(message.IsInitialized());
+}
+
+TEST(GeneratedMessageTest, RequiredForeign) {
+ // Test that IsInitialized() returns false if required fields in nested
+ // messages are missing.
+ unittest::TestRequiredForeign message;
+
+ EXPECT_TRUE(message.IsInitialized());
+
+ message.mutable_optional_message();
+ EXPECT_FALSE(message.IsInitialized());
+
+ message.mutable_optional_message()->set_a(1);
+ message.mutable_optional_message()->set_b(2);
+ message.mutable_optional_message()->set_c(3);
+ EXPECT_TRUE(message.IsInitialized());
+
+ message.add_repeated_message();
+ EXPECT_FALSE(message.IsInitialized());
+
+ message.mutable_repeated_message(0)->set_a(1);
+ message.mutable_repeated_message(0)->set_b(2);
+ message.mutable_repeated_message(0)->set_c(3);
+ EXPECT_TRUE(message.IsInitialized());
+}
+
+TEST(GeneratedMessageTest, ForeignNested) {
+ // Test that TestAllTypes::NestedMessage can be embedded directly into
+ // another message.
+ unittest::TestForeignNested message;
+
+ // If this compiles and runs without crashing, it must work. We have
+ // nothing more to test.
+ unittest::TestAllTypes::NestedMessage* nested =
+ message.mutable_foreign_nested();
+ nested->set_bb(1);
+}
+
+TEST(GeneratedMessageTest, ReallyLargeTagNumber) {
+ // Test that really large tag numbers don't break anything.
+ unittest::TestReallyLargeTagNumber message1, message2;
+ string data;
+
+ // For the most part, if this compiles and runs then we're probably good.
+ // (The most likely cause for failure would be if something were attempting
+ // to allocate a lookup table of some sort using tag numbers as the index.)
+ // We'll try serializing just for fun.
+ message1.set_a(1234);
+ message1.set_bb(5678);
+ message1.SerializeToString(&data);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(1234, message2.a());
+ EXPECT_EQ(5678, message2.bb());
+}
+
+TEST(GeneratedMessageTest, MutualRecursion) {
+ // Test that mutually-recursive message types work.
+ unittest::TestMutualRecursionA message;
+ unittest::TestMutualRecursionA* nested = message.mutable_bb()->mutable_a();
+ unittest::TestMutualRecursionA* nested2 = nested->mutable_bb()->mutable_a();
+
+ // Again, if the above compiles and runs, that's all we really have to
+ // test, but just for run we'll check that the system didn't somehow come
+ // up with a pointer loop...
+ EXPECT_NE(&message, nested);
+ EXPECT_NE(&message, nested2);
+ EXPECT_NE(nested, nested2);
+}
+
+TEST(GeneratedMessageTest, CamelCaseFieldNames) {
+ // This test is mainly checking that the following compiles, which verifies
+ // that the field names were coerced to lower-case.
+ //
+ // Protocol buffers standard style is to use lowercase-with-underscores for
+ // field names. Some old proto1 .protos unfortunately used camel-case field
+ // names. In proto1, these names were forced to lower-case. So, we do the
+ // same thing in proto2.
+
+ unittest::TestCamelCaseFieldNames message;
+
+ message.set_primitivefield(2);
+ message.set_stringfield("foo");
+ message.set_enumfield(unittest::FOREIGN_FOO);
+ message.mutable_messagefield()->set_c(6);
+
+ message.add_repeatedprimitivefield(8);
+ message.add_repeatedstringfield("qux");
+ message.add_repeatedenumfield(unittest::FOREIGN_BAR);
+ message.add_repeatedmessagefield()->set_c(15);
+
+ EXPECT_EQ(2, message.primitivefield());
+ EXPECT_EQ("foo", message.stringfield());
+ EXPECT_EQ(unittest::FOREIGN_FOO, message.enumfield());
+ EXPECT_EQ(6, message.messagefield().c());
+
+ EXPECT_EQ(8, message.repeatedprimitivefield(0));
+ EXPECT_EQ("qux", message.repeatedstringfield(0));
+ EXPECT_EQ(unittest::FOREIGN_BAR, message.repeatedenumfield(0));
+ EXPECT_EQ(15, message.repeatedmessagefield(0).c());
+}
+
+TEST(GeneratedMessageTest, TestConflictingSymbolNames) {
+ // test_bad_identifiers.proto successfully compiled, then it works. The
+ // following is just a token usage to insure that the code is, in fact,
+ // being compiled and linked.
+
+ protobuf_unittest::TestConflictingSymbolNames message;
+ message.set_uint32(1);
+ EXPECT_EQ(3, message.ByteSize());
+
+ message.set_friend_(5);
+ EXPECT_EQ(5, message.friend_());
+
+ message.set_class_(6);
+ EXPECT_EQ(6, message.class_());
+
+ // Instantiate extension template functions to test conflicting template
+ // parameter names.
+ typedef protobuf_unittest::TestConflictingSymbolNamesExtension ExtensionMessage;
+ message.AddExtension(ExtensionMessage::repeated_int32_ext, 123);
+ EXPECT_EQ(123,
+ message.GetExtension(ExtensionMessage::repeated_int32_ext, 0));
+}
+
+TEST(GeneratedMessageTest, TestConflictingEnumNames) {
+ protobuf_unittest::TestConflictingEnumNames message;
+ message.set_conflicting_enum(protobuf_unittest::TestConflictingEnumNames_NestedConflictingEnum_and_);
+ EXPECT_EQ(1, message.conflicting_enum());
+ message.set_conflicting_enum(protobuf_unittest::TestConflictingEnumNames_NestedConflictingEnum_XOR);
+ EXPECT_EQ(5, message.conflicting_enum());
+
+
+ protobuf_unittest::ConflictingEnum conflicting_enum;
+ conflicting_enum = protobuf_unittest::NOT_EQ;
+ EXPECT_EQ(1, conflicting_enum);
+ conflicting_enum = protobuf_unittest::return_;
+ EXPECT_EQ(3, conflicting_enum);
+}
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+
+TEST(GeneratedMessageTest, TestOptimizedForSize) {
+ // We rely on the tests in reflection_ops_unittest and wire_format_unittest
+ // to really test that reflection-based methods work. Here we are mostly
+ // just making sure that TestOptimizedForSize actually builds and seems to
+ // function.
+
+ protobuf_unittest::TestOptimizedForSize message, message2;
+ message.set_i(1);
+ message.mutable_msg()->set_c(2);
+ message2.CopyFrom(message);
+ EXPECT_EQ(1, message2.i());
+ EXPECT_EQ(2, message2.msg().c());
+}
+
+TEST(GeneratedMessageTest, TestEmbedOptimizedForSize) {
+ // Verifies that something optimized for speed can contain something optimized
+ // for size.
+
+ protobuf_unittest::TestEmbedOptimizedForSize message, message2;
+ message.mutable_optional_message()->set_i(1);
+ message.add_repeated_message()->mutable_msg()->set_c(2);
+ string data;
+ message.SerializeToString(&data);
+ ASSERT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(1, message2.optional_message().i());
+ EXPECT_EQ(2, message2.repeated_message(0).msg().c());
+}
+
+TEST(GeneratedMessageTest, TestSpaceUsed) {
+ unittest::TestAllTypes message1;
+ // sizeof provides a lower bound on SpaceUsed().
+ EXPECT_LE(sizeof(unittest::TestAllTypes), message1.SpaceUsed());
+ const int empty_message_size = message1.SpaceUsed();
+
+ // Setting primitive types shouldn't affect the space used.
+ message1.set_optional_int32(123);
+ message1.set_optional_int64(12345);
+ message1.set_optional_uint32(123);
+ message1.set_optional_uint64(12345);
+ EXPECT_EQ(empty_message_size, message1.SpaceUsed());
+
+ // On some STL implementations, setting the string to a small value should
+ // only increase SpaceUsed() by the size of a string object, though this is
+ // not true everywhere.
+ message1.set_optional_string("abc");
+ EXPECT_LE(empty_message_size + sizeof(string), message1.SpaceUsed());
+
+ // Setting a string to a value larger than the string object itself should
+ // increase SpaceUsed(), because it cannot store the value internally.
+ message1.set_optional_string(string(sizeof(string) + 1, 'x'));
+ int min_expected_increase = message1.optional_string().capacity() +
+ sizeof(string);
+ EXPECT_LE(empty_message_size + min_expected_increase,
+ message1.SpaceUsed());
+
+ int previous_size = message1.SpaceUsed();
+ // Adding an optional message should increase the size by the size of the
+ // nested message type. NestedMessage is simple enough (1 int field) that it
+ // is equal to sizeof(NestedMessage)
+ message1.mutable_optional_nested_message();
+ ASSERT_EQ(sizeof(unittest::TestAllTypes::NestedMessage),
+ message1.optional_nested_message().SpaceUsed());
+ EXPECT_EQ(previous_size +
+ sizeof(unittest::TestAllTypes::NestedMessage),
+ message1.SpaceUsed());
+}
+
+TEST(GeneratedMessageTest, TestOneofSpaceUsed) {
+ unittest::TestOneof2 message1;
+ EXPECT_LE(sizeof(unittest::TestOneof2), message1.SpaceUsed());
+
+ const int empty_message_size = message1.SpaceUsed();
+ // Setting primitive types shouldn't affect the space used.
+ message1.set_foo_int(123);
+ message1.set_bar_int(12345);
+ EXPECT_EQ(empty_message_size, message1.SpaceUsed());
+
+ // Setting a string in oneof to a small value should only increase SpaceUsed()
+ // by the size of a string object.
+ message1.set_foo_string("abc");
+ EXPECT_LE(empty_message_size + sizeof(string), message1.SpaceUsed());
+
+ // Setting a string in oneof to a value larger than the string object itself
+ // should increase SpaceUsed(), because it cannot store the value internally.
+ message1.set_foo_string(string(sizeof(string) + 1, 'x'));
+ int min_expected_increase = message1.foo_string().capacity() +
+ sizeof(string);
+ EXPECT_LE(empty_message_size + min_expected_increase,
+ message1.SpaceUsed());
+
+ // Setting a message in oneof should delete the other fields and increase the
+ // size by the size of the nested message type. NestedMessage is simple enough
+ // that it is equal to sizeof(NestedMessage)
+ message1.mutable_foo_message();
+ ASSERT_EQ(sizeof(unittest::TestOneof2::NestedMessage),
+ message1.foo_message().SpaceUsed());
+ EXPECT_EQ(empty_message_size +
+ sizeof(unittest::TestOneof2::NestedMessage),
+ message1.SpaceUsed());
+}
+
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+
+
+TEST(GeneratedMessageTest, FieldConstantValues) {
+ unittest::TestRequired message;
+ EXPECT_EQ(unittest::TestAllTypes_NestedMessage::kBbFieldNumber, 1);
+ EXPECT_EQ(unittest::TestAllTypes::kOptionalInt32FieldNumber, 1);
+ EXPECT_EQ(unittest::TestAllTypes::kOptionalgroupFieldNumber, 16);
+ EXPECT_EQ(unittest::TestAllTypes::kOptionalNestedMessageFieldNumber, 18);
+ EXPECT_EQ(unittest::TestAllTypes::kOptionalNestedEnumFieldNumber, 21);
+ EXPECT_EQ(unittest::TestAllTypes::kRepeatedInt32FieldNumber, 31);
+ EXPECT_EQ(unittest::TestAllTypes::kRepeatedgroupFieldNumber, 46);
+ EXPECT_EQ(unittest::TestAllTypes::kRepeatedNestedMessageFieldNumber, 48);
+ EXPECT_EQ(unittest::TestAllTypes::kRepeatedNestedEnumFieldNumber, 51);
+}
+
+TEST(GeneratedMessageTest, ExtensionConstantValues) {
+ EXPECT_EQ(unittest::TestRequired::kSingleFieldNumber, 1000);
+ EXPECT_EQ(unittest::TestRequired::kMultiFieldNumber, 1001);
+ EXPECT_EQ(unittest::kOptionalInt32ExtensionFieldNumber, 1);
+ EXPECT_EQ(unittest::kOptionalgroupExtensionFieldNumber, 16);
+ EXPECT_EQ(unittest::kOptionalNestedMessageExtensionFieldNumber, 18);
+ EXPECT_EQ(unittest::kOptionalNestedEnumExtensionFieldNumber, 21);
+ EXPECT_EQ(unittest::kRepeatedInt32ExtensionFieldNumber, 31);
+ EXPECT_EQ(unittest::kRepeatedgroupExtensionFieldNumber, 46);
+ EXPECT_EQ(unittest::kRepeatedNestedMessageExtensionFieldNumber, 48);
+ EXPECT_EQ(unittest::kRepeatedNestedEnumExtensionFieldNumber, 51);
+}
+
+TEST(GeneratedMessageTest, ParseFromTruncated) {
+ const string long_string = string(128, 'q');
+ FileDescriptorProto p;
+ p.add_extension()->set_name(long_string);
+ const string msg = p.SerializeAsString();
+ int successful_count = 0;
+ for (int i = 0; i <= msg.size(); i++) {
+ if (p.ParseFromArray(msg.c_str(), i)) {
+ ++successful_count;
+ }
+ }
+ // We don't really care about how often we succeeded.
+ // As long as we didn't crash, we're happy.
+ EXPECT_GE(successful_count, 1);
+}
+
+// ===================================================================
+
+TEST(GeneratedEnumTest, EnumValuesAsSwitchCases) {
+ // Test that our nested enum values can be used as switch cases. This test
+ // doesn't actually do anything, the proof that it works is that it
+ // compiles.
+ int i =0;
+ unittest::TestAllTypes::NestedEnum a = unittest::TestAllTypes::BAR;
+ switch (a) {
+ case unittest::TestAllTypes::FOO:
+ i = 1;
+ break;
+ case unittest::TestAllTypes::BAR:
+ i = 2;
+ break;
+ case unittest::TestAllTypes::BAZ:
+ i = 3;
+ break;
+ case unittest::TestAllTypes::NEG:
+ i = -1;
+ break;
+ // no default case: We want to make sure the compiler recognizes that
+ // all cases are covered. (GCC warns if you do not cover all cases of
+ // an enum in a switch.)
+ }
+
+ // Token check just for fun.
+ EXPECT_EQ(2, i);
+}
+
+TEST(GeneratedEnumTest, IsValidValue) {
+ // Test enum IsValidValue.
+ EXPECT_TRUE(unittest::TestAllTypes::NestedEnum_IsValid(1));
+ EXPECT_TRUE(unittest::TestAllTypes::NestedEnum_IsValid(2));
+ EXPECT_TRUE(unittest::TestAllTypes::NestedEnum_IsValid(3));
+
+ EXPECT_FALSE(unittest::TestAllTypes::NestedEnum_IsValid(0));
+ EXPECT_FALSE(unittest::TestAllTypes::NestedEnum_IsValid(4));
+
+ // Make sure it also works when there are dups.
+ EXPECT_TRUE(unittest::TestEnumWithDupValue_IsValid(1));
+ EXPECT_TRUE(unittest::TestEnumWithDupValue_IsValid(2));
+ EXPECT_TRUE(unittest::TestEnumWithDupValue_IsValid(3));
+
+ EXPECT_FALSE(unittest::TestEnumWithDupValue_IsValid(0));
+ EXPECT_FALSE(unittest::TestEnumWithDupValue_IsValid(4));
+}
+
+TEST(GeneratedEnumTest, MinAndMax) {
+ EXPECT_EQ(unittest::TestAllTypes::NEG,
+ unittest::TestAllTypes::NestedEnum_MIN);
+ EXPECT_EQ(unittest::TestAllTypes::BAZ,
+ unittest::TestAllTypes::NestedEnum_MAX);
+ EXPECT_EQ(4, unittest::TestAllTypes::NestedEnum_ARRAYSIZE);
+
+ EXPECT_EQ(unittest::FOREIGN_FOO, unittest::ForeignEnum_MIN);
+ EXPECT_EQ(unittest::FOREIGN_BAZ, unittest::ForeignEnum_MAX);
+ EXPECT_EQ(7, unittest::ForeignEnum_ARRAYSIZE);
+
+ EXPECT_EQ(1, unittest::TestEnumWithDupValue_MIN);
+ EXPECT_EQ(3, unittest::TestEnumWithDupValue_MAX);
+ EXPECT_EQ(4, unittest::TestEnumWithDupValue_ARRAYSIZE);
+
+ EXPECT_EQ(unittest::SPARSE_E, unittest::TestSparseEnum_MIN);
+ EXPECT_EQ(unittest::SPARSE_C, unittest::TestSparseEnum_MAX);
+ EXPECT_EQ(12589235, unittest::TestSparseEnum_ARRAYSIZE);
+
+ // Make sure we can take the address of _MIN, _MAX and _ARRAYSIZE.
+ void* null_pointer = 0; // NULL may be integer-type, not pointer-type.
+ EXPECT_NE(null_pointer, &unittest::TestAllTypes::NestedEnum_MIN);
+ EXPECT_NE(null_pointer, &unittest::TestAllTypes::NestedEnum_MAX);
+ EXPECT_NE(null_pointer, &unittest::TestAllTypes::NestedEnum_ARRAYSIZE);
+
+ EXPECT_NE(null_pointer, &unittest::ForeignEnum_MIN);
+ EXPECT_NE(null_pointer, &unittest::ForeignEnum_MAX);
+ EXPECT_NE(null_pointer, &unittest::ForeignEnum_ARRAYSIZE);
+
+ // Make sure we can use _MIN and _MAX as switch cases.
+ switch (unittest::SPARSE_A) {
+ case unittest::TestSparseEnum_MIN:
+ case unittest::TestSparseEnum_MAX:
+ break;
+ default:
+ break;
+ }
+}
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+
+TEST(GeneratedEnumTest, Name) {
+ // "Names" in the presence of dup values are a bit arbitrary.
+ EXPECT_EQ("FOO1", unittest::TestEnumWithDupValue_Name(unittest::FOO1));
+ EXPECT_EQ("FOO1", unittest::TestEnumWithDupValue_Name(unittest::FOO2));
+
+ EXPECT_EQ("SPARSE_A", unittest::TestSparseEnum_Name(unittest::SPARSE_A));
+ EXPECT_EQ("SPARSE_B", unittest::TestSparseEnum_Name(unittest::SPARSE_B));
+ EXPECT_EQ("SPARSE_C", unittest::TestSparseEnum_Name(unittest::SPARSE_C));
+ EXPECT_EQ("SPARSE_D", unittest::TestSparseEnum_Name(unittest::SPARSE_D));
+ EXPECT_EQ("SPARSE_E", unittest::TestSparseEnum_Name(unittest::SPARSE_E));
+ EXPECT_EQ("SPARSE_F", unittest::TestSparseEnum_Name(unittest::SPARSE_F));
+ EXPECT_EQ("SPARSE_G", unittest::TestSparseEnum_Name(unittest::SPARSE_G));
+}
+
+TEST(GeneratedEnumTest, Parse) {
+ unittest::TestEnumWithDupValue dup_value = unittest::FOO1;
+ EXPECT_TRUE(unittest::TestEnumWithDupValue_Parse("FOO1", &dup_value));
+ EXPECT_EQ(unittest::FOO1, dup_value);
+ EXPECT_TRUE(unittest::TestEnumWithDupValue_Parse("FOO2", &dup_value));
+ EXPECT_EQ(unittest::FOO2, dup_value);
+ EXPECT_FALSE(unittest::TestEnumWithDupValue_Parse("FOO", &dup_value));
+}
+
+TEST(GeneratedEnumTest, GetEnumDescriptor) {
+ EXPECT_EQ(unittest::TestAllTypes::NestedEnum_descriptor(),
+ GetEnumDescriptor<unittest::TestAllTypes::NestedEnum>());
+ EXPECT_EQ(unittest::ForeignEnum_descriptor(),
+ GetEnumDescriptor<unittest::ForeignEnum>());
+ EXPECT_EQ(unittest::TestEnumWithDupValue_descriptor(),
+ GetEnumDescriptor<unittest::TestEnumWithDupValue>());
+ EXPECT_EQ(unittest::TestSparseEnum_descriptor(),
+ GetEnumDescriptor<unittest::TestSparseEnum>());
+}
+
+enum NonProtoEnum {
+ kFoo = 1,
+};
+
+TEST(GeneratedEnumTest, IsProtoEnumTypeTrait) {
+ EXPECT_TRUE(is_proto_enum<unittest::TestAllTypes::NestedEnum>::value);
+ EXPECT_TRUE(is_proto_enum<unittest::ForeignEnum>::value);
+ EXPECT_TRUE(is_proto_enum<unittest::TestEnumWithDupValue>::value);
+ EXPECT_TRUE(is_proto_enum<unittest::TestSparseEnum>::value);
+
+ EXPECT_FALSE(is_proto_enum<int>::value);
+ EXPECT_FALSE(is_proto_enum<NonProtoEnum>::value);
+}
+
+#endif // PROTOBUF_TEST_NO_DESCRIPTORS
+
+// ===================================================================
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+
+// Support code for testing services.
+class GeneratedServiceTest : public testing::Test {
+ protected:
+ class MockTestService : public unittest::TestService {
+ public:
+ MockTestService()
+ : called_(false),
+ method_(""),
+ controller_(NULL),
+ request_(NULL),
+ response_(NULL),
+ done_(NULL) {}
+
+ ~MockTestService() {}
+
+ void Reset() { called_ = false; }
+
+ // implements TestService ----------------------------------------
+
+ void Foo(RpcController* controller,
+ const unittest::FooRequest* request,
+ unittest::FooResponse* response,
+ Closure* done) {
+ ASSERT_FALSE(called_);
+ called_ = true;
+ method_ = "Foo";
+ controller_ = controller;
+ request_ = request;
+ response_ = response;
+ done_ = done;
+ }
+
+ void Bar(RpcController* controller,
+ const unittest::BarRequest* request,
+ unittest::BarResponse* response,
+ Closure* done) {
+ ASSERT_FALSE(called_);
+ called_ = true;
+ method_ = "Bar";
+ controller_ = controller;
+ request_ = request;
+ response_ = response;
+ done_ = done;
+ }
+
+ // ---------------------------------------------------------------
+
+ bool called_;
+ string method_;
+ RpcController* controller_;
+ const Message* request_;
+ Message* response_;
+ Closure* done_;
+ };
+
+ class MockRpcChannel : public RpcChannel {
+ public:
+ MockRpcChannel()
+ : called_(false),
+ method_(NULL),
+ controller_(NULL),
+ request_(NULL),
+ response_(NULL),
+ done_(NULL),
+ destroyed_(NULL) {}
+
+ ~MockRpcChannel() {
+ if (destroyed_ != NULL) *destroyed_ = true;
+ }
+
+ void Reset() { called_ = false; }
+
+ // implements TestService ----------------------------------------
+
+ void CallMethod(const MethodDescriptor* method,
+ RpcController* controller,
+ const Message* request,
+ Message* response,
+ Closure* done) {
+ ASSERT_FALSE(called_);
+ called_ = true;
+ method_ = method;
+ controller_ = controller;
+ request_ = request;
+ response_ = response;
+ done_ = done;
+ }
+
+ // ---------------------------------------------------------------
+
+ bool called_;
+ const MethodDescriptor* method_;
+ RpcController* controller_;
+ const Message* request_;
+ Message* response_;
+ Closure* done_;
+ bool* destroyed_;
+ };
+
+ class MockController : public RpcController {
+ public:
+ void Reset() {
+ ADD_FAILURE() << "Reset() not expected during this test.";
+ }
+ bool Failed() const {
+ ADD_FAILURE() << "Failed() not expected during this test.";
+ return false;
+ }
+ string ErrorText() const {
+ ADD_FAILURE() << "ErrorText() not expected during this test.";
+ return "";
+ }
+ void StartCancel() {
+ ADD_FAILURE() << "StartCancel() not expected during this test.";
+ }
+ void SetFailed(const string& reason) {
+ ADD_FAILURE() << "SetFailed() not expected during this test.";
+ }
+ bool IsCanceled() const {
+ ADD_FAILURE() << "IsCanceled() not expected during this test.";
+ return false;
+ }
+ void NotifyOnCancel(Closure* callback) {
+ ADD_FAILURE() << "NotifyOnCancel() not expected during this test.";
+ }
+ };
+
+ GeneratedServiceTest()
+ : descriptor_(unittest::TestService::descriptor()),
+ foo_(descriptor_->FindMethodByName("Foo")),
+ bar_(descriptor_->FindMethodByName("Bar")),
+ stub_(&mock_channel_),
+ done_(::google::protobuf::internal::NewPermanentCallback(&DoNothing)) {}
+
+ virtual void SetUp() {
+ ASSERT_TRUE(foo_ != NULL);
+ ASSERT_TRUE(bar_ != NULL);
+ }
+
+ const ServiceDescriptor* descriptor_;
+ const MethodDescriptor* foo_;
+ const MethodDescriptor* bar_;
+
+ MockTestService mock_service_;
+ MockController mock_controller_;
+
+ MockRpcChannel mock_channel_;
+ unittest::TestService::Stub stub_;
+
+ // Just so we don't have to re-define these with every test.
+ unittest::FooRequest foo_request_;
+ unittest::FooResponse foo_response_;
+ unittest::BarRequest bar_request_;
+ unittest::BarResponse bar_response_;
+ google::protobuf::scoped_ptr<Closure> done_;
+};
+
+TEST_F(GeneratedServiceTest, GetDescriptor) {
+ // Test that GetDescriptor() works.
+
+ EXPECT_EQ(descriptor_, mock_service_.GetDescriptor());
+}
+
+TEST_F(GeneratedServiceTest, GetChannel) {
+ EXPECT_EQ(&mock_channel_, stub_.channel());
+}
+
+TEST_F(GeneratedServiceTest, OwnsChannel) {
+ MockRpcChannel* channel = new MockRpcChannel;
+ bool destroyed = false;
+ channel->destroyed_ = &destroyed;
+
+ {
+ unittest::TestService::Stub owning_stub(channel,
+ Service::STUB_OWNS_CHANNEL);
+ EXPECT_FALSE(destroyed);
+ }
+
+ EXPECT_TRUE(destroyed);
+}
+
+TEST_F(GeneratedServiceTest, CallMethod) {
+ // Test that CallMethod() works.
+
+ // Call Foo() via CallMethod().
+ mock_service_.CallMethod(foo_, &mock_controller_,
+ &foo_request_, &foo_response_, done_.get());
+
+ ASSERT_TRUE(mock_service_.called_);
+
+ EXPECT_EQ("Foo" , mock_service_.method_ );
+ EXPECT_EQ(&mock_controller_, mock_service_.controller_);
+ EXPECT_EQ(&foo_request_ , mock_service_.request_ );
+ EXPECT_EQ(&foo_response_ , mock_service_.response_ );
+ EXPECT_EQ(done_.get() , mock_service_.done_ );
+
+ // Try again, but call Bar() instead.
+ mock_service_.Reset();
+ mock_service_.CallMethod(bar_, &mock_controller_,
+ &bar_request_, &bar_response_, done_.get());
+
+ ASSERT_TRUE(mock_service_.called_);
+ EXPECT_EQ("Bar", mock_service_.method_);
+}
+
+TEST_F(GeneratedServiceTest, CallMethodTypeFailure) {
+ // Verify death if we call Foo() with Bar's message types.
+
+#ifdef PROTOBUF_HAS_DEATH_TEST // death tests do not work on Windows yet
+ EXPECT_DEBUG_DEATH(
+ mock_service_.CallMethod(foo_, &mock_controller_,
+ &foo_request_, &bar_response_, done_.get()),
+ "dynamic_cast");
+
+ mock_service_.Reset();
+ EXPECT_DEBUG_DEATH(
+ mock_service_.CallMethod(foo_, &mock_controller_,
+ &bar_request_, &foo_response_, done_.get()),
+ "dynamic_cast");
+#endif // PROTOBUF_HAS_DEATH_TEST
+}
+
+TEST_F(GeneratedServiceTest, GetPrototypes) {
+ // Test Get{Request,Response}Prototype() methods.
+
+ EXPECT_EQ(&unittest::FooRequest::default_instance(),
+ &mock_service_.GetRequestPrototype(foo_));
+ EXPECT_EQ(&unittest::BarRequest::default_instance(),
+ &mock_service_.GetRequestPrototype(bar_));
+
+ EXPECT_EQ(&unittest::FooResponse::default_instance(),
+ &mock_service_.GetResponsePrototype(foo_));
+ EXPECT_EQ(&unittest::BarResponse::default_instance(),
+ &mock_service_.GetResponsePrototype(bar_));
+}
+
+TEST_F(GeneratedServiceTest, Stub) {
+ // Test that the stub class works.
+
+ // Call Foo() via the stub.
+ stub_.Foo(&mock_controller_, &foo_request_, &foo_response_, done_.get());
+
+ ASSERT_TRUE(mock_channel_.called_);
+
+ EXPECT_EQ(foo_ , mock_channel_.method_ );
+ EXPECT_EQ(&mock_controller_, mock_channel_.controller_);
+ EXPECT_EQ(&foo_request_ , mock_channel_.request_ );
+ EXPECT_EQ(&foo_response_ , mock_channel_.response_ );
+ EXPECT_EQ(done_.get() , mock_channel_.done_ );
+
+ // Call Bar() via the stub.
+ mock_channel_.Reset();
+ stub_.Bar(&mock_controller_, &bar_request_, &bar_response_, done_.get());
+
+ ASSERT_TRUE(mock_channel_.called_);
+ EXPECT_EQ(bar_, mock_channel_.method_);
+}
+
+TEST_F(GeneratedServiceTest, NotImplemented) {
+ // Test that failing to implement a method of a service causes it to fail
+ // with a "not implemented" error message.
+
+ // A service which doesn't implement any methods.
+ class UnimplementedService : public unittest::TestService {
+ public:
+ UnimplementedService() {}
+ };
+
+ UnimplementedService unimplemented_service;
+
+ // And a controller which expects to get a "not implemented" error.
+ class ExpectUnimplementedController : public MockController {
+ public:
+ ExpectUnimplementedController() : called_(false) {}
+
+ void SetFailed(const string& reason) {
+ EXPECT_FALSE(called_);
+ called_ = true;
+ EXPECT_EQ("Method Foo() not implemented.", reason);
+ }
+
+ bool called_;
+ };
+
+ ExpectUnimplementedController controller;
+
+ // Call Foo.
+ unimplemented_service.Foo(&controller, &foo_request_, &foo_response_,
+ done_.get());
+
+ EXPECT_TRUE(controller.called_);
+}
+
+// ===================================================================
+
+class OneofTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ }
+
+ void ExpectEnumCasesWork(const unittest::TestOneof2 &message) {
+ switch (message.foo_case()) {
+ case unittest::TestOneof2::kFooInt:
+ EXPECT_TRUE(message.has_foo_int());
+ break;
+ case unittest::TestOneof2::kFooString:
+ EXPECT_TRUE(message.has_foo_string());
+ break;
+ case unittest::TestOneof2::kFooCord:
+ EXPECT_TRUE(message.has_foo_cord());
+ break;
+ case unittest::TestOneof2::kFooStringPiece:
+ EXPECT_TRUE(message.has_foo_string_piece());
+ break;
+ case unittest::TestOneof2::kFooBytes:
+ EXPECT_TRUE(message.has_foo_bytes());
+ break;
+ case unittest::TestOneof2::kFooEnum:
+ EXPECT_TRUE(message.has_foo_enum());
+ break;
+ case unittest::TestOneof2::kFooMessage:
+ EXPECT_TRUE(message.has_foo_message());
+ break;
+ case unittest::TestOneof2::kFoogroup:
+ EXPECT_TRUE(message.has_foogroup());
+ break;
+ case unittest::TestOneof2::kFooLazyMessage:
+ EXPECT_TRUE(message.has_foo_lazy_message());
+ break;
+ case unittest::TestOneof2::FOO_NOT_SET:
+ break;
+ }
+ }
+};
+
+TEST_F(OneofTest, SettingOneFieldClearsOthers) {
+ unittest::TestOneof2 message;
+
+ message.set_foo_int(123);
+ EXPECT_TRUE(message.has_foo_int());
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message);
+
+ message.set_foo_string("foo");
+ EXPECT_TRUE(message.has_foo_string());
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message);
+
+
+ message.set_foo_bytes("qux");
+ EXPECT_TRUE(message.has_foo_bytes());
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message);
+
+ message.set_foo_enum(unittest::TestOneof2::FOO);
+ EXPECT_TRUE(message.has_foo_enum());
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message);
+
+ message.mutable_foo_message()->set_qux_int(234);
+ EXPECT_TRUE(message.has_foo_message());
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message);
+
+ message.mutable_foogroup()->set_a(345);
+ EXPECT_TRUE(message.has_foogroup());
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message);
+
+
+ // we repeat this because we didn't test if this properly clears other fields
+ // at the beginning.
+ message.set_foo_int(123);
+ EXPECT_TRUE(message.has_foo_int());
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message);
+}
+
+TEST_F(OneofTest, EnumCases) {
+ unittest::TestOneof2 message;
+
+ message.set_foo_int(123);
+ ExpectEnumCasesWork(message);
+ message.set_foo_string("foo");
+ ExpectEnumCasesWork(message);
+ message.set_foo_bytes("qux");
+ ExpectEnumCasesWork(message);
+ message.set_foo_enum(unittest::TestOneof2::FOO);
+ ExpectEnumCasesWork(message);
+ message.mutable_foo_message()->set_qux_int(234);
+ ExpectEnumCasesWork(message);
+ message.mutable_foogroup()->set_a(345);
+ ExpectEnumCasesWork(message);
+}
+
+TEST_F(OneofTest, PrimitiveType) {
+ unittest::TestOneof2 message;
+ // Unset field returns default value
+ EXPECT_EQ(message.foo_int(), 0);
+
+ message.set_foo_int(123);
+ EXPECT_TRUE(message.has_foo_int());
+ EXPECT_EQ(message.foo_int(), 123);
+ message.clear_foo_int();
+ EXPECT_FALSE(message.has_foo_int());
+}
+
+TEST_F(OneofTest, EnumType) {
+ unittest::TestOneof2 message;
+ // Unset field returns default value
+ EXPECT_EQ(message.foo_enum(), 1);
+
+ message.set_foo_enum(unittest::TestOneof2::FOO);
+ EXPECT_TRUE(message.has_foo_enum());
+ EXPECT_EQ(message.foo_enum(), unittest::TestOneof2::FOO);
+ message.clear_foo_enum();
+ EXPECT_FALSE(message.has_foo_enum());
+}
+
+TEST_F(OneofTest, SetString) {
+ // Check that setting a string field in various ways works
+ unittest::TestOneof2 message;
+
+ // Unset field returns default value
+ EXPECT_EQ(message.foo_string(), "");
+
+ message.set_foo_string("foo");
+ EXPECT_TRUE(message.has_foo_string());
+ EXPECT_EQ(message.foo_string(), "foo");
+ message.clear_foo_string();
+ EXPECT_FALSE(message.has_foo_string());
+
+ message.set_foo_string(string("bar"));
+ EXPECT_TRUE(message.has_foo_string());
+ EXPECT_EQ(message.foo_string(), "bar");
+ message.clear_foo_string();
+ EXPECT_FALSE(message.has_foo_string());
+
+
+ message.set_foo_string("qux", 3);
+ EXPECT_TRUE(message.has_foo_string());
+ EXPECT_EQ(message.foo_string(), "qux");
+ message.clear_foo_string();
+ EXPECT_FALSE(message.has_foo_string());
+
+ message.mutable_foo_string()->assign("quux");
+ EXPECT_TRUE(message.has_foo_string());
+ EXPECT_EQ(message.foo_string(), "quux");
+ message.clear_foo_string();
+ EXPECT_FALSE(message.has_foo_string());
+
+ message.set_foo_string("corge");
+ EXPECT_TRUE(message.has_foo_string());
+ EXPECT_EQ(message.foo_string(), "corge");
+ message.clear_foo_string();
+ EXPECT_FALSE(message.has_foo_string());
+}
+
+TEST_F(OneofTest, ReleaseString) {
+ // Check that release_foo() starts out NULL, and gives us a value
+ // that we can delete after it's been set.
+ unittest::TestOneof2 message;
+
+ EXPECT_EQ(NULL, message.release_foo_string());
+ EXPECT_FALSE(message.has_foo_string());
+
+ message.set_foo_string("blah");
+ EXPECT_TRUE(message.has_foo_string());
+ google::protobuf::scoped_ptr<string> str(message.release_foo_string());
+ EXPECT_FALSE(message.has_foo_string());
+ ASSERT_TRUE(str != NULL);
+ EXPECT_EQ("blah", *str);
+
+ EXPECT_EQ(NULL, message.release_foo_string());
+ EXPECT_FALSE(message.has_foo_string());
+}
+
+TEST_F(OneofTest, SetAllocatedString) {
+ // Check that set_allocated_foo() works for strings.
+ unittest::TestOneof2 message;
+
+ EXPECT_FALSE(message.has_foo_string());
+ const string kHello("hello");
+ message.set_foo_string(kHello);
+ EXPECT_TRUE(message.has_foo_string());
+
+ message.set_allocated_foo_string(NULL);
+ EXPECT_FALSE(message.has_foo_string());
+ EXPECT_EQ("", message.foo_string());
+
+ message.set_allocated_foo_string(new string(kHello));
+ EXPECT_TRUE(message.has_foo_string());
+ EXPECT_EQ(kHello, message.foo_string());
+}
+
+
+TEST_F(OneofTest, SetMessage) {
+ // Check that setting a message field works
+ unittest::TestOneof2 message;
+
+ // Unset field returns default instance
+ EXPECT_EQ(&message.foo_message(),
+ &unittest::TestOneof2_NestedMessage::default_instance());
+ EXPECT_EQ(message.foo_message().qux_int(), 0);
+
+ message.mutable_foo_message()->set_qux_int(234);
+ EXPECT_TRUE(message.has_foo_message());
+ EXPECT_EQ(message.foo_message().qux_int(), 234);
+ message.clear_foo_message();
+ EXPECT_FALSE(message.has_foo_message());
+}
+
+TEST_F(OneofTest, ReleaseMessage) {
+ // Check that release_foo() starts out NULL, and gives us a value
+ // that we can delete after it's been set.
+ unittest::TestOneof2 message;
+
+ EXPECT_EQ(NULL, message.release_foo_message());
+ EXPECT_FALSE(message.has_foo_message());
+
+ message.mutable_foo_message()->set_qux_int(1);
+ EXPECT_TRUE(message.has_foo_message());
+ google::protobuf::scoped_ptr<unittest::TestOneof2_NestedMessage> mes(
+ message.release_foo_message());
+ EXPECT_FALSE(message.has_foo_message());
+ ASSERT_TRUE(mes != NULL);
+ EXPECT_EQ(1, mes->qux_int());
+
+ EXPECT_EQ(NULL, message.release_foo_message());
+ EXPECT_FALSE(message.has_foo_message());
+}
+
+TEST_F(OneofTest, SetAllocatedMessage) {
+ // Check that set_allocated_foo() works for messages.
+ unittest::TestOneof2 message;
+
+ EXPECT_FALSE(message.has_foo_message());
+
+ message.mutable_foo_message()->set_qux_int(1);
+ EXPECT_TRUE(message.has_foo_message());
+
+ message.set_allocated_foo_message(NULL);
+ EXPECT_FALSE(message.has_foo_message());
+ EXPECT_EQ(&message.foo_message(),
+ &unittest::TestOneof2_NestedMessage::default_instance());
+
+ message.mutable_foo_message()->set_qux_int(1);
+ unittest::TestOneof2_NestedMessage* mes = message.release_foo_message();
+ ASSERT_TRUE(mes != NULL);
+ EXPECT_FALSE(message.has_foo_message());
+
+ message.set_allocated_foo_message(mes);
+ EXPECT_TRUE(message.has_foo_message());
+ EXPECT_EQ(1, message.foo_message().qux_int());
+}
+
+
+TEST_F(OneofTest, Clear) {
+ unittest::TestOneof2 message;
+
+ message.set_foo_int(1);
+ EXPECT_TRUE(message.has_foo_int());
+ message.clear_foo_int();
+ EXPECT_FALSE(message.has_foo_int());
+}
+
+TEST_F(OneofTest, Defaults) {
+ unittest::TestOneof2 message;
+
+ EXPECT_FALSE(message.has_foo_int());
+ EXPECT_EQ(message.foo_int(), 0);
+
+ EXPECT_FALSE(message.has_foo_string());
+ EXPECT_EQ(message.foo_string(), "");
+
+
+ EXPECT_FALSE(message.has_foo_bytes());
+ EXPECT_EQ(message.foo_bytes(), "");
+
+ EXPECT_FALSE(message.has_foo_enum());
+ EXPECT_EQ(message.foo_enum(), 1);
+
+ EXPECT_FALSE(message.has_foo_message());
+ EXPECT_EQ(message.foo_message().qux_int(), 0);
+
+ EXPECT_FALSE(message.has_foogroup());
+ EXPECT_EQ(message.foogroup().a(), 0);
+
+
+ EXPECT_FALSE(message.has_bar_int());
+ EXPECT_EQ(message.bar_int(), 5);
+
+ EXPECT_FALSE(message.has_bar_string());
+ EXPECT_EQ(message.bar_string(), "STRING");
+
+
+ EXPECT_FALSE(message.has_bar_bytes());
+ EXPECT_EQ(message.bar_bytes(), "BYTES");
+
+ EXPECT_FALSE(message.has_bar_enum());
+ EXPECT_EQ(message.bar_enum(), 2);
+}
+
+TEST_F(OneofTest, SwapWithEmpty) {
+ unittest::TestOneof2 message1, message2;
+ message1.set_foo_string("FOO");
+ EXPECT_TRUE(message1.has_foo_string());
+ message1.Swap(&message2);
+ EXPECT_FALSE(message1.has_foo_string());
+ EXPECT_TRUE(message2.has_foo_string());
+ EXPECT_EQ(message2.foo_string(), "FOO");
+}
+
+TEST_F(OneofTest, SwapWithSelf) {
+ unittest::TestOneof2 message;
+ message.set_foo_string("FOO");
+ EXPECT_TRUE(message.has_foo_string());
+ message.Swap(&message);
+ EXPECT_TRUE(message.has_foo_string());
+ EXPECT_EQ(message.foo_string(), "FOO");
+}
+
+TEST_F(OneofTest, SwapBothHasFields) {
+ unittest::TestOneof2 message1, message2;
+
+ message1.set_foo_string("FOO");
+ EXPECT_TRUE(message1.has_foo_string());
+ message2.mutable_foo_message()->set_qux_int(1);
+ EXPECT_TRUE(message2.has_foo_message());
+
+ message1.Swap(&message2);
+ EXPECT_FALSE(message1.has_foo_string());
+ EXPECT_FALSE(message2.has_foo_message());
+ EXPECT_TRUE(message1.has_foo_message());
+ EXPECT_EQ(message1.foo_message().qux_int(), 1);
+ EXPECT_TRUE(message2.has_foo_string());
+ EXPECT_EQ(message2.foo_string(), "FOO");
+}
+
+TEST_F(OneofTest, CopyConstructor) {
+ unittest::TestOneof2 message1;
+ message1.set_foo_bytes("FOO");
+
+ unittest::TestOneof2 message2(message1);
+ EXPECT_TRUE(message2.has_foo_bytes());
+ EXPECT_EQ(message2.foo_bytes(), "FOO");
+}
+
+TEST_F(OneofTest, CopyFrom) {
+ unittest::TestOneof2 message1, message2;
+ message1.set_foo_enum(unittest::TestOneof2::BAR);
+ EXPECT_TRUE(message1.has_foo_enum());
+
+ message2.CopyFrom(message1);
+ EXPECT_TRUE(message2.has_foo_enum());
+ EXPECT_EQ(message2.foo_enum(), unittest::TestOneof2::BAR);
+
+ // Copying from self should be a no-op.
+ message2.CopyFrom(message2);
+ EXPECT_TRUE(message2.has_foo_enum());
+ EXPECT_EQ(message2.foo_enum(), unittest::TestOneof2::BAR);
+}
+
+TEST_F(OneofTest, CopyAssignmentOperator) {
+ unittest::TestOneof2 message1;
+ message1.mutable_foo_message()->set_qux_int(123);
+ EXPECT_TRUE(message1.has_foo_message());
+
+ unittest::TestOneof2 message2;
+ message2 = message1;
+ EXPECT_EQ(message2.foo_message().qux_int(), 123);
+
+ // Make sure that self-assignment does something sane.
+ message2 = message2;
+ EXPECT_EQ(message2.foo_message().qux_int(), 123);
+}
+
+TEST_F(OneofTest, UpcastCopyFrom) {
+ // Test the CopyFrom method that takes in the generic const Message&
+ // parameter.
+ unittest::TestOneof2 message1, message2;
+ message1.mutable_foogroup()->set_a(123);
+ EXPECT_TRUE(message1.has_foogroup());
+
+ const Message* source = implicit_cast<const Message*>(&message1);
+ message2.CopyFrom(*source);
+
+ EXPECT_TRUE(message2.has_foogroup());
+ EXPECT_EQ(message2.foogroup().a(), 123);
+}
+
+// Test the generated SerializeWithCachedSizesToArray(),
+// This indirectly tests MergePartialFromCodedStream()
+// We have to test each field type separately because we cannot set them at the
+// same time
+TEST_F(OneofTest, SerializationToArray) {
+ // Primitive type
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_int(123);
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_int(), 123);
+ }
+
+ // String
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_string("foo");
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_string(), "foo");
+ }
+
+
+ // Bytes
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_bytes("qux");
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_bytes(), "qux");
+ }
+
+ // Enum
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_enum(unittest::TestOneof2::FOO);
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_enum(), unittest::TestOneof2::FOO);
+ }
+
+ // Message
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.mutable_foo_message()->set_qux_int(234);
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_message().qux_int(), 234);
+ }
+
+ // Group
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.mutable_foogroup()->set_a(345);
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foogroup().a(), 345);
+ }
+
+}
+
+// Test the generated SerializeWithCachedSizes() by forcing the buffer to write
+// one byte at a time.
+// This indirectly tests MergePartialFromCodedStream()
+// We have to test each field type separately because we cannot set them at the
+// same time
+TEST_F(OneofTest, SerializationToStream) {
+ // Primitive type
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_int(123);
+ int size = message1.ByteSize();
+ data.resize(size);
+
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_int(), 123);
+ }
+
+ // String
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_string("foo");
+ int size = message1.ByteSize();
+ data.resize(size);
+
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_string(), "foo");
+ }
+
+
+ // Bytes
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_bytes("qux");
+ int size = message1.ByteSize();
+ data.resize(size);
+
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_bytes(), "qux");
+ }
+
+ // Enum
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.set_foo_enum(unittest::TestOneof2::FOO);
+ int size = message1.ByteSize();
+ data.resize(size);
+
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_enum(), unittest::TestOneof2::FOO);
+ }
+
+ // Message
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.mutable_foo_message()->set_qux_int(234);
+ int size = message1.ByteSize();
+ data.resize(size);
+
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foo_message().qux_int(), 234);
+ }
+
+ // Group
+ {
+ unittest::TestOneof2 message1, message2;
+ string data;
+ message1.mutable_foogroup()->set_a(345);
+ int size = message1.ByteSize();
+ data.resize(size);
+
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+
+ EXPECT_TRUE(message2.ParseFromString(data));
+ EXPECT_EQ(message2.foogroup().a(), 345);
+ }
+
+}
+
+TEST_F(OneofTest, MergeFrom) {
+ unittest::TestOneof2 message1, message2;
+
+ message1.set_foo_int(123);
+ message2.MergeFrom(message1);
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message2);
+ EXPECT_TRUE(message2.has_foo_int());
+ EXPECT_EQ(message2.foo_int(), 123);
+
+ message1.set_foo_string("foo");
+ message2.MergeFrom(message1);
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message2);
+ EXPECT_TRUE(message2.has_foo_string());
+ EXPECT_EQ(message2.foo_string(), "foo");
+
+
+ message1.set_foo_bytes("qux");
+ message2.MergeFrom(message1);
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message2);
+ EXPECT_TRUE(message2.has_foo_bytes());
+ EXPECT_EQ(message2.foo_bytes(), "qux");
+
+ message1.set_foo_enum(unittest::TestOneof2::FOO);
+ message2.MergeFrom(message1);
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message2);
+ EXPECT_TRUE(message2.has_foo_enum());
+ EXPECT_EQ(message2.foo_enum(), unittest::TestOneof2::FOO);
+
+ message1.mutable_foo_message()->set_qux_int(234);
+ message2.MergeFrom(message1);
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message2);
+ EXPECT_TRUE(message2.has_foo_message());
+ EXPECT_EQ(message2.foo_message().qux_int(), 234);
+
+ message1.mutable_foogroup()->set_a(345);
+ message2.MergeFrom(message1);
+ TestUtil::ExpectAtMostOneFieldSetInOneof(message2);
+ EXPECT_TRUE(message2.has_foogroup());
+ EXPECT_EQ(message2.foogroup().a(), 345);
+
+}
+
+} // namespace cpp_unittest
+} // namespace cpp
+} // namespace compiler
+
+namespace no_generic_services_test {
+ // Verify that no class called "TestService" was defined in
+ // unittest_no_generic_services.pb.h by defining a different type by the same
+ // name. If such a service was generated, this will not compile.
+ struct TestService {
+ int i;
+ };
+}
+
+namespace compiler {
+namespace cpp {
+namespace cpp_unittest {
+
+TEST_F(GeneratedServiceTest, NoGenericServices) {
+ // Verify that non-services in unittest_no_generic_services.proto were
+ // generated.
+ no_generic_services_test::TestMessage message;
+ message.set_a(1);
+ message.SetExtension(no_generic_services_test::test_extension, 123);
+ no_generic_services_test::TestEnum e = no_generic_services_test::FOO;
+ EXPECT_EQ(e, 1);
+
+ // Verify that a ServiceDescriptor is generated for the service even if the
+ // class itself is not.
+ const FileDescriptor* file =
+ no_generic_services_test::TestMessage::descriptor()->file();
+
+ ASSERT_EQ(1, file->service_count());
+ EXPECT_EQ("TestService", file->service(0)->name());
+ ASSERT_EQ(1, file->service(0)->method_count());
+ EXPECT_EQ("Foo", file->service(0)->method(0)->name());
+}
+
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+
+// ===================================================================
+
+// This test must run last. It verifies that descriptors were or were not
+// initialized depending on whether PROTOBUF_TEST_NO_DESCRIPTORS was defined.
+// When this is defined, we skip all tests which are expected to trigger
+// descriptor initialization. This verifies that everything else still works
+// if descriptors are not initialized.
+TEST(DescriptorInitializationTest, Initialized) {
+#ifdef PROTOBUF_TEST_NO_DESCRIPTORS
+ bool should_have_descriptors = false;
+#else
+ bool should_have_descriptors = true;
+#endif
+
+ EXPECT_EQ(should_have_descriptors,
+ DescriptorPool::generated_pool()->InternalIsFileLoaded(
+ "google/protobuf/unittest.proto"));
+}
+
+} // namespace cpp_unittest
+
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.h
new file mode 100644
index 0000000000..69c8f44c1d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/cpp_unittest.h
@@ -0,0 +1,51 @@
+// 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.
+
+// This header declares the namespace google::protobuf::protobuf_unittest in order to expose
+// any problems with the generated class names. We use this header to ensure
+// unittest.cc will declare the namespace prior to other includes, while obeying
+// normal include ordering.
+//
+// When generating a class name of "foo.Bar" we must ensure we prefix the class
+// name with "::", in case the namespace google::protobuf::foo exists. We intentionally
+// trigger that case here by declaring google::protobuf::protobuf_unittest.
+//
+// See ClassName in helpers.h for more details.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CPP_UNITTEST_H__
+#define GOOGLE_PROTOBUF_COMPILER_CPP_UNITTEST_H__
+
+namespace google {
+namespace protobuf {
+namespace protobuf_unittest {}
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CPP_UNITTEST_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/metadata_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/metadata_test.cc
new file mode 100644
index 0000000000..edd30780a9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/cpp/metadata_test.cc
@@ -0,0 +1,242 @@
+// 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.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/cpp/cpp_helpers.h>
+#include <google/protobuf/compiler/cpp/cpp_generator.h>
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace cpp {
+namespace {
+
+// A CodeGenerator that captures the FileDescriptor it's passed as a
+// FileDescriptorProto.
+class DescriptorCapturingGenerator : public CodeGenerator {
+ public:
+ // Does not own file; file must outlive the Generator.
+ explicit DescriptorCapturingGenerator(FileDescriptorProto* file)
+ : file_(file) {}
+
+ virtual bool Generate(const FileDescriptor* file, const string& parameter,
+ GeneratorContext* context, string* error) const {
+ file->CopyTo(file_);
+ return true;
+ }
+
+ private:
+ FileDescriptorProto* file_;
+};
+
+class CppMetadataTest : public ::testing::Test {
+ public:
+ // Adds a file with name `filename` and content `data`.
+ void AddFile(const string& filename, const string& data) {
+ GOOGLE_CHECK_OK(File::SetContents(TestTempDir() + "/" + filename, data,
+ true));
+ }
+
+ // Tries to capture a FileDescriptorProto, GeneratedCodeInfo, and output
+ // code from the previously added file with name `filename`. Returns true on
+ // success. If pb_h is non-null, expects a .pb.h and a .pb.h.meta (copied to
+ // pb_h and pb_h_info respecfively); similarly for proto_h and proto_h_info.
+ bool CaptureMetadata(const string& filename, FileDescriptorProto* file,
+ string* pb_h, GeneratedCodeInfo* pb_h_info,
+ string* proto_h, GeneratedCodeInfo* proto_h_info,
+ string* pb_cc) {
+ google::protobuf::compiler::CommandLineInterface cli;
+ cli.SetInputsAreProtoPathRelative(true);
+
+ CppGenerator cpp_generator;
+ DescriptorCapturingGenerator capturing_generator(file);
+ cli.RegisterGenerator("--cpp_out", &cpp_generator, "");
+ cli.RegisterGenerator("--capture_out", &capturing_generator, "");
+
+ string proto_path = "-I" + TestTempDir();
+ string cpp_out =
+ "--cpp_out=annotate_headers=true,"
+ "annotation_pragma_name=pragma_name,"
+ "annotation_guard_name=guard_name:" +
+ TestTempDir();
+ string capture_out = "--capture_out=" + TestTempDir();
+
+ const char* argv[] = {"protoc", proto_path.c_str(), cpp_out.c_str(),
+ capture_out.c_str(), filename.c_str()};
+
+ if (cli.Run(5, argv) != 0) {
+ return false;
+ }
+
+ string output_base = TestTempDir() + "/" + StripProto(filename);
+
+ if (pb_cc != NULL) {
+ GOOGLE_CHECK_OK(
+ File::GetContents(output_base + ".pb.cc", pb_cc, true));
+ }
+
+ if (pb_h != NULL && pb_h_info != NULL) {
+ GOOGLE_CHECK_OK(
+ File::GetContents(output_base + ".pb.h", pb_h, true));
+ if (!DecodeMetadata(output_base + ".pb.h.meta", pb_h_info)) {
+ return false;
+ }
+ }
+
+ if (proto_h != NULL && proto_h_info != NULL) {
+ GOOGLE_CHECK_OK(File::GetContents(output_base + ".proto.h", proto_h,
+ true));
+ if (!DecodeMetadata(output_base + ".proto.h.meta", proto_h_info)) {
+ return false;
+ }
+ }
+
+ return true;
+ }
+
+ private:
+ // Decodes GeneratedCodeInfo stored in path and copies it to info.
+ // Returns true on success.
+ bool DecodeMetadata(const string& path, GeneratedCodeInfo* info) {
+ string data;
+ GOOGLE_CHECK_OK(File::GetContents(path, &data, true));
+ io::ArrayInputStream input(data.data(), data.size());
+ return info->ParseFromZeroCopyStream(&input);
+ }
+};
+
+const char kSmallTestFile[] =
+ "syntax = \"proto2\";\n"
+ "package foo;\n"
+ "enum Enum { VALUE = 0; }\n"
+ "message Message { }\n";
+
+// Finds the Annotation for a given source file and path (or returns null if it
+// couldn't).
+const GeneratedCodeInfo::Annotation* FindAnnotationOnPath(
+ const GeneratedCodeInfo& info, const string& source_file,
+ const vector<int>& path) {
+ for (int i = 0; i < info.annotation_size(); ++i) {
+ const GeneratedCodeInfo::Annotation* annotation = &info.annotation(i);
+ if (annotation->source_file() != source_file ||
+ annotation->path_size() != path.size()) {
+ continue;
+ }
+ int node = 0;
+ for (; node < path.size(); ++node) {
+ if (annotation->path(node) != path[node]) {
+ break;
+ }
+ }
+ if (node == path.size()) {
+ return annotation;
+ }
+ }
+ return NULL;
+}
+
+// Returns true if the provided annotation covers a given substring in
+// file_content.
+bool AnnotationMatchesSubstring(const string& file_content,
+ const GeneratedCodeInfo::Annotation* annotation,
+ const string& expected_text) {
+ uint32 begin = annotation->begin();
+ uint32 end = annotation->end();
+ if (end < begin || end > file_content.size()) {
+ return false;
+ }
+ return file_content.substr(begin, end - begin) == expected_text;
+}
+
+TEST_F(CppMetadataTest, CapturesEnumNames) {
+ FileDescriptorProto file;
+ GeneratedCodeInfo info;
+ string pb_h;
+ AddFile("test.proto", kSmallTestFile);
+ EXPECT_TRUE(
+ CaptureMetadata("test.proto", &file, &pb_h, &info, NULL, NULL, NULL));
+ EXPECT_EQ("Enum", file.enum_type(0).name());
+ vector<int> enum_path;
+ enum_path.push_back(FileDescriptorProto::kEnumTypeFieldNumber);
+ enum_path.push_back(0);
+ const GeneratedCodeInfo::Annotation* enum_annotation =
+ FindAnnotationOnPath(info, "test.proto", enum_path);
+ EXPECT_TRUE(NULL != enum_annotation);
+ EXPECT_TRUE(AnnotationMatchesSubstring(pb_h, enum_annotation, "Enum"));
+}
+
+TEST_F(CppMetadataTest, AddsPragma) {
+ FileDescriptorProto file;
+ GeneratedCodeInfo info;
+ string pb_h;
+ AddFile("test.proto", kSmallTestFile);
+ EXPECT_TRUE(
+ CaptureMetadata("test.proto", &file, &pb_h, &info, NULL, NULL, NULL));
+ EXPECT_TRUE(pb_h.find("#ifdef guard_name") != string::npos);
+ EXPECT_TRUE(pb_h.find("#pragma pragma_name \"test.pb.h.meta\"") !=
+ string::npos);
+}
+
+TEST_F(CppMetadataTest, CapturesMessageNames) {
+ FileDescriptorProto file;
+ GeneratedCodeInfo info;
+ string pb_h;
+ AddFile("test.proto", kSmallTestFile);
+ EXPECT_TRUE(
+ CaptureMetadata("test.proto", &file, &pb_h, &info, NULL, NULL, NULL));
+ EXPECT_EQ("Message", file.message_type(0).name());
+ vector<int> message_path;
+ message_path.push_back(FileDescriptorProto::kMessageTypeFieldNumber);
+ message_path.push_back(0);
+ const GeneratedCodeInfo::Annotation* message_annotation =
+ FindAnnotationOnPath(info, "test.proto", message_path);
+ EXPECT_TRUE(NULL != message_annotation);
+ EXPECT_TRUE(AnnotationMatchesSubstring(pb_h, message_annotation, "Message"));
+}
+
+} // namespace
+} // namespace cpp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.cc
new file mode 100644
index 0000000000..587e022286
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.cc
@@ -0,0 +1,114 @@
+// 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.
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+// Functions to create C# XML documentation comments.
+// Currently this only includes documentation comments containing text specified as comments
+// in the .proto file; documentation comments generated just from field/message/enum/proto names
+// is inlined in the relevant code. If more control is required, that code can be moved here.
+
+void WriteDocCommentBodyImpl(io::Printer* printer, SourceLocation location) {
+ string comments = location.leading_comments.empty() ?
+ location.trailing_comments : location.leading_comments;
+ if (comments.empty()) {
+ return;
+ }
+ // XML escaping... no need for apostrophes etc as the whole text is going to be a child
+ // node of a summary element, not part of an attribute.
+ comments = StringReplace(comments, "&", "&amp;", true);
+ comments = StringReplace(comments, "<", "&lt;", true);
+ vector<string> lines = Split(comments, "\n", false /* skip_empty */);
+ // TODO: We really should work out which part to put in the summary and which to put in the remarks...
+ // but that needs to be part of a bigger effort to understand the markdown better anyway.
+ printer->Print("/// <summary>\n");
+ bool last_was_empty = false;
+ // We squash multiple blank lines down to one, and remove any trailing blank lines. We need
+ // to preserve the blank lines themselves, as this is relevant in the markdown.
+ // Note that we can't remove leading or trailing whitespace as *that's* relevant in markdown too.
+ // (We don't skip "just whitespace" lines, either.)
+ for (std::vector<string>::iterator it = lines.begin(); it != lines.end(); ++it) {
+ string line = *it;
+ if (line.empty()) {
+ last_was_empty = true;
+ } else {
+ if (last_was_empty) {
+ printer->Print("///\n");
+ }
+ last_was_empty = false;
+ printer->Print("/// $line$\n", "line", *it);
+ }
+ }
+ printer->Print("/// </summary>\n");
+}
+
+template <typename DescriptorType>
+static void WriteDocCommentBody(
+ io::Printer* printer, const DescriptorType* descriptor) {
+ SourceLocation location;
+ if (descriptor->GetSourceLocation(&location)) {
+ WriteDocCommentBodyImpl(printer, location);
+ }
+}
+
+void WriteMessageDocComment(io::Printer* printer, const Descriptor* message) {
+ WriteDocCommentBody(printer, message);
+}
+
+void WritePropertyDocComment(io::Printer* printer, const FieldDescriptor* field) {
+ WriteDocCommentBody(printer, field);
+}
+
+void WriteEnumDocComment(io::Printer* printer, const EnumDescriptor* enumDescriptor) {
+ WriteDocCommentBody(printer, enumDescriptor);
+}
+void WriteEnumValueDocComment(io::Printer* printer, const EnumValueDescriptor* value) {
+ WriteDocCommentBody(printer, value);
+}
+
+void WriteMethodDocComment(io::Printer* printer, const MethodDescriptor* method) {
+ WriteDocCommentBody(printer, method);
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.h
new file mode 100644
index 0000000000..75eb0ea04d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_doc_comment.h
@@ -0,0 +1,51 @@
+// 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.
+
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_DOC_COMMENT_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_DOC_COMMENT_H__
+
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+ void WriteMessageDocComment(io::Printer* printer, const Descriptor* message);
+ void WritePropertyDocComment(io::Printer* printer, const FieldDescriptor* field);
+ void WriteEnumDocComment(io::Printer* printer, const EnumDescriptor* enumDescriptor);
+ void WriteEnumValueDocComment(io::Printer* printer, const EnumValueDescriptor* value);
+ void WriteMethodDocComment(io::Printer* printer, const MethodDescriptor* method);
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_DOC_COMMENT_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.cc
new file mode 100644
index 0000000000..64381d0faa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.cc
@@ -0,0 +1,94 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_enum.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+
+using google::protobuf::internal::scoped_ptr;
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+EnumGenerator::EnumGenerator(const EnumDescriptor* descriptor, const Options* options) :
+ SourceGeneratorBase(descriptor->file(), options),
+ descriptor_(descriptor) {
+}
+
+EnumGenerator::~EnumGenerator() {
+}
+
+void EnumGenerator::Generate(io::Printer* printer) {
+ WriteEnumDocComment(printer, descriptor_);
+ printer->Print("$access_level$ enum $name$ {\n",
+ "access_level", class_access_level(),
+ "name", descriptor_->name());
+ printer->Indent();
+ std::set<string> used_names;
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ WriteEnumValueDocComment(printer, descriptor_->value(i));
+ string original_name = descriptor_->value(i)->name();
+ string name = options()->legacy_enum_values
+ ? descriptor_->value(i)->name()
+ : GetEnumValueName(descriptor_->name(), descriptor_->value(i)->name());
+ // Make sure we don't get any duplicate names due to prefix removal.
+ while (!used_names.insert(name).second) {
+ // It's possible we'll end up giving this warning multiple times, but that's better than not at all.
+ GOOGLE_LOG(WARNING) << "Duplicate enum value " << name << " (originally " << original_name
+ << ") in " << descriptor_->name() << "; adding underscore to distinguish";
+ name += "_";
+ }
+ printer->Print("[pbr::OriginalName(\"$original_name$\")] $name$ = $number$,\n",
+ "original_name", original_name,
+ "name", name,
+ "number", SimpleItoa(descriptor_->value(i)->number()));
+ }
+ printer->Outdent();
+ printer->Print("}\n");
+ printer->Print("\n");
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.h
new file mode 100644
index 0000000000..8925cdf2be
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum.h
@@ -0,0 +1,63 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_ENUM_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_ENUM_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_source_generator_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class EnumGenerator : public SourceGeneratorBase {
+ public:
+ EnumGenerator(const EnumDescriptor* descriptor, const Options* options);
+ ~EnumGenerator();
+
+ void Generate(io::Printer* printer);
+
+ private:
+ const EnumDescriptor* descriptor_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_ENUM_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.cc
new file mode 100644
index 0000000000..67c0b5961a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.cc
@@ -0,0 +1,120 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+#include <google/protobuf/compiler/csharp/csharp_enum_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+EnumFieldGenerator::EnumFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal, const Options *options)
+ : PrimitiveFieldGenerator(descriptor, fieldOrdinal, options) {
+}
+
+EnumFieldGenerator::~EnumFieldGenerator() {
+}
+
+void EnumFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$name$_ = ($type_name$) input.ReadEnum();\n");
+}
+
+void EnumFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "if ($has_property_check$) {\n"
+ " output.WriteRawTag($tag_bytes$);\n"
+ " output.WriteEnum((int) $property_name$);\n"
+ "}\n");
+}
+
+void EnumFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " size += $tag_size$ + pb::CodedOutputStream.ComputeEnumSize((int) $property_name$);\n"
+ "}\n");
+}
+
+void EnumFieldGenerator::GenerateCodecCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "pb::FieldCodec.ForEnum($tag$, x => (int) x, x => ($type_name$) x)");
+}
+
+EnumOneofFieldGenerator::EnumOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options)
+ : PrimitiveOneofFieldGenerator(descriptor, fieldOrdinal, options) {
+}
+
+EnumOneofFieldGenerator::~EnumOneofFieldGenerator() {
+}
+
+void EnumOneofFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ // TODO(jonskeet): What about if we read the default value?
+ printer->Print(
+ variables_,
+ "$oneof_name$_ = input.ReadEnum();\n"
+ "$oneof_name$Case_ = $oneof_property_name$OneofCase.$property_name$;\n");
+}
+
+void EnumOneofFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " output.WriteRawTag($tag_bytes$);\n"
+ " output.WriteEnum((int) $property_name$);\n"
+ "}\n");
+}
+
+void EnumOneofFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " size += $tag_size$ + pb::CodedOutputStream.ComputeEnumSize((int) $property_name$);\n"
+ "}\n");
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.h
new file mode 100644
index 0000000000..9b7669ba5d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_enum_field.h
@@ -0,0 +1,81 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_ENUM_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_ENUM_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_primitive_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class EnumFieldGenerator : public PrimitiveFieldGenerator {
+ public:
+ EnumFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~EnumFieldGenerator();
+
+ virtual void GenerateCodecCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumFieldGenerator);
+};
+
+class EnumOneofFieldGenerator : public PrimitiveOneofFieldGenerator {
+ public:
+ EnumOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~EnumOneofFieldGenerator();
+
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumOneofFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_ENUM_FIELD_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.cc
new file mode 100644
index 0000000000..e2011b76ca
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.cc
@@ -0,0 +1,430 @@
+// 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.
+
+#include <limits>
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/mathlimits.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/wire_format.h>
+
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_names.h>
+
+using google::protobuf::internal::scoped_ptr;
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+void FieldGeneratorBase::SetCommonFieldVariables(
+ map<string, string>* variables) {
+ // Note: this will be valid even though the tag emitted for packed and unpacked versions of
+ // repeated fields varies by wire format. The wire format is encoded in the bottom 3 bits, which
+ // never effects the tag size.
+ int tag_size = internal::WireFormat::TagSize(descriptor_->number(), descriptor_->type());
+ uint tag = internal::WireFormat::MakeTag(descriptor_);
+ uint8 tag_array[5];
+ io::CodedOutputStream::WriteTagToArray(tag, tag_array);
+ string tag_bytes = SimpleItoa(tag_array[0]);
+ for (int i = 1; i < tag_size; i++) {
+ tag_bytes += ", " + SimpleItoa(tag_array[i]);
+ }
+
+ (*variables)["access_level"] = "public";
+ (*variables)["tag"] = SimpleItoa(tag);
+ (*variables)["tag_size"] = SimpleItoa(tag_size);
+ (*variables)["tag_bytes"] = tag_bytes;
+
+ (*variables)["property_name"] = property_name();
+ (*variables)["type_name"] = type_name();
+ (*variables)["name"] = name();
+ (*variables)["descriptor_name"] = descriptor_->name();
+ (*variables)["default_value"] = default_value();
+ if (has_default_value()) {
+ (*variables)["name_def_message"] =
+ (*variables)["name"] + "_ = " + (*variables)["default_value"];
+ } else {
+ (*variables)["name_def_message"] = (*variables)["name"] + "_";
+ }
+ (*variables)["capitalized_type_name"] = capitalized_type_name();
+ (*variables)["number"] = number();
+ (*variables)["has_property_check"] =
+ (*variables)["property_name"] + " != " + (*variables)["default_value"];
+ (*variables)["other_has_property_check"] = "other." +
+ (*variables)["property_name"] + " != " + (*variables)["default_value"];
+}
+
+void FieldGeneratorBase::SetCommonOneofFieldVariables(
+ map<string, string>* variables) {
+ (*variables)["oneof_name"] = oneof_name();
+ (*variables)["has_property_check"] =
+ oneof_name() + "Case_ == " + oneof_property_name() +
+ "OneofCase." + property_name();
+ (*variables)["oneof_property_name"] = oneof_property_name();
+}
+
+FieldGeneratorBase::FieldGeneratorBase(const FieldDescriptor* descriptor,
+ int fieldOrdinal, const Options* options)
+ : SourceGeneratorBase(descriptor->file(), options),
+ descriptor_(descriptor),
+ fieldOrdinal_(fieldOrdinal) {
+ SetCommonFieldVariables(&variables_);
+}
+
+FieldGeneratorBase::~FieldGeneratorBase() {
+}
+
+void FieldGeneratorBase::GenerateFreezingCode(io::Printer* printer) {
+ // No-op: only message fields and repeated fields need
+ // special handling for freezing, so default to not generating any code.
+}
+
+void FieldGeneratorBase::GenerateCodecCode(io::Printer* printer) {
+ // No-op: expect this to be overridden by appropriate types.
+ // Could fail if we get called here though...
+}
+
+void FieldGeneratorBase::AddDeprecatedFlag(io::Printer* printer) {
+ if (descriptor_->options().deprecated())
+ {
+ printer->Print("[global::System.ObsoleteAttribute]\n");
+ }
+}
+
+void FieldGeneratorBase::AddPublicMemberAttributes(io::Printer* printer) {
+ AddDeprecatedFlag(printer);
+ WriteGeneratedCodeAttributes(printer);
+}
+
+std::string FieldGeneratorBase::oneof_property_name() {
+ return UnderscoresToCamelCase(descriptor_->containing_oneof()->name(), true);
+}
+
+std::string FieldGeneratorBase::oneof_name() {
+ return UnderscoresToCamelCase(descriptor_->containing_oneof()->name(), false);
+}
+
+std::string FieldGeneratorBase::property_name() {
+ return GetPropertyName(descriptor_);
+}
+
+std::string FieldGeneratorBase::name() {
+ return UnderscoresToCamelCase(GetFieldName(descriptor_), false);
+}
+
+std::string FieldGeneratorBase::type_name() {
+ return type_name(descriptor_);
+}
+
+std::string FieldGeneratorBase::type_name(const FieldDescriptor* descriptor) {
+ switch (descriptor->type()) {
+ case FieldDescriptor::TYPE_ENUM:
+ return GetClassName(descriptor->enum_type());
+ case FieldDescriptor::TYPE_MESSAGE:
+ case FieldDescriptor::TYPE_GROUP:
+ if (IsWrapperType(descriptor)) {
+ const FieldDescriptor* wrapped_field =
+ descriptor->message_type()->field(0);
+ string wrapped_field_type_name = type_name(wrapped_field);
+ // String and ByteString go to the same type; other wrapped types
+ // go to the nullable equivalent.
+ if (wrapped_field->type() == FieldDescriptor::TYPE_STRING ||
+ wrapped_field->type() == FieldDescriptor::TYPE_BYTES) {
+ return wrapped_field_type_name;
+ } else {
+ return wrapped_field_type_name + "?";
+ }
+ }
+ return GetClassName(descriptor->message_type());
+ case FieldDescriptor::TYPE_DOUBLE:
+ return "double";
+ case FieldDescriptor::TYPE_FLOAT:
+ return "float";
+ case FieldDescriptor::TYPE_INT64:
+ return "long";
+ case FieldDescriptor::TYPE_UINT64:
+ return "ulong";
+ case FieldDescriptor::TYPE_INT32:
+ return "int";
+ case FieldDescriptor::TYPE_FIXED64:
+ return "ulong";
+ case FieldDescriptor::TYPE_FIXED32:
+ return "uint";
+ case FieldDescriptor::TYPE_BOOL:
+ return "bool";
+ case FieldDescriptor::TYPE_STRING:
+ return "string";
+ case FieldDescriptor::TYPE_BYTES:
+ return "pb::ByteString";
+ case FieldDescriptor::TYPE_UINT32:
+ return "uint";
+ case FieldDescriptor::TYPE_SFIXED32:
+ return "int";
+ case FieldDescriptor::TYPE_SFIXED64:
+ return "long";
+ case FieldDescriptor::TYPE_SINT32:
+ return "int";
+ case FieldDescriptor::TYPE_SINT64:
+ return "long";
+ default:
+ GOOGLE_LOG(FATAL)<< "Unknown field type.";
+ return "";
+ }
+}
+
+bool FieldGeneratorBase::has_default_value() {
+ switch (descriptor_->type()) {
+ case FieldDescriptor::TYPE_ENUM:
+ case FieldDescriptor::TYPE_MESSAGE:
+ case FieldDescriptor::TYPE_GROUP:
+ return true;
+ case FieldDescriptor::TYPE_DOUBLE:
+ return descriptor_->default_value_double() != 0.0;
+ case FieldDescriptor::TYPE_FLOAT:
+ return descriptor_->default_value_float() != 0.0;
+ case FieldDescriptor::TYPE_INT64:
+ return descriptor_->default_value_int64() != 0L;
+ case FieldDescriptor::TYPE_UINT64:
+ return descriptor_->default_value_uint64() != 0L;
+ case FieldDescriptor::TYPE_INT32:
+ return descriptor_->default_value_int32() != 0;
+ case FieldDescriptor::TYPE_FIXED64:
+ return descriptor_->default_value_uint64() != 0L;
+ case FieldDescriptor::TYPE_FIXED32:
+ return descriptor_->default_value_uint32() != 0;
+ case FieldDescriptor::TYPE_BOOL:
+ return descriptor_->default_value_bool();
+ case FieldDescriptor::TYPE_STRING:
+ return true;
+ case FieldDescriptor::TYPE_BYTES:
+ return true;
+ case FieldDescriptor::TYPE_UINT32:
+ return descriptor_->default_value_uint32() != 0;
+ case FieldDescriptor::TYPE_SFIXED32:
+ return descriptor_->default_value_int32() != 0;
+ case FieldDescriptor::TYPE_SFIXED64:
+ return descriptor_->default_value_int64() != 0L;
+ case FieldDescriptor::TYPE_SINT32:
+ return descriptor_->default_value_int32() != 0;
+ case FieldDescriptor::TYPE_SINT64:
+ return descriptor_->default_value_int64() != 0L;
+ default:
+ GOOGLE_LOG(FATAL)<< "Unknown field type.";
+ return true;
+ }
+}
+
+bool FieldGeneratorBase::is_nullable_type() {
+ switch (descriptor_->type()) {
+ case FieldDescriptor::TYPE_ENUM:
+ case FieldDescriptor::TYPE_DOUBLE:
+ case FieldDescriptor::TYPE_FLOAT:
+ case FieldDescriptor::TYPE_INT64:
+ case FieldDescriptor::TYPE_UINT64:
+ case FieldDescriptor::TYPE_INT32:
+ case FieldDescriptor::TYPE_FIXED64:
+ case FieldDescriptor::TYPE_FIXED32:
+ case FieldDescriptor::TYPE_BOOL:
+ case FieldDescriptor::TYPE_UINT32:
+ case FieldDescriptor::TYPE_SFIXED32:
+ case FieldDescriptor::TYPE_SFIXED64:
+ case FieldDescriptor::TYPE_SINT32:
+ case FieldDescriptor::TYPE_SINT64:
+ return false;
+
+ case FieldDescriptor::TYPE_MESSAGE:
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_STRING:
+ case FieldDescriptor::TYPE_BYTES:
+ return true;
+
+ default:
+ GOOGLE_LOG(FATAL)<< "Unknown field type.";
+ return true;
+ }
+}
+
+bool AllPrintableAscii(const std::string& text) {
+ for(int i = 0; i < text.size(); i++) {
+ if (text[i] < 0x20 || text[i] > 0x7e) {
+ return false;
+ }
+ }
+ return true;
+}
+
+std::string FieldGeneratorBase::GetStringDefaultValueInternal() {
+ // No other default values needed for proto3...
+ return "\"\"";
+}
+
+std::string FieldGeneratorBase::GetBytesDefaultValueInternal() {
+ // No other default values needed for proto3...
+ return "pb::ByteString.Empty";
+}
+
+std::string FieldGeneratorBase::default_value() {
+ return default_value(descriptor_);
+}
+
+std::string FieldGeneratorBase::default_value(const FieldDescriptor* descriptor) {
+ switch (descriptor->type()) {
+ case FieldDescriptor::TYPE_ENUM:
+ // All proto3 enums have a default value of 0, and there's an implicit conversion from the constant 0 to
+ // any C# enum. This means we don't need to work out what we actually mapped the enum value name to.
+ return "0";
+ case FieldDescriptor::TYPE_MESSAGE:
+ case FieldDescriptor::TYPE_GROUP:
+ if (IsWrapperType(descriptor)) {
+ const FieldDescriptor* wrapped_field = descriptor->message_type()->field(0);
+ return default_value(wrapped_field);
+ } else {
+ return "null";
+ }
+ case FieldDescriptor::TYPE_DOUBLE: {
+ double value = descriptor->default_value_double();
+ if (value == numeric_limits<double>::infinity()) {
+ return "double.PositiveInfinity";
+ } else if (value == -numeric_limits<double>::infinity()) {
+ return "double.NegativeInfinity";
+ } else if (MathLimits<double>::IsNaN(value)) {
+ return "double.NaN";
+ }
+ return SimpleDtoa(value) + "D";
+ }
+ case FieldDescriptor::TYPE_FLOAT: {
+ float value = descriptor->default_value_float();
+ if (value == numeric_limits<float>::infinity()) {
+ return "float.PositiveInfinity";
+ } else if (value == -numeric_limits<float>::infinity()) {
+ return "float.NegativeInfinity";
+ } else if (MathLimits<float>::IsNaN(value)) {
+ return "float.NaN";
+ }
+ return SimpleFtoa(value) + "F";
+ }
+ case FieldDescriptor::TYPE_INT64:
+ return SimpleItoa(descriptor->default_value_int64()) + "L";
+ case FieldDescriptor::TYPE_UINT64:
+ return SimpleItoa(descriptor->default_value_uint64()) + "UL";
+ case FieldDescriptor::TYPE_INT32:
+ return SimpleItoa(descriptor->default_value_int32());
+ case FieldDescriptor::TYPE_FIXED64:
+ return SimpleItoa(descriptor->default_value_uint64()) + "UL";
+ case FieldDescriptor::TYPE_FIXED32:
+ return SimpleItoa(descriptor->default_value_uint32());
+ case FieldDescriptor::TYPE_BOOL:
+ if (descriptor->default_value_bool()) {
+ return "true";
+ } else {
+ return "false";
+ }
+ case FieldDescriptor::TYPE_STRING:
+ return GetStringDefaultValueInternal();
+ case FieldDescriptor::TYPE_BYTES:
+ return GetBytesDefaultValueInternal();
+ case FieldDescriptor::TYPE_UINT32:
+ return SimpleItoa(descriptor->default_value_uint32());
+ case FieldDescriptor::TYPE_SFIXED32:
+ return SimpleItoa(descriptor->default_value_int32());
+ case FieldDescriptor::TYPE_SFIXED64:
+ return SimpleItoa(descriptor->default_value_int64()) + "L";
+ case FieldDescriptor::TYPE_SINT32:
+ return SimpleItoa(descriptor->default_value_int32());
+ case FieldDescriptor::TYPE_SINT64:
+ return SimpleItoa(descriptor->default_value_int64()) + "L";
+ default:
+ GOOGLE_LOG(FATAL)<< "Unknown field type.";
+ return "";
+ }
+}
+
+std::string FieldGeneratorBase::number() {
+ return SimpleItoa(descriptor_->number());
+}
+
+std::string FieldGeneratorBase::capitalized_type_name() {
+ switch (descriptor_->type()) {
+ case FieldDescriptor::TYPE_ENUM:
+ return "Enum";
+ case FieldDescriptor::TYPE_MESSAGE:
+ return "Message";
+ case FieldDescriptor::TYPE_GROUP:
+ return "Group";
+ case FieldDescriptor::TYPE_DOUBLE:
+ return "Double";
+ case FieldDescriptor::TYPE_FLOAT:
+ return "Float";
+ case FieldDescriptor::TYPE_INT64:
+ return "Int64";
+ case FieldDescriptor::TYPE_UINT64:
+ return "UInt64";
+ case FieldDescriptor::TYPE_INT32:
+ return "Int32";
+ case FieldDescriptor::TYPE_FIXED64:
+ return "Fixed64";
+ case FieldDescriptor::TYPE_FIXED32:
+ return "Fixed32";
+ case FieldDescriptor::TYPE_BOOL:
+ return "Bool";
+ case FieldDescriptor::TYPE_STRING:
+ return "String";
+ case FieldDescriptor::TYPE_BYTES:
+ return "Bytes";
+ case FieldDescriptor::TYPE_UINT32:
+ return "UInt32";
+ case FieldDescriptor::TYPE_SFIXED32:
+ return "SFixed32";
+ case FieldDescriptor::TYPE_SFIXED64:
+ return "SFixed64";
+ case FieldDescriptor::TYPE_SINT32:
+ return "SInt32";
+ case FieldDescriptor::TYPE_SINT64:
+ return "SInt64";
+ default:
+ GOOGLE_LOG(FATAL)<< "Unknown field type.";
+ return "";
+ }
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.h
new file mode 100644
index 0000000000..4109f3caa0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_field_base.h
@@ -0,0 +1,105 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_FIELD_BASE_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_FIELD_BASE_H__
+
+#include <string>
+#include <google/protobuf/stubs/strutil.h>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_source_generator_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class FieldGeneratorBase : public SourceGeneratorBase {
+ public:
+ FieldGeneratorBase(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options* options);
+ ~FieldGeneratorBase();
+
+ virtual void GenerateCloningCode(io::Printer* printer) = 0;
+ virtual void GenerateFreezingCode(io::Printer* printer);
+ virtual void GenerateCodecCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer) = 0;
+ virtual void GenerateMergingCode(io::Printer* printer) = 0;
+ virtual void GenerateParsingCode(io::Printer* printer) = 0;
+ virtual void GenerateSerializationCode(io::Printer* printer) = 0;
+ virtual void GenerateSerializedSizeCode(io::Printer* printer) = 0;
+
+ virtual void WriteHash(io::Printer* printer) = 0;
+ virtual void WriteEquals(io::Printer* printer) = 0;
+ // Currently unused, as we use reflection to generate JSON
+ virtual void WriteToString(io::Printer* printer) = 0;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ const int fieldOrdinal_;
+ map<string, string> variables_;
+
+ void AddDeprecatedFlag(io::Printer* printer);
+ void AddNullCheck(io::Printer* printer);
+ void AddNullCheck(io::Printer* printer, const std::string& name);
+
+ void AddPublicMemberAttributes(io::Printer* printer);
+ void SetCommonOneofFieldVariables(map<string, string>* variables);
+
+ std::string oneof_property_name();
+ std::string oneof_name();
+ std::string property_name();
+ std::string name();
+ std::string type_name();
+ std::string type_name(const FieldDescriptor* descriptor);
+ bool has_default_value();
+ bool is_nullable_type();
+ std::string default_value();
+ std::string default_value(const FieldDescriptor* descriptor);
+ std::string number();
+ std::string capitalized_type_name();
+
+ private:
+ void SetCommonFieldVariables(map<string, string>* variables);
+ std::string GetStringDefaultValueInternal();
+ std::string GetBytesDefaultValueInternal();
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGeneratorBase);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_FIELD_BASE_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.cc
new file mode 100644
index 0000000000..d74e8c8847
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.cc
@@ -0,0 +1,118 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#include <google/protobuf/compiler/csharp/csharp_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_names.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+#include <google/protobuf/compiler/csharp/csharp_reflection_class.h>
+
+using google::protobuf::internal::scoped_ptr;
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+void GenerateFile(const google::protobuf::FileDescriptor* file,
+ io::Printer* printer,
+ const Options* options) {
+ ReflectionClassGenerator reflectionClassGenerator(file, options);
+ reflectionClassGenerator.Generate(printer);
+}
+
+bool Generator::Generate(
+ const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const {
+
+ vector<pair<string, string> > options;
+ ParseGeneratorParameter(parameter, &options);
+
+ // We only support proto3 - but we make an exception for descriptor.proto.
+ if (file->syntax() != FileDescriptor::SYNTAX_PROTO3 && !IsDescriptorProto(file)) {
+ *error = "C# code generation only supports proto3 syntax";
+ return false;
+ }
+
+ struct Options cli_options;
+
+ for (int i = 0; i < options.size(); i++) {
+ if (options[i].first == "file_extension") {
+ cli_options.file_extension = options[i].second;
+ } else if (options[i].first == "base_namespace") {
+ cli_options.base_namespace = options[i].second;
+ cli_options.base_namespace_specified = true;
+ } else if (options[i].first == "internal_access") {
+ cli_options.internal_access = true;
+ } else if (options[i].first == "legacy_enum_values") {
+ // TODO: Remove this before final release
+ cli_options.legacy_enum_values = true;
+ } else {
+ *error = "Unknown generator option: " + options[i].first;
+ return false;
+ }
+ }
+
+ string filename_error = "";
+ std::string filename = GetOutputFile(file,
+ cli_options.file_extension,
+ cli_options.base_namespace_specified,
+ cli_options.base_namespace,
+ &filename_error);
+
+ if (filename.empty()) {
+ *error = filename_error;
+ return false;
+ }
+ scoped_ptr<io::ZeroCopyOutputStream> output(
+ generator_context->Open(filename));
+ io::Printer printer(output.get(), '$');
+
+ GenerateFile(file, &printer, &cli_options);
+
+ return true;
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.h
new file mode 100644
index 0000000000..9b54e9149e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator.h
@@ -0,0 +1,58 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_GENERATOR_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class LIBPROTOC_EXPORT Generator
+ : public google::protobuf::compiler::CodeGenerator {
+ virtual bool Generate(
+ const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const;
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_GENERATOR_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator_unittest.cc
new file mode 100644
index 0000000000..5755fee00b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_generator_unittest.cc
@@ -0,0 +1,70 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+
+#include <memory>
+
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/printer.h>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/testing/file.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+namespace {
+
+TEST(CSharpEnumValue, PascalCasedPrefixStripping) {
+ EXPECT_EQ("Bar", GetEnumValueName("Foo", "BAR"));
+ EXPECT_EQ("BarBaz", GetEnumValueName("Foo", "BAR_BAZ"));
+ EXPECT_EQ("Bar", GetEnumValueName("Foo", "FOO_BAR"));
+ EXPECT_EQ("Bar", GetEnumValueName("Foo", "FOO__BAR"));
+ EXPECT_EQ("BarBaz", GetEnumValueName("Foo", "FOO_BAR_BAZ"));
+ EXPECT_EQ("BarBaz", GetEnumValueName("Foo", "Foo_BarBaz"));
+ EXPECT_EQ("Bar", GetEnumValueName("FO_O", "FOO_BAR"));
+ EXPECT_EQ("Bar", GetEnumValueName("FOO", "F_O_O_BAR"));
+ EXPECT_EQ("Bar", GetEnumValueName("Foo", "BAR"));
+ EXPECT_EQ("BarBaz", GetEnumValueName("Foo", "BAR_BAZ"));
+ EXPECT_EQ("Foo", GetEnumValueName("Foo", "FOO"));
+ EXPECT_EQ("Foo", GetEnumValueName("Foo", "FOO___"));
+ // Identifiers can't start with digits
+ EXPECT_EQ("_2Bar", GetEnumValueName("Foo", "FOO_2_BAR"));
+ EXPECT_EQ("_2", GetEnumValueName("Foo", "FOO___2"));
+}
+
+} // namespace
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.cc
new file mode 100644
index 0000000000..6c154c5a58
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.cc
@@ -0,0 +1,506 @@
+// 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.
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <limits>
+#include <vector>
+
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+#include <google/protobuf/compiler/csharp/csharp_enum_field.h>
+#include <google/protobuf/compiler/csharp/csharp_map_field.h>
+#include <google/protobuf/compiler/csharp/csharp_message_field.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+#include <google/protobuf/compiler/csharp/csharp_primitive_field.h>
+#include <google/protobuf/compiler/csharp/csharp_repeated_enum_field.h>
+#include <google/protobuf/compiler/csharp/csharp_repeated_message_field.h>
+#include <google/protobuf/compiler/csharp/csharp_repeated_primitive_field.h>
+#include <google/protobuf/compiler/csharp/csharp_wrapper_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+CSharpType GetCSharpType(FieldDescriptor::Type type) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32:
+ return CSHARPTYPE_INT32;
+ case FieldDescriptor::TYPE_INT64:
+ return CSHARPTYPE_INT64;
+ case FieldDescriptor::TYPE_UINT32:
+ return CSHARPTYPE_UINT32;
+ case FieldDescriptor::TYPE_UINT64:
+ return CSHARPTYPE_UINT32;
+ case FieldDescriptor::TYPE_SINT32:
+ return CSHARPTYPE_INT32;
+ case FieldDescriptor::TYPE_SINT64:
+ return CSHARPTYPE_INT64;
+ case FieldDescriptor::TYPE_FIXED32:
+ return CSHARPTYPE_UINT32;
+ case FieldDescriptor::TYPE_FIXED64:
+ return CSHARPTYPE_UINT64;
+ case FieldDescriptor::TYPE_SFIXED32:
+ return CSHARPTYPE_INT32;
+ case FieldDescriptor::TYPE_SFIXED64:
+ return CSHARPTYPE_INT64;
+ case FieldDescriptor::TYPE_FLOAT:
+ return CSHARPTYPE_FLOAT;
+ case FieldDescriptor::TYPE_DOUBLE:
+ return CSHARPTYPE_DOUBLE;
+ case FieldDescriptor::TYPE_BOOL:
+ return CSHARPTYPE_BOOL;
+ case FieldDescriptor::TYPE_ENUM:
+ return CSHARPTYPE_ENUM;
+ case FieldDescriptor::TYPE_STRING:
+ return CSHARPTYPE_STRING;
+ case FieldDescriptor::TYPE_BYTES:
+ return CSHARPTYPE_BYTESTRING;
+ case FieldDescriptor::TYPE_GROUP:
+ return CSHARPTYPE_MESSAGE;
+ case FieldDescriptor::TYPE_MESSAGE:
+ return CSHARPTYPE_MESSAGE;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+ GOOGLE_LOG(FATAL)<< "Can't get here.";
+ return (CSharpType) -1;
+}
+
+std::string StripDotProto(const std::string& proto_file) {
+ int lastindex = proto_file.find_last_of(".");
+ return proto_file.substr(0, lastindex);
+}
+
+std::string GetFileNamespace(const FileDescriptor* descriptor) {
+ if (descriptor->options().has_csharp_namespace()) {
+ return descriptor->options().csharp_namespace();
+ }
+ return UnderscoresToCamelCase(descriptor->package(), true, true);
+}
+
+// Returns the Pascal-cased last part of the proto file. For example,
+// input of "google/protobuf/foo_bar.proto" would result in "FooBar".
+std::string GetFileNameBase(const FileDescriptor* descriptor) {
+ std::string proto_file = descriptor->name();
+ int lastslash = proto_file.find_last_of("/");
+ std::string base = proto_file.substr(lastslash + 1);
+ return UnderscoresToPascalCase(StripDotProto(base));
+}
+
+std::string GetReflectionClassUnqualifiedName(const FileDescriptor* descriptor) {
+ // TODO: Detect collisions with existing messages,
+ // and append an underscore if necessary.
+ return GetFileNameBase(descriptor) + "Reflection";
+}
+
+// TODO(jtattermusch): can we reuse a utility function?
+std::string UnderscoresToCamelCase(const std::string& input,
+ bool cap_next_letter,
+ bool preserve_period) {
+ string result;
+ // Note: I distrust ctype.h due to locales.
+ for (int i = 0; i < input.size(); i++) {
+ if ('a' <= input[i] && input[i] <= 'z') {
+ if (cap_next_letter) {
+ result += input[i] + ('A' - 'a');
+ } else {
+ result += input[i];
+ }
+ cap_next_letter = false;
+ } else if ('A' <= input[i] && input[i] <= 'Z') {
+ if (i == 0 && !cap_next_letter) {
+ // Force first letter to lower-case unless explicitly told to
+ // capitalize it.
+ result += input[i] + ('a' - 'A');
+ } else {
+ // Capital letters after the first are left as-is.
+ result += input[i];
+ }
+ cap_next_letter = false;
+ } else if ('0' <= input[i] && input[i] <= '9') {
+ result += input[i];
+ cap_next_letter = true;
+ } else {
+ cap_next_letter = true;
+ if (input[i] == '.' && preserve_period) {
+ result += '.';
+ }
+ }
+ }
+ // Add a trailing "_" if the name should be altered.
+ if (input[input.size() - 1] == '#') {
+ result += '_';
+ }
+ return result;
+}
+
+std::string UnderscoresToPascalCase(const std::string& input) {
+ return UnderscoresToCamelCase(input, true);
+}
+
+// Convert a string which is expected to be SHOUTY_CASE (but may not be *precisely* shouty)
+// into a PascalCase string. Precise rules implemented:
+
+// Previous input character Current character Case
+// Any Non-alphanumeric Skipped
+// None - first char of input Alphanumeric Upper
+// Non-letter (e.g. _ or 1) Alphanumeric Upper
+// Numeric Alphanumeric Upper
+// Lower letter Alphanumeric Same as current
+// Upper letter Alphanumeric Lower
+std::string ShoutyToPascalCase(const std::string& input) {
+ string result;
+ // Simple way of implementing "always start with upper"
+ char previous = '_';
+ for (int i = 0; i < input.size(); i++) {
+ char current = input[i];
+ if (!ascii_isalnum(current)) {
+ previous = current;
+ continue;
+ }
+ if (!ascii_isalnum(previous)) {
+ result += ascii_toupper(current);
+ } else if (ascii_isdigit(previous)) {
+ result += ascii_toupper(current);
+ } else if (ascii_islower(previous)) {
+ result += current;
+ } else {
+ result += ascii_tolower(current);
+ }
+ previous = current;
+ }
+ return result;
+}
+
+// Attempt to remove a prefix from a value, ignoring casing and skipping underscores.
+// (foo, foo_bar) => bar - underscore after prefix is skipped
+// (FOO, foo_bar) => bar - casing is ignored
+// (foo_bar, foobarbaz) => baz - underscore in prefix is ignored
+// (foobar, foo_barbaz) => baz - underscore in value is ignored
+// (foo, bar) => bar - prefix isn't matched; return original value
+std::string TryRemovePrefix(const std::string& prefix, const std::string& value) {
+ // First normalize to a lower-case no-underscores prefix to match against
+ std::string prefix_to_match = "";
+ for (size_t i = 0; i < prefix.size(); i++) {
+ if (prefix[i] != '_') {
+ prefix_to_match += ascii_tolower(prefix[i]);
+ }
+ }
+
+ // This keeps track of how much of value we've consumed
+ size_t prefix_index, value_index;
+ for (prefix_index = 0, value_index = 0;
+ prefix_index < prefix_to_match.size() && value_index < value.size();
+ value_index++) {
+ // Skip over underscores in the value
+ if (value[value_index] == '_') {
+ continue;
+ }
+ if (ascii_tolower(value[value_index]) != prefix_to_match[prefix_index++]) {
+ // Failed to match the prefix - bail out early.
+ return value;
+ }
+ }
+
+ // If we didn't finish looking through the prefix, we can't strip it.
+ if (prefix_index < prefix_to_match.size()) {
+ return value;
+ }
+
+ // Step over any underscores after the prefix
+ while (value_index < value.size() && value[value_index] == '_') {
+ value_index++;
+ }
+
+ // If there's nothing left (e.g. it was a prefix with only underscores afterwards), don't strip.
+ if (value_index == value.size()) {
+ return value;
+ }
+
+ return value.substr(value_index);
+}
+
+// Format the enum value name in a pleasant way for C#:
+// - Strip the enum name as a prefix if possible
+// - Convert to PascalCase.
+// For example, an enum called Color with a value of COLOR_BLUE should
+// result in an enum value in C# called just Blue
+std::string GetEnumValueName(const std::string& enum_name, const std::string& enum_value_name) {
+ std::string stripped = TryRemovePrefix(enum_name, enum_value_name);
+ std::string result = ShoutyToPascalCase(stripped);
+ // Just in case we have an enum name of FOO and a value of FOO_2... make sure the returned
+ // string is a valid identifier.
+ if (ascii_isdigit(result[0])) {
+ result = "_" + result;
+ }
+ return result;
+}
+
+std::string ToCSharpName(const std::string& name, const FileDescriptor* file) {
+ std::string result = GetFileNamespace(file);
+ if (result != "") {
+ result += '.';
+ }
+ string classname;
+ if (file->package().empty()) {
+ classname = name;
+ } else {
+ // Strip the proto package from full_name since we've replaced it with
+ // the C# namespace.
+ classname = name.substr(file->package().size() + 1);
+ }
+ result += StringReplace(classname, ".", ".Types.", true);
+ return "global::" + result;
+}
+
+std::string GetReflectionClassName(const FileDescriptor* descriptor) {
+ std::string result = GetFileNamespace(descriptor);
+ if (!result.empty()) {
+ result += '.';
+ }
+ result += GetReflectionClassUnqualifiedName(descriptor);
+ return "global::" + result;
+}
+
+std::string GetClassName(const Descriptor* descriptor) {
+ return ToCSharpName(descriptor->full_name(), descriptor->file());
+}
+
+std::string GetClassName(const EnumDescriptor* descriptor) {
+ return ToCSharpName(descriptor->full_name(), descriptor->file());
+}
+
+// Groups are hacky: The name of the field is just the lower-cased name
+// of the group type. In C#, though, we would like to retain the original
+// capitalization of the type name.
+std::string GetFieldName(const FieldDescriptor* descriptor) {
+ if (descriptor->type() == FieldDescriptor::TYPE_GROUP) {
+ return descriptor->message_type()->name();
+ } else {
+ return descriptor->name();
+ }
+}
+
+std::string GetFieldConstantName(const FieldDescriptor* field) {
+ return GetPropertyName(field) + "FieldNumber";
+}
+
+std::string GetPropertyName(const FieldDescriptor* descriptor) {
+ // TODO(jtattermusch): consider introducing csharp_property_name field option
+ std::string property_name = UnderscoresToPascalCase(GetFieldName(descriptor));
+ // Avoid either our own type name or reserved names. Note that not all names
+ // are reserved - a field called to_string, write_to etc would still cause a problem.
+ // There are various ways of ending up with naming collisions, but we try to avoid obvious
+ // ones.
+ if (property_name == descriptor->containing_type()->name()
+ || property_name == "Types"
+ || property_name == "Descriptor") {
+ property_name += "_";
+ }
+ return property_name;
+}
+
+std::string GetOutputFile(
+ const google::protobuf::FileDescriptor* descriptor,
+ const std::string file_extension,
+ const bool generate_directories,
+ const std::string base_namespace,
+ string* error) {
+ string relative_filename = GetFileNameBase(descriptor) + file_extension;
+ if (!generate_directories) {
+ return relative_filename;
+ }
+ string ns = GetFileNamespace(descriptor);
+ string namespace_suffix = ns;
+ if (!base_namespace.empty()) {
+ // Check that the base_namespace is either equal to or a leading part of
+ // the file namespace. This isn't just a simple prefix; "Foo.B" shouldn't
+ // be regarded as a prefix of "Foo.Bar". The simplest option is to add "."
+ // to both.
+ string extended_ns = ns + ".";
+ if (extended_ns.find(base_namespace + ".") != 0) {
+ *error = "Namespace " + ns + " is not a prefix namespace of base namespace " + base_namespace;
+ return ""; // This will be ignored, because we've set an error.
+ }
+ namespace_suffix = ns.substr(base_namespace.length());
+ if (namespace_suffix.find(".") == 0) {
+ namespace_suffix = namespace_suffix.substr(1);
+ }
+ }
+
+ string namespace_dir = StringReplace(namespace_suffix, ".", "/", true);
+ if (!namespace_dir.empty()) {
+ namespace_dir += "/";
+ }
+ return namespace_dir + relative_filename;
+}
+
+// TODO: c&p from Java protoc plugin
+// For encodings with fixed sizes, returns that size in bytes. Otherwise
+// returns -1.
+int GetFixedSize(FieldDescriptor::Type type) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32 : return -1;
+ case FieldDescriptor::TYPE_INT64 : return -1;
+ case FieldDescriptor::TYPE_UINT32 : return -1;
+ case FieldDescriptor::TYPE_UINT64 : return -1;
+ case FieldDescriptor::TYPE_SINT32 : return -1;
+ case FieldDescriptor::TYPE_SINT64 : return -1;
+ case FieldDescriptor::TYPE_FIXED32 : return internal::WireFormatLite::kFixed32Size;
+ case FieldDescriptor::TYPE_FIXED64 : return internal::WireFormatLite::kFixed64Size;
+ case FieldDescriptor::TYPE_SFIXED32: return internal::WireFormatLite::kSFixed32Size;
+ case FieldDescriptor::TYPE_SFIXED64: return internal::WireFormatLite::kSFixed64Size;
+ case FieldDescriptor::TYPE_FLOAT : return internal::WireFormatLite::kFloatSize;
+ case FieldDescriptor::TYPE_DOUBLE : return internal::WireFormatLite::kDoubleSize;
+
+ case FieldDescriptor::TYPE_BOOL : return internal::WireFormatLite::kBoolSize;
+ case FieldDescriptor::TYPE_ENUM : return -1;
+
+ case FieldDescriptor::TYPE_STRING : return -1;
+ case FieldDescriptor::TYPE_BYTES : return -1;
+ case FieldDescriptor::TYPE_GROUP : return -1;
+ case FieldDescriptor::TYPE_MESSAGE : return -1;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return -1;
+}
+
+static const char base64_chars[] =
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+
+std::string StringToBase64(const std::string& input) {
+ std::string result;
+ size_t remaining = input.size();
+ const unsigned char *src = (const unsigned char*) input.c_str();
+ while (remaining > 2) {
+ result += base64_chars[src[0] >> 2];
+ result += base64_chars[((src[0] & 0x3) << 4) | (src[1] >> 4)];
+ result += base64_chars[((src[1] & 0xf) << 2) | (src[2] >> 6)];
+ result += base64_chars[src[2] & 0x3f];
+ remaining -= 3;
+ src += 3;
+ }
+ switch (remaining) {
+ case 2:
+ result += base64_chars[src[0] >> 2];
+ result += base64_chars[((src[0] & 0x3) << 4) | (src[1] >> 4)];
+ result += base64_chars[(src[1] & 0xf) << 2];
+ result += '=';
+ src += 2;
+ break;
+ case 1:
+ result += base64_chars[src[0] >> 2];
+ result += base64_chars[((src[0] & 0x3) << 4)];
+ result += '=';
+ result += '=';
+ src += 1;
+ break;
+ }
+ return result;
+}
+
+std::string FileDescriptorToBase64(const FileDescriptor* descriptor) {
+ std::string fdp_bytes;
+ FileDescriptorProto fdp;
+ descriptor->CopyTo(&fdp);
+ fdp.SerializeToString(&fdp_bytes);
+ return StringToBase64(fdp_bytes);
+}
+
+FieldGeneratorBase* CreateFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options* options) {
+ switch (descriptor->type()) {
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_MESSAGE:
+ if (descriptor->is_repeated()) {
+ if (descriptor->is_map()) {
+ return new MapFieldGenerator(descriptor, fieldOrdinal, options);
+ } else {
+ return new RepeatedMessageFieldGenerator(descriptor, fieldOrdinal, options);
+ }
+ } else {
+ if (IsWrapperType(descriptor)) {
+ if (descriptor->containing_oneof()) {
+ return new WrapperOneofFieldGenerator(descriptor, fieldOrdinal, options);
+ } else {
+ return new WrapperFieldGenerator(descriptor, fieldOrdinal, options);
+ }
+ } else {
+ if (descriptor->containing_oneof()) {
+ return new MessageOneofFieldGenerator(descriptor, fieldOrdinal, options);
+ } else {
+ return new MessageFieldGenerator(descriptor, fieldOrdinal, options);
+ }
+ }
+ }
+ case FieldDescriptor::TYPE_ENUM:
+ if (descriptor->is_repeated()) {
+ return new RepeatedEnumFieldGenerator(descriptor, fieldOrdinal, options);
+ } else {
+ if (descriptor->containing_oneof()) {
+ return new EnumOneofFieldGenerator(descriptor, fieldOrdinal, options);
+ } else {
+ return new EnumFieldGenerator(descriptor, fieldOrdinal, options);
+ }
+ }
+ default:
+ if (descriptor->is_repeated()) {
+ return new RepeatedPrimitiveFieldGenerator(descriptor, fieldOrdinal, options);
+ } else {
+ if (descriptor->containing_oneof()) {
+ return new PrimitiveOneofFieldGenerator(descriptor, fieldOrdinal, options);
+ } else {
+ return new PrimitiveFieldGenerator(descriptor, fieldOrdinal, options);
+ }
+ }
+ }
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.h
new file mode 100644
index 0000000000..1563ca7e1d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_helpers.h
@@ -0,0 +1,132 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_HELPERS_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_HELPERS_H__
+
+#include <string>
+#include <google/protobuf/stubs/port.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/io/printer.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+struct Options;
+class FieldGeneratorBase;
+
+// TODO: start using this enum.
+enum CSharpType {
+ CSHARPTYPE_INT32 = 1,
+ CSHARPTYPE_INT64 = 2,
+ CSHARPTYPE_UINT32 = 3,
+ CSHARPTYPE_UINT64 = 4,
+ CSHARPTYPE_FLOAT = 5,
+ CSHARPTYPE_DOUBLE = 6,
+ CSHARPTYPE_BOOL = 7,
+ CSHARPTYPE_STRING = 8,
+ CSHARPTYPE_BYTESTRING = 9,
+ CSHARPTYPE_MESSAGE = 10,
+ CSHARPTYPE_ENUM = 11,
+ MAX_CSHARPTYPE = 11
+};
+
+// Converts field type to corresponding C# type.
+CSharpType GetCSharpType(FieldDescriptor::Type type);
+
+std::string StripDotProto(const std::string& proto_file);
+
+// Gets unqualified name of the reflection class
+std::string GetReflectionClassUnqualifiedName(const FileDescriptor* descriptor);
+
+std::string GetClassName(const EnumDescriptor* descriptor);
+
+std::string GetFieldName(const FieldDescriptor* descriptor);
+
+std::string GetFieldConstantName(const FieldDescriptor* field);
+
+std::string GetPropertyName(const FieldDescriptor* descriptor);
+
+int GetFixedSize(FieldDescriptor::Type type);
+
+std::string UnderscoresToCamelCase(const std::string& input,
+ bool cap_next_letter,
+ bool preserve_period);
+
+inline std::string UnderscoresToCamelCase(const std::string& input, bool cap_next_letter) {
+ return UnderscoresToCamelCase(input, cap_next_letter, false);
+}
+
+std::string UnderscoresToPascalCase(const std::string& input);
+
+// Note that we wouldn't normally want to export this (we're not expecting
+// it to be used outside libprotoc itself) but this exposes it for testing.
+std::string LIBPROTOBUF_EXPORT GetEnumValueName(const std::string& enum_name, const std::string& enum_value_name);
+
+// TODO(jtattermusch): perhaps we could move this to strutil
+std::string StringToBase64(const std::string& input);
+
+std::string FileDescriptorToBase64(const FileDescriptor* descriptor);
+
+FieldGeneratorBase* CreateFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options* options);
+
+// Determines whether the given message is a map entry message,
+// i.e. one implicitly created by protoc due to a map<key, value> field.
+inline bool IsMapEntryMessage(const Descriptor* descriptor) {
+ return descriptor->options().map_entry();
+}
+
+// Determines whether we're generating code for the proto representation of
+// descriptors etc, for use in the runtime. This is the only type which is
+// allowed to use proto2 syntax, and it generates internal classes.
+inline bool IsDescriptorProto(const FileDescriptor* descriptor) {
+ return descriptor->name() == "google/protobuf/descriptor.proto";
+}
+
+inline bool IsWrapperType(const FieldDescriptor* descriptor) {
+ return descriptor->type() == FieldDescriptor::TYPE_MESSAGE &&
+ descriptor->message_type()->file()->name() == "google/protobuf/wrappers.proto";
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_HELPERS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.cc
new file mode 100644
index 0000000000..e6eac6edb2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.cc
@@ -0,0 +1,141 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2015 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_map_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+MapFieldGenerator::MapFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options* options)
+ : FieldGeneratorBase(descriptor, fieldOrdinal, options) {
+}
+
+MapFieldGenerator::~MapFieldGenerator() {
+}
+
+void MapFieldGenerator::GenerateMembers(io::Printer* printer) {
+ const FieldDescriptor* key_descriptor =
+ descriptor_->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor_->message_type()->FindFieldByName("value");
+ variables_["key_type_name"] = type_name(key_descriptor);
+ variables_["value_type_name"] = type_name(value_descriptor);
+ scoped_ptr<FieldGeneratorBase> key_generator(
+ CreateFieldGenerator(key_descriptor, 1, this->options()));
+ scoped_ptr<FieldGeneratorBase> value_generator(
+ CreateFieldGenerator(value_descriptor, 2, this->options()));
+
+ printer->Print(
+ variables_,
+ "private static readonly pbc::MapField<$key_type_name$, $value_type_name$>.Codec _map_$name$_codec\n"
+ " = new pbc::MapField<$key_type_name$, $value_type_name$>.Codec(");
+ key_generator->GenerateCodecCode(printer);
+ printer->Print(", ");
+ value_generator->GenerateCodecCode(printer);
+ printer->Print(
+ variables_,
+ ", $tag$);\n"
+ "private readonly pbc::MapField<$key_type_name$, $value_type_name$> $name$_ = new pbc::MapField<$key_type_name$, $value_type_name$>();\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ pbc::MapField<$key_type_name$, $value_type_name$> $property_name$ {\n"
+ " get { return $name$_; }\n"
+ "}\n");
+}
+
+void MapFieldGenerator::GenerateMergingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.Add(other.$name$_);\n");
+}
+
+void MapFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.AddEntriesFrom(input, _map_$name$_codec);\n");
+}
+
+void MapFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.WriteTo(output, _map_$name$_codec);\n");
+}
+
+void MapFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "size += $name$_.CalculateSize(_map_$name$_codec);\n");
+}
+
+void MapFieldGenerator::WriteHash(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "hash ^= $property_name$.GetHashCode();\n");
+}
+void MapFieldGenerator::WriteEquals(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if (!$property_name$.Equals(other.$property_name$)) return false;\n");
+}
+
+void MapFieldGenerator::WriteToString(io::Printer* printer) {
+ // TODO: If we ever actually use ToString, we'll need to impleme this...
+}
+
+void MapFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$name$_ = other.$name$_.Clone();\n");
+}
+
+void MapFieldGenerator::GenerateFreezingCode(io::Printer* printer) {
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.h
new file mode 100644
index 0000000000..84a33a0367
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_map_field.h
@@ -0,0 +1,73 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_MAP_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_MAP_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class MapFieldGenerator : public FieldGeneratorBase {
+ public:
+ MapFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options* options);
+ ~MapFieldGenerator();
+
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateFreezingCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateMergingCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ virtual void WriteHash(io::Printer* printer);
+ virtual void WriteEquals(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MapFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_MAP_FIELD_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.cc
new file mode 100644
index 0000000000..ed7448545f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.cc
@@ -0,0 +1,528 @@
+// 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.
+
+#include <sstream>
+#include <algorithm>
+#include <map>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/wire_format_lite.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_enum.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_message.h>
+#include <google/protobuf/compiler/csharp/csharp_names.h>
+
+using google::protobuf::internal::scoped_ptr;
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+bool CompareFieldNumbers(const FieldDescriptor* d1, const FieldDescriptor* d2) {
+ return d1->number() < d2->number();
+}
+
+MessageGenerator::MessageGenerator(const Descriptor* descriptor,
+ const Options* options)
+ : SourceGeneratorBase(descriptor->file(), options),
+ descriptor_(descriptor) {
+
+ // sorted field names
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_names_.push_back(descriptor_->field(i)->name());
+ }
+ std::sort(field_names_.begin(), field_names_.end());
+
+ // fields by number
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ fields_by_number_.push_back(descriptor_->field(i));
+ }
+ std::sort(fields_by_number_.begin(), fields_by_number_.end(),
+ CompareFieldNumbers);
+}
+
+MessageGenerator::~MessageGenerator() {
+}
+
+std::string MessageGenerator::class_name() {
+ return descriptor_->name();
+}
+
+std::string MessageGenerator::full_class_name() {
+ return GetClassName(descriptor_);
+}
+
+const std::vector<std::string>& MessageGenerator::field_names() {
+ return field_names_;
+}
+
+const std::vector<const FieldDescriptor*>& MessageGenerator::fields_by_number() {
+ return fields_by_number_;
+}
+
+void MessageGenerator::Generate(io::Printer* printer) {
+ map<string, string> vars;
+ vars["class_name"] = class_name();
+ vars["access_level"] = class_access_level();
+
+ WriteMessageDocComment(printer, descriptor_);
+ printer->Print(
+ vars,
+ "$access_level$ sealed partial class $class_name$ : pb::IMessage<$class_name$> {\n");
+ printer->Indent();
+
+ // All static fields and properties
+ printer->Print(
+ vars,
+ "private static readonly pb::MessageParser<$class_name$> _parser = new pb::MessageParser<$class_name$>(() => new $class_name$());\n");
+
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public static pb::MessageParser<$class_name$> Parser { get { return _parser; } }\n\n");
+
+ // Access the message descriptor via the relevant file descriptor or containing message descriptor.
+ if (!descriptor_->containing_type()) {
+ vars["descriptor_accessor"] = GetReflectionClassName(descriptor_->file())
+ + ".Descriptor.MessageTypes[" + SimpleItoa(descriptor_->index()) + "]";
+ } else {
+ vars["descriptor_accessor"] = GetClassName(descriptor_->containing_type())
+ + ".Descriptor.NestedTypes[" + SimpleItoa(descriptor_->index()) + "]";
+ }
+
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public static pbr::MessageDescriptor Descriptor {\n"
+ " get { return $descriptor_accessor$; }\n"
+ "}\n"
+ "\n");
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "pbr::MessageDescriptor pb::IMessage.Descriptor {\n"
+ " get { return Descriptor; }\n"
+ "}\n"
+ "\n");
+
+ // Parameterless constructor and partial OnConstruction method.
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public $class_name$() {\n"
+ " OnConstruction();\n"
+ "}\n\n"
+ "partial void OnConstruction();\n\n");
+
+ GenerateCloningCode(printer);
+ GenerateFreezingCode(printer);
+
+ // Fields/properties
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* fieldDescriptor = descriptor_->field(i);
+
+ // Rats: we lose the debug comment here :(
+ printer->Print(
+ "/// <summary>Field number for the \"$field_name$\" field.</summary>\n"
+ "public const int $field_constant_name$ = $index$;\n",
+ "field_name", fieldDescriptor->name(),
+ "field_constant_name", GetFieldConstantName(fieldDescriptor),
+ "index", SimpleItoa(fieldDescriptor->number()));
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(fieldDescriptor));
+ generator->GenerateMembers(printer);
+ printer->Print("\n");
+ }
+
+ // oneof properties
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ vars["name"] = UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), false);
+ vars["property_name"] = UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), true);
+ vars["original_name"] = descriptor_->oneof_decl(i)->name();
+ printer->Print(
+ vars,
+ "private object $name$_;\n"
+ "/// <summary>Enum of possible cases for the \"$original_name$\" oneof.</summary>\n"
+ "public enum $property_name$OneofCase {\n");
+ printer->Indent();
+ printer->Print("None = 0,\n");
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print("$field_property_name$ = $index$,\n",
+ "field_property_name", GetPropertyName(field),
+ "index", SimpleItoa(field->number()));
+ }
+ printer->Outdent();
+ printer->Print("}\n");
+ // TODO: Should we put the oneof .proto comments here?
+ // It's unclear exactly where they should go.
+ printer->Print(
+ vars,
+ "private $property_name$OneofCase $name$Case_ = $property_name$OneofCase.None;\n");
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public $property_name$OneofCase $property_name$Case {\n"
+ " get { return $name$Case_; }\n"
+ "}\n\n");
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public void Clear$property_name$() {\n"
+ " $name$Case_ = $property_name$OneofCase.None;\n"
+ " $name$_ = null;\n"
+ "}\n\n");
+ }
+
+ // Standard methods
+ GenerateFrameworkMethods(printer);
+ GenerateMessageSerializationMethods(printer);
+ GenerateMergingMethods(printer);
+
+ // Nested messages and enums
+ if (HasNestedGeneratedTypes()) {
+ printer->Print(
+ vars,
+ "#region Nested types\n"
+ "/// <summary>Container for nested types declared in the $class_name$ message type.</summary>\n");
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print("public static partial class Types {\n");
+ printer->Indent();
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ EnumGenerator enumGenerator(descriptor_->enum_type(i), this->options());
+ enumGenerator.Generate(printer);
+ }
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // Don't generate nested types for maps...
+ if (!IsMapEntryMessage(descriptor_->nested_type(i))) {
+ MessageGenerator messageGenerator(
+ descriptor_->nested_type(i), this->options());
+ messageGenerator.Generate(printer);
+ }
+ }
+ printer->Outdent();
+ printer->Print("}\n"
+ "#endregion\n"
+ "\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+ printer->Print("\n");
+}
+
+// Helper to work out whether we need to generate a class to hold nested types/enums.
+// Only tricky because we don't want to generate map entry types.
+bool MessageGenerator::HasNestedGeneratedTypes()
+{
+ if (descriptor_->enum_type_count() > 0) {
+ return true;
+ }
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ if (!IsMapEntryMessage(descriptor_->nested_type(i))) {
+ return true;
+ }
+ }
+ return false;
+}
+
+void MessageGenerator::GenerateCloningCode(io::Printer* printer) {
+ map<string, string> vars;
+ WriteGeneratedCodeAttributes(printer);
+ vars["class_name"] = class_name();
+ printer->Print(
+ vars,
+ "public $class_name$($class_name$ other) : this() {\n");
+ printer->Indent();
+ // Clone non-oneof fields first
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(descriptor_->field(i)));
+ generator->GenerateCloningCode(printer);
+ }
+ }
+ // Clone just the right field for each oneof
+ for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
+ vars["name"] = UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), false);
+ vars["property_name"] = UnderscoresToCamelCase(
+ descriptor_->oneof_decl(i)->name(), true);
+ printer->Print(vars, "switch (other.$property_name$Case) {\n");
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ scoped_ptr<FieldGeneratorBase> generator(CreateFieldGeneratorInternal(field));
+ vars["field_property_name"] = GetPropertyName(field);
+ printer->Print(
+ vars,
+ "case $property_name$OneofCase.$field_property_name$:\n");
+ printer->Indent();
+ generator->GenerateCloningCode(printer);
+ printer->Print("break;\n");
+ printer->Outdent();
+ }
+ printer->Outdent();
+ printer->Print("}\n\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public $class_name$ Clone() {\n"
+ " return new $class_name$(this);\n"
+ "}\n\n");
+}
+
+void MessageGenerator::GenerateFreezingCode(io::Printer* printer) {
+}
+
+void MessageGenerator::GenerateFrameworkMethods(io::Printer* printer) {
+ map<string, string> vars;
+ vars["class_name"] = class_name();
+
+ // Equality
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public override bool Equals(object other) {\n"
+ " return Equals(other as $class_name$);\n"
+ "}\n\n");
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public bool Equals($class_name$ other) {\n"
+ " if (ReferenceEquals(other, null)) {\n"
+ " return false;\n"
+ " }\n"
+ " if (ReferenceEquals(other, this)) {\n"
+ " return true;\n"
+ " }\n");
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(descriptor_->field(i)));
+ generator->WriteEquals(printer);
+ }
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print("if ($property_name$Case != other.$property_name$Case) return false;\n",
+ "property_name", UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), true));
+ }
+ printer->Outdent();
+ printer->Print(
+ " return true;\n"
+ "}\n\n");
+
+ // GetHashCode
+ // Start with a non-zero value to easily distinguish between null and "empty" messages.
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ "public override int GetHashCode() {\n"
+ " int hash = 1;\n");
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(descriptor_->field(i)));
+ generator->WriteHash(printer);
+ }
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print("hash ^= (int) $name$Case_;\n",
+ "name", UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), false));
+ }
+ printer->Print("return hash;\n");
+ printer->Outdent();
+ printer->Print("}\n\n");
+
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ "public override string ToString() {\n"
+ " return pb::JsonFormatter.ToDiagnosticString(this);\n"
+ "}\n\n");
+}
+
+void MessageGenerator::GenerateMessageSerializationMethods(io::Printer* printer) {
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ "public void WriteTo(pb::CodedOutputStream output) {\n");
+ printer->Indent();
+
+ // Serialize all the fields
+ for (int i = 0; i < fields_by_number().size(); i++) {
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(fields_by_number()[i]));
+ generator->GenerateSerializationCode(printer);
+ }
+
+ // TODO(jonskeet): Memoize size of frozen messages?
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ "public int CalculateSize() {\n");
+ printer->Indent();
+ printer->Print("int size = 0;\n");
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(descriptor_->field(i)));
+ generator->GenerateSerializedSizeCode(printer);
+ }
+ printer->Print("return size;\n");
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+void MessageGenerator::GenerateMergingMethods(io::Printer* printer) {
+ // Note: These are separate from GenerateMessageSerializationMethods()
+ // because they need to be generated even for messages that are optimized
+ // for code size.
+ map<string, string> vars;
+ vars["class_name"] = class_name();
+
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print(
+ vars,
+ "public void MergeFrom($class_name$ other) {\n");
+ printer->Indent();
+ printer->Print(
+ "if (other == null) {\n"
+ " return;\n"
+ "}\n");
+ // Merge non-oneof fields
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(descriptor_->field(i)));
+ generator->GenerateMergingCode(printer);
+ }
+ }
+ // Merge oneof fields
+ for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
+ vars["name"] = UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), false);
+ vars["property_name"] = UnderscoresToCamelCase(descriptor_->oneof_decl(i)->name(), true);
+ printer->Print(vars, "switch (other.$property_name$Case) {\n");
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ vars["field_property_name"] = GetPropertyName(field);
+ printer->Print(
+ vars,
+ "case $property_name$OneofCase.$field_property_name$:\n"
+ " $field_property_name$ = other.$field_property_name$;\n"
+ " break;\n");
+ }
+ printer->Outdent();
+ printer->Print("}\n\n");
+ }
+ printer->Outdent();
+ printer->Print("}\n\n");
+ WriteGeneratedCodeAttributes(printer);
+ printer->Print("public void MergeFrom(pb::CodedInputStream input) {\n");
+ printer->Indent();
+ printer->Print(
+ "uint tag;\n"
+ "while ((tag = input.ReadTag()) != 0) {\n"
+ " switch(tag) {\n");
+ printer->Indent();
+ printer->Indent();
+ printer->Print(
+ "default:\n"
+ " input.SkipLastField();\n" // We're not storing the data, but we still need to consume it.
+ " break;\n");
+ for (int i = 0; i < fields_by_number().size(); i++) {
+ const FieldDescriptor* field = fields_by_number()[i];
+ internal::WireFormatLite::WireType wt =
+ internal::WireFormat::WireTypeForFieldType(field->type());
+ uint32 tag = internal::WireFormatLite::MakeTag(field->number(), wt);
+ // Handle both packed and unpacked repeated fields with the same Read*Array call;
+ // the two generated cases are the packed and unpacked tags.
+ // TODO(jonskeet): Check that is_packable is equivalent to
+ // is_repeated && wt in { VARINT, FIXED32, FIXED64 }.
+ // It looks like it is...
+ if (field->is_packable()) {
+ printer->Print(
+ "case $packed_tag$:\n",
+ "packed_tag",
+ SimpleItoa(
+ internal::WireFormatLite::MakeTag(
+ field->number(),
+ internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED)));
+ }
+
+ printer->Print("case $tag$: {\n", "tag", SimpleItoa(tag));
+ printer->Indent();
+ scoped_ptr<FieldGeneratorBase> generator(
+ CreateFieldGeneratorInternal(field));
+ generator->GenerateParsingCode(printer);
+ printer->Print("break;\n");
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ printer->Outdent();
+ printer->Print("}\n"); // switch
+ printer->Outdent();
+ printer->Print("}\n"); // while
+ printer->Outdent();
+ printer->Print("}\n\n"); // method
+}
+
+int MessageGenerator::GetFieldOrdinal(const FieldDescriptor* descriptor) {
+ for (int i = 0; i < field_names().size(); i++) {
+ if (field_names()[i] == descriptor->name()) {
+ return i;
+ }
+ }
+ GOOGLE_LOG(DFATAL)<< "Could not find ordinal for field " << descriptor->name();
+ return -1;
+}
+
+FieldGeneratorBase* MessageGenerator::CreateFieldGeneratorInternal(
+ const FieldDescriptor* descriptor) {
+ return CreateFieldGenerator(descriptor, GetFieldOrdinal(descriptor), this->options());
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.h
new file mode 100644
index 0000000000..f794d68dfd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message.h
@@ -0,0 +1,89 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_MESSAGE_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_MESSAGE_H__
+
+#include <string>
+#include <vector>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_source_generator_base.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class FieldGeneratorBase;
+
+class MessageGenerator : public SourceGeneratorBase {
+ public:
+ MessageGenerator(const Descriptor* descriptor, const Options* options);
+ ~MessageGenerator();
+
+ void GenerateCloningCode(io::Printer* printer);
+ void GenerateFreezingCode(io::Printer* printer);
+ void GenerateFrameworkMethods(io::Printer* printer);
+ void Generate(io::Printer* printer);
+
+ private:
+ const Descriptor* descriptor_;
+ std::vector<std::string> field_names_;
+ std::vector<const FieldDescriptor*> fields_by_number_;
+
+ void GenerateMessageSerializationMethods(io::Printer* printer);
+ void GenerateMergingMethods(io::Printer* printer);
+
+ int GetFieldOrdinal(const FieldDescriptor* descriptor);
+ FieldGeneratorBase* CreateFieldGeneratorInternal(
+ const FieldDescriptor* descriptor);
+
+ bool HasNestedGeneratedTypes();
+
+ std::string class_name();
+ std::string full_class_name();
+
+ // field names sorted alphabetically
+ const std::vector<std::string>& field_names();
+
+ // field descriptors sorted by number
+ const std::vector<const FieldDescriptor*>& fields_by_number();
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.cc
new file mode 100644
index 0000000000..438f310221
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.cc
@@ -0,0 +1,200 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_message_field.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+MessageFieldGenerator::MessageFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options)
+ : FieldGeneratorBase(descriptor, fieldOrdinal, options) {
+ variables_["has_property_check"] = name() + "_ != null";
+ variables_["has_not_property_check"] = name() + "_ == null";
+}
+
+MessageFieldGenerator::~MessageFieldGenerator() {
+
+}
+
+void MessageFieldGenerator::GenerateMembers(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "private $type_name$ $name$_;\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ $type_name$ $property_name$ {\n"
+ " get { return $name$_; }\n"
+ " set {\n"
+ " $name$_ = value;\n"
+ " }\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::GenerateMergingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if (other.$has_property_check$) {\n"
+ " if ($has_not_property_check$) {\n"
+ " $name$_ = new $type_name$();\n"
+ " }\n"
+ " $property_name$.MergeFrom(other.$property_name$);\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_not_property_check$) {\n"
+ " $name$_ = new $type_name$();\n"
+ "}\n"
+ // TODO(jonskeet): Do we really need merging behaviour like this?
+ "input.ReadMessage($name$_);\n"); // No need to support TYPE_GROUP...
+}
+
+void MessageFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " output.WriteRawTag($tag_bytes$);\n"
+ " output.WriteMessage($property_name$);\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " size += $tag_size$ + pb::CodedOutputStream.ComputeMessageSize($property_name$);\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::WriteHash(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) hash ^= $property_name$.GetHashCode();\n");
+}
+void MessageFieldGenerator::WriteEquals(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if (!object.Equals($property_name$, other.$property_name$)) return false;\n");
+}
+void MessageFieldGenerator::WriteToString(io::Printer* printer) {
+ variables_["field_name"] = GetFieldName(descriptor_);
+ printer->Print(
+ variables_,
+ "PrintField(\"$field_name$\", has$property_name$, $name$_, writer);\n");
+}
+
+void MessageFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$property_name$ = other.$has_property_check$ ? other.$property_name$.Clone() : null;\n");
+}
+
+void MessageFieldGenerator::GenerateFreezingCode(io::Printer* printer) {
+}
+
+void MessageFieldGenerator::GenerateCodecCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "pb::FieldCodec.ForMessage($tag$, $type_name$.Parser)");
+}
+
+MessageOneofFieldGenerator::MessageOneofFieldGenerator(
+ const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options)
+ : MessageFieldGenerator(descriptor, fieldOrdinal, options) {
+ SetCommonOneofFieldVariables(&variables_);
+}
+
+MessageOneofFieldGenerator::~MessageOneofFieldGenerator() {
+
+}
+
+void MessageOneofFieldGenerator::GenerateMembers(io::Printer* printer) {
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ $type_name$ $property_name$ {\n"
+ " get { return $has_property_check$ ? ($type_name$) $oneof_name$_ : null; }\n"
+ " set {\n"
+ " $oneof_name$_ = value;\n"
+ " $oneof_name$Case_ = value == null ? $oneof_property_name$OneofCase.None : $oneof_property_name$OneofCase.$property_name$;\n"
+ " }\n"
+ "}\n");
+}
+
+void MessageOneofFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ // TODO(jonskeet): We may be able to do better than this
+ printer->Print(
+ variables_,
+ "$type_name$ subBuilder = new $type_name$();\n"
+ "if ($has_property_check$) {\n"
+ " subBuilder.MergeFrom($property_name$);\n"
+ "}\n"
+ "input.ReadMessage(subBuilder);\n" // No support of TYPE_GROUP
+ "$property_name$ = subBuilder;\n");
+}
+
+void MessageOneofFieldGenerator::WriteToString(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "PrintField(\"$descriptor_name$\", $has_property_check$, $oneof_name$_, writer);\n");
+}
+
+void MessageOneofFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$property_name$ = other.$property_name$.Clone();\n");
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.h
new file mode 100644
index 0000000000..7d614756fa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_message_field.h
@@ -0,0 +1,90 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_MESSAGE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_MESSAGE_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class MessageFieldGenerator : public FieldGeneratorBase {
+ public:
+ MessageFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~MessageFieldGenerator();
+
+ virtual void GenerateCodecCode(io::Printer* printer);
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateFreezingCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateMergingCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ virtual void WriteHash(io::Printer* printer);
+ virtual void WriteEquals(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageFieldGenerator);
+};
+
+class MessageOneofFieldGenerator : public MessageFieldGenerator {
+ public:
+ MessageOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~MessageOneofFieldGenerator();
+
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageOneofFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_MESSAGE_FIELD_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_names.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_names.h
new file mode 100644
index 0000000000..308051871c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_names.h
@@ -0,0 +1,103 @@
+// 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.
+//
+// Provides a mechanism for mapping a descriptor to the
+// fully-qualified name of the corresponding C# class.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_NAMES_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_NAMES_H__
+
+#include <string>
+
+namespace google {
+namespace protobuf {
+
+class Descriptor;
+class EnumDescriptor;
+class FileDescriptor;
+class ServiceDescriptor;
+
+namespace compiler {
+namespace csharp {
+
+// Requires:
+// descriptor != NULL
+//
+// Returns:
+// The namespace to use for given file descriptor.
+string GetFileNamespace(const FileDescriptor* descriptor);
+
+// Requires:
+// descriptor != NULL
+//
+// Returns:
+// The fully-qualified C# class name.
+string GetClassName(const Descriptor* descriptor);
+
+// Requires:
+// descriptor != NULL
+//
+// Returns:
+// The fully-qualified name of the C# class that provides
+// access to the file descriptor. Proto compiler generates
+// such class for each .proto file processed.
+string GetReflectionClassName(const FileDescriptor* descriptor);
+
+// Generates output file name for given file descriptor. If generate_directories
+// is true, the output file will be put under directory corresponding to file's
+// namespace. base_namespace can be used to strip some of the top level
+// directories. E.g. for file with namespace "Bar.Foo" and base_namespace="Bar",
+// the resulting file will be put under directory "Foo" (and not "Bar/Foo").
+//
+// Requires:
+// descriptor != NULL
+// error != NULL
+//
+// Returns:
+// The file name to use as output file for given file descriptor. In case
+// of failure, this function will return empty string and error parameter
+// will contain the error message.
+string GetOutputFile(
+ const google::protobuf::FileDescriptor* descriptor,
+ const string file_extension,
+ const bool generate_directories,
+ const string base_namespace,
+ string* error);
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_NAMES_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_options.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_options.h
new file mode 100644
index 0000000000..4079bf7f32
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_options.h
@@ -0,0 +1,86 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_OPTIONS_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_OPTIONS_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+// Generator options (used by csharp_generator.cc):
+struct Options {
+ Options() :
+ file_extension(".cs"),
+ base_namespace(""),
+ base_namespace_specified(false),
+ internal_access(false),
+ legacy_enum_values(false) {
+ }
+ // Extension of the generated file. Defaults to ".cs"
+ string file_extension;
+ // Base namespace to use to create directory hierarchy. Defaults to "".
+ // This option allows the simple creation of a conventional C# file layout,
+ // where directories are created relative to a project-specific base
+ // namespace. For example, in a project with a base namespace of PetShop, a
+ // proto of user.proto with a C# namespace of PetShop.Model.Shared would
+ // generate Model/Shared/User.cs underneath the specified --csharp_out
+ // directory.
+ //
+ // If no base namespace is specified, all files are generated in the
+ // --csharp_out directory, with no subdirectories created automatically.
+ string base_namespace;
+ // Whether the base namespace has been explicitly specified by the user.
+ // This is required as the base namespace can be explicitly set to the empty
+ // string, meaning "create a full directory hierarchy, starting from the first
+ // segment of the namespace."
+ bool base_namespace_specified;
+ // Whether the generated classes should have accessibility level of "internal".
+ // Defaults to false that generates "public" classes.
+ bool internal_access;
+ // By default, C# codegen now uses PascalCased enum values names, after
+ // removing the enum type name as a prefix (if it *is* a prefix of the value).
+ // Setting this option reverts to the previous behavior of just copying the
+ // value name specified in the .proto file, allowing gradual migration.
+ // This option will be removed before final release.
+ bool legacy_enum_values;
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_OPTIONS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.cc
new file mode 100644
index 0000000000..169122e6be
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.cc
@@ -0,0 +1,218 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+#include <google/protobuf/compiler/csharp/csharp_primitive_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+PrimitiveFieldGenerator::PrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options)
+ : FieldGeneratorBase(descriptor, fieldOrdinal, options) {
+ // TODO(jonskeet): Make this cleaner...
+ is_value_type = descriptor->type() != FieldDescriptor::TYPE_STRING
+ && descriptor->type() != FieldDescriptor::TYPE_BYTES;
+ if (!is_value_type) {
+ variables_["has_property_check"] = variables_["property_name"] + ".Length != 0";
+ variables_["other_has_property_check"] = "other." + variables_["property_name"] + ".Length != 0";
+ }
+}
+
+PrimitiveFieldGenerator::~PrimitiveFieldGenerator() {
+}
+
+void PrimitiveFieldGenerator::GenerateMembers(io::Printer* printer) {
+ // TODO(jonskeet): Work out whether we want to prevent the fields from ever being
+ // null, or whether we just handle it, in the cases of bytes and string.
+ // (Basically, should null-handling code be in the getter or the setter?)
+ printer->Print(
+ variables_,
+ "private $type_name$ $name_def_message$;\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ $type_name$ $property_name$ {\n"
+ " get { return $name$_; }\n"
+ " set {\n");
+ if (is_value_type) {
+ printer->Print(
+ variables_,
+ " $name$_ = value;\n");
+ } else {
+ printer->Print(
+ variables_,
+ " $name$_ = pb::ProtoPreconditions.CheckNotNull(value, \"value\");\n");
+ }
+ printer->Print(
+ " }\n"
+ "}\n");
+}
+
+void PrimitiveFieldGenerator::GenerateMergingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($other_has_property_check$) {\n"
+ " $property_name$ = other.$property_name$;\n"
+ "}\n");
+}
+
+void PrimitiveFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ // Note: invoke the property setter rather than writing straight to the field,
+ // so that we can normalize "null to empty" for strings and bytes.
+ printer->Print(
+ variables_,
+ "$property_name$ = input.Read$capitalized_type_name$();\n");
+}
+
+void PrimitiveFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " output.WriteRawTag($tag_bytes$);\n"
+ " output.Write$capitalized_type_name$($property_name$);\n"
+ "}\n");
+}
+
+void PrimitiveFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n");
+ printer->Indent();
+ int fixedSize = GetFixedSize(descriptor_->type());
+ if (fixedSize == -1) {
+ printer->Print(
+ variables_,
+ "size += $tag_size$ + pb::CodedOutputStream.Compute$capitalized_type_name$Size($property_name$);\n");
+ } else {
+ printer->Print(
+ "size += $tag_size$ + $fixed_size$;\n",
+ "fixed_size", SimpleItoa(fixedSize),
+ "tag_size", variables_["tag_size"]);
+ }
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void PrimitiveFieldGenerator::WriteHash(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) hash ^= $property_name$.GetHashCode();\n");
+}
+void PrimitiveFieldGenerator::WriteEquals(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($property_name$ != other.$property_name$) return false;\n");
+}
+void PrimitiveFieldGenerator::WriteToString(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "PrintField(\"$descriptor_name$\", $has_property_check$, $property_name$, writer);\n");
+}
+
+void PrimitiveFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$name$_ = other.$name$_;\n");
+}
+
+void PrimitiveFieldGenerator::GenerateCodecCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "pb::FieldCodec.For$capitalized_type_name$($tag$)");
+}
+
+PrimitiveOneofFieldGenerator::PrimitiveOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options)
+ : PrimitiveFieldGenerator(descriptor, fieldOrdinal, options) {
+ SetCommonOneofFieldVariables(&variables_);
+}
+
+PrimitiveOneofFieldGenerator::~PrimitiveOneofFieldGenerator() {
+}
+
+void PrimitiveOneofFieldGenerator::GenerateMembers(io::Printer* printer) {
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ $type_name$ $property_name$ {\n"
+ " get { return $has_property_check$ ? ($type_name$) $oneof_name$_ : $default_value$; }\n"
+ " set {\n");
+ if (is_value_type) {
+ printer->Print(
+ variables_,
+ " $oneof_name$_ = value;\n");
+ } else {
+ printer->Print(
+ variables_,
+ " $oneof_name$_ = pb::ProtoPreconditions.CheckNotNull(value, \"value\");\n");
+ }
+ printer->Print(
+ variables_,
+ " $oneof_name$Case_ = $oneof_property_name$OneofCase.$property_name$;\n"
+ " }\n"
+ "}\n");
+}
+
+void PrimitiveOneofFieldGenerator::WriteToString(io::Printer* printer) {
+ printer->Print(variables_,
+ "PrintField(\"$descriptor_name$\", $has_property_check$, $oneof_name$_, writer);\n");
+}
+
+void PrimitiveOneofFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$property_name$ = input.Read$capitalized_type_name$();\n");
+}
+
+void PrimitiveOneofFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$property_name$ = other.$property_name$;\n");
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.h
new file mode 100644
index 0000000000..5f466fc47c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_primitive_field.h
@@ -0,0 +1,94 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_PRIMITIVE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_PRIMITIVE_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+struct Options;
+
+class PrimitiveFieldGenerator : public FieldGeneratorBase {
+ public:
+ PrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~PrimitiveFieldGenerator();
+
+ virtual void GenerateCodecCode(io::Printer* printer);
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateMergingCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ virtual void WriteHash(io::Printer* printer);
+ virtual void WriteEquals(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+
+ protected:
+ bool is_value_type;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveFieldGenerator);
+};
+
+class PrimitiveOneofFieldGenerator : public PrimitiveFieldGenerator {
+ public:
+ PrimitiveOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~PrimitiveOneofFieldGenerator();
+
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveOneofFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_PRIMITIVE_FIELD_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.cc
new file mode 100644
index 0000000000..bac9aef7b8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.cc
@@ -0,0 +1,290 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+
+
+#include <google/protobuf/compiler/csharp/csharp_enum.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_message.h>
+#include <google/protobuf/compiler/csharp/csharp_names.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+#include <google/protobuf/compiler/csharp/csharp_reflection_class.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+ReflectionClassGenerator::ReflectionClassGenerator(const FileDescriptor* file,
+ const Options* options)
+ : SourceGeneratorBase(file, options),
+ file_(file) {
+ namespace_ = GetFileNamespace(file);
+ reflectionClassname_ = GetReflectionClassUnqualifiedName(file);
+}
+
+ReflectionClassGenerator::~ReflectionClassGenerator() {
+}
+
+void ReflectionClassGenerator::Generate(io::Printer* printer) {
+ WriteIntroduction(printer);
+
+ WriteDescriptor(printer);
+ // Close the class declaration.
+ printer->Outdent();
+ printer->Print("}\n");
+
+ // write children: Enums
+ if (file_->enum_type_count() > 0) {
+ printer->Print("#region Enums\n");
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ EnumGenerator enumGenerator(file_->enum_type(i), this->options());
+ enumGenerator.Generate(printer);
+ }
+ printer->Print("#endregion\n");
+ printer->Print("\n");
+ }
+
+ // write children: Messages
+ if (file_->message_type_count() > 0) {
+ printer->Print("#region Messages\n");
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ MessageGenerator messageGenerator(file_->message_type(i), this->options());
+ messageGenerator.Generate(printer);
+ }
+ printer->Print("#endregion\n");
+ printer->Print("\n");
+ }
+
+ // TODO(jtattermusch): add insertion point for services.
+
+ if (!namespace_.empty()) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ printer->Print("\n");
+ printer->Print("#endregion Designer generated code\n");
+}
+
+void ReflectionClassGenerator::WriteIntroduction(io::Printer* printer) {
+ printer->Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "// source: $file_name$\n"
+ "#pragma warning disable 1591, 0612, 3021\n"
+ "#region Designer generated code\n"
+ "\n"
+ "using pb = global::Google.Protobuf;\n"
+ "using pbc = global::Google.Protobuf.Collections;\n"
+ "using pbr = global::Google.Protobuf.Reflection;\n"
+ "using scg = global::System.Collections.Generic;\n",
+ "file_name", file_->name());
+
+ if (!namespace_.empty()) {
+ printer->Print("namespace $namespace$ {\n", "namespace", namespace_);
+ printer->Indent();
+ printer->Print("\n");
+ }
+
+ printer->Print(
+ "/// <summary>Holder for reflection information generated from $file_name$</summary>\n"
+ "$access_level$ static partial class $reflection_class_name$ {\n"
+ "\n",
+ "file_name", file_->name(),
+ "access_level", class_access_level(),
+ "reflection_class_name", reflectionClassname_);
+ printer->Indent();
+}
+
+void ReflectionClassGenerator::WriteDescriptor(io::Printer* printer) {
+ printer->Print(
+ "#region Descriptor\n"
+ "/// <summary>File descriptor for $file_name$</summary>\n"
+ "public static pbr::FileDescriptor Descriptor {\n"
+ " get { return descriptor; }\n"
+ "}\n"
+ "private static pbr::FileDescriptor descriptor;\n"
+ "\n"
+ "static $reflection_class_name$() {\n",
+ "file_name", file_->name(),
+ "reflection_class_name", reflectionClassname_);
+ printer->Indent();
+ printer->Print(
+ "byte[] descriptorData = global::System.Convert.FromBase64String(\n");
+ printer->Indent();
+ printer->Indent();
+ printer->Print("string.Concat(\n");
+ printer->Indent();
+
+ // TODO(jonskeet): Consider a C#-escaping format here instead of just Base64.
+ std::string base64 = FileDescriptorToBase64(file_);
+ while (base64.size() > 60) {
+ printer->Print("\"$base64$\",\n", "base64", base64.substr(0, 60));
+ base64 = base64.substr(60);
+ }
+ printer->Print("\"$base64$\"));\n", "base64", base64);
+ printer->Outdent();
+ printer->Outdent();
+ printer->Outdent();
+
+ // -----------------------------------------------------------------
+ // Invoke InternalBuildGeneratedFileFrom() to build the file.
+ printer->Print(
+ "descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,\n");
+ printer->Print(" new pbr::FileDescriptor[] { ");
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ // descriptor.proto is special: we don't allow access to the generated code, but there's
+ // a separately-exposed property to get at the file descriptor, specifically to allow this
+ // kind of dependency.
+ if (IsDescriptorProto(file_->dependency(i))) {
+ printer->Print("pbr::FileDescriptor.DescriptorProtoFileDescriptor, ");
+ } else {
+ printer->Print(
+ "$full_reflection_class_name$.Descriptor, ",
+ "full_reflection_class_name",
+ GetReflectionClassName(file_->dependency(i)));
+ }
+ }
+ printer->Print("},\n"
+ " new pbr::GeneratedClrTypeInfo(");
+ // Specify all the generated code information, recursively.
+ if (file_->enum_type_count() > 0) {
+ printer->Print("new[] {");
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ printer->Print("typeof($type_name$), ", "type_name", GetClassName(file_->enum_type(i)));
+ }
+ printer->Print("}, ");
+ }
+ else {
+ printer->Print("null, ");
+ }
+ if (file_->message_type_count() > 0) {
+ printer->Print("new pbr::GeneratedClrTypeInfo[] {\n");
+ printer->Indent();
+ printer->Indent();
+ printer->Indent();
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ WriteGeneratedCodeInfo(file_->message_type(i), printer, i == file_->message_type_count() - 1);
+ }
+ printer->Outdent();
+ printer->Print("\n}));\n");
+ printer->Outdent();
+ printer->Outdent();
+ }
+ else {
+ printer->Print("null));\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+ printer->Print("#endregion\n\n");
+}
+
+// Write out the generated code for a particular message. This consists of the CLR type, property names
+// corresponding to fields, names corresponding to oneofs, nested enums, and nested types. Each array part
+// can be specified as null if it would be empty, to make the generated code somewhat simpler to read.
+// We write a line break at the end of each generated code info, so that in the final file we'll see all
+// the types, pre-ordered depth first, one per line. The indentation will be slightly unusual,
+// in that it will look like a single array when it's actually constructing a tree, but it'll be easy to
+// read even with multiple levels of nesting.
+// The "last" parameter indicates whether this message descriptor is the last one being printed in this immediate
+// context. It governs whether or not a trailing comma and newline is written after the constructor, effectively
+// just controlling the formatting in the generated code.
+void ReflectionClassGenerator::WriteGeneratedCodeInfo(const Descriptor* descriptor, io::Printer* printer, bool last) {
+ if (IsMapEntryMessage(descriptor)) {
+ printer->Print("null, ");
+ return;
+ }
+ // Generated message type
+ printer->Print("new pbr::GeneratedClrTypeInfo(typeof($type_name$), $type_name$.Parser, ", "type_name", GetClassName(descriptor));
+
+ // Fields
+ if (descriptor->field_count() > 0) {
+ std::vector<std::string> fields;
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ fields.push_back(GetPropertyName(descriptor->field(i)));
+ }
+ printer->Print("new[]{ \"$fields$\" }, ", "fields", JoinStrings(fields, "\", \""));
+ }
+ else {
+ printer->Print("null, ");
+ }
+
+ // Oneofs
+ if (descriptor->oneof_decl_count() > 0) {
+ std::vector<std::string> oneofs;
+ for (int i = 0; i < descriptor->oneof_decl_count(); i++) {
+ oneofs.push_back(UnderscoresToCamelCase(descriptor->oneof_decl(i)->name(), true));
+ }
+ printer->Print("new[]{ \"$oneofs$\" }, ", "oneofs", JoinStrings(oneofs, "\", \""));
+ }
+ else {
+ printer->Print("null, ");
+ }
+
+ // Nested enums
+ if (descriptor->enum_type_count() > 0) {
+ std::vector<std::string> enums;
+ for (int i = 0; i < descriptor->enum_type_count(); i++) {
+ enums.push_back(GetClassName(descriptor->enum_type(i)));
+ }
+ printer->Print("new[]{ typeof($enums$) }, ", "enums", JoinStrings(enums, "), typeof("));
+ }
+ else {
+ printer->Print("null, ");
+ }
+
+ // Nested types
+ if (descriptor->nested_type_count() > 0) {
+ // Need to specify array type explicitly here, as all elements may be null.
+ printer->Print("new pbr::GeneratedClrTypeInfo[] { ");
+ for (int i = 0; i < descriptor->nested_type_count(); i++) {
+ WriteGeneratedCodeInfo(descriptor->nested_type(i), printer, i == descriptor->nested_type_count() - 1);
+ }
+ printer->Print("}");
+ }
+ else {
+ printer->Print("null");
+ }
+ printer->Print(last ? ")" : "),\n");
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.h
new file mode 100644
index 0000000000..e0c69f31fb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_reflection_class.h
@@ -0,0 +1,71 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_REFLECTION_CLASS_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_REFLECTION_CLASS_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_source_generator_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class ReflectionClassGenerator : public SourceGeneratorBase {
+ public:
+ ReflectionClassGenerator(const FileDescriptor* file, const Options* options);
+ ~ReflectionClassGenerator();
+
+ void Generate(io::Printer* printer);
+
+ private:
+ const FileDescriptor* file_;
+
+ std::string namespace_;
+ std::string reflectionClassname_;
+
+ void WriteIntroduction(io::Printer* printer);
+ void WriteDescriptor(io::Printer* printer);
+ void WriteGeneratedCodeInfo(const Descriptor* descriptor,
+ io::Printer* printer,
+ bool last);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ReflectionClassGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_REFLECTION_CLASS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.cc
new file mode 100644
index 0000000000..683c4b0b7a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.cc
@@ -0,0 +1,127 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/wire_format.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_repeated_enum_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+RepeatedEnumFieldGenerator::RepeatedEnumFieldGenerator(
+ const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options)
+ : FieldGeneratorBase(descriptor, fieldOrdinal, options) {
+}
+
+RepeatedEnumFieldGenerator::~RepeatedEnumFieldGenerator() {
+
+}
+
+void RepeatedEnumFieldGenerator::GenerateMembers(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "private static readonly pb::FieldCodec<$type_name$> _repeated_$name$_codec\n"
+ " = pb::FieldCodec.ForEnum($tag$, x => (int) x, x => ($type_name$) x);\n");
+ printer->Print(variables_,
+ "private readonly pbc::RepeatedField<$type_name$> $name$_ = new pbc::RepeatedField<$type_name$>();\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ pbc::RepeatedField<$type_name$> $property_name$ {\n"
+ " get { return $name$_; }\n"
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::GenerateMergingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.Add(other.$name$_);\n");
+}
+
+void RepeatedEnumFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.AddEntriesFrom(input, _repeated_$name$_codec);\n");
+}
+
+void RepeatedEnumFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.WriteTo(output, _repeated_$name$_codec);\n");
+}
+
+void RepeatedEnumFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "size += $name$_.CalculateSize(_repeated_$name$_codec);\n");
+}
+
+void RepeatedEnumFieldGenerator::WriteHash(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "hash ^= $name$_.GetHashCode();\n");
+}
+
+void RepeatedEnumFieldGenerator::WriteEquals(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if(!$name$_.Equals(other.$name$_)) return false;\n");
+}
+
+void RepeatedEnumFieldGenerator::WriteToString(io::Printer* printer) {
+ printer->Print(variables_,
+ "PrintField(\"$descriptor_name$\", $name$_, writer);\n");
+}
+
+void RepeatedEnumFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$name$_ = other.$name$_.Clone();\n");
+}
+
+void RepeatedEnumFieldGenerator::GenerateFreezingCode(io::Printer* printer) {
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.h
new file mode 100644
index 0000000000..819b583262
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_enum_field.h
@@ -0,0 +1,75 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_ENUM_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_ENUM_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+// TODO(jonskeet): Refactor repeated field support; all the implementations are *really* similar. We
+// should probably have a RepeatedFieldGeneratorBase.
+class RepeatedEnumFieldGenerator : public FieldGeneratorBase {
+ public:
+ RepeatedEnumFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~RepeatedEnumFieldGenerator();
+
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateFreezingCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateMergingCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ virtual void WriteHash(io::Printer* printer);
+ virtual void WriteEquals(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedEnumFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_ENUM_FIELD_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.cc
new file mode 100644
index 0000000000..8fa0b0504f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.cc
@@ -0,0 +1,144 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_repeated_message_field.h>
+#include <google/protobuf/compiler/csharp/csharp_message_field.h>
+#include <google/protobuf/compiler/csharp/csharp_wrapper_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+RepeatedMessageFieldGenerator::RepeatedMessageFieldGenerator(
+ const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options)
+ : FieldGeneratorBase(descriptor, fieldOrdinal, options) {
+}
+
+RepeatedMessageFieldGenerator::~RepeatedMessageFieldGenerator() {
+
+}
+
+void RepeatedMessageFieldGenerator::GenerateMembers(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "private static readonly pb::FieldCodec<$type_name$> _repeated_$name$_codec\n"
+ " = ");
+ // Don't want to duplicate the codec code here... maybe we should have a
+ // "create single field generator for this repeated field"
+ // function, but it doesn't seem worth it for just this.
+ if (IsWrapperType(descriptor_)) {
+ scoped_ptr<FieldGeneratorBase> single_generator(
+ new WrapperFieldGenerator(descriptor_, fieldOrdinal_, this->options()));
+ single_generator->GenerateCodecCode(printer);
+ } else {
+ scoped_ptr<FieldGeneratorBase> single_generator(
+ new MessageFieldGenerator(descriptor_, fieldOrdinal_, this->options()));
+ single_generator->GenerateCodecCode(printer);
+ }
+ printer->Print(";\n");
+ printer->Print(
+ variables_,
+ "private readonly pbc::RepeatedField<$type_name$> $name$_ = new pbc::RepeatedField<$type_name$>();\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ pbc::RepeatedField<$type_name$> $property_name$ {\n"
+ " get { return $name$_; }\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::GenerateMergingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.Add(other.$name$_);\n");
+}
+
+void RepeatedMessageFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.AddEntriesFrom(input, _repeated_$name$_codec);\n");
+}
+
+void RepeatedMessageFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.WriteTo(output, _repeated_$name$_codec);\n");
+}
+
+void RepeatedMessageFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "size += $name$_.CalculateSize(_repeated_$name$_codec);\n");
+}
+
+void RepeatedMessageFieldGenerator::WriteHash(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "hash ^= $name$_.GetHashCode();\n");
+}
+
+void RepeatedMessageFieldGenerator::WriteEquals(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if(!$name$_.Equals(other.$name$_)) return false;\n");
+}
+
+void RepeatedMessageFieldGenerator::WriteToString(io::Printer* printer) {
+ variables_["field_name"] = GetFieldName(descriptor_);
+ printer->Print(
+ variables_,
+ "PrintField(\"$field_name$\", $name$_, writer);\n");
+}
+
+void RepeatedMessageFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$name$_ = other.$name$_.Clone();\n");
+}
+
+void RepeatedMessageFieldGenerator::GenerateFreezingCode(io::Printer* printer) {
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.h
new file mode 100644
index 0000000000..6e33648b6c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_message_field.h
@@ -0,0 +1,75 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_MESSAGE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_MESSAGE_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+struct Options;
+
+class RepeatedMessageFieldGenerator : public FieldGeneratorBase {
+ public:
+ RepeatedMessageFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~RepeatedMessageFieldGenerator();
+
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateFreezingCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateMergingCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ virtual void WriteHash(io::Printer* printer);
+ virtual void WriteEquals(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedMessageFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_MESSAGE_FIELD_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.cc
new file mode 100644
index 0000000000..cd91506ff1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.cc
@@ -0,0 +1,125 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/wire_format.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_repeated_primitive_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+RepeatedPrimitiveFieldGenerator::RepeatedPrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options)
+ : FieldGeneratorBase(descriptor, fieldOrdinal, options) {
+}
+
+RepeatedPrimitiveFieldGenerator::~RepeatedPrimitiveFieldGenerator() {
+
+}
+
+void RepeatedPrimitiveFieldGenerator::GenerateMembers(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "private static readonly pb::FieldCodec<$type_name$> _repeated_$name$_codec\n"
+ " = pb::FieldCodec.For$capitalized_type_name$($tag$);\n");
+ printer->Print(variables_,
+ "private readonly pbc::RepeatedField<$type_name$> $name$_ = new pbc::RepeatedField<$type_name$>();\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ pbc::RepeatedField<$type_name$> $property_name$ {\n"
+ " get { return $name$_; }\n"
+ "}\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::GenerateMergingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.Add(other.$name$_);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.AddEntriesFrom(input, _repeated_$name$_codec);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$name$_.WriteTo(output, _repeated_$name$_codec);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "size += $name$_.CalculateSize(_repeated_$name$_codec);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::WriteHash(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "hash ^= $name$_.GetHashCode();\n");
+}
+void RepeatedPrimitiveFieldGenerator::WriteEquals(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if(!$name$_.Equals(other.$name$_)) return false;\n");
+}
+void RepeatedPrimitiveFieldGenerator::WriteToString(io::Printer* printer) {
+ printer->Print(variables_,
+ "PrintField(\"$descriptor_name$\", $name$_, writer);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$name$_ = other.$name$_.Clone();\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::GenerateFreezingCode(io::Printer* printer) {
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.h
new file mode 100644
index 0000000000..a59348a95f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_repeated_primitive_field.h
@@ -0,0 +1,71 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_PRIMITIVE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_PRIMITIVE_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+class RepeatedPrimitiveFieldGenerator : public FieldGeneratorBase {
+ public:
+ RepeatedPrimitiveFieldGenerator(const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options);
+ ~RepeatedPrimitiveFieldGenerator();
+
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateFreezingCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateMergingCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ virtual void WriteHash(io::Printer* printer);
+ virtual void WriteEquals(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedPrimitiveFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_REPEATED_PRIMITIVE_FIELD_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.cc
new file mode 100644
index 0000000000..1fda7ddf31
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.cc
@@ -0,0 +1,73 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+
+#include <google/protobuf/compiler/csharp/csharp_source_generator_base.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_names.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+SourceGeneratorBase::SourceGeneratorBase(const FileDescriptor* descriptor,
+ const Options *options)
+ : descriptor_(descriptor), options_(options) {
+}
+
+SourceGeneratorBase::~SourceGeneratorBase() {
+}
+
+void SourceGeneratorBase::WriteGeneratedCodeAttributes(io::Printer* printer) {
+ printer->Print("[global::System.Diagnostics.DebuggerNonUserCodeAttribute]\n");
+}
+
+std::string SourceGeneratorBase::class_access_level() {
+ return (IsDescriptorProto(descriptor_) || this->options()->internal_access) ? "internal" : "public";
+}
+
+const Options* SourceGeneratorBase::options() {
+ return this->options_;
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.h
new file mode 100644
index 0000000000..c741080ed8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_source_generator_base.h
@@ -0,0 +1,70 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_SOURCE_GENERATOR_BASE_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_SOURCE_GENERATOR_BASE_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+struct Options;
+
+class SourceGeneratorBase {
+ protected:
+ SourceGeneratorBase(const FileDescriptor* descriptor, const Options* options);
+ virtual ~SourceGeneratorBase();
+
+ std::string class_access_level();
+ const Options* options();
+
+ // Write any attributes used to decorate generated function members (methods and properties).
+ // Should not be used to decorate types.
+ void WriteGeneratedCodeAttributes(io::Printer* printer);
+
+ private:
+ const FileDescriptor* descriptor_;
+ const Options *options_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(SourceGeneratorBase);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_SOURCE_GENERATOR_BASE_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.cc
new file mode 100644
index 0000000000..797d498ed3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.cc
@@ -0,0 +1,211 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+
+#include <google/protobuf/compiler/csharp/csharp_doc_comment.h>
+#include <google/protobuf/compiler/csharp/csharp_helpers.h>
+#include <google/protobuf/compiler/csharp/csharp_options.h>
+#include <google/protobuf/compiler/csharp/csharp_wrapper_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+WrapperFieldGenerator::WrapperFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal, const Options *options)
+ : FieldGeneratorBase(descriptor, fieldOrdinal, options) {
+ variables_["has_property_check"] = name() + "_ != null";
+ variables_["has_not_property_check"] = name() + "_ == null";
+ const FieldDescriptor* wrapped_field = descriptor->message_type()->field(0);
+ is_value_type = wrapped_field->type() != FieldDescriptor::TYPE_STRING &&
+ wrapped_field->type() != FieldDescriptor::TYPE_BYTES;
+ if (is_value_type) {
+ variables_["nonnullable_type_name"] = type_name(wrapped_field);
+ }
+}
+
+WrapperFieldGenerator::~WrapperFieldGenerator() {
+}
+
+void WrapperFieldGenerator::GenerateMembers(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "private static readonly pb::FieldCodec<$type_name$> _single_$name$_codec = ");
+ GenerateCodecCode(printer);
+ printer->Print(
+ variables_,
+ ";\n"
+ "private $type_name$ $name$_;\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ $type_name$ $property_name$ {\n"
+ " get { return $name$_; }\n"
+ " set {\n"
+ " $name$_ = value;\n"
+ " }\n"
+ "}\n");
+}
+
+void WrapperFieldGenerator::GenerateMergingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if (other.$has_property_check$) {\n"
+ " if ($has_not_property_check$ || other.$property_name$ != $default_value$) {\n"
+ " $property_name$ = other.$property_name$;\n"
+ " }\n"
+ "}\n");
+}
+
+void WrapperFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$type_name$ value = _single_$name$_codec.Read(input);\n"
+ "if ($has_not_property_check$ || value != $default_value$) {\n"
+ " $property_name$ = value;\n"
+ "}\n");
+}
+
+void WrapperFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " _single_$name$_codec.WriteTagAndValue(output, $property_name$);\n"
+ "}\n");
+}
+
+void WrapperFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " size += _single_$name$_codec.CalculateSizeWithTag($property_name$);\n"
+ "}\n");
+}
+
+void WrapperFieldGenerator::WriteHash(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) hash ^= $property_name$.GetHashCode();\n");
+}
+
+void WrapperFieldGenerator::WriteEquals(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "if ($property_name$ != other.$property_name$) return false;\n");
+}
+
+void WrapperFieldGenerator::WriteToString(io::Printer* printer) {
+ // TODO: Implement if we ever actually need it...
+}
+
+void WrapperFieldGenerator::GenerateCloningCode(io::Printer* printer) {
+ printer->Print(variables_,
+ "$property_name$ = other.$property_name$;\n");
+}
+
+void WrapperFieldGenerator::GenerateCodecCode(io::Printer* printer) {
+ if (is_value_type) {
+ printer->Print(
+ variables_,
+ "pb::FieldCodec.ForStructWrapper<$nonnullable_type_name$>($tag$)");
+ } else {
+ printer->Print(
+ variables_,
+ "pb::FieldCodec.ForClassWrapper<$type_name$>($tag$)");
+ }
+}
+
+WrapperOneofFieldGenerator::WrapperOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int fieldOrdinal, const Options *options)
+ : WrapperFieldGenerator(descriptor, fieldOrdinal, options) {
+ SetCommonOneofFieldVariables(&variables_);
+}
+
+WrapperOneofFieldGenerator::~WrapperOneofFieldGenerator() {
+}
+
+void WrapperOneofFieldGenerator::GenerateMembers(io::Printer* printer) {
+ // Note: deliberately _oneof_$name$_codec, not _$oneof_name$_codec... we have one codec per field.
+ printer->Print(
+ variables_,
+ "private static readonly pb::FieldCodec<$type_name$> _oneof_$name$_codec = ");
+ GenerateCodecCode(printer);
+ printer->Print(";\n");
+ WritePropertyDocComment(printer, descriptor_);
+ AddPublicMemberAttributes(printer);
+ printer->Print(
+ variables_,
+ "$access_level$ $type_name$ $property_name$ {\n"
+ " get { return $has_property_check$ ? ($type_name$) $oneof_name$_ : ($type_name$) null; }\n"
+ " set {\n"
+ " $oneof_name$_ = value;\n"
+ " $oneof_name$Case_ = value == null ? $oneof_property_name$OneofCase.None : $oneof_property_name$OneofCase.$property_name$;\n"
+ " }\n"
+ "}\n");
+}
+
+void WrapperOneofFieldGenerator::GenerateParsingCode(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$property_name$ = _oneof_$name$_codec.Read(input);\n");
+}
+
+void WrapperOneofFieldGenerator::GenerateSerializationCode(io::Printer* printer) {
+ // TODO: I suspect this is wrong...
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " _oneof_$name$_codec.WriteTagAndValue(output, ($type_name$) $oneof_name$_);\n"
+ "}\n");
+}
+
+void WrapperOneofFieldGenerator::GenerateSerializedSizeCode(io::Printer* printer) {
+ // TODO: I suspect this is wrong...
+ printer->Print(
+ variables_,
+ "if ($has_property_check$) {\n"
+ " size += _oneof_$name$_codec.CalculateSizeWithTag($property_name$);\n"
+ "}\n");
+}
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.h
new file mode 100644
index 0000000000..250dfd2548
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/csharp/csharp_wrapper_field.h
@@ -0,0 +1,91 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_CSHARP_WRAPPER_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_CSHARP_WRAPPER_FIELD_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_field_base.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace csharp {
+
+struct Options;
+
+class WrapperFieldGenerator : public FieldGeneratorBase {
+ public:
+ WrapperFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~WrapperFieldGenerator();
+
+ virtual void GenerateCodecCode(io::Printer* printer);
+ virtual void GenerateCloningCode(io::Printer* printer);
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateMergingCode(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ virtual void WriteHash(io::Printer* printer);
+ virtual void WriteEquals(io::Printer* printer);
+ virtual void WriteToString(io::Printer* printer);
+
+ private:
+ bool is_value_type; // True for int32 etc; false for bytes and string
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(WrapperFieldGenerator);
+};
+
+class WrapperOneofFieldGenerator : public WrapperFieldGenerator {
+ public:
+ WrapperOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int fieldOrdinal,
+ const Options *options);
+ ~WrapperOneofFieldGenerator();
+
+ virtual void GenerateMembers(io::Printer* printer);
+ virtual void GenerateParsingCode(io::Printer* printer);
+ virtual void GenerateSerializationCode(io::Printer* printer);
+ virtual void GenerateSerializedSizeCode(io::Printer* printer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(WrapperOneofFieldGenerator);
+};
+
+} // namespace csharp
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_CSHARP_WRAPPER_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.cc
new file mode 100644
index 0000000000..0d9093c047
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.cc
@@ -0,0 +1,496 @@
+// 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.
+
+#ifdef _MSC_VER
+#include <io.h>
+#else
+#include <unistd.h>
+#endif
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <errno.h>
+
+#include <algorithm>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/importer.h>
+
+#include <google/protobuf/compiler/parser.h>
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+#ifdef _WIN32
+#ifndef F_OK
+#define F_OK 00 // not defined by MSVC for whatever reason
+#endif
+#include <ctype.h>
+#endif
+
+// Returns true if the text looks like a Windows-style absolute path, starting
+// with a drive letter. Example: "C:\foo". TODO(kenton): Share this with
+// copy in command_line_interface.cc?
+static bool IsWindowsAbsolutePath(const string& text) {
+#if defined(_WIN32) || defined(__CYGWIN__)
+ return text.size() >= 3 && text[1] == ':' &&
+ isalpha(text[0]) &&
+ (text[2] == '/' || text[2] == '\\') &&
+ text.find_last_of(':') == 1;
+#else
+ return false;
+#endif
+}
+
+MultiFileErrorCollector::~MultiFileErrorCollector() {}
+
+// This class serves two purposes:
+// - It implements the ErrorCollector interface (used by Tokenizer and Parser)
+// in terms of MultiFileErrorCollector, using a particular filename.
+// - It lets us check if any errors have occurred.
+class SourceTreeDescriptorDatabase::SingleFileErrorCollector
+ : public io::ErrorCollector {
+ public:
+ SingleFileErrorCollector(const string& filename,
+ MultiFileErrorCollector* multi_file_error_collector)
+ : filename_(filename),
+ multi_file_error_collector_(multi_file_error_collector),
+ had_errors_(false) {}
+ ~SingleFileErrorCollector() {}
+
+ bool had_errors() { return had_errors_; }
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(int line, int column, const string& message) {
+ if (multi_file_error_collector_ != NULL) {
+ multi_file_error_collector_->AddError(filename_, line, column, message);
+ }
+ had_errors_ = true;
+ }
+
+ private:
+ string filename_;
+ MultiFileErrorCollector* multi_file_error_collector_;
+ bool had_errors_;
+};
+
+// ===================================================================
+
+SourceTreeDescriptorDatabase::SourceTreeDescriptorDatabase(
+ SourceTree* source_tree)
+ : source_tree_(source_tree),
+ error_collector_(NULL),
+ using_validation_error_collector_(false),
+ validation_error_collector_(this) {}
+
+SourceTreeDescriptorDatabase::~SourceTreeDescriptorDatabase() {}
+
+bool SourceTreeDescriptorDatabase::FindFileByName(
+ const string& filename, FileDescriptorProto* output) {
+ google::protobuf::scoped_ptr<io::ZeroCopyInputStream> input(source_tree_->Open(filename));
+ if (input == NULL) {
+ if (error_collector_ != NULL) {
+ error_collector_->AddError(filename, -1, 0,
+ source_tree_->GetLastErrorMessage());
+ }
+ return false;
+ }
+
+ // Set up the tokenizer and parser.
+ SingleFileErrorCollector file_error_collector(filename, error_collector_);
+ io::Tokenizer tokenizer(input.get(), &file_error_collector);
+
+ Parser parser;
+ if (error_collector_ != NULL) {
+ parser.RecordErrorsTo(&file_error_collector);
+ }
+ if (using_validation_error_collector_) {
+ parser.RecordSourceLocationsTo(&source_locations_);
+ }
+
+ // Parse it.
+ output->set_name(filename);
+ return parser.Parse(&tokenizer, output) &&
+ !file_error_collector.had_errors();
+}
+
+bool SourceTreeDescriptorDatabase::FindFileContainingSymbol(
+ const string& symbol_name, FileDescriptorProto* output) {
+ return false;
+}
+
+bool SourceTreeDescriptorDatabase::FindFileContainingExtension(
+ const string& containing_type, int field_number,
+ FileDescriptorProto* output) {
+ return false;
+}
+
+// -------------------------------------------------------------------
+
+SourceTreeDescriptorDatabase::ValidationErrorCollector::
+ValidationErrorCollector(SourceTreeDescriptorDatabase* owner)
+ : owner_(owner) {}
+
+SourceTreeDescriptorDatabase::ValidationErrorCollector::
+~ValidationErrorCollector() {}
+
+void SourceTreeDescriptorDatabase::ValidationErrorCollector::AddError(
+ const string& filename,
+ const string& element_name,
+ const Message* descriptor,
+ ErrorLocation location,
+ const string& message) {
+ if (owner_->error_collector_ == NULL) return;
+
+ int line, column;
+ owner_->source_locations_.Find(descriptor, location, &line, &column);
+ owner_->error_collector_->AddError(filename, line, column, message);
+}
+
+void SourceTreeDescriptorDatabase::ValidationErrorCollector::AddWarning(
+ const string& filename,
+ const string& element_name,
+ const Message* descriptor,
+ ErrorLocation location,
+ const string& message) {
+ if (owner_->error_collector_ == NULL) return;
+
+ int line, column;
+ owner_->source_locations_.Find(descriptor, location, &line, &column);
+ owner_->error_collector_->AddWarning(filename, line, column, message);
+}
+
+// ===================================================================
+
+Importer::Importer(SourceTree* source_tree,
+ MultiFileErrorCollector* error_collector)
+ : database_(source_tree),
+ pool_(&database_, database_.GetValidationErrorCollector()) {
+ pool_.EnforceWeakDependencies(true);
+ database_.RecordErrorsTo(error_collector);
+}
+
+Importer::~Importer() {}
+
+const FileDescriptor* Importer::Import(const string& filename) {
+ return pool_.FindFileByName(filename);
+}
+
+void Importer::AddUnusedImportTrackFile(const string& file_name) {
+ pool_.AddUnusedImportTrackFile(file_name);
+}
+
+void Importer::ClearUnusedImportTrackFiles() {
+ pool_.ClearUnusedImportTrackFiles();
+}
+
+// ===================================================================
+
+SourceTree::~SourceTree() {}
+
+string SourceTree::GetLastErrorMessage() {
+ return "File not found.";
+}
+
+DiskSourceTree::DiskSourceTree() {}
+
+DiskSourceTree::~DiskSourceTree() {}
+
+static inline char LastChar(const string& str) {
+ return str[str.size() - 1];
+}
+
+// Given a path, returns an equivalent path with these changes:
+// - On Windows, any backslashes are replaced with forward slashes.
+// - Any instances of the directory "." are removed.
+// - Any consecutive '/'s are collapsed into a single slash.
+// Note that the resulting string may be empty.
+//
+// TODO(kenton): It would be nice to handle "..", e.g. so that we can figure
+// out that "foo/bar.proto" is inside "baz/../foo". However, if baz is a
+// symlink or doesn't exist, then things get complicated, and we can't
+// actually determine this without investigating the filesystem, probably
+// in non-portable ways. So, we punt.
+//
+// TODO(kenton): It would be nice to use realpath() here except that it
+// resolves symbolic links. This could cause problems if people place
+// symbolic links in their source tree. For example, if you executed:
+// protoc --proto_path=foo foo/bar/baz.proto
+// then if foo/bar is a symbolic link, foo/bar/baz.proto will canonicalize
+// to a path which does not appear to be under foo, and thus the compiler
+// will complain that baz.proto is not inside the --proto_path.
+static string CanonicalizePath(string path) {
+#ifdef _WIN32
+ // The Win32 API accepts forward slashes as a path delimiter even though
+ // backslashes are standard. Let's avoid confusion and use only forward
+ // slashes.
+ if (HasPrefixString(path, "\\\\")) {
+ // Avoid converting two leading backslashes.
+ path = "\\\\" + StringReplace(path.substr(2), "\\", "/", true);
+ } else {
+ path = StringReplace(path, "\\", "/", true);
+ }
+#endif
+
+ vector<string> canonical_parts;
+ vector<string> parts = Split(
+ path, "/", true); // Note: Removes empty parts.
+ for (int i = 0; i < parts.size(); i++) {
+ if (parts[i] == ".") {
+ // Ignore.
+ } else {
+ canonical_parts.push_back(parts[i]);
+ }
+ }
+ string result = Join(canonical_parts, "/");
+ if (!path.empty() && path[0] == '/') {
+ // Restore leading slash.
+ result = '/' + result;
+ }
+ if (!path.empty() && LastChar(path) == '/' &&
+ !result.empty() && LastChar(result) != '/') {
+ // Restore trailing slash.
+ result += '/';
+ }
+ return result;
+}
+
+static inline bool ContainsParentReference(const string& path) {
+ return path == ".." ||
+ HasPrefixString(path, "../") ||
+ HasSuffixString(path, "/..") ||
+ path.find("/../") != string::npos;
+}
+
+// Maps a file from an old location to a new one. Typically, old_prefix is
+// a virtual path and new_prefix is its corresponding disk path. Returns
+// false if the filename did not start with old_prefix, otherwise replaces
+// old_prefix with new_prefix and stores the result in *result. Examples:
+// string result;
+// assert(ApplyMapping("foo/bar", "", "baz", &result));
+// assert(result == "baz/foo/bar");
+//
+// assert(ApplyMapping("foo/bar", "foo", "baz", &result));
+// assert(result == "baz/bar");
+//
+// assert(ApplyMapping("foo", "foo", "bar", &result));
+// assert(result == "bar");
+//
+// assert(!ApplyMapping("foo/bar", "baz", "qux", &result));
+// assert(!ApplyMapping("foo/bar", "baz", "qux", &result));
+// assert(!ApplyMapping("foobar", "foo", "baz", &result));
+static bool ApplyMapping(const string& filename,
+ const string& old_prefix,
+ const string& new_prefix,
+ string* result) {
+ if (old_prefix.empty()) {
+ // old_prefix matches any relative path.
+ if (ContainsParentReference(filename)) {
+ // We do not allow the file name to use "..".
+ return false;
+ }
+ if (HasPrefixString(filename, "/") ||
+ IsWindowsAbsolutePath(filename)) {
+ // This is an absolute path, so it isn't matched by the empty string.
+ return false;
+ }
+ result->assign(new_prefix);
+ if (!result->empty()) result->push_back('/');
+ result->append(filename);
+ return true;
+ } else if (HasPrefixString(filename, old_prefix)) {
+ // old_prefix is a prefix of the filename. Is it the whole filename?
+ if (filename.size() == old_prefix.size()) {
+ // Yep, it's an exact match.
+ *result = new_prefix;
+ return true;
+ } else {
+ // Not an exact match. Is the next character a '/'? Otherwise,
+ // this isn't actually a match at all. E.g. the prefix "foo/bar"
+ // does not match the filename "foo/barbaz".
+ int after_prefix_start = -1;
+ if (filename[old_prefix.size()] == '/') {
+ after_prefix_start = old_prefix.size() + 1;
+ } else if (filename[old_prefix.size() - 1] == '/') {
+ // old_prefix is never empty, and canonicalized paths never have
+ // consecutive '/' characters.
+ after_prefix_start = old_prefix.size();
+ }
+ if (after_prefix_start != -1) {
+ // Yep. So the prefixes are directories and the filename is a file
+ // inside them.
+ string after_prefix = filename.substr(after_prefix_start);
+ if (ContainsParentReference(after_prefix)) {
+ // We do not allow the file name to use "..".
+ return false;
+ }
+ result->assign(new_prefix);
+ if (!result->empty()) result->push_back('/');
+ result->append(after_prefix);
+ return true;
+ }
+ }
+ }
+
+ return false;
+}
+
+void DiskSourceTree::MapPath(const string& virtual_path,
+ const string& disk_path) {
+ mappings_.push_back(Mapping(virtual_path, CanonicalizePath(disk_path)));
+}
+
+DiskSourceTree::DiskFileToVirtualFileResult
+DiskSourceTree::DiskFileToVirtualFile(
+ const string& disk_file,
+ string* virtual_file,
+ string* shadowing_disk_file) {
+ int mapping_index = -1;
+ string canonical_disk_file = CanonicalizePath(disk_file);
+
+ for (int i = 0; i < mappings_.size(); i++) {
+ // Apply the mapping in reverse.
+ if (ApplyMapping(canonical_disk_file, mappings_[i].disk_path,
+ mappings_[i].virtual_path, virtual_file)) {
+ // Success.
+ mapping_index = i;
+ break;
+ }
+ }
+
+ if (mapping_index == -1) {
+ return NO_MAPPING;
+ }
+
+ // Iterate through all mappings with higher precedence and verify that none
+ // of them map this file to some other existing file.
+ for (int i = 0; i < mapping_index; i++) {
+ if (ApplyMapping(*virtual_file, mappings_[i].virtual_path,
+ mappings_[i].disk_path, shadowing_disk_file)) {
+ if (access(shadowing_disk_file->c_str(), F_OK) >= 0) {
+ // File exists.
+ return SHADOWED;
+ }
+ }
+ }
+ shadowing_disk_file->clear();
+
+ // Verify that we can open the file. Note that this also has the side-effect
+ // of verifying that we are not canonicalizing away any non-existent
+ // directories.
+ google::protobuf::scoped_ptr<io::ZeroCopyInputStream> stream(OpenDiskFile(disk_file));
+ if (stream == NULL) {
+ return CANNOT_OPEN;
+ }
+
+ return SUCCESS;
+}
+
+bool DiskSourceTree::VirtualFileToDiskFile(const string& virtual_file,
+ string* disk_file) {
+ google::protobuf::scoped_ptr<io::ZeroCopyInputStream> stream(
+ OpenVirtualFile(virtual_file, disk_file));
+ return stream != NULL;
+}
+
+io::ZeroCopyInputStream* DiskSourceTree::Open(const string& filename) {
+ return OpenVirtualFile(filename, NULL);
+}
+
+string DiskSourceTree::GetLastErrorMessage() {
+ return last_error_message_;
+}
+
+io::ZeroCopyInputStream* DiskSourceTree::OpenVirtualFile(
+ const string& virtual_file,
+ string* disk_file) {
+ if (virtual_file != CanonicalizePath(virtual_file) ||
+ ContainsParentReference(virtual_file)) {
+ // We do not allow importing of paths containing things like ".." or
+ // consecutive slashes since the compiler expects files to be uniquely
+ // identified by file name.
+ last_error_message_ = "Backslashes, consecutive slashes, \".\", or \"..\" "
+ "are not allowed in the virtual path";
+ return NULL;
+ }
+
+ for (int i = 0; i < mappings_.size(); i++) {
+ string temp_disk_file;
+ if (ApplyMapping(virtual_file, mappings_[i].virtual_path,
+ mappings_[i].disk_path, &temp_disk_file)) {
+ io::ZeroCopyInputStream* stream = OpenDiskFile(temp_disk_file);
+ if (stream != NULL) {
+ if (disk_file != NULL) {
+ *disk_file = temp_disk_file;
+ }
+ return stream;
+ }
+
+ if (errno == EACCES) {
+ // The file exists but is not readable.
+ last_error_message_ = "Read access is denied for file: " +
+ temp_disk_file;
+ return NULL;
+ }
+ }
+ }
+ last_error_message_ = "File not found.";
+ return NULL;
+}
+
+io::ZeroCopyInputStream* DiskSourceTree::OpenDiskFile(
+ const string& filename) {
+ int file_descriptor;
+ do {
+ file_descriptor = open(filename.c_str(), O_RDONLY);
+ } while (file_descriptor < 0 && errno == EINTR);
+ if (file_descriptor >= 0) {
+ io::FileInputStream* result = new io::FileInputStream(file_descriptor);
+ result->SetCloseOnDelete(true);
+ return result;
+ } else {
+ return NULL;
+ }
+}
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.h
new file mode 100644
index 0000000000..cc8fcc39b0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer.h
@@ -0,0 +1,326 @@
+// 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 is the public interface to the .proto file parser.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_IMPORTER_H__
+#define GOOGLE_PROTOBUF_COMPILER_IMPORTER_H__
+
+#include <string>
+#include <vector>
+#include <set>
+#include <utility>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor_database.h>
+#include <google/protobuf/compiler/parser.h>
+
+namespace google {
+namespace protobuf {
+
+namespace io { class ZeroCopyInputStream; }
+
+namespace compiler {
+
+// Defined in this file.
+class Importer;
+class MultiFileErrorCollector;
+class SourceTree;
+class DiskSourceTree;
+
+// TODO(kenton): Move all SourceTree stuff to a separate file?
+
+// An implementation of DescriptorDatabase which loads files from a SourceTree
+// and parses them.
+//
+// Note: This class is not thread-safe since it maintains a table of source
+// code locations for error reporting. However, when a DescriptorPool wraps
+// a DescriptorDatabase, it uses mutex locking to make sure only one method
+// of the database is called at a time, even if the DescriptorPool is used
+// from multiple threads. Therefore, there is only a problem if you create
+// multiple DescriptorPools wrapping the same SourceTreeDescriptorDatabase
+// and use them from multiple threads.
+//
+// Note: This class does not implement FindFileContainingSymbol() or
+// FindFileContainingExtension(); these will always return false.
+class LIBPROTOBUF_EXPORT SourceTreeDescriptorDatabase : public DescriptorDatabase {
+ public:
+ SourceTreeDescriptorDatabase(SourceTree* source_tree);
+ ~SourceTreeDescriptorDatabase();
+
+ // Instructs the SourceTreeDescriptorDatabase to report any parse errors
+ // to the given MultiFileErrorCollector. This should be called before
+ // parsing. error_collector must remain valid until either this method
+ // is called again or the SourceTreeDescriptorDatabase is destroyed.
+ void RecordErrorsTo(MultiFileErrorCollector* error_collector) {
+ error_collector_ = error_collector;
+ }
+
+ // Gets a DescriptorPool::ErrorCollector which records errors to the
+ // MultiFileErrorCollector specified with RecordErrorsTo(). This collector
+ // has the ability to determine exact line and column numbers of errors
+ // from the information given to it by the DescriptorPool.
+ DescriptorPool::ErrorCollector* GetValidationErrorCollector() {
+ using_validation_error_collector_ = true;
+ return &validation_error_collector_;
+ }
+
+ // implements DescriptorDatabase -----------------------------------
+ bool FindFileByName(const string& filename, FileDescriptorProto* output);
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output);
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output);
+
+ private:
+ class SingleFileErrorCollector;
+
+ SourceTree* source_tree_;
+ MultiFileErrorCollector* error_collector_;
+
+ class LIBPROTOBUF_EXPORT ValidationErrorCollector : public DescriptorPool::ErrorCollector {
+ public:
+ ValidationErrorCollector(SourceTreeDescriptorDatabase* owner);
+ ~ValidationErrorCollector();
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(const string& filename,
+ const string& element_name,
+ const Message* descriptor,
+ ErrorLocation location,
+ const string& message);
+
+ virtual void AddWarning(const string& filename,
+ const string& element_name,
+ const Message* descriptor,
+ ErrorLocation location,
+ const string& message);
+
+ private:
+ SourceTreeDescriptorDatabase* owner_;
+ };
+ friend class ValidationErrorCollector;
+
+ bool using_validation_error_collector_;
+ SourceLocationTable source_locations_;
+ ValidationErrorCollector validation_error_collector_;
+};
+
+// Simple interface for parsing .proto files. This wraps the process
+// of opening the file, parsing it with a Parser, recursively parsing all its
+// imports, and then cross-linking the results to produce a FileDescriptor.
+//
+// This is really just a thin wrapper around SourceTreeDescriptorDatabase.
+// You may find that SourceTreeDescriptorDatabase is more flexible.
+//
+// TODO(kenton): I feel like this class is not well-named.
+class LIBPROTOBUF_EXPORT Importer {
+ public:
+ Importer(SourceTree* source_tree,
+ MultiFileErrorCollector* error_collector);
+ ~Importer();
+
+ // Import the given file and build a FileDescriptor representing it. If
+ // the file is already in the DescriptorPool, the existing FileDescriptor
+ // will be returned. The FileDescriptor is property of the DescriptorPool,
+ // and will remain valid until it is destroyed. If any errors occur, they
+ // will be reported using the error collector and Import() will return NULL.
+ //
+ // A particular Importer object will only report errors for a particular
+ // file once. All future attempts to import the same file will return NULL
+ // without reporting any errors. The idea is that you might want to import
+ // a lot of files without seeing the same errors over and over again. If
+ // you want to see errors for the same files repeatedly, you can use a
+ // separate Importer object to import each one (but use the same
+ // DescriptorPool so that they can be cross-linked).
+ const FileDescriptor* Import(const string& filename);
+
+ // The DescriptorPool in which all imported FileDescriptors and their
+ // contents are stored.
+ inline const DescriptorPool* pool() const {
+ return &pool_;
+ }
+
+ void AddUnusedImportTrackFile(const string& file_name);
+ void ClearUnusedImportTrackFiles();
+
+ private:
+ SourceTreeDescriptorDatabase database_;
+ DescriptorPool pool_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Importer);
+};
+
+// If the importer encounters problems while trying to import the proto files,
+// it reports them to a MultiFileErrorCollector.
+class LIBPROTOBUF_EXPORT MultiFileErrorCollector {
+ public:
+ inline MultiFileErrorCollector() {}
+ virtual ~MultiFileErrorCollector();
+
+ // Line and column numbers are zero-based. A line number of -1 indicates
+ // an error with the entire file (e.g. "not found").
+ virtual void AddError(const string& filename, int line, int column,
+ const string& message) = 0;
+
+ virtual void AddWarning(const string& filename, int line, int column,
+ const string& message) {}
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MultiFileErrorCollector);
+};
+
+// Abstract interface which represents a directory tree containing proto files.
+// Used by the default implementation of Importer to resolve import statements
+// Most users will probably want to use the DiskSourceTree implementation,
+// below.
+class LIBPROTOBUF_EXPORT SourceTree {
+ public:
+ inline SourceTree() {}
+ virtual ~SourceTree();
+
+ // Open the given file and return a stream that reads it, or NULL if not
+ // found. The caller takes ownership of the returned object. The filename
+ // must be a path relative to the root of the source tree and must not
+ // contain "." or ".." components.
+ virtual io::ZeroCopyInputStream* Open(const string& filename) = 0;
+
+ // If Open() returns NULL, calling this method immediately will return an
+ // description of the error.
+ // Subclasses should implement this method and return a meaningful value for
+ // better error reporting.
+ // TODO(xiaofeng): change this to a pure virtual function.
+ virtual string GetLastErrorMessage();
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(SourceTree);
+};
+
+// An implementation of SourceTree which loads files from locations on disk.
+// Multiple mappings can be set up to map locations in the DiskSourceTree to
+// locations in the physical filesystem.
+class LIBPROTOBUF_EXPORT DiskSourceTree : public SourceTree {
+ public:
+ DiskSourceTree();
+ ~DiskSourceTree();
+
+ // Map a path on disk to a location in the SourceTree. The path may be
+ // either a file or a directory. If it is a directory, the entire tree
+ // under it will be mapped to the given virtual location. To map a directory
+ // to the root of the source tree, pass an empty string for virtual_path.
+ //
+ // If multiple mapped paths apply when opening a file, they will be searched
+ // in order. For example, if you do:
+ // MapPath("bar", "foo/bar");
+ // MapPath("", "baz");
+ // and then you do:
+ // Open("bar/qux");
+ // the DiskSourceTree will first try to open foo/bar/qux, then baz/bar/qux,
+ // returning the first one that opens successfuly.
+ //
+ // disk_path may be an absolute path or relative to the current directory,
+ // just like a path you'd pass to open().
+ void MapPath(const string& virtual_path, const string& disk_path);
+
+ // Return type for DiskFileToVirtualFile().
+ enum DiskFileToVirtualFileResult {
+ SUCCESS,
+ SHADOWED,
+ CANNOT_OPEN,
+ NO_MAPPING
+ };
+
+ // Given a path to a file on disk, find a virtual path mapping to that
+ // file. The first mapping created with MapPath() whose disk_path contains
+ // the filename is used. However, that virtual path may not actually be
+ // usable to open the given file. Possible return values are:
+ // * SUCCESS: The mapping was found. *virtual_file is filled in so that
+ // calling Open(*virtual_file) will open the file named by disk_file.
+ // * SHADOWED: A mapping was found, but using Open() to open this virtual
+ // path will end up returning some different file. This is because some
+ // other mapping with a higher precedence also matches this virtual path
+ // and maps it to a different file that exists on disk. *virtual_file
+ // is filled in as it would be in the SUCCESS case. *shadowing_disk_file
+ // is filled in with the disk path of the file which would be opened if
+ // you were to call Open(*virtual_file).
+ // * CANNOT_OPEN: The mapping was found and was not shadowed, but the
+ // file specified cannot be opened. When this value is returned,
+ // errno will indicate the reason the file cannot be opened. *virtual_file
+ // will be set to the virtual path as in the SUCCESS case, even though
+ // it is not useful.
+ // * NO_MAPPING: Indicates that no mapping was found which contains this
+ // file.
+ DiskFileToVirtualFileResult
+ DiskFileToVirtualFile(const string& disk_file,
+ string* virtual_file,
+ string* shadowing_disk_file);
+
+ // Given a virtual path, find the path to the file on disk.
+ // Return true and update disk_file with the on-disk path if the file exists.
+ // Return false and leave disk_file untouched if the file doesn't exist.
+ bool VirtualFileToDiskFile(const string& virtual_file, string* disk_file);
+
+ // implements SourceTree -------------------------------------------
+ virtual io::ZeroCopyInputStream* Open(const string& filename);
+
+ virtual string GetLastErrorMessage();
+
+ private:
+ struct Mapping {
+ string virtual_path;
+ string disk_path;
+
+ inline Mapping(const string& virtual_path_param,
+ const string& disk_path_param)
+ : virtual_path(virtual_path_param), disk_path(disk_path_param) {}
+ };
+ vector<Mapping> mappings_;
+ string last_error_message_;
+
+ // Like Open(), but returns the on-disk path in disk_file if disk_file is
+ // non-NULL and the file could be successfully opened.
+ io::ZeroCopyInputStream* OpenVirtualFile(const string& virtual_file,
+ string* disk_file);
+
+ // Like Open() but given the actual on-disk path.
+ io::ZeroCopyInputStream* OpenDiskFile(const string& filename);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DiskSourceTree);
+};
+
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_IMPORTER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer_unittest.cc
new file mode 100644
index 0000000000..1b6e970071
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/importer_unittest.cc
@@ -0,0 +1,523 @@
+// 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.
+
+#include <google/protobuf/compiler/importer.h>
+
+#include <google/protobuf/stubs/hash.h>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/map_util.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+namespace {
+
+bool FileExists(const string& path) {
+ return File::Exists(path);
+}
+
+#define EXPECT_SUBSTRING(needle, haystack) \
+ EXPECT_PRED_FORMAT2(testing::IsSubstring, (needle), (haystack))
+
+class MockErrorCollector : public MultiFileErrorCollector {
+ public:
+ MockErrorCollector() {}
+ ~MockErrorCollector() {}
+
+ string text_;
+ string warning_text_;
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(const string& filename, int line, int column,
+ const string& message) {
+ strings::SubstituteAndAppend(&text_, "$0:$1:$2: $3\n",
+ filename, line, column, message);
+ }
+
+ void AddWarning(const string& filename, int line, int column,
+ const string& message) {
+ strings::SubstituteAndAppend(&warning_text_, "$0:$1:$2: $3\n",
+ filename, line, column, message);
+ }
+};
+
+// -------------------------------------------------------------------
+
+// A dummy implementation of SourceTree backed by a simple map.
+class MockSourceTree : public SourceTree {
+ public:
+ MockSourceTree() {}
+ ~MockSourceTree() {}
+
+ void AddFile(const string& name, const char* contents) {
+ files_[name] = contents;
+ }
+
+ // implements SourceTree -------------------------------------------
+ io::ZeroCopyInputStream* Open(const string& filename) {
+ const char* contents = FindPtrOrNull(files_, filename);
+ if (contents == NULL) {
+ return NULL;
+ } else {
+ return new io::ArrayInputStream(contents, strlen(contents));
+ }
+ }
+
+ string GetLastErrorMessage() {
+ return "File not found.";
+ }
+
+ private:
+ hash_map<string, const char*> files_;
+};
+
+// ===================================================================
+
+class ImporterTest : public testing::Test {
+ protected:
+ ImporterTest()
+ : importer_(&source_tree_, &error_collector_) {}
+
+ void AddFile(const string& filename, const char* text) {
+ source_tree_.AddFile(filename, text);
+ }
+
+ // Return the collected error text
+ string error() const { return error_collector_.text_; }
+ string warning() const { return error_collector_.warning_text_; }
+
+ MockErrorCollector error_collector_;
+ MockSourceTree source_tree_;
+ Importer importer_;
+};
+
+TEST_F(ImporterTest, Import) {
+ // Test normal importing.
+ AddFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n");
+
+ const FileDescriptor* file = importer_.Import("foo.proto");
+ EXPECT_EQ("", error_collector_.text_);
+ ASSERT_TRUE(file != NULL);
+
+ ASSERT_EQ(1, file->message_type_count());
+ EXPECT_EQ("Foo", file->message_type(0)->name());
+
+ // Importing again should return same object.
+ EXPECT_EQ(file, importer_.Import("foo.proto"));
+}
+
+TEST_F(ImporterTest, ImportNested) {
+ // Test that importing a file which imports another file works.
+ AddFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "import \"bar.proto\";\n"
+ "message Foo {\n"
+ " optional Bar bar = 1;\n"
+ "}\n");
+ AddFile("bar.proto",
+ "syntax = \"proto2\";\n"
+ "message Bar {}\n");
+
+ // Note that both files are actually parsed by the first call to Import()
+ // here, since foo.proto imports bar.proto. The second call just returns
+ // the same ProtoFile for bar.proto which was constructed while importing
+ // foo.proto. We test that this is the case below by checking that bar
+ // is among foo's dependencies (by pointer).
+ const FileDescriptor* foo = importer_.Import("foo.proto");
+ const FileDescriptor* bar = importer_.Import("bar.proto");
+ EXPECT_EQ("", error_collector_.text_);
+ ASSERT_TRUE(foo != NULL);
+ ASSERT_TRUE(bar != NULL);
+
+ // Check that foo's dependency is the same object as bar.
+ ASSERT_EQ(1, foo->dependency_count());
+ EXPECT_EQ(bar, foo->dependency(0));
+
+ // Check that foo properly cross-links bar.
+ ASSERT_EQ(1, foo->message_type_count());
+ ASSERT_EQ(1, bar->message_type_count());
+ ASSERT_EQ(1, foo->message_type(0)->field_count());
+ ASSERT_EQ(FieldDescriptor::TYPE_MESSAGE,
+ foo->message_type(0)->field(0)->type());
+ EXPECT_EQ(bar->message_type(0),
+ foo->message_type(0)->field(0)->message_type());
+}
+
+TEST_F(ImporterTest, FileNotFound) {
+ // Error: Parsing a file that doesn't exist.
+ EXPECT_TRUE(importer_.Import("foo.proto") == NULL);
+ EXPECT_EQ(
+ "foo.proto:-1:0: File not found.\n",
+ error_collector_.text_);
+}
+
+TEST_F(ImporterTest, ImportNotFound) {
+ // Error: Importing a file that doesn't exist.
+ AddFile("foo.proto",
+ "syntax = \"proto2\";\n"
+ "import \"bar.proto\";\n");
+
+ EXPECT_TRUE(importer_.Import("foo.proto") == NULL);
+ EXPECT_EQ(
+ "bar.proto:-1:0: File not found.\n"
+ "foo.proto:-1:0: Import \"bar.proto\" was not found or had errors.\n",
+ error_collector_.text_);
+}
+
+TEST_F(ImporterTest, RecursiveImport) {
+ // Error: Recursive import.
+ AddFile("recursive1.proto",
+ "syntax = \"proto2\";\n"
+ "import \"recursive2.proto\";\n");
+ AddFile("recursive2.proto",
+ "syntax = \"proto2\";\n"
+ "import \"recursive1.proto\";\n");
+
+ EXPECT_TRUE(importer_.Import("recursive1.proto") == NULL);
+ EXPECT_EQ(
+ "recursive1.proto:-1:0: File recursively imports itself: recursive1.proto "
+ "-> recursive2.proto -> recursive1.proto\n"
+ "recursive2.proto:-1:0: Import \"recursive1.proto\" was not found "
+ "or had errors.\n"
+ "recursive1.proto:-1:0: Import \"recursive2.proto\" was not found "
+ "or had errors.\n",
+ error_collector_.text_);
+}
+
+
+// ===================================================================
+
+class DiskSourceTreeTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ dirnames_.push_back(TestTempDir() + "/test_proto2_import_path_1");
+ dirnames_.push_back(TestTempDir() + "/test_proto2_import_path_2");
+
+ for (int i = 0; i < dirnames_.size(); i++) {
+ if (FileExists(dirnames_[i])) {
+ File::DeleteRecursively(dirnames_[i], NULL, NULL);
+ }
+ GOOGLE_CHECK_OK(File::CreateDir(dirnames_[i], 0777));
+ }
+ }
+
+ virtual void TearDown() {
+ for (int i = 0; i < dirnames_.size(); i++) {
+ if (FileExists(dirnames_[i])) {
+ File::DeleteRecursively(dirnames_[i], NULL, NULL);
+ }
+ }
+ }
+
+ void AddFile(const string& filename, const char* contents) {
+ GOOGLE_CHECK_OK(File::SetContents(filename, contents, true));
+ }
+
+ void AddSubdir(const string& dirname) {
+ GOOGLE_CHECK_OK(File::CreateDir(dirname, 0777));
+ }
+
+ void ExpectFileContents(const string& filename,
+ const char* expected_contents) {
+ google::protobuf::scoped_ptr<io::ZeroCopyInputStream> input(source_tree_.Open(filename));
+
+ ASSERT_FALSE(input == NULL);
+
+ // Read all the data from the file.
+ string file_contents;
+ const void* data;
+ int size;
+ while (input->Next(&data, &size)) {
+ file_contents.append(reinterpret_cast<const char*>(data), size);
+ }
+
+ EXPECT_EQ(expected_contents, file_contents);
+ }
+
+ void ExpectCannotOpenFile(const string& filename,
+ const string& error_message) {
+ google::protobuf::scoped_ptr<io::ZeroCopyInputStream> input(source_tree_.Open(filename));
+ EXPECT_TRUE(input == NULL);
+ EXPECT_EQ(error_message, source_tree_.GetLastErrorMessage());
+ }
+
+ DiskSourceTree source_tree_;
+
+ // Paths of two on-disk directories to use during the test.
+ vector<string> dirnames_;
+};
+
+TEST_F(DiskSourceTreeTest, MapRoot) {
+ // Test opening a file in a directory that is mapped to the root of the
+ // source tree.
+ AddFile(dirnames_[0] + "/foo", "Hello World!");
+ source_tree_.MapPath("", dirnames_[0]);
+
+ ExpectFileContents("foo", "Hello World!");
+ ExpectCannotOpenFile("bar", "File not found.");
+}
+
+TEST_F(DiskSourceTreeTest, MapDirectory) {
+ // Test opening a file in a directory that is mapped to somewhere other
+ // than the root of the source tree.
+
+ AddFile(dirnames_[0] + "/foo", "Hello World!");
+ source_tree_.MapPath("baz", dirnames_[0]);
+
+ ExpectFileContents("baz/foo", "Hello World!");
+ ExpectCannotOpenFile("baz/bar", "File not found.");
+ ExpectCannotOpenFile("foo", "File not found.");
+ ExpectCannotOpenFile("bar", "File not found.");
+
+ // Non-canonical file names should not work.
+ ExpectCannotOpenFile("baz//foo",
+ "Backslashes, consecutive slashes, \".\", or \"..\" are "
+ "not allowed in the virtual path");
+ ExpectCannotOpenFile("baz/../baz/foo",
+ "Backslashes, consecutive slashes, \".\", or \"..\" are "
+ "not allowed in the virtual path");
+ ExpectCannotOpenFile("baz/./foo",
+ "Backslashes, consecutive slashes, \".\", or \"..\" are "
+ "not allowed in the virtual path");
+ ExpectCannotOpenFile("baz/foo/", "File not found.");
+}
+
+TEST_F(DiskSourceTreeTest, NoParent) {
+ // Test that we cannot open files in a parent of a mapped directory.
+
+ AddFile(dirnames_[0] + "/foo", "Hello World!");
+ AddSubdir(dirnames_[0] + "/bar");
+ AddFile(dirnames_[0] + "/bar/baz", "Blah.");
+ source_tree_.MapPath("", dirnames_[0] + "/bar");
+
+ ExpectFileContents("baz", "Blah.");
+ ExpectCannotOpenFile("../foo",
+ "Backslashes, consecutive slashes, \".\", or \"..\" are "
+ "not allowed in the virtual path");
+ ExpectCannotOpenFile("../bar/baz",
+ "Backslashes, consecutive slashes, \".\", or \"..\" are "
+ "not allowed in the virtual path");
+}
+
+TEST_F(DiskSourceTreeTest, MapFile) {
+ // Test opening a file that is mapped directly into the source tree.
+
+ AddFile(dirnames_[0] + "/foo", "Hello World!");
+ source_tree_.MapPath("foo", dirnames_[0] + "/foo");
+
+ ExpectFileContents("foo", "Hello World!");
+ ExpectCannotOpenFile("bar", "File not found.");
+}
+
+TEST_F(DiskSourceTreeTest, SearchMultipleDirectories) {
+ // Test mapping and searching multiple directories.
+
+ AddFile(dirnames_[0] + "/foo", "Hello World!");
+ AddFile(dirnames_[1] + "/foo", "This file should be hidden.");
+ AddFile(dirnames_[1] + "/bar", "Goodbye World!");
+ source_tree_.MapPath("", dirnames_[0]);
+ source_tree_.MapPath("", dirnames_[1]);
+
+ ExpectFileContents("foo", "Hello World!");
+ ExpectFileContents("bar", "Goodbye World!");
+ ExpectCannotOpenFile("baz", "File not found.");
+}
+
+TEST_F(DiskSourceTreeTest, OrderingTrumpsSpecificity) {
+ // Test that directories are always searched in order, even when a latter
+ // directory is more-specific than a former one.
+
+ // Create the "bar" directory so we can put a file in it.
+ GOOGLE_CHECK_OK(File::CreateDir(dirnames_[0] + "/bar", 0777));
+
+ // Add files and map paths.
+ AddFile(dirnames_[0] + "/bar/foo", "Hello World!");
+ AddFile(dirnames_[1] + "/foo", "This file should be hidden.");
+ source_tree_.MapPath("", dirnames_[0]);
+ source_tree_.MapPath("bar", dirnames_[1]);
+
+ // Check.
+ ExpectFileContents("bar/foo", "Hello World!");
+}
+
+TEST_F(DiskSourceTreeTest, DiskFileToVirtualFile) {
+ // Test DiskFileToVirtualFile.
+
+ AddFile(dirnames_[0] + "/foo", "Hello World!");
+ AddFile(dirnames_[1] + "/foo", "This file should be hidden.");
+ source_tree_.MapPath("bar", dirnames_[0]);
+ source_tree_.MapPath("bar", dirnames_[1]);
+
+ string virtual_file;
+ string shadowing_disk_file;
+
+ EXPECT_EQ(DiskSourceTree::NO_MAPPING,
+ source_tree_.DiskFileToVirtualFile(
+ "/foo", &virtual_file, &shadowing_disk_file));
+
+ EXPECT_EQ(DiskSourceTree::SHADOWED,
+ source_tree_.DiskFileToVirtualFile(
+ dirnames_[1] + "/foo", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("bar/foo", virtual_file);
+ EXPECT_EQ(dirnames_[0] + "/foo", shadowing_disk_file);
+
+ EXPECT_EQ(DiskSourceTree::CANNOT_OPEN,
+ source_tree_.DiskFileToVirtualFile(
+ dirnames_[1] + "/baz", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("bar/baz", virtual_file);
+
+ EXPECT_EQ(DiskSourceTree::SUCCESS,
+ source_tree_.DiskFileToVirtualFile(
+ dirnames_[0] + "/foo", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("bar/foo", virtual_file);
+}
+
+TEST_F(DiskSourceTreeTest, DiskFileToVirtualFileCanonicalization) {
+ // Test handling of "..", ".", etc. in DiskFileToVirtualFile().
+
+ source_tree_.MapPath("dir1", "..");
+ source_tree_.MapPath("dir2", "../../foo");
+ source_tree_.MapPath("dir3", "./foo/bar/.");
+ source_tree_.MapPath("dir4", ".");
+ source_tree_.MapPath("", "/qux");
+ source_tree_.MapPath("dir5", "/quux/");
+
+ string virtual_file;
+ string shadowing_disk_file;
+
+ // "../.." should not be considered to be under "..".
+ EXPECT_EQ(DiskSourceTree::NO_MAPPING,
+ source_tree_.DiskFileToVirtualFile(
+ "../../baz", &virtual_file, &shadowing_disk_file));
+
+ // "/foo" is not mapped (it should not be misintepreted as being under ".").
+ EXPECT_EQ(DiskSourceTree::NO_MAPPING,
+ source_tree_.DiskFileToVirtualFile(
+ "/foo", &virtual_file, &shadowing_disk_file));
+
+#ifdef WIN32
+ // "C:\foo" is not mapped (it should not be misintepreted as being under ".").
+ EXPECT_EQ(DiskSourceTree::NO_MAPPING,
+ source_tree_.DiskFileToVirtualFile(
+ "C:\\foo", &virtual_file, &shadowing_disk_file));
+#endif // WIN32
+
+ // But "../baz" should be.
+ EXPECT_EQ(DiskSourceTree::CANNOT_OPEN,
+ source_tree_.DiskFileToVirtualFile(
+ "../baz", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("dir1/baz", virtual_file);
+
+ // "../../foo/baz" is under "../../foo".
+ EXPECT_EQ(DiskSourceTree::CANNOT_OPEN,
+ source_tree_.DiskFileToVirtualFile(
+ "../../foo/baz", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("dir2/baz", virtual_file);
+
+ // "foo/./bar/baz" is under "./foo/bar/.".
+ EXPECT_EQ(DiskSourceTree::CANNOT_OPEN,
+ source_tree_.DiskFileToVirtualFile(
+ "foo/bar/baz", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("dir3/baz", virtual_file);
+
+ // "bar" is under ".".
+ EXPECT_EQ(DiskSourceTree::CANNOT_OPEN,
+ source_tree_.DiskFileToVirtualFile(
+ "bar", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("dir4/bar", virtual_file);
+
+ // "/qux/baz" is under "/qux".
+ EXPECT_EQ(DiskSourceTree::CANNOT_OPEN,
+ source_tree_.DiskFileToVirtualFile(
+ "/qux/baz", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("baz", virtual_file);
+
+ // "/quux/bar" is under "/quux".
+ EXPECT_EQ(DiskSourceTree::CANNOT_OPEN,
+ source_tree_.DiskFileToVirtualFile(
+ "/quux/bar", &virtual_file, &shadowing_disk_file));
+ EXPECT_EQ("dir5/bar", virtual_file);
+}
+
+TEST_F(DiskSourceTreeTest, VirtualFileToDiskFile) {
+ // Test VirtualFileToDiskFile.
+
+ AddFile(dirnames_[0] + "/foo", "Hello World!");
+ AddFile(dirnames_[1] + "/foo", "This file should be hidden.");
+ AddFile(dirnames_[1] + "/quux", "This file should not be hidden.");
+ source_tree_.MapPath("bar", dirnames_[0]);
+ source_tree_.MapPath("bar", dirnames_[1]);
+
+ // Existent files, shadowed and non-shadowed case.
+ string disk_file;
+ EXPECT_TRUE(source_tree_.VirtualFileToDiskFile("bar/foo", &disk_file));
+ EXPECT_EQ(dirnames_[0] + "/foo", disk_file);
+ EXPECT_TRUE(source_tree_.VirtualFileToDiskFile("bar/quux", &disk_file));
+ EXPECT_EQ(dirnames_[1] + "/quux", disk_file);
+
+ // Nonexistent file in existent directory and vice versa.
+ string not_touched = "not touched";
+ EXPECT_FALSE(source_tree_.VirtualFileToDiskFile("bar/baz", &not_touched));
+ EXPECT_EQ("not touched", not_touched);
+ EXPECT_FALSE(source_tree_.VirtualFileToDiskFile("baz/foo", &not_touched));
+ EXPECT_EQ("not touched", not_touched);
+
+ // Accept NULL as output parameter.
+ EXPECT_TRUE(source_tree_.VirtualFileToDiskFile("bar/foo", NULL));
+ EXPECT_FALSE(source_tree_.VirtualFileToDiskFile("baz/foo", NULL));
+}
+
+} // namespace
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.cc
new file mode 100644
index 0000000000..6cfa14a012
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.cc
@@ -0,0 +1,202 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_context.h>
+
+#include <google/protobuf/compiler/java/java_field.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+Context::Context(const FileDescriptor* file, const Options& options)
+ : name_resolver_(new ClassNameResolver), options_(options) {
+ InitializeFieldGeneratorInfo(file);
+}
+
+Context::~Context() {
+}
+
+ClassNameResolver* Context::GetNameResolver() {
+ return name_resolver_.get();
+}
+
+namespace {
+// Whether two fields have conflicting accessors (assuming name1 and name2
+// are different). name1 and name2 are field1 and field2's camel-case name
+// respectively.
+bool IsConflicting(const FieldDescriptor* field1, const string& name1,
+ const FieldDescriptor* field2, const string& name2,
+ string* info) {
+ if (field1->is_repeated()) {
+ if (field2->is_repeated()) {
+ // Both fields are repeated.
+ return false;
+ } else {
+ // field1 is repeated, and field2 is not.
+ if (name1 + "Count" == name2) {
+ *info = "both repeated field \"" + field1->name() + "\" and singular " +
+ "field \"" + field2->name() + "\" generates the method \"" +
+ "get" + name1 + "Count()\"";
+ return true;
+ }
+ if (name1 + "List" == name2) {
+ *info = "both repeated field \"" + field1->name() + "\" and singular " +
+ "field \"" + field2->name() + "\" generates the method \"" +
+ "get" + name1 + "List()\"";
+ return true;
+ }
+ // Well, there are obviously many more conflicting cases, but it probably
+ // doesn't worth the effort to exhaust all of them because they rarely
+ // happen and as we are continuing adding new methods/changing existing
+ // methods the number of different conflicting cases will keep growing.
+ // We can just add more cases here when they are found in the real world.
+ return false;
+ }
+ } else {
+ if (field2->is_repeated()) {
+ return IsConflicting(field2, name2, field1, name1, info);
+ } else {
+ // None of the two fields are repeated.
+ return false;
+ }
+ }
+}
+} // namespace
+
+void Context::InitializeFieldGeneratorInfo(const FileDescriptor* file) {
+ for (int i = 0; i < file->message_type_count(); ++i) {
+ InitializeFieldGeneratorInfoForMessage(file->message_type(i));
+ }
+}
+
+void Context::InitializeFieldGeneratorInfoForMessage(
+ const Descriptor* message) {
+ for (int i = 0; i < message->nested_type_count(); ++i) {
+ InitializeFieldGeneratorInfoForMessage(message->nested_type(i));
+ }
+ vector<const FieldDescriptor*> fields;
+ for (int i = 0; i < message->field_count(); ++i) {
+ fields.push_back(message->field(i));
+ }
+ InitializeFieldGeneratorInfoForFields(fields);
+
+ for (int i = 0; i < message->oneof_decl_count(); ++i) {
+ const OneofDescriptor* oneof = message->oneof_decl(i);
+ OneofGeneratorInfo info;
+ info.name = UnderscoresToCamelCase(oneof->name(), false);
+ info.capitalized_name = UnderscoresToCamelCase(oneof->name(), true);
+ oneof_generator_info_map_[oneof] = info;
+ }
+}
+
+void Context::InitializeFieldGeneratorInfoForFields(
+ const vector<const FieldDescriptor*>& fields) {
+ // Find out all fields that conflict with some other field in the same
+ // message.
+ vector<bool> is_conflict(fields.size());
+ vector<string> conflict_reason(fields.size());
+ for (int i = 0; i < fields.size(); ++i) {
+ const FieldDescriptor* field = fields[i];
+ const string& name = UnderscoresToCapitalizedCamelCase(field);
+ for (int j = i + 1; j < fields.size(); ++j) {
+ const FieldDescriptor* other = fields[j];
+ const string& other_name = UnderscoresToCapitalizedCamelCase(other);
+ if (name == other_name) {
+ is_conflict[i] = is_conflict[j] = true;
+ conflict_reason[i] = conflict_reason[j] =
+ "capitalized name of field \"" + field->name() +
+ "\" conflicts with field \"" + other->name() + "\"";
+ } else if (IsConflicting(field, name, other, other_name,
+ &conflict_reason[j])) {
+ is_conflict[i] = is_conflict[j] = true;
+ conflict_reason[i] = conflict_reason[j];
+ }
+ }
+ if (is_conflict[i]) {
+ GOOGLE_LOG(WARNING) << "field \"" << field->full_name() << "\" is conflicting "
+ << "with another field: " << conflict_reason[i];
+ }
+ }
+ for (int i = 0; i < fields.size(); ++i) {
+ const FieldDescriptor* field = fields[i];
+ FieldGeneratorInfo info;
+ info.name = UnderscoresToCamelCase(field);
+ info.capitalized_name = UnderscoresToCapitalizedCamelCase(field);
+ // For fields conflicting with some other fields, we append the field
+ // number to their field names in generated code to avoid conflicts.
+ if (is_conflict[i]) {
+ info.name += SimpleItoa(field->number());
+ info.capitalized_name += SimpleItoa(field->number());
+ info.disambiguated_reason = conflict_reason[i];
+ }
+ field_generator_info_map_[field] = info;
+ }
+}
+
+const FieldGeneratorInfo* Context::GetFieldGeneratorInfo(
+ const FieldDescriptor* field) const {
+ const FieldGeneratorInfo* result =
+ FindOrNull(field_generator_info_map_, field);
+ if (result == NULL) {
+ GOOGLE_LOG(FATAL) << "Can not find FieldGeneratorInfo for field: "
+ << field->full_name();
+ }
+ return result;
+}
+
+const OneofGeneratorInfo* Context::GetOneofGeneratorInfo(
+ const OneofDescriptor* oneof) const {
+ const OneofGeneratorInfo* result =
+ FindOrNull(oneof_generator_info_map_, oneof);
+ if (result == NULL) {
+ GOOGLE_LOG(FATAL) << "Can not find OneofGeneratorInfo for oneof: "
+ << oneof->name();
+ }
+ return result;
+}
+
+// Does this message class have generated parsing, serialization, and other
+// standard methods for which reflection-based fallback implementations exist?
+bool Context::HasGeneratedMethods(const Descriptor* descriptor) const {
+ return options_.enforce_lite ||
+ descriptor->file()->options().optimize_for() != FileOptions::CODE_SIZE;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.h
new file mode 100644
index 0000000000..f92ae87ea7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_context.h
@@ -0,0 +1,112 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_CONTEXT_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_CONTEXT_H__
+
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_options.h>
+
+namespace google {
+namespace protobuf {
+ class FileDescriptor;
+ class FieldDescriptor;
+ class OneofDescriptor;
+ class Descriptor;
+ class EnumDescriptor;
+ namespace compiler {
+ namespace java {
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+} // namespace protobuf
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+struct FieldGeneratorInfo;
+struct OneofGeneratorInfo;
+// A context object holds the information that is shared among all code
+// generators.
+class Context {
+ public:
+ Context(const FileDescriptor* file, const Options& options);
+ ~Context();
+
+ // Get the name resolver associated with this context. The resolver
+ // can be used to map descriptors to Java class names.
+ ClassNameResolver* GetNameResolver();
+
+ // Get the FieldGeneratorInfo for a given field.
+ const FieldGeneratorInfo* GetFieldGeneratorInfo(
+ const FieldDescriptor* field) const;
+
+ // Get the OneofGeneratorInfo for a given oneof.
+ const OneofGeneratorInfo* GetOneofGeneratorInfo(
+ const OneofDescriptor* oneof) const;
+
+ const Options& options() const { return options_; }
+
+ // Enforces all the files (including transitive dependencies) to use
+ // LiteRuntime.
+
+ bool EnforceLite() const { return options_.enforce_lite; }
+
+ // Does this message class have generated parsing, serialization, and other
+ // standard methods for which reflection-based fallback implementations exist?
+ bool HasGeneratedMethods(const Descriptor* descriptor) const;
+
+ private:
+ void InitializeFieldGeneratorInfo(const FileDescriptor* file);
+ void InitializeFieldGeneratorInfoForMessage(const Descriptor* message);
+ void InitializeFieldGeneratorInfoForFields(
+ const vector<const FieldDescriptor*>& fields);
+
+ google::protobuf::scoped_ptr<ClassNameResolver> name_resolver_;
+ map<const FieldDescriptor*, FieldGeneratorInfo> field_generator_info_map_;
+ map<const OneofDescriptor*, OneofGeneratorInfo> oneof_generator_info_map_;
+ Options options_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Context);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_CONTEXT_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.cc
new file mode 100644
index 0000000000..0b5caba434
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.cc
@@ -0,0 +1,233 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+
+#include <vector>
+
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+string EscapeJavadoc(const string& input) {
+ string result;
+ result.reserve(input.size() * 2);
+
+ char prev = '*';
+
+ for (string::size_type i = 0; i < input.size(); i++) {
+ char c = input[i];
+ switch (c) {
+ case '*':
+ // Avoid "/*".
+ if (prev == '/') {
+ result.append("&#42;");
+ } else {
+ result.push_back(c);
+ }
+ break;
+ case '/':
+ // Avoid "*/".
+ if (prev == '*') {
+ result.append("&#47;");
+ } else {
+ result.push_back(c);
+ }
+ break;
+ case '@':
+ // '@' starts javadoc tags including the @deprecated tag, which will
+ // cause a compile-time error if inserted before a declaration that
+ // does not have a corresponding @Deprecated annotation.
+ result.append("&#64;");
+ break;
+ case '<':
+ // Avoid interpretation as HTML.
+ result.append("&lt;");
+ break;
+ case '>':
+ // Avoid interpretation as HTML.
+ result.append("&gt;");
+ break;
+ case '&':
+ // Avoid interpretation as HTML.
+ result.append("&amp;");
+ break;
+ case '\\':
+ // Java interprets Unicode escape sequences anywhere!
+ result.append("&#92;");
+ break;
+ default:
+ result.push_back(c);
+ break;
+ }
+
+ prev = c;
+ }
+
+ return result;
+}
+
+static void WriteDocCommentBodyForLocation(
+ io::Printer* printer, const SourceLocation& location) {
+ string comments = location.leading_comments.empty() ?
+ location.trailing_comments : location.leading_comments;
+ if (!comments.empty()) {
+ // TODO(kenton): Ideally we should parse the comment text as Markdown and
+ // write it back as HTML, but this requires a Markdown parser. For now
+ // we just use <pre> to get fixed-width text formatting.
+
+ // If the comment itself contains block comment start or end markers,
+ // HTML-escape them so that they don't accidentally close the doc comment.
+ comments = EscapeJavadoc(comments);
+
+ vector<string> lines = Split(comments, "\n");
+ while (!lines.empty() && lines.back().empty()) {
+ lines.pop_back();
+ }
+
+ printer->Print(" * <pre>\n");
+ for (int i = 0; i < lines.size(); i++) {
+ // Most lines should start with a space. Watch out for lines that start
+ // with a /, since putting that right after the leading asterisk will
+ // close the comment.
+ if (!lines[i].empty() && lines[i][0] == '/') {
+ printer->Print(" * $line$\n", "line", lines[i]);
+ } else {
+ printer->Print(" *$line$\n", "line", lines[i]);
+ }
+ }
+ printer->Print(
+ " * </pre>\n"
+ " *\n");
+ }
+}
+
+template <typename DescriptorType>
+static void WriteDocCommentBody(
+ io::Printer* printer, const DescriptorType* descriptor) {
+ SourceLocation location;
+ if (descriptor->GetSourceLocation(&location)) {
+ WriteDocCommentBodyForLocation(printer, location);
+ }
+}
+
+static string FirstLineOf(const string& value) {
+ string result = value;
+
+ string::size_type pos = result.find_first_of('\n');
+ if (pos != string::npos) {
+ result.erase(pos);
+ }
+
+ // If line ends in an opening brace, make it "{ ... }" so it looks nice.
+ if (!result.empty() && result[result.size() - 1] == '{') {
+ result.append(" ... }");
+ }
+
+ return result;
+}
+
+void WriteMessageDocComment(io::Printer* printer, const Descriptor* message) {
+ printer->Print("/**\n");
+ WriteDocCommentBody(printer, message);
+ printer->Print(
+ " * Protobuf type {@code $fullname$}\n"
+ " */\n",
+ "fullname", EscapeJavadoc(message->full_name()));
+}
+
+void WriteFieldDocComment(io::Printer* printer, const FieldDescriptor* field) {
+ // In theory we should have slightly different comments for setters, getters,
+ // etc., but in practice everyone already knows the difference between these
+ // so it's redundant information.
+
+ // We start the comment with the main body based on the comments from the
+ // .proto file (if present). We then end with the field declaration, e.g.:
+ // optional string foo = 5;
+ // If the field is a group, the debug string might end with {.
+ printer->Print("/**\n");
+ WriteDocCommentBody(printer, field);
+ printer->Print(
+ " * <code>$def$</code>\n",
+ "def", EscapeJavadoc(FirstLineOf(field->DebugString())));
+ printer->Print(" */\n");
+}
+
+void WriteEnumDocComment(io::Printer* printer, const EnumDescriptor* enum_) {
+ printer->Print("/**\n");
+ WriteDocCommentBody(printer, enum_);
+ printer->Print(
+ " * Protobuf enum {@code $fullname$}\n"
+ " */\n",
+ "fullname", EscapeJavadoc(enum_->full_name()));
+}
+
+void WriteEnumValueDocComment(io::Printer* printer,
+ const EnumValueDescriptor* value) {
+ printer->Print("/**\n");
+ WriteDocCommentBody(printer, value);
+ printer->Print(
+ " * <code>$def$</code>\n"
+ " */\n",
+ "def", EscapeJavadoc(FirstLineOf(value->DebugString())));
+}
+
+void WriteServiceDocComment(io::Printer* printer,
+ const ServiceDescriptor* service) {
+ printer->Print("/**\n");
+ WriteDocCommentBody(printer, service);
+ printer->Print(
+ " * Protobuf service {@code $fullname$}\n"
+ " */\n",
+ "fullname", EscapeJavadoc(service->full_name()));
+}
+
+void WriteMethodDocComment(io::Printer* printer,
+ const MethodDescriptor* method) {
+ printer->Print("/**\n");
+ WriteDocCommentBody(printer, method);
+ printer->Print(
+ " * <code>$def$</code>\n"
+ " */\n",
+ "def", EscapeJavadoc(FirstLineOf(method->DebugString())));
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.h
new file mode 100644
index 0000000000..7d9535c959
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment.h
@@ -0,0 +1,69 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_DOC_COMMENT_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_DOC_COMMENT_H__
+
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+void WriteMessageDocComment(io::Printer* printer, const Descriptor* message);
+void WriteFieldDocComment(io::Printer* printer, const FieldDescriptor* field);
+void WriteEnumDocComment(io::Printer* printer, const EnumDescriptor* enum_);
+void WriteEnumValueDocComment(io::Printer* printer,
+ const EnumValueDescriptor* value);
+void WriteServiceDocComment(io::Printer* printer,
+ const ServiceDescriptor* service);
+void WriteMethodDocComment(io::Printer* printer,
+ const MethodDescriptor* method);
+
+// Exposed for testing only.
+LIBPROTOC_EXPORT string EscapeJavadoc(const string& input);
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_DOC_COMMENT_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment_unittest.cc
new file mode 100644
index 0000000000..ae582ea649
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_doc_comment_unittest.cc
@@ -0,0 +1,67 @@
+// 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)
+
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+namespace {
+
+TEST(JavaDocCommentTest, Escaping) {
+ EXPECT_EQ("foo /&#42; bar *&#47; baz", EscapeJavadoc("foo /* bar */ baz"));
+ EXPECT_EQ("foo /&#42;&#47; baz", EscapeJavadoc("foo /*/ baz"));
+ EXPECT_EQ("{&#64;foo}", EscapeJavadoc("{@foo}"));
+ EXPECT_EQ("&lt;i&gt;&amp;&lt;/i&gt;", EscapeJavadoc("<i>&</i>"));
+ EXPECT_EQ("foo&#92;u1234bar", EscapeJavadoc("foo\\u1234bar"));
+ EXPECT_EQ("&#64;deprecated", EscapeJavadoc("@deprecated"));
+}
+
+// TODO(kenton): It's hard to write a robust test of the doc comments -- we
+// can only really compare the output against a golden value, which is a
+// fairly tedious and fragile testing strategy. If we want to go that route,
+// it probably makes sense to bite the bullet and write a test that compares
+// the whole generated output for unittest.proto against a golden value, with
+// a very simple script that can be run to regenerate it with the latest code.
+// This would mean that updates to the golden file would have to be included
+// in any change to the code generator, which would actually be fairly useful
+// as it allows the reviewer to see clearly how the generated code is
+// changing.
+
+} // namespace
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.cc
new file mode 100644
index 0000000000..b46cfe9cc6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.cc
@@ -0,0 +1,397 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_enum.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+bool EnumHasCustomOptions(const EnumDescriptor* descriptor) {
+ if (descriptor->options().unknown_fields().field_count() > 0) return true;
+ for (int i = 0; i < descriptor->value_count(); ++i) {
+ const EnumValueDescriptor* value = descriptor->value(i);
+ if (value->options().unknown_fields().field_count() > 0) return true;
+ }
+ return false;
+}
+} // namespace
+
+EnumGenerator::EnumGenerator(const EnumDescriptor* descriptor,
+ bool immutable_api,
+ Context* context)
+ : descriptor_(descriptor), immutable_api_(immutable_api),
+ context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ const EnumValueDescriptor* value = descriptor_->value(i);
+ const EnumValueDescriptor* canonical_value =
+ descriptor_->FindValueByNumber(value->number());
+
+ if (value == canonical_value) {
+ canonical_values_.push_back(value);
+ } else {
+ Alias alias;
+ alias.value = value;
+ alias.canonical_value = canonical_value;
+ aliases_.push_back(alias);
+ }
+ }
+}
+
+EnumGenerator::~EnumGenerator() {}
+
+void EnumGenerator::Generate(io::Printer* printer) {
+ WriteEnumDocComment(printer, descriptor_);
+ MaybePrintGeneratedAnnotation(context_, printer, descriptor_, immutable_api_);
+ printer->Print(
+ "public enum $classname$\n"
+ " implements com.google.protobuf.ProtocolMessageEnum {\n",
+ "classname", descriptor_->name());
+ printer->Annotate("classname", descriptor_);
+ printer->Indent();
+
+ bool ordinal_is_index = true;
+ string index_text = "ordinal()";
+ for (int i = 0; i < canonical_values_.size(); i++) {
+ if (canonical_values_[i]->index() != i) {
+ ordinal_is_index = false;
+ index_text = "index";
+ break;
+ }
+ }
+
+ for (int i = 0; i < canonical_values_.size(); i++) {
+ map<string, string> vars;
+ vars["name"] = canonical_values_[i]->name();
+ vars["index"] = SimpleItoa(canonical_values_[i]->index());
+ vars["number"] = SimpleItoa(canonical_values_[i]->number());
+ WriteEnumValueDocComment(printer, canonical_values_[i]);
+ if (canonical_values_[i]->options().deprecated()) {
+ printer->Print("@java.lang.Deprecated\n");
+ }
+ if (ordinal_is_index) {
+ printer->Print(vars,
+ "$name$($number$),\n");
+ } else {
+ printer->Print(vars,
+ "$name$($index$, $number$),\n");
+ }
+ }
+
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ if (ordinal_is_index) {
+ printer->Print("UNRECOGNIZED(-1),\n");
+ } else {
+ printer->Print("UNRECOGNIZED(-1, -1),\n");
+ }
+ }
+
+ printer->Print(
+ ";\n"
+ "\n");
+
+ // -----------------------------------------------------------------
+
+ for (int i = 0; i < aliases_.size(); i++) {
+ map<string, string> vars;
+ vars["classname"] = descriptor_->name();
+ vars["name"] = aliases_[i].value->name();
+ vars["canonical_name"] = aliases_[i].canonical_value->name();
+ WriteEnumValueDocComment(printer, aliases_[i].value);
+ printer->Print(vars,
+ "public static final $classname$ $name$ = $canonical_name$;\n");
+ }
+
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ map<string, string> vars;
+ vars["name"] = descriptor_->value(i)->name();
+ vars["number"] = SimpleItoa(descriptor_->value(i)->number());
+ WriteEnumValueDocComment(printer, descriptor_->value(i));
+ printer->Print(vars,
+ "public static final int $name$_VALUE = $number$;\n");
+ }
+ printer->Print("\n");
+
+ // -----------------------------------------------------------------
+
+ printer->Print(
+ "\n"
+ "public final int getNumber() {\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ if (ordinal_is_index) {
+ printer->Print(
+ " if (this == UNRECOGNIZED) {\n"
+ " throw new java.lang.IllegalArgumentException(\n"
+ " \"Can't get the number of an unknown enum value.\");\n"
+ " }\n");
+ } else {
+ printer->Print(
+ " if (index == -1) {\n"
+ " throw new java.lang.IllegalArgumentException(\n"
+ " \"Can't get the number of an unknown enum value.\");\n"
+ " }\n");
+ }
+ }
+ printer->Print(
+ " return value;\n"
+ "}\n"
+ "\n"
+ "/**\n"
+ " * @deprecated Use {@link #forNumber(int)} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public static $classname$ valueOf(int value) {\n"
+ " return forNumber(value);\n"
+ "}\n"
+ "\n"
+ "public static $classname$ forNumber(int value) {\n"
+ " switch (value) {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+ printer->Indent();
+
+ for (int i = 0; i < canonical_values_.size(); i++) {
+ printer->Print(
+ "case $number$: return $name$;\n",
+ "name", canonical_values_[i]->name(),
+ "number", SimpleItoa(canonical_values_[i]->number()));
+ }
+
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " default: return null;\n"
+ " }\n"
+ "}\n"
+ "\n"
+ "public static com.google.protobuf.Internal.EnumLiteMap<$classname$>\n"
+ " internalGetValueMap() {\n"
+ " return internalValueMap;\n"
+ "}\n"
+ "private static final com.google.protobuf.Internal.EnumLiteMap<\n"
+ " $classname$> internalValueMap =\n"
+ " new com.google.protobuf.Internal.EnumLiteMap<$classname$>() {\n"
+ " public $classname$ findValueByNumber(int number) {\n"
+ " return $classname$.forNumber(number);\n"
+ " }\n"
+ " };\n"
+ "\n",
+ "classname", descriptor_->name());
+
+ // -----------------------------------------------------------------
+ // Reflection
+
+ if (HasDescriptorMethods(descriptor_, context_->EnforceLite())) {
+ printer->Print(
+ "public final com.google.protobuf.Descriptors.EnumValueDescriptor\n"
+ " getValueDescriptor() {\n"
+ " return getDescriptor().getValues().get($index_text$);\n"
+ "}\n"
+ "public final com.google.protobuf.Descriptors.EnumDescriptor\n"
+ " getDescriptorForType() {\n"
+ " return getDescriptor();\n"
+ "}\n"
+ "public static final com.google.protobuf.Descriptors.EnumDescriptor\n"
+ " getDescriptor() {\n",
+ "index_text", index_text);
+
+ // TODO(kenton): Cache statically? Note that we can't access descriptors
+ // at module init time because it wouldn't work with descriptor.proto, but
+ // we can cache the value the first time getDescriptor() is called.
+ if (descriptor_->containing_type() == NULL) {
+ if (!MultipleJavaFiles(descriptor_->file(), immutable_api_)) {
+ printer->Print(
+ " return $file$.getDescriptor().getEnumTypes().get($index$);\n",
+ "file", name_resolver_->GetClassName(descriptor_->file(),
+ immutable_api_),
+ "index", SimpleItoa(descriptor_->index()));
+ } else {
+ printer->Indent();
+ if (EnumHasCustomOptions(descriptor_)) {
+ // We need to load the immutable classes in order to parse custom
+ // options. However, since file level enums (no outer class) are
+ // shared by immutable code and mutable code, the immutable classes
+ // may not exist. So we try to use Java reflection to retrieve the
+ // descriptor from immutable classes.
+ printer->Print(
+ "try {\n"
+ " java.lang.Class immutableFileClass =\n"
+ " java.lang.Class.forName(\"$immutable_file_class_name$\");\n"
+ " @java.lang.SuppressWarnings(\"unchecked\")\n"
+ " java.lang.reflect.Method m =\n"
+ " immutableFileClass.getMethod(\"getDescriptor\");\n"
+ " com.google.protobuf.Descriptors.FileDescriptor file =\n"
+ " (com.google.protobuf.Descriptors.FileDescriptor)\n"
+ " m.invoke(immutableFileClass);\n"
+ " return file.getEnumTypes().get($index$);\n"
+ "} catch (java.lang.Exception e) {\n"
+ // Immutable classes cannot be found. Proceed as if custom options
+ // don't exist.
+ "}\n",
+ "immutable_file_class_name",
+ name_resolver_->GetImmutableClassName(descriptor_->file()),
+ "index", SimpleItoa(descriptor_->index()));
+ }
+ printer->Print(
+ "return $immutable_package$.$descriptor_class$.$descriptor$\n"
+ " .getEnumTypes().get($index$);\n",
+ "immutable_package", FileJavaPackage(descriptor_->file(), true),
+ "descriptor_class",
+ name_resolver_->GetDescriptorClassName(descriptor_->file()),
+ "descriptor", "getDescriptor()",
+ "index", SimpleItoa(descriptor_->index()));
+ printer->Outdent();
+ }
+ } else {
+ printer->Print(
+ " return $parent$.$descriptor$.getEnumTypes().get($index$);\n",
+ "parent", name_resolver_->GetClassName(descriptor_->containing_type(),
+ immutable_api_),
+ "descriptor", descriptor_->containing_type()->options()
+ .no_standard_descriptor_accessor()
+ ? "getDefaultInstance().getDescriptorForType()"
+ : "getDescriptor()",
+ "index", SimpleItoa(descriptor_->index()));
+ }
+
+ printer->Print(
+ "}\n"
+ "\n"
+ "private static final $classname$[] VALUES = ",
+ "classname", descriptor_->name());
+
+ if (CanUseEnumValues()) {
+ // If the constants we are going to output are exactly the ones we
+ // have declared in the Java enum in the same order, then we can use
+ // the values() method that the Java compiler automatically generates
+ // for every enum.
+ printer->Print("values();\n");
+ } else {
+ printer->Print(
+ "{\n"
+ " ");
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ printer->Print("$name$, ",
+ "name", descriptor_->value(i)->name());
+ }
+ printer->Print(
+ "\n"
+ "};\n");
+ }
+
+ printer->Print(
+ "\n"
+ "public static $classname$ valueOf(\n"
+ " com.google.protobuf.Descriptors.EnumValueDescriptor desc) {\n"
+ " if (desc.getType() != getDescriptor()) {\n"
+ " throw new java.lang.IllegalArgumentException(\n"
+ " \"EnumValueDescriptor is not for this type.\");\n"
+ " }\n",
+ "classname", descriptor_->name());
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(
+ " if (desc.getIndex() == -1) {\n"
+ " return UNRECOGNIZED;\n"
+ " }\n");
+ }
+ printer->Print(
+ " return VALUES[desc.getIndex()];\n"
+ "}\n"
+ "\n");
+
+ if (!ordinal_is_index) {
+ printer->Print("private final int index;\n");
+ }
+ }
+
+ // -----------------------------------------------------------------
+
+ printer->Print(
+ "private final int value;\n\n");
+
+ if (ordinal_is_index) {
+ printer->Print(
+ "private $classname$(int value) {\n",
+ "classname", descriptor_->name());
+ } else {
+ printer->Print(
+ "private $classname$(int index, int value) {\n",
+ "classname", descriptor_->name());
+ }
+ if (HasDescriptorMethods(descriptor_, context_->EnforceLite()) &&
+ !ordinal_is_index) {
+ printer->Print(" this.index = index;\n");
+ }
+ printer->Print(
+ " this.value = value;\n"
+ "}\n");
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(enum_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+bool EnumGenerator::CanUseEnumValues() {
+ if (canonical_values_.size() != descriptor_->value_count()) {
+ return false;
+ }
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ if (descriptor_->value(i)->name() != canonical_values_[i]->name()) {
+ return false;
+ }
+ }
+ return true;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.h
new file mode 100644
index 0000000000..c33e713df1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum.h
@@ -0,0 +1,98 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_H__
+
+#include <string>
+#include <vector>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class EnumGenerator {
+ public:
+ EnumGenerator(const EnumDescriptor* descriptor, bool immutable_api,
+ Context* context);
+ ~EnumGenerator();
+
+ void Generate(io::Printer* printer);
+
+ private:
+ const EnumDescriptor* descriptor_;
+
+ // The proto language allows multiple enum constants to have the same numeric
+ // value. Java, however, does not allow multiple enum constants to be
+ // considered equivalent. We treat the first defined constant for any
+ // given numeric value as "canonical" and the rest as aliases of that
+ // canonical value.
+ vector<const EnumValueDescriptor*> canonical_values_;
+
+ struct Alias {
+ const EnumValueDescriptor* value;
+ const EnumValueDescriptor* canonical_value;
+ };
+ vector<Alias> aliases_;
+
+ bool immutable_api_;
+
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ bool CanUseEnumValues();
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.cc
new file mode 100644
index 0000000000..2e916c5679
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.cc
@@ -0,0 +1,969 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_enum_field.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+void SetEnumVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ (*variables)["type"] =
+ name_resolver->GetImmutableClassName(descriptor->enum_type());
+ (*variables)["mutable_type"] =
+ name_resolver->GetMutableClassName(descriptor->enum_type());
+ (*variables)["default"] = ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["default_number"] = SimpleItoa(
+ descriptor->default_value_enum()->number());
+ (*variables)["tag"] = SimpleItoa(internal::WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ internal::WireFormat::TagSize(descriptor->number(), GetType(descriptor)));
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+ (*variables)["on_changed"] = "onChanged();";
+ // Use deprecated valueOf() method to be compatible with old generated code
+ // for v2.5.0/v2.6.1.
+ // TODO(xiaofeng): Use "forNumber" when we no longer support compatibility
+ // with v2.5.0/v2.6.1.
+ (*variables)["for_number"] = "valueOf";
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+ (*variables)["get_has_field_bit_builder"] = GenerateGetBit(builderBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["set_has_field_bit_builder"] =
+ GenerateSetBit(builderBitIndex) + ";";
+ (*variables)["clear_has_field_bit_builder"] =
+ GenerateClearBit(builderBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["set_has_field_bit_builder"] = "";
+ (*variables)["clear_has_field_bit_builder"] = "";
+
+ (*variables)["is_field_present_message"] =
+ (*variables)["name"] + "_ != " +
+ (*variables)["default"] + ".getNumber()";
+ }
+
+ // For repated builders, one bit is used for whether the array is immutable.
+ (*variables)["get_mutable_bit_builder"] = GenerateGetBit(builderBitIndex);
+ (*variables)["set_mutable_bit_builder"] = GenerateSetBit(builderBitIndex);
+ (*variables)["clear_mutable_bit_builder"] = GenerateClearBit(builderBitIndex);
+
+ // For repeated fields, one bit is used for whether the array is immutable
+ // in the parsing constructor.
+ (*variables)["get_mutable_bit_parser"] =
+ GenerateGetBitMutableLocal(builderBitIndex);
+ (*variables)["set_mutable_bit_parser"] =
+ GenerateSetBitMutableLocal(builderBitIndex);
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+
+ if (SupportUnknownEnumValue(descriptor->file())) {
+ (*variables)["unknown"] = (*variables)["type"] + ".UNRECOGNIZED";
+ } else {
+ (*variables)["unknown"] = (*variables)["default"];
+ }
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutableEnumFieldGenerator::
+ImmutableEnumFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex),
+ name_resolver_(context->GetNameResolver()) {
+ SetEnumVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutableEnumFieldGenerator::~ImmutableEnumFieldGenerator() {}
+
+int ImmutableEnumFieldGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutableEnumFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Value();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$();\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private int $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " return $name$_;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " $type$ result = $type$.$for_number$($name$_);\n"
+ " return result == null ? $unknown$ : result;\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private int $name$_ = $default_number$;\n");
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_builder$;\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " return $name$_;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Value(int value) {\n"
+ " $name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " $type$ result = $type$.$for_number$($name$_);\n"
+ " return result == null ? $unknown$ : result;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " $set_has_field_bit_builder$\n"
+ " $name$_ = value.getNumber();\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " $clear_has_field_bit_builder$\n"
+ " $name$_ = $default_number$;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for enums
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default_number$;\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = $default_number$;\n"
+ "$clear_has_field_bit_builder$\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "if (other.has$capitalized_name$()) {\n"
+ " set$capitalized_name$(other.get$capitalized_name$());\n"
+ "}\n");
+ } else if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "if (other.$name$_ != $default_number$) {\n"
+ " set$capitalized_name$Value(other.get$capitalized_name$Value());\n"
+ "}\n");
+ } else {
+ GOOGLE_LOG(FATAL) << "Can't reach here.";
+ }
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "if ($get_has_field_bit_from_local$) {\n"
+ " $set_has_field_bit_to_local$;\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "result.$name$_ = $name$_;\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$set_has_field_bit_message$\n"
+ "$name$_ = rawValue;\n");
+ } else {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$type$ value = $type$.$for_number$(rawValue);\n"
+ "if (value == null) {\n");
+ if (PreserveUnknownFields(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ " unknownFields.mergeVarintField($number$, rawValue);\n");
+ }
+ printer->Print(variables_,
+ "} else {\n"
+ " $set_has_field_bit_message$\n"
+ " $name$_ = rawValue;\n"
+ "}\n");
+ }
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for enums
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " output.writeEnum($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeEnumSize($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && $name$_ == other.$name$_;\n");
+}
+
+void ImmutableEnumFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + $name$_;\n");
+}
+
+string ImmutableEnumFieldGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->enum_type());
+}
+
+// ===================================================================
+
+ImmutableEnumOneofFieldGenerator::
+ImmutableEnumOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableEnumFieldGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutableEnumOneofFieldGenerator::
+~ImmutableEnumOneofFieldGenerator() {}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return (java.lang.Integer) $oneof_name$_;\n"
+ " }\n"
+ " return $default_number$;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $type$ result = $type$.$for_number$(\n"
+ " (java.lang.Integer) $oneof_name$_);\n"
+ " return result == null ? $unknown$ : result;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ((java.lang.Integer) $oneof_name$_).intValue();\n"
+ " }\n"
+ " return $default_number$;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Value(int value) {\n"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $type$ result = $type$.$for_number$(\n"
+ " (java.lang.Integer) $oneof_name$_);\n"
+ " return result == null ? $unknown$ : result;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value.getNumber();\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " $on_changed$\n"
+ " }\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " result.$oneof_name$_ = $oneof_name$_;\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "set$capitalized_name$Value(other.get$capitalized_name$Value());\n");
+ } else {
+ printer->Print(variables_,
+ "set$capitalized_name$(other.get$capitalized_name$());\n");
+ }
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = rawValue;\n");
+ } else {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$type$ value = $type$.$for_number$(rawValue);\n"
+ "if (value == null) {\n");
+ if (PreserveUnknownFields(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ " unknownFields.mergeVarintField($number$, rawValue);\n");
+ }
+ printer->Print(variables_,
+ "} else {\n"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = rawValue;\n"
+ "}\n");
+ }
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.writeEnum($number$, ((java.lang.Integer) $oneof_name$_));\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeEnumSize($number$, ((java.lang.Integer) $oneof_name$_));\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$Value()\n"
+ " == other.get$capitalized_name$Value();\n");
+ } else {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+ }
+}
+
+void ImmutableEnumOneofFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + get$capitalized_name$Value();\n");
+ } else {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + get$capitalized_name$().getNumber();\n");
+ }
+}
+
+// ===================================================================
+
+RepeatedImmutableEnumFieldGenerator::
+RepeatedImmutableEnumFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetEnumVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutableEnumFieldGenerator::~RepeatedImmutableEnumFieldGenerator() {}
+
+int RepeatedImmutableEnumFieldGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutableEnumFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<$type$> get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$(int index);\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<java.lang.Integer>\n"
+ "get$capitalized_name$ValueList();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Value(int index);\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private java.util.List<java.lang.Integer> $name$_;\n"
+ "private static final com.google.protobuf.Internal.ListAdapter.Converter<\n"
+ " java.lang.Integer, $type$> $name$_converter_ =\n"
+ " new com.google.protobuf.Internal.ListAdapter.Converter<\n"
+ " java.lang.Integer, $type$>() {\n"
+ " public $type$ convert(java.lang.Integer from) {\n"
+ " $type$ result = $type$.$for_number$(from);\n"
+ " return result == null ? $unknown$ : result;\n"
+ " }\n"
+ " };\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return new com.google.protobuf.Internal.ListAdapter<\n"
+ " java.lang.Integer, $type$>($name$_, $name$_converter_);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $name$_converter_.convert($name$_.get(index));\n"
+ "}\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<java.lang.Integer>\n"
+ "get$capitalized_name$ValueList() {\n"
+ " return $name$_;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ }
+
+ if (descriptor_->is_packed() &&
+ context_->HasGeneratedMethods(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ "private int $name$MemoizedSerializedSize;\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ // One field is the list and the other field keeps track of whether the
+ // list is immutable. If it's immutable, the invariant is that it must
+ // either an instance of Collections.emptyList() or it's an ArrayList
+ // wrapped in a Collections.unmodifiableList() wrapper and nobody else has
+ // a refererence to the underlying ArrayList. This invariant allows us to
+ // share instances of lists between protocol buffers avoiding expensive
+ // memory allocations. Note, immutable is a strong guarantee here -- not
+ // just that the list cannot be modified via the reference but that the
+ // list can never be modified.
+ "private java.util.List<java.lang.Integer> $name$_ =\n"
+ " java.util.Collections.emptyList();\n"
+
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$get_mutable_bit_builder$) {\n"
+ " $name$_ = new java.util.ArrayList<java.lang.Integer>($name$_);\n"
+ " $set_mutable_bit_builder$;\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ // Note: We return an unmodifiable list because otherwise the caller
+ // could hold on to the returned list and modify it after the message
+ // has been built, thus mutating the message which is supposed to be
+ // immutable.
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return new com.google.protobuf.Internal.ListAdapter<\n"
+ " java.lang.Integer, $type$>($name$_, $name$_converter_);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $name$_converter_.convert($name$_.get(index));\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, value.getNumber());\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value.getNumber());\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " for ($type$ value : values) {\n"
+ " $name$_.add(value.getNumber());\n"
+ " }\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " $name$_ = java.util.Collections.emptyList();\n"
+ " $clear_mutable_bit_builder$;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<java.lang.Integer>\n"
+ "get$capitalized_name$ValueList() {\n"
+ " return java.util.Collections.unmodifiableList($name$_);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Value(\n"
+ " int index, int value) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, value);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$Value(int value) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$Value(\n"
+ " java.lang.Iterable<java.lang.Integer> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " for (int value : values) {\n"
+ " $name$_.add(value);\n"
+ " }\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for enums
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = java.util.Collections.emptyList();\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = java.util.Collections.emptyList();\n"
+ "$clear_mutable_bit_builder$;\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // The code below does two optimizations:
+ // 1. If the other list is empty, there's nothing to do. This ensures we
+ // don't allocate a new array if we already have an immutable one.
+ // 2. If the other list is non-empty and our current list is empty, we can
+ // reuse the other list which is guaranteed to be immutable.
+ printer->Print(variables_,
+ "if (!other.$name$_.isEmpty()) {\n"
+ " if ($name$_.isEmpty()) {\n"
+ " $name$_ = other.$name$_;\n"
+ " $clear_mutable_bit_builder$;\n"
+ " } else {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.addAll(other.$name$_);\n"
+ " }\n"
+ " $on_changed$\n"
+ "}\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ // The code below ensures that the result has an immutable list. If our
+ // list is immutable, we can just reuse it. If not, we make it immutable.
+ printer->Print(variables_,
+ "if ($get_mutable_bit_builder$) {\n"
+ " $name$_ = java.util.Collections.unmodifiableList($name$_);\n"
+ " $clear_mutable_bit_builder$;\n"
+ "}\n"
+ "result.$name$_ = $name$_;\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ // Read and store the enum
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "if (!$get_mutable_bit_parser$) {\n"
+ " $name$_ = new java.util.ArrayList<java.lang.Integer>();\n"
+ " $set_mutable_bit_parser$;\n"
+ "}\n"
+ "$name$_.add(rawValue);\n");
+ } else {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$type$ value = $type$.$for_number$(rawValue);\n"
+ "if (value == null) {\n");
+ if (PreserveUnknownFields(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ " unknownFields.mergeVarintField($number$, rawValue);\n");
+ }
+ printer->Print(variables_,
+ "} else {\n"
+ " if (!$get_mutable_bit_parser$) {\n"
+ " $name$_ = new java.util.ArrayList<java.lang.Integer>();\n"
+ " $set_mutable_bit_parser$;\n"
+ " }\n"
+ " $name$_.add(rawValue);\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateParsingCodeFromPacked(io::Printer* printer) const {
+ // Wrap GenerateParsingCode's contents with a while loop.
+
+ printer->Print(variables_,
+ "int length = input.readRawVarint32();\n"
+ "int oldLimit = input.pushLimit(length);\n"
+ "while(input.getBytesUntilLimit() > 0) {\n");
+ printer->Indent();
+
+ GenerateParsingCode(printer);
+
+ printer->Outdent();
+ printer->Print(variables_,
+ "}\n"
+ "input.popLimit(oldLimit);\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_mutable_bit_parser$) {\n"
+ " $name$_ = java.util.Collections.unmodifiableList($name$_);\n"
+ "}\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ "if (get$capitalized_name$List().size() > 0) {\n"
+ " output.writeUInt32NoTag($tag$);\n"
+ " output.writeUInt32NoTag($name$MemoizedSerializedSize);\n"
+ "}\n"
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.writeEnumNoTag($name$_.get(i));\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.writeEnum($number$, $name$_.get(i));\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "{\n"
+ " int dataSize = 0;\n");
+ printer->Indent();
+
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " dataSize += com.google.protobuf.CodedOutputStream\n"
+ " .computeEnumSizeNoTag($name$_.get(i));\n"
+ "}\n");
+ printer->Print(
+ "size += dataSize;\n");
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ "if (!get$capitalized_name$List().isEmpty()) {"
+ " size += $tag_size$;\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeUInt32SizeNoTag(dataSize);\n"
+ "}");
+ } else {
+ printer->Print(variables_,
+ "size += $tag_size$ * $name$_.size();\n");
+ }
+
+ // cache the data size for packed fields.
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ "$name$MemoizedSerializedSize = dataSize;\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && $name$_.equals(other.$name$_);\n");
+}
+
+void RepeatedImmutableEnumFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + $name$_.hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutableEnumFieldGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->enum_type());
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.h
new file mode 100644
index 0000000000..b8ff734373
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field.h
@@ -0,0 +1,160 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableEnumFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit ImmutableEnumFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableEnumFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableEnumFieldGenerator);
+};
+
+class ImmutableEnumOneofFieldGenerator : public ImmutableEnumFieldGenerator {
+ public:
+ ImmutableEnumOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableEnumOneofFieldGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableEnumOneofFieldGenerator);
+};
+
+class RepeatedImmutableEnumFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit RepeatedImmutableEnumFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableEnumFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingCodeFromPacked(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableEnumFieldGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.cc
new file mode 100644
index 0000000000..aa0eb5e829
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.cc
@@ -0,0 +1,962 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_enum_field_lite.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+void SetEnumVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ (*variables)["type"] =
+ name_resolver->GetImmutableClassName(descriptor->enum_type());
+ (*variables)["mutable_type"] =
+ name_resolver->GetMutableClassName(descriptor->enum_type());
+ (*variables)["default"] = ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["default_number"] = SimpleItoa(
+ descriptor->default_value_enum()->number());
+ (*variables)["tag"] = SimpleItoa(internal::WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ internal::WireFormat::TagSize(descriptor->number(), GetType(descriptor)));
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["clear_has_field_bit_message"] =
+ GenerateClearBit(messageBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["clear_has_field_bit_message"] = "";
+
+ (*variables)["is_field_present_message"] =
+ (*variables)["name"] + "_ != " +
+ (*variables)["default"] + ".getNumber()";
+ }
+
+ // For repeated builders, the underlying list tracks mutability state.
+ (*variables)["is_mutable"] = (*variables)["name"] + "_.isModifiable()";
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+
+ if (SupportUnknownEnumValue(descriptor->file())) {
+ (*variables)["unknown"] = (*variables)["type"] + ".UNRECOGNIZED";
+ } else {
+ (*variables)["unknown"] = (*variables)["default"];
+ }
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutableEnumFieldLiteGenerator::
+ImmutableEnumFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex),
+ name_resolver_(context->GetNameResolver()) {
+ SetEnumVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutableEnumFieldLiteGenerator::~ImmutableEnumFieldLiteGenerator() {}
+
+int ImmutableEnumFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutableEnumFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Value();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$();\n");
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private int $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " return $name$_;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " $type$ result = $type$.forNumber($name$_);\n"
+ " return result == null ? $unknown$ : result;\n"
+ "}\n");
+
+ // Generate private setters for the builder to proxy into.
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$Value(int value) {\n"
+ " $set_has_field_bit_message$"
+ " $name$_ = value;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " $set_has_field_bit_message$\n"
+ " $name$_ = value.getNumber();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $clear_has_field_bit_message$\n"
+ " $name$_ = $default_number$;\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " return instance.get$capitalized_name$Value();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Value(int value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$Value(value);\n"
+ " return this;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for enums
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ if (!IsDefaultValueJavaDefault(descriptor_)) {
+ printer->Print(variables_, "$name$_ = $default_number$;\n");
+ }
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "$name$_ = visitor.visitInt(has$capitalized_name$(), $name$_,\n"
+ " other.has$capitalized_name$(), other.$name$_);\n");
+ } else if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "$name$_ = visitor.visitInt($name$_ != $default_number$, $name$_,"
+ " other.$name$_ != $default_number$, other.$name$_);\n");
+ } else {
+ GOOGLE_LOG(FATAL) << "Can't reach here.";
+ }
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ // noop for scalars
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$set_has_field_bit_message$\n"
+ "$name$_ = rawValue;\n");
+ } else {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$type$ value = $type$.forNumber(rawValue);\n"
+ "if (value == null) {\n");
+ if (PreserveUnknownFields(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ " super.mergeVarintField($number$, rawValue);\n");
+ }
+ printer->Print(variables_,
+ "} else {\n"
+ " $set_has_field_bit_message$\n"
+ " $name$_ = rawValue;\n"
+ "}\n");
+ }
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for enums
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " output.writeEnum($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeEnumSize($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && $name$_ == other.$name$_;\n");
+}
+
+void ImmutableEnumFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + $name$_;\n");
+}
+
+string ImmutableEnumFieldLiteGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->enum_type());
+}
+
+// ===================================================================
+
+ImmutableEnumOneofFieldLiteGenerator::
+ImmutableEnumOneofFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableEnumFieldLiteGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutableEnumOneofFieldLiteGenerator::
+~ImmutableEnumOneofFieldLiteGenerator() {}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return (java.lang.Integer) $oneof_name$_;\n"
+ " }\n"
+ " return $default_number$;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $type$ result = $type$.forNumber((java.lang.Integer) $oneof_name$_);\n"
+ " return result == null ? $unknown$ : result;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n");
+
+ // Generate private setters for the builder to proxy into.
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$Value(int value) {\n"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value.getNumber();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " }\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+ }
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value() {\n"
+ " return instance.get$capitalized_name$Value();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Value(int value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$Value(value);\n"
+ " return this;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$oneof_name$_ = visitor.visitOneofInt(\n"
+ " $has_oneof_case_message$, $oneof_name$_, other.$oneof_name$_);\n");
+}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = rawValue;\n");
+ } else {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$type$ value = $type$.forNumber(rawValue);\n"
+ "if (value == null) {\n");
+ if (PreserveUnknownFields(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ " super.mergeVarintField($number$, rawValue);\n");
+ }
+ printer->Print(variables_,
+ "} else {\n"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = rawValue;\n"
+ "}\n");
+ }
+}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.writeEnum($number$, ((java.lang.Integer) $oneof_name$_));\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeEnumSize($number$, ((java.lang.Integer) $oneof_name$_));\n"
+ "}\n");
+}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$Value()\n"
+ " == other.get$capitalized_name$Value();\n");
+ } else {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+ }
+}
+
+void ImmutableEnumOneofFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + get$capitalized_name$Value();\n");
+ } else {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + get$capitalized_name$().getNumber();\n");
+ }
+}
+
+// ===================================================================
+
+RepeatedImmutableEnumFieldLiteGenerator::
+RepeatedImmutableEnumFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetEnumVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutableEnumFieldLiteGenerator::
+~RepeatedImmutableEnumFieldLiteGenerator() {}
+
+int RepeatedImmutableEnumFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutableEnumFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<$type$> get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$(int index);\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<java.lang.Integer>\n"
+ "get$capitalized_name$ValueList();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Value(int index);\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private com.google.protobuf.Internal.IntList $name$_;\n"
+ "private static final com.google.protobuf.Internal.ListAdapter.Converter<\n"
+ " java.lang.Integer, $type$> $name$_converter_ =\n"
+ " new com.google.protobuf.Internal.ListAdapter.Converter<\n"
+ " java.lang.Integer, $type$>() {\n"
+ " public $type$ convert(java.lang.Integer from) {\n"
+ " $type$ result = $type$.forNumber(from);\n"
+ " return result == null ? $unknown$ : result;\n"
+ " }\n"
+ " };\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return new com.google.protobuf.Internal.ListAdapter<\n"
+ " java.lang.Integer, $type$>($name$_, $name$_converter_);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $name$_converter_.convert($name$_.getInt(index));\n"
+ "}\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<java.lang.Integer>\n"
+ "get$capitalized_name$ValueList() {\n"
+ " return $name$_;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value(int index) {\n"
+ " return $name$_.getInt(index);\n"
+ "}\n");
+ }
+
+ if (descriptor_->options().packed() &&
+ context_->HasGeneratedMethods(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ "private int $name$MemoizedSerializedSize;\n");
+ }
+
+ // Generate private setters for the builder to proxy into.
+ printer->Print(variables_,
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ " }\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.setInt(index, value.getNumber());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.addInt(value.getNumber());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " for ($type$ value : values) {\n"
+ " $name$_.addInt(value.getNumber());\n"
+ " }\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $name$_ = emptyIntList();\n"
+ "}\n");
+
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$Value(\n"
+ " int index, int value) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.setInt(index, value);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$Value(int value) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.addInt(value);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void addAll$capitalized_name$Value(\n"
+ " java.lang.Iterable<java.lang.Integer> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " for (int value : values) {\n"
+ " $name$_.addInt(value);\n"
+ " }\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return instance.get$capitalized_name$List();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return instance.get$capitalized_name$Count();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return instance.get$capitalized_name$(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(index, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values) {\n"
+ " copyOnWrite();\n"
+ " instance.addAll$capitalized_name$(values);"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<java.lang.Integer>\n"
+ "get$capitalized_name$ValueList() {\n"
+ " return java.util.Collections.unmodifiableList(\n"
+ " instance.get$capitalized_name$ValueList());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Value(int index) {\n"
+ " return instance.get$capitalized_name$Value(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Value(\n"
+ " int index, int value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$Value(index, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$Value(int value) {\n"
+ " instance.add$capitalized_name$Value(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$Value(\n"
+ " java.lang.Iterable<java.lang.Integer> values) {\n"
+ " copyOnWrite();\n"
+ " instance.addAll$capitalized_name$Value(values);\n"
+ " return this;\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for enums
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = emptyIntList();\n");
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_= visitor.visitIntList($name$_, other.$name$_);\n");
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_.makeImmutable();\n");
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ // Read and store the enum
+ printer->Print(variables_,
+ "if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ "}\n");
+
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "$name$_.addInt(input.readEnum());\n");
+ } else {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$type$ value = $type$.forNumber(rawValue);\n"
+ "if (value == null) {\n"
+ // We store the unknown value in unknown fields.
+ " super.mergeVarintField($number$, rawValue);\n"
+ "} else {\n"
+ " $name$_.addInt(rawValue);\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateParsingCodeFromPacked(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "int length = input.readRawVarint32();\n"
+ "int oldLimit = input.pushLimit(length);\n"
+ "while(input.getBytesUntilLimit() > 0) {\n");
+ printer->Indent();
+
+ // Read and store the enum
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(variables_,
+ "$name$_.addInt(input.readEnum());\n");
+ } else {
+ printer->Print(variables_,
+ "int rawValue = input.readEnum();\n"
+ "$type$ value = $type$.forNumber(rawValue);\n"
+ "if (value == null) {\n"
+ // We store the unknown value in unknown fields.
+ " super.mergeVarintField($number$, rawValue);\n"
+ "} else {\n"
+ " $name$_.addInt(rawValue);\n"
+ "}\n");
+ }
+
+ printer->Outdent();
+ printer->Print(variables_,
+ "}\n"
+ "input.popLimit(oldLimit);\n");
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_mutable$) {\n"
+ " $name$_.makeImmutable();\n"
+ "}\n");
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ if (descriptor_->options().packed()) {
+ printer->Print(variables_,
+ "if (get$capitalized_name$List().size() > 0) {\n"
+ " output.writeUInt32NoTag($tag$);\n"
+ " output.writeUInt32NoTag($name$MemoizedSerializedSize);\n"
+ "}\n"
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.writeEnumNoTag($name$_.getInt(i));\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.writeEnum($number$, $name$_.getInt(i));\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "{\n"
+ " int dataSize = 0;\n");
+ printer->Indent();
+
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " dataSize += com.google.protobuf.CodedOutputStream\n"
+ " .computeEnumSizeNoTag($name$_.getInt(i));\n"
+ "}\n");
+ printer->Print(
+ "size += dataSize;\n");
+ if (descriptor_->options().packed()) {
+ printer->Print(variables_,
+ "if (!get$capitalized_name$List().isEmpty()) {"
+ " size += $tag_size$;\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeUInt32SizeNoTag(dataSize);\n"
+ "}");
+ } else {
+ printer->Print(variables_,
+ "size += $tag_size$ * $name$_.size();\n");
+ }
+
+ // cache the data size for packed fields.
+ if (descriptor_->options().packed()) {
+ printer->Print(variables_,
+ "$name$MemoizedSerializedSize = dataSize;\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && $name$_.equals(other.$name$_);\n");
+}
+
+void RepeatedImmutableEnumFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + $name$_.hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutableEnumFieldLiteGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->enum_type());
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.h
new file mode 100644
index 0000000000..9201b8d66a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_field_lite.h
@@ -0,0 +1,159 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_FIELD_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_FIELD_LITE_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableEnumFieldLiteGenerator : public ImmutableFieldLiteGenerator {
+ public:
+ explicit ImmutableEnumFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableEnumFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableEnumFieldLiteGenerator);
+};
+
+class ImmutableEnumOneofFieldLiteGenerator
+ : public ImmutableEnumFieldLiteGenerator {
+ public:
+ ImmutableEnumOneofFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableEnumOneofFieldLiteGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableEnumOneofFieldLiteGenerator);
+};
+
+class RepeatedImmutableEnumFieldLiteGenerator
+ : public ImmutableFieldLiteGenerator {
+ public:
+ explicit RepeatedImmutableEnumFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableEnumFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingCodeFromPacked(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableEnumFieldLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_FIELD_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.cc
new file mode 100644
index 0000000000..99f52d4012
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.cc
@@ -0,0 +1,221 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_enum_lite.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+bool EnumHasCustomOptions(const EnumDescriptor* descriptor) {
+ if (descriptor->options().unknown_fields().field_count() > 0) return true;
+ for (int i = 0; i < descriptor->value_count(); ++i) {
+ const EnumValueDescriptor* value = descriptor->value(i);
+ if (value->options().unknown_fields().field_count() > 0) return true;
+ }
+ return false;
+}
+} // namespace
+
+EnumLiteGenerator::EnumLiteGenerator(const EnumDescriptor* descriptor,
+ bool immutable_api, Context* context)
+ : descriptor_(descriptor),
+ immutable_api_(immutable_api),
+ context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ const EnumValueDescriptor* value = descriptor_->value(i);
+ const EnumValueDescriptor* canonical_value =
+ descriptor_->FindValueByNumber(value->number());
+
+ if (value == canonical_value) {
+ canonical_values_.push_back(value);
+ } else {
+ Alias alias;
+ alias.value = value;
+ alias.canonical_value = canonical_value;
+ aliases_.push_back(alias);
+ }
+ }
+}
+
+EnumLiteGenerator::~EnumLiteGenerator() {}
+
+void EnumLiteGenerator::Generate(io::Printer* printer) {
+ WriteEnumDocComment(printer, descriptor_);
+ MaybePrintGeneratedAnnotation(context_, printer, descriptor_, immutable_api_);
+ printer->Print(
+ "public enum $classname$\n"
+ " implements com.google.protobuf.Internal.EnumLite {\n",
+ "classname", descriptor_->name());
+ printer->Annotate("classname", descriptor_);
+ printer->Indent();
+
+ for (int i = 0; i < canonical_values_.size(); i++) {
+ map<string, string> vars;
+ vars["name"] = canonical_values_[i]->name();
+ vars["number"] = SimpleItoa(canonical_values_[i]->number());
+ WriteEnumValueDocComment(printer, canonical_values_[i]);
+ if (canonical_values_[i]->options().deprecated()) {
+ printer->Print("@java.lang.Deprecated\n");
+ }
+ printer->Print(vars,
+ "$name$($number$),\n");
+ }
+
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print("UNRECOGNIZED(-1),\n");
+ }
+
+ printer->Print(
+ ";\n"
+ "\n");
+
+ // -----------------------------------------------------------------
+
+ for (int i = 0; i < aliases_.size(); i++) {
+ map<string, string> vars;
+ vars["classname"] = descriptor_->name();
+ vars["name"] = aliases_[i].value->name();
+ vars["canonical_name"] = aliases_[i].canonical_value->name();
+ WriteEnumValueDocComment(printer, aliases_[i].value);
+ printer->Print(vars,
+ "public static final $classname$ $name$ = $canonical_name$;\n");
+ }
+
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ map<string, string> vars;
+ vars["name"] = descriptor_->value(i)->name();
+ vars["number"] = SimpleItoa(descriptor_->value(i)->number());
+ WriteEnumValueDocComment(printer, descriptor_->value(i));
+ printer->Print(vars,
+ "public static final int $name$_VALUE = $number$;\n");
+ }
+ printer->Print("\n");
+
+ // -----------------------------------------------------------------
+
+ printer->Print(
+ "\n"
+ "public final int getNumber() {\n"
+ " return value;\n"
+ "}\n"
+ "\n"
+ "/**\n"
+ " * @deprecated Use {@link #forNumber(int)} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public static $classname$ valueOf(int value) {\n"
+ " return forNumber(value);\n"
+ "}\n"
+ "\n"
+ "public static $classname$ forNumber(int value) {\n"
+ " switch (value) {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+ printer->Indent();
+
+ for (int i = 0; i < canonical_values_.size(); i++) {
+ printer->Print(
+ "case $number$: return $name$;\n",
+ "name", canonical_values_[i]->name(),
+ "number", SimpleItoa(canonical_values_[i]->number()));
+ }
+
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " default: return null;\n"
+ " }\n"
+ "}\n"
+ "\n"
+ "public static com.google.protobuf.Internal.EnumLiteMap<$classname$>\n"
+ " internalGetValueMap() {\n"
+ " return internalValueMap;\n"
+ "}\n"
+ "private static final com.google.protobuf.Internal.EnumLiteMap<\n"
+ " $classname$> internalValueMap =\n"
+ " new com.google.protobuf.Internal.EnumLiteMap<$classname$>() {\n"
+ " public $classname$ findValueByNumber(int number) {\n"
+ " return $classname$.forNumber(number);\n"
+ " }\n"
+ " };\n"
+ "\n",
+ "classname", descriptor_->name());
+
+ printer->Print(
+ "private final int value;\n\n"
+ "private $classname$(int value) {\n",
+ "classname", descriptor_->name());
+ printer->Print(
+ " this.value = value;\n"
+ "}\n");
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(enum_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+bool EnumLiteGenerator::CanUseEnumValues() {
+ if (canonical_values_.size() != descriptor_->value_count()) {
+ return false;
+ }
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ if (descriptor_->value(i)->name() != canonical_values_[i]->name()) {
+ return false;
+ }
+ }
+ return true;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.h
new file mode 100644
index 0000000000..f27cb76fb1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_enum_lite.h
@@ -0,0 +1,98 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_LITE_H__
+
+#include <string>
+#include <vector>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class EnumLiteGenerator {
+ public:
+ EnumLiteGenerator(const EnumDescriptor* descriptor, bool immutable_api,
+ Context* context);
+ ~EnumLiteGenerator();
+
+ void Generate(io::Printer* printer);
+
+ private:
+ const EnumDescriptor* descriptor_;
+
+ // The proto language allows multiple enum constants to have the same numeric
+ // value. Java, however, does not allow multiple enum constants to be
+ // considered equivalent. We treat the first defined constant for any
+ // given numeric value as "canonical" and the rest as aliases of that
+ // canonical value.
+ vector<const EnumValueDescriptor*> canonical_values_;
+
+ struct Alias {
+ const EnumValueDescriptor* value;
+ const EnumValueDescriptor* canonical_value;
+ };
+ vector<Alias> aliases_;
+
+ bool immutable_api_;
+
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ bool CanUseEnumValues();
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_ENUM_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.cc
new file mode 100644
index 0000000000..46b5faaa50
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.cc
@@ -0,0 +1,174 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_extension.h>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+ImmutableExtensionGenerator::ImmutableExtensionGenerator(
+ const FieldDescriptor* descriptor, Context* context)
+ : descriptor_(descriptor), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ if (descriptor_->extension_scope() != NULL) {
+ scope_ = name_resolver_->GetImmutableClassName(
+ descriptor_->extension_scope());
+ } else {
+ scope_ = name_resolver_->GetImmutableClassName(descriptor_->file());
+ }
+}
+
+ImmutableExtensionGenerator::~ImmutableExtensionGenerator() {}
+
+// Initializes the vars referenced in the generated code templates.
+void ExtensionGenerator::InitTemplateVars(const FieldDescriptor* descriptor,
+ const string& scope,
+ bool immutable,
+ ClassNameResolver* name_resolver,
+ map<string, string>* vars_pointer) {
+ map<string, string> &vars = *vars_pointer;
+ vars["scope"] = scope;
+ vars["name"] = UnderscoresToCamelCase(descriptor);
+ vars["containing_type"] =
+ name_resolver->GetClassName(descriptor->containing_type(), immutable);
+ vars["number"] = SimpleItoa(descriptor->number());
+ vars["constant_name"] = FieldConstantName(descriptor);
+ vars["index"] = SimpleItoa(descriptor->index());
+ vars["default"] = descriptor->is_repeated() ?
+ "" : DefaultValue(descriptor, immutable, name_resolver);
+ vars["type_constant"] = FieldTypeName(GetType(descriptor));
+ vars["packed"] = descriptor->options().packed() ? "true" : "false";
+ vars["enum_map"] = "null";
+ vars["prototype"] = "null";
+
+ JavaType java_type = GetJavaType(descriptor);
+ string singular_type;
+ switch (java_type) {
+ case JAVATYPE_MESSAGE:
+ singular_type = name_resolver->GetClassName(descriptor->message_type(),
+ immutable);
+ vars["prototype"] = singular_type + ".getDefaultInstance()";
+ break;
+ case JAVATYPE_ENUM:
+ singular_type = name_resolver->GetClassName(descriptor->enum_type(),
+ immutable);
+ vars["enum_map"] = singular_type + ".internalGetValueMap()";
+ break;
+ case JAVATYPE_STRING:
+ singular_type = "java.lang.String";
+ break;
+ case JAVATYPE_BYTES:
+ singular_type = immutable ? "com.google.protobuf.ByteString" : "byte[]";
+ break;
+ default:
+ singular_type = BoxedPrimitiveTypeName(java_type);
+ break;
+ }
+ vars["type"] = descriptor->is_repeated() ?
+ "java.util.List<" + singular_type + ">" : singular_type;
+ vars["singular_type"] = singular_type;
+}
+
+void ImmutableExtensionGenerator::Generate(io::Printer* printer) {
+ map<string, string> vars;
+ const bool kUseImmutableNames = true;
+ InitTemplateVars(descriptor_, scope_, kUseImmutableNames, name_resolver_,
+ &vars);
+ printer->Print(vars,
+ "public static final int $constant_name$ = $number$;\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ if (descriptor_->extension_scope() == NULL) {
+ // Non-nested
+ printer->Print(
+ vars,
+ "public static final\n"
+ " com.google.protobuf.GeneratedMessage.GeneratedExtension<\n"
+ " $containing_type$,\n"
+ " $type$> $name$ = com.google.protobuf.GeneratedMessage\n"
+ " .newFileScopedGeneratedExtension(\n"
+ " $singular_type$.class,\n"
+ " $prototype$);\n");
+ } else {
+ // Nested
+ printer->Print(
+ vars,
+ "public static final\n"
+ " com.google.protobuf.GeneratedMessage.GeneratedExtension<\n"
+ " $containing_type$,\n"
+ " $type$> $name$ = com.google.protobuf.GeneratedMessage\n"
+ " .newMessageScopedGeneratedExtension(\n"
+ " $scope$.getDefaultInstance(),\n"
+ " $index$,\n"
+ " $singular_type$.class,\n"
+ " $prototype$);\n");
+ }
+}
+
+int ImmutableExtensionGenerator::GenerateNonNestedInitializationCode(
+ io::Printer* printer) {
+ int bytecode_estimate = 0;
+ if (descriptor_->extension_scope() == NULL) {
+ // Only applies to non-nested extensions.
+ printer->Print(
+ "$name$.internalInit(descriptor.getExtensions().get($index$));\n",
+ "name", UnderscoresToCamelCase(descriptor_),
+ "index", SimpleItoa(descriptor_->index()));
+ bytecode_estimate += 21;
+ }
+ return bytecode_estimate;
+}
+
+int ImmutableExtensionGenerator::GenerateRegistrationCode(
+ io::Printer* printer) {
+ printer->Print(
+ "registry.add($scope$.$name$);\n",
+ "scope", scope_,
+ "name", UnderscoresToCamelCase(descriptor_));
+ return 7;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.h
new file mode 100644
index 0000000000..bdd4226379
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension.h
@@ -0,0 +1,113 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_EXTENSION_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_EXTENSION_H__
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+ class FieldDescriptor; // descriptor.h
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+// Generates code for an extension, which may be within the scope of some
+// message or may be at file scope. This is much simpler than FieldGenerator
+// since extensions are just simple identifiers with interesting types.
+class ExtensionGenerator {
+ public:
+ explicit ExtensionGenerator() {}
+ virtual ~ExtensionGenerator() {}
+
+ virtual void Generate(io::Printer* printer) = 0;
+
+ // Returns an estimate of the number of bytes the printed code will compile to
+ virtual int GenerateNonNestedInitializationCode(io::Printer* printer) = 0;
+
+ // Returns an estimate of the number of bytes the printed code will compile to
+ virtual int GenerateRegistrationCode(io::Printer* printer) = 0;
+
+ protected:
+ static void InitTemplateVars(const FieldDescriptor* descriptor,
+ const string& scope,
+ bool immutable,
+ ClassNameResolver* name_resolver,
+ map<string, string>* vars_pointer);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionGenerator);
+};
+
+class ImmutableExtensionGenerator : public ExtensionGenerator {
+ public:
+ explicit ImmutableExtensionGenerator(const FieldDescriptor* descriptor,
+ Context* context);
+ virtual ~ImmutableExtensionGenerator();
+
+ virtual void Generate(io::Printer* printer);
+ virtual int GenerateNonNestedInitializationCode(io::Printer* printer);
+ virtual int GenerateRegistrationCode(io::Printer* printer);
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ string scope_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableExtensionGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_EXTENSION_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.cc
new file mode 100644
index 0000000000..23261bac2f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.cc
@@ -0,0 +1,118 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_extension_lite.h>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+ImmutableExtensionLiteGenerator::ImmutableExtensionLiteGenerator(
+ const FieldDescriptor* descriptor, Context* context)
+ : descriptor_(descriptor), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ if (descriptor_->extension_scope() != NULL) {
+ scope_ = name_resolver_->GetImmutableClassName(
+ descriptor_->extension_scope());
+ } else {
+ scope_ = name_resolver_->GetImmutableClassName(descriptor_->file());
+ }
+}
+
+ImmutableExtensionLiteGenerator::~ImmutableExtensionLiteGenerator() {}
+
+void ImmutableExtensionLiteGenerator::Generate(io::Printer* printer) {
+ map<string, string> vars;
+ const bool kUseImmutableNames = true;
+ InitTemplateVars(descriptor_, scope_, kUseImmutableNames, name_resolver_,
+ &vars);
+ printer->Print(vars,
+ "public static final int $constant_name$ = $number$;\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ if (descriptor_->is_repeated()) {
+ printer->Print(
+ vars,
+ "public static final\n"
+ " com.google.protobuf.GeneratedMessageLite.GeneratedExtension<\n"
+ " $containing_type$,\n"
+ " $type$> $name$ = com.google.protobuf.GeneratedMessageLite\n"
+ " .newRepeatedGeneratedExtension(\n"
+ " $containing_type$.getDefaultInstance(),\n"
+ " $prototype$,\n"
+ " $enum_map$,\n"
+ " $number$,\n"
+ " com.google.protobuf.WireFormat.FieldType.$type_constant$,\n"
+ " $packed$,\n"
+ " $singular_type$.class);\n");
+ } else {
+ printer->Print(
+ vars,
+ "public static final\n"
+ " com.google.protobuf.GeneratedMessageLite.GeneratedExtension<\n"
+ " $containing_type$,\n"
+ " $type$> $name$ = com.google.protobuf.GeneratedMessageLite\n"
+ " .newSingularGeneratedExtension(\n"
+ " $containing_type$.getDefaultInstance(),\n"
+ " $default$,\n"
+ " $prototype$,\n"
+ " $enum_map$,\n"
+ " $number$,\n"
+ " com.google.protobuf.WireFormat.FieldType.$type_constant$,\n"
+ " $singular_type$.class);\n");
+ }
+}
+
+int ImmutableExtensionLiteGenerator::GenerateNonNestedInitializationCode(
+ io::Printer* printer) {
+ return 0;
+}
+
+int ImmutableExtensionLiteGenerator::GenerateRegistrationCode(
+ io::Printer* printer) {
+ printer->Print(
+ "registry.add($scope$.$name$);\n",
+ "scope", scope_,
+ "name", UnderscoresToCamelCase(descriptor_));
+ return 7;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.h
new file mode 100644
index 0000000000..4cd49bda20
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_extension_lite.h
@@ -0,0 +1,76 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_EXTENSION_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_EXTENSION_LITE_H__
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_extension.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+// Generates code for a lite extension, which may be within the scope of some
+// message or may be at file scope. This is much simpler than FieldGenerator
+// since extensions are just simple identifiers with interesting types.
+class ImmutableExtensionLiteGenerator : public ExtensionGenerator {
+ public:
+ explicit ImmutableExtensionLiteGenerator(const FieldDescriptor* descriptor,
+ Context* context);
+ virtual ~ImmutableExtensionLiteGenerator();
+
+ virtual void Generate(io::Printer* printer);
+
+ // Returns an estimate of the number of bytes the printed code will compile to
+ virtual int GenerateNonNestedInitializationCode(io::Printer* printer);
+
+ // Returns an estimate of the number of bytes the printed code will compile to
+ virtual int GenerateRegistrationCode(io::Printer* printer);
+
+ private:
+ const FieldDescriptor* descriptor_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ string scope_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableExtensionLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_EXTENSION_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.cc
new file mode 100644
index 0000000000..3c7bc5c467
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.cc
@@ -0,0 +1,332 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_field.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_enum_field.h>
+#include <google/protobuf/compiler/java/java_enum_field_lite.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_lazy_message_field.h>
+#include <google/protobuf/compiler/java/java_lazy_message_field_lite.h>
+#include <google/protobuf/compiler/java/java_map_field.h>
+#include <google/protobuf/compiler/java/java_map_field_lite.h>
+#include <google/protobuf/compiler/java/java_message_field.h>
+#include <google/protobuf/compiler/java/java_message_field_lite.h>
+#include <google/protobuf/compiler/java/java_primitive_field.h>
+#include <google/protobuf/compiler/java/java_primitive_field_lite.h>
+#include <google/protobuf/compiler/java/java_string_field.h>
+#include <google/protobuf/compiler/java/java_string_field_lite.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+ImmutableFieldGenerator* MakeImmutableGenerator(
+ const FieldDescriptor* field, int messageBitIndex, int builderBitIndex,
+ Context* context) {
+ if (field->is_repeated()) {
+ switch (GetJavaType(field)) {
+ case JAVATYPE_MESSAGE:
+ if (IsMapEntry(field->message_type())) {
+ return new ImmutableMapFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ if (IsLazy(field, context->EnforceLite())) {
+ return new RepeatedImmutableLazyMessageFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ return new RepeatedImmutableMessageFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ }
+ case JAVATYPE_ENUM:
+ return new RepeatedImmutableEnumFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ case JAVATYPE_STRING:
+ return new RepeatedImmutableStringFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ default:
+ return new RepeatedImmutablePrimitiveFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ } else {
+ if (field->containing_oneof()) {
+ switch (GetJavaType(field)) {
+ case JAVATYPE_MESSAGE:
+ if (IsLazy(field, context->EnforceLite())) {
+ return new ImmutableLazyMessageOneofFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ return new ImmutableMessageOneofFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ case JAVATYPE_ENUM:
+ return new ImmutableEnumOneofFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ case JAVATYPE_STRING:
+ return new ImmutableStringOneofFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ default:
+ return new ImmutablePrimitiveOneofFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ } else {
+ switch (GetJavaType(field)) {
+ case JAVATYPE_MESSAGE:
+ if (IsLazy(field, context->EnforceLite())) {
+ return new ImmutableLazyMessageFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ return new ImmutableMessageFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ case JAVATYPE_ENUM:
+ return new ImmutableEnumFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ case JAVATYPE_STRING:
+ return new ImmutableStringFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ default:
+ return new ImmutablePrimitiveFieldGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ }
+ }
+}
+
+ImmutableFieldLiteGenerator* MakeImmutableLiteGenerator(
+ const FieldDescriptor* field, int messageBitIndex, int builderBitIndex,
+ Context* context) {
+ if (field->is_repeated()) {
+ switch (GetJavaType(field)) {
+ case JAVATYPE_MESSAGE:
+ if (IsMapEntry(field->message_type())) {
+ return new ImmutableMapFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ if (IsLazy(field, context->EnforceLite())) {
+ return new RepeatedImmutableLazyMessageFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ return new RepeatedImmutableMessageFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ }
+ case JAVATYPE_ENUM:
+ return new RepeatedImmutableEnumFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ case JAVATYPE_STRING:
+ return new RepeatedImmutableStringFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ default:
+ return new RepeatedImmutablePrimitiveFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ } else {
+ if (field->containing_oneof()) {
+ switch (GetJavaType(field)) {
+ case JAVATYPE_MESSAGE:
+ if (IsLazy(field, context->EnforceLite())) {
+ return new ImmutableLazyMessageOneofFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ return new ImmutableMessageOneofFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ case JAVATYPE_ENUM:
+ return new ImmutableEnumOneofFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ case JAVATYPE_STRING:
+ return new ImmutableStringOneofFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ default:
+ return new ImmutablePrimitiveOneofFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ } else {
+ switch (GetJavaType(field)) {
+ case JAVATYPE_MESSAGE:
+ if (IsLazy(field, context->EnforceLite())) {
+ return new ImmutableLazyMessageFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ } else {
+ return new ImmutableMessageFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ case JAVATYPE_ENUM:
+ return new ImmutableEnumFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ case JAVATYPE_STRING:
+ return new ImmutableStringFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ default:
+ return new ImmutablePrimitiveFieldLiteGenerator(
+ field, messageBitIndex, builderBitIndex, context);
+ }
+ }
+ }
+}
+
+
+static inline void ReportUnexpectedPackedFieldsCall(io::Printer* printer) {
+ // Reaching here indicates a bug. Cases are:
+ // - This FieldGenerator should support packing,
+ // but this method should be overridden.
+ // - This FieldGenerator doesn't support packing, and this method
+ // should never have been called.
+ GOOGLE_LOG(FATAL) << "GenerateParsingCodeFromPacked() "
+ << "called on field generator that does not support packing.";
+}
+
+} // namespace
+
+ImmutableFieldGenerator::~ImmutableFieldGenerator() {}
+
+void ImmutableFieldGenerator::
+GenerateParsingCodeFromPacked(io::Printer* printer) const {
+ ReportUnexpectedPackedFieldsCall(printer);
+}
+
+ImmutableFieldLiteGenerator::~ImmutableFieldLiteGenerator() {}
+
+void ImmutableFieldLiteGenerator::
+GenerateParsingCodeFromPacked(io::Printer* printer) const {
+ ReportUnexpectedPackedFieldsCall(printer);
+}
+
+// ===================================================================
+
+template <>
+FieldGeneratorMap<ImmutableFieldGenerator>::FieldGeneratorMap(
+ const Descriptor* descriptor, Context* context)
+ : descriptor_(descriptor),
+ field_generators_(new google::protobuf::scoped_ptr<
+ ImmutableFieldGenerator>[descriptor->field_count()]) {
+
+ // Construct all the FieldGenerators and assign them bit indices for their
+ // bit fields.
+ int messageBitIndex = 0;
+ int builderBitIndex = 0;
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ ImmutableFieldGenerator* generator = MakeImmutableGenerator(
+ descriptor->field(i), messageBitIndex, builderBitIndex, context);
+ field_generators_[i].reset(generator);
+ messageBitIndex += generator->GetNumBitsForMessage();
+ builderBitIndex += generator->GetNumBitsForBuilder();
+ }
+}
+
+template<>
+FieldGeneratorMap<ImmutableFieldGenerator>::~FieldGeneratorMap() {}
+
+template <>
+FieldGeneratorMap<ImmutableFieldLiteGenerator>::FieldGeneratorMap(
+ const Descriptor* descriptor, Context* context)
+ : descriptor_(descriptor),
+ field_generators_(new google::protobuf::scoped_ptr<
+ ImmutableFieldLiteGenerator>[descriptor->field_count()]) {
+ // Construct all the FieldGenerators and assign them bit indices for their
+ // bit fields.
+ int messageBitIndex = 0;
+ int builderBitIndex = 0;
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ ImmutableFieldLiteGenerator* generator = MakeImmutableLiteGenerator(
+ descriptor->field(i), messageBitIndex, builderBitIndex, context);
+ field_generators_[i].reset(generator);
+ messageBitIndex += generator->GetNumBitsForMessage();
+ builderBitIndex += generator->GetNumBitsForBuilder();
+ }
+}
+
+template<>
+FieldGeneratorMap<ImmutableFieldLiteGenerator>::~FieldGeneratorMap() {}
+
+
+void SetCommonFieldVariables(const FieldDescriptor* descriptor,
+ const FieldGeneratorInfo* info,
+ map<string, string>* variables) {
+ (*variables)["field_name"] = descriptor->name();
+ (*variables)["name"] = info->name;
+ (*variables)["capitalized_name"] = info->capitalized_name;
+ (*variables)["disambiguated_reason"] = info->disambiguated_reason;
+ (*variables)["constant_name"] = FieldConstantName(descriptor);
+ (*variables)["number"] = SimpleItoa(descriptor->number());
+}
+
+void SetCommonOneofVariables(const FieldDescriptor* descriptor,
+ const OneofGeneratorInfo* info,
+ map<string, string>* variables) {
+ (*variables)["oneof_name"] = info->name;
+ (*variables)["oneof_capitalized_name"] = info->capitalized_name;
+ (*variables)["oneof_index"] =
+ SimpleItoa(descriptor->containing_oneof()->index());
+ (*variables)["set_oneof_case_message"] = info->name +
+ "Case_ = " + SimpleItoa(descriptor->number());
+ (*variables)["clear_oneof_case_message"] = info->name +
+ "Case_ = 0";
+ (*variables)["has_oneof_case_message"] = info->name +
+ "Case_ == " + SimpleItoa(descriptor->number());
+}
+
+void PrintExtraFieldInfo(const map<string, string>& variables,
+ io::Printer* printer) {
+ const map<string, string>::const_iterator it =
+ variables.find("disambiguated_reason");
+ if (it != variables.end() && !it->second.empty()) {
+ printer->Print(
+ variables,
+ "// An alternative name is used for field \"$field_name$\" because:\n"
+ "// $disambiguated_reason$\n");
+ }
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.h
new file mode 100644
index 0000000000..4dd4f57f6d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_field.h
@@ -0,0 +1,197 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_FIELD_H__
+
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/stubs/logging.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableFieldGenerator {
+ public:
+ ImmutableFieldGenerator() {}
+ virtual ~ImmutableFieldGenerator();
+
+ virtual int GetNumBitsForMessage() const = 0;
+ virtual int GetNumBitsForBuilder() const = 0;
+ virtual void GenerateInterfaceMembers(io::Printer* printer) const = 0;
+ virtual void GenerateMembers(io::Printer* printer) const = 0;
+ virtual void GenerateBuilderMembers(io::Printer* printer) const = 0;
+ virtual void GenerateInitializationCode(io::Printer* printer) const = 0;
+ virtual void GenerateBuilderClearCode(io::Printer* printer) const = 0;
+ virtual void GenerateMergingCode(io::Printer* printer) const = 0;
+ virtual void GenerateBuildingCode(io::Printer* printer) const = 0;
+ virtual void GenerateParsingCode(io::Printer* printer) const = 0;
+ virtual void GenerateParsingCodeFromPacked(io::Printer* printer) const;
+ virtual void GenerateParsingDoneCode(io::Printer* printer) const = 0;
+ virtual void GenerateSerializationCode(io::Printer* printer) const = 0;
+ virtual void GenerateSerializedSizeCode(io::Printer* printer) const = 0;
+ virtual void GenerateFieldBuilderInitializationCode(io::Printer* printer)
+ const = 0;
+
+ virtual void GenerateEqualsCode(io::Printer* printer) const = 0;
+ virtual void GenerateHashCode(io::Printer* printer) const = 0;
+
+ virtual string GetBoxedType() const = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableFieldGenerator);
+};
+
+class ImmutableFieldLiteGenerator {
+ public:
+ ImmutableFieldLiteGenerator() {}
+ virtual ~ImmutableFieldLiteGenerator();
+
+ virtual int GetNumBitsForMessage() const = 0;
+ virtual int GetNumBitsForBuilder() const = 0;
+ virtual void GenerateInterfaceMembers(io::Printer* printer) const = 0;
+ virtual void GenerateMembers(io::Printer* printer) const = 0;
+ virtual void GenerateBuilderMembers(io::Printer* printer) const = 0;
+ virtual void GenerateInitializationCode(io::Printer* printer) const = 0;
+ virtual void GenerateVisitCode(io::Printer* printer) const = 0;
+ virtual void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer)
+ const = 0;
+ virtual void GenerateParsingCode(io::Printer* printer) const = 0;
+ virtual void GenerateParsingCodeFromPacked(io::Printer* printer) const;
+ virtual void GenerateParsingDoneCode(io::Printer* printer) const = 0;
+ virtual void GenerateSerializationCode(io::Printer* printer) const = 0;
+ virtual void GenerateSerializedSizeCode(io::Printer* printer) const = 0;
+ virtual void GenerateFieldBuilderInitializationCode(io::Printer* printer)
+ const = 0;
+
+ virtual void GenerateEqualsCode(io::Printer* printer) const = 0;
+ virtual void GenerateHashCode(io::Printer* printer) const = 0;
+
+ virtual string GetBoxedType() const = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableFieldLiteGenerator);
+};
+
+
+// Convenience class which constructs FieldGenerators for a Descriptor.
+template<typename FieldGeneratorType>
+class FieldGeneratorMap {
+ public:
+ explicit FieldGeneratorMap(const Descriptor* descriptor,
+ Context* context);
+ ~FieldGeneratorMap();
+
+ const FieldGeneratorType& get(const FieldDescriptor* field) const;
+
+ private:
+ const Descriptor* descriptor_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<FieldGeneratorType> > field_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGeneratorMap);
+};
+
+template<typename FieldGeneratorType>
+inline const FieldGeneratorType&
+FieldGeneratorMap<FieldGeneratorType>::get(const FieldDescriptor* field) const {
+ GOOGLE_CHECK_EQ(field->containing_type(), descriptor_);
+ return *field_generators_[field->index()];
+}
+
+// Instantiate template for mutable and immutable maps.
+template<>
+FieldGeneratorMap<ImmutableFieldGenerator>::
+FieldGeneratorMap(const Descriptor* descriptor,
+ Context* context);
+
+template<>
+FieldGeneratorMap<ImmutableFieldGenerator>::~FieldGeneratorMap();
+
+
+// Field information used in FieldGeneartors.
+struct FieldGeneratorInfo {
+ string name;
+ string capitalized_name;
+ string disambiguated_reason;
+};
+
+// Oneof information used in OneofFieldGeneartors.
+struct OneofGeneratorInfo {
+ string name;
+ string capitalized_name;
+};
+
+// Set some common variables used in variable FieldGenerators.
+void SetCommonFieldVariables(const FieldDescriptor* descriptor,
+ const FieldGeneratorInfo* info,
+ map<string, string>* variables);
+
+// Set some common oneof variables used in OneofFieldGenerators.
+void SetCommonOneofVariables(const FieldDescriptor* descriptor,
+ const OneofGeneratorInfo* info,
+ map<string, string>* variables);
+
+// Print useful comments before a field's accessors.
+void PrintExtraFieldInfo(const map<string, string>& variables,
+ io::Printer* printer);
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.cc
new file mode 100644
index 0000000000..5e387285bb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.cc
@@ -0,0 +1,639 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_file.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <set>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_enum.h>
+#include <google/protobuf/compiler/java/java_enum_lite.h>
+#include <google/protobuf/compiler/java/java_extension.h>
+#include <google/protobuf/compiler/java/java_generator_factory.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_message.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/compiler/java/java_service.h>
+#include <google/protobuf/compiler/java/java_shared_code_generator.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+struct FieldDescriptorCompare {
+ bool operator ()(const FieldDescriptor* f1, const FieldDescriptor* f2) {
+ if(f1 == NULL) {
+ return false;
+ }
+ if(f2 == NULL) {
+ return true;
+ }
+ return f1->full_name() < f2->full_name();
+ }
+};
+
+typedef std::set<const FieldDescriptor*, FieldDescriptorCompare> FieldDescriptorSet;
+
+// Recursively searches the given message to collect extensions.
+// Returns true if all the extensions can be recognized. The extensions will be
+// appended in to the extensions parameter.
+// Returns false when there are unknown fields, in which case the data in the
+// extensions output parameter is not reliable and should be discarded.
+bool CollectExtensions(const Message& message,
+ FieldDescriptorSet* extensions) {
+ const Reflection* reflection = message.GetReflection();
+
+ // There are unknown fields that could be extensions, thus this call fails.
+ if (reflection->GetUnknownFields(message).field_count() > 0) return false;
+
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message, &fields);
+
+ for (int i = 0; i < fields.size(); i++) {
+ if (fields[i]->is_extension()) extensions->insert(fields[i]);
+
+ if (GetJavaType(fields[i]) == JAVATYPE_MESSAGE) {
+ if (fields[i]->is_repeated()) {
+ int size = reflection->FieldSize(message, fields[i]);
+ for (int j = 0; j < size; j++) {
+ const Message& sub_message =
+ reflection->GetRepeatedMessage(message, fields[i], j);
+ if (!CollectExtensions(sub_message, extensions)) return false;
+ }
+ } else {
+ const Message& sub_message = reflection->GetMessage(message, fields[i]);
+ if (!CollectExtensions(sub_message, extensions)) return false;
+ }
+ }
+ }
+
+ return true;
+}
+
+// Finds all extensions in the given message and its sub-messages. If the
+// message contains unknown fields (which could be extensions), then those
+// extensions are defined in alternate_pool.
+// The message will be converted to a DynamicMessage backed by alternate_pool
+// in order to handle this case.
+void CollectExtensions(const FileDescriptorProto& file_proto,
+ const DescriptorPool& alternate_pool,
+ FieldDescriptorSet* extensions,
+ const string& file_data) {
+ if (!CollectExtensions(file_proto, extensions)) {
+ // There are unknown fields in the file_proto, which are probably
+ // extensions. We need to parse the data into a dynamic message based on the
+ // builder-pool to find out all extensions.
+ const Descriptor* file_proto_desc = alternate_pool.FindMessageTypeByName(
+ file_proto.GetDescriptor()->full_name());
+ GOOGLE_CHECK(file_proto_desc)
+ << "Find unknown fields in FileDescriptorProto when building "
+ << file_proto.name()
+ << ". It's likely that those fields are custom options, however, "
+ "descriptor.proto is not in the transitive dependencies. "
+ "This normally should not happen. Please report a bug.";
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> dynamic_file_proto(
+ factory.GetPrototype(file_proto_desc)->New());
+ GOOGLE_CHECK(dynamic_file_proto.get() != NULL);
+ GOOGLE_CHECK(dynamic_file_proto->ParseFromString(file_data));
+
+ // Collect the extensions again from the dynamic message. There should be no
+ // more unknown fields this time, i.e. all the custom options should be
+ // parsed as extensions now.
+ extensions->clear();
+ GOOGLE_CHECK(CollectExtensions(*dynamic_file_proto, extensions))
+ << "Find unknown fields in FileDescriptorProto when building "
+ << file_proto.name()
+ << ". It's likely that those fields are custom options, however, "
+ "those options cannot be recognized in the builder pool. "
+ "This normally should not happen. Please report a bug.";
+ }
+}
+
+// Compare two field descriptors, returning true if the first should come
+// before the second.
+bool CompareFieldsByName(const FieldDescriptor *a, const FieldDescriptor *b) {
+ return a->full_name() < b->full_name();
+}
+
+// Our static initialization methods can become very, very large.
+// So large that if we aren't careful we end up blowing the JVM's
+// 64K bytes of bytecode/method. Fortunately, since these static
+// methods are executed only once near the beginning of a program,
+// there's usually plenty of stack space available and we can
+// extend our methods by simply chaining them to another method
+// with a tail call. This inserts the sequence call-next-method,
+// end this one, begin-next-method as needed.
+void MaybeRestartJavaMethod(io::Printer* printer,
+ int *bytecode_estimate,
+ int *method_num,
+ const char *chain_statement,
+ const char *method_decl) {
+ // The goal here is to stay under 64K bytes of jvm bytecode/method,
+ // since otherwise we hit a hardcoded limit in the jvm and javac will
+ // then fail with the error "code too large". This limit lets our
+ // estimates be off by a factor of two and still we're okay.
+ static const int bytesPerMethod = kMaxStaticSize;
+
+ if ((*bytecode_estimate) > bytesPerMethod) {
+ ++(*method_num);
+ printer->Print(chain_statement, "method_num", SimpleItoa(*method_num));
+ printer->Outdent();
+ printer->Print("}\n");
+ printer->Print(method_decl, "method_num", SimpleItoa(*method_num));
+ printer->Indent();
+ *bytecode_estimate = 0;
+ }
+}
+
+
+} // namespace
+
+FileGenerator::FileGenerator(const FileDescriptor* file, const Options& options,
+ bool immutable_api)
+ : file_(file),
+ java_package_(FileJavaPackage(file, immutable_api)),
+ message_generators_(
+ new google::protobuf::scoped_ptr<MessageGenerator>[file->message_type_count()]),
+ extension_generators_(
+ new google::protobuf::scoped_ptr<ExtensionGenerator>[file->extension_count()]),
+ context_(new Context(file, options)),
+ name_resolver_(context_->GetNameResolver()),
+ options_(options),
+ immutable_api_(immutable_api) {
+ classname_ = name_resolver_->GetFileClassName(file, immutable_api);
+ generator_factory_.reset(
+ new ImmutableGeneratorFactory(context_.get()));
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ message_generators_[i].reset(
+ generator_factory_->NewMessageGenerator(file_->message_type(i)));
+ }
+ for (int i = 0; i < file_->extension_count(); ++i) {
+ extension_generators_[i].reset(
+ generator_factory_->NewExtensionGenerator(file_->extension(i)));
+ }
+}
+
+FileGenerator::~FileGenerator() {}
+
+bool FileGenerator::Validate(string* error) {
+ // Check that no class name matches the file's class name. This is a common
+ // problem that leads to Java compile errors that can be hard to understand.
+ // It's especially bad when using the java_multiple_files, since we would
+ // end up overwriting the outer class with one of the inner ones.
+ if (name_resolver_->HasConflictingClassName(file_, classname_)) {
+ error->assign(file_->name());
+ error->append(
+ ": Cannot generate Java output because the file's outer class name, \"");
+ error->append(classname_);
+ error->append(
+ "\", matches the name of one of the types declared inside it. "
+ "Please either rename the type or use the java_outer_classname "
+ "option to specify a different outer class name for the .proto file.");
+ return false;
+ }
+ return true;
+}
+
+void FileGenerator::Generate(io::Printer* printer) {
+ // We don't import anything because we refer to all classes by their
+ // fully-qualified names in the generated source.
+ printer->Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "// source: $filename$\n"
+ "\n",
+ "filename", file_->name());
+ if (!java_package_.empty()) {
+ printer->Print(
+ "package $package$;\n"
+ "\n",
+ "package", java_package_);
+ }
+ PrintGeneratedAnnotation(
+ printer, '$', options_.annotate_code ? classname_ + ".java.pb.meta" : "");
+ printer->Print(
+ "public final class $classname$ {\n"
+ " private $ctor$() {}\n",
+ "classname", classname_, "ctor", classname_);
+ printer->Annotate("classname", file_->name());
+ printer->Indent();
+
+ // -----------------------------------------------------------------
+
+ printer->Print(
+ "public static void registerAllExtensions(\n"
+ " com.google.protobuf.ExtensionRegistryLite registry) {\n");
+
+ printer->Indent();
+
+ for (int i = 0; i < file_->extension_count(); i++) {
+ extension_generators_[i]->GenerateRegistrationCode(printer);
+ }
+
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateExtensionRegistrationCode(printer);
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ if (HasDescriptorMethods(file_, context_->EnforceLite())) {
+ // Overload registerAllExtensions for the non-lite usage to
+ // redundantly maintain the original signature (this is
+ // redundant because ExtensionRegistryLite now invokes
+ // ExtensionRegistry in the non-lite usage). Intent is
+ // to remove this in the future.
+ printer->Print(
+ "\n"
+ "public static void registerAllExtensions(\n"
+ " com.google.protobuf.ExtensionRegistry registry) {\n"
+ " registerAllExtensions(\n"
+ " (com.google.protobuf.ExtensionRegistryLite) registry);\n"
+ "}\n");
+ }
+
+ // -----------------------------------------------------------------
+
+ if (!MultipleJavaFiles(file_, immutable_api_)) {
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ if (HasDescriptorMethods(file_, context_->EnforceLite())) {
+ EnumGenerator(file_->enum_type(i), immutable_api_, context_.get())
+ .Generate(printer);
+ } else {
+ EnumLiteGenerator(file_->enum_type(i), immutable_api_, context_.get())
+ .Generate(printer);
+ }
+ }
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateInterface(printer);
+ message_generators_[i]->Generate(printer);
+ }
+ if (HasGenericServices(file_, context_->EnforceLite())) {
+ for (int i = 0; i < file_->service_count(); i++) {
+ google::protobuf::scoped_ptr<ServiceGenerator> generator(
+ generator_factory_->NewServiceGenerator(file_->service(i)));
+ generator->Generate(printer);
+ }
+ }
+ }
+
+ // Extensions must be generated in the outer class since they are values,
+ // not classes.
+ for (int i = 0; i < file_->extension_count(); i++) {
+ extension_generators_[i]->Generate(printer);
+ }
+
+ // Static variables. We'd like them to be final if possible, but due to
+ // the JVM's 64k size limit on static blocks, we have to initialize some
+ // of them in methods; thus they cannot be final.
+ int static_block_bytecode_estimate = 0;
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateStaticVariables(
+ printer, &static_block_bytecode_estimate);
+ }
+
+ printer->Print("\n");
+
+ if (HasDescriptorMethods(file_, context_->EnforceLite())) {
+ if (immutable_api_) {
+ GenerateDescriptorInitializationCodeForImmutable(printer);
+ } else {
+ GenerateDescriptorInitializationCodeForMutable(printer);
+ }
+ } else {
+ printer->Print(
+ "static {\n");
+ printer->Indent();
+ int bytecode_estimate = 0;
+ int method_num = 0;
+
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ bytecode_estimate += message_generators_[i]->GenerateStaticVariableInitializers(printer);
+ MaybeRestartJavaMethod(
+ printer,
+ &bytecode_estimate, &method_num,
+ "_clinit_autosplit_$method_num$();\n",
+ "private static void _clinit_autosplit_$method_num$() {\n");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(outer_class_scope)\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void FileGenerator::GenerateDescriptorInitializationCodeForImmutable(
+ io::Printer* printer) {
+ printer->Print(
+ "public static com.google.protobuf.Descriptors.FileDescriptor\n"
+ " getDescriptor() {\n"
+ " return descriptor;\n"
+ "}\n"
+ "private static $final$ com.google.protobuf.Descriptors.FileDescriptor\n"
+ " descriptor;\n"
+ "static {\n",
+ // TODO(dweis): Mark this as final.
+ "final", "");
+ printer->Indent();
+
+ SharedCodeGenerator shared_code_generator(file_, options_);
+ shared_code_generator.GenerateDescriptors(printer);
+
+ int bytecode_estimate = 0;
+ int method_num = 0;
+
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ bytecode_estimate += message_generators_[i]->GenerateStaticVariableInitializers(printer);
+ MaybeRestartJavaMethod(
+ printer,
+ &bytecode_estimate, &method_num,
+ "_clinit_autosplit_dinit_$method_num$();\n",
+ "private static void _clinit_autosplit_dinit_$method_num$() {\n");
+ }
+ for (int i = 0; i < file_->extension_count(); i++) {
+ bytecode_estimate += extension_generators_[i]->GenerateNonNestedInitializationCode(printer);
+ MaybeRestartJavaMethod(
+ printer,
+ &bytecode_estimate, &method_num,
+ "_clinit_autosplit_dinit_$method_num$();\n",
+ "private static void _clinit_autosplit_dinit_$method_num$() {\n");
+ }
+
+ // Proto compiler builds a DescriptorPool, which holds all the descriptors to
+ // generate, when processing the ".proto" files. We call this DescriptorPool
+ // the parsed pool (a.k.a. file_->pool()).
+ //
+ // Note that when users try to extend the (.*)DescriptorProto in their
+ // ".proto" files, it does not affect the pre-built FileDescriptorProto class
+ // in proto compiler. When we put the descriptor data in the file_proto, those
+ // extensions become unknown fields.
+ //
+ // Now we need to find out all the extension value to the (.*)DescriptorProto
+ // in the file_proto message, and prepare an ExtensionRegistry to return.
+ //
+ // To find those extensions, we need to parse the data into a dynamic message
+ // of the FileDescriptor based on the builder-pool, then we can use
+ // reflections to find all extension fields
+ FileDescriptorProto file_proto;
+ file_->CopyTo(&file_proto);
+ string file_data;
+ file_proto.SerializeToString(&file_data);
+ FieldDescriptorSet extensions;
+ CollectExtensions(file_proto, *file_->pool(), &extensions, file_data);
+
+ if (extensions.size() > 0) {
+ // Must construct an ExtensionRegistry containing all existing extensions
+ // and use it to parse the descriptor data again to recognize extensions.
+ printer->Print(
+ "com.google.protobuf.ExtensionRegistry registry =\n"
+ " com.google.protobuf.ExtensionRegistry.newInstance();\n");
+ FieldDescriptorSet::iterator it;
+ for (it = extensions.begin(); it != extensions.end(); it++) {
+ google::protobuf::scoped_ptr<ExtensionGenerator> generator(
+ generator_factory_->NewExtensionGenerator(*it));
+ bytecode_estimate += generator->GenerateRegistrationCode(printer);
+ MaybeRestartJavaMethod(
+ printer,
+ &bytecode_estimate, &method_num,
+ "_clinit_autosplit_dinit_$method_num$(registry);\n",
+ "private static void _clinit_autosplit_dinit_$method_num$(\n"
+ " com.google.protobuf.ExtensionRegistry registry) {\n");
+ }
+ printer->Print(
+ "com.google.protobuf.Descriptors.FileDescriptor\n"
+ " .internalUpdateFileDescriptor(descriptor, registry);\n");
+ }
+
+ // Force descriptor initialization of all dependencies.
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ if (ShouldIncludeDependency(file_->dependency(i), true)) {
+ string dependency =
+ name_resolver_->GetImmutableClassName(file_->dependency(i));
+ printer->Print(
+ "$dependency$.getDescriptor();\n",
+ "dependency", dependency);
+ }
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+}
+
+void FileGenerator::GenerateDescriptorInitializationCodeForMutable(io::Printer* printer) {
+ printer->Print(
+ "public static com.google.protobuf.Descriptors.FileDescriptor\n"
+ " getDescriptor() {\n"
+ " return descriptor;\n"
+ "}\n"
+ "private static final com.google.protobuf.Descriptors.FileDescriptor\n"
+ " descriptor;\n"
+ "static {\n");
+ printer->Indent();
+
+ printer->Print(
+ "descriptor = $immutable_package$.$descriptor_classname$.descriptor;\n",
+ "immutable_package", FileJavaPackage(file_, true),
+ "descriptor_classname", name_resolver_->GetDescriptorClassName(file_));
+
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ message_generators_[i]->GenerateStaticVariableInitializers(printer);
+ }
+ for (int i = 0; i < file_->extension_count(); i++) {
+ extension_generators_[i]->GenerateNonNestedInitializationCode(printer);
+ }
+
+ // Check if custom options exist. If any, try to load immutable classes since
+ // custom options are only represented with immutable messages.
+ FileDescriptorProto file_proto;
+ file_->CopyTo(&file_proto);
+ string file_data;
+ file_proto.SerializeToString(&file_data);
+ FieldDescriptorSet extensions;
+ CollectExtensions(file_proto, *file_->pool(), &extensions, file_data);
+
+ if (extensions.size() > 0) {
+ // Try to load immutable messages' outer class. Its initialization code
+ // will take care of interpreting custom options.
+ printer->Print(
+ "try {\n"
+ // Note that we have to load the immutable class dynamically here as
+ // we want the mutable code to be independent from the immutable code
+ // at compile time. It is required to implement dual-compile for
+ // mutable and immutable API in blaze.
+ " java.lang.Class immutableClass = java.lang.Class.forName(\n"
+ " \"$immutable_classname$\");\n"
+ "} catch (java.lang.ClassNotFoundException e) {\n"
+ // The immutable class can not be found. Custom options are left
+ // as unknown fields.
+ // TODO(xiaofeng): inform the user with a warning?
+ "}\n",
+ "immutable_classname", name_resolver_->GetImmutableClassName(file_));
+ }
+
+ // Force descriptor initialization of all dependencies.
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ if (ShouldIncludeDependency(file_->dependency(i), false)) {
+ string dependency = name_resolver_->GetMutableClassName(
+ file_->dependency(i));
+ printer->Print(
+ "$dependency$.getDescriptor();\n",
+ "dependency", dependency);
+ }
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+}
+
+template <typename GeneratorClass, typename DescriptorClass>
+static void GenerateSibling(const string& package_dir,
+ const string& java_package,
+ const DescriptorClass* descriptor,
+ GeneratorContext* context,
+ vector<string>* file_list, bool annotate_code,
+ vector<string>* annotation_list,
+ const string& name_suffix,
+ GeneratorClass* generator,
+ void (GeneratorClass::*pfn)(io::Printer* printer)) {
+ string filename = package_dir + descriptor->name() + name_suffix + ".java";
+ file_list->push_back(filename);
+ string info_full_path = filename + ".pb.meta";
+ GeneratedCodeInfo annotations;
+ io::AnnotationProtoCollector<GeneratedCodeInfo> annotation_collector(
+ &annotations);
+
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(filename));
+ io::Printer printer(output.get(), '$',
+ annotate_code ? &annotation_collector : NULL);
+
+ printer.Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "// source: $filename$\n"
+ "\n",
+ "filename", descriptor->file()->name());
+ if (!java_package.empty()) {
+ printer.Print(
+ "package $package$;\n"
+ "\n",
+ "package", java_package);
+ }
+
+ (generator->*pfn)(&printer);
+
+ if (annotate_code) {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> info_output(
+ context->Open(info_full_path));
+ annotations.SerializeToZeroCopyStream(info_output.get());
+ annotation_list->push_back(info_full_path);
+ }
+}
+
+void FileGenerator::GenerateSiblings(const string& package_dir,
+ GeneratorContext* context,
+ vector<string>* file_list,
+ vector<string>* annotation_list) {
+ if (MultipleJavaFiles(file_, immutable_api_)) {
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ if (HasDescriptorMethods(file_, context_->EnforceLite())) {
+ EnumGenerator generator(file_->enum_type(i), immutable_api_,
+ context_.get());
+ GenerateSibling<EnumGenerator>(
+ package_dir, java_package_, file_->enum_type(i), context, file_list,
+ options_.annotate_code, annotation_list, "", &generator,
+ &EnumGenerator::Generate);
+ } else {
+ EnumLiteGenerator generator(file_->enum_type(i), immutable_api_,
+ context_.get());
+ GenerateSibling<EnumLiteGenerator>(
+ package_dir, java_package_, file_->enum_type(i), context, file_list,
+ options_.annotate_code, annotation_list, "", &generator,
+ &EnumLiteGenerator::Generate);
+ }
+ }
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ if (immutable_api_) {
+ GenerateSibling<MessageGenerator>(
+ package_dir, java_package_, file_->message_type(i), context,
+ file_list, options_.annotate_code, annotation_list, "OrBuilder",
+ message_generators_[i].get(), &MessageGenerator::GenerateInterface);
+ }
+ GenerateSibling<MessageGenerator>(
+ package_dir, java_package_, file_->message_type(i), context,
+ file_list, options_.annotate_code, annotation_list, "",
+ message_generators_[i].get(), &MessageGenerator::Generate);
+ }
+ if (HasGenericServices(file_, context_->EnforceLite())) {
+ for (int i = 0; i < file_->service_count(); i++) {
+ google::protobuf::scoped_ptr<ServiceGenerator> generator(
+ generator_factory_->NewServiceGenerator(file_->service(i)));
+ GenerateSibling<ServiceGenerator>(
+ package_dir, java_package_, file_->service(i), context, file_list,
+ options_.annotate_code, annotation_list, "", generator.get(),
+ &ServiceGenerator::Generate);
+ }
+ }
+ }
+}
+
+bool FileGenerator::ShouldIncludeDependency(
+ const FileDescriptor* descriptor, bool immutable_api) {
+ return true;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.h
new file mode 100644
index 0000000000..1e643f79bd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_file.h
@@ -0,0 +1,120 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_FILE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_FILE_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_options.h>
+
+namespace google {
+namespace protobuf {
+ class FileDescriptor; // descriptor.h
+ namespace io {
+ class Printer; // printer.h
+ }
+ namespace compiler {
+ class GeneratorContext; // code_generator.h
+ namespace java {
+ class Context; // context.h
+ class MessageGenerator; // message.h
+ class GeneratorFactory; // generator_factory.h
+ class ExtensionGenerator; // extension.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class FileGenerator {
+ public:
+ FileGenerator(const FileDescriptor* file, const Options& options,
+ bool immutable_api = true);
+ ~FileGenerator();
+
+ // Checks for problems that would otherwise lead to cryptic compile errors.
+ // Returns true if there are no problems, or writes an error description to
+ // the given string and returns false otherwise.
+ bool Validate(string* error);
+
+ void Generate(io::Printer* printer);
+
+ // If we aren't putting everything into one file, this will write all the
+ // files other than the outer file (i.e. one for each message, enum, and
+ // service type).
+ void GenerateSiblings(const string& package_dir,
+ GeneratorContext* generator_context,
+ vector<string>* file_list,
+ vector<string>* annotation_list);
+
+ const string& java_package() { return java_package_; }
+ const string& classname() { return classname_; }
+
+ private:
+ void GenerateDescriptorInitializationCodeForImmutable(io::Printer* printer);
+ void GenerateDescriptorInitializationCodeForMutable(io::Printer* printer);
+
+ bool ShouldIncludeDependency(const FileDescriptor* descriptor,
+ bool immutable_api_);
+
+ const FileDescriptor* file_;
+ string java_package_;
+ string classname_;
+
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<MessageGenerator> > message_generators_;
+ google::protobuf::scoped_array<google::protobuf::scoped_ptr<ExtensionGenerator> > extension_generators_;
+ google::protobuf::scoped_ptr<GeneratorFactory> generator_factory_;
+ google::protobuf::scoped_ptr<Context> context_;
+ ClassNameResolver* name_resolver_;
+ const Options options_;
+ bool immutable_api_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_FILE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.cc
new file mode 100644
index 0000000000..b1ab404330
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.cc
@@ -0,0 +1,202 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_generator.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/java/java_file.h>
+#include <google/protobuf/compiler/java/java_generator_factory.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_options.h>
+#include <google/protobuf/compiler/java/java_shared_code_generator.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+
+JavaGenerator::JavaGenerator() {}
+JavaGenerator::~JavaGenerator() {}
+
+bool JavaGenerator::Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ // -----------------------------------------------------------------
+ // parse generator options
+
+
+ vector<pair<string, string> > options;
+ ParseGeneratorParameter(parameter, &options);
+ Options file_options;
+
+ for (int i = 0; i < options.size(); i++) {
+ if (options[i].first == "output_list_file") {
+ file_options.output_list_file = options[i].second;
+ } else if (options[i].first == "immutable") {
+ file_options.generate_immutable_code = true;
+ } else if (options[i].first == "mutable") {
+ file_options.generate_mutable_code = true;
+ } else if (options[i].first == "shared") {
+ file_options.generate_shared_code = true;
+ } else if (options[i].first == "annotate_code") {
+ file_options.annotate_code = true;
+ } else if (options[i].first == "annotation_list_file") {
+ file_options.annotation_list_file = options[i].second;
+ } else {
+ *error = "Unknown generator option: " + options[i].first;
+ return false;
+ }
+ }
+
+ if (file_options.enforce_lite && file_options.generate_mutable_code) {
+ *error = "lite runtime generator option cannot be used with mutable API.";
+ return false;
+ }
+
+ // By default we generate immutable code and shared code for immutable API.
+ if (!file_options.generate_immutable_code &&
+ !file_options.generate_mutable_code &&
+ !file_options.generate_shared_code) {
+ file_options.generate_immutable_code = true;
+ file_options.generate_shared_code = true;
+ }
+
+ // -----------------------------------------------------------------
+
+
+ vector<string> all_files;
+ vector<string> all_annotations;
+
+
+ vector<FileGenerator*> file_generators;
+ if (file_options.generate_immutable_code) {
+ file_generators.push_back(new FileGenerator(file, file_options,
+ /* immutable = */ true));
+ }
+ if (file_options.generate_mutable_code) {
+ file_generators.push_back(new FileGenerator(file, file_options,
+ /* mutable = */ false));
+ }
+ for (int i = 0; i < file_generators.size(); ++i) {
+ if (!file_generators[i]->Validate(error)) {
+ for (int j = 0; j < file_generators.size(); ++j) {
+ delete file_generators[j];
+ }
+ return false;
+ }
+ }
+
+ for (int i = 0; i < file_generators.size(); ++i) {
+ FileGenerator* file_generator = file_generators[i];
+
+ string package_dir = JavaPackageToDir(file_generator->java_package());
+
+ string java_filename = package_dir;
+ java_filename += file_generator->classname();
+ java_filename += ".java";
+ all_files.push_back(java_filename);
+ string info_full_path = java_filename + ".pb.meta";
+ if (file_options.annotate_code) {
+ all_annotations.push_back(info_full_path);
+ }
+
+ // Generate main java file.
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->Open(java_filename));
+ GeneratedCodeInfo annotations;
+ io::AnnotationProtoCollector<GeneratedCodeInfo> annotation_collector(
+ &annotations);
+ io::Printer printer(output.get(), '$', file_options.annotate_code
+ ? &annotation_collector
+ : NULL);
+
+ file_generator->Generate(&printer);
+
+ // Generate sibling files.
+ file_generator->GenerateSiblings(package_dir, context, &all_files,
+ &all_annotations);
+
+ if (file_options.annotate_code) {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> info_output(
+ context->Open(info_full_path));
+ annotations.SerializeToZeroCopyStream(info_output.get());
+ }
+ }
+
+ for (int i = 0; i < file_generators.size(); ++i) {
+ delete file_generators[i];
+ }
+ file_generators.clear();
+
+ // Generate output list if requested.
+ if (!file_options.output_list_file.empty()) {
+ // Generate output list. This is just a simple text file placed in a
+ // deterministic location which lists the .java files being generated.
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> srclist_raw_output(
+ context->Open(file_options.output_list_file));
+ io::Printer srclist_printer(srclist_raw_output.get(), '$');
+ for (int i = 0; i < all_files.size(); i++) {
+ srclist_printer.Print("$filename$\n", "filename", all_files[i]);
+ }
+ }
+
+ if (!file_options.annotation_list_file.empty()) {
+ // Generate output list. This is just a simple text file placed in a
+ // deterministic location which lists the .java files being generated.
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> annotation_list_raw_output(
+ context->Open(file_options.annotation_list_file));
+ io::Printer annotation_list_printer(annotation_list_raw_output.get(), '$');
+ for (int i = 0; i < all_annotations.size(); i++) {
+ annotation_list_printer.Print("$filename$\n", "filename",
+ all_annotations[i]);
+ }
+ }
+
+ return true;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.h
new file mode 100644
index 0000000000..47f76be983
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator.h
@@ -0,0 +1,72 @@
+// 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.
+//
+// Generates Java code for a given .proto file.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_GENERATOR_H__
+
+#include <string>
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+// CodeGenerator implementation which generates Java code. If you create your
+// own protocol compiler binary and you want it to support Java output, you
+// can do so by registering an instance of this CodeGenerator with the
+// CommandLineInterface in your main() function.
+class LIBPROTOC_EXPORT JavaGenerator : public CodeGenerator {
+ public:
+ JavaGenerator();
+ ~JavaGenerator();
+
+ // implements CodeGenerator ----------------------------------------
+ bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(JavaGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.cc
new file mode 100644
index 0000000000..3218b41076
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.cc
@@ -0,0 +1,87 @@
+// 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: liujisi@google.com (Pherl Liu)
+
+#include <google/protobuf/compiler/java/java_generator_factory.h>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_enum_field.h>
+#include <google/protobuf/compiler/java/java_extension.h>
+#include <google/protobuf/compiler/java/java_extension_lite.h>
+#include <google/protobuf/compiler/java/java_field.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_message.h>
+#include <google/protobuf/compiler/java/java_message_lite.h>
+#include <google/protobuf/compiler/java/java_service.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+GeneratorFactory::GeneratorFactory() {}
+GeneratorFactory::~GeneratorFactory() {}
+
+// ===================================================================
+
+ImmutableGeneratorFactory::ImmutableGeneratorFactory(
+ Context* context) : context_(context) {
+}
+ImmutableGeneratorFactory::~ImmutableGeneratorFactory() {}
+
+MessageGenerator* ImmutableGeneratorFactory::NewMessageGenerator(
+ const Descriptor* descriptor) const {
+ if (HasDescriptorMethods(descriptor, context_->EnforceLite())) {
+ return new ImmutableMessageGenerator(descriptor, context_);
+ } else {
+ return new ImmutableMessageLiteGenerator(descriptor, context_);
+ }
+}
+
+ExtensionGenerator* ImmutableGeneratorFactory::NewExtensionGenerator(
+ const FieldDescriptor* descriptor) const {
+ if (HasDescriptorMethods(descriptor->file(), context_->EnforceLite())) {
+ return new ImmutableExtensionGenerator(descriptor, context_);
+ } else {
+ return new ImmutableExtensionLiteGenerator(descriptor, context_);
+ }
+}
+
+ServiceGenerator* ImmutableGeneratorFactory::NewServiceGenerator(
+ const ServiceDescriptor* descriptor) const {
+ return new ImmutableServiceGenerator(descriptor, context_);
+}
+
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.h
new file mode 100644
index 0000000000..55365a9d4e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_generator_factory.h
@@ -0,0 +1,101 @@
+// 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: liujisi@google.com (Pherl Liu)
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_GENERATOR_FACTORY_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_GENERATOR_FACTORY_H__
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+ class FieldDescriptor; // descriptor.h
+ class Descriptor; // descriptor.h
+ class ServiceDescriptor; // descriptor.h
+ namespace compiler {
+ namespace java {
+ class MessageGenerator; // message.h
+ class ExtensionGenerator; // extension.h
+ class ServiceGenerator; // service.h
+ class Context; // context.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class GeneratorFactory {
+ public:
+ GeneratorFactory();
+ virtual ~GeneratorFactory();
+
+ virtual MessageGenerator* NewMessageGenerator(
+ const Descriptor* descriptor) const = 0;
+
+ virtual ExtensionGenerator* NewExtensionGenerator(
+ const FieldDescriptor* descriptor) const = 0;
+
+ virtual ServiceGenerator* NewServiceGenerator(
+ const ServiceDescriptor* descriptor) const = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(GeneratorFactory);
+};
+
+// Factory that creates generators for immutable-default messages.
+class ImmutableGeneratorFactory : public GeneratorFactory {
+ public:
+ ImmutableGeneratorFactory(Context* context);
+ virtual ~ImmutableGeneratorFactory();
+
+ virtual MessageGenerator* NewMessageGenerator(
+ const Descriptor* descriptor) const;
+
+ virtual ExtensionGenerator* NewExtensionGenerator(
+ const FieldDescriptor* descriptor) const;
+
+ virtual ServiceGenerator* NewServiceGenerator(
+ const ServiceDescriptor* descriptor) const;
+
+ private:
+ Context* context_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableGeneratorFactory);
+};
+
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_GENERATOR_FACTORY_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.cc
new file mode 100644
index 0000000000..c31df2651f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.cc
@@ -0,0 +1,776 @@
+// 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.
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <limits>
+#include <vector>
+
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+const char kThickSeparator[] =
+ "// ===================================================================\n";
+const char kThinSeparator[] =
+ "// -------------------------------------------------------------------\n";
+
+namespace {
+
+const char* kDefaultPackage = "";
+
+// Names that should be avoided as field names.
+// Using them will cause the compiler to generate accessors whose names are
+// colliding with methods defined in base classes.
+const char* kForbiddenWordList[] = {
+ // message base class:
+ "cached_size", "serialized_size",
+ // java.lang.Object:
+ "class",
+};
+
+bool IsForbidden(const string& field_name) {
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(kForbiddenWordList); ++i) {
+ if (field_name == kForbiddenWordList[i]) {
+ return true;
+ }
+ }
+ return false;
+}
+
+string FieldName(const FieldDescriptor* field) {
+ string field_name;
+ // Groups are hacky: The name of the field is just the lower-cased name
+ // of the group type. In Java, though, we would like to retain the original
+ // capitalization of the type name.
+ if (GetType(field) == FieldDescriptor::TYPE_GROUP) {
+ field_name = field->message_type()->name();
+ } else {
+ field_name = field->name();
+ }
+ if (IsForbidden(field_name)) {
+ // Append a trailing "#" to indicate that the name should be decorated to
+ // avoid collision with other names.
+ field_name += "#";
+ }
+ return field_name;
+}
+
+
+} // namespace
+
+void PrintGeneratedAnnotation(io::Printer* printer, char delimiter,
+ const string& annotation_file) {
+ if (annotation_file.empty()) {
+ return;
+ }
+ string ptemplate =
+ "@javax.annotation.Generated(value=\"protoc\", comments=\"annotations:";
+ ptemplate.push_back(delimiter);
+ ptemplate.append("annotation_file");
+ ptemplate.push_back(delimiter);
+ ptemplate.append("\")\n");
+ printer->Print(ptemplate.c_str(), "annotation_file", annotation_file);
+}
+
+string UnderscoresToCamelCase(const string& input, bool cap_next_letter) {
+ string result;
+ // Note: I distrust ctype.h due to locales.
+ for (int i = 0; i < input.size(); i++) {
+ if ('a' <= input[i] && input[i] <= 'z') {
+ if (cap_next_letter) {
+ result += input[i] + ('A' - 'a');
+ } else {
+ result += input[i];
+ }
+ cap_next_letter = false;
+ } else if ('A' <= input[i] && input[i] <= 'Z') {
+ if (i == 0 && !cap_next_letter) {
+ // Force first letter to lower-case unless explicitly told to
+ // capitalize it.
+ result += input[i] + ('a' - 'A');
+ } else {
+ // Capital letters after the first are left as-is.
+ result += input[i];
+ }
+ cap_next_letter = false;
+ } else if ('0' <= input[i] && input[i] <= '9') {
+ result += input[i];
+ cap_next_letter = true;
+ } else {
+ cap_next_letter = true;
+ }
+ }
+ // Add a trailing "_" if the name should be altered.
+ if (input[input.size() - 1] == '#') {
+ result += '_';
+ }
+ return result;
+}
+
+string UnderscoresToCamelCase(const FieldDescriptor* field) {
+ return UnderscoresToCamelCase(FieldName(field), false);
+}
+
+string UnderscoresToCapitalizedCamelCase(const FieldDescriptor* field) {
+ return UnderscoresToCamelCase(FieldName(field), true);
+}
+
+string UnderscoresToCamelCase(const MethodDescriptor* method) {
+ return UnderscoresToCamelCase(method->name(), false);
+}
+
+string UniqueFileScopeIdentifier(const Descriptor* descriptor) {
+ return "static_" + StringReplace(descriptor->full_name(), ".", "_", true);
+}
+
+string StripProto(const string& filename) {
+ if (HasSuffixString(filename, ".protodevel")) {
+ return StripSuffixString(filename, ".protodevel");
+ } else {
+ return StripSuffixString(filename, ".proto");
+ }
+}
+
+string FileClassName(const FileDescriptor* file, bool immutable) {
+ ClassNameResolver name_resolver;
+ return name_resolver.GetFileClassName(file, immutable);
+}
+
+string FileJavaPackage(const FileDescriptor* file, bool immutable) {
+ string result;
+
+ if (file->options().has_java_package()) {
+ result = file->options().java_package();
+ } else {
+ result = kDefaultPackage;
+ if (!file->package().empty()) {
+ if (!result.empty()) result += '.';
+ result += file->package();
+ }
+ }
+
+ return result;
+}
+
+string JavaPackageToDir(string package_name) {
+ string package_dir =
+ StringReplace(package_name, ".", "/", true);
+ if (!package_dir.empty()) package_dir += "/";
+ return package_dir;
+}
+
+// TODO(xiaofeng): This function is only kept for it's publicly referenced.
+// It should be removed after mutable API up-integration.
+string ToJavaName(const string& full_name,
+ const FileDescriptor* file) {
+ string result;
+ if (file->options().java_multiple_files()) {
+ result = FileJavaPackage(file);
+ } else {
+ result = ClassName(file);
+ }
+ if (!result.empty()) {
+ result += '.';
+ }
+ if (file->package().empty()) {
+ result += full_name;
+ } else {
+ // Strip the proto package from full_name since we've replaced it with
+ // the Java package.
+ result += full_name.substr(file->package().size() + 1);
+ }
+ return result;
+}
+
+string ClassName(const Descriptor* descriptor) {
+ ClassNameResolver name_resolver;
+ return name_resolver.GetClassName(descriptor, true);
+}
+
+string ClassName(const EnumDescriptor* descriptor) {
+ ClassNameResolver name_resolver;
+ return name_resolver.GetClassName(descriptor, true);
+}
+
+string ClassName(const ServiceDescriptor* descriptor) {
+ ClassNameResolver name_resolver;
+ return name_resolver.GetClassName(descriptor, true);
+}
+
+string ClassName(const FileDescriptor* descriptor) {
+ ClassNameResolver name_resolver;
+ return name_resolver.GetClassName(descriptor, true);
+}
+
+string ExtraMessageInterfaces(const Descriptor* descriptor) {
+ string interfaces = "// @@protoc_insertion_point(message_implements:"
+ + descriptor->full_name() + ")";
+ return interfaces;
+}
+
+
+string ExtraBuilderInterfaces(const Descriptor* descriptor) {
+ string interfaces = "// @@protoc_insertion_point(builder_implements:"
+ + descriptor->full_name() + ")";
+ return interfaces;
+}
+
+string ExtraMessageOrBuilderInterfaces(const Descriptor* descriptor) {
+ string interfaces = "// @@protoc_insertion_point(interface_extends:"
+ + descriptor->full_name() + ")";
+ return interfaces;
+}
+
+string FieldConstantName(const FieldDescriptor *field) {
+ string name = field->name() + "_FIELD_NUMBER";
+ UpperString(&name);
+ return name;
+}
+
+FieldDescriptor::Type GetType(const FieldDescriptor* field) {
+ return field->type();
+}
+
+JavaType GetJavaType(const FieldDescriptor* field) {
+ switch (GetType(field)) {
+ case FieldDescriptor::TYPE_INT32:
+ case FieldDescriptor::TYPE_UINT32:
+ case FieldDescriptor::TYPE_SINT32:
+ case FieldDescriptor::TYPE_FIXED32:
+ case FieldDescriptor::TYPE_SFIXED32:
+ return JAVATYPE_INT;
+
+ case FieldDescriptor::TYPE_INT64:
+ case FieldDescriptor::TYPE_UINT64:
+ case FieldDescriptor::TYPE_SINT64:
+ case FieldDescriptor::TYPE_FIXED64:
+ case FieldDescriptor::TYPE_SFIXED64:
+ return JAVATYPE_LONG;
+
+ case FieldDescriptor::TYPE_FLOAT:
+ return JAVATYPE_FLOAT;
+
+ case FieldDescriptor::TYPE_DOUBLE:
+ return JAVATYPE_DOUBLE;
+
+ case FieldDescriptor::TYPE_BOOL:
+ return JAVATYPE_BOOLEAN;
+
+ case FieldDescriptor::TYPE_STRING:
+ return JAVATYPE_STRING;
+
+ case FieldDescriptor::TYPE_BYTES:
+ return JAVATYPE_BYTES;
+
+ case FieldDescriptor::TYPE_ENUM:
+ return JAVATYPE_ENUM;
+
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_MESSAGE:
+ return JAVATYPE_MESSAGE;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return JAVATYPE_INT;
+}
+
+const char* PrimitiveTypeName(JavaType type) {
+ switch (type) {
+ case JAVATYPE_INT : return "int";
+ case JAVATYPE_LONG : return "long";
+ case JAVATYPE_FLOAT : return "float";
+ case JAVATYPE_DOUBLE : return "double";
+ case JAVATYPE_BOOLEAN: return "boolean";
+ case JAVATYPE_STRING : return "java.lang.String";
+ case JAVATYPE_BYTES : return "com.google.protobuf.ByteString";
+ case JAVATYPE_ENUM : return NULL;
+ case JAVATYPE_MESSAGE: return NULL;
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+const char* BoxedPrimitiveTypeName(JavaType type) {
+ switch (type) {
+ case JAVATYPE_INT : return "java.lang.Integer";
+ case JAVATYPE_LONG : return "java.lang.Long";
+ case JAVATYPE_FLOAT : return "java.lang.Float";
+ case JAVATYPE_DOUBLE : return "java.lang.Double";
+ case JAVATYPE_BOOLEAN: return "java.lang.Boolean";
+ case JAVATYPE_STRING : return "java.lang.String";
+ case JAVATYPE_BYTES : return "com.google.protobuf.ByteString";
+ case JAVATYPE_ENUM : return NULL;
+ case JAVATYPE_MESSAGE: return NULL;
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+const char* FieldTypeName(FieldDescriptor::Type field_type) {
+ switch (field_type) {
+ case FieldDescriptor::TYPE_INT32 : return "INT32";
+ case FieldDescriptor::TYPE_UINT32 : return "UINT32";
+ case FieldDescriptor::TYPE_SINT32 : return "SINT32";
+ case FieldDescriptor::TYPE_FIXED32 : return "FIXED32";
+ case FieldDescriptor::TYPE_SFIXED32: return "SFIXED32";
+ case FieldDescriptor::TYPE_INT64 : return "INT64";
+ case FieldDescriptor::TYPE_UINT64 : return "UINT64";
+ case FieldDescriptor::TYPE_SINT64 : return "SINT64";
+ case FieldDescriptor::TYPE_FIXED64 : return "FIXED64";
+ case FieldDescriptor::TYPE_SFIXED64: return "SFIXED64";
+ case FieldDescriptor::TYPE_FLOAT : return "FLOAT";
+ case FieldDescriptor::TYPE_DOUBLE : return "DOUBLE";
+ case FieldDescriptor::TYPE_BOOL : return "BOOL";
+ case FieldDescriptor::TYPE_STRING : return "STRING";
+ case FieldDescriptor::TYPE_BYTES : return "BYTES";
+ case FieldDescriptor::TYPE_ENUM : return "ENUM";
+ case FieldDescriptor::TYPE_GROUP : return "GROUP";
+ case FieldDescriptor::TYPE_MESSAGE : return "MESSAGE";
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+bool AllAscii(const string& text) {
+ for (int i = 0; i < text.size(); i++) {
+ if ((text[i] & 0x80) != 0) {
+ return false;
+ }
+ }
+ return true;
+}
+
+string DefaultValue(const FieldDescriptor* field, bool immutable,
+ ClassNameResolver* name_resolver) {
+ // Switch on CppType since we need to know which default_value_* method
+ // of FieldDescriptor to call.
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return SimpleItoa(field->default_value_int32());
+ case FieldDescriptor::CPPTYPE_UINT32:
+ // Need to print as a signed int since Java has no unsigned.
+ return SimpleItoa(static_cast<int32>(field->default_value_uint32()));
+ case FieldDescriptor::CPPTYPE_INT64:
+ return SimpleItoa(field->default_value_int64()) + "L";
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return SimpleItoa(static_cast<int64>(field->default_value_uint64())) +
+ "L";
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value = field->default_value_double();
+ if (value == numeric_limits<double>::infinity()) {
+ return "Double.POSITIVE_INFINITY";
+ } else if (value == -numeric_limits<double>::infinity()) {
+ return "Double.NEGATIVE_INFINITY";
+ } else if (value != value) {
+ return "Double.NaN";
+ } else {
+ return SimpleDtoa(value) + "D";
+ }
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ float value = field->default_value_float();
+ if (value == numeric_limits<float>::infinity()) {
+ return "Float.POSITIVE_INFINITY";
+ } else if (value == -numeric_limits<float>::infinity()) {
+ return "Float.NEGATIVE_INFINITY";
+ } else if (value != value) {
+ return "Float.NaN";
+ } else {
+ return SimpleFtoa(value) + "F";
+ }
+ }
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field->default_value_bool() ? "true" : "false";
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (GetType(field) == FieldDescriptor::TYPE_BYTES) {
+ if (field->has_default_value()) {
+ // See comments in Internal.java for gory details.
+ return strings::Substitute(
+ "com.google.protobuf.Internal.bytesDefaultValue(\"$0\")",
+ CEscape(field->default_value_string()));
+ } else {
+ return "com.google.protobuf.ByteString.EMPTY";
+ }
+ } else {
+ if (AllAscii(field->default_value_string())) {
+ // All chars are ASCII. In this case CEscape() works fine.
+ return "\"" + CEscape(field->default_value_string()) + "\"";
+ } else {
+ // See comments in Internal.java for gory details.
+ return strings::Substitute(
+ "com.google.protobuf.Internal.stringDefaultValue(\"$0\")",
+ CEscape(field->default_value_string()));
+ }
+ }
+
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return name_resolver->GetClassName(field->enum_type(), immutable) + "." +
+ field->default_value_enum()->name();
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return name_resolver->GetClassName(field->message_type(), immutable) +
+ ".getDefaultInstance()";
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return "";
+}
+
+bool IsDefaultValueJavaDefault(const FieldDescriptor* field) {
+ // Switch on CppType since we need to know which default_value_* method
+ // of FieldDescriptor to call.
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return field->default_value_int32() == 0;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return field->default_value_uint32() == 0;
+ case FieldDescriptor::CPPTYPE_INT64:
+ return field->default_value_int64() == 0L;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return field->default_value_uint64() == 0L;
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return field->default_value_double() == 0.0;
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return field->default_value_float() == 0.0;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field->default_value_bool() == false;
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return field->default_value_enum()->number() == 0;
+ case FieldDescriptor::CPPTYPE_STRING:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return false;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return false;
+}
+
+bool IsByteStringWithCustomDefaultValue(const FieldDescriptor* field) {
+ return GetJavaType(field) == JAVATYPE_BYTES &&
+ field->default_value_string() != "";
+}
+
+const char* bit_masks[] = {
+ "0x00000001",
+ "0x00000002",
+ "0x00000004",
+ "0x00000008",
+ "0x00000010",
+ "0x00000020",
+ "0x00000040",
+ "0x00000080",
+
+ "0x00000100",
+ "0x00000200",
+ "0x00000400",
+ "0x00000800",
+ "0x00001000",
+ "0x00002000",
+ "0x00004000",
+ "0x00008000",
+
+ "0x00010000",
+ "0x00020000",
+ "0x00040000",
+ "0x00080000",
+ "0x00100000",
+ "0x00200000",
+ "0x00400000",
+ "0x00800000",
+
+ "0x01000000",
+ "0x02000000",
+ "0x04000000",
+ "0x08000000",
+ "0x10000000",
+ "0x20000000",
+ "0x40000000",
+ "0x80000000",
+};
+
+string GetBitFieldName(int index) {
+ string varName = "bitField";
+ varName += SimpleItoa(index);
+ varName += "_";
+ return varName;
+}
+
+string GetBitFieldNameForBit(int bitIndex) {
+ return GetBitFieldName(bitIndex / 32);
+}
+
+namespace {
+
+string GenerateGetBitInternal(const string& prefix, int bitIndex) {
+ string varName = prefix + GetBitFieldNameForBit(bitIndex);
+ int bitInVarIndex = bitIndex % 32;
+
+ string mask = bit_masks[bitInVarIndex];
+ string result = "((" + varName + " & " + mask + ") == " + mask + ")";
+ return result;
+}
+
+string GenerateSetBitInternal(const string& prefix, int bitIndex) {
+ string varName = prefix + GetBitFieldNameForBit(bitIndex);
+ int bitInVarIndex = bitIndex % 32;
+
+ string mask = bit_masks[bitInVarIndex];
+ string result = varName + " |= " + mask;
+ return result;
+}
+
+} // namespace
+
+string GenerateGetBit(int bitIndex) {
+ return GenerateGetBitInternal("", bitIndex);
+}
+
+string GenerateSetBit(int bitIndex) {
+ return GenerateSetBitInternal("", bitIndex);
+}
+
+string GenerateClearBit(int bitIndex) {
+ string varName = GetBitFieldNameForBit(bitIndex);
+ int bitInVarIndex = bitIndex % 32;
+
+ string mask = bit_masks[bitInVarIndex];
+ string result = varName + " = (" + varName + " & ~" + mask + ")";
+ return result;
+}
+
+string GenerateGetBitFromLocal(int bitIndex) {
+ return GenerateGetBitInternal("from_", bitIndex);
+}
+
+string GenerateSetBitToLocal(int bitIndex) {
+ return GenerateSetBitInternal("to_", bitIndex);
+}
+
+string GenerateGetBitMutableLocal(int bitIndex) {
+ return GenerateGetBitInternal("mutable_", bitIndex);
+}
+
+string GenerateSetBitMutableLocal(int bitIndex) {
+ return GenerateSetBitInternal("mutable_", bitIndex);
+}
+
+bool IsReferenceType(JavaType type) {
+ switch (type) {
+ case JAVATYPE_INT : return false;
+ case JAVATYPE_LONG : return false;
+ case JAVATYPE_FLOAT : return false;
+ case JAVATYPE_DOUBLE : return false;
+ case JAVATYPE_BOOLEAN: return false;
+ case JAVATYPE_STRING : return true;
+ case JAVATYPE_BYTES : return true;
+ case JAVATYPE_ENUM : return true;
+ case JAVATYPE_MESSAGE: return true;
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return false;
+}
+
+const char* GetCapitalizedType(const FieldDescriptor* field, bool immutable) {
+ switch (GetType(field)) {
+ case FieldDescriptor::TYPE_INT32 : return "Int32";
+ case FieldDescriptor::TYPE_UINT32 : return "UInt32";
+ case FieldDescriptor::TYPE_SINT32 : return "SInt32";
+ case FieldDescriptor::TYPE_FIXED32 : return "Fixed32";
+ case FieldDescriptor::TYPE_SFIXED32: return "SFixed32";
+ case FieldDescriptor::TYPE_INT64 : return "Int64";
+ case FieldDescriptor::TYPE_UINT64 : return "UInt64";
+ case FieldDescriptor::TYPE_SINT64 : return "SInt64";
+ case FieldDescriptor::TYPE_FIXED64 : return "Fixed64";
+ case FieldDescriptor::TYPE_SFIXED64: return "SFixed64";
+ case FieldDescriptor::TYPE_FLOAT : return "Float";
+ case FieldDescriptor::TYPE_DOUBLE : return "Double";
+ case FieldDescriptor::TYPE_BOOL : return "Bool";
+ case FieldDescriptor::TYPE_STRING : return "String";
+ case FieldDescriptor::TYPE_BYTES : {
+ return "Bytes";
+ }
+ case FieldDescriptor::TYPE_ENUM : return "Enum";
+ case FieldDescriptor::TYPE_GROUP : return "Group";
+ case FieldDescriptor::TYPE_MESSAGE : return "Message";
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+// For encodings with fixed sizes, returns that size in bytes. Otherwise
+// returns -1.
+int FixedSize(FieldDescriptor::Type type) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32 : return -1;
+ case FieldDescriptor::TYPE_INT64 : return -1;
+ case FieldDescriptor::TYPE_UINT32 : return -1;
+ case FieldDescriptor::TYPE_UINT64 : return -1;
+ case FieldDescriptor::TYPE_SINT32 : return -1;
+ case FieldDescriptor::TYPE_SINT64 : return -1;
+ case FieldDescriptor::TYPE_FIXED32 : return WireFormatLite::kFixed32Size;
+ case FieldDescriptor::TYPE_FIXED64 : return WireFormatLite::kFixed64Size;
+ case FieldDescriptor::TYPE_SFIXED32: return WireFormatLite::kSFixed32Size;
+ case FieldDescriptor::TYPE_SFIXED64: return WireFormatLite::kSFixed64Size;
+ case FieldDescriptor::TYPE_FLOAT : return WireFormatLite::kFloatSize;
+ case FieldDescriptor::TYPE_DOUBLE : return WireFormatLite::kDoubleSize;
+
+ case FieldDescriptor::TYPE_BOOL : return WireFormatLite::kBoolSize;
+ case FieldDescriptor::TYPE_ENUM : return -1;
+
+ case FieldDescriptor::TYPE_STRING : return -1;
+ case FieldDescriptor::TYPE_BYTES : return -1;
+ case FieldDescriptor::TYPE_GROUP : return -1;
+ case FieldDescriptor::TYPE_MESSAGE : return -1;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return -1;
+}
+
+// Sort the fields of the given Descriptor by number into a new[]'d array
+// and return it. The caller should delete the returned array.
+const FieldDescriptor** SortFieldsByNumber(const Descriptor* descriptor) {
+ const FieldDescriptor** fields =
+ new const FieldDescriptor*[descriptor->field_count()];
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ fields[i] = descriptor->field(i);
+ }
+ std::sort(fields, fields + descriptor->field_count(),
+ FieldOrderingByNumber());
+ return fields;
+}
+
+// Returns true if the message type has any required fields. If it doesn't,
+// we can optimize out calls to its isInitialized() method.
+//
+// already_seen is used to avoid checking the same type multiple times
+// (and also to protect against recursion).
+bool HasRequiredFields(
+ const Descriptor* type,
+ hash_set<const Descriptor*>* already_seen) {
+ if (already_seen->count(type) > 0) {
+ // The type is already in cache. This means that either:
+ // a. The type has no required fields.
+ // b. We are in the midst of checking if the type has required fields,
+ // somewhere up the stack. In this case, we know that if the type
+ // has any required fields, they'll be found when we return to it,
+ // and the whole call to HasRequiredFields() will return true.
+ // Therefore, we don't have to check if this type has required fields
+ // here.
+ return false;
+ }
+ already_seen->insert(type);
+
+ // If the type has extensions, an extension with message type could contain
+ // required fields, so we have to be conservative and assume such an
+ // extension exists.
+ if (type->extension_range_count() > 0) return true;
+
+ for (int i = 0; i < type->field_count(); i++) {
+ const FieldDescriptor* field = type->field(i);
+ if (field->is_required()) {
+ return true;
+ }
+ if (GetJavaType(field) == JAVATYPE_MESSAGE) {
+ if (HasRequiredFields(field->message_type(), already_seen)) {
+ return true;
+ }
+ }
+ }
+
+ return false;
+}
+
+bool HasRequiredFields(const Descriptor* type) {
+ hash_set<const Descriptor*> already_seen;
+ return HasRequiredFields(type, &already_seen);
+}
+
+bool HasRepeatedFields(const Descriptor* descriptor) {
+ for (int i = 0; i < descriptor->field_count(); ++i) {
+ const FieldDescriptor* field = descriptor->field(i);
+ if (field->is_repeated()) {
+ return true;
+ }
+ }
+ return false;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.h
new file mode 100644
index 0000000000..829ec3d763
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_helpers.h
@@ -0,0 +1,396 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_HELPERS_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_HELPERS_H__
+
+#include <string>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+// Commonly-used separator comments. Thick is a line of '=', thin is a line
+// of '-'.
+extern const char kThickSeparator[];
+extern const char kThinSeparator[];
+
+// If annotation_file is non-empty, prints a javax.annotation.Generated
+// annotation to the given Printer. annotation_file will be referenced in the
+// annotation's comments field. delimiter should be the Printer's delimiter
+// character. annotation_file will be included verbatim into a Java literal
+// string, so it should not contain quotes or invalid Java escape sequences;
+// however, these are unlikely to appear in practice, as the value of
+// annotation_file should be generated from the filename of the source file
+// being annotated (which in turn must be a Java identifier plus ".java").
+void PrintGeneratedAnnotation(io::Printer* printer, char delimiter = '$',
+ const string& annotation_file = "");
+
+// Converts a name to camel-case. If cap_first_letter is true, capitalize the
+// first letter.
+string UnderscoresToCamelCase(const string& name, bool cap_first_letter);
+// Converts the field's name to camel-case, e.g. "foo_bar_baz" becomes
+// "fooBarBaz" or "FooBarBaz", respectively.
+string UnderscoresToCamelCase(const FieldDescriptor* field);
+string UnderscoresToCapitalizedCamelCase(const FieldDescriptor* field);
+
+// Similar, but for method names. (Typically, this merely has the effect
+// of lower-casing the first letter of the name.)
+string UnderscoresToCamelCase(const MethodDescriptor* method);
+
+// Get an identifier that uniquely identifies this type within the file.
+// This is used to declare static variables related to this type at the
+// outermost file scope.
+string UniqueFileScopeIdentifier(const Descriptor* descriptor);
+
+// Strips ".proto" or ".protodevel" from the end of a filename.
+string StripProto(const string& filename);
+
+// Gets the unqualified class name for the file. For each .proto file, there
+// will be one Java class containing all the immutable messages and another
+// Java class containing all the mutable messages.
+// TODO(xiaofeng): remove the default value after updating client code.
+string FileClassName(const FileDescriptor* file, bool immutable = true);
+
+// Returns the file's Java package name.
+string FileJavaPackage(const FileDescriptor* file, bool immutable = true);
+
+// Returns output directory for the given package name.
+string JavaPackageToDir(string package_name);
+
+// Converts the given fully-qualified name in the proto namespace to its
+// fully-qualified name in the Java namespace, given that it is in the given
+// file.
+// TODO(xiaofeng): this method is deprecated and should be removed in the
+// future.
+string ToJavaName(const string& full_name,
+ const FileDescriptor* file);
+
+// TODO(xiaofeng): the following methods are kept for they are exposed
+// publicly in //google/protobuf/compiler/java/names.h. They return
+// immutable names only and should be removed after mutable API is
+// integrated into google3.
+string ClassName(const Descriptor* descriptor);
+string ClassName(const EnumDescriptor* descriptor);
+string ClassName(const ServiceDescriptor* descriptor);
+string ClassName(const FileDescriptor* descriptor);
+
+// Comma-separate list of option-specified interfaces implemented by the
+// Message, to follow the "implements" declaration of the Message definition.
+string ExtraMessageInterfaces(const Descriptor* descriptor);
+// Comma-separate list of option-specified interfaces implemented by the
+// MutableMessage, to follow the "implements" declaration of the MutableMessage
+// definition.
+string ExtraMutableMessageInterfaces(const Descriptor* descriptor);
+// Comma-separate list of option-specified interfaces implemented by the
+// Builder, to follow the "implements" declaration of the Builder definition.
+string ExtraBuilderInterfaces(const Descriptor* descriptor);
+// Comma-separate list of option-specified interfaces extended by the
+// MessageOrBuilder, to follow the "extends" declaration of the
+// MessageOrBuilder definition.
+string ExtraMessageOrBuilderInterfaces(const Descriptor* descriptor);
+
+// Get the unqualified Java class name for mutable messages. i.e. without
+// package or outer classnames.
+inline string ShortMutableJavaClassName(const Descriptor* descriptor) {
+ return descriptor->name();
+}
+
+
+// Whether we should generate multiple java files for messages.
+inline bool MultipleJavaFiles(
+ const FileDescriptor* descriptor, bool immutable) {
+ return descriptor->options().java_multiple_files();
+}
+
+// Returns true if `descriptor` will be written to its own .java file.
+// `immutable` should be set to true if we're generating for the immutable API.
+template <typename Descriptor>
+bool IsOwnFile(const Descriptor* descriptor, bool immutable) {
+ return descriptor->containing_type() == NULL &&
+ MultipleJavaFiles(descriptor->file(), immutable);
+}
+
+template <>
+inline bool IsOwnFile(const ServiceDescriptor* descriptor, bool immutable) {
+ return MultipleJavaFiles(descriptor->file(), immutable);
+}
+
+// If `descriptor` describes an object with its own .java file,
+// returns the name (relative to that .java file) of the file that stores
+// annotation data for that descriptor. `suffix` is usually empty, but may
+// (e.g.) be "OrBuilder" for some generated interfaces.
+template <typename Descriptor>
+string AnnotationFileName(const Descriptor* descriptor, const string& suffix) {
+ return descriptor->name() + suffix + ".java.pb.meta";
+}
+
+template <typename Descriptor>
+void MaybePrintGeneratedAnnotation(Context* context, io::Printer* printer,
+ Descriptor* descriptor, bool immutable,
+ const string& suffix = "") {
+ if (context->options().annotate_code && IsOwnFile(descriptor, immutable)) {
+ PrintGeneratedAnnotation(printer, '$',
+ AnnotationFileName(descriptor, suffix));
+ }
+}
+
+// Get the unqualified name that should be used for a field's field
+// number constant.
+string FieldConstantName(const FieldDescriptor *field);
+
+// Returns the type of the FieldDescriptor.
+// This does nothing interesting for the open source release, but is used for
+// hacks that improve compatibility with version 1 protocol buffers at Google.
+FieldDescriptor::Type GetType(const FieldDescriptor* field);
+
+enum JavaType {
+ JAVATYPE_INT,
+ JAVATYPE_LONG,
+ JAVATYPE_FLOAT,
+ JAVATYPE_DOUBLE,
+ JAVATYPE_BOOLEAN,
+ JAVATYPE_STRING,
+ JAVATYPE_BYTES,
+ JAVATYPE_ENUM,
+ JAVATYPE_MESSAGE
+};
+
+JavaType GetJavaType(const FieldDescriptor* field);
+
+const char* PrimitiveTypeName(JavaType type);
+
+// Get the fully-qualified class name for a boxed primitive type, e.g.
+// "java.lang.Integer" for JAVATYPE_INT. Returns NULL for enum and message
+// types.
+const char* BoxedPrimitiveTypeName(JavaType type);
+
+// Get the name of the java enum constant representing this type. E.g.,
+// "INT32" for FieldDescriptor::TYPE_INT32. The enum constant's full
+// name is "com.google.protobuf.WireFormat.FieldType.INT32".
+const char* FieldTypeName(const FieldDescriptor::Type field_type);
+
+class ClassNameResolver;
+string DefaultValue(const FieldDescriptor* field, bool immutable,
+ ClassNameResolver* name_resolver);
+inline string ImmutableDefaultValue(const FieldDescriptor* field,
+ ClassNameResolver* name_resolver) {
+ return DefaultValue(field, true, name_resolver);
+}
+bool IsDefaultValueJavaDefault(const FieldDescriptor* field);
+bool IsByteStringWithCustomDefaultValue(const FieldDescriptor* field);
+
+// Does this message class have descriptor and reflection methods?
+inline bool HasDescriptorMethods(const Descriptor* descriptor,
+ bool enforce_lite) {
+ return !enforce_lite &&
+ descriptor->file()->options().optimize_for() !=
+ FileOptions::LITE_RUNTIME;
+}
+inline bool HasDescriptorMethods(const EnumDescriptor* descriptor,
+ bool enforce_lite) {
+ return !enforce_lite &&
+ descriptor->file()->options().optimize_for() !=
+ FileOptions::LITE_RUNTIME;
+}
+inline bool HasDescriptorMethods(const FileDescriptor* descriptor,
+ bool enforce_lite) {
+ return !enforce_lite &&
+ descriptor->options().optimize_for() != FileOptions::LITE_RUNTIME;
+}
+
+// Should we generate generic services for this file?
+inline bool HasGenericServices(const FileDescriptor *file, bool enforce_lite) {
+ return file->service_count() > 0 &&
+ HasDescriptorMethods(file, enforce_lite) &&
+ file->options().java_generic_services();
+}
+
+inline bool IsLazy(const FieldDescriptor* descriptor, bool enforce_lite) {
+ // Currently, the proto-lite version supports lazy field.
+ // TODO(niwasaki): Support lazy fields also for other proto runtimes.
+ if (HasDescriptorMethods(descriptor->file(), enforce_lite)) {
+ return false;
+ }
+ return descriptor->options().lazy();
+}
+
+// Methods for shared bitfields.
+
+// Gets the name of the shared bitfield for the given index.
+string GetBitFieldName(int index);
+
+// Gets the name of the shared bitfield for the given bit index.
+// Effectively, GetBitFieldName(bitIndex / 32)
+string GetBitFieldNameForBit(int bitIndex);
+
+// Generates the java code for the expression that returns the boolean value
+// of the bit of the shared bitfields for the given bit index.
+// Example: "((bitField1_ & 0x04) == 0x04)"
+string GenerateGetBit(int bitIndex);
+
+// Generates the java code for the expression that sets the bit of the shared
+// bitfields for the given bit index.
+// Example: "bitField1_ = (bitField1_ | 0x04)"
+string GenerateSetBit(int bitIndex);
+
+// Generates the java code for the expression that clears the bit of the shared
+// bitfields for the given bit index.
+// Example: "bitField1_ = (bitField1_ & ~0x04)"
+string GenerateClearBit(int bitIndex);
+
+// Does the same as GenerateGetBit but operates on the bit field on a local
+// variable. This is used by the builder to copy the value in the builder to
+// the message.
+// Example: "((from_bitField1_ & 0x04) == 0x04)"
+string GenerateGetBitFromLocal(int bitIndex);
+
+// Does the same as GenerateSetBit but operates on the bit field on a local
+// variable. This is used by the builder to copy the value in the builder to
+// the message.
+// Example: "to_bitField1_ = (to_bitField1_ | 0x04)"
+string GenerateSetBitToLocal(int bitIndex);
+
+// Does the same as GenerateGetBit but operates on the bit field on a local
+// variable. This is used by the parsing constructor to record if a repeated
+// field is mutable.
+// Example: "((mutable_bitField1_ & 0x04) == 0x04)"
+string GenerateGetBitMutableLocal(int bitIndex);
+
+// Does the same as GenerateSetBit but operates on the bit field on a local
+// variable. This is used by the parsing constructor to record if a repeated
+// field is mutable.
+// Example: "mutable_bitField1_ = (mutable_bitField1_ | 0x04)"
+string GenerateSetBitMutableLocal(int bitIndex);
+
+// Returns whether the JavaType is a reference type.
+bool IsReferenceType(JavaType type);
+
+// Returns the capitalized name for calling relative functions in
+// CodedInputStream
+const char* GetCapitalizedType(const FieldDescriptor* field, bool immutable);
+
+// For encodings with fixed sizes, returns that size in bytes. Otherwise
+// returns -1.
+int FixedSize(FieldDescriptor::Type type);
+
+// Comparators used to sort fields in MessageGenerator
+struct FieldOrderingByNumber {
+ inline bool operator()(const FieldDescriptor* a,
+ const FieldDescriptor* b) const {
+ return a->number() < b->number();
+ }
+};
+
+struct ExtensionRangeOrdering {
+ bool operator()(const Descriptor::ExtensionRange* a,
+ const Descriptor::ExtensionRange* b) const {
+ return a->start < b->start;
+ }
+};
+
+// Sort the fields of the given Descriptor by number into a new[]'d array
+// and return it. The caller should delete the returned array.
+const FieldDescriptor** SortFieldsByNumber(const Descriptor* descriptor);
+
+// Does this message class have any packed fields?
+inline bool HasPackedFields(const Descriptor* descriptor) {
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ if (descriptor->field(i)->is_packed()) {
+ return true;
+ }
+ }
+ return false;
+}
+
+// Check a message type and its sub-message types recursively to see if any of
+// them has a required field. Return true if a required field is found.
+bool HasRequiredFields(const Descriptor* descriptor);
+
+// Whether a .proto file supports field presence test for non-message types.
+inline bool SupportFieldPresence(const FileDescriptor* descriptor) {
+ return descriptor->syntax() != FileDescriptor::SYNTAX_PROTO3;
+}
+
+// Whether generate classes expose public PARSER instances.
+inline bool ExposePublicParser(const FileDescriptor* descriptor) {
+ // TODO(liujisi): Mark the PARSER private in 3.1.x releases.
+ return descriptor->syntax() == FileDescriptor::SYNTAX_PROTO2;
+}
+
+// Whether unknown enum values are kept (i.e., not stored in UnknownFieldSet
+// but in the message and can be queried using additional getters that return
+// ints.
+inline bool SupportUnknownEnumValue(const FileDescriptor* descriptor) {
+ return descriptor->syntax() == FileDescriptor::SYNTAX_PROTO3;
+}
+
+// Check whether a mesasge has repeated fields.
+bool HasRepeatedFields(const Descriptor* descriptor);
+
+inline bool IsMapEntry(const Descriptor* descriptor) {
+ return descriptor->options().map_entry();
+}
+
+inline bool IsMapField(const FieldDescriptor* descriptor) {
+ return descriptor->is_map();
+}
+
+inline bool PreserveUnknownFields(const Descriptor* descriptor) {
+ return descriptor->file()->syntax() != FileDescriptor::SYNTAX_PROTO3;
+}
+
+inline bool IsAnyMessage(const Descriptor* descriptor) {
+ return descriptor->full_name() == "google.protobuf.Any";
+}
+
+inline bool CheckUtf8(const FieldDescriptor* descriptor) {
+ return descriptor->file()->syntax() == FileDescriptor::SYNTAX_PROTO3 ||
+ descriptor->file()->options().java_string_check_utf8();
+}
+
+inline string GeneratedCodeVersionSuffix() {
+ return "V3";
+}
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_HELPERS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.cc
new file mode 100644
index 0000000000..abf8e55cf7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.cc
@@ -0,0 +1,814 @@
+// 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: niwasaki@google.com (Naoki Iwasaki)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_lazy_message_field.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/io/printer.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+ImmutableLazyMessageFieldGenerator::
+ImmutableLazyMessageFieldGenerator(
+ const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableMessageFieldGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+}
+
+ImmutableLazyMessageFieldGenerator::~ImmutableLazyMessageFieldGenerator() {}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private com.google.protobuf.LazyFieldLite $name$_ =\n"
+ " new com.google.protobuf.LazyFieldLite();\n");
+
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return ($type$) $name$_.getValue($type$.getDefaultInstance());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder() {\n"
+ " return $name$_;\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // When using nested-builders, the code initially works just like the
+ // non-nested builder case. It only creates a nested builder lazily on
+ // demand and then forever delegates to it after creation.
+
+ printer->Print(variables_,
+ "private com.google.protobuf.LazyFieldLite $name$_ =\n"
+ " new com.google.protobuf.LazyFieldLite();\n");
+
+ printer->Print(variables_,
+ // If this builder is non-null, it is used and the other fields are
+ // ignored.
+ "private com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> $name$Builder_;"
+ "\n");
+
+ // The comments above the methods below are based on a hypothetical
+ // field of type "Field" called "Field".
+
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_builder$;\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return ($type$) $name$_.getValue($type$.getDefaultInstance());\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$($type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "$name$_.setValue(value);\n"
+ "$on_changed$\n",
+
+ NULL, // Lazy fields are supported only for lite-runtime.
+
+ "$set_has_field_bit_builder$;\n"
+ "return this;\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue)",
+
+ "$name$_.setValue(builderForValue.build());\n"
+ "$on_changed$\n",
+
+ NULL,
+
+ "$set_has_field_bit_builder$;\n"
+ "return this;\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value)",
+
+ "if ($get_has_field_bit_builder$ &&\n"
+ " !$name$_.containsDefaultInstance()) {\n"
+ " $name$_.setValue(\n"
+ " $type$.newBuilder(\n"
+ " get$capitalized_name$()).mergeFrom(value).buildPartial());\n"
+ "} else {\n"
+ " $name$_.setValue(value);\n"
+ "}\n"
+ "$on_changed$\n",
+
+ NULL,
+
+ "$set_has_field_bit_builder$;\n"
+ "return this;\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder clear$capitalized_name$()",
+
+ "$name$_.clear();\n"
+ "$on_changed$\n",
+
+ NULL,
+
+ "$clear_has_field_bit_builder$;\n"
+ "return this;\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder get$capitalized_name$Builder() {\n"
+ " $set_has_field_bit_builder$;\n"
+ " $on_changed$\n"
+ " return get$capitalized_name$FieldBuilder().getBuilder();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder() {\n"
+ " if ($name$Builder_ != null) {\n"
+ " return $name$Builder_.getMessageOrBuilder();\n"
+ " } else {\n"
+ " return $name$_;\n"
+ " }\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> \n"
+ " get$capitalized_name$FieldBuilder() {\n"
+ " if ($name$Builder_ == null) {\n"
+ " $name$Builder_ = new com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder>(\n"
+ " $name$_,\n"
+ " getParentForChildren(),\n"
+ " isClean());\n"
+ " $name$_ = null;\n"
+ " }\n"
+ " return $name$Builder_;\n"
+ "}\n");
+}
+
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.clear();\n");
+}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_.clear();\n");
+ printer->Print(variables_, "$clear_has_field_bit_builder$;\n");
+}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (other.has$capitalized_name$()) {\n"
+ " $name$_.merge(other.$name$_);\n"
+ " $set_has_field_bit_builder$;\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_has_field_bit_from_local$) {\n"
+ " $set_has_field_bit_to_local$;\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "result.$name$_.set(\n"
+ " $name$_);\n");
+}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_.setByteString(input.readBytes(), extensionRegistry);\n");
+ printer->Print(variables_,
+ "$set_has_field_bit_message$;\n");
+}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ // Do not de-serialize lazy fields.
+ printer->Print(variables_,
+ "if ($get_has_field_bit_message$) {\n"
+ " output.writeBytes($number$, $name$_.toByteString());\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_has_field_bit_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeLazyFieldSize($number$, $name$_);\n"
+ "}\n");
+}
+
+// ===================================================================
+
+ImmutableLazyMessageOneofFieldGenerator::
+ImmutableLazyMessageOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableLazyMessageFieldGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+ variables_["lazy_type"] = "com.google.protobuf.LazyFieldLite";
+}
+
+ImmutableLazyMessageOneofFieldGenerator::
+~ImmutableLazyMessageOneofFieldGenerator() {}
+
+void ImmutableLazyMessageOneofFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($type$) (($lazy_type$) $oneof_name$_).getValue(\n"
+ " $type$.getDefaultInstance());\n"
+ " }\n"
+ " return $type$.getDefaultInstance();\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageOneofFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($type$) (($lazy_type$) $oneof_name$_).getValue(\n"
+ " $type$.getDefaultInstance());\n"
+ " }\n"
+ " return $type$.getDefaultInstance();\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$($type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ " $set_oneof_case_message$;\n"
+ "}\n"
+ "(($lazy_type$) $oneof_name$_).setValue(value);\n"
+ "$on_changed$\n",
+
+ NULL, // Lazy fields are supported only for lite-runtime.
+
+ "return this;\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue)",
+
+ "if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ " $set_oneof_case_message$;\n"
+ "}\n"
+ "(($lazy_type$) $oneof_name$_).setValue(builderForValue.build());\n"
+ "$on_changed$\n",
+
+ NULL,
+
+ "return this;\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value)",
+
+ "if ($has_oneof_case_message$ &&\n"
+ " !(($lazy_type$) $oneof_name$_).containsDefaultInstance()) {\n"
+ " (($lazy_type$) $oneof_name$_).setValue(\n"
+ " $type$.newBuilder(\n"
+ " get$capitalized_name$()).mergeFrom(value).buildPartial());\n"
+ "} else {\n"
+ " if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ " $set_oneof_case_message$;\n"
+ " }\n"
+ " (($lazy_type$) $oneof_name$_).setValue(value);\n"
+ "}\n"
+ "$on_changed$\n",
+
+ NULL,
+
+ "return this;\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder clear$capitalized_name$()",
+
+ "if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " $on_changed$\n"
+ "}\n",
+
+ NULL,
+
+ "return this;\n");
+}
+
+void ImmutableLazyMessageOneofFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ "}\n"
+ "(($lazy_type$) $oneof_name$_).merge(\n"
+ " ($lazy_type$) other.$oneof_name$_);\n"
+ "$set_oneof_case_message$;\n");
+}
+
+void ImmutableLazyMessageOneofFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n");
+ printer->Indent();
+
+ printer->Print(variables_,
+ "result.$oneof_name$_ = new $lazy_type$();\n"
+ "(($lazy_type$) result.$oneof_name$_).set(\n"
+ " (($lazy_type$) $oneof_name$_));\n");
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void ImmutableLazyMessageOneofFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ "}\n"
+ "(($lazy_type$) $oneof_name$_).setByteString(\n"
+ " input.readBytes(), extensionRegistry);\n"
+ "$set_oneof_case_message$;\n");
+}
+
+void ImmutableLazyMessageOneofFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ // Do not de-serialize lazy fields.
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.writeBytes(\n"
+ " $number$, (($lazy_type$) $oneof_name$_).toByteString());\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageOneofFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeLazyFieldSize($number$, ($lazy_type$) $oneof_name$_);\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutableLazyMessageFieldGenerator::
+RepeatedImmutableLazyMessageFieldGenerator(
+ const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : RepeatedImmutableMessageFieldGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+}
+
+
+RepeatedImmutableLazyMessageFieldGenerator::
+~RepeatedImmutableLazyMessageFieldGenerator() {}
+
+void RepeatedImmutableLazyMessageFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private java.util.List<com.google.protobuf.LazyFieldLite> $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$>\n"
+ " get$capitalized_name$List() {\n"
+ " java.util.List<$type$> list =\n"
+ " new java.util.ArrayList<$type$>($name$_.size());\n"
+ " for (com.google.protobuf.LazyFieldLite lf : $name$_) {\n"
+ " list.add(($type$) lf.getValue($type$.getDefaultInstance()));\n"
+ " }\n"
+ " return list;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<? extends $type$OrBuilder>\n"
+ " get$capitalized_name$OrBuilderList() {\n"
+ " return get$capitalized_name$List();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return ($type$)\n"
+ " $name$_.get(index).getValue($type$.getDefaultInstance());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder(\n"
+ " int index) {\n"
+ " return ($type$OrBuilder)\n"
+ " $name$_.get(index).getValue($type$.getDefaultInstance());\n"
+ "}\n");
+}
+
+void RepeatedImmutableLazyMessageFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // When using nested-builders, the code initially works just like the
+ // non-nested builder case. It only creates a nested builder lazily on
+ // demand and then forever delegates to it after creation.
+
+ printer->Print(variables_,
+ "private java.util.List<com.google.protobuf.LazyFieldLite> $name$_ =\n"
+ " java.util.Collections.emptyList();\n"
+
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$get_mutable_bit_builder$) {\n"
+ " $name$_ =\n"
+ " new java.util.ArrayList<com.google.protobuf.LazyFieldLite>(\n"
+ " $name$_);\n"
+ " $set_mutable_bit_builder$;\n"
+ " }\n"
+ "}\n"
+ "\n");
+
+ printer->Print(variables_,
+ // If this builder is non-null, it is used and the other fields are
+ // ignored.
+ "private com.google.protobuf.RepeatedFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> $name$Builder_;\n"
+ "\n");
+
+ // The comments above the methods below are based on a hypothetical
+ // repeated field of type "Field" called "RepeatedField".
+
+ // List<Field> getRepeatedFieldList()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List()",
+
+ "java.util.List<$type$> list =\n"
+ " new java.util.ArrayList<$type$>($name$_.size());\n"
+ "for (com.google.protobuf.LazyFieldLite lf : $name$_) {\n"
+ " list.add(($type$) lf.getValue($type$.getDefaultInstance()));\n"
+ "}\n"
+ "return java.util.Collections.unmodifiableList(list);\n",
+
+ "return $name$Builder_.getMessageList();\n",
+
+ NULL);
+
+ // int getRepeatedFieldCount()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public int get$capitalized_name$Count()",
+
+ "return $name$_.size();\n",
+ "return $name$Builder_.getCount();\n",
+
+ NULL);
+
+ // Field getRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public $type$ get$capitalized_name$(int index)",
+
+ "return ($type$) $name$_.get(index).getValue(\n"
+ " $type$.getDefaultInstance());\n",
+
+ "return $name$Builder_.getMessage(index);\n",
+
+ NULL);
+
+ // Builder setRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value)",
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.set(index, com.google.protobuf.LazyFieldLite.fromValue(value));\n"
+ "$on_changed$\n",
+ "$name$Builder_.setMessage(index, value);\n",
+ "return this;\n");
+
+ // Builder setRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.set(index, com.google.protobuf.LazyFieldLite.fromValue(\n"
+ " builderForValue.build()));\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.setMessage(index, builderForValue.build());\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$($type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(com.google.protobuf.LazyFieldLite.fromValue(value));\n"
+
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(value);\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(index, com.google.protobuf.LazyFieldLite.fromValue(value));\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(index, value);\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " $type$.Builder builderForValue)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(com.google.protobuf.LazyFieldLite.fromValue(\n"
+ " builderForValue.build()));\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(builderForValue.build());\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(index, com.google.protobuf.LazyFieldLite.fromValue(\n"
+ " builderForValue.build()));\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(index, builderForValue.build());\n",
+
+ "return this;\n");
+
+ // Builder addAllRepeatedField(Iterable<Field> values)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "for (com.google.protobuf.MessageLite v : values) {\n"
+ " $name$_.add(com.google.protobuf.LazyFieldLite.fromValue(v));\n"
+ "}\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addAllMessages(values);\n",
+
+ "return this;\n");
+
+ // Builder clearAllRepeatedField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder clear$capitalized_name$()",
+
+ "$name$_ = java.util.Collections.emptyList();\n"
+ "$clear_mutable_bit_builder$;\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.clear();\n",
+
+ "return this;\n");
+
+ // Builder removeRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder remove$capitalized_name$(int index)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.remove(index);\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.remove(index);\n",
+
+ "return this;\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder get$capitalized_name$Builder(\n"
+ " int index) {\n"
+ " return get$capitalized_name$FieldBuilder().getBuilder(index);\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder(\n"
+ " int index) {\n"
+ " if ($name$Builder_ == null) {\n"
+ " return $name$_.get(index);"
+ " } else {\n"
+ " return $name$Builder_.getMessageOrBuilder(index);\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<? extends $type$OrBuilder> \n"
+ " get$capitalized_name$OrBuilderList() {\n"
+ " if ($name$Builder_ != null) {\n"
+ " return $name$Builder_.getMessageOrBuilderList();\n"
+ " } else {\n"
+ " return java.util.Collections.unmodifiableList($name$_);\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder add$capitalized_name$Builder() {\n"
+ " return get$capitalized_name$FieldBuilder().addBuilder(\n"
+ " $type$.getDefaultInstance());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder add$capitalized_name$Builder(\n"
+ " int index) {\n"
+ " return get$capitalized_name$FieldBuilder().addBuilder(\n"
+ " index, $type$.getDefaultInstance());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$.Builder> \n"
+ " get$capitalized_name$BuilderList() {\n"
+ " return get$capitalized_name$FieldBuilder().getBuilderList();\n"
+ "}\n"
+ "private com.google.protobuf.RepeatedFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> \n"
+ " get$capitalized_name$FieldBuilder() {\n"
+ " if ($name$Builder_ == null) {\n"
+ " $name$Builder_ = new com.google.protobuf.RepeatedFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder>(\n"
+ " $name$_,\n"
+ " $get_mutable_bit_builder$,\n"
+ " getParentForChildren(),\n"
+ " isClean());\n"
+ " $name$_ = null;\n"
+ " }\n"
+ " return $name$Builder_;\n"
+ "}\n");
+}
+
+void RepeatedImmutableLazyMessageFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!$get_mutable_bit_parser$) {\n"
+ " $name$_ =\n"
+ " new java.util.ArrayList<com.google.protobuf.LazyFieldLite>();\n"
+ " $set_mutable_bit_parser$;\n"
+ "}\n"
+ "$name$_.add(new com.google.protobuf.LazyFieldLite(\n"
+ " extensionRegistry, input.readBytes()));\n");
+}
+
+void RepeatedImmutableLazyMessageFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.writeBytes($number$, $name$_.get(i).toByteString());\n"
+ "}\n");
+}
+
+void RepeatedImmutableLazyMessageFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeLazyFieldSize($number$, $name$_.get(i));\n"
+ "}\n");
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.h
new file mode 100644
index 0000000000..b1b7f2820e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field.h
@@ -0,0 +1,121 @@
+// 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: niwasaki@google.com (Naoki Iwasaki)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_LAZY_MESSAGE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_LAZY_MESSAGE_FIELD_H__
+
+#include <google/protobuf/compiler/java/java_field.h>
+#include <google/protobuf/compiler/java/java_message_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableLazyMessageFieldGenerator
+ : public ImmutableMessageFieldGenerator {
+ public:
+ explicit ImmutableLazyMessageFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableLazyMessageFieldGenerator();
+
+ // overroads ImmutableMessageFieldGenerator ---------------------------------
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableLazyMessageFieldGenerator);
+};
+
+class ImmutableLazyMessageOneofFieldGenerator
+ : public ImmutableLazyMessageFieldGenerator {
+ public:
+ ImmutableLazyMessageOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableLazyMessageOneofFieldGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableLazyMessageOneofFieldGenerator);
+};
+
+class RepeatedImmutableLazyMessageFieldGenerator
+ : public RepeatedImmutableMessageFieldGenerator {
+ public:
+ explicit RepeatedImmutableLazyMessageFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableLazyMessageFieldGenerator();
+
+ // overroads RepeatedImmutableMessageFieldGenerator -------------------------
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableLazyMessageFieldGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_LAZY_MESSAGE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.cc
new file mode 100644
index 0000000000..dac1b51f73
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.cc
@@ -0,0 +1,723 @@
+// 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: niwasaki@google.com (Naoki Iwasaki)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_lazy_message_field_lite.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/io/printer.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+ImmutableLazyMessageFieldLiteGenerator::
+ImmutableLazyMessageFieldLiteGenerator(
+ const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableMessageFieldLiteGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+}
+
+ImmutableLazyMessageFieldLiteGenerator::
+~ImmutableLazyMessageFieldLiteGenerator() {}
+
+void ImmutableLazyMessageFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private com.google.protobuf.LazyFieldLite $name$_;");
+
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $name$_ != null;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($name$_ == null) {\n"
+ " return $type$.getDefaultInstance();\n"
+ " }\n"
+ " return ($type$) $name$_.getValue($type$.getDefaultInstance());\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " if ($name$_ == null) {\n"
+ " $name$_ = new com.google.protobuf.LazyFieldLite();\n"
+ " }\n"
+ " $name$_.setValue(value);\n"
+ " $set_has_field_bit_message$\n"
+ "}\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " if ($name$_ == null) {\n"
+ " $name$_ = new com.google.protobuf.LazyFieldLite();\n"
+ " }\n"
+ " $name$_.setValue(builderForValue.build());\n"
+ " $set_has_field_bit_message$\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void merge$capitalized_name$($type$ value) {\n"
+ " if (has$capitalized_name$() &&\n"
+ " !$name$_.containsDefaultInstance()) {\n"
+ " $name$_.setValue(\n"
+ " $type$.newBuilder(\n"
+ " get$capitalized_name$()).mergeFrom(value).buildPartial());\n"
+ " } else {\n"
+ " if ($name$_ == null) {\n"
+ " $name$_ = new com.google.protobuf.LazyFieldLite();\n"
+ " }\n"
+ " $name$_.setValue(value);\n"
+ " $set_has_field_bit_message$\n"
+ " }\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $name$_ = null;\n"
+ " $clear_has_field_bit_message$;\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // The comments above the methods below are based on a hypothetical
+ // field of type "Field" called "Field".
+
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.merge$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+
+void ImmutableLazyMessageFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {}
+
+void ImmutableLazyMessageFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = visitor.visitLazyMessage($name$_, other.$name$_);\n");
+}
+
+void ImmutableLazyMessageFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($name$_ == null) {\n"
+ " $name$_ = new com.google.protobuf.LazyFieldLite();\n"
+ "}\n"
+ "$name$_.mergeFrom(input, extensionRegistry);\n");
+ printer->Print(variables_,
+ "$set_has_field_bit_message$\n");
+}
+
+void ImmutableLazyMessageFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ // Do not de-serialize lazy fields.
+ printer->Print(variables_,
+ "if (has$capitalized_name$()) {\n"
+ " output.writeBytes($number$, $name$_.toByteString());\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (has$capitalized_name$()) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeLazyFieldSize($number$, $name$_);\n"
+ "}\n");
+}
+
+// ===================================================================
+
+ImmutableLazyMessageOneofFieldLiteGenerator::
+ImmutableLazyMessageOneofFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableLazyMessageFieldLiteGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+ variables_["lazy_type"] = "com.google.protobuf.LazyFieldLite";
+}
+
+ImmutableLazyMessageOneofFieldLiteGenerator::
+~ImmutableLazyMessageOneofFieldLiteGenerator() {}
+
+void ImmutableLazyMessageOneofFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($type$) (($lazy_type$) $oneof_name$_).getValue(\n"
+ " $type$.getDefaultInstance());\n"
+ " }\n"
+ " return $type$.getDefaultInstance();\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ " $set_oneof_case_message$;\n"
+ " }\n"
+ " (($lazy_type$) $oneof_name$_).setValue(value);\n"
+ "}\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ " $set_oneof_case_message$;\n"
+ " }\n"
+ " (($lazy_type$) $oneof_name$_).setValue(builderForValue.build());\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void merge$capitalized_name$($type$ value) {\n"
+ " if ($has_oneof_case_message$ &&\n"
+ " !(($lazy_type$) $oneof_name$_).containsDefaultInstance()) {\n"
+ " (($lazy_type$) $oneof_name$_).setValue(\n"
+ " $type$.newBuilder(\n"
+ " get$capitalized_name$()).mergeFrom(value).buildPartial());\n"
+ " } else {\n"
+ " if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ " $set_oneof_case_message$;\n"
+ " }\n"
+ " (($lazy_type$) $oneof_name$_).setValue(value);\n"
+ " }\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " }\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageOneofFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.merge$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageOneofFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$oneof_name$_ = visitor.visitOneofLazyMessage(\n"
+ " $has_oneof_case_message$,\n"
+ " ($lazy_type$) $oneof_name$_,\n"
+ " ($lazy_type$) other.$oneof_name$_);\n");
+}
+
+void ImmutableLazyMessageOneofFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = new $lazy_type$();\n"
+ "}\n"
+ "(($lazy_type$) $oneof_name$_).mergeFrom(input, extensionRegistry);\n"
+ "$set_oneof_case_message$;\n");
+}
+
+void ImmutableLazyMessageOneofFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ // Do not de-serialize lazy fields.
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.writeBytes(\n"
+ " $number$, (($lazy_type$) $oneof_name$_).toByteString());\n"
+ "}\n");
+}
+
+void ImmutableLazyMessageOneofFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeLazyFieldSize($number$, ($lazy_type$) $oneof_name$_);\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutableLazyMessageFieldLiteGenerator::
+RepeatedImmutableLazyMessageFieldLiteGenerator(
+ const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : RepeatedImmutableMessageFieldLiteGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+}
+
+
+RepeatedImmutableLazyMessageFieldLiteGenerator::
+~RepeatedImmutableLazyMessageFieldLiteGenerator() {}
+
+void RepeatedImmutableLazyMessageFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private com.google.protobuf.Internal.ProtobufList<\n"
+ " com.google.protobuf.LazyFieldLite> $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$>\n"
+ " get$capitalized_name$List() {\n"
+ " java.util.List<$type$> list =\n"
+ " new java.util.ArrayList<$type$>($name$_.size());\n"
+ " for (com.google.protobuf.LazyFieldLite lf : $name$_) {\n"
+ " list.add(($type$) lf.getValue($type$.getDefaultInstance()));\n"
+ " }\n"
+ // TODO(dweis): Make this list immutable?
+ " return list;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<? extends $type$OrBuilder>\n"
+ " get$capitalized_name$OrBuilderList() {\n"
+ " return get$capitalized_name$List();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return ($type$)\n"
+ " $name$_.get(index).getValue($type$.getDefaultInstance());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder(\n"
+ " int index) {\n"
+ " return ($type$OrBuilder)\n"
+ " $name$_.get(index).getValue($type$.getDefaultInstance());\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ " }\n"
+ "}\n"
+ "\n");
+
+ // Builder setRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(\n"
+ " index, com.google.protobuf.LazyFieldLite.fromValue(value));\n"
+ "}\n");
+
+ // Builder setRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, com.google.protobuf.LazyFieldLite.fromValue(\n"
+ " builderForValue.build()));\n"
+ "}\n");
+
+ // Builder addRepeatedField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(com.google.protobuf.LazyFieldLite.fromValue(value));\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(\n"
+ " index, com.google.protobuf.LazyFieldLite.fromValue(value));\n"
+ "}\n");
+
+ // Builder addRepeatedField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(com.google.protobuf.LazyFieldLite.fromValue(\n"
+ " builderForValue.build()));\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(index, com.google.protobuf.LazyFieldLite.fromValue(\n"
+ " builderForValue.build()));\n"
+ "}\n");
+
+ // Builder addAllRepeatedField(Iterable<Field> values)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " for (com.google.protobuf.MessageLite v : values) {\n"
+ " $name$_.add(com.google.protobuf.LazyFieldLite.fromValue(v));\n"
+ " }\n"
+ "}\n");
+
+ // Builder clearAllRepeatedField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $name$_ = emptyProtobufList();\n"
+ "}\n");
+
+ // Builder removeRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void remove$capitalized_name$(int index) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.remove(index);\n"
+ "}\n");
+}
+
+void RepeatedImmutableLazyMessageFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // List<Field> getRepeatedFieldList()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return java.util.Collections.unmodifiableList(\n"
+ " instance.get$capitalized_name$List());\n"
+ "}\n");
+
+ // int getRepeatedFieldCount()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return instance.get$capitalized_name$Count();\n"
+ "}\n");
+
+ // Field getRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return instance.get$capitalized_name$(index);\n"
+ "}\n");
+
+ // Builder setRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(index, value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder setRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(index, builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addRepeatedField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(index, value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addRepeatedField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(index, builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addAllRepeatedField(Iterable<Field> values)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values) {\n"
+ " copyOnWrite();\n"
+ " instance.addAll$capitalized_name$(values);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder clearAllRepeatedField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder removeRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder remove$capitalized_name$(int index) {\n"
+ " copyOnWrite();\n"
+ " instance.remove$capitalized_name$(index);\n"
+ " return this;\n"
+ "}\n");
+}
+
+void RepeatedImmutableLazyMessageFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ "}\n"
+ "$name$_.add(new com.google.protobuf.LazyFieldLite(\n"
+ " extensionRegistry, input.readBytes()));\n");
+}
+
+void RepeatedImmutableLazyMessageFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.writeBytes($number$, $name$_.get(i).toByteString());\n"
+ "}\n");
+}
+
+void RepeatedImmutableLazyMessageFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeLazyFieldSize($number$, $name$_.get(i));\n"
+ "}\n");
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.h
new file mode 100644
index 0000000000..47ebeb49a0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_lazy_message_field_lite.h
@@ -0,0 +1,118 @@
+// 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: niwasaki@google.com (Naoki Iwasaki)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_LAZY_MESSAGE_FIELD_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_LAZY_MESSAGE_FIELD_LITE_H__
+
+#include <google/protobuf/compiler/java/java_field.h>
+#include <google/protobuf/compiler/java/java_message_field_lite.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableLazyMessageFieldLiteGenerator
+ : public ImmutableMessageFieldLiteGenerator {
+ public:
+ explicit ImmutableLazyMessageFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableLazyMessageFieldLiteGenerator();
+
+ // overroads ImmutableMessageFieldLiteGenerator ------------------------------
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableLazyMessageFieldLiteGenerator);
+};
+
+class ImmutableLazyMessageOneofFieldLiteGenerator
+ : public ImmutableLazyMessageFieldLiteGenerator {
+ public:
+ ImmutableLazyMessageOneofFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableLazyMessageOneofFieldLiteGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableLazyMessageOneofFieldLiteGenerator);
+};
+
+class RepeatedImmutableLazyMessageFieldLiteGenerator
+ : public RepeatedImmutableMessageFieldLiteGenerator {
+ public:
+ explicit RepeatedImmutableLazyMessageFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableLazyMessageFieldLiteGenerator();
+
+ // overroads RepeatedImmutableMessageFieldLiteGenerator ----------------------
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableLazyMessageFieldLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_LAZY_MESSAGE_FIELD_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.cc
new file mode 100644
index 0000000000..16c5bec578
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.cc
@@ -0,0 +1,743 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_map_field.h>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+const FieldDescriptor* KeyField(const FieldDescriptor* descriptor) {
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, descriptor->type());
+ const Descriptor* message = descriptor->message_type();
+ GOOGLE_CHECK(message->options().map_entry());
+ return message->FindFieldByName("key");
+}
+
+const FieldDescriptor* ValueField(const FieldDescriptor* descriptor) {
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, descriptor->type());
+ const Descriptor* message = descriptor->message_type();
+ GOOGLE_CHECK(message->options().map_entry());
+ return message->FindFieldByName("value");
+}
+
+string TypeName(const FieldDescriptor* field,
+ ClassNameResolver* name_resolver,
+ bool boxed) {
+ if (GetJavaType(field) == JAVATYPE_MESSAGE) {
+ return name_resolver->GetImmutableClassName(field->message_type());
+ } else if (GetJavaType(field) == JAVATYPE_ENUM) {
+ return name_resolver->GetImmutableClassName(field->enum_type());
+ } else {
+ return boxed ? BoxedPrimitiveTypeName(GetJavaType(field))
+ : PrimitiveTypeName(GetJavaType(field));
+ }
+}
+
+string WireType(const FieldDescriptor* field) {
+ return "com.google.protobuf.WireFormat.FieldType." +
+ string(FieldTypeName(field->type()));
+}
+
+void SetMessageVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ Context* context,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+ ClassNameResolver* name_resolver = context->GetNameResolver();
+
+ (*variables)["type"] =
+ name_resolver->GetImmutableClassName(descriptor->message_type());
+ const FieldDescriptor* key = KeyField(descriptor);
+ const FieldDescriptor* value = ValueField(descriptor);
+ const JavaType keyJavaType = GetJavaType(key);
+ const JavaType valueJavaType = GetJavaType(value);
+
+ (*variables)["key_type"] = TypeName(key, name_resolver, false);
+ (*variables)["boxed_key_type"] = TypeName(key, name_resolver, true);
+ (*variables)["key_wire_type"] = WireType(key);
+ (*variables)["key_default_value"] = DefaultValue(key, true, name_resolver);
+ (*variables)["key_null_check"] = IsReferenceType(keyJavaType) ?
+ "if (key == null) { throw new java.lang.NullPointerException(); }" : "";
+ (*variables)["value_null_check"] = IsReferenceType(valueJavaType) ?
+ "if (value == null) { throw new java.lang.NullPointerException(); }" : "";
+ if (valueJavaType == JAVATYPE_ENUM) {
+ // We store enums as Integers internally.
+ (*variables)["value_type"] = "int";
+ (*variables)["boxed_value_type"] = "java.lang.Integer";
+ (*variables)["value_wire_type"] = WireType(value);
+ (*variables)["value_default_value"] =
+ DefaultValue(value, true, name_resolver) + ".getNumber()";
+
+ (*variables)["value_enum_type"] = TypeName(value, name_resolver, false);
+
+ if (SupportUnknownEnumValue(descriptor->file())) {
+ // Map unknown values to a special UNRECOGNIZED value if supported.
+ (*variables)["unrecognized_value"] =
+ (*variables)["value_enum_type"] + ".UNRECOGNIZED";
+ } else {
+ // Map unknown values to the default value if we don't have UNRECOGNIZED.
+ (*variables)["unrecognized_value"] =
+ DefaultValue(value, true, name_resolver);
+ }
+ } else {
+ (*variables)["value_type"] = TypeName(value, name_resolver, false);
+ (*variables)["boxed_value_type"] = TypeName(value, name_resolver, true);
+ (*variables)["value_wire_type"] = WireType(value);
+ (*variables)["value_default_value"] =
+ DefaultValue(value, true, name_resolver);
+ }
+ (*variables)["type_parameters"] =
+ (*variables)["boxed_key_type"] + ", " + (*variables)["boxed_value_type"];
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+ (*variables)["on_changed"] = "onChanged();";
+
+ // For repeated fields, one bit is used for whether the array is immutable
+ // in the parsing constructor.
+ (*variables)["get_mutable_bit_parser"] =
+ GenerateGetBitMutableLocal(builderBitIndex);
+ (*variables)["set_mutable_bit_parser"] =
+ GenerateSetBitMutableLocal(builderBitIndex);
+
+ (*variables)["default_entry"] = (*variables)["capitalized_name"] +
+ "DefaultEntryHolder.defaultEntry";
+ (*variables)["map_field_parameter"] = (*variables)["default_entry"];
+ (*variables)["descriptor"] =
+ name_resolver->GetImmutableClassName(descriptor->file()) +
+ ".internal_" + UniqueFileScopeIdentifier(descriptor->message_type()) +
+ "_descriptor, ";
+}
+
+} // namespace
+
+ImmutableMapFieldGenerator::
+ImmutableMapFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), name_resolver_(context->GetNameResolver()) {
+ SetMessageVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ context, &variables_);
+}
+
+ImmutableMapFieldGenerator::
+~ImmutableMapFieldGenerator() {}
+
+int ImmutableMapFieldGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int ImmutableMapFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void ImmutableMapFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$boolean contains$capitalized_name$(\n"
+ " $key_type$ key);\n");
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$Map();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$$value_enum_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_enum_type$ defaultValue);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$$value_enum_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key);\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$ValueMap()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$Value();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$ValueMap();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$ValueOrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$ValueOrThrow(\n"
+ " $key_type$ key);\n");
+ }
+ } else {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$Map();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key);\n");
+ }
+}
+
+void ImmutableMapFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "private static final class $capitalized_name$DefaultEntryHolder {\n"
+ " static final com.google.protobuf.MapEntry<\n"
+ " $type_parameters$> defaultEntry =\n"
+ " com.google.protobuf.MapEntry\n"
+ " .<$type_parameters$>newDefaultInstance(\n"
+ " $descriptor$\n"
+ " $key_wire_type$,\n"
+ " $key_default_value$,\n"
+ " $value_wire_type$,\n"
+ " $value_default_value$);\n"
+ "}\n");
+ printer->Print(
+ variables_,
+ "private com.google.protobuf.MapField<\n"
+ " $type_parameters$> $name$_;\n"
+ "private com.google.protobuf.MapField<$type_parameters$>\n"
+ "internalGet$capitalized_name$() {\n"
+ " if ($name$_ == null) {\n"
+ " return com.google.protobuf.MapField.emptyMapField(\n"
+ " $map_field_parameter$);\n"
+ " }\n"
+ " return $name$_;\n"
+ "}\n");
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "private static final\n"
+ "com.google.protobuf.Internal.MapAdapter.Converter<\n"
+ " java.lang.Integer, $value_enum_type$> $name$ValueConverter =\n"
+ " com.google.protobuf.Internal.MapAdapter.newEnumConverter(\n"
+ " $value_enum_type$.internalGetValueMap(),\n"
+ " $unrecognized_value$);\n");
+ }
+ GenerateMapGetters(printer);
+}
+
+void ImmutableMapFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "private com.google.protobuf.MapField<\n"
+ " $type_parameters$> $name$_;\n"
+ "private com.google.protobuf.MapField<$type_parameters$>\n"
+ "internalGet$capitalized_name$() {\n"
+ " if ($name$_ == null) {\n"
+ " return com.google.protobuf.MapField.emptyMapField(\n"
+ " $map_field_parameter$);\n"
+ " }\n"
+ " return $name$_;\n"
+ "}\n"
+ "private com.google.protobuf.MapField<$type_parameters$>\n"
+ "internalGetMutable$capitalized_name$() {\n"
+ " $on_changed$;\n"
+ " if ($name$_ == null) {\n"
+ " $name$_ = com.google.protobuf.MapField.newMapField(\n"
+ " $map_field_parameter$);\n"
+ " }\n"
+ " if (!$name$_.isMutable()) {\n"
+ " $name$_ = $name$_.copy();\n"
+ " }\n"
+ " return $name$_;\n"
+ "}\n");
+ GenerateMapGetters(printer);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public Builder clear$capitalized_name$() {\n"
+ " getMutable$capitalized_name$().clear();\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public Builder remove$capitalized_name$(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " getMutable$capitalized_name$().remove(key);\n"
+ " return this;\n"
+ "}\n");
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use alternate mutation accessors instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "getMutable$capitalized_name$() {\n"
+ " return new com.google.protobuf.Internal.MapAdapter<\n"
+ " $boxed_key_type$, $value_enum_type$, java.lang.Integer>(\n"
+ " internalGetMutable$capitalized_name$().getMutableMap(),\n"
+ " $name$ValueConverter);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$public Builder put$capitalized_name$(\n"
+ " $key_type$ key,\n"
+ " $value_enum_type$ value) {\n"
+ " $key_null_check$\n"
+ " $value_null_check$\n"
+ " getMutable$capitalized_name$().put(key, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ // TODO(arielb): null check map keys/values here and everywhere else
+ // related to putAll
+ "$deprecation$public Builder putAll$capitalized_name$(\n"
+ " java.util.Map<$boxed_key_type$, $value_enum_type$> values) {\n"
+ " getMutable$capitalized_name$().putAll(values);\n"
+ " return this;\n"
+ "}\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use alternate mutation accessors instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "getMutable$capitalized_name$Value() {\n"
+ " return internalGetMutable$capitalized_name$().getMutableMap();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$public Builder put$capitalized_name$Value(\n"
+ " $key_type$ key,\n"
+ " $value_type$ value) {\n"
+ " $key_null_check$\n"
+ " if ($value_enum_type$.forNumber(value) == null) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " getMutable$capitalized_name$Value().put(key, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$public Builder putAll$capitalized_name$Value(\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> values) {\n"
+ " getMutable$capitalized_name$Value().putAll(values);\n"
+ " return this;\n"
+ "}\n");
+ }
+ } else {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use alternate mutation accessors instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$type_parameters$>\n"
+ "getMutable$capitalized_name$() {\n"
+ " return internalGetMutable$capitalized_name$().getMutableMap();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$"
+ "public Builder put$capitalized_name$(\n"
+ " $key_type$ key,\n"
+ " $value_type$ value) {\n"
+ " $key_null_check$\n"
+ " $value_null_check$\n"
+ " getMutable$capitalized_name$().put(key, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public Builder putAll$capitalized_name$(\n"
+ " java.util.Map<$type_parameters$> values) {\n"
+ " getMutable$capitalized_name$().putAll(values);\n"
+ " return this;\n"
+ "}\n");
+ }
+}
+
+void ImmutableMapFieldGenerator::
+GenerateMapGetters(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public int get$capitalized_name$Count() {\n"
+ " return internalGet$capitalized_name$().getMap().size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public boolean contains$capitalized_name$(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " return internalGet$capitalized_name$().getMap().containsKey(key);\n"
+ "}\n");
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$() {\n"
+ " return get$capitalized_name$Map();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$Map() {\n"
+ " return new com.google.protobuf.Internal.MapAdapter<\n"
+ " $boxed_key_type$, $value_enum_type$, java.lang.Integer>(\n"
+ " internalGet$capitalized_name$().getMap(),\n"
+ " $name$ValueConverter);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_enum_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_enum_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$().getMap();\n"
+ " return map.containsKey(key)\n"
+ " ? $name$ValueConverter.doForward(map.get(key))\n"
+ " : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_enum_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$().getMap();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return $name$ValueConverter.doForward(map.get(key));\n"
+ "}\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$ValueMap()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "get$capitalized_name$Value() {\n"
+ " return get$capitalized_name$ValueMap();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "get$capitalized_name$ValueMap() {\n"
+ " return internalGet$capitalized_name$().getMap();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$ValueOrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$().getMap();\n"
+ " return map.containsKey(key) ? map.get(key) : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$ValueOrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$().getMap();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return map.get(key);\n"
+ "}\n");
+ }
+ } else {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$type_parameters$> get$capitalized_name$() {\n"
+ " return get$capitalized_name$Map();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$type_parameters$> get$capitalized_name$Map() {\n"
+ " return internalGet$capitalized_name$().getMap();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$type_parameters$> map =\n"
+ " internalGet$capitalized_name$().getMap();\n"
+ " return map.containsKey(key) ? map.get(key) : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$type_parameters$> map =\n"
+ " internalGet$capitalized_name$().getMap();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return map.get(key);\n"
+ "}\n");
+ }
+}
+
+void ImmutableMapFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // Nothing to initialize.
+}
+
+void ImmutableMapFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ // Nothing to initialize.
+}
+
+void ImmutableMapFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "internalGetMutable$capitalized_name$().clear();\n");
+}
+
+void ImmutableMapFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "internalGetMutable$capitalized_name$().mergeFrom(\n"
+ " other.internalGet$capitalized_name$());\n");
+}
+
+void ImmutableMapFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "result.$name$_ = internalGet$capitalized_name$();\n"
+ "result.$name$_.makeImmutable();\n");
+}
+
+void ImmutableMapFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "if (!$get_mutable_bit_parser$) {\n"
+ " $name$_ = com.google.protobuf.MapField.newMapField(\n"
+ " $map_field_parameter$);\n"
+ " $set_mutable_bit_parser$;\n"
+ "}\n");
+ if (!SupportUnknownEnumValue(descriptor_->file()) &&
+ GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "com.google.protobuf.ByteString bytes = input.readBytes();\n"
+ "com.google.protobuf.MapEntry<$type_parameters$>\n"
+ "$name$ = $default_entry$.getParserForType().parseFrom(bytes);\n");
+ printer->Print(
+ variables_,
+ "if ($value_enum_type$.forNumber($name$.getValue()) == null) {\n"
+ " unknownFields.mergeLengthDelimitedField($number$, bytes);\n"
+ "} else {\n"
+ " $name$_.getMutableMap().put($name$.getKey(), $name$.getValue());\n"
+ "}\n");
+ } else {
+ printer->Print(
+ variables_,
+ "com.google.protobuf.MapEntry<$type_parameters$>\n"
+ "$name$ = input.readMessage(\n"
+ " $default_entry$.getParserForType(), extensionRegistry);\n"
+ "$name$_.getMutableMap().put($name$.getKey(), $name$.getValue());\n");
+ }
+}
+
+void ImmutableMapFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // Nothing to do here.
+}
+
+void ImmutableMapFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "for (java.util.Map.Entry<$type_parameters$> entry\n"
+ " : internalGet$capitalized_name$().getMap().entrySet()) {\n"
+ " com.google.protobuf.MapEntry<$type_parameters$>\n"
+ " $name$ = $default_entry$.newBuilderForType()\n"
+ " .setKey(entry.getKey())\n"
+ " .setValue(entry.getValue())\n"
+ " .build();\n"
+ " output.writeMessage($number$, $name$);\n"
+ "}\n");
+}
+
+void ImmutableMapFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "for (java.util.Map.Entry<$type_parameters$> entry\n"
+ " : internalGet$capitalized_name$().getMap().entrySet()) {\n"
+ " com.google.protobuf.MapEntry<$type_parameters$>\n"
+ " $name$ = $default_entry$.newBuilderForType()\n"
+ " .setKey(entry.getKey())\n"
+ " .setValue(entry.getValue())\n"
+ " .build();\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeMessageSize($number$, $name$);\n"
+ "}\n");
+}
+
+void ImmutableMapFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "result = result && internalGet$capitalized_name$().equals(\n"
+ " other.internalGet$capitalized_name$());\n");
+}
+
+void ImmutableMapFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "if (!internalGet$capitalized_name$().getMap().isEmpty()) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + internalGet$capitalized_name$().hashCode();\n"
+ "}\n");
+}
+
+string ImmutableMapFieldGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->message_type());
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.h
new file mode 100644
index 0000000000..ae7ce7c5b1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field.h
@@ -0,0 +1,80 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MAP_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MAP_FIELD_H__
+
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableMapFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit ImmutableMapFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableMapFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ ClassNameResolver* name_resolver_;
+ void GenerateMapGetters(io::Printer* printer) const;
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MAP_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.cc
new file mode 100644
index 0000000000..0d3bea1703
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.cc
@@ -0,0 +1,836 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_map_field_lite.h>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+const FieldDescriptor* KeyField(const FieldDescriptor* descriptor) {
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, descriptor->type());
+ const Descriptor* message = descriptor->message_type();
+ GOOGLE_CHECK(message->options().map_entry());
+ return message->FindFieldByName("key");
+}
+
+const FieldDescriptor* ValueField(const FieldDescriptor* descriptor) {
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, descriptor->type());
+ const Descriptor* message = descriptor->message_type();
+ GOOGLE_CHECK(message->options().map_entry());
+ return message->FindFieldByName("value");
+}
+
+string TypeName(const FieldDescriptor* field,
+ ClassNameResolver* name_resolver,
+ bool boxed) {
+ if (GetJavaType(field) == JAVATYPE_MESSAGE) {
+ return name_resolver->GetImmutableClassName(field->message_type());
+ } else if (GetJavaType(field) == JAVATYPE_ENUM) {
+ return name_resolver->GetImmutableClassName(field->enum_type());
+ } else {
+ return boxed ? BoxedPrimitiveTypeName(GetJavaType(field))
+ : PrimitiveTypeName(GetJavaType(field));
+ }
+}
+
+string WireType(const FieldDescriptor* field) {
+ return "com.google.protobuf.WireFormat.FieldType." +
+ string(FieldTypeName(field->type()));
+}
+
+void SetMessageVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ Context* context,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ ClassNameResolver* name_resolver = context->GetNameResolver();
+ (*variables)["type"] =
+ name_resolver->GetImmutableClassName(descriptor->message_type());
+ const FieldDescriptor* key = KeyField(descriptor);
+ const FieldDescriptor* value = ValueField(descriptor);
+ const JavaType keyJavaType = GetJavaType(key);
+ const JavaType valueJavaType = GetJavaType(value);
+
+ (*variables)["key_type"] = TypeName(key, name_resolver, false);
+ (*variables)["boxed_key_type"] = TypeName(key, name_resolver, true);
+ (*variables)["key_wire_type"] = WireType(key);
+ (*variables)["key_default_value"] = DefaultValue(key, true, name_resolver);
+ (*variables)["key_null_check"] = IsReferenceType(keyJavaType) ?
+ "if (key == null) { throw new java.lang.NullPointerException(); }" : "";
+ (*variables)["value_null_check"] = IsReferenceType(valueJavaType) ?
+ "if (value == null) { throw new java.lang.NullPointerException(); }" : "";
+
+ if (GetJavaType(value) == JAVATYPE_ENUM) {
+ // We store enums as Integers internally.
+ (*variables)["value_type"] = "int";
+ (*variables)["boxed_value_type"] = "java.lang.Integer";
+ (*variables)["value_wire_type"] = WireType(value);
+ (*variables)["value_default_value"] =
+ DefaultValue(value, true, name_resolver) + ".getNumber()";
+
+ (*variables)["value_enum_type"] = TypeName(value, name_resolver, false);
+
+ if (SupportUnknownEnumValue(descriptor->file())) {
+ // Map unknown values to a special UNRECOGNIZED value if supported.
+ (*variables)["unrecognized_value"] =
+ (*variables)["value_enum_type"] + ".UNRECOGNIZED";
+ } else {
+ // Map unknown values to the default value if we don't have UNRECOGNIZED.
+ (*variables)["unrecognized_value"] =
+ DefaultValue(value, true, name_resolver);
+ }
+ } else {
+ (*variables)["value_type"] = TypeName(value, name_resolver, false);
+ (*variables)["boxed_value_type"] = TypeName(value, name_resolver, true);
+ (*variables)["value_wire_type"] = WireType(value);
+ (*variables)["value_default_value"] =
+ DefaultValue(value, true, name_resolver);
+ }
+ (*variables)["type_parameters"] =
+ (*variables)["boxed_key_type"] + ", " + (*variables)["boxed_value_type"];
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+
+ (*variables)["default_entry"] = (*variables)["capitalized_name"] +
+ "DefaultEntryHolder.defaultEntry";
+}
+
+} // namespace
+
+ImmutableMapFieldLiteGenerator::
+ImmutableMapFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), name_resolver_(context->GetNameResolver()) {
+ SetMessageVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ context, &variables_);
+}
+
+ImmutableMapFieldLiteGenerator::
+~ImmutableMapFieldLiteGenerator() {}
+
+int ImmutableMapFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int ImmutableMapFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$boolean contains$capitalized_name$(\n"
+ " $key_type$ key);\n");
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$Map();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$$value_enum_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_enum_type$ defaultValue);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$$value_enum_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key);\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$ValueMap()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$Value();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$ValueMap();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$ValueOrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$ValueOrThrow(\n"
+ " $key_type$ key);\n");
+ }
+ } else {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$java.util.Map<$type_parameters$>\n"
+ "get$capitalized_name$Map();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "$value_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key);\n");
+ }
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "private static final class $capitalized_name$DefaultEntryHolder {\n"
+ " static final com.google.protobuf.MapEntryLite<\n"
+ " $type_parameters$> defaultEntry =\n"
+ " com.google.protobuf.MapEntryLite\n"
+ " .<$type_parameters$>newDefaultInstance(\n"
+ " $key_wire_type$,\n"
+ " $key_default_value$,\n"
+ " $value_wire_type$,\n"
+ " $value_default_value$);\n"
+ "}\n");
+ printer->Print(
+ variables_,
+ "private com.google.protobuf.MapFieldLite<\n"
+ " $type_parameters$> $name$_ =\n"
+ " com.google.protobuf.MapFieldLite.emptyMapField();\n"
+ "private com.google.protobuf.MapFieldLite<$type_parameters$>\n"
+ "internalGet$capitalized_name$() {\n"
+ " return $name$_;\n"
+ "}\n"
+ "private com.google.protobuf.MapFieldLite<$type_parameters$>\n"
+ "internalGetMutable$capitalized_name$() {\n"
+ " if (!$name$_.isMutable()) {\n"
+ " $name$_ = $name$_.mutableCopy();\n"
+ " }\n"
+ " return $name$_;\n"
+ "}\n");
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public int get$capitalized_name$Count() {\n"
+ " return internalGet$capitalized_name$().size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public boolean contains$capitalized_name$(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " return internalGet$capitalized_name$().containsKey(key);\n"
+ "}\n");
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "private static final\n"
+ "com.google.protobuf.Internal.MapAdapter.Converter<\n"
+ " java.lang.Integer, $value_enum_type$> $name$ValueConverter =\n"
+ " com.google.protobuf.Internal.MapAdapter.newEnumConverter(\n"
+ " $value_enum_type$.internalGetValueMap(),\n"
+ " $unrecognized_value$);\n");
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$() {\n"
+ " return get$capitalized_name$Map();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$Map() {\n"
+ " return java.util.Collections.unmodifiableMap(\n"
+ " new com.google.protobuf.Internal.MapAdapter<\n"
+ " $boxed_key_type$, $value_enum_type$, java.lang.Integer>(\n"
+ " internalGet$capitalized_name$(),\n"
+ " $name$ValueConverter));\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_enum_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_enum_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$();\n"
+ " return map.containsKey(key)\n"
+ " ? $name$ValueConverter.doForward(map.get(key))\n"
+ " : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_enum_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return $name$ValueConverter.doForward(map.get(key));\n"
+ "}\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$ValueMap()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "get$capitalized_name$Value() {\n"
+ " return get$capitalized_name$ValueMap();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "get$capitalized_name$ValueMap() {\n"
+ " return java.util.Collections.unmodifiableMap(\n"
+ " internalGet$capitalized_name$());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$ValueOrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$();\n"
+ " return map.containsKey(key) ? map.get(key) : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$ValueOrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " internalGet$capitalized_name$();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return map.get(key);\n"
+ "}\n");
+ }
+ } else {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$type_parameters$> get$capitalized_name$() {\n"
+ " return get$capitalized_name$Map();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$type_parameters$> get$capitalized_name$Map() {\n"
+ " return java.util.Collections.unmodifiableMap(\n"
+ " internalGet$capitalized_name$());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$type_parameters$> map =\n"
+ " internalGet$capitalized_name$();\n"
+ " return map.containsKey(key) ? map.get(key) : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$type_parameters$> map =\n"
+ " internalGet$capitalized_name$();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return map.get(key);\n"
+ "}\n");
+ }
+
+ // Generate private setters for the builder to proxy into.
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "private java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "getMutable$capitalized_name$Map() {\n"
+ " return new com.google.protobuf.Internal.MapAdapter<\n"
+ " $boxed_key_type$, $value_enum_type$, java.lang.Integer>(\n"
+ " internalGetMutable$capitalized_name$(),\n"
+ " $name$ValueConverter);\n"
+ "}\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "private java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "getMutable$capitalized_name$ValueMap() {\n"
+ " return internalGetMutable$capitalized_name$();\n"
+ "}\n");
+ }
+ } else {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "private java.util.Map<$type_parameters$>\n"
+ "getMutable$capitalized_name$Map() {\n"
+ " return internalGetMutable$capitalized_name$();\n"
+ "}\n");
+ }
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public int get$capitalized_name$Count() {\n"
+ " return instance.get$capitalized_name$Map().size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public boolean contains$capitalized_name$(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " return instance.get$capitalized_name$Map().containsKey(key);\n"
+ "}\n");
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$Map().clear();\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public Builder remove$capitalized_name$(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$Map().remove(key);\n"
+ " return this;\n"
+ "}\n");
+ if (GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$() {\n"
+ " return get$capitalized_name$Map();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$boxed_key_type$, $value_enum_type$>\n"
+ "get$capitalized_name$Map() {\n"
+ " return java.util.Collections.unmodifiableMap(\n"
+ " instance.get$capitalized_name$Map());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_enum_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_enum_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $value_enum_type$> map =\n"
+ " instance.get$capitalized_name$Map();\n"
+ " return map.containsKey(key)\n"
+ " ? map.get(key)\n"
+ " : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_enum_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $value_enum_type$> map =\n"
+ " instance.get$capitalized_name$Map();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return map.get(key);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$public Builder put$capitalized_name$(\n"
+ " $key_type$ key,\n"
+ " $value_enum_type$ value) {\n"
+ " $key_null_check$\n"
+ " $value_null_check$\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$Map().put(key, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$public Builder putAll$capitalized_name$(\n"
+ " java.util.Map<$boxed_key_type$, $value_enum_type$> values) {\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$Map().putAll(values);\n"
+ " return this;\n"
+ "}\n");
+ if (SupportUnknownEnumValue(descriptor_->file())) {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$ValueMap()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "get$capitalized_name$Value() {\n"
+ " return get$capitalized_name$ValueMap();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public java.util.Map<$boxed_key_type$, $boxed_value_type$>\n"
+ "get$capitalized_name$ValueMap() {\n"
+ " return java.util.Collections.unmodifiableMap(\n"
+ " instance.get$capitalized_name$ValueMap());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$ValueOrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " instance.get$capitalized_name$ValueMap();\n"
+ " return map.containsKey(key) ? map.get(key) : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$ValueOrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> map =\n"
+ " instance.get$capitalized_name$ValueMap();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return map.get(key);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$public Builder put$capitalized_name$Value(\n"
+ " $key_type$ key,\n"
+ " $value_type$ value) {\n"
+ " $key_null_check$\n"
+ " if ($value_enum_type$.forNumber(value) == null) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$ValueMap().put(key, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$public Builder putAll$capitalized_name$Value(\n"
+ " java.util.Map<$boxed_key_type$, $boxed_value_type$> values) {\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$ValueMap().putAll(values);\n"
+ " return this;\n"
+ "}\n");
+ }
+ } else {
+ printer->Print(
+ variables_,
+ "/**\n"
+ " * Use {@link #get$capitalized_name$Map()} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public java.util.Map<$type_parameters$> get$capitalized_name$() {\n"
+ " return get$capitalized_name$Map();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$"
+ "public java.util.Map<$type_parameters$> get$capitalized_name$Map() {\n"
+ " return java.util.Collections.unmodifiableMap(\n"
+ " instance.get$capitalized_name$Map());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$OrDefault(\n"
+ " $key_type$ key,\n"
+ " $value_type$ defaultValue) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$type_parameters$> map =\n"
+ " instance.get$capitalized_name$Map();\n"
+ " return map.containsKey(key) ? map.get(key) : defaultValue;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$\n"
+ "public $value_type$ get$capitalized_name$OrThrow(\n"
+ " $key_type$ key) {\n"
+ " $key_null_check$\n"
+ " java.util.Map<$type_parameters$> map =\n"
+ " instance.get$capitalized_name$Map();\n"
+ " if (!map.containsKey(key)) {\n"
+ " throw new java.lang.IllegalArgumentException();\n"
+ " }\n"
+ " return map.get(key);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$"
+ "public Builder put$capitalized_name$(\n"
+ " $key_type$ key,\n"
+ " $value_type$ value) {\n"
+ " $key_null_check$\n"
+ " $value_null_check$\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$Map().put(key, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(
+ variables_,
+ "$deprecation$"
+ "public Builder putAll$capitalized_name$(\n"
+ " java.util.Map<$type_parameters$> values) {\n"
+ " copyOnWrite();\n"
+ " instance.getMutable$capitalized_name$Map().putAll(values);\n"
+ " return this;\n"
+ "}\n");
+ }
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // Nothing to initialize.
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ // Nothing to initialize.
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "$name$_ = visitor.visitMap(\n"
+ " $name$_, other.internalGet$capitalized_name$());\n");
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_.makeImmutable();\n");
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "if (!$name$_.isMutable()) {\n"
+ " $name$_ = $name$_.mutableCopy();\n"
+ "}\n");
+ if (!SupportUnknownEnumValue(descriptor_->file()) &&
+ GetJavaType(ValueField(descriptor_)) == JAVATYPE_ENUM) {
+ printer->Print(
+ variables_,
+ "com.google.protobuf.ByteString bytes = input.readBytes();\n"
+ "java.util.Map.Entry<$type_parameters$> $name$ =\n"
+ " $default_entry$.parseEntry(bytes, extensionRegistry);\n");
+ printer->Print(
+ variables_,
+ "if ($value_enum_type$.forNumber($name$.getValue()) == null) {\n"
+ " super.mergeLengthDelimitedField($number$, bytes);\n"
+ "} else {\n"
+ " $name$_.put($name$);\n"
+ "}\n");
+ } else {
+ printer->Print(
+ variables_,
+ "$default_entry$.parseInto($name$_, input, extensionRegistry);");
+ }
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // Nothing to do here.
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "for (java.util.Map.Entry<$type_parameters$> entry\n"
+ " : internalGet$capitalized_name$().entrySet()) {\n"
+ " $default_entry$.serializeTo(\n"
+ " output, $number$, entry.getKey(), entry.getValue());\n"
+ "}\n");
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "for (java.util.Map.Entry<$type_parameters$> entry\n"
+ " : internalGet$capitalized_name$().entrySet()) {\n"
+ " size += $default_entry$.computeMessageSize(\n"
+ " $number$, entry.getKey(), entry.getValue());\n"
+ "}\n");
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "result = result && internalGet$capitalized_name$().equals(\n"
+ " other.internalGet$capitalized_name$());\n");
+}
+
+void ImmutableMapFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "if (!internalGet$capitalized_name$().isEmpty()) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + internalGet$capitalized_name$().hashCode();\n"
+ "}\n");
+}
+
+string ImmutableMapFieldLiteGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->message_type());
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.h
new file mode 100644
index 0000000000..555b5c5bdd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_map_field_lite.h
@@ -0,0 +1,78 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MAP_FIELD_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MAP_FIELD_LITE_H__
+
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableMapFieldLiteGenerator : public ImmutableFieldLiteGenerator {
+ public:
+ explicit ImmutableMapFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableMapFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ ClassNameResolver* name_resolver_;
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MAP_FIELD_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.cc
new file mode 100644
index 0000000000..6c80d07064
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.cc
@@ -0,0 +1,1466 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_message.h>
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_enum.h>
+#include <google/protobuf/compiler/java/java_extension.h>
+#include <google/protobuf/compiler/java/java_generator_factory.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_message_builder.h>
+#include <google/protobuf/compiler/java/java_message_builder_lite.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+bool GenerateHasBits(const Descriptor* descriptor) {
+ return SupportFieldPresence(descriptor->file()) ||
+ HasRepeatedFields(descriptor);
+}
+
+string MapValueImmutableClassdName(const Descriptor* descriptor,
+ ClassNameResolver* name_resolver) {
+ const FieldDescriptor* value_field = descriptor->FindFieldByName("value");
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, value_field->type());
+ return name_resolver->GetImmutableClassName(value_field->message_type());
+}
+} // namespace
+
+// ===================================================================
+
+MessageGenerator::MessageGenerator(const Descriptor* descriptor)
+ : descriptor_(descriptor) {}
+
+MessageGenerator::~MessageGenerator() {}
+
+// ===================================================================
+ImmutableMessageGenerator::ImmutableMessageGenerator(
+ const Descriptor* descriptor, Context* context)
+ : MessageGenerator(descriptor), context_(context),
+ name_resolver_(context->GetNameResolver()),
+ field_generators_(descriptor, context_) {
+ GOOGLE_CHECK(HasDescriptorMethods(descriptor->file(), context->EnforceLite()))
+ << "Generator factory error: A non-lite message generator is used to "
+ "generate lite messages.";
+}
+
+ImmutableMessageGenerator::~ImmutableMessageGenerator() {}
+
+void ImmutableMessageGenerator::GenerateStaticVariables(
+ io::Printer* printer, int* bytecode_estimate) {
+ // Because descriptor.proto (com.google.protobuf.DescriptorProtos) is
+ // used in the construction of descriptors, we have a tricky bootstrapping
+ // problem. To help control static initialization order, we make sure all
+ // descriptors and other static data that depends on them are members of
+ // the outermost class in the file. This way, they will be initialized in
+ // a deterministic order.
+
+ map<string, string> vars;
+ vars["identifier"] = UniqueFileScopeIdentifier(descriptor_);
+ vars["index"] = SimpleItoa(descriptor_->index());
+ vars["classname"] = name_resolver_->GetImmutableClassName(descriptor_);
+ if (descriptor_->containing_type() != NULL) {
+ vars["parent"] = UniqueFileScopeIdentifier(
+ descriptor_->containing_type());
+ }
+ if (MultipleJavaFiles(descriptor_->file(), /* immutable = */ true)) {
+ // We can only make these package-private since the classes that use them
+ // are in separate files.
+ vars["private"] = "";
+ } else {
+ vars["private"] = "private ";
+ }
+ if (*bytecode_estimate <= kMaxStaticSize) {
+ vars["final"] = "final ";
+ } else {
+ vars["final"] = "";
+ }
+
+ // The descriptor for this type.
+ printer->Print(vars,
+ // TODO(teboring): final needs to be added back. The way to fix it is to
+ // generate methods that can construct the types, and then still declare the
+ // types, and then init them in clinit with the new method calls.
+ "$private$static $final$com.google.protobuf.Descriptors.Descriptor\n"
+ " internal_$identifier$_descriptor;\n");
+ *bytecode_estimate += 30;
+
+ // And the FieldAccessorTable.
+ GenerateFieldAccessorTable(printer, bytecode_estimate);
+
+ // Generate static members for all nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // TODO(kenton): Reuse MessageGenerator objects?
+ ImmutableMessageGenerator(descriptor_->nested_type(i), context_)
+ .GenerateStaticVariables(printer, bytecode_estimate);
+ }
+}
+
+int ImmutableMessageGenerator::GenerateStaticVariableInitializers(
+ io::Printer* printer) {
+ int bytecode_estimate = 0;
+ map<string, string> vars;
+ vars["identifier"] = UniqueFileScopeIdentifier(descriptor_);
+ vars["index"] = SimpleItoa(descriptor_->index());
+ vars["classname"] = name_resolver_->GetImmutableClassName(descriptor_);
+ if (descriptor_->containing_type() != NULL) {
+ vars["parent"] = UniqueFileScopeIdentifier(
+ descriptor_->containing_type());
+ }
+
+ // The descriptor for this type.
+ if (descriptor_->containing_type() == NULL) {
+ printer->Print(vars,
+ "internal_$identifier$_descriptor =\n"
+ " getDescriptor().getMessageTypes().get($index$);\n");
+ bytecode_estimate += 30;
+ } else {
+ printer->Print(vars,
+ "internal_$identifier$_descriptor =\n"
+ " internal_$parent$_descriptor.getNestedTypes().get($index$);\n");
+ bytecode_estimate += 30;
+ }
+
+ // And the FieldAccessorTable.
+ bytecode_estimate += GenerateFieldAccessorTableInitializer(printer);
+
+ // Generate static member initializers for all nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // TODO(kenton): Reuse MessageGenerator objects?
+ bytecode_estimate +=
+ ImmutableMessageGenerator(descriptor_->nested_type(i), context_)
+ .GenerateStaticVariableInitializers(printer);
+ }
+ return bytecode_estimate;
+}
+
+void ImmutableMessageGenerator::
+GenerateFieldAccessorTable(io::Printer* printer, int* bytecode_estimate) {
+ map<string, string> vars;
+ vars["identifier"] = UniqueFileScopeIdentifier(descriptor_);
+ if (MultipleJavaFiles(descriptor_->file(), /* immutable = */ true)) {
+ // We can only make these package-private since the classes that use them
+ // are in separate files.
+ vars["private"] = "";
+ } else {
+ vars["private"] = "private ";
+ }
+ if (*bytecode_estimate <= kMaxStaticSize) {
+ vars["final"] = "final ";
+ } else {
+ vars["final"] = "";
+ }
+ vars["ver"] = GeneratedCodeVersionSuffix();
+ printer->Print(vars,
+ "$private$static $final$\n"
+ " com.google.protobuf.GeneratedMessage$ver$.FieldAccessorTable\n"
+ " internal_$identifier$_fieldAccessorTable;\n");
+
+ // 6 bytes per field and oneof
+ *bytecode_estimate += 10 + 6 * descriptor_->field_count()
+ + 6 * descriptor_->oneof_decl_count();
+}
+
+int ImmutableMessageGenerator::
+GenerateFieldAccessorTableInitializer(io::Printer* printer) {
+ int bytecode_estimate = 10;
+ printer->Print(
+ "internal_$identifier$_fieldAccessorTable = new\n"
+ " com.google.protobuf.GeneratedMessage$ver$.FieldAccessorTable(\n"
+ " internal_$identifier$_descriptor,\n"
+ " new java.lang.String[] { ",
+ "identifier", UniqueFileScopeIdentifier(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ bytecode_estimate += 6;
+ printer->Print(
+ "\"$field_name$\", ",
+ "field_name", info->capitalized_name);
+ }
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ const OneofDescriptor* oneof = descriptor_->oneof_decl(i);
+ const OneofGeneratorInfo* info = context_->GetOneofGeneratorInfo(oneof);
+ bytecode_estimate += 6;
+ printer->Print(
+ "\"$oneof_name$\", ",
+ "oneof_name", info->capitalized_name);
+ }
+ printer->Print("});\n");
+ return bytecode_estimate;
+}
+
+// ===================================================================
+
+void ImmutableMessageGenerator::GenerateInterface(io::Printer* printer) {
+ MaybePrintGeneratedAnnotation(context_, printer, descriptor_,
+ /* immutable = */ true, "OrBuilder");
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "public interface $classname$OrBuilder$idend$ extends\n"
+ " $extra_interfaces$\n"
+ " com.google.protobuf.GeneratedMessage$ver$.\n"
+ " ExtendableMessageOrBuilder<$classname$> {\n",
+ "extra_interfaces", ExtraMessageOrBuilderInterfaces(descriptor_),
+ "classname", descriptor_->name(),
+ "idend", "", "ver", GeneratedCodeVersionSuffix());
+ } else {
+ printer->Print(
+ "public interface $classname$OrBuilder$idend$ extends\n"
+ " $extra_interfaces$\n"
+ " com.google.protobuf.MessageOrBuilder {\n",
+ "extra_interfaces", ExtraMessageOrBuilderInterfaces(descriptor_),
+ "classname", descriptor_->name(),
+ "idend", "");
+ }
+ printer->Annotate("classname", "idend", descriptor_);
+
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ printer->Print("\n");
+ field_generators_.get(descriptor_->field(i))
+ .GenerateInterfaceMembers(printer);
+ }
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "\n"
+ "public $classname$.$oneof_capitalized_name$Case "
+ "get$oneof_capitalized_name$Case();\n",
+ "oneof_capitalized_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name,
+ "classname",
+ context_->GetNameResolver()->GetImmutableClassName(
+ descriptor_));
+ }
+ printer->Outdent();
+
+ printer->Print("}\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageGenerator::Generate(io::Printer* printer) {
+ bool is_own_file = IsOwnFile(descriptor_, /* immutable = */ true);
+
+ map<string, string> variables;
+ variables["static"] = is_own_file ? " " : " static ";
+ variables["classname"] = descriptor_->name();
+ variables["extra_interfaces"] = ExtraMessageInterfaces(descriptor_);
+ variables["ver"] = GeneratedCodeVersionSuffix();
+
+ WriteMessageDocComment(printer, descriptor_);
+ MaybePrintGeneratedAnnotation(context_, printer, descriptor_,
+ /* immutable = */ true);
+
+ // The builder_type stores the super type name of the nested Builder class.
+ string builder_type;
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(variables,
+ "public $static$final class $classname$ extends\n");
+ printer->Annotate("classname", descriptor_);
+ printer->Print(
+ variables,
+ " com.google.protobuf.GeneratedMessage$ver$.ExtendableMessage<\n"
+ " $classname$> implements\n"
+ " $extra_interfaces$\n"
+ " $classname$OrBuilder {\n");
+ builder_type = strings::Substitute(
+ "com.google.protobuf.GeneratedMessage$1.ExtendableBuilder<$0, ?>",
+ name_resolver_->GetImmutableClassName(descriptor_),
+ GeneratedCodeVersionSuffix());
+ } else {
+ printer->Print(variables,
+ "public $static$final class $classname$ extends\n");
+ printer->Annotate("classname", descriptor_);
+ printer->Print(variables,
+ " com.google.protobuf.GeneratedMessage$ver$ implements\n"
+ " $extra_interfaces$\n"
+ " $classname$OrBuilder {\n");
+ builder_type = strings::Substitute(
+ "com.google.protobuf.GeneratedMessage$0.Builder<?>",
+ GeneratedCodeVersionSuffix());
+ }
+ printer->Indent();
+ // Using builder_type, instead of Builder, prevents the Builder class from
+ // being loaded into PermGen space when the default instance is created.
+ // This optimizes the PermGen space usage for clients that do not modify
+ // messages.
+ printer->Print(
+ "// Use $classname$.newBuilder() to construct.\n"
+ "private $classname$($buildertype$ builder) {\n"
+ " super(builder);\n"
+ "}\n",
+ "classname", descriptor_->name(),
+ "buildertype", builder_type);
+ printer->Print(
+ "private $classname$() {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+ GenerateInitializers(printer);
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+
+ printer->Print(
+ "@java.lang.Override\n"
+ "public final com.google.protobuf.UnknownFieldSet\n"
+ "getUnknownFields() {\n");
+ if (PreserveUnknownFields(descriptor_)) {
+ printer->Print(
+ " return this.unknownFields;\n");
+ } else {
+ printer->Print(
+ " return com.google.protobuf.UnknownFieldSet.getDefaultInstance();\n");
+ }
+ printer->Print(
+ "}\n");
+
+ if (context_->HasGeneratedMethods(descriptor_)) {
+ GenerateParsingConstructor(printer);
+ }
+
+ GenerateDescriptorMethods(printer);
+
+ // Nested types
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ EnumGenerator(descriptor_->enum_type(i), true, context_)
+ .Generate(printer);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // Don't generate Java classes for map entry messages.
+ if (IsMapEntry(descriptor_->nested_type(i))) continue;
+ ImmutableMessageGenerator messageGenerator(
+ descriptor_->nested_type(i), context_);
+ messageGenerator.GenerateInterface(printer);
+ messageGenerator.Generate(printer);
+ }
+
+ if (GenerateHasBits(descriptor_)) {
+ // Integers for bit fields.
+ int totalBits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ totalBits += field_generators_.get(descriptor_->field(i))
+ .GetNumBitsForMessage();
+ }
+ int totalInts = (totalBits + 31) / 32;
+ for (int i = 0; i < totalInts; i++) {
+ printer->Print("private int $bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+
+ // oneof
+ map<string, string> vars;
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ vars["oneof_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name;
+ vars["oneof_capitalized_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name;
+ vars["oneof_index"] = SimpleItoa(descriptor_->oneof_decl(i)->index());
+ // oneofCase_ and oneof_
+ printer->Print(vars,
+ "private int $oneof_name$Case_ = 0;\n"
+ "private java.lang.Object $oneof_name$_;\n");
+ // OneofCase enum
+ printer->Print(vars,
+ "public enum $oneof_capitalized_name$Case\n"
+ " implements com.google.protobuf.Internal.EnumLite {\n");
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "$field_name$($field_number$),\n",
+ "field_name",
+ ToUpper(field->name()),
+ "field_number",
+ SimpleItoa(field->number()));
+ }
+ printer->Print(
+ "$cap_oneof_name$_NOT_SET(0);\n",
+ "cap_oneof_name",
+ ToUpper(vars["oneof_name"]));
+ printer->Print(vars,
+ "private final int value;\n"
+ "private $oneof_capitalized_name$Case(int value) {\n"
+ " this.value = value;\n"
+ "}\n");
+ printer->Print(vars,
+ "/**\n"
+ " * @deprecated Use {@link #forNumber(int)} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public static $oneof_capitalized_name$Case valueOf(int value) {\n"
+ " return forNumber(value);\n"
+ "}\n"
+ "\n"
+ "public static $oneof_capitalized_name$Case forNumber(int value) {\n"
+ " switch (value) {\n");
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ " case $field_number$: return $field_name$;\n",
+ "field_number",
+ SimpleItoa(field->number()),
+ "field_name",
+ ToUpper(field->name()));
+ }
+ printer->Print(
+ " case 0: return $cap_oneof_name$_NOT_SET;\n"
+ " default: return null;\n"
+ " }\n"
+ "}\n"
+ "public int getNumber() {\n"
+ " return this.value;\n"
+ "}\n",
+ "cap_oneof_name", ToUpper(vars["oneof_name"]));
+ printer->Outdent();
+ printer->Print("};\n\n");
+ // oneofCase()
+ printer->Print(vars,
+ "public $oneof_capitalized_name$Case\n"
+ "get$oneof_capitalized_name$Case() {\n"
+ " return $oneof_capitalized_name$Case.forNumber(\n"
+ " $oneof_name$Case_);\n"
+ "}\n"
+ "\n");
+ }
+
+ if (IsAnyMessage(descriptor_)) {
+ GenerateAnyMethods(printer);
+ }
+
+ // Fields
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ printer->Print("public static final int $constant_name$ = $number$;\n",
+ "constant_name", FieldConstantName(descriptor_->field(i)),
+ "number", SimpleItoa(descriptor_->field(i)->number()));
+ field_generators_.get(descriptor_->field(i)).GenerateMembers(printer);
+ printer->Print("\n");
+ }
+
+ if (context_->HasGeneratedMethods(descriptor_)) {
+ GenerateIsInitialized(printer);
+ GenerateMessageSerializationMethods(printer);
+ GenerateEqualsAndHashCode(printer);
+ }
+
+
+ GenerateParseFromMethods(printer);
+ GenerateBuilder(printer);
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(class_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+
+ // Carefully initialize the default instance in such a way that it doesn't
+ // conflict with other initialization.
+ printer->Print(
+ "private static final $classname$ DEFAULT_INSTANCE;\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+ printer->Print(
+ "static {\n"
+ " DEFAULT_INSTANCE = new $classname$();\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "public static $classname$ getDefaultInstance() {\n"
+ " return DEFAULT_INSTANCE;\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ GenerateParser(printer);
+
+ printer->Print(
+ "public $classname$ getDefaultInstanceForType() {\n"
+ " return DEFAULT_INSTANCE;\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ // Extensions must be declared after the DEFAULT_INSTANCE is initialized
+ // because the DEFAULT_INSTANCE is used by the extension to lazily retrieve
+ // the outer class's FileDescriptor.
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ ImmutableExtensionGenerator(descriptor_->extension(i), context_)
+ .Generate(printer);
+ }
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+
+// ===================================================================
+
+void ImmutableMessageGenerator::
+GenerateMessageSerializationMethods(io::Printer* printer) {
+ google::protobuf::scoped_array<const FieldDescriptor * > sorted_fields(
+ SortFieldsByNumber(descriptor_));
+
+ vector<const Descriptor::ExtensionRange*> sorted_extensions;
+ for (int i = 0; i < descriptor_->extension_range_count(); ++i) {
+ sorted_extensions.push_back(descriptor_->extension_range(i));
+ }
+ std::sort(sorted_extensions.begin(), sorted_extensions.end(),
+ ExtensionRangeOrdering());
+
+ printer->Print(
+ "public void writeTo(com.google.protobuf.CodedOutputStream output)\n"
+ " throws java.io.IOException {\n");
+ printer->Indent();
+ if (HasPackedFields(descriptor_)) {
+ // writeTo(CodedOutputStream output) might be invoked without
+ // getSerializedSize() ever being called, but we need the memoized
+ // sizes in case this message has packed fields. Rather than emit checks for
+ // each packed field, just call getSerializedSize() up front.
+ // In most cases, getSerializedSize() will have already been called anyway
+ // by one of the wrapper writeTo() methods, making this call cheap.
+ printer->Print(
+ "getSerializedSize();\n");
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ if (descriptor_->options().message_set_wire_format()) {
+ printer->Print(
+ "com.google.protobuf.GeneratedMessage$ver$\n"
+ " .ExtendableMessage<$classname$>.ExtensionWriter\n"
+ " extensionWriter = newMessageSetExtensionWriter();\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+ } else {
+ printer->Print(
+ "com.google.protobuf.GeneratedMessage$ver$\n"
+ " .ExtendableMessage<$classname$>.ExtensionWriter\n"
+ " extensionWriter = newExtensionWriter();\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+ }
+ }
+
+ // Merge the fields and the extension ranges, both sorted by field number.
+ for (int i = 0, j = 0;
+ i < descriptor_->field_count() || j < sorted_extensions.size();
+ ) {
+ if (i == descriptor_->field_count()) {
+ GenerateSerializeOneExtensionRange(printer, sorted_extensions[j++]);
+ } else if (j == sorted_extensions.size()) {
+ GenerateSerializeOneField(printer, sorted_fields[i++]);
+ } else if (sorted_fields[i]->number() < sorted_extensions[j]->start) {
+ GenerateSerializeOneField(printer, sorted_fields[i++]);
+ } else {
+ GenerateSerializeOneExtensionRange(printer, sorted_extensions[j++]);
+ }
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (descriptor_->options().message_set_wire_format()) {
+ printer->Print(
+ "unknownFields.writeAsMessageSetTo(output);\n");
+ } else {
+ printer->Print(
+ "unknownFields.writeTo(output);\n");
+ }
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n"
+ "public int getSerializedSize() {\n"
+ " int size = memoizedSize;\n"
+ " if (size != -1) return size;\n"
+ "\n"
+ " size = 0;\n");
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(sorted_fields[i]).GenerateSerializedSizeCode(printer);
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ if (descriptor_->options().message_set_wire_format()) {
+ printer->Print(
+ "size += extensionsSerializedSizeAsMessageSet();\n");
+ } else {
+ printer->Print(
+ "size += extensionsSerializedSize();\n");
+ }
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (descriptor_->options().message_set_wire_format()) {
+ printer->Print(
+ "size += unknownFields.getSerializedSizeAsMessageSet();\n");
+ } else {
+ printer->Print(
+ "size += unknownFields.getSerializedSize();\n");
+ }
+ }
+
+ printer->Outdent();
+ printer->Print(
+ " memoizedSize = size;\n"
+ " return size;\n"
+ "}\n"
+ "\n");
+
+ printer->Print(
+ "private static final long serialVersionUID = 0L;\n");
+}
+
+void ImmutableMessageGenerator::
+GenerateParseFromMethods(io::Printer* printer) {
+ // Note: These are separate from GenerateMessageSerializationMethods()
+ // because they need to be generated even for messages that are optimized
+ // for code size.
+ printer->Print(
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.ByteString data)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return PARSER.parseFrom(data);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.ByteString data,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return PARSER.parseFrom(data, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseFrom(byte[] data)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return PARSER.parseFrom(data);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " byte[] data,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return PARSER.parseFrom(data, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseFrom(java.io.InputStream input)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessage$ver$\n"
+ " .parseWithIOException(PARSER, input);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " java.io.InputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessage$ver$\n"
+ " .parseWithIOException(PARSER, input, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseDelimitedFrom(java.io.InputStream input)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessage$ver$\n"
+ " .parseDelimitedWithIOException(PARSER, input);\n"
+ "}\n"
+ "public static $classname$ parseDelimitedFrom(\n"
+ " java.io.InputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessage$ver$\n"
+ " .parseDelimitedWithIOException(PARSER, input, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.CodedInputStream input)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessage$ver$\n"
+ " .parseWithIOException(PARSER, input);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.CodedInputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessage$ver$\n"
+ " .parseWithIOException(PARSER, input, extensionRegistry);\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+}
+
+void ImmutableMessageGenerator::GenerateSerializeOneField(
+ io::Printer* printer, const FieldDescriptor* field) {
+ field_generators_.get(field).GenerateSerializationCode(printer);
+}
+
+void ImmutableMessageGenerator::GenerateSerializeOneExtensionRange(
+ io::Printer* printer, const Descriptor::ExtensionRange* range) {
+ printer->Print(
+ "extensionWriter.writeUntil($end$, output);\n",
+ "end", SimpleItoa(range->end));
+}
+
+// ===================================================================
+
+void ImmutableMessageGenerator::GenerateBuilder(io::Printer* printer) {
+ // LITE_RUNTIME implements this at the GeneratedMessageLite level.
+ printer->Print(
+ "public Builder newBuilderForType() { return newBuilder(); }\n");
+
+ printer->Print(
+ "public static Builder newBuilder() {\n"
+ " return DEFAULT_INSTANCE.toBuilder();\n"
+ "}\n"
+ "public static Builder newBuilder($classname$ prototype) {\n"
+ " return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype);\n"
+ "}\n"
+ "public Builder toBuilder() {\n"
+ " return this == DEFAULT_INSTANCE\n"
+ " ? new Builder() : new Builder().mergeFrom(this);\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "@java.lang.Override\n"
+ "protected Builder newBuilderForType(\n"
+ " com.google.protobuf.GeneratedMessage$ver$.BuilderParent parent) {\n"
+ " Builder builder = new Builder(parent);\n"
+ " return builder;\n"
+ "}\n",
+ "ver", GeneratedCodeVersionSuffix());
+
+ MessageBuilderGenerator builderGenerator(descriptor_, context_);
+ builderGenerator.Generate(printer);
+}
+
+void ImmutableMessageGenerator::
+GenerateDescriptorMethods(io::Printer* printer) {
+ if (!descriptor_->options().no_standard_descriptor_accessor()) {
+ printer->Print(
+ "public static final com.google.protobuf.Descriptors.Descriptor\n"
+ " getDescriptor() {\n"
+ " return $fileclass$.internal_$identifier$_descriptor;\n"
+ "}\n"
+ "\n",
+ "fileclass", name_resolver_->GetImmutableClassName(descriptor_->file()),
+ "identifier", UniqueFileScopeIdentifier(descriptor_));
+ }
+ vector<const FieldDescriptor*> map_fields;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (GetJavaType(field) == JAVATYPE_MESSAGE &&
+ IsMapEntry(field->message_type())) {
+ map_fields.push_back(field);
+ }
+ }
+ if (!map_fields.empty()) {
+ printer->Print(
+ "@SuppressWarnings({\"rawtypes\"})\n"
+ "protected com.google.protobuf.MapField internalGetMapField(\n"
+ " int number) {\n"
+ " switch (number) {\n");
+ printer->Indent();
+ printer->Indent();
+ for (int i = 0; i < map_fields.size(); ++i) {
+ const FieldDescriptor* field = map_fields[i];
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ printer->Print(
+ "case $number$:\n"
+ " return internalGet$capitalized_name$();\n",
+ "number", SimpleItoa(field->number()),
+ "capitalized_name", info->capitalized_name);
+ }
+ printer->Print(
+ "default:\n"
+ " throw new RuntimeException(\n"
+ " \"Invalid map field number: \" + number);\n");
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n"
+ "}\n");
+ }
+ printer->Print(
+ "protected com.google.protobuf.GeneratedMessage$ver$.FieldAccessorTable\n"
+ " internalGetFieldAccessorTable() {\n"
+ " return $fileclass$.internal_$identifier$_fieldAccessorTable\n"
+ " .ensureFieldAccessorsInitialized(\n"
+ " $classname$.class, $classname$.Builder.class);\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "fileclass", name_resolver_->GetImmutableClassName(descriptor_->file()),
+ "identifier", UniqueFileScopeIdentifier(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+}
+
+// ===================================================================
+
+void ImmutableMessageGenerator::GenerateIsInitialized(
+ io::Printer* printer) {
+ // Memoizes whether the protocol buffer is fully initialized (has all
+ // required fields). -1 means not yet computed. 0 means false and 1 means
+ // true.
+ printer->Print(
+ "private byte memoizedIsInitialized = -1;\n");
+ printer->Print(
+ "public final boolean isInitialized() {\n");
+ printer->Indent();
+
+ // Don't directly compare to -1 to avoid an Android x86 JIT bug.
+ printer->Print(
+ "byte isInitialized = memoizedIsInitialized;\n"
+ "if (isInitialized == 1) return true;\n"
+ "if (isInitialized == 0) return false;\n"
+ "\n");
+
+ // Check that all required fields in this message are set.
+ // TODO(kenton): We can optimize this when we switch to putting all the
+ // "has" fields into a single bitfield.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+
+ if (field->is_required()) {
+ printer->Print(
+ "if (!has$name$()) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " return false;\n"
+ "}\n",
+ "name", info->capitalized_name);
+ }
+ }
+
+ // Now check that all embedded messages are initialized.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ if (GetJavaType(field) == JAVATYPE_MESSAGE &&
+ HasRequiredFields(field->message_type())) {
+ switch (field->label()) {
+ case FieldDescriptor::LABEL_REQUIRED:
+ printer->Print(
+ "if (!get$name$().isInitialized()) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " return false;\n"
+ "}\n",
+ "type", name_resolver_->GetImmutableClassName(
+ field->message_type()),
+ "name", info->capitalized_name);
+ break;
+ case FieldDescriptor::LABEL_OPTIONAL:
+ if (!SupportFieldPresence(descriptor_->file()) &&
+ field->containing_oneof() != NULL) {
+ const OneofDescriptor* oneof = field->containing_oneof();
+ const OneofGeneratorInfo* oneof_info =
+ context_->GetOneofGeneratorInfo(oneof);
+ printer->Print(
+ "if ($oneof_name$Case_ == $field_number$) {\n",
+ "oneof_name", oneof_info->name,
+ "field_number", SimpleItoa(field->number()));
+ } else {
+ printer->Print(
+ "if (has$name$()) {\n",
+ "name", info->capitalized_name);
+ }
+ printer->Print(
+ " if (!get$name$().isInitialized()) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " return false;\n"
+ " }\n"
+ "}\n",
+ "name", info->capitalized_name);
+ break;
+ case FieldDescriptor::LABEL_REPEATED:
+ if (IsMapEntry(field->message_type())) {
+ printer->Print(
+ "for ($type$ item : get$name$().values()) {\n"
+ " if (!item.isInitialized()) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " return false;\n"
+ " }\n"
+ "}\n",
+ "type", MapValueImmutableClassdName(field->message_type(),
+ name_resolver_),
+ "name", info->capitalized_name);
+ } else {
+ printer->Print(
+ "for (int i = 0; i < get$name$Count(); i++) {\n"
+ " if (!get$name$(i).isInitialized()) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " return false;\n"
+ " }\n"
+ "}\n",
+ "type", name_resolver_->GetImmutableClassName(
+ field->message_type()),
+ "name", info->capitalized_name);
+ }
+ break;
+ }
+ }
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "if (!extensionsAreInitialized()) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " return false;\n"
+ "}\n");
+ }
+
+ printer->Outdent();
+
+ printer->Print(
+ " memoizedIsInitialized = 1;\n");
+
+ printer->Print(
+ " return true;\n"
+ "}\n"
+ "\n");
+}
+
+// ===================================================================
+
+namespace {
+bool CheckHasBitsForEqualsAndHashCode(const FieldDescriptor* field) {
+ if (field->is_repeated()) {
+ return false;
+ }
+ if (SupportFieldPresence(field->file())) {
+ return true;
+ }
+ return GetJavaType(field) == JAVATYPE_MESSAGE &&
+ field->containing_oneof() == NULL;
+}
+} // namespace
+
+void ImmutableMessageGenerator::
+GenerateEqualsAndHashCode(io::Printer* printer) {
+ printer->Print(
+ "@java.lang.Override\n"
+ "public boolean equals(final java.lang.Object obj) {\n");
+ printer->Indent();
+ printer->Print(
+ "if (obj == this) {\n"
+ " return true;\n"
+ "}\n"
+ "if (!(obj instanceof $classname$)) {\n"
+ " return super.equals(obj);\n"
+ "}\n"
+ "$classname$ other = ($classname$) obj;\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print("boolean result = true;\n");
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (field->containing_oneof() == NULL) {
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ bool check_has_bits = CheckHasBitsForEqualsAndHashCode(field);
+ if (check_has_bits) {
+ printer->Print(
+ "result = result && (has$name$() == other.has$name$());\n"
+ "if (has$name$()) {\n",
+ "name", info->capitalized_name);
+ printer->Indent();
+ }
+ field_generators_.get(field).GenerateEqualsCode(printer);
+ if (check_has_bits) {
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+ }
+ }
+
+ // Compare oneofs.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "result = result && get$oneof_capitalized_name$Case().equals(\n"
+ " other.get$oneof_capitalized_name$Case());\n",
+ "oneof_capitalized_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name);
+ printer->Print(
+ "if (!result) return false;\n"
+ "switch ($oneof_name$Case_) {\n",
+ "oneof_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name);
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "case $field_number$:\n",
+ "field_number",
+ SimpleItoa(field->number()));
+ printer->Indent();
+ field_generators_.get(field).GenerateEqualsCode(printer);
+ printer->Print("break;\n");
+ printer->Outdent();
+ }
+ printer->Print(
+ "case 0:\n"
+ "default:\n");
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ // Always consider unknown fields for equality. This will sometimes return
+ // false for non-canonical ordering when running in LITE_RUNTIME but it's
+ // the best we can do.
+ printer->Print(
+ "result = result && unknownFields.equals(other.unknownFields);\n");
+ }
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "result = result &&\n"
+ " getExtensionFields().equals(other.getExtensionFields());\n");
+ }
+ printer->Print(
+ "return result;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+
+ printer->Print(
+ "@java.lang.Override\n"
+ "public int hashCode() {\n");
+ printer->Indent();
+ printer->Print(
+ "if (memoizedHashCode != 0) {\n");
+ printer->Indent();
+ printer->Print(
+ "return memoizedHashCode;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "int hash = 41;\n");
+
+ printer->Print("hash = (19 * hash) + getDescriptorForType().hashCode();\n");
+
+ // hashCode non-oneofs.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (field->containing_oneof() == NULL) {
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ bool check_has_bits = CheckHasBitsForEqualsAndHashCode(field);
+ if (check_has_bits) {
+ printer->Print(
+ "if (has$name$()) {\n",
+ "name", info->capitalized_name);
+ printer->Indent();
+ }
+ field_generators_.get(field).GenerateHashCode(printer);
+ if (check_has_bits) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+ }
+ }
+
+ // hashCode oneofs.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "switch ($oneof_name$Case_) {\n",
+ "oneof_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name);
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "case $field_number$:\n",
+ "field_number",
+ SimpleItoa(field->number()));
+ printer->Indent();
+ field_generators_.get(field).GenerateHashCode(printer);
+ printer->Print("break;\n");
+ printer->Outdent();
+ }
+ printer->Print(
+ "case 0:\n"
+ "default:\n");
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "hash = hashFields(hash, getExtensionFields());\n");
+ }
+
+ printer->Print(
+ "hash = (29 * hash) + unknownFields.hashCode();\n");
+ printer->Print(
+ "memoizedHashCode = hash;\n"
+ "return hash;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageGenerator::
+GenerateExtensionRegistrationCode(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ ImmutableExtensionGenerator(descriptor_->extension(i), context_)
+ .GenerateRegistrationCode(printer);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ ImmutableMessageGenerator(descriptor_->nested_type(i), context_)
+ .GenerateExtensionRegistrationCode(printer);
+ }
+}
+
+// ===================================================================
+void ImmutableMessageGenerator::
+GenerateParsingConstructor(io::Printer* printer) {
+ google::protobuf::scoped_array<const FieldDescriptor * > sorted_fields(
+ SortFieldsByNumber(descriptor_));
+
+ printer->Print(
+ "private $classname$(\n"
+ " com.google.protobuf.CodedInputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+
+ // Initialize all fields to default.
+ printer->Print(
+ "this();\n");
+
+ // Use builder bits to track mutable repeated fields.
+ int totalBuilderBits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const ImmutableFieldGenerator& field =
+ field_generators_.get(descriptor_->field(i));
+ totalBuilderBits += field.GetNumBitsForBuilder();
+ }
+ int totalBuilderInts = (totalBuilderBits + 31) / 32;
+ for (int i = 0; i < totalBuilderInts; i++) {
+ printer->Print("int mutable_$bit_field_name$ = 0;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ printer->Print(
+ "com.google.protobuf.UnknownFieldSet.Builder unknownFields =\n"
+ " com.google.protobuf.UnknownFieldSet.newBuilder();\n");
+ }
+
+ printer->Print(
+ "try {\n");
+ printer->Indent();
+
+ printer->Print(
+ "boolean done = false;\n"
+ "while (!done) {\n");
+ printer->Indent();
+
+ printer->Print(
+ "int tag = input.readTag();\n"
+ "switch (tag) {\n");
+ printer->Indent();
+
+ printer->Print(
+ "case 0:\n" // zero signals EOF / limit reached
+ " done = true;\n"
+ " break;\n");
+
+ if (PreserveUnknownFields(descriptor_)) {
+ printer->Print(
+ "default: {\n"
+ " if (!parseUnknownField(input, unknownFields,\n"
+ " extensionRegistry, tag)) {\n"
+ " done = true;\n" // it's an endgroup tag
+ " }\n"
+ " break;\n"
+ "}\n");
+ } else {
+ printer->Print(
+ "default: {\n"
+ " if (!input.skipField(tag)) {\n"
+ " done = true;\n" // it's an endgroup tag
+ " }\n"
+ " break;\n"
+ "}\n");
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = sorted_fields[i];
+ uint32 tag = WireFormatLite::MakeTag(field->number(),
+ WireFormat::WireTypeForFieldType(field->type()));
+
+ printer->Print(
+ "case $tag$: {\n",
+ "tag", SimpleItoa(tag));
+ printer->Indent();
+
+ field_generators_.get(field).GenerateParsingCode(printer);
+
+ printer->Outdent();
+ printer->Print(
+ " break;\n"
+ "}\n");
+
+ if (field->is_packable()) {
+ // To make packed = true wire compatible, we generate parsing code from a
+ // packed version of this field regardless of field->options().packed().
+ uint32 packed_tag = WireFormatLite::MakeTag(field->number(),
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED);
+ printer->Print(
+ "case $tag$: {\n",
+ "tag", SimpleItoa(packed_tag));
+ printer->Indent();
+
+ field_generators_.get(field).GenerateParsingCodeFromPacked(printer);
+
+ printer->Outdent();
+ printer->Print(
+ " break;\n"
+ "}\n");
+ }
+ }
+
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n" // switch (tag)
+ "}\n"); // while (!done)
+
+ printer->Outdent();
+ printer->Print(
+ "} catch (com.google.protobuf.InvalidProtocolBufferException e) {\n"
+ " throw e.setUnfinishedMessage(this);\n"
+ "} catch (java.io.IOException e) {\n"
+ " throw new com.google.protobuf.InvalidProtocolBufferException(\n"
+ " e).setUnfinishedMessage(this);\n"
+ "} finally {\n");
+ printer->Indent();
+
+ // Make repeated field list immutable.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = sorted_fields[i];
+ field_generators_.get(field).GenerateParsingDoneCode(printer);
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ // Make unknown fields immutable.
+ printer->Print("this.unknownFields = unknownFields.build();\n");
+ }
+
+ // Make extensions immutable.
+ printer->Print(
+ "makeExtensionsImmutable();\n");
+
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n" // finally
+ "}\n");
+}
+
+// ===================================================================
+void ImmutableMessageGenerator::GenerateParser(io::Printer* printer) {
+ printer->Print(
+ "$visibility$ static final com.google.protobuf.Parser<$classname$>\n"
+ " PARSER = new com.google.protobuf.AbstractParser<$classname$>() {\n",
+ "visibility",
+ ExposePublicParser(descriptor_->file()) ? "@java.lang.Deprecated public"
+ : "private",
+ "classname", descriptor_->name());
+ printer->Indent();
+ printer->Print(
+ "public $classname$ parsePartialFrom(\n"
+ " com.google.protobuf.CodedInputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n",
+ "classname", descriptor_->name());
+ if (context_->HasGeneratedMethods(descriptor_)) {
+ printer->Print(
+ " return new $classname$(input, extensionRegistry);\n",
+ "classname", descriptor_->name());
+ } else {
+ // When parsing constructor isn't generated, use builder to parse
+ // messages. Note, will fallback to use reflection based mergeFieldFrom()
+ // in AbstractMessage.Builder.
+ printer->Indent();
+ printer->Print(
+ "Builder builder = newBuilder();\n"
+ "try {\n"
+ " builder.mergeFrom(input, extensionRegistry);\n"
+ "} catch (com.google.protobuf.InvalidProtocolBufferException e) {\n"
+ " throw e.setUnfinishedMessage(builder.buildPartial());\n"
+ "} catch (java.io.IOException e) {\n"
+ " throw new com.google.protobuf.InvalidProtocolBufferException(\n"
+ " e.getMessage()).setUnfinishedMessage(\n"
+ " builder.buildPartial());\n"
+ "}\n"
+ "return builder.buildPartial();\n");
+ printer->Outdent();
+ }
+ printer->Print(
+ "}\n");
+ printer->Outdent();
+ printer->Print(
+ "};\n"
+ "\n");
+
+ printer->Print(
+ "public static com.google.protobuf.Parser<$classname$> parser() {\n"
+ " return PARSER;\n"
+ "}\n"
+ "\n"
+ "@java.lang.Override\n"
+ "public com.google.protobuf.Parser<$classname$> getParserForType() {\n"
+ " return PARSER;\n"
+ "}\n"
+ "\n",
+ "classname", descriptor_->name());
+}
+
+// ===================================================================
+void ImmutableMessageGenerator::GenerateInitializers(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateInitializationCode(printer);
+ }
+ }
+}
+
+
+void ImmutableMessageGenerator::GenerateAnyMethods(io::Printer* printer) {
+ printer->Print(
+ "private static String getTypeUrl(\n"
+ " java.lang.String typeUrlPrefix,\n"
+ " com.google.protobuf.Descriptors.Descriptor descriptor) {\n"
+ " return typeUrlPrefix.endsWith(\"/\")\n"
+ " ? typeUrlPrefix + descriptor.getFullName()\n"
+ " : typeUrlPrefix + \"/\" + descriptor.getFullName();\n"
+ "}\n"
+ "\n"
+ "private static String getTypeNameFromTypeUrl(\n"
+ " java.lang.String typeUrl) {\n"
+ " int pos = typeUrl.lastIndexOf('/');\n"
+ " return pos == -1 ? \"\" : typeUrl.substring(pos + 1);\n"
+ "}\n"
+ "\n"
+ "public static <T extends com.google.protobuf.Message> Any pack(\n"
+ " T message) {\n"
+ " return Any.newBuilder()\n"
+ " .setTypeUrl(getTypeUrl(\"type.googleapis.com\",\n"
+ " message.getDescriptorForType()))\n"
+ " .setValue(message.toByteString())\n"
+ " .build();\n"
+ "}\n"
+ "\n"
+ "/**\n"
+ " * Packs a message uisng the given type URL prefix. The type URL will\n"
+ " * be constructed by concatenating the message type's full name to the\n"
+ " * prefix with an optional \"/\" separator if the prefix doesn't end\n"
+ " * with \"/\" already.\n"
+ " */\n"
+ "public static <T extends com.google.protobuf.Message> Any pack(\n"
+ " T message, java.lang.String typeUrlPrefix) {\n"
+ " return Any.newBuilder()\n"
+ " .setTypeUrl(getTypeUrl(typeUrlPrefix,\n"
+ " message.getDescriptorForType()))\n"
+ " .setValue(message.toByteString())\n"
+ " .build();\n"
+ "}\n"
+ "\n"
+ "public <T extends com.google.protobuf.Message> boolean is(\n"
+ " java.lang.Class<T> clazz) {\n"
+ " T defaultInstance =\n"
+ " com.google.protobuf.Internal.getDefaultInstance(clazz);\n"
+ " return getTypeNameFromTypeUrl(getTypeUrl()).equals(\n"
+ " defaultInstance.getDescriptorForType().getFullName());\n"
+ "}\n"
+ "\n"
+ "private volatile com.google.protobuf.Message cachedUnpackValue;\n"
+ "\n"
+ "public <T extends com.google.protobuf.Message> T unpack(\n"
+ " java.lang.Class<T> clazz)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " if (!is(clazz)) {\n"
+ " throw new com.google.protobuf.InvalidProtocolBufferException(\n"
+ " \"Type of the Any message does not match the given class.\");\n"
+ " }\n"
+ " if (cachedUnpackValue != null) {\n"
+ " return (T) cachedUnpackValue;\n"
+ " }\n"
+ " T defaultInstance =\n"
+ " com.google.protobuf.Internal.getDefaultInstance(clazz);\n"
+ " T result = (T) defaultInstance.getParserForType()\n"
+ " .parseFrom(getValue());\n"
+ " cachedUnpackValue = result;\n"
+ " return result;\n"
+ "}\n");
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.h
new file mode 100644
index 0000000000..da1447c176
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message.h
@@ -0,0 +1,142 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_H__
+
+#include <string>
+#include <map>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+static const int kMaxStaticSize = 1 << 15; // aka 32k
+
+class MessageGenerator {
+ public:
+ explicit MessageGenerator(const Descriptor* descriptor);
+ virtual ~MessageGenerator();
+
+ // All static variables have to be declared at the top-level of the file
+ // so that we can control initialization order, which is important for
+ // DescriptorProto bootstrapping to work.
+ virtual void GenerateStaticVariables(
+ io::Printer* printer, int* bytecode_estimate) = 0;
+
+ // Output code which initializes the static variables generated by
+ // GenerateStaticVariables(). Returns an estimate of bytecode size.
+ virtual int GenerateStaticVariableInitializers(io::Printer* printer) = 0;
+
+ // Generate the class itself.
+ virtual void Generate(io::Printer* printer) = 0;
+
+ // Generates the base interface that both the class and its builder implement
+ virtual void GenerateInterface(io::Printer* printer) = 0;
+
+ // Generate code to register all contained extensions with an
+ // ExtensionRegistry.
+ virtual void GenerateExtensionRegistrationCode(io::Printer* printer) = 0;
+
+ protected:
+ const Descriptor* descriptor_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageGenerator);
+};
+
+class ImmutableMessageGenerator : public MessageGenerator {
+ public:
+ ImmutableMessageGenerator(const Descriptor* descriptor, Context* context);
+ virtual ~ImmutableMessageGenerator();
+
+ virtual void Generate(io::Printer* printer);
+ virtual void GenerateInterface(io::Printer* printer);
+ virtual void GenerateExtensionRegistrationCode(io::Printer* printer);
+ virtual void GenerateStaticVariables(
+ io::Printer* printer, int* bytecode_estimate);
+
+ // Returns an estimate of the number of bytes the printed code will compile to
+ virtual int GenerateStaticVariableInitializers(io::Printer* printer);
+
+ private:
+
+ void GenerateFieldAccessorTable(io::Printer* printer, int* bytecode_estimate);
+
+ // Returns an estimate of the number of bytes the printed code will compile to
+ int GenerateFieldAccessorTableInitializer(io::Printer* printer);
+
+ void GenerateMessageSerializationMethods(io::Printer* printer);
+ void GenerateParseFromMethods(io::Printer* printer);
+ void GenerateSerializeOneField(io::Printer* printer,
+ const FieldDescriptor* field);
+ void GenerateSerializeOneExtensionRange(
+ io::Printer* printer, const Descriptor::ExtensionRange* range);
+
+ void GenerateBuilder(io::Printer* printer);
+ void GenerateIsInitialized(io::Printer* printer);
+ void GenerateDescriptorMethods(io::Printer* printer);
+ void GenerateInitializers(io::Printer* printer);
+ void GenerateEqualsAndHashCode(io::Printer* printer);
+ void GenerateParser(io::Printer* printer);
+ void GenerateParsingConstructor(io::Printer* printer);
+ void GenerateAnyMethods(io::Printer* printer);
+
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ FieldGeneratorMap<ImmutableFieldGenerator> field_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableMessageGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.cc
new file mode 100644
index 0000000000..421546943a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.cc
@@ -0,0 +1,737 @@
+// 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: dweis@google.com (Daniel Weis)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <google/protobuf/compiler/java/java_message_builder.h>
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_enum.h>
+#include <google/protobuf/compiler/java/java_extension.h>
+#include <google/protobuf/compiler/java/java_generator_factory.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+bool GenerateHasBits(const Descriptor* descriptor) {
+ return SupportFieldPresence(descriptor->file()) ||
+ HasRepeatedFields(descriptor);
+}
+
+string MapValueImmutableClassdName(const Descriptor* descriptor,
+ ClassNameResolver* name_resolver) {
+ const FieldDescriptor* value_field = descriptor->FindFieldByName("value");
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, value_field->type());
+ return name_resolver->GetImmutableClassName(value_field->message_type());
+}
+} // namespace
+
+MessageBuilderGenerator::MessageBuilderGenerator(
+ const Descriptor* descriptor, Context* context)
+ : descriptor_(descriptor), context_(context),
+ name_resolver_(context->GetNameResolver()),
+ field_generators_(descriptor, context_) {
+ GOOGLE_CHECK(HasDescriptorMethods(descriptor->file(), context->EnforceLite()))
+ << "Generator factory error: A non-lite message generator is used to "
+ "generate lite messages.";
+}
+
+MessageBuilderGenerator::~MessageBuilderGenerator() {}
+
+void MessageBuilderGenerator::
+Generate(io::Printer* printer) {
+ WriteMessageDocComment(printer, descriptor_);
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "public static final class Builder extends\n"
+ " com.google.protobuf.GeneratedMessage$ver$.ExtendableBuilder<\n"
+ " $classname$, Builder> implements\n"
+ " $extra_interfaces$\n"
+ " $classname$OrBuilder {\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "extra_interfaces", ExtraBuilderInterfaces(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+ } else {
+ printer->Print(
+ "public static final class Builder extends\n"
+ " com.google.protobuf.GeneratedMessage$ver$.Builder<Builder> implements\n"
+ " $extra_interfaces$\n"
+ " $classname$OrBuilder {\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "extra_interfaces", ExtraBuilderInterfaces(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+ }
+ printer->Indent();
+
+ GenerateDescriptorMethods(printer);
+ GenerateCommonBuilderMethods(printer);
+
+ if (context_->HasGeneratedMethods(descriptor_)) {
+ GenerateIsInitialized(printer);
+ GenerateBuilderParsingMethods(printer);
+ }
+
+ // oneof
+ map<string, string> vars;
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ vars["oneof_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name;
+ vars["oneof_capitalized_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name;
+ vars["oneof_index"] = SimpleItoa(descriptor_->oneof_decl(i)->index());
+ // oneofCase_ and oneof_
+ printer->Print(vars,
+ "private int $oneof_name$Case_ = 0;\n"
+ "private java.lang.Object $oneof_name$_;\n");
+ // oneofCase() and clearOneof()
+ printer->Print(vars,
+ "public $oneof_capitalized_name$Case\n"
+ " get$oneof_capitalized_name$Case() {\n"
+ " return $oneof_capitalized_name$Case.forNumber(\n"
+ " $oneof_name$Case_);\n"
+ "}\n"
+ "\n"
+ "public Builder clear$oneof_capitalized_name$() {\n"
+ " $oneof_name$Case_ = 0;\n"
+ " $oneof_name$_ = null;\n");
+ printer->Print(" onChanged();\n");
+ printer->Print(
+ " return this;\n"
+ "}\n"
+ "\n");
+ }
+
+ if (GenerateHasBits(descriptor_)) {
+ // Integers for bit fields.
+ int totalBits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ totalBits += field_generators_.get(descriptor_->field(i))
+ .GetNumBitsForBuilder();
+ }
+ int totalInts = (totalBits + 31) / 32;
+ for (int i = 0; i < totalInts; i++) {
+ printer->Print("private int $bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ printer->Print("\n");
+ field_generators_.get(descriptor_->field(i))
+ .GenerateBuilderMembers(printer);
+ }
+
+ if (!PreserveUnknownFields(descriptor_)) {
+ printer->Print(
+ "public final Builder setUnknownFields(\n"
+ " final com.google.protobuf.UnknownFieldSet unknownFields) {\n"
+ " return this;\n"
+ "}\n"
+ "\n"
+ "public final Builder mergeUnknownFields(\n"
+ " final com.google.protobuf.UnknownFieldSet unknownFields) {\n"
+ " return this;\n"
+ "}\n"
+ "\n");
+ } else {
+ printer->Print(
+ "public final Builder setUnknownFields(\n"
+ " final com.google.protobuf.UnknownFieldSet unknownFields) {\n"
+ " return super.setUnknownFields(unknownFields);\n"
+ "}\n"
+ "\n"
+ "public final Builder mergeUnknownFields(\n"
+ " final com.google.protobuf.UnknownFieldSet unknownFields) {\n"
+ " return super.mergeUnknownFields(unknownFields);\n"
+ "}\n"
+ "\n");
+ }
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(builder_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+// ===================================================================
+
+void MessageBuilderGenerator::
+GenerateDescriptorMethods(io::Printer* printer) {
+ if (!descriptor_->options().no_standard_descriptor_accessor()) {
+ printer->Print(
+ "public static final com.google.protobuf.Descriptors.Descriptor\n"
+ " getDescriptor() {\n"
+ " return $fileclass$.internal_$identifier$_descriptor;\n"
+ "}\n"
+ "\n",
+ "fileclass", name_resolver_->GetImmutableClassName(descriptor_->file()),
+ "identifier", UniqueFileScopeIdentifier(descriptor_));
+ }
+ vector<const FieldDescriptor*> map_fields;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (GetJavaType(field) == JAVATYPE_MESSAGE &&
+ IsMapEntry(field->message_type())) {
+ map_fields.push_back(field);
+ }
+ }
+ if (!map_fields.empty()) {
+ printer->Print(
+ "@SuppressWarnings({\"rawtypes\"})\n"
+ "protected com.google.protobuf.MapField internalGetMapField(\n"
+ " int number) {\n"
+ " switch (number) {\n");
+ printer->Indent();
+ printer->Indent();
+ for (int i = 0; i < map_fields.size(); ++i) {
+ const FieldDescriptor* field = map_fields[i];
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ printer->Print(
+ "case $number$:\n"
+ " return internalGet$capitalized_name$();\n",
+ "number", SimpleItoa(field->number()),
+ "capitalized_name", info->capitalized_name);
+ }
+ printer->Print(
+ "default:\n"
+ " throw new RuntimeException(\n"
+ " \"Invalid map field number: \" + number);\n");
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n"
+ "}\n");
+ printer->Print(
+ "@SuppressWarnings({\"rawtypes\"})\n"
+ "protected com.google.protobuf.MapField internalGetMutableMapField(\n"
+ " int number) {\n"
+ " switch (number) {\n");
+ printer->Indent();
+ printer->Indent();
+ for (int i = 0; i < map_fields.size(); ++i) {
+ const FieldDescriptor* field = map_fields[i];
+ const FieldGeneratorInfo* info =
+ context_->GetFieldGeneratorInfo(field);
+ printer->Print(
+ "case $number$:\n"
+ " return internalGetMutable$capitalized_name$();\n",
+ "number", SimpleItoa(field->number()),
+ "capitalized_name", info->capitalized_name);
+ }
+ printer->Print(
+ "default:\n"
+ " throw new RuntimeException(\n"
+ " \"Invalid map field number: \" + number);\n");
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n"
+ "}\n");
+ }
+ printer->Print(
+ "protected com.google.protobuf.GeneratedMessage$ver$.FieldAccessorTable\n"
+ " internalGetFieldAccessorTable() {\n"
+ " return $fileclass$.internal_$identifier$_fieldAccessorTable\n"
+ " .ensureFieldAccessorsInitialized(\n"
+ " $classname$.class, $classname$.Builder.class);\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "fileclass", name_resolver_->GetImmutableClassName(descriptor_->file()),
+ "identifier", UniqueFileScopeIdentifier(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+}
+
+// ===================================================================
+
+void MessageBuilderGenerator::
+GenerateCommonBuilderMethods(io::Printer* printer) {
+ printer->Print(
+ "// Construct using $classname$.newBuilder()\n"
+ "private Builder() {\n"
+ " maybeForceBuilderInitialization();\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "private Builder(\n"
+ " com.google.protobuf.GeneratedMessage$ver$.BuilderParent parent) {\n"
+ " super(parent);\n"
+ " maybeForceBuilderInitialization();\n"
+ "}\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "ver", GeneratedCodeVersionSuffix());
+
+ printer->Print(
+ "private void maybeForceBuilderInitialization() {\n"
+ " if (com.google.protobuf.GeneratedMessage$ver$\n"
+ " .alwaysUseFieldBuilders) {\n",
+ "ver", GeneratedCodeVersionSuffix());
+
+ printer->Indent();
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateFieldBuilderInitializationCode(printer);
+ }
+ }
+ printer->Outdent();
+ printer->Outdent();
+
+ printer->Print(
+ " }\n"
+ "}\n");
+
+ printer->Print(
+ "public Builder clear() {\n"
+ " super.clear();\n");
+
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateBuilderClearCode(printer);
+ }
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "$oneof_name$Case_ = 0;\n"
+ "$oneof_name$_ = null;\n",
+ "oneof_name", context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name);
+ }
+
+ printer->Outdent();
+
+ printer->Print(
+ " return this;\n"
+ "}\n"
+ "\n");
+
+ printer->Print(
+ "public com.google.protobuf.Descriptors.Descriptor\n"
+ " getDescriptorForType() {\n"
+ " return $fileclass$.internal_$identifier$_descriptor;\n"
+ "}\n"
+ "\n",
+ "fileclass", name_resolver_->GetImmutableClassName(descriptor_->file()),
+ "identifier", UniqueFileScopeIdentifier(descriptor_));
+
+ // LITE runtime implements this in GeneratedMessageLite.
+ printer->Print(
+ "public $classname$ getDefaultInstanceForType() {\n"
+ " return $classname$.getDefaultInstance();\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "public $classname$ build() {\n"
+ " $classname$ result = buildPartial();\n"
+ " if (!result.isInitialized()) {\n"
+ " throw newUninitializedMessageException(result);\n"
+ " }\n"
+ " return result;\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "public $classname$ buildPartial() {\n"
+ " $classname$ result = new $classname$(this);\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Indent();
+
+ int totalBuilderBits = 0;
+ int totalMessageBits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const ImmutableFieldGenerator& field =
+ field_generators_.get(descriptor_->field(i));
+ totalBuilderBits += field.GetNumBitsForBuilder();
+ totalMessageBits += field.GetNumBitsForMessage();
+ }
+ int totalBuilderInts = (totalBuilderBits + 31) / 32;
+ int totalMessageInts = (totalMessageBits + 31) / 32;
+
+ if (GenerateHasBits(descriptor_)) {
+ // Local vars for from and to bit fields to avoid accessing the builder and
+ // message over and over for these fields. Seems to provide a slight
+ // perforamance improvement in micro benchmark and this is also what proto1
+ // code does.
+ for (int i = 0; i < totalBuilderInts; i++) {
+ printer->Print("int from_$bit_field_name$ = $bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ for (int i = 0; i < totalMessageInts; i++) {
+ printer->Print("int to_$bit_field_name$ = 0;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+
+ // Output generation code for each field.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i)).GenerateBuildingCode(printer);
+ }
+
+ if (GenerateHasBits(descriptor_)) {
+ // Copy the bit field results to the generated message
+ for (int i = 0; i < totalMessageInts; i++) {
+ printer->Print("result.$bit_field_name$ = to_$bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print("result.$oneof_name$Case_ = $oneof_name$Case_;\n",
+ "oneof_name", context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name);
+ }
+
+ printer->Outdent();
+
+ printer->Print(
+ " onBuilt();\n");
+
+ printer->Print(
+ " return result;\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "public Builder clone() {\n"
+ " return (Builder) super.clone();\n"
+ "}\n"
+ "public Builder setField(\n"
+ " com.google.protobuf.Descriptors.FieldDescriptor field,\n"
+ " Object value) {\n"
+ " return (Builder) super.setField(field, value);\n"
+ "}\n"
+ "public Builder clearField(\n"
+ " com.google.protobuf.Descriptors.FieldDescriptor field) {\n"
+ " return (Builder) super.clearField(field);\n"
+ "}\n"
+ "public Builder clearOneof(\n"
+ " com.google.protobuf.Descriptors.OneofDescriptor oneof) {\n"
+ " return (Builder) super.clearOneof(oneof);\n"
+ "}\n"
+ "public Builder setRepeatedField(\n"
+ " com.google.protobuf.Descriptors.FieldDescriptor field,\n"
+ " int index, Object value) {\n"
+ " return (Builder) super.setRepeatedField(field, index, value);\n"
+ "}\n"
+ "public Builder addRepeatedField(\n"
+ " com.google.protobuf.Descriptors.FieldDescriptor field,\n"
+ " Object value) {\n"
+ " return (Builder) super.addRepeatedField(field, value);\n"
+ "}\n");
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "public <Type> Builder setExtension(\n"
+ " com.google.protobuf.GeneratedMessage.GeneratedExtension<\n"
+ " $classname$, Type> extension,\n"
+ " Type value) {\n"
+ " return (Builder) super.setExtension(extension, value);\n"
+ "}\n"
+ "public <Type> Builder setExtension(\n"
+ " com.google.protobuf.GeneratedMessage.GeneratedExtension<\n"
+ " $classname$, java.util.List<Type>> extension,\n"
+ " int index, Type value) {\n"
+ " return (Builder) super.setExtension(extension, index, value);\n"
+ "}\n"
+ "public <Type> Builder addExtension(\n"
+ " com.google.protobuf.GeneratedMessage.GeneratedExtension<\n"
+ " $classname$, java.util.List<Type>> extension,\n"
+ " Type value) {\n"
+ " return (Builder) super.addExtension(extension, value);\n"
+ "}\n"
+ "public <Type> Builder clearExtension(\n"
+ " com.google.protobuf.GeneratedMessage.GeneratedExtension<\n"
+ " $classname$, ?> extension) {\n"
+ " return (Builder) super.clearExtension(extension);\n"
+ "}\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+ }
+
+ // -----------------------------------------------------------------
+
+ if (context_->HasGeneratedMethods(descriptor_)) {
+ printer->Print(
+ "public Builder mergeFrom(com.google.protobuf.Message other) {\n"
+ " if (other instanceof $classname$) {\n"
+ " return mergeFrom(($classname$)other);\n"
+ " } else {\n"
+ " super.mergeFrom(other);\n"
+ " return this;\n"
+ " }\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "public Builder mergeFrom($classname$ other) {\n"
+ // Optimization: If other is the default instance, we know none of its
+ // fields are set so we can skip the merge.
+ " if (other == $classname$.getDefaultInstance()) return this;\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(
+ descriptor_->field(i)).GenerateMergingCode(printer);
+ }
+ }
+
+ // Merge oneof fields.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
+ printer->Print(
+ "switch (other.get$oneof_capitalized_name$Case()) {\n",
+ "oneof_capitalized_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name);
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "case $field_name$: {\n",
+ "field_name",
+ ToUpper(field->name()));
+ printer->Indent();
+ field_generators_.get(field).GenerateMergingCode(printer);
+ printer->Print(
+ "break;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+ printer->Print(
+ "case $cap_oneof_name$_NOT_SET: {\n"
+ " break;\n"
+ "}\n",
+ "cap_oneof_name",
+ ToUpper(context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name));
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+
+ printer->Outdent();
+
+ // if message type has extensions
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ " this.mergeExtensionFields(other);\n");
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ printer->Print(
+ " this.mergeUnknownFields(other.unknownFields);\n");
+ }
+
+ printer->Print(
+ " onChanged();\n");
+
+ printer->Print(
+ " return this;\n"
+ "}\n"
+ "\n");
+
+ }
+}
+
+// ===================================================================
+
+void MessageBuilderGenerator::
+GenerateBuilderParsingMethods(io::Printer* printer) {
+ printer->Print(
+ "public Builder mergeFrom(\n"
+ " com.google.protobuf.CodedInputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws java.io.IOException {\n"
+ " $classname$ parsedMessage = null;\n"
+ " try {\n"
+ " parsedMessage = PARSER.parsePartialFrom(input, extensionRegistry);\n"
+ " } catch (com.google.protobuf.InvalidProtocolBufferException e) {\n"
+ " parsedMessage = ($classname$) e.getUnfinishedMessage();\n"
+ " throw e.unwrapIOException();\n"
+ " } finally {\n"
+ " if (parsedMessage != null) {\n"
+ " mergeFrom(parsedMessage);\n"
+ " }\n"
+ " }\n"
+ " return this;\n"
+ "}\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+}
+
+// ===================================================================
+
+void MessageBuilderGenerator::GenerateIsInitialized(
+ io::Printer* printer) {
+ printer->Print(
+ "public final boolean isInitialized() {\n");
+ printer->Indent();
+
+ // Check that all required fields in this message are set.
+ // TODO(kenton): We can optimize this when we switch to putting all the
+ // "has" fields into a single bitfield.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+
+ if (field->is_required()) {
+ printer->Print(
+ "if (!has$name$()) {\n"
+ " return false;\n"
+ "}\n",
+ "name", info->capitalized_name);
+ }
+ }
+
+ // Now check that all embedded messages are initialized.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ if (GetJavaType(field) == JAVATYPE_MESSAGE &&
+ HasRequiredFields(field->message_type())) {
+ switch (field->label()) {
+ case FieldDescriptor::LABEL_REQUIRED:
+ printer->Print(
+ "if (!get$name$().isInitialized()) {\n"
+ " return false;\n"
+ "}\n",
+ "type", name_resolver_->GetImmutableClassName(
+ field->message_type()),
+ "name", info->capitalized_name);
+ break;
+ case FieldDescriptor::LABEL_OPTIONAL:
+ if (!SupportFieldPresence(descriptor_->file()) &&
+ field->containing_oneof() != NULL) {
+ const OneofDescriptor* oneof = field->containing_oneof();
+ const OneofGeneratorInfo* oneof_info =
+ context_->GetOneofGeneratorInfo(oneof);
+ printer->Print(
+ "if ($oneof_name$Case_ == $field_number$) {\n",
+ "oneof_name", oneof_info->name,
+ "field_number", SimpleItoa(field->number()));
+ } else {
+ printer->Print(
+ "if (has$name$()) {\n",
+ "name", info->capitalized_name);
+ }
+ printer->Print(
+ " if (!get$name$().isInitialized()) {\n"
+ " return false;\n"
+ " }\n"
+ "}\n",
+ "name", info->capitalized_name);
+ break;
+ case FieldDescriptor::LABEL_REPEATED:
+ if (IsMapEntry(field->message_type())) {
+ printer->Print(
+ "for ($type$ item : get$name$().values()) {\n"
+ " if (!item.isInitialized()) {\n"
+ " return false;\n"
+ " }\n"
+ "}\n",
+ "type", MapValueImmutableClassdName(field->message_type(),
+ name_resolver_),
+ "name", info->capitalized_name);
+ } else {
+ printer->Print(
+ "for (int i = 0; i < get$name$Count(); i++) {\n"
+ " if (!get$name$(i).isInitialized()) {\n"
+ " return false;\n"
+ " }\n"
+ "}\n",
+ "type", name_resolver_->GetImmutableClassName(
+ field->message_type()),
+ "name", info->capitalized_name);
+ }
+ break;
+ }
+ }
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "if (!extensionsAreInitialized()) {\n"
+ " return false;\n"
+ "}\n");
+ }
+
+ printer->Outdent();
+
+ printer->Print(
+ " return true;\n"
+ "}\n"
+ "\n");
+}
+
+// ===================================================================
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.h
new file mode 100644
index 0000000000..015ea06206
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder.h
@@ -0,0 +1,86 @@
+// 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: dweis@google.com (Daniel Weis)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_BUILDER_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_BUILDER_H__
+
+#include <string>
+#include <map>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class MessageBuilderGenerator {
+ public:
+ explicit MessageBuilderGenerator(const Descriptor* descriptor,
+ Context* context);
+ virtual ~MessageBuilderGenerator();
+
+ virtual void Generate(io::Printer* printer);
+
+ private:
+ void GenerateCommonBuilderMethods(io::Printer* printer);
+ void GenerateDescriptorMethods(io::Printer* printer);
+ void GenerateBuilderParsingMethods(io::Printer* printer);
+ void GenerateIsInitialized(io::Printer* printer);
+
+ const Descriptor* descriptor_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ FieldGeneratorMap<ImmutableFieldGenerator> field_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageBuilderGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_BUILDER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.cc
new file mode 100644
index 0000000000..dd429dc93e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.cc
@@ -0,0 +1,179 @@
+// 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: dweis@google.com (Daniel Weis)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <google/protobuf/compiler/java/java_message_builder_lite.h>
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_enum.h>
+#include <google/protobuf/compiler/java/java_extension.h>
+#include <google/protobuf/compiler/java/java_generator_factory.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+bool GenerateHasBits(const Descriptor* descriptor) {
+ return SupportFieldPresence(descriptor->file()) ||
+ HasRepeatedFields(descriptor);
+}
+
+string MapValueImmutableClassdName(const Descriptor* descriptor,
+ ClassNameResolver* name_resolver) {
+ const FieldDescriptor* value_field = descriptor->FindFieldByName("value");
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, value_field->type());
+ return name_resolver->GetImmutableClassName(value_field->message_type());
+}
+} // namespace
+
+MessageBuilderLiteGenerator::MessageBuilderLiteGenerator(
+ const Descriptor* descriptor, Context* context)
+ : descriptor_(descriptor), context_(context),
+ name_resolver_(context->GetNameResolver()),
+ field_generators_(descriptor, context_) {
+ GOOGLE_CHECK(!HasDescriptorMethods(descriptor->file(), context->EnforceLite()))
+ << "Generator factory error: A lite message generator is used to "
+ "generate non-lite messages.";
+}
+
+MessageBuilderLiteGenerator::~MessageBuilderLiteGenerator() {}
+
+void MessageBuilderLiteGenerator::
+Generate(io::Printer* printer) {
+ WriteMessageDocComment(printer, descriptor_);
+ printer->Print(
+ "public static final class Builder extends\n"
+ " com.google.protobuf.GeneratedMessageLite.$extendible$Builder<\n"
+ " $classname$, Builder> implements\n"
+ " $extra_interfaces$\n"
+ " $classname$OrBuilder {\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_),
+ "extra_interfaces", ExtraBuilderInterfaces(descriptor_),
+ "extendible",
+ descriptor_->extension_range_count() > 0 ? "Extendable" : "");
+ printer->Indent();
+
+ GenerateCommonBuilderMethods(printer);
+
+ // oneof
+ map<string, string> vars;
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ vars["oneof_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name;
+ vars["oneof_capitalized_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name;
+ vars["oneof_index"] = SimpleItoa(descriptor_->oneof_decl(i)->index());
+
+ // oneofCase() and clearOneof()
+ printer->Print(vars,
+ "public $oneof_capitalized_name$Case\n"
+ " get$oneof_capitalized_name$Case() {\n"
+ " return instance.get$oneof_capitalized_name$Case();\n"
+ "}\n"
+ "\n"
+ "public Builder clear$oneof_capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$oneof_capitalized_name$();\n"
+ " return this;\n"
+ "}\n"
+ "\n");
+ }
+
+ if (GenerateHasBits(descriptor_)) {
+ // Integers for bit fields.
+ int totalBits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ totalBits += field_generators_.get(descriptor_->field(i))
+ .GetNumBitsForBuilder();
+ }
+ int totalInts = (totalBits + 31) / 32;
+ for (int i = 0; i < totalInts; i++) {
+ printer->Print("private int $bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ printer->Print("\n");
+ field_generators_.get(descriptor_->field(i))
+ .GenerateBuilderMembers(printer);
+ }
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(builder_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+// ===================================================================
+
+void MessageBuilderLiteGenerator::
+GenerateCommonBuilderMethods(io::Printer* printer) {
+ printer->Print(
+ "// Construct using $classname$.newBuilder()\n"
+ "private Builder() {\n"
+ " super(DEFAULT_INSTANCE);\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+}
+
+// ===================================================================
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.h
new file mode 100644
index 0000000000..8597b2e66f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_builder_lite.h
@@ -0,0 +1,83 @@
+// 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: dweis@google.com (Daniel Weis)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_BUILDER_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_BUILDER_LITE_H__
+
+#include <string>
+#include <map>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class MessageBuilderLiteGenerator {
+ public:
+ explicit MessageBuilderLiteGenerator(const Descriptor* descriptor,
+ Context* context);
+ virtual ~MessageBuilderLiteGenerator();
+
+ virtual void Generate(io::Printer* printer);
+
+ private:
+ void GenerateCommonBuilderMethods(io::Printer* printer);
+
+ const Descriptor* descriptor_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ FieldGeneratorMap<ImmutableFieldLiteGenerator> field_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageBuilderLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_BUILDER_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.cc
new file mode 100644
index 0000000000..c9865dda27
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.cc
@@ -0,0 +1,1296 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_message_field.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+void SetMessageVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ (*variables)["type"] =
+ name_resolver->GetImmutableClassName(descriptor->message_type());
+ (*variables)["mutable_type"] =
+ name_resolver->GetMutableClassName(descriptor->message_type());
+ (*variables)["group_or_message"] =
+ (GetType(descriptor) == FieldDescriptor::TYPE_GROUP) ?
+ "Group" : "Message";
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+ (*variables)["on_changed"] = "onChanged();";
+ (*variables)["ver"] = GeneratedCodeVersionSuffix();
+ (*variables)["get_parser"] =
+ ExposePublicParser(descriptor->message_type()->file())
+ ? "PARSER" : "parser()";
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+ (*variables)["get_has_field_bit_builder"] = GenerateGetBit(builderBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["set_has_field_bit_builder"] =
+ GenerateSetBit(builderBitIndex) + ";";
+ (*variables)["clear_has_field_bit_builder"] =
+ GenerateClearBit(builderBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["set_has_field_bit_builder"] = "";
+ (*variables)["clear_has_field_bit_builder"] = "";
+
+ (*variables)["is_field_present_message"] =
+ (*variables)["name"] + "_ != null";
+ }
+
+ // For repated builders, one bit is used for whether the array is immutable.
+ (*variables)["get_mutable_bit_builder"] = GenerateGetBit(builderBitIndex);
+ (*variables)["set_mutable_bit_builder"] = GenerateSetBit(builderBitIndex);
+ (*variables)["clear_mutable_bit_builder"] = GenerateClearBit(builderBitIndex);
+
+ // For repeated fields, one bit is used for whether the array is immutable
+ // in the parsing constructor.
+ (*variables)["get_mutable_bit_parser"] =
+ GenerateGetBitMutableLocal(builderBitIndex);
+ (*variables)["set_mutable_bit_parser"] =
+ GenerateSetBitMutableLocal(builderBitIndex);
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutableMessageFieldGenerator::
+ImmutableMessageFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetMessageVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutableMessageFieldGenerator::~ImmutableMessageFieldGenerator() {}
+
+int ImmutableMessageFieldGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutableMessageFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ // TODO(jonp): In the future, consider having a method specific to the
+ // interface so that builders can choose dynamically to either return a
+ // message or a nested builder, so that asking for the interface doesn't
+ // cause a message to ever be built.
+ if (SupportFieldPresence(descriptor_->file()) ||
+ descriptor_->containing_oneof() == NULL) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$();\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$OrBuilder get$capitalized_name$OrBuilder();\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private $type$ $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return $name$_ == null ? $type$.getDefaultInstance() : $name$_;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder "
+ "get$capitalized_name$OrBuilder() {\n"
+ " return $name$_ == null ? $type$.getDefaultInstance() : $name$_;\n"
+ "}\n");
+ } else {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $name$_ != null;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return $name$_ == null ? $type$.getDefaultInstance() : $name$_;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder "
+ "get$capitalized_name$OrBuilder() {\n"
+ " return get$capitalized_name$();\n"
+ "}\n");
+ }
+}
+
+void ImmutableMessageFieldGenerator::PrintNestedBuilderCondition(
+ io::Printer* printer,
+ const char* regular_case,
+ const char* nested_builder_case) const {
+ printer->Print(variables_, "if ($name$Builder_ == null) {\n");
+ printer->Indent();
+ printer->Print(variables_, regular_case);
+ printer->Outdent();
+ printer->Print("} else {\n");
+ printer->Indent();
+ printer->Print(variables_, nested_builder_case);
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void ImmutableMessageFieldGenerator::PrintNestedBuilderFunction(
+ io::Printer* printer,
+ const char* method_prototype,
+ const char* regular_case,
+ const char* nested_builder_case,
+ const char* trailing_code) const {
+ printer->Print(variables_, method_prototype);
+ printer->Print(" {\n");
+ printer->Indent();
+ PrintNestedBuilderCondition(printer, regular_case, nested_builder_case);
+ if (trailing_code != NULL) {
+ printer->Print(variables_, trailing_code);
+ }
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // When using nested-builders, the code initially works just like the
+ // non-nested builder case. It only creates a nested builder lazily on
+ // demand and then forever delegates to it after creation.
+
+ bool support_field_presence = SupportFieldPresence(descriptor_->file());
+
+ printer->Print(variables_,
+ "private $type$ $name$_ = null;\n");
+
+ printer->Print(variables_,
+ // If this builder is non-null, it is used and the other fields are
+ // ignored.
+ "private com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> $name$Builder_;"
+ "\n");
+
+ // The comments above the methods below are based on a hypothetical
+ // field of type "Field" called "Field".
+
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ if (support_field_presence) {
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_builder$;\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $name$Builder_ != null || $name$_ != null;\n"
+ "}\n");
+ }
+
+ // Field getField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public $type$ get$capitalized_name$()",
+ "return $name$_ == null ? $type$.getDefaultInstance() : $name$_;\n",
+ "return $name$Builder_.getMessage();\n",
+ NULL);
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$($type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "$name$_ = value;\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.setMessage(value);\n",
+
+ "$set_has_field_bit_builder$\n"
+ "return this;\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue)",
+
+ "$name$_ = builderForValue.build();\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.setMessage(builderForValue.build());\n",
+
+ "$set_has_field_bit_builder$\n"
+ "return this;\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value)",
+
+ support_field_presence
+ ? "if ($get_has_field_bit_builder$ &&\n"
+ " $name$_ != null &&\n"
+ " $name$_ != $type$.getDefaultInstance()) {\n"
+ " $name$_ =\n"
+ " $type$.newBuilder($name$_).mergeFrom(value).buildPartial();\n"
+ "} else {\n"
+ " $name$_ = value;\n"
+ "}\n"
+ "$on_changed$\n"
+ : "if ($name$_ != null) {\n"
+ " $name$_ =\n"
+ " $type$.newBuilder($name$_).mergeFrom(value).buildPartial();\n"
+ "} else {\n"
+ " $name$_ = value;\n"
+ "}\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.mergeFrom(value);\n",
+
+ "$set_has_field_bit_builder$\n"
+ "return this;\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder clear$capitalized_name$()",
+
+ "$name$_ = null;\n"
+ "$on_changed$\n",
+
+ support_field_presence
+ ? "$name$Builder_.clear();\n"
+ : "$name$_ = null;\n"
+ "$name$Builder_ = null;\n",
+
+ "$clear_has_field_bit_builder$\n"
+ "return this;\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder get$capitalized_name$Builder() {\n"
+ " $set_has_field_bit_builder$\n"
+ " $on_changed$\n"
+ " return get$capitalized_name$FieldBuilder().getBuilder();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder() {\n"
+ " if ($name$Builder_ != null) {\n"
+ " return $name$Builder_.getMessageOrBuilder();\n"
+ " } else {\n"
+ " return $name$_ == null ?\n"
+ " $type$.getDefaultInstance() : $name$_;\n"
+ " }\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> \n"
+ " get$capitalized_name$FieldBuilder() {\n"
+ " if ($name$Builder_ == null) {\n"
+ " $name$Builder_ = new com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder>(\n"
+ " get$capitalized_name$(),\n"
+ " getParentForChildren(),\n"
+ " isClean());\n"
+ " $name$_ = null;\n"
+ " }\n"
+ " return $name$Builder_;\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "get$capitalized_name$FieldBuilder();\n");
+ }
+}
+
+
+void ImmutableMessageFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {}
+
+void ImmutableMessageFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ PrintNestedBuilderCondition(printer,
+ "$name$_ = null;\n",
+
+ "$name$Builder_.clear();\n");
+ printer->Print(variables_, "$clear_has_field_bit_builder$\n");
+ } else {
+ PrintNestedBuilderCondition(printer,
+ "$name$_ = null;\n",
+
+ "$name$_ = null;\n"
+ "$name$Builder_ = null;\n");
+ }
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (other.has$capitalized_name$()) {\n"
+ " merge$capitalized_name$(other.get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "if ($get_has_field_bit_from_local$) {\n"
+ " $set_has_field_bit_to_local$;\n"
+ "}\n");
+ }
+
+ PrintNestedBuilderCondition(printer,
+ "result.$name$_ = $name$_;\n",
+
+ "result.$name$_ = $name$Builder_.build();\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$type$.Builder subBuilder = null;\n"
+ "if ($is_field_present_message$) {\n"
+ " subBuilder = $name$_.toBuilder();\n"
+ "}\n");
+
+ if (GetType(descriptor_) == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "$name$_ = input.readGroup($number$, $type$.$get_parser$,\n"
+ " extensionRegistry);\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_ = input.readMessage($type$.$get_parser$, extensionRegistry);\n");
+ }
+
+ printer->Print(variables_,
+ "if (subBuilder != null) {\n"
+ " subBuilder.mergeFrom($name$_);\n"
+ " $name$_ = subBuilder.buildPartial();\n"
+ "}\n"
+ "$set_has_field_bit_message$\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for messages.
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " output.write$group_or_message$($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$group_or_message$Size($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+}
+
+void ImmutableMessageFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + get$capitalized_name$().hashCode();\n");
+}
+
+string ImmutableMessageFieldGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->message_type());
+}
+
+// ===================================================================
+
+ImmutableMessageOneofFieldGenerator::
+ImmutableMessageOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableMessageFieldGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutableMessageOneofFieldGenerator::
+~ImmutableMessageOneofFieldGenerator() {}
+
+void ImmutableMessageOneofFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($type$) $oneof_name$_;\n"
+ " }\n"
+ " return $type$.getDefaultInstance();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($type$) $oneof_name$_;\n"
+ " }\n"
+ " return $type$.getDefaultInstance();\n"
+ "}\n");
+}
+
+void ImmutableMessageOneofFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // When using nested-builders, the code initially works just like the
+ // non-nested builder case. It only creates a nested builder lazily on
+ // demand and then forever delegates to it after creation.
+ printer->Print(variables_,
+ // If this builder is non-null, it is used and the other fields are
+ // ignored.
+ "private com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> $name$Builder_;"
+ "\n");
+
+ // The comments above the methods below are based on a hypothetical
+ // field of type "Field" called "Field".
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+
+ // Field getField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public $type$ get$capitalized_name$()",
+
+ "if ($has_oneof_case_message$) {\n"
+ " return ($type$) $oneof_name$_;\n"
+ "}\n"
+ "return $type$.getDefaultInstance();\n",
+
+ "if ($has_oneof_case_message$) {\n"
+ " return $name$Builder_.getMessage();\n"
+ "}\n"
+ "return $type$.getDefaultInstance();\n",
+
+ NULL);
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$($type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "$oneof_name$_ = value;\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.setMessage(value);\n",
+
+ "$set_oneof_case_message$;\n"
+ "return this;\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue)",
+
+ "$oneof_name$_ = builderForValue.build();\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.setMessage(builderForValue.build());\n",
+
+ "$set_oneof_case_message$;\n"
+ "return this;\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value)",
+
+ "if ($has_oneof_case_message$ &&\n"
+ " $oneof_name$_ != $type$.getDefaultInstance()) {\n"
+ " $oneof_name$_ = $type$.newBuilder(($type$) $oneof_name$_)\n"
+ " .mergeFrom(value).buildPartial();\n"
+ "} else {\n"
+ " $oneof_name$_ = value;\n"
+ "}\n"
+ "$on_changed$\n",
+
+ "if ($has_oneof_case_message$) {\n"
+ " $name$Builder_.mergeFrom(value);\n"
+ "}\n"
+ "$name$Builder_.setMessage(value);\n",
+
+ "$set_oneof_case_message$;\n"
+ "return this;\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder clear$capitalized_name$()",
+
+ "if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " $on_changed$\n"
+ "}\n",
+
+ "if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ "}\n"
+ "$name$Builder_.clear();\n",
+
+ "return this;\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder get$capitalized_name$Builder() {\n"
+ " return get$capitalized_name$FieldBuilder().getBuilder();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder() {\n"
+ " if (($has_oneof_case_message$) && ($name$Builder_ != null)) {\n"
+ " return $name$Builder_.getMessageOrBuilder();\n"
+ " } else {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($type$) $oneof_name$_;\n"
+ " }\n"
+ " return $type$.getDefaultInstance();\n"
+ " }\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> \n"
+ " get$capitalized_name$FieldBuilder() {\n"
+ " if ($name$Builder_ == null) {\n"
+ " if (!($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = $type$.getDefaultInstance();\n"
+ " }\n"
+ " $name$Builder_ = new com.google.protobuf.SingleFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder>(\n"
+ " ($type$) $oneof_name$_,\n"
+ " getParentForChildren(),\n"
+ " isClean());\n"
+ " $oneof_name$_ = null;\n"
+ " }\n"
+ " $set_oneof_case_message$;\n"
+ " $on_changed$;\n"
+ " return $name$Builder_;\n"
+ "}\n");
+}
+
+void ImmutableMessageOneofFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n");
+ printer->Indent();
+
+ PrintNestedBuilderCondition(printer,
+ "result.$oneof_name$_ = $oneof_name$_;\n",
+
+ "result.$oneof_name$_ = $name$Builder_.build();\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void ImmutableMessageOneofFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "merge$capitalized_name$(other.get$capitalized_name$());\n");
+}
+
+void ImmutableMessageOneofFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$type$.Builder subBuilder = null;\n"
+ "if ($has_oneof_case_message$) {\n"
+ " subBuilder = (($type$) $oneof_name$_).toBuilder();\n"
+ "}\n");
+
+ if (GetType(descriptor_) == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "$oneof_name$_ = input.readGroup($number$, $type$.$get_parser$,\n"
+ " extensionRegistry);\n");
+ } else {
+ printer->Print(variables_,
+ "$oneof_name$_ =\n"
+ " input.readMessage($type$.$get_parser$, extensionRegistry);\n");
+ }
+
+ printer->Print(variables_,
+ "if (subBuilder != null) {\n"
+ " subBuilder.mergeFrom(($type$) $oneof_name$_);\n"
+ " $oneof_name$_ = subBuilder.buildPartial();\n"
+ "}\n");
+ printer->Print(variables_,
+ "$set_oneof_case_message$;\n");
+}
+
+void ImmutableMessageOneofFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.write$group_or_message$($number$, ($type$) $oneof_name$_);\n"
+ "}\n");
+}
+
+void ImmutableMessageOneofFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$group_or_message$Size($number$, ($type$) $oneof_name$_);\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutableMessageFieldGenerator::
+RepeatedImmutableMessageFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetMessageVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutableMessageFieldGenerator::
+~RepeatedImmutableMessageFieldGenerator() {}
+
+int RepeatedImmutableMessageFieldGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutableMessageFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ // TODO(jonp): In the future, consider having methods specific to the
+ // interface so that builders can choose dynamically to either return a
+ // message or a nested builder, so that asking for the interface doesn't
+ // cause a message to ever be built.
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<$type$> \n"
+ " get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$(int index);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<? extends $type$OrBuilder> \n"
+ " get$capitalized_name$OrBuilderList();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$OrBuilder get$capitalized_name$OrBuilder(\n"
+ " int index);\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private java.util.List<$type$> $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return $name$_;\n" // note: unmodifiable list
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<? extends $type$OrBuilder> \n"
+ " get$capitalized_name$OrBuilderList() {\n"
+ " return $name$_;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder(\n"
+ " int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+
+}
+
+void RepeatedImmutableMessageFieldGenerator::PrintNestedBuilderCondition(
+ io::Printer* printer,
+ const char* regular_case,
+ const char* nested_builder_case) const {
+ printer->Print(variables_, "if ($name$Builder_ == null) {\n");
+ printer->Indent();
+ printer->Print(variables_, regular_case);
+ printer->Outdent();
+ printer->Print("} else {\n");
+ printer->Indent();
+ printer->Print(variables_, nested_builder_case);
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::PrintNestedBuilderFunction(
+ io::Printer* printer,
+ const char* method_prototype,
+ const char* regular_case,
+ const char* nested_builder_case,
+ const char* trailing_code) const {
+ printer->Print(variables_, method_prototype);
+ printer->Print(" {\n");
+ printer->Indent();
+ PrintNestedBuilderCondition(printer, regular_case, nested_builder_case);
+ if (trailing_code != NULL) {
+ printer->Print(variables_, trailing_code);
+ }
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // When using nested-builders, the code initially works just like the
+ // non-nested builder case. It only creates a nested builder lazily on
+ // demand and then forever delegates to it after creation.
+
+ printer->Print(variables_,
+ // Used when the builder is null.
+ // One field is the list and the other field keeps track of whether the
+ // list is immutable. If it's immutable, the invariant is that it must
+ // either an instance of Collections.emptyList() or it's an ArrayList
+ // wrapped in a Collections.unmodifiableList() wrapper and nobody else has
+ // a refererence to the underlying ArrayList. This invariant allows us to
+ // share instances of lists between protocol buffers avoiding expensive
+ // memory allocations. Note, immutable is a strong guarantee here -- not
+ // just that the list cannot be modified via the reference but that the
+ // list can never be modified.
+ "private java.util.List<$type$> $name$_ =\n"
+ " java.util.Collections.emptyList();\n"
+
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$get_mutable_bit_builder$) {\n"
+ " $name$_ = new java.util.ArrayList<$type$>($name$_);\n"
+ " $set_mutable_bit_builder$;\n"
+ " }\n"
+ "}\n"
+ "\n");
+
+ printer->Print(variables_,
+ // If this builder is non-null, it is used and the other fields are
+ // ignored.
+ "private com.google.protobuf.RepeatedFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> $name$Builder_;\n"
+ "\n");
+
+ // The comments above the methods below are based on a hypothetical
+ // repeated field of type "Field" called "RepeatedField".
+
+ // List<Field> getRepeatedFieldList()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List()",
+
+ "return java.util.Collections.unmodifiableList($name$_);\n",
+ "return $name$Builder_.getMessageList();\n",
+
+ NULL);
+
+ // int getRepeatedFieldCount()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public int get$capitalized_name$Count()",
+
+ "return $name$_.size();\n",
+ "return $name$Builder_.getCount();\n",
+
+ NULL);
+
+ // Field getRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public $type$ get$capitalized_name$(int index)",
+
+ "return $name$_.get(index);\n",
+
+ "return $name$Builder_.getMessage(index);\n",
+
+ NULL);
+
+ // Builder setRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value)",
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.set(index, value);\n"
+ "$on_changed$\n",
+ "$name$Builder_.setMessage(index, value);\n",
+ "return this;\n");
+
+ // Builder setRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.set(index, builderForValue.build());\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.setMessage(index, builderForValue.build());\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$($type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(value);\n"
+
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(value);\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$ value)",
+
+ "if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ "}\n"
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(index, value);\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(index, value);\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " $type$.Builder builderForValue)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(builderForValue.build());\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(builderForValue.build());\n",
+
+ "return this;\n");
+
+ // Builder addRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.add(index, builderForValue.build());\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addMessage(index, builderForValue.build());\n",
+
+ "return this;\n");
+
+ // Builder addAllRepeatedField(Iterable<Field> values)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "com.google.protobuf.AbstractMessageLite.Builder.addAll(\n"
+ " values, $name$_);\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.addAllMessages(values);\n",
+
+ "return this;\n");
+
+ // Builder clearAllRepeatedField()
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder clear$capitalized_name$()",
+
+ "$name$_ = java.util.Collections.emptyList();\n"
+ "$clear_mutable_bit_builder$;\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.clear();\n",
+
+ "return this;\n");
+
+ // Builder removeRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ PrintNestedBuilderFunction(printer,
+ "$deprecation$public Builder remove$capitalized_name$(int index)",
+
+ "ensure$capitalized_name$IsMutable();\n"
+ "$name$_.remove(index);\n"
+ "$on_changed$\n",
+
+ "$name$Builder_.remove(index);\n",
+
+ "return this;\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder get$capitalized_name$Builder(\n"
+ " int index) {\n"
+ " return get$capitalized_name$FieldBuilder().getBuilder(index);\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder(\n"
+ " int index) {\n"
+ " if ($name$Builder_ == null) {\n"
+ " return $name$_.get(index);"
+ " } else {\n"
+ " return $name$Builder_.getMessageOrBuilder(index);\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<? extends $type$OrBuilder> \n"
+ " get$capitalized_name$OrBuilderList() {\n"
+ " if ($name$Builder_ != null) {\n"
+ " return $name$Builder_.getMessageOrBuilderList();\n"
+ " } else {\n"
+ " return java.util.Collections.unmodifiableList($name$_);\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder add$capitalized_name$Builder() {\n"
+ " return get$capitalized_name$FieldBuilder().addBuilder(\n"
+ " $type$.getDefaultInstance());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$.Builder add$capitalized_name$Builder(\n"
+ " int index) {\n"
+ " return get$capitalized_name$FieldBuilder().addBuilder(\n"
+ " index, $type$.getDefaultInstance());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$.Builder> \n"
+ " get$capitalized_name$BuilderList() {\n"
+ " return get$capitalized_name$FieldBuilder().getBuilderList();\n"
+ "}\n"
+ "private com.google.protobuf.RepeatedFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder> \n"
+ " get$capitalized_name$FieldBuilder() {\n"
+ " if ($name$Builder_ == null) {\n"
+ " $name$Builder_ = new com.google.protobuf.RepeatedFieldBuilder$ver$<\n"
+ " $type$, $type$.Builder, $type$OrBuilder>(\n"
+ " $name$_,\n"
+ " $get_mutable_bit_builder$,\n"
+ " getParentForChildren(),\n"
+ " isClean());\n"
+ " $name$_ = null;\n"
+ " }\n"
+ " return $name$Builder_;\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "get$capitalized_name$FieldBuilder();\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = java.util.Collections.emptyList();\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ PrintNestedBuilderCondition(printer,
+ "$name$_ = java.util.Collections.emptyList();\n"
+ "$clear_mutable_bit_builder$;\n",
+
+ "$name$Builder_.clear();\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // The code below does two optimizations (non-nested builder case):
+ // 1. If the other list is empty, there's nothing to do. This ensures we
+ // don't allocate a new array if we already have an immutable one.
+ // 2. If the other list is non-empty and our current list is empty, we can
+ // reuse the other list which is guaranteed to be immutable.
+ PrintNestedBuilderCondition(printer,
+ "if (!other.$name$_.isEmpty()) {\n"
+ " if ($name$_.isEmpty()) {\n"
+ " $name$_ = other.$name$_;\n"
+ " $clear_mutable_bit_builder$;\n"
+ " } else {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.addAll(other.$name$_);\n"
+ " }\n"
+ " $on_changed$\n"
+ "}\n",
+
+ "if (!other.$name$_.isEmpty()) {\n"
+ " if ($name$Builder_.isEmpty()) {\n"
+ " $name$Builder_.dispose();\n"
+ " $name$Builder_ = null;\n"
+ " $name$_ = other.$name$_;\n"
+ " $clear_mutable_bit_builder$;\n"
+ " $name$Builder_ = \n"
+ " com.google.protobuf.GeneratedMessage$ver$.alwaysUseFieldBuilders ?\n"
+ " get$capitalized_name$FieldBuilder() : null;\n"
+ " } else {\n"
+ " $name$Builder_.addAllMessages(other.$name$_);\n"
+ " }\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ // The code below (non-nested builder case) ensures that the result has an
+ // immutable list. If our list is immutable, we can just reuse it. If not,
+ // we make it immutable.
+ PrintNestedBuilderCondition(printer,
+ "if ($get_mutable_bit_builder$) {\n"
+ " $name$_ = java.util.Collections.unmodifiableList($name$_);\n"
+ " $clear_mutable_bit_builder$;\n"
+ "}\n"
+ "result.$name$_ = $name$_;\n",
+
+ "result.$name$_ = $name$Builder_.build();\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!$get_mutable_bit_parser$) {\n"
+ " $name$_ = new java.util.ArrayList<$type$>();\n"
+ " $set_mutable_bit_parser$;\n"
+ "}\n");
+
+ if (GetType(descriptor_) == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "$name$_.add(input.readGroup($number$, $type$.$get_parser$,\n"
+ " extensionRegistry));\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_.add(\n"
+ " input.readMessage($type$.$get_parser$, extensionRegistry));\n");
+ }
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_mutable_bit_parser$) {\n"
+ " $name$_ = java.util.Collections.unmodifiableList($name$_);\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.write$group_or_message$($number$, $name$_.get(i));\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$group_or_message$Size($number$, $name$_.get(i));\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$List()\n"
+ " .equals(other.get$capitalized_name$List());\n");
+}
+
+void RepeatedImmutableMessageFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + get$capitalized_name$List().hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutableMessageFieldGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->message_type());
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.h
new file mode 100644
index 0000000000..ea8225a5fa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field.h
@@ -0,0 +1,173 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableMessageFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit ImmutableMessageFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableMessageFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ void PrintNestedBuilderCondition(io::Printer* printer,
+ const char* regular_case, const char* nested_builder_case) const;
+ void PrintNestedBuilderFunction(io::Printer* printer,
+ const char* method_prototype, const char* regular_case,
+ const char* nested_builder_case,
+ const char* trailing_code) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableMessageFieldGenerator);
+};
+
+class ImmutableMessageOneofFieldGenerator
+ : public ImmutableMessageFieldGenerator {
+ public:
+ ImmutableMessageOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableMessageOneofFieldGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableMessageOneofFieldGenerator);
+};
+
+class RepeatedImmutableMessageFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit RepeatedImmutableMessageFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableMessageFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ void PrintNestedBuilderCondition(io::Printer* printer,
+ const char* regular_case, const char* nested_builder_case) const;
+ void PrintNestedBuilderFunction(io::Printer* printer,
+ const char* method_prototype, const char* regular_case,
+ const char* nested_builder_case,
+ const char* trailing_code) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableMessageFieldGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.cc
new file mode 100644
index 0000000000..142818169d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.cc
@@ -0,0 +1,941 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_message_field_lite.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+
+void SetMessageVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ (*variables)["type"] =
+ name_resolver->GetImmutableClassName(descriptor->message_type());
+ (*variables)["mutable_type"] =
+ name_resolver->GetMutableClassName(descriptor->message_type());
+ (*variables)["group_or_message"] =
+ (GetType(descriptor) == FieldDescriptor::TYPE_GROUP) ?
+ "Group" : "Message";
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["clear_has_field_bit_message"] =
+ GenerateClearBit(messageBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["clear_has_field_bit_message"] = "";
+
+ (*variables)["is_field_present_message"] =
+ (*variables)["name"] + "_ != null";
+ }
+
+ // For repeated builders, the underlying list tracks mutability state.
+ (*variables)["is_mutable"] = (*variables)["name"] + "_.isModifiable()";
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutableMessageFieldLiteGenerator::
+ImmutableMessageFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetMessageVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutableMessageFieldLiteGenerator::~ImmutableMessageFieldLiteGenerator() {}
+
+int ImmutableMessageFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutableMessageFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ // TODO(jonp): In the future, consider having a method specific to the
+ // interface so that builders can choose dynamically to either return a
+ // message or a nested builder, so that asking for the interface doesn't
+ // cause a message to ever be built.
+ if (SupportFieldPresence(descriptor_->file()) ||
+ descriptor_->containing_oneof() == NULL) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$();\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private $type$ $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return $name$_ == null ? $type$.getDefaultInstance() : $name$_;\n"
+ "}\n");
+ } else {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $name$_ != null;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return $name$_ == null ? $type$.getDefaultInstance() : $name$_;\n"
+ "}\n");
+ }
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " $name$_ = value;\n"
+ " $set_has_field_bit_message$\n"
+ " }\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " $name$_ = builderForValue.build();\n"
+ " $set_has_field_bit_message$\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void merge$capitalized_name$($type$ value) {\n"
+ " if ($name$_ != null &&\n"
+ " $name$_ != $type$.getDefaultInstance()) {\n"
+ " $name$_ =\n"
+ " $type$.newBuilder($name$_).mergeFrom(value).buildPartial();\n"
+ " } else {\n"
+ " $name$_ = value;\n"
+ " }\n"
+ " $set_has_field_bit_message$\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {"
+ " $name$_ = null;\n"
+ " $clear_has_field_bit_message$\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // The comments above the methods below are based on a hypothetical
+ // field of type "Field" called "Field".
+
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+
+ // Field getField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ " }\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.merge$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "get$capitalized_name$FieldBuilder();\n");
+ }
+}
+
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = visitor.visitMessage($name$_, other.$name$_);\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ // noop for scalars
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ // TODO(dweis): Update this code to avoid the builder allocation and instead
+ // only allocate a submessage that isn't made immutable. Rely on the top
+ // message calling makeImmutable once done to actually traverse the tree and
+ // finalize state. This will avoid:
+ // - transitive builder allocations
+ // - the extra transitive iteration for streamed fields
+ // - reallocations for copying repeated fields
+ printer->Print(variables_,
+ "$type$.Builder subBuilder = null;\n"
+ "if ($is_field_present_message$) {\n"
+ " subBuilder = $name$_.toBuilder();\n"
+ "}\n");
+
+ if (GetType(descriptor_) == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "$name$_ = input.readGroup($number$, $type$.parser(),\n"
+ " extensionRegistry);\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_ = input.readMessage($type$.parser(), extensionRegistry);\n");
+ }
+
+ printer->Print(variables_,
+ "if (subBuilder != null) {\n"
+ " subBuilder.mergeFrom($name$_);\n"
+ " $name$_ = subBuilder.buildPartial();\n"
+ "}\n"
+ "$set_has_field_bit_message$\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for messages.
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " output.write$group_or_message$($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$group_or_message$Size($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+}
+
+void ImmutableMessageFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n"
+ "hash = (53 * hash) + get$capitalized_name$().hashCode();\n");
+}
+
+string ImmutableMessageFieldLiteGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->message_type());
+}
+
+// ===================================================================
+
+ImmutableMessageOneofFieldLiteGenerator::
+ImmutableMessageOneofFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableMessageFieldLiteGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutableMessageOneofFieldLiteGenerator::
+~ImmutableMessageOneofFieldLiteGenerator() {}
+
+void ImmutableMessageOneofFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($type$) $oneof_name$_;\n"
+ " }\n"
+ " return $type$.getDefaultInstance();\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " $oneof_name$_ = value;\n"
+ " $set_oneof_case_message$;\n"
+ "}\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " $oneof_name$_ = builderForValue.build();\n"
+ " $set_oneof_case_message$;\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void merge$capitalized_name$($type$ value) {\n"
+ " if ($has_oneof_case_message$ &&\n"
+ " $oneof_name$_ != $type$.getDefaultInstance()) {\n"
+ " $oneof_name$_ = $type$.newBuilder(($type$) $oneof_name$_)\n"
+ " .mergeFrom(value).buildPartial();\n"
+ " } else {\n"
+ " $oneof_name$_ = value;\n"
+ " }\n"
+ " $set_oneof_case_message$;\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " }\n"
+ "}\n");
+}
+
+void ImmutableMessageOneofFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // The comments above the methods below are based on a hypothetical
+ // field of type "Field" called "Field".
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ // boolean hasField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+ }
+
+ // Field getField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ // Field.Builder setField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder setField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder mergeField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder merge$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.merge$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Field.Builder clearField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableMessageOneofFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$oneof_name$_ = visitor.visitOneofMessage(\n"
+ " $has_oneof_case_message$,\n"
+ " $oneof_name$_,\n"
+ " other.$oneof_name$_);\n");
+}
+
+void ImmutableMessageOneofFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$type$.Builder subBuilder = null;\n"
+ "if ($has_oneof_case_message$) {\n"
+ " subBuilder = (($type$) $oneof_name$_).toBuilder();\n"
+ "}\n");
+
+ if (GetType(descriptor_) == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "$oneof_name$_ = input.readGroup($number$, $type$.parser(),\n"
+ " extensionRegistry);\n");
+ } else {
+ printer->Print(variables_,
+ "$oneof_name$_ =\n"
+ " input.readMessage($type$.parser(), extensionRegistry);\n");
+ }
+
+ printer->Print(variables_,
+ "if (subBuilder != null) {\n"
+ " subBuilder.mergeFrom(($type$) $oneof_name$_);\n"
+ " $oneof_name$_ = subBuilder.buildPartial();\n"
+ "}\n");
+ printer->Print(variables_,
+ "$set_oneof_case_message$;\n");
+}
+
+void ImmutableMessageOneofFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.write$group_or_message$($number$, ($type$) $oneof_name$_);\n"
+ "}\n");
+}
+
+void ImmutableMessageOneofFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$group_or_message$Size($number$, ($type$) $oneof_name$_);\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutableMessageFieldLiteGenerator::
+RepeatedImmutableMessageFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetMessageVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutableMessageFieldLiteGenerator::
+~RepeatedImmutableMessageFieldLiteGenerator() {}
+
+int RepeatedImmutableMessageFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutableMessageFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ // TODO(jonp): In the future, consider having methods specific to the
+ // interface so that builders can choose dynamically to either return a
+ // message or a nested builder, so that asking for the interface doesn't
+ // cause a message to ever be built.
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<$type$> \n"
+ " get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$(int index);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private com.google.protobuf.Internal.ProtobufList<$type$> $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return $name$_;\n" // note: unmodifiable list
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<? extends $type$OrBuilder> \n"
+ " get$capitalized_name$OrBuilderList() {\n"
+ " return $name$_;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$OrBuilder get$capitalized_name$OrBuilder(\n"
+ " int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ " }\n"
+ "}\n"
+ "\n");
+
+ // Builder setRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, value);\n"
+ "}\n");
+
+ // Builder setRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, builderForValue.build());\n"
+ "}\n");
+
+ // Builder addRepeatedField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$($type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value);\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(index, value);\n"
+ "}\n");
+ // Builder addRepeatedField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(builderForValue.build());\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(index, builderForValue.build());\n"
+ "}\n");
+
+ // Builder addAllRepeatedField(Iterable<Field> values)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " com.google.protobuf.AbstractMessageLite.addAll(\n"
+ " values, $name$_);\n"
+ "}\n");
+
+ // Builder clearAllRepeatedField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $name$_ = emptyProtobufList();\n"
+ "}\n");
+
+ // Builder removeRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void remove$capitalized_name$(int index) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.remove(index);\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // The comments above the methods below are based on a hypothetical
+ // repeated field of type "Field" called "RepeatedField".
+
+ // List<Field> getRepeatedFieldList()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$type$> get$capitalized_name$List() {\n"
+ " return java.util.Collections.unmodifiableList(\n"
+ " instance.get$capitalized_name$List());\n"
+ "}\n");
+
+ // int getRepeatedFieldCount()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return instance.get$capitalized_name$Count();\n"
+ "}");
+
+ // Field getRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return instance.get$capitalized_name$(index);\n"
+ "}\n");
+
+ // Builder setRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(index, value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder setRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(index, builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addRepeatedField(Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field value)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(index, value);\n"
+ " return this;\n"
+ "}\n");
+ // Builder addRepeatedField(Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addRepeatedField(int index, Field.Builder builderForValue)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " int index, $type$.Builder builderForValue) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(index, builderForValue);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder addAllRepeatedField(Iterable<Field> values)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $type$> values) {\n"
+ " copyOnWrite();\n"
+ " instance.addAll$capitalized_name$(values);\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder clearAllRepeatedField()
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+
+ // Builder removeRepeatedField(int index)
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder remove$capitalized_name$(int index) {\n"
+ " copyOnWrite();\n"
+ " instance.remove$capitalized_name$(index);\n"
+ " return this;\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "get$capitalized_name$FieldBuilder();\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = emptyProtobufList();\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_= visitor.visitList($name$_, other.$name$_);\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_.makeImmutable();\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ "}\n");
+
+ if (GetType(descriptor_) == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "$name$_.add(input.readGroup($number$, $type$.parser(),\n"
+ " extensionRegistry));\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_.add(\n"
+ " input.readMessage($type$.parser(), extensionRegistry));\n");
+ }
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_mutable$) {\n"
+ " $name$_.makeImmutable();\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.write$group_or_message$($number$, $name$_.get(i));\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$group_or_message$Size($number$, $name$_.get(i));\n"
+ "}\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$List()\n"
+ " .equals(other.get$capitalized_name$List());\n");
+}
+
+void RepeatedImmutableMessageFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + get$capitalized_name$List().hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutableMessageFieldLiteGenerator::GetBoxedType() const {
+ return name_resolver_->GetImmutableClassName(descriptor_->message_type());
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.h
new file mode 100644
index 0000000000..6132154778
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_field_lite.h
@@ -0,0 +1,157 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_FIELD_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_FIELD_LITE_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableMessageFieldLiteGenerator : public ImmutableFieldLiteGenerator {
+ public:
+ explicit ImmutableMessageFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableMessageFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableMessageFieldLiteGenerator);
+};
+
+class ImmutableMessageOneofFieldLiteGenerator
+ : public ImmutableMessageFieldLiteGenerator {
+ public:
+ ImmutableMessageOneofFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableMessageOneofFieldLiteGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableMessageOneofFieldLiteGenerator);
+};
+
+class RepeatedImmutableMessageFieldLiteGenerator
+ : public ImmutableFieldLiteGenerator {
+ public:
+ explicit RepeatedImmutableMessageFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableMessageFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableMessageFieldLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_FIELD_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.cc
new file mode 100644
index 0000000000..7c8c4a0314
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.cc
@@ -0,0 +1,1099 @@
+// 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: dweis@google.com (Daniel Weis)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <google/protobuf/compiler/java/java_message_lite.h>
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_enum_lite.h>
+#include <google/protobuf/compiler/java/java_extension_lite.h>
+#include <google/protobuf/compiler/java/java_generator_factory.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_message_builder.h>
+#include <google/protobuf/compiler/java/java_message_builder_lite.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+bool GenerateHasBits(const Descriptor* descriptor) {
+ return SupportFieldPresence(descriptor->file()) ||
+ HasRepeatedFields(descriptor);
+}
+
+string MapValueImmutableClassdName(const Descriptor* descriptor,
+ ClassNameResolver* name_resolver) {
+ const FieldDescriptor* value_field = descriptor->FindFieldByName("value");
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, value_field->type());
+ return name_resolver->GetImmutableClassName(value_field->message_type());
+}
+} // namespace
+
+// ===================================================================
+ImmutableMessageLiteGenerator::ImmutableMessageLiteGenerator(
+ const Descriptor* descriptor, Context* context)
+ : MessageGenerator(descriptor), context_(context),
+ name_resolver_(context->GetNameResolver()),
+ field_generators_(descriptor, context_) {
+ GOOGLE_CHECK(!HasDescriptorMethods(descriptor->file(), context->EnforceLite()))
+ << "Generator factory error: A lite message generator is used to "
+ "generate non-lite messages.";
+}
+
+ImmutableMessageLiteGenerator::~ImmutableMessageLiteGenerator() {}
+
+void ImmutableMessageLiteGenerator::GenerateStaticVariables(
+ io::Printer* printer, int* bytecode_estimate) {
+ // Generate static members for all nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // TODO(kenton): Reuse MessageGenerator objects?
+ ImmutableMessageLiteGenerator(descriptor_->nested_type(i), context_)
+ .GenerateStaticVariables(printer, bytecode_estimate);
+ }
+}
+
+int ImmutableMessageLiteGenerator::GenerateStaticVariableInitializers(
+ io::Printer* printer) {
+ int bytecode_estimate = 0;
+ // Generate static member initializers for all nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // TODO(kenton): Reuse MessageGenerator objects?
+ bytecode_estimate +=
+ ImmutableMessageLiteGenerator(descriptor_->nested_type(i), context_)
+ .GenerateStaticVariableInitializers(printer);
+ }
+ return bytecode_estimate;
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::GenerateInterface(io::Printer* printer) {
+ MaybePrintGeneratedAnnotation(context_, printer, descriptor_,
+ /* immutable = */ true, "OrBuilder");
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "public interface $classname$OrBuilder$idend$ extends \n"
+ " $extra_interfaces$\n"
+ " com.google.protobuf.GeneratedMessageLite.\n"
+ " ExtendableMessageOrBuilder<\n"
+ " $classname$, $classname$.Builder> {\n",
+ "extra_interfaces", ExtraMessageOrBuilderInterfaces(descriptor_),
+ "classname", descriptor_->name(),
+ "idend", "");
+ } else {
+ printer->Print(
+ "public interface $classname$OrBuilder$idend$ extends\n"
+ " $extra_interfaces$\n"
+ " com.google.protobuf.MessageLiteOrBuilder {\n",
+ "extra_interfaces", ExtraMessageOrBuilderInterfaces(descriptor_),
+ "classname", descriptor_->name(),
+ "idend", "");
+ }
+ printer->Annotate("classname", "idend", descriptor_);
+
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ printer->Print("\n");
+ field_generators_.get(descriptor_->field(i))
+ .GenerateInterfaceMembers(printer);
+ }
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "\n"
+ "public $classname$.$oneof_capitalized_name$Case "
+ "get$oneof_capitalized_name$Case();\n",
+ "oneof_capitalized_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name,
+ "classname",
+ context_->GetNameResolver()->GetImmutableClassName(descriptor_));
+ }
+ printer->Outdent();
+
+ printer->Print("}\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::Generate(io::Printer* printer) {
+ bool is_own_file = IsOwnFile(descriptor_, /* immutable = */ true);
+
+ map<string, string> variables;
+ variables["static"] = is_own_file ? " " : " static ";
+ variables["classname"] = descriptor_->name();
+ variables["extra_interfaces"] = ExtraMessageInterfaces(descriptor_);
+
+ WriteMessageDocComment(printer, descriptor_);
+ MaybePrintGeneratedAnnotation(context_, printer, descriptor_,
+ /* immutable = */ true);
+
+ // The builder_type stores the super type name of the nested Builder class.
+ string builder_type;
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(variables,
+ "public $static$final class $classname$ extends\n"
+ " com.google.protobuf.GeneratedMessageLite.ExtendableMessage<\n"
+ " $classname$, $classname$.Builder> implements\n"
+ " $extra_interfaces$\n"
+ " $classname$OrBuilder {\n");
+ builder_type = strings::Substitute(
+ "com.google.protobuf.GeneratedMessageLite.ExtendableBuilder<$0, ?>",
+ name_resolver_->GetImmutableClassName(descriptor_));
+ } else {
+ printer->Print(variables,
+ "public $static$final class $classname$ extends\n"
+ " com.google.protobuf.GeneratedMessageLite<\n"
+ " $classname$, $classname$.Builder> implements\n"
+ " $extra_interfaces$\n"
+ " $classname$OrBuilder {\n");
+
+ builder_type = "com.google.protobuf.GeneratedMessageLite.Builder";
+ }
+ printer->Indent();
+
+
+ GenerateConstructor(printer);
+
+ // Nested types
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ EnumLiteGenerator(descriptor_->enum_type(i), true, context_)
+ .Generate(printer);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // Don't generate Java classes for map entry messages.
+ if (IsMapEntry(descriptor_->nested_type(i))) continue;
+ ImmutableMessageLiteGenerator messageGenerator(
+ descriptor_->nested_type(i), context_);
+ messageGenerator.GenerateInterface(printer);
+ messageGenerator.Generate(printer);
+ }
+
+ if (GenerateHasBits(descriptor_)) {
+ // Integers for bit fields.
+ int totalBits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ totalBits += field_generators_.get(descriptor_->field(i))
+ .GetNumBitsForMessage();
+ }
+ int totalInts = (totalBits + 31) / 32;
+ for (int i = 0; i < totalInts; i++) {
+ printer->Print("private int $bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+
+ // oneof
+ map<string, string> vars;
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ vars["oneof_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name;
+ vars["oneof_capitalized_name"] = context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name;
+ vars["oneof_index"] = SimpleItoa(descriptor_->oneof_decl(i)->index());
+ // oneofCase_ and oneof_
+ printer->Print(vars,
+ "private int $oneof_name$Case_ = 0;\n"
+ "private java.lang.Object $oneof_name$_;\n");
+ // OneofCase enum
+ printer->Print(vars,
+ "public enum $oneof_capitalized_name$Case\n"
+ " implements com.google.protobuf.Internal.EnumLite {\n");
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "$field_name$($field_number$),\n",
+ "field_name",
+ ToUpper(field->name()),
+ "field_number",
+ SimpleItoa(field->number()));
+ }
+ printer->Print(
+ "$cap_oneof_name$_NOT_SET(0);\n",
+ "cap_oneof_name",
+ ToUpper(vars["oneof_name"]));
+ printer->Print(vars,
+ "private final int value;\n"
+ "private $oneof_capitalized_name$Case(int value) {\n"
+ " this.value = value;\n"
+ "}\n");
+ printer->Print(vars,
+ "/**\n"
+ " * @deprecated Use {@link #forNumber(int)} instead.\n"
+ " */\n"
+ "@java.lang.Deprecated\n"
+ "public static $oneof_capitalized_name$Case valueOf(int value) {\n"
+ " return forNumber(value);\n"
+ "}\n"
+ "\n"
+ "public static $oneof_capitalized_name$Case forNumber(int value) {\n"
+ " switch (value) {\n");
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ " case $field_number$: return $field_name$;\n",
+ "field_number",
+ SimpleItoa(field->number()),
+ "field_name",
+ ToUpper(field->name()));
+ }
+ printer->Print(
+ " case 0: return $cap_oneof_name$_NOT_SET;\n"
+ " default: return null;\n"
+ " }\n"
+ "}\n"
+ "public int getNumber() {\n"
+ " return this.value;\n"
+ "}\n",
+ "cap_oneof_name", ToUpper(vars["oneof_name"]));
+ printer->Outdent();
+ printer->Print("};\n\n");
+ // oneofCase()
+ printer->Print(vars,
+ "public $oneof_capitalized_name$Case\n"
+ "get$oneof_capitalized_name$Case() {\n"
+ " return $oneof_capitalized_name$Case.forNumber(\n"
+ " $oneof_name$Case_);\n"
+ "}\n"
+ "\n"
+ "private void clear$oneof_capitalized_name$() {\n"
+ " $oneof_name$Case_ = 0;\n"
+ " $oneof_name$_ = null;\n"
+ "}\n"
+ "\n");
+ }
+
+ // Fields
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ printer->Print("public static final int $constant_name$ = $number$;\n",
+ "constant_name", FieldConstantName(descriptor_->field(i)),
+ "number", SimpleItoa(descriptor_->field(i)->number()));
+ field_generators_.get(descriptor_->field(i)).GenerateMembers(printer);
+ printer->Print("\n");
+ }
+
+ GenerateMessageSerializationMethods(printer);
+
+ GenerateParseFromMethods(printer);
+ GenerateBuilder(printer);
+
+ if (HasRequiredFields(descriptor_)) {
+ // Memoizes whether the protocol buffer is fully initialized (has all
+ // required fields). -1 means not yet computed. 0 means false and 1 means
+ // true.
+ printer->Print(
+ "private byte memoizedIsInitialized = -1;\n");
+ }
+
+ printer->Print(
+ "protected final Object dynamicMethod(\n"
+ " com.google.protobuf.GeneratedMessageLite.MethodToInvoke method,\n"
+ " Object arg0, Object arg1) {\n"
+ " switch (method) {\n"
+ " case NEW_MUTABLE_INSTANCE: {\n"
+ " return new $classname$();\n"
+ " }\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Indent();
+ printer->Indent();
+
+ printer->Print(
+ "case IS_INITIALIZED: {\n");
+ printer->Indent();
+ GenerateDynamicMethodIsInitialized(printer);
+ printer->Outdent();
+
+ printer->Print(
+ "}\n"
+ "case MAKE_IMMUTABLE: {\n");
+
+ printer->Indent();
+ GenerateDynamicMethodMakeImmutable(printer);
+ printer->Outdent();
+
+ printer->Print(
+ "}\n"
+ "case NEW_BUILDER: {\n");
+
+ printer->Indent();
+ GenerateDynamicMethodNewBuilder(printer);
+ printer->Outdent();
+
+ printer->Print(
+ "}\n"
+ "case VISIT: {\n");
+
+ printer->Indent();
+ GenerateDynamicMethodVisit(printer);
+ printer->Outdent();
+
+ printer->Print(
+ "}\n"
+ "case MERGE_FROM_STREAM: {\n");
+
+ printer->Indent();
+ GenerateDynamicMethodMergeFromStream(printer);
+ printer->Outdent();
+
+ printer->Print(
+ "}\n"
+ "case GET_DEFAULT_INSTANCE: {\n"
+ " return DEFAULT_INSTANCE;\n"
+ "}\n"
+ "case GET_PARSER: {\n"
+ // Generally one would use the lazy initialization holder pattern for
+ // manipulating static fields but that has exceptional cost on Android as
+ // it will generate an extra class for every message. Instead, use the
+ // double-check locking pattern which works just as well.
+ " if (PARSER == null) {"
+ " synchronized ($classname$.class) {\n"
+ " if (PARSER == null) {\n"
+ " PARSER = new DefaultInstanceBasedParser(DEFAULT_INSTANCE);\n"
+ " }\n"
+ " }\n"
+ " }\n"
+ " return PARSER;\n"
+ "}\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Outdent();
+ printer->Outdent();
+
+ printer->Print(
+ " }\n"
+ " throw new UnsupportedOperationException();\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(class_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+
+ // Carefully initialize the default instance in such a way that it doesn't
+ // conflict with other initialization.
+ printer->Print(
+ "private static final $classname$ DEFAULT_INSTANCE;\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ printer->Print(
+ "static {\n"
+ " DEFAULT_INSTANCE = new $classname$();\n"
+ " DEFAULT_INSTANCE.makeImmutable();\n"
+ "}\n"
+ "\n",
+ "classname", descriptor_->name());
+ printer->Print(
+ "public static $classname$ getDefaultInstance() {\n"
+ " return DEFAULT_INSTANCE;\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ GenerateParser(printer);
+
+ // Extensions must be declared after the DEFAULT_INSTANCE is initialized
+ // because the DEFAULT_INSTANCE is used by the extension to lazily retrieve
+ // the outer class's FileDescriptor.
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ ImmutableExtensionLiteGenerator(descriptor_->extension(i), context_)
+ .Generate(printer);
+ }
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::
+GenerateMessageSerializationMethods(io::Printer* printer) {
+ google::protobuf::scoped_array<const FieldDescriptor * > sorted_fields(
+ SortFieldsByNumber(descriptor_));
+
+ vector<const Descriptor::ExtensionRange*> sorted_extensions;
+ for (int i = 0; i < descriptor_->extension_range_count(); ++i) {
+ sorted_extensions.push_back(descriptor_->extension_range(i));
+ }
+ std::sort(sorted_extensions.begin(), sorted_extensions.end(),
+ ExtensionRangeOrdering());
+
+ printer->Print(
+ "public void writeTo(com.google.protobuf.CodedOutputStream output)\n"
+ " throws java.io.IOException {\n");
+ printer->Indent();
+ if (HasPackedFields(descriptor_)) {
+ // writeTo(CodedOutputStream output) might be invoked without
+ // getSerializedSize() ever being called, but we need the memoized
+ // sizes in case this message has packed fields. Rather than emit checks for
+ // each packed field, just call getSerializedSize() up front.
+ // In most cases, getSerializedSize() will have already been called anyway
+ // by one of the wrapper writeTo() methods, making this call cheap.
+ printer->Print(
+ "getSerializedSize();\n");
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ if (descriptor_->options().message_set_wire_format()) {
+ printer->Print(
+ "com.google.protobuf.GeneratedMessageLite\n"
+ " .ExtendableMessage<$classname$, $classname$.Builder>\n"
+ " .ExtensionWriter extensionWriter =\n"
+ " newMessageSetExtensionWriter();\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+ } else {
+ printer->Print(
+ "com.google.protobuf.GeneratedMessageLite\n"
+ " .ExtendableMessage<$classname$, $classname$.Builder>\n"
+ " .ExtensionWriter extensionWriter =\n"
+ " newExtensionWriter();\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+ }
+ }
+
+ // Merge the fields and the extension ranges, both sorted by field number.
+ for (int i = 0, j = 0;
+ i < descriptor_->field_count() || j < sorted_extensions.size();
+ ) {
+ if (i == descriptor_->field_count()) {
+ GenerateSerializeOneExtensionRange(printer, sorted_extensions[j++]);
+ } else if (j == sorted_extensions.size()) {
+ GenerateSerializeOneField(printer, sorted_fields[i++]);
+ } else if (sorted_fields[i]->number() < sorted_extensions[j]->start) {
+ GenerateSerializeOneField(printer, sorted_fields[i++]);
+ } else {
+ GenerateSerializeOneExtensionRange(printer, sorted_extensions[j++]);
+ }
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ printer->Print(
+ "unknownFields.writeTo(output);\n");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n"
+ "public int getSerializedSize() {\n"
+ " int size = memoizedSerializedSize;\n"
+ " if (size != -1) return size;\n"
+ "\n"
+ " size = 0;\n");
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(sorted_fields[i]).GenerateSerializedSizeCode(printer);
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ if (descriptor_->options().message_set_wire_format()) {
+ printer->Print(
+ "size += extensionsSerializedSizeAsMessageSet();\n");
+ } else {
+ printer->Print(
+ "size += extensionsSerializedSize();\n");
+ }
+ }
+
+ if (PreserveUnknownFields(descriptor_)) {
+ printer->Print(
+ "size += unknownFields.getSerializedSize();\n");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ " memoizedSerializedSize = size;\n"
+ " return size;\n"
+ "}\n"
+ "\n");
+}
+
+void ImmutableMessageLiteGenerator::
+GenerateParseFromMethods(io::Printer* printer) {
+ // Note: These are separate from GenerateMessageSerializationMethods()
+ // because they need to be generated even for messages that are optimized
+ // for code size.
+ printer->Print(
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.ByteString data)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, data);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.ByteString data,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, data, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseFrom(byte[] data)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, data);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " byte[] data,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws com.google.protobuf.InvalidProtocolBufferException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, data, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseFrom(java.io.InputStream input)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, input);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " java.io.InputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, input, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseDelimitedFrom(java.io.InputStream input)\n"
+ " throws java.io.IOException {\n"
+ " return parseDelimitedFrom(DEFAULT_INSTANCE, input);\n"
+ "}\n"
+ "public static $classname$ parseDelimitedFrom(\n"
+ " java.io.InputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws java.io.IOException {\n"
+ " return parseDelimitedFrom(DEFAULT_INSTANCE, input, extensionRegistry);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.CodedInputStream input)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, input);\n"
+ "}\n"
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.CodedInputStream input,\n"
+ " com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
+ " throws java.io.IOException {\n"
+ " return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
+ " DEFAULT_INSTANCE, input, extensionRegistry);\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+}
+
+void ImmutableMessageLiteGenerator::GenerateSerializeOneField(
+ io::Printer* printer, const FieldDescriptor* field) {
+ field_generators_.get(field).GenerateSerializationCode(printer);
+}
+
+void ImmutableMessageLiteGenerator::GenerateSerializeOneExtensionRange(
+ io::Printer* printer, const Descriptor::ExtensionRange* range) {
+ printer->Print(
+ "extensionWriter.writeUntil($end$, output);\n",
+ "end", SimpleItoa(range->end));
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::GenerateBuilder(io::Printer* printer) {
+ printer->Print(
+ "public static Builder newBuilder() {\n"
+ " return DEFAULT_INSTANCE.toBuilder();\n"
+ "}\n"
+ "public static Builder newBuilder($classname$ prototype) {\n"
+ " return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype);\n"
+ "}\n"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ MessageBuilderLiteGenerator builderGenerator(descriptor_, context_);
+ builderGenerator.Generate(printer);
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::GenerateDynamicMethodIsInitialized(
+ io::Printer* printer) {
+ // Returns null for false, DEFAULT_INSTANCE for true.
+ if (!HasRequiredFields(descriptor_)) {
+ printer->Print("return DEFAULT_INSTANCE;\n");
+ return;
+ }
+
+ // Don't directly compare to -1 to avoid an Android x86 JIT bug.
+ printer->Print(
+ "byte isInitialized = memoizedIsInitialized;\n"
+ "if (isInitialized == 1) return DEFAULT_INSTANCE;\n"
+ "if (isInitialized == 0) return null;\n"
+ "\n"
+ "boolean shouldMemoize = ((Boolean) arg0).booleanValue();\n");
+
+ // Check that all required fields in this message are set.
+ // TODO(kenton): We can optimize this when we switch to putting all the
+ // "has" fields into a single bitfield.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+
+ if (field->is_required()) {
+ printer->Print(
+ "if (!has$name$()) {\n"
+ " if (shouldMemoize) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " }\n"
+ " return null;\n"
+ "}\n",
+ "name", info->capitalized_name);
+ }
+ }
+
+ // Now check that all embedded messages are initialized.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
+ if (GetJavaType(field) == JAVATYPE_MESSAGE &&
+ HasRequiredFields(field->message_type())) {
+ switch (field->label()) {
+ case FieldDescriptor::LABEL_REQUIRED:
+ printer->Print(
+ "if (!get$name$().isInitialized()) {\n"
+ " if (shouldMemoize) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " }\n"
+ " return null;\n"
+ "}\n",
+ "type", name_resolver_->GetImmutableClassName(
+ field->message_type()),
+ "name", info->capitalized_name);
+ break;
+ case FieldDescriptor::LABEL_OPTIONAL:
+ if (!SupportFieldPresence(descriptor_->file()) &&
+ field->containing_oneof() != NULL) {
+ const OneofDescriptor* oneof = field->containing_oneof();
+ const OneofGeneratorInfo* oneof_info =
+ context_->GetOneofGeneratorInfo(oneof);
+ printer->Print(
+ "if ($oneof_name$Case_ == $field_number$) {\n",
+ "oneof_name", oneof_info->name,
+ "field_number", SimpleItoa(field->number()));
+ } else {
+ printer->Print(
+ "if (has$name$()) {\n",
+ "name", info->capitalized_name);
+ }
+ printer->Print(
+ " if (!get$name$().isInitialized()) {\n"
+ " if (shouldMemoize) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " }\n"
+ " return null;\n"
+ " }\n"
+ "}\n",
+ "name", info->capitalized_name);
+ break;
+ case FieldDescriptor::LABEL_REPEATED:
+ if (IsMapEntry(field->message_type())) {
+ printer->Print(
+ "for ($type$ item : get$name$().values()) {\n"
+ " if (!item.isInitialized()) {\n"
+ " if (shouldMemoize) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " }\n"
+ " return null;\n"
+ " }\n"
+ "}\n",
+ "type", MapValueImmutableClassdName(field->message_type(),
+ name_resolver_),
+ "name", info->capitalized_name);
+ } else {
+ printer->Print(
+ "for (int i = 0; i < get$name$Count(); i++) {\n"
+ " if (!get$name$(i).isInitialized()) {\n"
+ " if (shouldMemoize) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " }\n"
+ " return null;\n"
+ " }\n"
+ "}\n",
+ "type", name_resolver_->GetImmutableClassName(
+ field->message_type()),
+ "name", info->capitalized_name);
+ }
+ break;
+ }
+ }
+ }
+
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "if (!extensionsAreInitialized()) {\n"
+ " if (shouldMemoize) {\n"
+ " memoizedIsInitialized = 0;\n"
+ " }\n"
+ " return null;\n"
+ "}\n");
+ }
+
+ printer->Print(
+ "if (shouldMemoize) memoizedIsInitialized = 1;\n");
+
+ printer->Print(
+ "return DEFAULT_INSTANCE;\n"
+ "\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::GenerateDynamicMethodMakeImmutable(
+ io::Printer* printer) {
+
+ // Output generation code for each field.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateDynamicMethodMakeImmutableCode(printer);
+ }
+
+ printer->Print(
+ "return null;\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::GenerateDynamicMethodNewBuilder(
+ io::Printer* printer) {
+ printer->Print(
+ "return new Builder();\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::GenerateDynamicMethodVisit(
+ io::Printer* printer) {
+ printer->Print(
+ "Visitor visitor = (Visitor) arg0;\n"
+ "$classname$ other = ($classname$) arg1;\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(
+ descriptor_->field(i)).GenerateVisitCode(printer);
+ }
+ }
+
+ // Merge oneof fields.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
+ printer->Print(
+ "switch (other.get$oneof_capitalized_name$Case()) {\n",
+ "oneof_capitalized_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->capitalized_name);
+ printer->Indent();
+ for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
+ printer->Print(
+ "case $field_name$: {\n",
+ "field_name",
+ ToUpper(field->name()));
+ printer->Indent();
+ field_generators_.get(field).GenerateVisitCode(printer);
+ printer->Print(
+ "break;\n");
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+ printer->Print(
+ "case $cap_oneof_name$_NOT_SET: {\n"
+ " visitor.visitOneofNotSet($oneof_name$Case_ != 0);\n"
+ " break;\n"
+ "}\n",
+ "cap_oneof_name",
+ ToUpper(context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name),
+ "oneof_name",
+ context_->GetOneofGeneratorInfo(
+ descriptor_->oneof_decl(i))->name);
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+ }
+
+ printer->Print(
+ "if (visitor == com.google.protobuf.GeneratedMessageLite.MergeFromVisitor\n"
+ " .INSTANCE) {\n");
+ printer->Indent();
+ for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
+ const OneofDescriptor* field = descriptor_->oneof_decl(i);
+ printer->Print(
+ "if (other.$oneof_name$Case_ != 0) {\n"
+ " $oneof_name$Case_ = other.$oneof_name$Case_;\n"
+ "}\n",
+ "oneof_name", context_->GetOneofGeneratorInfo(field)->name);
+ }
+
+ if (GenerateHasBits(descriptor_)) {
+ // Integers for bit fields.
+ int totalBits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ totalBits += field_generators_.get(descriptor_->field(i))
+ .GetNumBitsForMessage();
+ }
+ int totalInts = (totalBits + 31) / 32;
+
+ for (int i = 0; i < totalInts; i++) {
+ printer->Print(
+ "$bit_field_name$ |= other.$bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+
+
+ printer->Print(
+ "return this;\n");
+}
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::GenerateDynamicMethodMergeFromStream(
+ io::Printer* printer) {
+ printer->Print(
+ "com.google.protobuf.CodedInputStream input =\n"
+ " (com.google.protobuf.CodedInputStream) arg0;\n"
+ "com.google.protobuf.ExtensionRegistryLite extensionRegistry =\n"
+ " (com.google.protobuf.ExtensionRegistryLite) arg1;\n"
+ "try {\n");
+ printer->Indent();
+
+ printer->Print(
+ "boolean done = false;\n"
+ "while (!done) {\n");
+ printer->Indent();
+
+ printer->Print(
+ "int tag = input.readTag();\n"
+ "switch (tag) {\n");
+ printer->Indent();
+
+ printer->Print(
+ "case 0:\n" // zero signals EOF / limit reached
+ " done = true;\n"
+ " break;\n");
+
+ if (PreserveUnknownFields(descriptor_)) {
+ if (descriptor_->extension_range_count() > 0) {
+ printer->Print(
+ "default: {\n"
+ " if (!parseUnknownField(getDefaultInstanceForType(),\n"
+ " input, extensionRegistry, tag)) {\n"
+ " done = true;\n" // it's an endgroup tag
+ " }\n"
+ " break;\n"
+ "}\n");
+ } else {
+ printer->Print(
+ "default: {\n"
+ " if (!parseUnknownField(tag, input)) {\n"
+ " done = true;\n" // it's an endgroup tag
+ " }\n"
+ " break;\n"
+ "}\n");
+ }
+ } else {
+ printer->Print(
+ "default: {\n"
+ " if (!input.skipField(tag)) {\n"
+ " done = true;\n" // it's an endgroup tag
+ " }\n"
+ " break;\n"
+ "}\n");
+ }
+
+ google::protobuf::scoped_array<const FieldDescriptor * > sorted_fields(
+ SortFieldsByNumber(descriptor_));
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = sorted_fields[i];
+ uint32 tag = WireFormatLite::MakeTag(field->number(),
+ WireFormat::WireTypeForFieldType(field->type()));
+
+ printer->Print(
+ "case $tag$: {\n",
+ "tag", SimpleItoa(tag));
+ printer->Indent();
+
+ field_generators_.get(field).GenerateParsingCode(printer);
+
+ printer->Outdent();
+ printer->Print(
+ " break;\n"
+ "}\n");
+
+ if (field->is_packable()) {
+ // To make packed = true wire compatible, we generate parsing code from a
+ // packed version of this field regardless of field->options().packed().
+ uint32 packed_tag = WireFormatLite::MakeTag(field->number(),
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED);
+ printer->Print(
+ "case $tag$: {\n",
+ "tag", SimpleItoa(packed_tag));
+ printer->Indent();
+
+ field_generators_.get(field).GenerateParsingCodeFromPacked(printer);
+
+ printer->Outdent();
+ printer->Print(
+ " break;\n"
+ "}\n");
+ }
+ }
+
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n" // switch (tag)
+ "}\n"); // while (!done)
+
+ printer->Outdent();
+ printer->Print(
+ "} catch (com.google.protobuf.InvalidProtocolBufferException e) {\n"
+ " throw new RuntimeException(e.setUnfinishedMessage(this));\n"
+ "} catch (java.io.IOException e) {\n"
+ " throw new RuntimeException(\n"
+ " new com.google.protobuf.InvalidProtocolBufferException(\n"
+ " e.getMessage()).setUnfinishedMessage(this));\n"
+ "} finally {\n");
+ printer->Indent();
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"); // finally
+}
+
+// ===================================================================
+
+namespace {
+bool CheckHasBitsForEqualsAndHashCode(const FieldDescriptor* field) {
+ if (field->is_repeated()) {
+ return false;
+ }
+ if (SupportFieldPresence(field->file())) {
+ return true;
+ }
+ return GetJavaType(field) == JAVATYPE_MESSAGE &&
+ field->containing_oneof() == NULL;
+}
+} // namespace
+
+// ===================================================================
+
+void ImmutableMessageLiteGenerator::
+GenerateExtensionRegistrationCode(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ ImmutableExtensionLiteGenerator(descriptor_->extension(i), context_)
+ .GenerateRegistrationCode(printer);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ ImmutableMessageLiteGenerator(descriptor_->nested_type(i), context_)
+ .GenerateExtensionRegistrationCode(printer);
+ }
+}
+
+// ===================================================================
+void ImmutableMessageLiteGenerator::
+GenerateConstructor(io::Printer* printer) {
+ printer->Print(
+ "private $classname$() {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+
+ // Initialize all fields to default.
+ GenerateInitializers(printer);
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+}
+
+// ===================================================================
+void ImmutableMessageLiteGenerator::GenerateParser(io::Printer* printer) {
+ printer->Print(
+ "private static volatile com.google.protobuf.Parser<$classname$> PARSER;\n"
+ "\n"
+ "public static com.google.protobuf.Parser<$classname$> parser() {\n"
+ " return DEFAULT_INSTANCE.getParserForType();\n"
+ "}\n",
+ "classname", descriptor_->name());
+}
+
+// ===================================================================
+void ImmutableMessageLiteGenerator::GenerateInitializers(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (!descriptor_->field(i)->containing_oneof()) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateInitializationCode(printer);
+ }
+ }
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.h
new file mode 100644
index 0000000000..1e319c6d6e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_message_lite.h
@@ -0,0 +1,92 @@
+// 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: dweis@google.com (Daniel Weis)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_LITE_H__
+
+#include <string>
+#include <map>
+#include <google/protobuf/compiler/java/java_field.h>
+#include <google/protobuf/compiler/java/java_message.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableMessageLiteGenerator : public MessageGenerator {
+ public:
+ ImmutableMessageLiteGenerator(const Descriptor* descriptor, Context* context);
+ virtual ~ImmutableMessageLiteGenerator();
+
+ virtual void Generate(io::Printer* printer);
+ virtual void GenerateInterface(io::Printer* printer);
+ virtual void GenerateExtensionRegistrationCode(io::Printer* printer);
+ virtual void GenerateStaticVariables(
+ io::Printer* printer, int* bytecode_estimate);
+ virtual int GenerateStaticVariableInitializers(io::Printer* printer);
+
+ private:
+
+ void GenerateMessageSerializationMethods(io::Printer* printer);
+ void GenerateParseFromMethods(io::Printer* printer);
+ void GenerateSerializeOneField(io::Printer* printer,
+ const FieldDescriptor* field);
+ void GenerateSerializeOneExtensionRange(
+ io::Printer* printer, const Descriptor::ExtensionRange* range);
+
+ void GenerateBuilder(io::Printer* printer);
+ void GenerateDynamicMethodIsInitialized(io::Printer* printer);
+ void GenerateDynamicMethodMakeImmutable(io::Printer* printer);
+ void GenerateDynamicMethodVisit(io::Printer* printer);
+ void GenerateDynamicMethodMergeFromStream(io::Printer* printer);
+ void GenerateDynamicMethodNewBuilder(io::Printer* printer);
+ void GenerateInitializers(io::Printer* printer);
+ void GenerateEqualsAndHashCode(io::Printer* printer);
+ void GenerateParser(io::Printer* printer);
+ void GenerateConstructor(io::Printer* printer);
+
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ FieldGeneratorMap<ImmutableFieldLiteGenerator> field_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableMessageLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_MESSAGE_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.cc
new file mode 100644
index 0000000000..bffe4f16e7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.cc
@@ -0,0 +1,273 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+namespace {
+// A suffix that will be appended to the file's outer class name if the name
+// conflicts with some other types defined in the file.
+const char* kOuterClassNameSuffix = "OuterClass";
+
+// Strip package name from a descriptor's full name.
+// For example:
+// Full name : foo.Bar.Baz
+// Package name: foo
+// After strip : Bar.Baz
+string StripPackageName(const string& full_name,
+ const FileDescriptor* file) {
+ if (file->package().empty()) {
+ return full_name;
+ } else {
+ // Strip package name
+ return full_name.substr(file->package().size() + 1);
+ }
+}
+
+// Get the name of a message's Java class without package name prefix.
+string ClassNameWithoutPackage(const Descriptor* descriptor,
+ bool immutable) {
+ return StripPackageName(descriptor->full_name(),
+ descriptor->file());
+}
+
+// Get the name of an enum's Java class without package name prefix.
+string ClassNameWithoutPackage(const EnumDescriptor* descriptor,
+ bool immutable) {
+ // Doesn't append "Mutable" for enum type's name.
+ const Descriptor* message_descriptor = descriptor->containing_type();
+ if (message_descriptor == NULL) {
+ return descriptor->name();
+ } else {
+ return ClassNameWithoutPackage(message_descriptor, immutable) +
+ "." + descriptor->name();
+ }
+}
+
+// Get the name of a service's Java class without package name prefix.
+string ClassNameWithoutPackage(const ServiceDescriptor* descriptor,
+ bool immutable) {
+ string full_name = StripPackageName(descriptor->full_name(),
+ descriptor->file());
+ // We don't allow nested service definitions.
+ GOOGLE_CHECK(full_name.find('.') == string::npos);
+ return full_name;
+}
+
+// Check whether a given message or its nested types has the given class name.
+bool MessageHasConflictingClassName(const Descriptor* message,
+ const string& classname) {
+ if (message->name() == classname) return true;
+ for (int i = 0; i < message->nested_type_count(); ++i) {
+ if (MessageHasConflictingClassName(message->nested_type(i), classname)) {
+ return true;
+ }
+ }
+ for (int i = 0; i < message->enum_type_count(); ++i) {
+ if (message->enum_type(i)->name() == classname) {
+ return true;
+ }
+ }
+ return false;
+}
+
+} // namespace
+
+ClassNameResolver::ClassNameResolver() {
+}
+
+ClassNameResolver::~ClassNameResolver() {
+}
+
+string ClassNameResolver::GetFileDefaultImmutableClassName(
+ const FileDescriptor* file) {
+ string basename;
+ string::size_type last_slash = file->name().find_last_of('/');
+ if (last_slash == string::npos) {
+ basename = file->name();
+ } else {
+ basename = file->name().substr(last_slash + 1);
+ }
+ return UnderscoresToCamelCase(StripProto(basename), true);
+}
+
+string ClassNameResolver::GetFileImmutableClassName(
+ const FileDescriptor* file) {
+ string& class_name = file_immutable_outer_class_names_[file];
+ if (class_name.empty()) {
+ if (file->options().has_java_outer_classname()) {
+ class_name = file->options().java_outer_classname();
+ } else {
+ class_name = GetFileDefaultImmutableClassName(file);
+ if (HasConflictingClassName(file, class_name)) {
+ class_name += kOuterClassNameSuffix;
+ }
+ }
+ }
+ return class_name;
+}
+
+string ClassNameResolver::GetFileClassName(const FileDescriptor* file,
+ bool immutable) {
+ if (immutable) {
+ return GetFileImmutableClassName(file);
+ } else {
+ return "Mutable" + GetFileImmutableClassName(file);
+ }
+}
+
+// Check whether there is any type defined in the proto file that has
+// the given class name.
+bool ClassNameResolver::HasConflictingClassName(
+ const FileDescriptor* file, const string& classname) {
+ for (int i = 0; i < file->enum_type_count(); i++) {
+ if (file->enum_type(i)->name() == classname) {
+ return true;
+ }
+ }
+ for (int i = 0; i < file->service_count(); i++) {
+ if (file->service(i)->name() == classname) {
+ return true;
+ }
+ }
+ for (int i = 0; i < file->message_type_count(); i++) {
+ if (MessageHasConflictingClassName(file->message_type(i), classname)) {
+ return true;
+ }
+ }
+ return false;
+}
+
+string ClassNameResolver::GetDescriptorClassName(
+ const FileDescriptor* descriptor) {
+ return GetFileImmutableClassName(descriptor);
+}
+
+string ClassNameResolver::GetClassName(const FileDescriptor* descriptor,
+ bool immutable) {
+ string result = FileJavaPackage(descriptor, immutable);
+ if (!result.empty()) result += '.';
+ result += GetFileClassName(descriptor, immutable);
+ return result;
+}
+
+// Get the full name of a Java class by prepending the Java package name
+// or outer class name.
+string ClassNameResolver::GetClassFullName(const string& name_without_package,
+ const FileDescriptor* file,
+ bool immutable,
+ bool multiple_files) {
+ string result;
+ if (multiple_files) {
+ result = FileJavaPackage(file, immutable);
+ } else {
+ result = GetClassName(file, immutable);
+ }
+ if (!result.empty()) {
+ result += '.';
+ }
+ result += name_without_package;
+ return result;
+}
+
+string ClassNameResolver::GetClassName(const Descriptor* descriptor,
+ bool immutable) {
+ return GetClassFullName(ClassNameWithoutPackage(descriptor, immutable),
+ descriptor->file(), immutable,
+ MultipleJavaFiles(descriptor->file(), immutable));
+}
+
+string ClassNameResolver::GetClassName(const EnumDescriptor* descriptor,
+ bool immutable) {
+ return GetClassFullName(ClassNameWithoutPackage(descriptor, immutable),
+ descriptor->file(), immutable,
+ MultipleJavaFiles(descriptor->file(), immutable));
+}
+
+string ClassNameResolver::GetClassName(const ServiceDescriptor* descriptor,
+ bool immutable) {
+ return GetClassFullName(ClassNameWithoutPackage(descriptor, immutable),
+ descriptor->file(), immutable,
+ MultipleJavaFiles(descriptor->file(), immutable));
+}
+
+// Get the Java Class style full name of a message.
+string ClassNameResolver::GetJavaClassFullName(
+ const string& name_without_package,
+ const FileDescriptor* file,
+ bool immutable) {
+ string result;
+ if (MultipleJavaFiles(file, immutable)) {
+ result = FileJavaPackage(file, immutable);
+ if (!result.empty()) result += '.';
+ } else {
+ result = GetClassName(file, immutable);
+ if (!result.empty()) result += '$';
+ }
+ result += StringReplace(name_without_package, ".", "$", true);
+ return result;
+}
+
+string ClassNameResolver::GetExtensionIdentifierName(
+ const FieldDescriptor* descriptor, bool immutable) {
+ return GetClassName(descriptor->containing_type(), immutable) + "." +
+ descriptor->name();
+}
+
+
+string ClassNameResolver::GetJavaImmutableClassName(
+ const Descriptor* descriptor) {
+ return GetJavaClassFullName(
+ ClassNameWithoutPackage(descriptor, true),
+ descriptor->file(), true);
+}
+
+string ClassNameResolver::GetJavaImmutableClassName(
+ const EnumDescriptor* descriptor) {
+ return GetJavaClassFullName(
+ ClassNameWithoutPackage(descriptor, true),
+ descriptor->file(), true);
+}
+
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.h
new file mode 100644
index 0000000000..570d8d8f1f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_name_resolver.h
@@ -0,0 +1,125 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_NAME_RESOLVER_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_NAME_RESOLVER_H__
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+class Descriptor;
+class EnumDescriptor;
+class FieldDescriptor;
+class FileDescriptor;
+class ServiceDescriptor;
+
+namespace compiler {
+namespace java {
+
+// Used to get the Java class related names for a given descriptor. It caches
+// the results to avoid redundant calculation across multiple name queries.
+// Thread-safety note: This class is *not* thread-safe.
+class ClassNameResolver {
+ public:
+ ClassNameResolver();
+ ~ClassNameResolver();
+
+ // Gets the unqualified outer class name for the file.
+ string GetFileClassName(const FileDescriptor* file, bool immutable);
+ // Gets the unqualified immutable outer class name of a file.
+ string GetFileImmutableClassName(const FileDescriptor* file);
+ // Gets the unqualified default immutable outer class name of a file
+ // (converted from the proto file's name).
+ string GetFileDefaultImmutableClassName(const FileDescriptor* file);
+
+ // Check whether there is any type defined in the proto file that has
+ // the given class name.
+ bool HasConflictingClassName(const FileDescriptor* file,
+ const string& classname);
+
+ // Gets the name of the outer class that holds descriptor information.
+ // Descriptors are shared between immutable messages and mutable messages.
+ // Since both of them are generated optionally, the descriptors need to be
+ // put in another common place.
+ string GetDescriptorClassName(const FileDescriptor* file);
+
+ // Gets the fully-qualified class name corresponding to the given descriptor.
+ string GetClassName(const Descriptor* descriptor, bool immutable);
+ string GetClassName(const EnumDescriptor* descriptor, bool immutable);
+ string GetClassName(const ServiceDescriptor* descriptor, bool immutable);
+ string GetClassName(const FileDescriptor* descriptor, bool immutable);
+
+ template<class DescriptorType>
+ string GetImmutableClassName(const DescriptorType* descriptor) {
+ return GetClassName(descriptor, true);
+ }
+ template<class DescriptorType>
+ string GetMutableClassName(const DescriptorType* descriptor) {
+ return GetClassName(descriptor, false);
+ }
+
+ // Gets the fully qualified name of an extension identifier.
+ string GetExtensionIdentifierName(const FieldDescriptor* descriptor,
+ bool immutable);
+
+ // Gets the fully qualified name for generated classes in Java convention.
+ // Nested classes will be separated using '$' instead of '.'
+ // For example:
+ // com.package.OuterClass$OuterMessage$InnerMessage
+ string GetJavaImmutableClassName(const Descriptor* descriptor);
+ string GetJavaImmutableClassName(const EnumDescriptor* descriptor);
+ private:
+ // Get the full name of a Java class by prepending the Java package name
+ // or outer class name.
+ string GetClassFullName(const string& name_without_package,
+ const FileDescriptor* file,
+ bool immutable,
+ bool multiple_files);
+ // Get the Java Class style full name of a message.
+ string GetJavaClassFullName(
+ const string& name_without_package,
+ const FileDescriptor* file,
+ bool immutable);
+ // Caches the result to provide better performance.
+ map<const FileDescriptor*, string> file_immutable_outer_class_names_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ClassNameResolver);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_NAME_RESOLVER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_names.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_names.h
new file mode 100644
index 0000000000..0d6143353a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_names.h
@@ -0,0 +1,87 @@
+// 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.
+//
+// Provides a mechanism for mapping a descriptor to the
+// fully-qualified name of the corresponding Java class.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_NAMES_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_NAMES_H__
+
+#include <string>
+
+namespace google {
+namespace protobuf {
+
+class Descriptor;
+class EnumDescriptor;
+class FileDescriptor;
+class ServiceDescriptor;
+
+namespace compiler {
+namespace java {
+
+// Requires:
+// descriptor != NULL
+//
+// Returns:
+// The fully-qualified Java class name.
+string ClassName(const Descriptor* descriptor);
+
+// Requires:
+// descriptor != NULL
+//
+// Returns:
+// The fully-qualified Java class name.
+string ClassName(const EnumDescriptor* descriptor);
+
+// Requires:
+// descriptor != NULL
+//
+// Returns:
+// The fully-qualified Java class name.
+string ClassName(const FileDescriptor* descriptor);
+
+// Requires:
+// descriptor != NULL
+//
+// Returns:
+// The fully-qualified Java class name.
+string ClassName(const ServiceDescriptor* descriptor);
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_NAMES_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_options.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_options.h
new file mode 100644
index 0000000000..7bce14470d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_options.h
@@ -0,0 +1,73 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_OPTIONS_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_OPTIONS_H__
+
+#include <string>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+// Generator options
+struct Options {
+ Options()
+ : generate_immutable_code(false),
+ generate_mutable_code(false),
+ generate_shared_code(false),
+ enforce_lite(false),
+ annotate_code(false) {
+ }
+
+ bool generate_immutable_code;
+ bool generate_mutable_code;
+ bool generate_shared_code;
+ // When set, the protoc will generate the current files and all the transitive
+ // dependencies as lite runtime.
+ bool enforce_lite;
+ // If true, we should build .meta files and emit @Generated annotations into
+ // generated code.
+ bool annotate_code;
+ // Name of a file where we will write a list of generated .meta file names,
+ // one per line.
+ string annotation_list_file;
+ // Name of a file where we will write a list of generated file names, one
+ // per line.
+ string output_list_file;
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_OPTIONS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_plugin_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_plugin_unittest.cc
new file mode 100644
index 0000000000..3e4910c88a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_plugin_unittest.cc
@@ -0,0 +1,128 @@
+// 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)
+//
+// TODO(kenton): Share code with the versions of this test in other languages?
+// It seemed like parameterizing it would add more complexity than it is
+// worth.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/java/java_generator.h>
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/printer.h>
+
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+namespace {
+
+class TestGenerator : public CodeGenerator {
+ public:
+ TestGenerator() {}
+ ~TestGenerator() {}
+
+ virtual bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ string filename = "Test.java";
+ TryInsert(filename, "outer_class_scope", context);
+ TryInsert(filename, "class_scope:foo.Bar", context);
+ TryInsert(filename, "class_scope:foo.Bar.Baz", context);
+ TryInsert(filename, "builder_scope:foo.Bar", context);
+ TryInsert(filename, "builder_scope:foo.Bar.Baz", context);
+ TryInsert(filename, "enum_scope:foo.Qux", context);
+ return true;
+ }
+
+ void TryInsert(const string& filename, const string& insertion_point,
+ GeneratorContext* context) const {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->OpenForInsert(filename, insertion_point));
+ io::Printer printer(output.get(), '$');
+ printer.Print("// inserted $name$\n", "name", insertion_point);
+ }
+};
+
+// This test verifies that all the expected insertion points exist. It does
+// not verify that they are correctly-placed; that would require actually
+// compiling the output which is a bit more than I care to do for this test.
+TEST(JavaPluginTest, PluginTest) {
+ GOOGLE_CHECK_OK(File::SetContents(TestTempDir() + "/test.proto",
+ "syntax = \"proto2\";\n"
+ "package foo;\n"
+ "option java_package = \"\";\n"
+ "option java_outer_classname = \"Test\";\n"
+ "message Bar {\n"
+ " message Baz {}\n"
+ "}\n"
+ "enum Qux { BLAH = 1; }\n",
+ true));
+
+ google::protobuf::compiler::CommandLineInterface cli;
+ cli.SetInputsAreProtoPathRelative(true);
+
+ JavaGenerator java_generator;
+ TestGenerator test_generator;
+ cli.RegisterGenerator("--java_out", &java_generator, "");
+ cli.RegisterGenerator("--test_out", &test_generator, "");
+
+ string proto_path = "-I" + TestTempDir();
+ string java_out = "--java_out=" + TestTempDir();
+ string test_out = "--test_out=" + TestTempDir();
+
+ const char* argv[] = {
+ "protoc",
+ proto_path.c_str(),
+ java_out.c_str(),
+ test_out.c_str(),
+ "test.proto"
+ };
+
+ EXPECT_EQ(0, cli.Run(5, argv));
+}
+
+} // namespace
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.cc
new file mode 100644
index 0000000000..877baf0a63
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.cc
@@ -0,0 +1,860 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/compiler/java/java_primitive_field.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+void SetPrimitiveVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ (*variables)["type"] = PrimitiveTypeName(GetJavaType(descriptor));
+ (*variables)["boxed_type"] = BoxedPrimitiveTypeName(GetJavaType(descriptor));
+ (*variables)["field_type"] = (*variables)["type"];
+ (*variables)["field_list_type"] = "java.util.List<" +
+ (*variables)["boxed_type"] + ">";
+ (*variables)["empty_list"] = "java.util.Collections.emptyList()";
+ (*variables)["default"] = ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["default_init"] = IsDefaultValueJavaDefault(descriptor) ?
+ "" : ("= " + ImmutableDefaultValue(descriptor, name_resolver));
+ (*variables)["capitalized_type"] =
+ GetCapitalizedType(descriptor, /* immutable = */ true);
+ (*variables)["tag"] = SimpleItoa(WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ WireFormat::TagSize(descriptor->number(), GetType(descriptor)));
+ if (IsReferenceType(GetJavaType(descriptor))) {
+ (*variables)["null_check"] =
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n";
+ } else {
+ (*variables)["null_check"] = "";
+ }
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+ int fixed_size = FixedSize(GetType(descriptor));
+ if (fixed_size != -1) {
+ (*variables)["fixed_size"] = SimpleItoa(fixed_size);
+ }
+ (*variables)["on_changed"] = "onChanged();";
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+ (*variables)["get_has_field_bit_builder"] = GenerateGetBit(builderBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["set_has_field_bit_builder"] =
+ GenerateSetBit(builderBitIndex) + ";";
+ (*variables)["clear_has_field_bit_builder"] =
+ GenerateClearBit(builderBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["set_has_field_bit_builder"] = "";
+ (*variables)["clear_has_field_bit_builder"] = "";
+
+ if (descriptor->type() == FieldDescriptor::TYPE_BYTES) {
+ (*variables)["is_field_present_message"] =
+ "!" + (*variables)["name"] + "_.isEmpty()";
+ } else {
+ (*variables)["is_field_present_message"] =
+ (*variables)["name"] + "_ != " + (*variables)["default"];
+ }
+ }
+
+ // For repated builders, one bit is used for whether the array is immutable.
+ (*variables)["get_mutable_bit_builder"] = GenerateGetBit(builderBitIndex);
+ (*variables)["set_mutable_bit_builder"] = GenerateSetBit(builderBitIndex);
+ (*variables)["clear_mutable_bit_builder"] = GenerateClearBit(builderBitIndex);
+
+ // For repeated fields, one bit is used for whether the array is immutable
+ // in the parsing constructor.
+ (*variables)["get_mutable_bit_parser"] =
+ GenerateGetBitMutableLocal(builderBitIndex);
+ (*variables)["set_mutable_bit_parser"] =
+ GenerateSetBitMutableLocal(builderBitIndex);
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutablePrimitiveFieldGenerator::
+ImmutablePrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutablePrimitiveFieldGenerator::~ImmutablePrimitiveFieldGenerator() {}
+
+int ImmutablePrimitiveFieldGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutablePrimitiveFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$();\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private $field_type$ $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return $name$_;\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private $field_type$ $name$_ $default_init$;\n");
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_builder$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return $name$_;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ "$null_check$"
+ " $set_has_field_bit_builder$\n"
+ " $name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " $clear_has_field_bit_builder$\n");
+ JavaType type = GetJavaType(descriptor_);
+ if (type == JAVATYPE_STRING || type == JAVATYPE_BYTES) {
+ // The default value is not a simple literal so we want to avoid executing
+ // it multiple times. Instead, get the default out of the default instance.
+ printer->Print(variables_,
+ " $name$_ = getDefaultInstance().get$capitalized_name$();\n");
+ } else {
+ printer->Print(variables_,
+ " $name$_ = $default$;\n");
+ }
+ printer->Print(variables_,
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = $default$;\n"
+ "$clear_has_field_bit_builder$\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "if (other.has$capitalized_name$()) {\n"
+ " set$capitalized_name$(other.get$capitalized_name$());\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "if (other.get$capitalized_name$() != $default$) {\n"
+ " set$capitalized_name$(other.get$capitalized_name$());\n"
+ "}\n");
+ }
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "if ($get_has_field_bit_from_local$) {\n"
+ " $set_has_field_bit_to_local$;\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "result.$name$_ = $name$_;\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$set_has_field_bit_message$\n"
+ "$name$_ = input.read$capitalized_type$();\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for primitives.
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " output.write$capitalized_type$($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$capitalized_type$Size($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ switch (GetJavaType(descriptor_)) {
+ case JAVATYPE_INT:
+ case JAVATYPE_LONG:
+ case JAVATYPE_BOOLEAN:
+ printer->Print(variables_,
+ "result = result && (get$capitalized_name$()\n"
+ " == other.get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_FLOAT:
+ printer->Print(variables_,
+ "result = result && (\n"
+ " java.lang.Float.floatToIntBits(get$capitalized_name$())\n"
+ " == java.lang.Float.floatToIntBits(\n"
+ " other.get$capitalized_name$()));\n");
+ break;
+
+ case JAVATYPE_DOUBLE:
+ printer->Print(variables_,
+ "result = result && (\n"
+ " java.lang.Double.doubleToLongBits(get$capitalized_name$())\n"
+ " == java.lang.Double.doubleToLongBits(\n"
+ " other.get$capitalized_name$()));\n");
+ break;
+
+ case JAVATYPE_STRING:
+ case JAVATYPE_BYTES:
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_ENUM:
+ case JAVATYPE_MESSAGE:
+ default:
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ break;
+ }
+}
+
+void ImmutablePrimitiveFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n");
+ switch (GetJavaType(descriptor_)) {
+ case JAVATYPE_INT:
+ printer->Print(variables_,
+ "hash = (53 * hash) + get$capitalized_name$();\n");
+ break;
+
+ case JAVATYPE_LONG:
+ printer->Print(variables_,
+ "hash = (53 * hash) + com.google.protobuf.Internal.hashLong(\n"
+ " get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_BOOLEAN:
+ printer->Print(variables_,
+ "hash = (53 * hash) + com.google.protobuf.Internal.hashBoolean(\n"
+ " get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_FLOAT:
+ printer->Print(variables_,
+ "hash = (53 * hash) + java.lang.Float.floatToIntBits(\n"
+ " get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_DOUBLE:
+ printer->Print(variables_,
+ "hash = (53 * hash) + com.google.protobuf.Internal.hashLong(\n"
+ " java.lang.Double.doubleToLongBits(get$capitalized_name$()));\n");
+ break;
+
+ case JAVATYPE_STRING:
+ case JAVATYPE_BYTES:
+ printer->Print(variables_,
+ "hash = (53 * hash) + get$capitalized_name$().hashCode();\n");
+ break;
+
+ case JAVATYPE_ENUM:
+ case JAVATYPE_MESSAGE:
+ default:
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ break;
+ }
+}
+
+string ImmutablePrimitiveFieldGenerator::GetBoxedType() const {
+ return BoxedPrimitiveTypeName(GetJavaType(descriptor_));
+}
+
+// ===================================================================
+
+ImmutablePrimitiveOneofFieldGenerator::
+ImmutablePrimitiveOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutablePrimitiveFieldGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutablePrimitiveOneofFieldGenerator::
+~ImmutablePrimitiveOneofFieldGenerator() {}
+
+void ImmutablePrimitiveOneofFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($boxed_type$) $oneof_name$_;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n");
+}
+
+
+void ImmutablePrimitiveOneofFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($boxed_type$) $oneof_name$_;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ "$null_check$"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " $on_changed$\n"
+ " }\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveOneofFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " result.$oneof_name$_ = $oneof_name$_;\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveOneofFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "set$capitalized_name$(other.get$capitalized_name$());\n");
+}
+
+void ImmutablePrimitiveOneofFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = input.read$capitalized_type$();\n");
+}
+
+void ImmutablePrimitiveOneofFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.write$capitalized_type$(\n"
+ " $number$, ($type$)(($boxed_type$) $oneof_name$_));\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveOneofFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$capitalized_type$Size(\n"
+ " $number$, ($type$)(($boxed_type$) $oneof_name$_));\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutablePrimitiveFieldGenerator::
+RepeatedImmutablePrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutablePrimitiveFieldGenerator::
+~RepeatedImmutablePrimitiveFieldGenerator() {}
+
+int RepeatedImmutablePrimitiveFieldGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutablePrimitiveFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<$boxed_type$> get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$(int index);\n");
+}
+
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private $field_list_type$ $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$boxed_type$>\n"
+ " get$capitalized_name$List() {\n"
+ " return $name$_;\n" // note: unmodifiable list
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+
+ if (descriptor_->is_packed() &&
+ context_->HasGeneratedMethods(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ "private int $name$MemoizedSerializedSize = -1;\n");
+ }
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // One field is the list and the bit field keeps track of whether the
+ // list is immutable. If it's immutable, the invariant is that it must
+ // either an instance of Collections.emptyList() or it's an ArrayList
+ // wrapped in a Collections.unmodifiableList() wrapper and nobody else has
+ // a refererence to the underlying ArrayList. This invariant allows us to
+ // share instances of lists between protocol buffers avoiding expensive
+ // memory allocations. Note, immutable is a strong guarantee here -- not
+ // just that the list cannot be modified via the reference but that the
+ // list can never be modified.
+ printer->Print(variables_,
+ "private $field_list_type$ $name$_ = $empty_list$;\n");
+
+ printer->Print(variables_,
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$get_mutable_bit_builder$) {\n"
+ " $name$_ = new java.util.ArrayList<$boxed_type$>($name$_);\n"
+ " $set_mutable_bit_builder$;\n"
+ " }\n"
+ "}\n");
+
+ // Note: We return an unmodifiable list because otherwise the caller
+ // could hold on to the returned list and modify it after the message
+ // has been built, thus mutating the message which is supposed to be
+ // immutable.
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$boxed_type$>\n"
+ " get$capitalized_name$List() {\n"
+ " return java.util.Collections.unmodifiableList($name$_);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, value);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$($type$ value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $boxed_type$> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " com.google.protobuf.AbstractMessageLite.Builder.addAll(\n"
+ " values, $name$_);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " $name$_ = $empty_list$;\n"
+ " $clear_mutable_bit_builder$;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $empty_list$;\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = $empty_list$;\n"
+ "$clear_mutable_bit_builder$;\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // The code below does two optimizations:
+ // 1. If the other list is empty, there's nothing to do. This ensures we
+ // don't allocate a new array if we already have an immutable one.
+ // 2. If the other list is non-empty and our current list is empty, we can
+ // reuse the other list which is guaranteed to be immutable.
+ printer->Print(variables_,
+ "if (!other.$name$_.isEmpty()) {\n"
+ " if ($name$_.isEmpty()) {\n"
+ " $name$_ = other.$name$_;\n"
+ " $clear_mutable_bit_builder$;\n"
+ " } else {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.addAll(other.$name$_);\n"
+ " }\n"
+ " $on_changed$\n"
+ "}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ // The code below ensures that the result has an immutable list. If our
+ // list is immutable, we can just reuse it. If not, we make it immutable.
+ printer->Print(variables_,
+ "if ($get_mutable_bit_builder$) {\n"
+ " $name$_ = java.util.Collections.unmodifiableList($name$_);\n"
+ " $clear_mutable_bit_builder$;\n"
+ "}\n"
+ "result.$name$_ = $name$_;\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!$get_mutable_bit_parser$) {\n"
+ " $name$_ = new java.util.ArrayList<$boxed_type$>();\n"
+ " $set_mutable_bit_parser$;\n"
+ "}\n"
+ "$name$_.add(input.read$capitalized_type$());\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateParsingCodeFromPacked(io::Printer* printer) const {
+ printer->Print(variables_,
+ "int length = input.readRawVarint32();\n"
+ "int limit = input.pushLimit(length);\n"
+ "if (!$get_mutable_bit_parser$ && input.getBytesUntilLimit() > 0) {\n"
+ " $name$_ = new java.util.ArrayList<$boxed_type$>();\n"
+ " $set_mutable_bit_parser$;\n"
+ "}\n"
+ "while (input.getBytesUntilLimit() > 0) {\n"
+ " $name$_.add(input.read$capitalized_type$());\n"
+ "}\n"
+ "input.popLimit(limit);\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_mutable_bit_parser$) {\n"
+ " $name$_ = java.util.Collections.unmodifiableList($name$_);\n"
+ "}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ if (descriptor_->is_packed()) {
+ // We invoke getSerializedSize in writeTo for messages that have packed
+ // fields in ImmutableMessageGenerator::GenerateMessageSerializationMethods.
+ // That makes it safe to rely on the memoized size here.
+ printer->Print(variables_,
+ "if (get$capitalized_name$List().size() > 0) {\n"
+ " output.writeUInt32NoTag($tag$);\n"
+ " output.writeUInt32NoTag($name$MemoizedSerializedSize);\n"
+ "}\n"
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.write$capitalized_type$NoTag($name$_.get(i));\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.write$capitalized_type$($number$, $name$_.get(i));\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "{\n"
+ " int dataSize = 0;\n");
+ printer->Indent();
+
+ if (FixedSize(GetType(descriptor_)) == -1) {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " dataSize += com.google.protobuf.CodedOutputStream\n"
+ " .compute$capitalized_type$SizeNoTag($name$_.get(i));\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "dataSize = $fixed_size$ * get$capitalized_name$List().size();\n");
+ }
+
+ printer->Print(
+ "size += dataSize;\n");
+
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ "if (!get$capitalized_name$List().isEmpty()) {\n"
+ " size += $tag_size$;\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeInt32SizeNoTag(dataSize);\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "size += $tag_size$ * get$capitalized_name$List().size();\n");
+ }
+
+ // cache the data size for packed fields.
+ if (descriptor_->is_packed()) {
+ printer->Print(variables_,
+ "$name$MemoizedSerializedSize = dataSize;\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$List()\n"
+ " .equals(other.get$capitalized_name$List());\n");
+}
+
+void RepeatedImmutablePrimitiveFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + get$capitalized_name$List().hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutablePrimitiveFieldGenerator::GetBoxedType() const {
+ return BoxedPrimitiveTypeName(GetJavaType(descriptor_));
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.h
new file mode 100644
index 0000000000..d0cd12d976
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field.h
@@ -0,0 +1,160 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_PRIMITIVE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_PRIMITIVE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutablePrimitiveFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit ImmutablePrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutablePrimitiveFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutablePrimitiveFieldGenerator);
+};
+
+class ImmutablePrimitiveOneofFieldGenerator
+ : public ImmutablePrimitiveFieldGenerator {
+ public:
+ ImmutablePrimitiveOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutablePrimitiveOneofFieldGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutablePrimitiveOneofFieldGenerator);
+};
+
+class RepeatedImmutablePrimitiveFieldGenerator
+ : public ImmutableFieldGenerator {
+ public:
+ explicit RepeatedImmutablePrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ virtual ~RepeatedImmutablePrimitiveFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingCodeFromPacked(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutablePrimitiveFieldGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_PRIMITIVE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.cc
new file mode 100644
index 0000000000..ad2db30c43
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.cc
@@ -0,0 +1,914 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/compiler/java/java_primitive_field_lite.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+void SetPrimitiveVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+ JavaType javaType = GetJavaType(descriptor);
+ (*variables)["type"] = PrimitiveTypeName(javaType);
+ (*variables)["boxed_type"] = BoxedPrimitiveTypeName(javaType);
+ (*variables)["field_type"] = (*variables)["type"];
+ (*variables)["default"] = ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["capitalized_type"] =
+ GetCapitalizedType(descriptor, /* immutable = */ true);
+ (*variables)["tag"] = SimpleItoa(WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ WireFormat::TagSize(descriptor->number(), GetType(descriptor)));
+
+ string capitalized_type = UnderscoresToCamelCase(PrimitiveTypeName(javaType),
+ true /* cap_next_letter */);
+ switch (javaType) {
+ case JAVATYPE_INT:
+ case JAVATYPE_LONG:
+ case JAVATYPE_FLOAT:
+ case JAVATYPE_DOUBLE:
+ case JAVATYPE_BOOLEAN:
+ (*variables)["field_list_type"] =
+ "com.google.protobuf.Internal." + capitalized_type + "List";
+ (*variables)["empty_list"] = "empty" + capitalized_type + "List()";
+ (*variables)["make_name_unmodifiable"] =
+ (*variables)["name"] + "_.makeImmutable()";
+ (*variables)["repeated_get"] =
+ (*variables)["name"] + "_.get" + capitalized_type;
+ (*variables)["repeated_add"] =
+ (*variables)["name"] + "_.add" + capitalized_type;
+ (*variables)["repeated_set"] =
+ (*variables)["name"] + "_.set" + capitalized_type;
+ (*variables)["visit_type"] = capitalized_type;
+ (*variables)["visit_type_list"] = "visit" + capitalized_type + "List";
+ break;
+ default:
+ (*variables)["field_list_type"] =
+ "com.google.protobuf.Internal.ProtobufList<" +
+ (*variables)["boxed_type"] + ">";
+ (*variables)["empty_list"] = "emptyProtobufList()";
+ (*variables)["make_name_unmodifiable"] =
+ (*variables)["name"] + "_.makeImmutable()";
+ (*variables)["repeated_get"] = (*variables)["name"] + "_.get";
+ (*variables)["repeated_add"] = (*variables)["name"] + "_.add";
+ (*variables)["repeated_set"] = (*variables)["name"] + "_.set";
+ (*variables)["visit_type"] = "ByteString";
+ (*variables)["visit_type_list"] = "visitList";
+ }
+
+ if (javaType == JAVATYPE_BYTES) {
+ (*variables)["bytes_default"] =
+ ToUpper((*variables)["name"]) + "_DEFAULT_VALUE";
+ }
+
+ if (IsReferenceType(javaType)) {
+ (*variables)["null_check"] =
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n";
+ } else {
+ (*variables)["null_check"] = "";
+ }
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+ int fixed_size = FixedSize(GetType(descriptor));
+ if (fixed_size != -1) {
+ (*variables)["fixed_size"] = SimpleItoa(fixed_size);
+ }
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["clear_has_field_bit_message"] =
+ GenerateClearBit(messageBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["clear_has_field_bit_message"] = "";
+
+ if (descriptor->type() == FieldDescriptor::TYPE_BYTES) {
+ (*variables)["is_field_present_message"] =
+ "!" + (*variables)["name"] + "_.isEmpty()";
+ } else {
+ (*variables)["is_field_present_message"] =
+ (*variables)["name"] + "_ != " + (*variables)["default"];
+ }
+ }
+
+ // For repeated builders, the underlying list tracks mutability state.
+ (*variables)["is_mutable"] = (*variables)["name"] + "_.isModifiable()";
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutablePrimitiveFieldLiteGenerator::
+ImmutablePrimitiveFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutablePrimitiveFieldLiteGenerator::~ImmutablePrimitiveFieldLiteGenerator() {}
+
+int ImmutablePrimitiveFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutablePrimitiveFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$();\n");
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ if (IsByteStringWithCustomDefaultValue(descriptor_)) {
+ // allocate this once statically since we know ByteStrings are immutable
+ // values that can be reused.
+ printer->Print(
+ variables_,
+ "private static final $field_type$ $bytes_default$ = $default$;\n");
+ }
+ printer->Print(variables_,
+ "private $field_type$ $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return $name$_;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ "$null_check$"
+ " $set_has_field_bit_message$\n"
+ " $name$_ = value;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $clear_has_field_bit_message$\n");
+ JavaType type = GetJavaType(descriptor_);
+ if (type == JAVATYPE_STRING || type == JAVATYPE_BYTES) {
+ // The default value is not a simple literal so we want to avoid executing
+ // it multiple times. Instead, get the default out of the default instance.
+ printer->Print(variables_,
+ " $name$_ = getDefaultInstance().get$capitalized_name$();\n");
+ } else {
+ printer->Print(variables_,
+ " $name$_ = $default$;\n");
+ }
+ printer->Print(variables_,
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ if (IsByteStringWithCustomDefaultValue(descriptor_)) {
+ printer->Print(variables_, "$name$_ = $bytes_default$;\n");
+ } else if (!IsDefaultValueJavaDefault(descriptor_)) {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+ }
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "$name$_ = visitor.visit$visit_type$(\n"
+ " has$capitalized_name$(), $name$_,\n"
+ " other.has$capitalized_name$(), other.$name$_);\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_ = visitor.visit$visit_type$($name$_ != $default$, $name$_,\n"
+ " other.$name$_ != $default$, other.$name$_);\n");
+ }
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ // noop for scalars
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$set_has_field_bit_message$\n"
+ "$name$_ = input.read$capitalized_type$();\n");
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for primitives.
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " output.write$capitalized_type$($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$capitalized_type$Size($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ switch (GetJavaType(descriptor_)) {
+ case JAVATYPE_INT:
+ case JAVATYPE_LONG:
+ case JAVATYPE_BOOLEAN:
+ printer->Print(variables_,
+ "result = result && (get$capitalized_name$()\n"
+ " == other.get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_FLOAT:
+ printer->Print(variables_,
+ "result = result && (\n"
+ " java.lang.Float.floatToIntBits(get$capitalized_name$())\n"
+ " == java.lang.Float.floatToIntBits(\n"
+ " other.get$capitalized_name$()));\n");
+ break;
+
+ case JAVATYPE_DOUBLE:
+ printer->Print(variables_,
+ "result = result && (\n"
+ " java.lang.Double.doubleToLongBits(get$capitalized_name$())\n"
+ " == java.lang.Double.doubleToLongBits(\n"
+ " other.get$capitalized_name$()));\n");
+ break;
+
+ case JAVATYPE_STRING:
+ case JAVATYPE_BYTES:
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_ENUM:
+ case JAVATYPE_MESSAGE:
+ default:
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ break;
+ }
+}
+
+void ImmutablePrimitiveFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n");
+ switch (GetJavaType(descriptor_)) {
+ case JAVATYPE_INT:
+ printer->Print(variables_,
+ "hash = (53 * hash) + get$capitalized_name$();\n");
+ break;
+
+ case JAVATYPE_LONG:
+ printer->Print(variables_,
+ "hash = (53 * hash) + com.google.protobuf.Internal.hashLong(\n"
+ " get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_BOOLEAN:
+ printer->Print(variables_,
+ "hash = (53 * hash) + com.google.protobuf.Internal.hashBoolean(\n"
+ " get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_FLOAT:
+ printer->Print(variables_,
+ "hash = (53 * hash) + java.lang.Float.floatToIntBits(\n"
+ " get$capitalized_name$());\n");
+ break;
+
+ case JAVATYPE_DOUBLE:
+ printer->Print(variables_,
+ "hash = (53 * hash) + com.google.protobuf.Internal.hashLong(\n"
+ " java.lang.Double.doubleToLongBits(get$capitalized_name$()));\n");
+ break;
+
+ case JAVATYPE_STRING:
+ case JAVATYPE_BYTES:
+ printer->Print(variables_,
+ "hash = (53 * hash) + get$capitalized_name$().hashCode();\n");
+ break;
+
+ case JAVATYPE_ENUM:
+ case JAVATYPE_MESSAGE:
+ default:
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ break;
+ }
+}
+
+string ImmutablePrimitiveFieldLiteGenerator::GetBoxedType() const {
+ return BoxedPrimitiveTypeName(GetJavaType(descriptor_));
+}
+
+// ===================================================================
+
+ImmutablePrimitiveOneofFieldLiteGenerator::
+ImmutablePrimitiveOneofFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutablePrimitiveFieldLiteGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutablePrimitiveOneofFieldLiteGenerator::
+~ImmutablePrimitiveOneofFieldLiteGenerator() {}
+
+void ImmutablePrimitiveOneofFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " return ($boxed_type$) $oneof_name$_;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$($type$ value) {\n"
+ "$null_check$"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " }\n"
+ "}\n");
+}
+
+
+void ImmutablePrimitiveOneofFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveOneofFieldLiteGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void ImmutablePrimitiveOneofFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$oneof_name$_ = visitor.visitOneof$visit_type$(\n"
+ " $has_oneof_case_message$, $oneof_name$_, other.$oneof_name$_);\n");
+}
+
+void ImmutablePrimitiveOneofFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = input.read$capitalized_type$();\n");
+}
+
+void ImmutablePrimitiveOneofFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.write$capitalized_type$(\n"
+ " $number$, ($type$)(($boxed_type$) $oneof_name$_));\n"
+ "}\n");
+}
+
+void ImmutablePrimitiveOneofFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .compute$capitalized_type$Size(\n"
+ " $number$, ($type$)(($boxed_type$) $oneof_name$_));\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutablePrimitiveFieldLiteGenerator::
+RepeatedImmutablePrimitiveFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutablePrimitiveFieldLiteGenerator::
+~RepeatedImmutablePrimitiveFieldLiteGenerator() {}
+
+int RepeatedImmutablePrimitiveFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutablePrimitiveFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<$boxed_type$> get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$$type$ get$capitalized_name$(int index);\n");
+}
+
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private $field_list_type$ $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$boxed_type$>\n"
+ " get$capitalized_name$List() {\n"
+ " return $name$_;\n" // note: unmodifiable list
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return $repeated_get$(index);\n"
+ "}\n");
+
+ if (descriptor_->options().packed() &&
+ context_->HasGeneratedMethods(descriptor_->containing_type())) {
+ printer->Print(variables_,
+ "private int $name$MemoizedSerializedSize = -1;\n");
+ }
+
+ printer->Print(variables_,
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $repeated_set$(index, value);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$($type$ value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $repeated_add$(value);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $boxed_type$> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " com.google.protobuf.AbstractMessageLite.addAll(\n"
+ " values, $name$_);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $name$_ = $empty_list$;\n"
+ "}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<$boxed_type$>\n"
+ " get$capitalized_name$List() {\n"
+ " return java.util.Collections.unmodifiableList(\n"
+ " instance.get$capitalized_name$List());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return instance.get$capitalized_name$Count();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public $type$ get$capitalized_name$(int index) {\n"
+ " return instance.get$capitalized_name$(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, $type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(index, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$($type$ value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<? extends $boxed_type$> values) {\n"
+ " copyOnWrite();\n"
+ " instance.addAll$capitalized_name$(values);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $empty_list$;\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_= visitor.$visit_type_list$($name$_, other.$name$_);\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_.makeImmutable();\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ // TODO(dweis): Scan the input buffer to count, then initialize
+ // appropriately.
+ // TODO(dweis): Scan the input buffer to count and ensure capacity.
+ printer->Print(variables_,
+ "if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ "}\n"
+ "$repeated_add$(input.read$capitalized_type$());\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateParsingCodeFromPacked(io::Printer* printer) const {
+ printer->Print(variables_,
+ "int length = input.readRawVarint32();\n"
+ "int limit = input.pushLimit(length);\n"
+ "if (!$is_mutable$ && input.getBytesUntilLimit() > 0) {\n");
+
+ int fixed_size = FixedSize(GetType(descriptor_));
+ if (fixed_size == -1) {
+ // TODO(dweis): Scan the input buffer to count, then initialize
+ // appropriately.
+ printer->Print(variables_,
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n");
+ } else {
+ printer->Print(variables_,
+ " final int currentSize = $name$_.size();\n"
+ " $name$_ = $name$_.mutableCopyWithCapacity(\n"
+ " currentSize + (length/$fixed_size$));\n");
+ }
+
+ // TODO(dweis): Scan the input buffer to count and ensure capacity.
+ printer->Print(variables_,
+ "}\n"
+ "while (input.getBytesUntilLimit() > 0) {\n"
+ " $repeated_add$(input.read$capitalized_type$());\n"
+ "}\n"
+ "input.popLimit(limit);\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_mutable$) {\n"
+ " $make_name_unmodifiable$;\n"
+ "}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ if (descriptor_->options().packed()) {
+ // We invoke getSerializedSize in writeTo for messages that have packed
+ // fields in ImmutableMessageGenerator::GenerateMessageSerializationMethods.
+ // That makes it safe to rely on the memoized size here.
+ printer->Print(variables_,
+ "if (get$capitalized_name$List().size() > 0) {\n"
+ " output.writeUInt32NoTag($tag$);\n"
+ " output.writeUInt32NoTag($name$MemoizedSerializedSize);\n"
+ "}\n"
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.write$capitalized_type$NoTag($repeated_get$(i));\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.write$capitalized_type$($number$, $repeated_get$(i));\n"
+ "}\n");
+ }
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "{\n"
+ " int dataSize = 0;\n");
+ printer->Indent();
+
+ if (FixedSize(GetType(descriptor_)) == -1) {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " dataSize += com.google.protobuf.CodedOutputStream\n"
+ " .compute$capitalized_type$SizeNoTag($repeated_get$(i));\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "dataSize = $fixed_size$ * get$capitalized_name$List().size();\n");
+ }
+
+ printer->Print(
+ "size += dataSize;\n");
+
+ if (descriptor_->options().packed()) {
+ printer->Print(variables_,
+ "if (!get$capitalized_name$List().isEmpty()) {\n"
+ " size += $tag_size$;\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeInt32SizeNoTag(dataSize);\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "size += $tag_size$ * get$capitalized_name$List().size();\n");
+ }
+
+ // cache the data size for packed fields.
+ if (descriptor_->options().packed()) {
+ printer->Print(variables_,
+ "$name$MemoizedSerializedSize = dataSize;\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$List()\n"
+ " .equals(other.get$capitalized_name$List());\n");
+}
+
+void RepeatedImmutablePrimitiveFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + get$capitalized_name$List().hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutablePrimitiveFieldLiteGenerator::GetBoxedType() const {
+ return BoxedPrimitiveTypeName(GetJavaType(descriptor_));
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.h
new file mode 100644
index 0000000000..6cfbbb98cf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_primitive_field_lite.h
@@ -0,0 +1,163 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_PRIMITIVE_FIELD_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_PRIMITIVE_FIELD_LITE_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutablePrimitiveFieldLiteGenerator
+ : public ImmutableFieldLiteGenerator {
+ public:
+ explicit ImmutablePrimitiveFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutablePrimitiveFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutablePrimitiveFieldLiteGenerator);
+};
+
+class ImmutablePrimitiveOneofFieldLiteGenerator
+ : public ImmutablePrimitiveFieldLiteGenerator {
+ public:
+ ImmutablePrimitiveOneofFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutablePrimitiveOneofFieldLiteGenerator();
+
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutablePrimitiveOneofFieldLiteGenerator);
+};
+
+class RepeatedImmutablePrimitiveFieldLiteGenerator
+ : public ImmutableFieldLiteGenerator {
+ public:
+ explicit RepeatedImmutablePrimitiveFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ virtual ~RepeatedImmutablePrimitiveFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingCodeFromPacked(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutablePrimitiveFieldLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_PRIMITIVE_FIELD_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.cc
new file mode 100644
index 0000000000..9f34f01069
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.cc
@@ -0,0 +1,473 @@
+// 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.
+
+#include <google/protobuf/compiler/java/java_service.h>
+
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+ServiceGenerator::ServiceGenerator(const ServiceDescriptor* descriptor)
+ : descriptor_(descriptor) {}
+
+ServiceGenerator::~ServiceGenerator() {}
+
+// ===================================================================
+ImmutableServiceGenerator::ImmutableServiceGenerator(
+ const ServiceDescriptor* descriptor, Context* context)
+ : ServiceGenerator(descriptor), context_(context),
+ name_resolver_(context->GetNameResolver()) {}
+
+ImmutableServiceGenerator::~ImmutableServiceGenerator() {}
+
+void ImmutableServiceGenerator::Generate(io::Printer* printer) {
+ bool is_own_file = IsOwnFile(descriptor_, /* immutable = */ true);
+ WriteServiceDocComment(printer, descriptor_);
+ MaybePrintGeneratedAnnotation(context_, printer, descriptor_,
+ /* immutable = */ true);
+ printer->Print(
+ "public $static$ abstract class $classname$\n"
+ " implements com.google.protobuf.Service {\n",
+ "static", is_own_file ? "" : "static",
+ "classname", descriptor_->name());
+ printer->Indent();
+
+ printer->Print(
+ "protected $classname$() {}\n\n",
+ "classname", descriptor_->name());
+
+ GenerateInterface(printer);
+
+ GenerateNewReflectiveServiceMethod(printer);
+ GenerateNewReflectiveBlockingServiceMethod(printer);
+
+ GenerateAbstractMethods(printer);
+
+ // Generate getDescriptor() and getDescriptorForType().
+ printer->Print(
+ "public static final\n"
+ " com.google.protobuf.Descriptors.ServiceDescriptor\n"
+ " getDescriptor() {\n"
+ " return $file$.getDescriptor().getServices().get($index$);\n"
+ "}\n",
+ "file", name_resolver_->GetImmutableClassName(descriptor_->file()),
+ "index", SimpleItoa(descriptor_->index()));
+ GenerateGetDescriptorForType(printer);
+
+ // Generate more stuff.
+ GenerateCallMethod(printer);
+ GenerateGetPrototype(REQUEST, printer);
+ GenerateGetPrototype(RESPONSE, printer);
+ GenerateStub(printer);
+ GenerateBlockingStub(printer);
+
+ // Add an insertion point.
+ printer->Print(
+ "\n"
+ "// @@protoc_insertion_point(class_scope:$full_name$)\n",
+ "full_name", descriptor_->full_name());
+
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+void ImmutableServiceGenerator::GenerateGetDescriptorForType(
+ io::Printer* printer) {
+ printer->Print(
+ "public final com.google.protobuf.Descriptors.ServiceDescriptor\n"
+ " getDescriptorForType() {\n"
+ " return getDescriptor();\n"
+ "}\n");
+}
+
+void ImmutableServiceGenerator::GenerateInterface(io::Printer* printer) {
+ printer->Print("public interface Interface {\n");
+ printer->Indent();
+ GenerateAbstractMethods(printer);
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+void ImmutableServiceGenerator::GenerateNewReflectiveServiceMethod(
+ io::Printer* printer) {
+ printer->Print(
+ "public static com.google.protobuf.Service newReflectiveService(\n"
+ " final Interface impl) {\n"
+ " return new $classname$() {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ printer->Print("@java.lang.Override\n");
+ GenerateMethodSignature(printer, method, IS_CONCRETE);
+ printer->Print(
+ " {\n"
+ " impl.$method$(controller, request, done);\n"
+ "}\n\n",
+ "method", UnderscoresToCamelCase(method));
+ }
+
+ printer->Outdent();
+ printer->Print("};\n");
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+void ImmutableServiceGenerator::GenerateNewReflectiveBlockingServiceMethod(
+ io::Printer* printer) {
+ printer->Print(
+ "public static com.google.protobuf.BlockingService\n"
+ " newReflectiveBlockingService(final BlockingInterface impl) {\n"
+ " return new com.google.protobuf.BlockingService() {\n");
+ printer->Indent();
+ printer->Indent();
+
+ GenerateGetDescriptorForType(printer);
+
+ GenerateCallBlockingMethod(printer);
+ GenerateGetPrototype(REQUEST, printer);
+ GenerateGetPrototype(RESPONSE, printer);
+
+ printer->Outdent();
+ printer->Print("};\n");
+ printer->Outdent();
+ printer->Print("}\n\n");
+}
+
+void ImmutableServiceGenerator::GenerateAbstractMethods(io::Printer* printer) {
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ WriteMethodDocComment(printer, method);
+ GenerateMethodSignature(printer, method, IS_ABSTRACT);
+ printer->Print(";\n\n");
+ }
+}
+
+void ImmutableServiceGenerator::GenerateCallMethod(io::Printer* printer) {
+ printer->Print(
+ "\n"
+ "public final void callMethod(\n"
+ " com.google.protobuf.Descriptors.MethodDescriptor method,\n"
+ " com.google.protobuf.RpcController controller,\n"
+ " com.google.protobuf.Message request,\n"
+ " com.google.protobuf.RpcCallback<\n"
+ " com.google.protobuf.Message> done) {\n"
+ " if (method.getService() != getDescriptor()) {\n"
+ " throw new java.lang.IllegalArgumentException(\n"
+ " \"Service.callMethod() given method descriptor for wrong \" +\n"
+ " \"service type.\");\n"
+ " }\n"
+ " switch(method.getIndex()) {\n");
+ printer->Indent();
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ map<string, string> vars;
+ vars["index"] = SimpleItoa(i);
+ vars["method"] = UnderscoresToCamelCase(method);
+ vars["input"] = name_resolver_->GetImmutableClassName(
+ method->input_type());
+ vars["output"] = name_resolver_->GetImmutableClassName(
+ method->output_type());
+ printer->Print(vars,
+ "case $index$:\n"
+ " this.$method$(controller, ($input$)request,\n"
+ " com.google.protobuf.RpcUtil.<$output$>specializeCallback(\n"
+ " done));\n"
+ " return;\n");
+ }
+
+ printer->Print(
+ "default:\n"
+ " throw new java.lang.AssertionError(\"Can't get here.\");\n");
+
+ printer->Outdent();
+ printer->Outdent();
+
+ printer->Print(
+ " }\n"
+ "}\n"
+ "\n");
+}
+
+void ImmutableServiceGenerator::GenerateCallBlockingMethod(
+ io::Printer* printer) {
+ printer->Print(
+ "\n"
+ "public final com.google.protobuf.Message callBlockingMethod(\n"
+ " com.google.protobuf.Descriptors.MethodDescriptor method,\n"
+ " com.google.protobuf.RpcController controller,\n"
+ " com.google.protobuf.Message request)\n"
+ " throws com.google.protobuf.ServiceException {\n"
+ " if (method.getService() != getDescriptor()) {\n"
+ " throw new java.lang.IllegalArgumentException(\n"
+ " \"Service.callBlockingMethod() given method descriptor for \" +\n"
+ " \"wrong service type.\");\n"
+ " }\n"
+ " switch(method.getIndex()) {\n");
+ printer->Indent();
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ map<string, string> vars;
+ vars["index"] = SimpleItoa(i);
+ vars["method"] = UnderscoresToCamelCase(method);
+ vars["input"] = name_resolver_->GetImmutableClassName(
+ method->input_type());
+ vars["output"] = name_resolver_->GetImmutableClassName(
+ method->output_type());
+ printer->Print(vars,
+ "case $index$:\n"
+ " return impl.$method$(controller, ($input$)request);\n");
+ }
+
+ printer->Print(
+ "default:\n"
+ " throw new java.lang.AssertionError(\"Can't get here.\");\n");
+
+ printer->Outdent();
+ printer->Outdent();
+
+ printer->Print(
+ " }\n"
+ "}\n"
+ "\n");
+}
+
+void ImmutableServiceGenerator::GenerateGetPrototype(RequestOrResponse which,
+ io::Printer* printer) {
+ /*
+ * TODO(cpovirk): The exception message says "Service.foo" when it may be
+ * "BlockingService.foo." Consider fixing.
+ */
+ printer->Print(
+ "public final com.google.protobuf.Message\n"
+ " get$request_or_response$Prototype(\n"
+ " com.google.protobuf.Descriptors.MethodDescriptor method) {\n"
+ " if (method.getService() != getDescriptor()) {\n"
+ " throw new java.lang.IllegalArgumentException(\n"
+ " \"Service.get$request_or_response$Prototype() given method \" +\n"
+ " \"descriptor for wrong service type.\");\n"
+ " }\n"
+ " switch(method.getIndex()) {\n",
+ "request_or_response", (which == REQUEST) ? "Request" : "Response");
+ printer->Indent();
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ map<string, string> vars;
+ vars["index"] = SimpleItoa(i);
+ vars["type"] = name_resolver_->GetImmutableClassName(
+ (which == REQUEST) ? method->input_type() : method->output_type());
+ printer->Print(vars,
+ "case $index$:\n"
+ " return $type$.getDefaultInstance();\n");
+ }
+
+ printer->Print(
+ "default:\n"
+ " throw new java.lang.AssertionError(\"Can't get here.\");\n");
+
+ printer->Outdent();
+ printer->Outdent();
+
+ printer->Print(
+ " }\n"
+ "}\n"
+ "\n");
+}
+
+void ImmutableServiceGenerator::GenerateStub(io::Printer* printer) {
+ printer->Print(
+ "public static Stub newStub(\n"
+ " com.google.protobuf.RpcChannel channel) {\n"
+ " return new Stub(channel);\n"
+ "}\n"
+ "\n"
+ "public static final class Stub extends $classname$ implements Interface {"
+ "\n",
+ "classname", name_resolver_->GetImmutableClassName(descriptor_));
+ printer->Indent();
+
+ printer->Print(
+ "private Stub(com.google.protobuf.RpcChannel channel) {\n"
+ " this.channel = channel;\n"
+ "}\n"
+ "\n"
+ "private final com.google.protobuf.RpcChannel channel;\n"
+ "\n"
+ "public com.google.protobuf.RpcChannel getChannel() {\n"
+ " return channel;\n"
+ "}\n");
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ printer->Print("\n");
+ GenerateMethodSignature(printer, method, IS_CONCRETE);
+ printer->Print(" {\n");
+ printer->Indent();
+
+ map<string, string> vars;
+ vars["index"] = SimpleItoa(i);
+ vars["output"] = name_resolver_->GetImmutableClassName(
+ method->output_type());
+ printer->Print(vars,
+ "channel.callMethod(\n"
+ " getDescriptor().getMethods().get($index$),\n"
+ " controller,\n"
+ " request,\n"
+ " $output$.getDefaultInstance(),\n"
+ " com.google.protobuf.RpcUtil.generalizeCallback(\n"
+ " done,\n"
+ " $output$.class,\n"
+ " $output$.getDefaultInstance()));\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+}
+
+void ImmutableServiceGenerator::GenerateBlockingStub(io::Printer* printer) {
+ printer->Print(
+ "public static BlockingInterface newBlockingStub(\n"
+ " com.google.protobuf.BlockingRpcChannel channel) {\n"
+ " return new BlockingStub(channel);\n"
+ "}\n"
+ "\n");
+
+ printer->Print(
+ "public interface BlockingInterface {");
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ GenerateBlockingMethodSignature(printer, method);
+ printer->Print(";\n");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+
+ printer->Print(
+ "private static final class BlockingStub implements BlockingInterface {\n");
+ printer->Indent();
+
+ printer->Print(
+ "private BlockingStub(com.google.protobuf.BlockingRpcChannel channel) {\n"
+ " this.channel = channel;\n"
+ "}\n"
+ "\n"
+ "private final com.google.protobuf.BlockingRpcChannel channel;\n");
+
+ for (int i = 0; i < descriptor_->method_count(); i++) {
+ const MethodDescriptor* method = descriptor_->method(i);
+ GenerateBlockingMethodSignature(printer, method);
+ printer->Print(" {\n");
+ printer->Indent();
+
+ map<string, string> vars;
+ vars["index"] = SimpleItoa(i);
+ vars["output"] = name_resolver_->GetImmutableClassName(
+ method->output_type());
+ printer->Print(vars,
+ "return ($output$) channel.callBlockingMethod(\n"
+ " getDescriptor().getMethods().get($index$),\n"
+ " controller,\n"
+ " request,\n"
+ " $output$.getDefaultInstance());\n");
+
+ printer->Outdent();
+ printer->Print(
+ "}\n"
+ "\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void ImmutableServiceGenerator::GenerateMethodSignature(io::Printer* printer,
+ const MethodDescriptor* method,
+ IsAbstract is_abstract) {
+ map<string, string> vars;
+ vars["name"] = UnderscoresToCamelCase(method);
+ vars["input"] = name_resolver_->GetImmutableClassName(method->input_type());
+ vars["output"] = name_resolver_->GetImmutableClassName(method->output_type());
+ vars["abstract"] = (is_abstract == IS_ABSTRACT) ? "abstract" : "";
+ printer->Print(vars,
+ "public $abstract$ void $name$(\n"
+ " com.google.protobuf.RpcController controller,\n"
+ " $input$ request,\n"
+ " com.google.protobuf.RpcCallback<$output$> done)");
+}
+
+void ImmutableServiceGenerator::GenerateBlockingMethodSignature(
+ io::Printer* printer,
+ const MethodDescriptor* method) {
+ map<string, string> vars;
+ vars["method"] = UnderscoresToCamelCase(method);
+ vars["input"] = name_resolver_->GetImmutableClassName(method->input_type());
+ vars["output"] = name_resolver_->GetImmutableClassName(method->output_type());
+ printer->Print(vars,
+ "\n"
+ "public $output$ $method$(\n"
+ " com.google.protobuf.RpcController controller,\n"
+ " $input$ request)\n"
+ " throws com.google.protobuf.ServiceException");
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.h
new file mode 100644
index 0000000000..5fc9e2f66c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_service.h
@@ -0,0 +1,135 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_SERVICE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_SERVICE_H__
+
+#include <map>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ServiceGenerator {
+ public:
+ explicit ServiceGenerator(const ServiceDescriptor* descriptor);
+ virtual ~ServiceGenerator();
+
+ virtual void Generate(io::Printer* printer) = 0;
+
+ enum RequestOrResponse { REQUEST, RESPONSE };
+ enum IsAbstract { IS_ABSTRACT, IS_CONCRETE };
+
+ protected:
+ const ServiceDescriptor* descriptor_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ServiceGenerator);
+};
+
+class ImmutableServiceGenerator : public ServiceGenerator {
+ public:
+ ImmutableServiceGenerator(const ServiceDescriptor* descriptor,
+ Context* context);
+ virtual ~ImmutableServiceGenerator();
+
+ virtual void Generate(io::Printer* printer);
+
+ private:
+
+ // Generate the getDescriptorForType() method.
+ void GenerateGetDescriptorForType(io::Printer* printer);
+
+ // Generate a Java interface for the service.
+ void GenerateInterface(io::Printer* printer);
+
+ // Generate newReflectiveService() method.
+ void GenerateNewReflectiveServiceMethod(io::Printer* printer);
+
+ // Generate newReflectiveBlockingService() method.
+ void GenerateNewReflectiveBlockingServiceMethod(io::Printer* printer);
+
+ // Generate abstract method declarations for all methods.
+ void GenerateAbstractMethods(io::Printer* printer);
+
+ // Generate the implementation of Service.callMethod().
+ void GenerateCallMethod(io::Printer* printer);
+
+ // Generate the implementation of BlockingService.callBlockingMethod().
+ void GenerateCallBlockingMethod(io::Printer* printer);
+
+ // Generate the implementations of Service.get{Request,Response}Prototype().
+ void GenerateGetPrototype(RequestOrResponse which, io::Printer* printer);
+
+ // Generate a stub implementation of the service.
+ void GenerateStub(io::Printer* printer);
+
+ // Generate a method signature, possibly abstract, without body or trailing
+ // semicolon.
+ void GenerateMethodSignature(io::Printer* printer,
+ const MethodDescriptor* method,
+ IsAbstract is_abstract);
+
+ // Generate a blocking stub interface and implementation of the service.
+ void GenerateBlockingStub(io::Printer* printer);
+
+ // Generate the method signature for one method of a blocking stub.
+ void GenerateBlockingMethodSignature(io::Printer* printer,
+ const MethodDescriptor* method);
+
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableServiceGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+#endif // NET_PROTO2_COMPILER_JAVA_SERVICE_H__
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.cc
new file mode 100644
index 0000000000..5289372117
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.cc
@@ -0,0 +1,222 @@
+// 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: xiaofeng@google.com (Feng Xiao)
+
+#include <google/protobuf/compiler/java/java_shared_code_generator.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+SharedCodeGenerator::SharedCodeGenerator(const FileDescriptor* file,
+ const Options& options)
+ : name_resolver_(new ClassNameResolver), file_(file), options_(options) {}
+
+SharedCodeGenerator::~SharedCodeGenerator() {
+}
+
+void SharedCodeGenerator::Generate(GeneratorContext* context,
+ vector<string>* file_list,
+ vector<string>* annotation_file_list) {
+ string java_package = FileJavaPackage(file_);
+ string package_dir = JavaPackageToDir(java_package);
+
+ if (HasDescriptorMethods(file_, options_.enforce_lite)) {
+ // Generate descriptors.
+ string classname = name_resolver_->GetDescriptorClassName(file_);
+ string filename = package_dir + classname + ".java";
+ file_list->push_back(filename);
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(filename));
+ GeneratedCodeInfo annotations;
+ io::AnnotationProtoCollector<GeneratedCodeInfo> annotation_collector(
+ &annotations);
+ google::protobuf::scoped_ptr<io::Printer> printer(
+ new io::Printer(output.get(), '$',
+ options_.annotate_code ? &annotation_collector : NULL));
+ string info_relative_path = classname + ".java.pb.meta";
+ string info_full_path = filename + ".pb.meta";
+ printer->Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "// source: $filename$\n"
+ "\n",
+ "filename", file_->name());
+ if (!java_package.empty()) {
+ printer->Print(
+ "package $package$;\n"
+ "\n",
+ "package", java_package);
+ }
+ PrintGeneratedAnnotation(printer.get(), '$',
+ options_.annotate_code ? info_relative_path : "");
+ printer->Print(
+ "public final class $classname$ {\n"
+ " public static com.google.protobuf.Descriptors.FileDescriptor\n"
+ " descriptor;\n"
+ " static {\n",
+ "classname", classname);
+ printer->Annotate("classname", file_->name());
+ printer->Indent();
+ printer->Indent();
+ GenerateDescriptors(printer.get());
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n"
+ "}\n");
+
+ if (options_.annotate_code) {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> info_output(
+ context->Open(info_full_path));
+ annotations.SerializeToZeroCopyStream(info_output.get());
+ annotation_file_list->push_back(info_full_path);
+ }
+
+ printer.reset();
+ output.reset();
+ }
+}
+
+
+void SharedCodeGenerator::GenerateDescriptors(io::Printer* printer) {
+ // Embed the descriptor. We simply serialize the entire FileDescriptorProto
+ // and embed it as a string literal, which is parsed and built into real
+ // descriptors at initialization time. We unfortunately have to put it in
+ // a string literal, not a byte array, because apparently using a literal
+ // byte array causes the Java compiler to generate *instructions* to
+ // initialize each and every byte of the array, e.g. as if you typed:
+ // b[0] = 123; b[1] = 456; b[2] = 789;
+ // This makes huge bytecode files and can easily hit the compiler's internal
+ // code size limits (error "code to large"). String literals are apparently
+ // embedded raw, which is what we want.
+ FileDescriptorProto file_proto;
+ file_->CopyTo(&file_proto);
+
+
+ string file_data;
+ file_proto.SerializeToString(&file_data);
+
+ printer->Print(
+ "java.lang.String[] descriptorData = {\n");
+ printer->Indent();
+
+ // Only write 40 bytes per line.
+ static const int kBytesPerLine = 40;
+ for (int i = 0; i < file_data.size(); i += kBytesPerLine) {
+ if (i > 0) {
+ // Every 400 lines, start a new string literal, in order to avoid the
+ // 64k length limit.
+ if (i % 400 == 0) {
+ printer->Print(",\n");
+ } else {
+ printer->Print(" +\n");
+ }
+ }
+ printer->Print("\"$data$\"",
+ "data", CEscape(file_data.substr(i, kBytesPerLine)));
+ }
+
+ printer->Outdent();
+ printer->Print("\n};\n");
+
+ // -----------------------------------------------------------------
+ // Create the InternalDescriptorAssigner.
+
+ printer->Print(
+ "com.google.protobuf.Descriptors.FileDescriptor."
+ "InternalDescriptorAssigner assigner =\n"
+ " new com.google.protobuf.Descriptors.FileDescriptor."
+ " InternalDescriptorAssigner() {\n"
+ " public com.google.protobuf.ExtensionRegistry assignDescriptors(\n"
+ " com.google.protobuf.Descriptors.FileDescriptor root) {\n"
+ " descriptor = root;\n"
+ // Custom options will be handled when immutable messages' outer class is
+ // loaded. Here we just return null and let custom options be unknown
+ // fields.
+ " return null;\n"
+ " }\n"
+ " };\n");
+
+ // -----------------------------------------------------------------
+ // Find out all dependencies.
+ vector<pair<string, string> > dependencies;
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ if (ShouldIncludeDependency(file_->dependency(i))) {
+ string filename = file_->dependency(i)->name();
+ string classname = FileJavaPackage(file_->dependency(i)) + "." +
+ name_resolver_->GetDescriptorClassName(
+ file_->dependency(i));
+ dependencies.push_back(std::make_pair(filename, classname));
+ }
+ }
+
+ // -----------------------------------------------------------------
+ // Invoke internalBuildGeneratedFileFrom() to build the file.
+ printer->Print(
+ "com.google.protobuf.Descriptors.FileDescriptor\n"
+ " .internalBuildGeneratedFileFrom(descriptorData,\n");
+ printer->Print(
+ " new com.google.protobuf.Descriptors.FileDescriptor[] {\n");
+
+ for (int i = 0; i < dependencies.size(); i++) {
+ const string& dependency = dependencies[i].second;
+ printer->Print(
+ " $dependency$.getDescriptor(),\n",
+ "dependency", dependency);
+ }
+
+ printer->Print(
+ " }, assigner);\n");
+}
+
+bool SharedCodeGenerator::ShouldIncludeDependency(
+ const FileDescriptor* descriptor) {
+ return true;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.h
new file mode 100644
index 0000000000..7e1e1f17cc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_shared_code_generator.h
@@ -0,0 +1,96 @@
+// 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: xiaofeng@google.com (Feng Xiao)
+//
+// Generators that generate shared code between immutable API and mutable API.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_SHARED_CODE_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_SHARED_CODE_GENERATOR_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_options.h>
+
+namespace google {
+namespace protobuf {
+ class FileDescriptor; // descriptor.h
+ namespace compiler {
+ class GeneratorContext; // code_generator.h
+ namespace java {
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+// A generator that generates code that are shared between immutable API
+// and mutable API. Currently only descriptors are shared.
+class SharedCodeGenerator {
+ public:
+ SharedCodeGenerator(const FileDescriptor* file, const Options& options);
+ ~SharedCodeGenerator();
+
+ void Generate(GeneratorContext* generator_context, vector<string>* file_list,
+ vector<string>* annotation_file_list);
+
+ void GenerateDescriptors(io::Printer* printer);
+
+ private:
+ // Returns whether the dependency should be included in the output file.
+ // Always returns true for opensource, but used internally at Google to help
+ // improve compatibility with version 1 of protocol buffers.
+ bool ShouldIncludeDependency(const FileDescriptor* descriptor);
+
+ google::protobuf::scoped_ptr<ClassNameResolver> name_resolver_;
+ const FileDescriptor* file_;
+ const Options options_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(SharedCodeGenerator);
+};
+
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_SHARED_CODE_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.cc
new file mode 100644
index 0000000000..ff1865b178
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.cc
@@ -0,0 +1,1005 @@
+// 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)
+// Author: jonp@google.com (Jon Perlow)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/compiler/java/java_string_field.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+void SetPrimitiveVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ (*variables)["empty_list"] = "com.google.protobuf.LazyStringArrayList.EMPTY";
+
+ (*variables)["default"] = ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["default_init"] =
+ "= " + ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["capitalized_type"] = "String";
+ (*variables)["tag"] = SimpleItoa(WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ WireFormat::TagSize(descriptor->number(), GetType(descriptor)));
+ (*variables)["null_check"] =
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n";
+ (*variables)["writeString"] =
+ "com.google.protobuf.GeneratedMessage" + GeneratedCodeVersionSuffix() +
+ ".writeString";
+ (*variables)["computeStringSize"] =
+ "com.google.protobuf.GeneratedMessage" + GeneratedCodeVersionSuffix() +
+ ".computeStringSize";
+
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+ (*variables)["on_changed"] = "onChanged();";
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+ (*variables)["get_has_field_bit_builder"] = GenerateGetBit(builderBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["set_has_field_bit_builder"] =
+ GenerateSetBit(builderBitIndex) + ";";
+ (*variables)["clear_has_field_bit_builder"] =
+ GenerateClearBit(builderBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["set_has_field_bit_builder"] = "";
+ (*variables)["clear_has_field_bit_builder"] = "";
+
+ (*variables)["is_field_present_message"] =
+ "!get" + (*variables)["capitalized_name"] + "Bytes().isEmpty()";
+ }
+
+ // For repeated builders, one bit is used for whether the array is immutable.
+ (*variables)["get_mutable_bit_builder"] = GenerateGetBit(builderBitIndex);
+ (*variables)["set_mutable_bit_builder"] = GenerateSetBit(builderBitIndex);
+ (*variables)["clear_mutable_bit_builder"] = GenerateClearBit(builderBitIndex);
+
+ // For repeated fields, one bit is used for whether the array is immutable
+ // in the parsing constructor.
+ (*variables)["get_mutable_bit_parser"] =
+ GenerateGetBitMutableLocal(builderBitIndex);
+ (*variables)["set_mutable_bit_parser"] =
+ GenerateSetBitMutableLocal(builderBitIndex);
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutableStringFieldGenerator::
+ImmutableStringFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutableStringFieldGenerator::~ImmutableStringFieldGenerator() {}
+
+int ImmutableStringFieldGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutableStringFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+// A note about how strings are handled. This code used to just store a String
+// in the Message. This had two issues:
+//
+// 1. It wouldn't roundtrip byte arrays that were not vaid UTF-8 encoded
+// strings, but rather fields that were raw bytes incorrectly marked
+// as strings in the proto file. This is common because in the proto1
+// syntax, string was the way to indicate bytes and C++ engineers can
+// easily make this mistake without affecting the C++ API. By converting to
+// strings immediately, some java code might corrupt these byte arrays as
+// it passes through a java server even if the field was never accessed by
+// application code.
+//
+// 2. There's a performance hit to converting between bytes and strings and
+// it many cases, the field is never even read by the application code. This
+// avoids unnecessary conversions in the common use cases.
+//
+// So now, the field for String is maintained as an Object reference which can
+// either store a String or a ByteString. The code uses an instanceof check
+// to see which one it has and converts to the other one if needed. It remembers
+// the last value requested (in a thread safe manner) as this is most likely
+// the one needed next. The thread safety is such that if two threads both
+// convert the field because the changes made by each thread were not visible to
+// the other, they may cause a conversion to happen more times than would
+// otherwise be necessary. This was deemed better than adding synchronization
+// overhead. It will not cause any corruption issues or affect the behavior of
+// the API. The instanceof check is also highly optimized in the JVM and we
+// decided it was better to reduce the memory overhead by not having two
+// separate fields but rather use dynamic type checking.
+//
+// For single fields, the logic for this is done inside the generated code. For
+// repeated fields, the logic is done in LazyStringArrayList and
+// UnmodifiableLazyStringList.
+void ImmutableStringFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.lang.String get$capitalized_name$();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes();\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private volatile java.lang.Object $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " java.lang.Object ref = $name$_;\n"
+ " if (ref instanceof java.lang.String) {\n"
+ " return (java.lang.String) ref;\n"
+ " } else {\n"
+ " com.google.protobuf.ByteString bs = \n"
+ " (com.google.protobuf.ByteString) ref;\n"
+ " java.lang.String s = bs.toStringUtf8();\n");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " $name$_ = s;\n");
+ } else {
+ printer->Print(variables_,
+ " if (bs.isValidUtf8()) {\n"
+ " $name$_ = s;\n"
+ " }\n");
+ }
+ printer->Print(variables_,
+ " return s;\n"
+ " }\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " java.lang.Object ref = $name$_;\n"
+ " if (ref instanceof java.lang.String) {\n"
+ " com.google.protobuf.ByteString b = \n"
+ " com.google.protobuf.ByteString.copyFromUtf8(\n"
+ " (java.lang.String) ref);\n"
+ " $name$_ = b;\n"
+ " return b;\n"
+ " } else {\n"
+ " return (com.google.protobuf.ByteString) ref;\n"
+ " }\n"
+ "}\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private java.lang.Object $name$_ $default_init$;\n");
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_builder$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " java.lang.Object ref = $name$_;\n"
+ " if (!(ref instanceof java.lang.String)) {\n"
+ " com.google.protobuf.ByteString bs =\n"
+ " (com.google.protobuf.ByteString) ref;\n"
+ " java.lang.String s = bs.toStringUtf8();\n");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " $name$_ = s;\n");
+ } else {
+ printer->Print(variables_,
+ " if (bs.isValidUtf8()) {\n"
+ " $name$_ = s;\n"
+ " }\n");
+ }
+ printer->Print(variables_,
+ " return s;\n"
+ " } else {\n"
+ " return (java.lang.String) ref;\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " java.lang.Object ref = $name$_;\n"
+ " if (ref instanceof String) {\n"
+ " com.google.protobuf.ByteString b = \n"
+ " com.google.protobuf.ByteString.copyFromUtf8(\n"
+ " (java.lang.String) ref);\n"
+ " $name$_ = b;\n"
+ " return b;\n"
+ " } else {\n"
+ " return (com.google.protobuf.ByteString) ref;\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ "$null_check$"
+ " $set_has_field_bit_builder$\n"
+ " $name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " $clear_has_field_bit_builder$\n");
+ // The default value is not a simple literal so we want to avoid executing
+ // it multiple times. Instead, get the default out of the default instance.
+ printer->Print(variables_,
+ " $name$_ = getDefaultInstance().get$capitalized_name$();\n");
+ printer->Print(variables_,
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ "$null_check$");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " checkByteStringIsUtf8(value);\n");
+ }
+ printer->Print(variables_,
+ " $set_has_field_bit_builder$\n"
+ " $name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void ImmutableStringFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = $default$;\n"
+ "$clear_has_field_bit_builder$\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ // Allow a slight breach of abstraction here in order to avoid forcing
+ // all string fields to Strings when copying fields from a Message.
+ printer->Print(variables_,
+ "if (other.has$capitalized_name$()) {\n"
+ " $set_has_field_bit_builder$\n"
+ " $name$_ = other.$name$_;\n"
+ " $on_changed$\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "if (!other.get$capitalized_name$().isEmpty()) {\n"
+ " $name$_ = other.$name$_;\n"
+ " $on_changed$\n"
+ "}\n");
+ }
+}
+
+void ImmutableStringFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "if ($get_has_field_bit_from_local$) {\n"
+ " $set_has_field_bit_to_local$;\n"
+ "}\n");
+ }
+ printer->Print(variables_,
+ "result.$name$_ = $name$_;\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ "java.lang.String s = input.readStringRequireUtf8();\n"
+ "$set_has_field_bit_message$\n"
+ "$name$_ = s;\n");
+ } else {
+ printer->Print(variables_,
+ "com.google.protobuf.ByteString bs = input.readBytes();\n"
+ "$set_has_field_bit_message$\n"
+ "$name$_ = bs;\n");
+ }
+}
+
+void ImmutableStringFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for strings.
+}
+
+void ImmutableStringFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " $writeString$(output, $number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += $computeStringSize$($number$, $name$_);\n"
+ "}\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+}
+
+void ImmutableStringFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n");
+ printer->Print(variables_,
+ "hash = (53 * hash) + get$capitalized_name$().hashCode();\n");
+}
+
+string ImmutableStringFieldGenerator::GetBoxedType() const {
+ return "java.lang.String";
+}
+
+// ===================================================================
+
+ImmutableStringOneofFieldGenerator::
+ImmutableStringOneofFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableStringFieldGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutableStringOneofFieldGenerator::
+~ImmutableStringOneofFieldGenerator() {}
+
+void ImmutableStringOneofFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " java.lang.Object ref $default_init$;\n"
+ " if ($has_oneof_case_message$) {\n"
+ " ref = $oneof_name$_;\n"
+ " }\n"
+ " if (ref instanceof java.lang.String) {\n"
+ " return (java.lang.String) ref;\n"
+ " } else {\n"
+ " com.google.protobuf.ByteString bs = \n"
+ " (com.google.protobuf.ByteString) ref;\n"
+ " java.lang.String s = bs.toStringUtf8();\n");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " if ($has_oneof_case_message$) {\n"
+ " $oneof_name$_ = s;\n"
+ " }\n");
+ } else {
+ printer->Print(variables_,
+ " if (bs.isValidUtf8() && ($has_oneof_case_message$)) {\n"
+ " $oneof_name$_ = s;\n"
+ " }\n");
+ }
+ printer->Print(variables_,
+ " return s;\n"
+ " }\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " java.lang.Object ref $default_init$;\n"
+ " if ($has_oneof_case_message$) {\n"
+ " ref = $oneof_name$_;\n"
+ " }\n"
+ " if (ref instanceof java.lang.String) {\n"
+ " com.google.protobuf.ByteString b = \n"
+ " com.google.protobuf.ByteString.copyFromUtf8(\n"
+ " (java.lang.String) ref);\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $oneof_name$_ = b;\n"
+ " }\n"
+ " return b;\n"
+ " } else {\n"
+ " return (com.google.protobuf.ByteString) ref;\n"
+ " }\n"
+ "}\n");
+}
+
+void ImmutableStringOneofFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " java.lang.Object ref $default_init$;\n"
+ " if ($has_oneof_case_message$) {\n"
+ " ref = $oneof_name$_;\n"
+ " }\n"
+ " if (!(ref instanceof java.lang.String)) {\n"
+ " com.google.protobuf.ByteString bs =\n"
+ " (com.google.protobuf.ByteString) ref;\n"
+ " java.lang.String s = bs.toStringUtf8();\n"
+ " if ($has_oneof_case_message$) {\n");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " $oneof_name$_ = s;\n");
+ } else {
+ printer->Print(variables_,
+ " if (bs.isValidUtf8()) {\n"
+ " $oneof_name$_ = s;\n"
+ " }\n");
+ }
+ printer->Print(variables_,
+ " }\n"
+ " return s;\n"
+ " } else {\n"
+ " return (java.lang.String) ref;\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " java.lang.Object ref $default_init$;\n"
+ " if ($has_oneof_case_message$) {\n"
+ " ref = $oneof_name$_;\n"
+ " }\n"
+ " if (ref instanceof String) {\n"
+ " com.google.protobuf.ByteString b = \n"
+ " com.google.protobuf.ByteString.copyFromUtf8(\n"
+ " (java.lang.String) ref);\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $oneof_name$_ = b;\n"
+ " }\n"
+ " return b;\n"
+ " } else {\n"
+ " return (com.google.protobuf.ByteString) ref;\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ "$null_check$"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " $on_changed$\n"
+ " }\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ "$null_check$");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " checkByteStringIsUtf8(value);\n");
+ }
+ printer->Print(variables_,
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableStringOneofFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // Allow a slight breach of abstraction here in order to avoid forcing
+ // all string fields to Strings when copying fields from a Message.
+ printer->Print(variables_,
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = other.$oneof_name$_;\n"
+ "$on_changed$\n");
+}
+
+void ImmutableStringOneofFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " result.$oneof_name$_ = $oneof_name$_;\n"
+ "}\n");
+}
+
+void ImmutableStringOneofFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ "java.lang.String s = input.readStringRequireUtf8();\n"
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = s;\n");
+ } else {
+ printer->Print(variables_,
+ "com.google.protobuf.ByteString bs = input.readBytes();\n"
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = bs;\n");
+ }
+}
+
+void ImmutableStringOneofFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " $writeString$(output, $number$, $oneof_name$_);\n"
+ "}\n");
+}
+
+void ImmutableStringOneofFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += $computeStringSize$($number$, $oneof_name$_);\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutableStringFieldGenerator::
+RepeatedImmutableStringFieldGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutableStringFieldGenerator::
+~RepeatedImmutableStringFieldGenerator() {}
+
+int RepeatedImmutableStringFieldGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutableStringFieldGenerator::GetNumBitsForBuilder() const {
+ return 1;
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ // NOTE: the same method in the implementation class actually returns
+ // com.google.protobuf.ProtocolStringList (a subclass of List). It's
+ // changed between protobuf 2.5.0 release and protobuf 2.6.1 release.
+ // To retain binary compatibility with both 2.5.0 and 2.6.1 generated
+ // code, we make this interface method return List so both methods
+ // with different return types exist in the compiled byte code.
+ "$deprecation$java.util.List<java.lang.String>\n"
+ " get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.lang.String get$capitalized_name$(int index);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes(int index);\n");
+}
+
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private com.google.protobuf.LazyStringList $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ProtocolStringList\n"
+ " get$capitalized_name$List() {\n"
+ " return $name$_;\n" // note: unmodifiable list
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes(int index) {\n"
+ " return $name$_.getByteString(index);\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ // One field is the list and the bit field keeps track of whether the
+ // list is immutable. If it's immutable, the invariant is that it must
+ // either an instance of Collections.emptyList() or it's an ArrayList
+ // wrapped in a Collections.unmodifiableList() wrapper and nobody else has
+ // a refererence to the underlying ArrayList. This invariant allows us to
+ // share instances of lists between protocol buffers avoiding expensive
+ // memory allocations. Note, immutable is a strong guarantee here -- not
+ // just that the list cannot be modified via the reference but that the
+ // list can never be modified.
+ printer->Print(variables_,
+ "private com.google.protobuf.LazyStringList $name$_ = $empty_list$;\n");
+
+ printer->Print(variables_,
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$get_mutable_bit_builder$) {\n"
+ " $name$_ = new com.google.protobuf.LazyStringArrayList($name$_);\n"
+ " $set_mutable_bit_builder$;\n"
+ " }\n"
+ "}\n");
+
+ // Note: We return an unmodifiable list because otherwise the caller
+ // could hold on to the returned list and modify it after the message
+ // has been built, thus mutating the message which is supposed to be
+ // immutable.
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ProtocolStringList\n"
+ " get$capitalized_name$List() {\n"
+ " return $name$_.getUnmodifiableView();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes(int index) {\n"
+ " return $name$_.getByteString(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, java.lang.String value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, value);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<java.lang.String> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " com.google.protobuf.AbstractMessageLite.Builder.addAll(\n"
+ " values, $name$_);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " $name$_ = $empty_list$;\n"
+ " $clear_mutable_bit_builder$;\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ "$null_check$");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " checkByteStringIsUtf8(value);\n");
+ }
+ printer->Print(variables_,
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value);\n"
+ " $on_changed$\n"
+ " return this;\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for primitives
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $empty_list$;\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateBuilderClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = $empty_list$;\n"
+ "$clear_mutable_bit_builder$;\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // The code below does two optimizations:
+ // 1. If the other list is empty, there's nothing to do. This ensures we
+ // don't allocate a new array if we already have an immutable one.
+ // 2. If the other list is non-empty and our current list is empty, we can
+ // reuse the other list which is guaranteed to be immutable.
+ printer->Print(variables_,
+ "if (!other.$name$_.isEmpty()) {\n"
+ " if ($name$_.isEmpty()) {\n"
+ " $name$_ = other.$name$_;\n"
+ " $clear_mutable_bit_builder$;\n"
+ " } else {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.addAll(other.$name$_);\n"
+ " }\n"
+ " $on_changed$\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateBuildingCode(io::Printer* printer) const {
+ // The code below ensures that the result has an immutable list. If our
+ // list is immutable, we can just reuse it. If not, we make it immutable.
+
+ printer->Print(variables_,
+ "if ($get_mutable_bit_builder$) {\n"
+ " $name$_ = $name$_.getUnmodifiableView();\n"
+ " $clear_mutable_bit_builder$;\n"
+ "}\n"
+ "result.$name$_ = $name$_;\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ "java.lang.String s = input.readStringRequireUtf8();\n");
+ } else {
+ printer->Print(variables_,
+ "com.google.protobuf.ByteString bs = input.readBytes();\n");
+ }
+ printer->Print(variables_,
+ "if (!$get_mutable_bit_parser$) {\n"
+ " $name$_ = new com.google.protobuf.LazyStringArrayList();\n"
+ " $set_mutable_bit_parser$;\n"
+ "}\n");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ "$name$_.add(s);\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_.add(bs);\n");
+ }
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_mutable_bit_parser$) {\n"
+ " $name$_ = $name$_.getUnmodifiableView();\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " $writeString$(output, $number$, $name$_.getRaw(i));\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "{\n"
+ " int dataSize = 0;\n");
+ printer->Indent();
+
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " dataSize += computeStringSizeNoTag($name$_.getRaw(i));\n"
+ "}\n");
+
+ printer->Print(
+ "size += dataSize;\n");
+
+ printer->Print(variables_,
+ "size += $tag_size$ * get$capitalized_name$List().size();\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$List()\n"
+ " .equals(other.get$capitalized_name$List());\n");
+}
+
+void RepeatedImmutableStringFieldGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + get$capitalized_name$List().hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutableStringFieldGenerator::GetBoxedType() const {
+ return "String";
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.h
new file mode 100644
index 0000000000..a3b57351dc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field.h
@@ -0,0 +1,159 @@
+// 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)
+// Author: jonp@google.com (Jon Perlow)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_STRING_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_STRING_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableStringFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit ImmutableStringFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableStringFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableStringFieldGenerator);
+};
+
+class ImmutableStringOneofFieldGenerator
+ : public ImmutableStringFieldGenerator {
+ public:
+ ImmutableStringOneofFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableStringOneofFieldGenerator();
+
+ private:
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableStringOneofFieldGenerator);
+};
+
+class RepeatedImmutableStringFieldGenerator : public ImmutableFieldGenerator {
+ public:
+ explicit RepeatedImmutableStringFieldGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableStringFieldGenerator();
+
+ // implements ImmutableFieldGenerator ---------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateBuilderClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateBuildingCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableStringFieldGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_STRING_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.cc
new file mode 100644
index 0000000000..0b92c02185
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.cc
@@ -0,0 +1,872 @@
+// 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)
+// Author: jonp@google.com (Jon Perlow)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/java/java_context.h>
+#include <google/protobuf/compiler/java/java_doc_comment.h>
+#include <google/protobuf/compiler/java/java_helpers.h>
+#include <google/protobuf/compiler/java/java_name_resolver.h>
+#include <google/protobuf/compiler/java/java_string_field_lite.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+void SetPrimitiveVariables(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ const FieldGeneratorInfo* info,
+ ClassNameResolver* name_resolver,
+ map<string, string>* variables) {
+ SetCommonFieldVariables(descriptor, info, variables);
+
+ (*variables)["empty_list"] =
+ "com.google.protobuf.GeneratedMessageLite.emptyProtobufList()";
+
+ (*variables)["default"] = ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["default_init"] =
+ "= " + ImmutableDefaultValue(descriptor, name_resolver);
+ (*variables)["capitalized_type"] = "String";
+ (*variables)["tag"] = SimpleItoa(WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ WireFormat::TagSize(descriptor->number(), GetType(descriptor)));
+ (*variables)["null_check"] =
+ " if (value == null) {\n"
+ " throw new NullPointerException();\n"
+ " }\n";
+
+ // TODO(birdo): Add @deprecated javadoc when generating javadoc is supported
+ // by the proto compiler
+ (*variables)["deprecation"] = descriptor->options().deprecated()
+ ? "@java.lang.Deprecated " : "";
+
+ if (SupportFieldPresence(descriptor->file())) {
+ // For singular messages and builders, one bit is used for the hasField bit.
+ (*variables)["get_has_field_bit_message"] = GenerateGetBit(messageBitIndex);
+
+ // Note that these have a trailing ";".
+ (*variables)["set_has_field_bit_message"] =
+ GenerateSetBit(messageBitIndex) + ";";
+ (*variables)["clear_has_field_bit_message"] =
+ GenerateClearBit(messageBitIndex) + ";";
+
+ (*variables)["is_field_present_message"] = GenerateGetBit(messageBitIndex);
+ } else {
+ (*variables)["set_has_field_bit_message"] = "";
+ (*variables)["clear_has_field_bit_message"] = "";
+
+ (*variables)["is_field_present_message"] =
+ "!" + (*variables)["name"] + "_.isEmpty()";
+ }
+
+ // For repeated builders, the underlying list tracks mutability state.
+ (*variables)["is_mutable"] = (*variables)["name"] + "_.isModifiable()";
+
+ (*variables)["get_has_field_bit_from_local"] =
+ GenerateGetBitFromLocal(builderBitIndex);
+ (*variables)["set_has_field_bit_to_local"] =
+ GenerateSetBitToLocal(messageBitIndex);
+}
+
+} // namespace
+
+// ===================================================================
+
+ImmutableStringFieldLiteGenerator::
+ImmutableStringFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+ImmutableStringFieldLiteGenerator::~ImmutableStringFieldLiteGenerator() {}
+
+int ImmutableStringFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 1;
+}
+
+int ImmutableStringFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+// A note about how strings are handled. In the SPEED and CODE_SIZE runtimes,
+// strings are not stored as java.lang.String in the Message because of two
+// issues:
+//
+// 1. It wouldn't roundtrip byte arrays that were not vaid UTF-8 encoded
+// strings, but rather fields that were raw bytes incorrectly marked
+// as strings in the proto file. This is common because in the proto1
+// syntax, string was the way to indicate bytes and C++ engineers can
+// easily make this mistake without affecting the C++ API. By converting to
+// strings immediately, some java code might corrupt these byte arrays as
+// it passes through a java server even if the field was never accessed by
+// application code.
+//
+// 2. There's a performance hit to converting between bytes and strings and
+// it many cases, the field is never even read by the application code. This
+// avoids unnecessary conversions in the common use cases.
+//
+// In the LITE_RUNTIME, we store strings as java.lang.String because we assume
+// that the users of this runtime are not subject to proto1 constraints and are
+// running code on devices that are user facing. That is, the developers are
+// properly incentivized to only fetch the data they need to read and wish to
+// reduce the number of allocations incurred when running on a user's device.
+
+// TODO(dweis): Consider dropping all of the *Bytes() methods. They really
+// shouldn't be necessary or used on devices.
+void ImmutableStringFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$boolean has$capitalized_name$();\n");
+ }
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.lang.String get$capitalized_name$();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes();\n");
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private java.lang.String $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $get_has_field_bit_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " return $name$_;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " return com.google.protobuf.ByteString.copyFromUtf8($name$_);\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ "$null_check$"
+ " $set_has_field_bit_message$\n"
+ " $name$_ = value;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $clear_has_field_bit_message$\n"
+ // The default value is not a simple literal so we want to avoid executing
+ // it multiple times. Instead, get the default out of the default instance.
+ " $name$_ = getDefaultInstance().get$capitalized_name$();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ "$null_check$");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " checkByteStringIsUtf8(value);\n");
+ }
+ printer->Print(variables_,
+ " $set_has_field_bit_message$\n"
+ " $name$_ = value.toStringUtf8();\n"
+ "}\n");
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " return instance.get$capitalized_name$Bytes();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$Bytes(value);\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for strings
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $default$;\n");
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ printer->Print(variables_,
+ "$name$_ = visitor.visitString(\n"
+ " has$capitalized_name$(), $name$_,\n"
+ " other.has$capitalized_name$(), other.$name$_);\n");
+ } else {
+ printer->Print(variables_,
+ "$name$_ = visitor.visitString(!$name$_.isEmpty(), $name$_,\n"
+ " !other.$name$_.isEmpty(), other.$name$_);\n");
+ }
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ // noop for scalars
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ "String s = input.readStringRequireUtf8();\n"
+ "$set_has_field_bit_message$\n"
+ "$name$_ = s;\n");
+ } else {
+ // Lite runtime should attempt to reduce allocations by attempting to
+ // construct the string directly from the input stream buffer. This avoids
+ // spurious intermediary ByteString allocations, cutting overall allocations
+ // in half.
+ printer->Print(variables_,
+ "String s = input.readString();\n"
+ "$set_has_field_bit_message$\n"
+ "$name$_ = s;\n");
+ }
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ // noop for strings
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ // Lite runtime should reduce allocations by serializing the string directly.
+ // This avoids spurious intermediary ByteString allocations, cutting overall
+ // allocations in half.
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " output.writeString($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ // Lite runtime should reduce allocations by computing on the string directly.
+ // This avoids spurious intermediary ByteString allocations, cutting overall
+ // allocations in half.
+ printer->Print(variables_,
+ "if ($is_field_present_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeStringSize($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$()\n"
+ " .equals(other.get$capitalized_name$());\n");
+}
+
+void ImmutableStringFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "hash = (37 * hash) + $constant_name$;\n");
+ printer->Print(variables_,
+ "hash = (53 * hash) + get$capitalized_name$().hashCode();\n");
+}
+
+string ImmutableStringFieldLiteGenerator::GetBoxedType() const {
+ return "java.lang.String";
+}
+
+// ===================================================================
+
+ImmutableStringOneofFieldLiteGenerator::
+ImmutableStringOneofFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : ImmutableStringFieldLiteGenerator(
+ descriptor, messageBitIndex, builderBitIndex, context) {
+ const OneofGeneratorInfo* info =
+ context->GetOneofGeneratorInfo(descriptor->containing_oneof());
+ SetCommonOneofVariables(descriptor, info, &variables_);
+}
+
+ImmutableStringOneofFieldLiteGenerator::
+~ImmutableStringOneofFieldLiteGenerator() {}
+
+void ImmutableStringOneofFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ PrintExtraFieldInfo(variables_, printer);
+
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case_message$;\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " java.lang.String ref $default_init$;\n"
+ " if ($has_oneof_case_message$) {\n"
+ " ref = (java.lang.String) $oneof_name$_;\n"
+ " }\n"
+ " return ref;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " java.lang.String ref $default_init$;\n"
+ " if ($has_oneof_case_message$) {\n"
+ " ref = (java.lang.String) $oneof_name$_;\n"
+ " }\n"
+ " return com.google.protobuf.ByteString.copyFromUtf8(ref);\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ "$null_check$"
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " if ($has_oneof_case_message$) {\n"
+ " $clear_oneof_case_message$;\n"
+ " $oneof_name$_ = null;\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ "$null_check$");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " checkByteStringIsUtf8(value);\n");
+ }
+ printer->Print(variables_,
+ " $set_oneof_case_message$;\n"
+ " $oneof_name$_ = value.toStringUtf8();\n"
+ "}\n");
+}
+
+void ImmutableStringOneofFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ if (SupportFieldPresence(descriptor_->file())) {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public boolean has$capitalized_name$() {\n"
+ " return instance.has$capitalized_name$();\n"
+ "}\n");
+ }
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$() {\n"
+ " return instance.get$capitalized_name$();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes() {\n"
+ " return instance.get$capitalized_name$Bytes();\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$Bytes(value);\n"
+ " return this;\n"
+ "}\n");
+}
+
+void ImmutableStringOneofFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$oneof_name$_ = visitor.visitOneofString(\n"
+ " $has_oneof_case_message$, $oneof_name$_, other.$oneof_name$_);\n");
+}
+
+void ImmutableStringOneofFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ "String s = input.readStringRequireUtf8();\n"
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = s;\n");
+ } else {
+ // Lite runtime should attempt to reduce allocations by attempting to
+ // construct the string directly from the input stream buffer. This avoids
+ // spurious intermediary ByteString allocations, cutting overall allocations
+ // in half.
+ printer->Print(variables_,
+ "String s = input.readString();\n"
+ "$set_oneof_case_message$;\n"
+ "$oneof_name$_ = s;\n");
+ }
+}
+
+void ImmutableStringOneofFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ // Lite runtime should reduce allocations by serializing the string directly.
+ // This avoids spurious intermediary ByteString allocations, cutting overall
+ // allocations in half.
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " output.writeString($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+void ImmutableStringOneofFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ // Lite runtime should reduce allocations by computing on the string directly.
+ // This avoids spurious intermediary ByteString allocations, cutting overall
+ // allocations in half.
+ printer->Print(variables_,
+ "if ($has_oneof_case_message$) {\n"
+ " size += com.google.protobuf.CodedOutputStream\n"
+ " .computeStringSize($number$, get$capitalized_name$());\n"
+ "}\n");
+}
+
+// ===================================================================
+
+RepeatedImmutableStringFieldLiteGenerator::
+RepeatedImmutableStringFieldLiteGenerator(const FieldDescriptor* descriptor,
+ int messageBitIndex,
+ int builderBitIndex,
+ Context* context)
+ : descriptor_(descriptor), messageBitIndex_(messageBitIndex),
+ builderBitIndex_(builderBitIndex), context_(context),
+ name_resolver_(context->GetNameResolver()) {
+ SetPrimitiveVariables(descriptor, messageBitIndex, builderBitIndex,
+ context->GetFieldGeneratorInfo(descriptor),
+ name_resolver_, &variables_);
+}
+
+RepeatedImmutableStringFieldLiteGenerator::
+~RepeatedImmutableStringFieldLiteGenerator() {}
+
+int RepeatedImmutableStringFieldLiteGenerator::GetNumBitsForMessage() const {
+ return 0;
+}
+
+int RepeatedImmutableStringFieldLiteGenerator::GetNumBitsForBuilder() const {
+ return 0;
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateInterfaceMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.util.List<String>\n"
+ " get$capitalized_name$List();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$int get$capitalized_name$Count();\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$java.lang.String get$capitalized_name$(int index);\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes(int index);\n");
+}
+
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateMembers(io::Printer* printer) const {
+ printer->Print(variables_,
+ "private com.google.protobuf.Internal.ProtobufList<String> $name$_;\n");
+ PrintExtraFieldInfo(variables_, printer);
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<String> get$capitalized_name$List() {\n"
+ " return $name$_;\n" // note: unmodifiable list
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return $name$_.size();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$(int index) {\n"
+ " return $name$_.get(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes(int index) {\n"
+ " return com.google.protobuf.ByteString.copyFromUtf8(\n"
+ " $name$_.get(index));\n"
+ "}\n");
+
+ printer->Print(variables_,
+ "private void ensure$capitalized_name$IsMutable() {\n"
+ " if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ " }\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void set$capitalized_name$(\n"
+ " int index, java.lang.String value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.set(index, value);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ "$null_check$"
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void addAll$capitalized_name$(\n"
+ " java.lang.Iterable<java.lang.String> values) {\n"
+ " ensure$capitalized_name$IsMutable();\n"
+ " com.google.protobuf.AbstractMessageLite.addAll(\n"
+ " values, $name$_);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void clear$capitalized_name$() {\n"
+ " $name$_ = $empty_list$;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "private void add$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ "$null_check$");
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ " checkByteStringIsUtf8(value);\n");
+ }
+ printer->Print(variables_,
+ " ensure$capitalized_name$IsMutable();\n"
+ " $name$_.add(value.toStringUtf8());\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateBuilderMembers(io::Printer* printer) const {
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.util.List<String>\n"
+ " get$capitalized_name$List() {\n"
+ " return java.util.Collections.unmodifiableList(\n"
+ " instance.get$capitalized_name$List());\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public int get$capitalized_name$Count() {\n"
+ " return instance.get$capitalized_name$Count();\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public java.lang.String get$capitalized_name$(int index) {\n"
+ " return instance.get$capitalized_name$(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public com.google.protobuf.ByteString\n"
+ " get$capitalized_name$Bytes(int index) {\n"
+ " return instance.get$capitalized_name$Bytes(index);\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder set$capitalized_name$(\n"
+ " int index, java.lang.String value) {\n"
+ " copyOnWrite();\n"
+ " instance.set$capitalized_name$(index, value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$(\n"
+ " java.lang.String value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$(value);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder addAll$capitalized_name$(\n"
+ " java.lang.Iterable<java.lang.String> values) {\n"
+ " copyOnWrite();\n"
+ " instance.addAll$capitalized_name$(values);\n"
+ " return this;\n"
+ "}\n");
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder clear$capitalized_name$() {\n"
+ " copyOnWrite();\n"
+ " instance.clear$capitalized_name$();\n"
+ " return this;\n"
+ "}\n");
+
+ WriteFieldDocComment(printer, descriptor_);
+ printer->Print(variables_,
+ "$deprecation$public Builder add$capitalized_name$Bytes(\n"
+ " com.google.protobuf.ByteString value) {\n"
+ " copyOnWrite();\n"
+ " instance.add$capitalized_name$Bytes(value);\n"
+ " return this;\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateFieldBuilderInitializationCode(io::Printer* printer) const {
+ // noop for strings
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateInitializationCode(io::Printer* printer) const {
+ printer->Print(variables_, "$name$_ = $empty_list$;\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateVisitCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_= visitor.visitList($name$_, other.$name$_);\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_.makeImmutable();\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateParsingCode(io::Printer* printer) const {
+ if (CheckUtf8(descriptor_)) {
+ printer->Print(variables_,
+ "String s = input.readStringRequireUtf8();\n");
+ } else {
+ // Lite runtime should attempt to reduce allocations by attempting to
+ // construct the string directly from the input stream buffer. This avoids
+ // spurious intermediary ByteString allocations, cutting overall allocations
+ // in half.
+ printer->Print(variables_,
+ "String s = input.readString();\n");
+ }
+ printer->Print(variables_,
+ "if (!$is_mutable$) {\n"
+ " $name$_ =\n"
+ " com.google.protobuf.GeneratedMessageLite.mutableCopy($name$_);\n"
+ "}\n");
+ printer->Print(variables_,
+ "$name$_.add(s);\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateParsingDoneCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($is_mutable$) {\n"
+ " $name$_.makeImmutable();\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ // Lite runtime should reduce allocations by serializing the string directly.
+ // This avoids spurious intermediary ByteString allocations, cutting overall
+ // allocations in half.
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " output.writeString($number$, $name$_.get(i));\n"
+ "}\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ // Lite runtime should reduce allocations by computing on the string directly.
+ // This avoids spurious intermediary ByteString allocations, cutting overall
+ // allocations in half.
+ printer->Print(variables_,
+ "{\n"
+ " int dataSize = 0;\n");
+ printer->Indent();
+
+ printer->Print(variables_,
+ "for (int i = 0; i < $name$_.size(); i++) {\n"
+ " dataSize += com.google.protobuf.CodedOutputStream\n"
+ " .computeStringSizeNoTag($name$_.get(i));\n"
+ "}\n");
+
+ printer->Print(
+ "size += dataSize;\n");
+
+
+ printer->Print(variables_,
+ "size += $tag_size$ * get$capitalized_name$List().size();\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = result && get$capitalized_name$List()\n"
+ " .equals(other.get$capitalized_name$List());\n");
+}
+
+void RepeatedImmutableStringFieldLiteGenerator::
+GenerateHashCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (get$capitalized_name$Count() > 0) {\n"
+ " hash = (37 * hash) + $constant_name$;\n"
+ " hash = (53 * hash) + get$capitalized_name$List().hashCode();\n"
+ "}\n");
+}
+
+string RepeatedImmutableStringFieldLiteGenerator::GetBoxedType() const {
+ return "String";
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.h
new file mode 100644
index 0000000000..4148aa4dfb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/java/java_string_field_lite.h
@@ -0,0 +1,157 @@
+// 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)
+// Author: jonp@google.com (Jon Perlow)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVA_STRING_FIELD_LITE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVA_STRING_FIELD_LITE_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/java/java_field.h>
+
+namespace google {
+namespace protobuf {
+ namespace compiler {
+ namespace java {
+ class Context; // context.h
+ class ClassNameResolver; // name_resolver.h
+ }
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace java {
+
+class ImmutableStringFieldLiteGenerator : public ImmutableFieldLiteGenerator {
+ public:
+ explicit ImmutableStringFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableStringFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ protected:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableStringFieldLiteGenerator);
+};
+
+class ImmutableStringOneofFieldLiteGenerator
+ : public ImmutableStringFieldLiteGenerator {
+ public:
+ ImmutableStringOneofFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~ImmutableStringOneofFieldLiteGenerator();
+
+ private:
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ImmutableStringOneofFieldLiteGenerator);
+};
+
+class RepeatedImmutableStringFieldLiteGenerator
+ : public ImmutableFieldLiteGenerator {
+ public:
+ explicit RepeatedImmutableStringFieldLiteGenerator(
+ const FieldDescriptor* descriptor, int messageBitIndex,
+ int builderBitIndex, Context* context);
+ ~RepeatedImmutableStringFieldLiteGenerator();
+
+ // implements ImmutableFieldLiteGenerator ------------------------------------
+ int GetNumBitsForMessage() const;
+ int GetNumBitsForBuilder() const;
+ void GenerateInterfaceMembers(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer) const;
+ void GenerateBuilderMembers(io::Printer* printer) const;
+ void GenerateInitializationCode(io::Printer* printer) const;
+ void GenerateVisitCode(io::Printer* printer) const;
+ void GenerateDynamicMethodMakeImmutableCode(io::Printer* printer) const;
+ void GenerateParsingCode(io::Printer* printer) const;
+ void GenerateParsingDoneCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateFieldBuilderInitializationCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCode(io::Printer* printer) const;
+
+ string GetBoxedType() const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ const int messageBitIndex_;
+ const int builderBitIndex_;
+ Context* context_;
+ ClassNameResolver* name_resolver_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedImmutableStringFieldLiteGenerator);
+};
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVA_STRING_FIELD_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.cc
new file mode 100644
index 0000000000..c6e8dfe90d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.cc
@@ -0,0 +1,143 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+#include <google/protobuf/compiler/javanano/javanano_enum.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+EnumGenerator::EnumGenerator(const EnumDescriptor* descriptor, const Params& params)
+ : params_(params), descriptor_(descriptor) {
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ const EnumValueDescriptor* value = descriptor_->value(i);
+ const EnumValueDescriptor* canonical_value =
+ descriptor_->FindValueByNumber(value->number());
+
+ if (value == canonical_value) {
+ canonical_values_.push_back(value);
+ } else {
+ Alias alias;
+ alias.value = value;
+ alias.canonical_value = canonical_value;
+ aliases_.push_back(alias);
+ }
+ }
+}
+
+EnumGenerator::~EnumGenerator() {}
+
+void EnumGenerator::Generate(io::Printer* printer) {
+ printer->Print(
+ "\n"
+ "// enum $classname$\n",
+ "classname", descriptor_->name());
+
+ const string classname = RenameJavaKeywords(descriptor_->name());
+
+ // Start of container interface
+ // If generating intdefs, we use the container interface as the intdef if
+ // present. Otherwise, we just make an empty @interface parallel to the
+ // constants.
+ bool use_intdef = params_.generate_intdefs();
+ bool use_shell_class = params_.java_enum_style();
+ if (use_intdef) {
+ // @IntDef annotation so tools can enforce correctness
+ // Annotations will be discarded by the compiler
+ printer->Print("@java.lang.annotation.Retention("
+ "java.lang.annotation.RetentionPolicy.SOURCE)\n"
+ "@android.support.annotation.IntDef({\n");
+ printer->Indent();
+ for (int i = 0; i < canonical_values_.size(); i++) {
+ const string constant_name =
+ RenameJavaKeywords(canonical_values_[i]->name());
+ if (use_shell_class) {
+ printer->Print("$classname$.$name$,\n",
+ "classname", classname,
+ "name", constant_name);
+ } else {
+ printer->Print("$name$,\n", "name", constant_name);
+ }
+ }
+ printer->Outdent();
+ printer->Print("})\n");
+ }
+ if (use_shell_class || use_intdef) {
+ printer->Print(
+ "public $at_for_intdef$interface $classname$ {\n",
+ "classname", classname,
+ "at_for_intdef", use_intdef ? "@" : "");
+ if (use_shell_class) {
+ printer->Indent();
+ } else {
+ printer->Print("}\n\n");
+ }
+ }
+
+ // Canonical values
+ for (int i = 0; i < canonical_values_.size(); i++) {
+ printer->Print(
+ "public static final int $name$ = $canonical_value$;\n",
+ "name", RenameJavaKeywords(canonical_values_[i]->name()),
+ "canonical_value", SimpleItoa(canonical_values_[i]->number()));
+ }
+
+ // Aliases
+ for (int i = 0; i < aliases_.size(); i++) {
+ printer->Print(
+ "public static final int $name$ = $canonical_name$;\n",
+ "name", RenameJavaKeywords(aliases_[i].value->name()),
+ "canonical_name", RenameJavaKeywords(aliases_[i].canonical_value->name()));
+ }
+
+ // End of container interface
+ if (use_shell_class) {
+ printer->Outdent();
+ printer->Print("}\n");
+ }
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.h
new file mode 100644
index 0000000000..10dd364876
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum.h
@@ -0,0 +1,87 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_ENUM_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_ENUM_H__
+
+#include <string>
+#include <vector>
+
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class EnumGenerator {
+ public:
+ explicit EnumGenerator(const EnumDescriptor* descriptor, const Params& params);
+ ~EnumGenerator();
+
+ void Generate(io::Printer* printer);
+
+ private:
+ const Params& params_;
+ const EnumDescriptor* descriptor_;
+
+ // The proto language allows multiple enum constants to have the same numeric
+ // value. Java, however, does not allow multiple enum constants to be
+ // considered equivalent. We treat the first defined constant for any
+ // given numeric value as "canonical" and the rest as aliases of that
+ // canonical value.
+ vector<const EnumValueDescriptor*> canonical_values_;
+
+ struct Alias {
+ const EnumValueDescriptor* value;
+ const EnumValueDescriptor* canonical_value;
+ };
+ vector<Alias> aliases_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_ENUM_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.cc
new file mode 100644
index 0000000000..7666db38a2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.cc
@@ -0,0 +1,544 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/javanano/javanano_enum_field.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+namespace {
+
+// TODO(kenton): Factor out a "SetCommonFieldVariables()" to get rid of
+// repeat code between this and the other field types.
+void SetEnumVariables(const Params& params,
+ const FieldDescriptor* descriptor, map<string, string>* variables) {
+ (*variables)["name"] =
+ RenameJavaKeywords(UnderscoresToCamelCase(descriptor));
+ (*variables)["capitalized_name"] =
+ RenameJavaKeywords(UnderscoresToCapitalizedCamelCase(descriptor));
+ (*variables)["number"] = SimpleItoa(descriptor->number());
+ if (params.use_reference_types_for_primitives()
+ && !params.reftypes_primitive_enums()
+ && !descriptor->is_repeated()) {
+ (*variables)["type"] = "java.lang.Integer";
+ (*variables)["default"] = "null";
+ } else {
+ (*variables)["type"] = "int";
+ (*variables)["default"] = DefaultValue(params, descriptor);
+ }
+ (*variables)["repeated_default"] =
+ "com.google.protobuf.nano.WireFormatNano.EMPTY_INT_ARRAY";
+ (*variables)["tag"] = SimpleItoa(internal::WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ internal::WireFormat::TagSize(descriptor->number(), descriptor->type()));
+ (*variables)["non_packed_tag"] = SimpleItoa(
+ internal::WireFormatLite::MakeTag(descriptor->number(),
+ internal::WireFormat::WireTypeForFieldType(descriptor->type())));
+ (*variables)["message_name"] = descriptor->containing_type()->name();
+ const EnumDescriptor* enum_type = descriptor->enum_type();
+ (*variables)["message_type_intdef"] = "@"
+ + ToJavaName(params, enum_type->name(), true,
+ enum_type->containing_type(), enum_type->file());
+}
+
+void LoadEnumValues(const Params& params,
+ const EnumDescriptor* enum_descriptor, vector<string>* canonical_values) {
+ string enum_class_name = ClassName(params, enum_descriptor);
+ for (int i = 0; i < enum_descriptor->value_count(); i++) {
+ const EnumValueDescriptor* value = enum_descriptor->value(i);
+ const EnumValueDescriptor* canonical_value =
+ enum_descriptor->FindValueByNumber(value->number());
+ if (value == canonical_value) {
+ canonical_values->push_back(
+ enum_class_name + "." + RenameJavaKeywords(value->name()));
+ }
+ }
+}
+
+void PrintCaseLabels(
+ io::Printer* printer, const vector<string>& canonical_values) {
+ for (int i = 0; i < canonical_values.size(); i++) {
+ printer->Print(
+ " case $value$:\n",
+ "value", canonical_values[i]);
+ }
+}
+
+} // namespace
+
+// ===================================================================
+
+EnumFieldGenerator::
+EnumFieldGenerator(const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetEnumVariables(params, descriptor, &variables_);
+ LoadEnumValues(params, descriptor->enum_type(), &canonical_values_);
+}
+
+EnumFieldGenerator::~EnumFieldGenerator() {}
+
+void EnumFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /* unused lazy_init */) const {
+ if (params_.generate_intdefs()) {
+ printer->Print(variables_, "$message_type_intdef$\n");
+ }
+ printer->Print(variables_, "public $type$ $name$;\n");
+
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "public boolean has$capitalized_name$;\n");
+ }
+}
+
+void EnumFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$ = $default$;\n");
+
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "has$capitalized_name$ = false;\n");
+ }
+}
+
+void EnumFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "int value = input.readInt32();\n"
+ "switch (value) {\n");
+ PrintCaseLabels(printer, canonical_values_);
+ printer->Print(variables_,
+ " this.$name$ = value;\n");
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ " has$capitalized_name$ = true;\n");
+ }
+ printer->Print(
+ " break;\n"
+ "}\n");
+ // No default case: in case of invalid value from the wire, preserve old
+ // field value. Also we are not storing the invalid value into the unknown
+ // fields, because there is no way to get the value out.
+}
+
+void EnumFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ if (descriptor_->is_required() && !params_.generate_has()) {
+ // Always serialize a required field if we don't have the 'has' signal.
+ printer->Print(variables_,
+ "output.writeInt32($number$, this.$name$);\n");
+ } else {
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "if (this.$name$ != $default$ || has$capitalized_name$) {\n");
+ } else {
+ printer->Print(variables_,
+ "if (this.$name$ != $default$) {\n");
+ }
+ printer->Print(variables_,
+ " output.writeInt32($number$, this.$name$);\n"
+ "}\n");
+ }
+}
+
+void EnumFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ if (descriptor_->is_required() && !params_.generate_has()) {
+ printer->Print(variables_,
+ "size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .computeInt32Size($number$, this.$name$);\n");
+ } else {
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "if (this.$name$ != $default$ || has$capitalized_name$) {\n");
+ } else {
+ printer->Print(variables_,
+ "if (this.$name$ != $default$) {\n");
+ }
+ printer->Print(variables_,
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .computeInt32Size($number$, this.$name$);\n"
+ "}\n");
+ }
+}
+
+void EnumFieldGenerator::GenerateEqualsCode(io::Printer* printer) const {
+ if (params_.use_reference_types_for_primitives()
+ && !params_.reftypes_primitive_enums()) {
+ printer->Print(variables_,
+ "if (this.$name$ == null) {\n"
+ " if (other.$name$ != null) {\n"
+ " return false;\n"
+ " }\n"
+ "} else if (!this.$name$.equals(other.$name$)) {\n"
+ " return false;"
+ "}\n");
+ } else {
+ // We define equality as serialized form equality. If generate_has(),
+ // then if the field value equals the default value in both messages,
+ // but one's 'has' field is set and the other's is not, the serialized
+ // forms are different and we should return false.
+ printer->Print(variables_,
+ "if (this.$name$ != other.$name$");
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "\n"
+ " || (this.$name$ == $default$\n"
+ " && this.has$capitalized_name$ != other.has$capitalized_name$)");
+ }
+ printer->Print(") {\n"
+ " return false;\n"
+ "}\n");
+ }
+}
+
+void EnumFieldGenerator::GenerateHashCodeCode(io::Printer* printer) const {
+ printer->Print(
+ "result = 31 * result + ");
+ if (params_.use_reference_types_for_primitives()
+ && !params_.reftypes_primitive_enums()) {
+ printer->Print(variables_,
+ "(this.$name$ == null ? 0 : this.$name$)");
+ } else {
+ printer->Print(variables_,
+ "this.$name$");
+ }
+ printer->Print(";\n");
+}
+
+// ===================================================================
+
+AccessorEnumFieldGenerator::
+AccessorEnumFieldGenerator(const FieldDescriptor* descriptor,
+ const Params& params, int has_bit_index)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetEnumVariables(params, descriptor, &variables_);
+ LoadEnumValues(params, descriptor->enum_type(), &canonical_values_);
+ SetBitOperationVariables("has", has_bit_index, &variables_);
+}
+
+AccessorEnumFieldGenerator::~AccessorEnumFieldGenerator() {}
+
+void AccessorEnumFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /* unused lazy_init */) const {
+ printer->Print(variables_, "private int $name$_;\n");
+ if (params_.generate_intdefs()) {
+ printer->Print(variables_, "$message_type_intdef$\n");
+ }
+ printer->Print(variables_,
+ "public int get$capitalized_name$() {\n"
+ " return $name$_;\n"
+ "}\n"
+ "public $message_name$ set$capitalized_name$(");
+ if (params_.generate_intdefs()) {
+ printer->Print(variables_,
+ "\n"
+ " $message_type_intdef$ ");
+ }
+ printer->Print(variables_,
+ "int value) {\n"
+ " $name$_ = value;\n"
+ " $set_has$;\n"
+ " return this;\n"
+ "}\n"
+ "public boolean has$capitalized_name$() {\n"
+ " return $get_has$;\n"
+ "}\n"
+ "public $message_name$ clear$capitalized_name$() {\n"
+ " $name$_ = $default$;\n"
+ " $clear_has$;\n"
+ " return this;\n"
+ "}\n");
+}
+
+void AccessorEnumFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = $default$;\n");
+}
+
+void AccessorEnumFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "int value = input.readInt32();\n"
+ "switch (value) {\n");
+ PrintCaseLabels(printer, canonical_values_);
+ printer->Print(variables_,
+ " $name$_ = value;\n"
+ " $set_has$;\n"
+ " break;\n"
+ "}\n");
+ // No default case: in case of invalid value from the wire, preserve old
+ // field value. Also we are not storing the invalid value into the unknown
+ // fields, because there is no way to get the value out.
+}
+
+void AccessorEnumFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_has$) {\n"
+ " output.writeInt32($number$, $name$_);\n"
+ "}\n");
+}
+
+void AccessorEnumFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_has$) {\n"
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .computeInt32Size($number$, $name$_);\n"
+ "}\n");
+}
+
+void AccessorEnumFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($different_has$\n"
+ " || $name$_ != other.$name$_) {\n"
+ " return false;\n"
+ "}\n");
+}
+
+void AccessorEnumFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = 31 * result + $name$_;\n");
+}
+
+// ===================================================================
+
+RepeatedEnumFieldGenerator::
+RepeatedEnumFieldGenerator(const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetEnumVariables(params, descriptor, &variables_);
+ LoadEnumValues(params, descriptor->enum_type(), &canonical_values_);
+}
+
+RepeatedEnumFieldGenerator::~RepeatedEnumFieldGenerator() {}
+
+void RepeatedEnumFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /* unused lazy_init */) const {
+ printer->Print(variables_,
+ "public $type$[] $name$;\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$ = $repeated_default$;\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // First, figure out the maximum length of the array, then parse,
+ // and finally copy the valid values to the field.
+ printer->Print(variables_,
+ "int length = com.google.protobuf.nano.WireFormatNano\n"
+ " .getRepeatedFieldArrayLength(input, $non_packed_tag$);\n"
+ "int[] validValues = new int[length];\n"
+ "int validCount = 0;\n"
+ "for (int i = 0; i < length; i++) {\n"
+ " if (i != 0) { // tag for first value already consumed.\n"
+ " input.readTag();\n"
+ " }\n"
+ " int value = input.readInt32();\n"
+ " switch (value) {\n");
+ printer->Indent();
+ PrintCaseLabels(printer, canonical_values_);
+ printer->Outdent();
+ printer->Print(variables_,
+ " validValues[validCount++] = value;\n"
+ " break;\n"
+ " }\n"
+ "}\n"
+ "if (validCount != 0) {\n"
+ " int i = this.$name$ == null ? 0 : this.$name$.length;\n"
+ " if (i == 0 && validCount == validValues.length) {\n"
+ " this.$name$ = validValues;\n"
+ " } else {\n"
+ " int[] newArray = new int[i + validCount];\n"
+ " if (i != 0) {\n"
+ " java.lang.System.arraycopy(this.$name$, 0, newArray, 0, i);\n"
+ " }\n"
+ " java.lang.System.arraycopy(validValues, 0, newArray, i, validCount);\n"
+ " this.$name$ = newArray;\n"
+ " }\n"
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateMergingCodeFromPacked(io::Printer* printer) const {
+ printer->Print(variables_,
+ "int bytes = input.readRawVarint32();\n"
+ "int limit = input.pushLimit(bytes);\n"
+ "// First pass to compute array length.\n"
+ "int arrayLength = 0;\n"
+ "int startPos = input.getPosition();\n"
+ "while (input.getBytesUntilLimit() > 0) {\n"
+ " switch (input.readInt32()) {\n");
+ printer->Indent();
+ PrintCaseLabels(printer, canonical_values_);
+ printer->Outdent();
+ printer->Print(variables_,
+ " arrayLength++;\n"
+ " break;\n"
+ " }\n"
+ "}\n"
+ "if (arrayLength != 0) {\n"
+ " input.rewindToPosition(startPos);\n"
+ " int i = this.$name$ == null ? 0 : this.$name$.length;\n"
+ " int[] newArray = new int[i + arrayLength];\n"
+ " if (i != 0) {\n"
+ " java.lang.System.arraycopy(this.$name$, 0, newArray, 0, i);\n"
+ " }\n"
+ " while (input.getBytesUntilLimit() > 0) {\n"
+ " int value = input.readInt32();\n"
+ " switch (value) {\n");
+ printer->Indent();
+ printer->Indent();
+ PrintCaseLabels(printer, canonical_values_);
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(variables_,
+ " newArray[i++] = value;\n"
+ " break;\n"
+ " }\n"
+ " }\n"
+ " this.$name$ = newArray;\n"
+ "}\n"
+ "input.popLimit(limit);\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateRepeatedDataSizeCode(io::Printer* printer) const {
+ // Creates a variable dataSize and puts the serialized size in there.
+ printer->Print(variables_,
+ "int dataSize = 0;\n"
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " int element = this.$name$[i];\n"
+ " dataSize += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .computeInt32SizeNoTag(element);\n"
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n");
+ printer->Indent();
+
+ if (descriptor_->options().packed()) {
+ GenerateRepeatedDataSizeCode(printer);
+ printer->Print(variables_,
+ "output.writeRawVarint32($tag$);\n"
+ "output.writeRawVarint32(dataSize);\n"
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " output.writeRawVarint32(this.$name$[i]);\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " output.writeInt32($number$, this.$name$[i]);\n"
+ "}\n");
+ }
+
+ printer->Outdent();
+ printer->Print(variables_,
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n");
+ printer->Indent();
+
+ GenerateRepeatedDataSizeCode(printer);
+
+ printer->Print(
+ "size += dataSize;\n");
+ if (descriptor_->options().packed()) {
+ printer->Print(variables_,
+ "size += $tag_size$;\n"
+ "size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .computeRawVarint32Size(dataSize);\n");
+ } else {
+ printer->Print(variables_,
+ "size += $tag_size$ * this.$name$.length;\n");
+ }
+
+ printer->Outdent();
+
+ printer->Print(
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateFixClonedCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n"
+ " cloned.$name$ = this.$name$.clone();\n"
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!com.google.protobuf.nano.InternalNano.equals(\n"
+ " this.$name$, other.$name$)) {\n"
+ " return false;\n"
+ "}\n");
+}
+
+void RepeatedEnumFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = 31 * result\n"
+ " + com.google.protobuf.nano.InternalNano.hashCode(this.$name$);\n");
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.h
new file mode 100644
index 0000000000..b94790d6bd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_enum_field.h
@@ -0,0 +1,126 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_ENUM_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_ENUM_FIELD_H__
+
+#include <map>
+#include <string>
+#include <vector>
+#include <google/protobuf/compiler/javanano/javanano_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class EnumFieldGenerator : public FieldGenerator {
+ public:
+ explicit EnumFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params);
+ ~EnumFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ vector<string> canonical_values_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumFieldGenerator);
+};
+
+class AccessorEnumFieldGenerator : public FieldGenerator {
+ public:
+ explicit AccessorEnumFieldGenerator(const FieldDescriptor* descriptor,
+ const Params& params, int has_bit_index);
+ ~AccessorEnumFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ vector<string> canonical_values_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(AccessorEnumFieldGenerator);
+};
+
+class RepeatedEnumFieldGenerator : public FieldGenerator {
+ public:
+ explicit RepeatedEnumFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params);
+ ~RepeatedEnumFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateMergingCodeFromPacked(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+ void GenerateFixClonedCode(io::Printer* printer) const;
+
+ private:
+ void GenerateRepeatedDataSizeCode(io::Printer* printer) const;
+
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+ vector<string> canonical_values_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedEnumFieldGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_ENUM_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.cc
new file mode 100644
index 0000000000..0b9d1d8de7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.cc
@@ -0,0 +1,150 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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: bduff@google.com (Brian Duff)
+
+#include <google/protobuf/compiler/javanano/javanano_extension.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/wire_format.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+const char* GetTypeConstantName(const FieldDescriptor::Type type) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32 : return "TYPE_INT32" ;
+ case FieldDescriptor::TYPE_UINT32 : return "TYPE_UINT32" ;
+ case FieldDescriptor::TYPE_SINT32 : return "TYPE_SINT32" ;
+ case FieldDescriptor::TYPE_FIXED32 : return "TYPE_FIXED32" ;
+ case FieldDescriptor::TYPE_SFIXED32: return "TYPE_SFIXED32";
+ case FieldDescriptor::TYPE_INT64 : return "TYPE_INT64" ;
+ case FieldDescriptor::TYPE_UINT64 : return "TYPE_UINT64" ;
+ case FieldDescriptor::TYPE_SINT64 : return "TYPE_SINT64" ;
+ case FieldDescriptor::TYPE_FIXED64 : return "TYPE_FIXED64" ;
+ case FieldDescriptor::TYPE_SFIXED64: return "TYPE_SFIXED64";
+ case FieldDescriptor::TYPE_FLOAT : return "TYPE_FLOAT" ;
+ case FieldDescriptor::TYPE_DOUBLE : return "TYPE_DOUBLE" ;
+ case FieldDescriptor::TYPE_BOOL : return "TYPE_BOOL" ;
+ case FieldDescriptor::TYPE_STRING : return "TYPE_STRING" ;
+ case FieldDescriptor::TYPE_BYTES : return "TYPE_BYTES" ;
+ case FieldDescriptor::TYPE_ENUM : return "TYPE_ENUM" ;
+ case FieldDescriptor::TYPE_GROUP : return "TYPE_GROUP" ;
+ case FieldDescriptor::TYPE_MESSAGE : return "TYPE_MESSAGE" ;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+} // namespace
+
+void SetVariables(const FieldDescriptor* descriptor, const Params params,
+ map<string, string>* variables) {
+ (*variables)["extends"] = ClassName(params, descriptor->containing_type());
+ (*variables)["name"] = RenameJavaKeywords(UnderscoresToCamelCase(descriptor));
+ bool repeated = descriptor->is_repeated();
+ (*variables)["repeated"] = repeated ? "Repeated" : "";
+ (*variables)["type"] = GetTypeConstantName(descriptor->type());
+ JavaType java_type = GetJavaType(descriptor->type());
+ string tag = SimpleItoa(WireFormat::MakeTag(descriptor));
+ if (java_type == JAVATYPE_MESSAGE) {
+ (*variables)["ext_type"] = "MessageTyped";
+ string message_type = ClassName(params, descriptor->message_type());
+ if (repeated) {
+ message_type += "[]";
+ }
+ (*variables)["class"] = message_type;
+ // For message typed extensions, tags_params contains a single tag
+ // for both singular and repeated cases.
+ (*variables)["tag_params"] = tag;
+ } else {
+ (*variables)["ext_type"] = "PrimitiveTyped";
+ if (!repeated) {
+ (*variables)["class"] = BoxedPrimitiveTypeName(java_type);
+ (*variables)["tag_params"] = tag;
+ } else {
+ (*variables)["class"] = PrimitiveTypeName(java_type) + "[]";
+ if (!descriptor->is_packable()) {
+ // Non-packable: nonPackedTag == tag, packedTag == 0
+ (*variables)["tag_params"] = tag + ", " + tag + ", 0";
+ } else if (descriptor->options().packed()) {
+ // Packable and packed: tag == packedTag
+ string non_packed_tag = SimpleItoa(WireFormatLite::MakeTag(
+ descriptor->number(),
+ WireFormat::WireTypeForFieldType(descriptor->type())));
+ (*variables)["tag_params"] = tag + ", " + non_packed_tag + ", " + tag;
+ } else {
+ // Packable and not packed: tag == nonPackedTag
+ string packed_tag = SimpleItoa(WireFormatLite::MakeTag(
+ descriptor->number(), WireFormatLite::WIRETYPE_LENGTH_DELIMITED));
+ (*variables)["tag_params"] = tag + ", " + tag + ", " + packed_tag;
+ }
+ }
+ }
+}
+
+ExtensionGenerator::
+ExtensionGenerator(const FieldDescriptor* descriptor, const Params& params)
+ : params_(params), descriptor_(descriptor) {
+ SetVariables(descriptor, params, &variables_);
+}
+
+ExtensionGenerator::~ExtensionGenerator() {}
+
+void ExtensionGenerator::Generate(io::Printer* printer) const {
+ printer->Print("\n");
+ PrintFieldComment(printer, descriptor_);
+ printer->Print(variables_,
+ "public static final com.google.protobuf.nano.Extension<\n"
+ " $extends$,\n"
+ " $class$> $name$ =\n"
+ " com.google.protobuf.nano.Extension.create$repeated$$ext_type$(\n"
+ " com.google.protobuf.nano.Extension.$type$,\n"
+ " $class$.class,\n"
+ " $tag_params$L);\n");
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.h
new file mode 100644
index 0000000000..4843e29622
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_extension.h
@@ -0,0 +1,74 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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: bduff@google.com (Brian Duff)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_EXTENSION_H_
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_EXTENSION_H_
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+#include <google/protobuf/descriptor.pb.h>
+
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class ExtensionGenerator {
+ public:
+ explicit ExtensionGenerator(const FieldDescriptor* descriptor, const Params& params);
+ ~ExtensionGenerator();
+
+ void Generate(io::Printer* printer) const;
+
+ private:
+ const Params& params_;
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_EXTENSION_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.cc
new file mode 100644
index 0000000000..85257f3f73
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.cc
@@ -0,0 +1,209 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <google/protobuf/compiler/javanano/javanano_field.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/compiler/javanano/javanano_primitive_field.h>
+#include <google/protobuf/compiler/javanano/javanano_enum_field.h>
+#include <google/protobuf/compiler/javanano/javanano_map_field.h>
+#include <google/protobuf/compiler/javanano/javanano_message_field.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+FieldGenerator::~FieldGenerator() {}
+
+bool FieldGenerator::SavedDefaultNeeded() const {
+ // No saved default for this field by default.
+ // Subclasses whose instances may need saved defaults will override this
+ // and return the appropriate value.
+ return false;
+}
+
+void FieldGenerator::GenerateInitSavedDefaultCode(io::Printer* printer) const {
+ // No saved default for this field by default.
+ // Subclasses whose instances may need saved defaults will override this
+ // and generate the appropriate init code to the printer.
+}
+
+void FieldGenerator::GenerateMergingCodeFromPacked(io::Printer* printer) const {
+ // Reaching here indicates a bug. Cases are:
+ // - This FieldGenerator should support packing, but this method should be
+ // overridden.
+ // - This FieldGenerator doesn't support packing, and this method should
+ // never have been called.
+ GOOGLE_LOG(FATAL) << "GenerateParsingCodeFromPacked() "
+ << "called on field generator that does not support packing.";
+}
+
+// =============================================
+
+FieldGeneratorMap::FieldGeneratorMap(
+ const Descriptor* descriptor, const Params &params)
+ : descriptor_(descriptor),
+ field_generators_(
+ new scoped_ptr<FieldGenerator>[descriptor->field_count()]) {
+
+ int next_has_bit_index = 0;
+ bool saved_defaults_needed = false;
+ // Construct all the FieldGenerators.
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ FieldGenerator* field_generator = MakeGenerator(
+ descriptor->field(i), params, &next_has_bit_index);
+ saved_defaults_needed = saved_defaults_needed
+ || field_generator->SavedDefaultNeeded();
+ field_generators_[i].reset(field_generator);
+ }
+ total_bits_ = next_has_bit_index;
+ saved_defaults_needed_ = saved_defaults_needed;
+}
+
+FieldGenerator* FieldGeneratorMap::MakeGenerator(const FieldDescriptor* field,
+ const Params &params, int* next_has_bit_index) {
+ JavaType java_type = GetJavaType(field);
+ if (field->is_repeated()) {
+ switch (java_type) {
+ case JAVATYPE_MESSAGE:
+ if (IsMapEntry(field->message_type())) {
+ return new MapFieldGenerator(field, params);
+ } else {
+ return new RepeatedMessageFieldGenerator(field, params);
+ }
+ case JAVATYPE_ENUM:
+ return new RepeatedEnumFieldGenerator(field, params);
+ default:
+ return new RepeatedPrimitiveFieldGenerator(field, params);
+ }
+ } else if (field->containing_oneof()) {
+ switch (java_type) {
+ case JAVATYPE_MESSAGE:
+ return new MessageOneofFieldGenerator(field, params);
+ case JAVATYPE_ENUM:
+ default:
+ return new PrimitiveOneofFieldGenerator(field, params);
+ }
+ } else if (params.optional_field_accessors() && field->is_optional()
+ && java_type != JAVATYPE_MESSAGE) {
+ // We need a has-bit for each primitive/enum field because their default
+ // values could be same as explicitly set values. But we don't need it
+ // for a message field because they have no defaults and Nano uses 'null'
+ // for unset messages, which cannot be set explicitly.
+ switch (java_type) {
+ case JAVATYPE_ENUM:
+ return new AccessorEnumFieldGenerator(
+ field, params, (*next_has_bit_index)++);
+ default:
+ return new AccessorPrimitiveFieldGenerator(
+ field, params, (*next_has_bit_index)++);
+ }
+ } else {
+ switch (java_type) {
+ case JAVATYPE_MESSAGE:
+ return new MessageFieldGenerator(field, params);
+ case JAVATYPE_ENUM:
+ return new EnumFieldGenerator(field, params);
+ default:
+ return new PrimitiveFieldGenerator(field, params);
+ }
+ }
+}
+
+FieldGeneratorMap::~FieldGeneratorMap() {}
+
+const FieldGenerator& FieldGeneratorMap::get(
+ const FieldDescriptor* field) const {
+ GOOGLE_CHECK_EQ(field->containing_type(), descriptor_);
+ return *field_generators_[field->index()];
+}
+
+void SetCommonOneofVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables) {
+ (*variables)["oneof_name"] =
+ UnderscoresToCamelCase(descriptor->containing_oneof());
+ (*variables)["oneof_capitalized_name"] =
+ UnderscoresToCapitalizedCamelCase(descriptor->containing_oneof());
+ (*variables)["oneof_index"] =
+ SimpleItoa(descriptor->containing_oneof()->index());
+ (*variables)["set_oneof_case"] =
+ "this." + (*variables)["oneof_name"] +
+ "Case_ = " + SimpleItoa(descriptor->number());
+ (*variables)["clear_oneof_case"] =
+ "this." + (*variables)["oneof_name"] + "Case_ = 0";
+ (*variables)["has_oneof_case"] =
+ "this." + (*variables)["oneof_name"] + "Case_ == " +
+ SimpleItoa(descriptor->number());
+}
+
+void GenerateOneofFieldEquals(const FieldDescriptor* descriptor,
+ const map<string, string>& variables,
+ io::Printer* printer) {
+ if (GetJavaType(descriptor) == JAVATYPE_BYTES) {
+ printer->Print(variables,
+ "if (this.has$capitalized_name$()) {\n"
+ " if (!java.util.Arrays.equals((byte[]) this.$oneof_name$_,\n"
+ " (byte[]) other.$oneof_name$_)) {\n"
+ " return false;\n"
+ " }\n"
+ "}\n");
+ } else {
+ printer->Print(variables,
+ "if (this.has$capitalized_name$()) {\n"
+ " if (!this.$oneof_name$_.equals(other.$oneof_name$_)) {\n"
+ " return false;\n"
+ " }\n"
+ "}\n");
+ }
+}
+
+void GenerateOneofFieldHashCode(const FieldDescriptor* descriptor,
+ const map<string, string>& variables,
+ io::Printer* printer) {
+ if (GetJavaType(descriptor) == JAVATYPE_BYTES) {
+ printer->Print(variables,
+ "result = 31 * result + ($has_oneof_case$\n"
+ " ? java.util.Arrays.hashCode((byte[]) this.$oneof_name$_) : 0);\n");
+ } else {
+ printer->Print(variables,
+ "result = 31 * result +\n"
+ " ($has_oneof_case$ ? this.$oneof_name$_.hashCode() : 0);\n");
+ }
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.h
new file mode 100644
index 0000000000..57c221f47c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_field.h
@@ -0,0 +1,130 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class FieldGenerator {
+ public:
+ FieldGenerator(const Params& params) : params_(params) {}
+ virtual ~FieldGenerator();
+
+ virtual bool SavedDefaultNeeded() const;
+ virtual void GenerateInitSavedDefaultCode(io::Printer* printer) const;
+
+ // Generates code for Java fields and methods supporting this field.
+ // If this field needs a saved default (SavedDefaultNeeded() is true),
+ // then @lazy_init controls how the static field for that default value
+ // and its initialization code should be generated. If @lazy_init is
+ // true, the static field is not declared final and the initialization
+ // code is generated only when GenerateInitSavedDefaultCode is called;
+ // otherwise, the static field is declared final and initialized inline.
+ // GenerateInitSavedDefaultCode will not be called in the latter case.
+ virtual void GenerateMembers(
+ io::Printer* printer, bool lazy_init) const = 0;
+
+ virtual void GenerateClearCode(io::Printer* printer) const = 0;
+ virtual void GenerateMergingCode(io::Printer* printer) const = 0;
+
+ // Generates code to merge from packed serialized form. The default
+ // implementation will fail; subclasses which can handle packed serialized
+ // forms will override this and print appropriate code to the printer.
+ virtual void GenerateMergingCodeFromPacked(io::Printer* printer) const;
+
+ virtual void GenerateSerializationCode(io::Printer* printer) const = 0;
+ virtual void GenerateSerializedSizeCode(io::Printer* printer) const = 0;
+ virtual void GenerateEqualsCode(io::Printer* printer) const = 0;
+ virtual void GenerateHashCodeCode(io::Printer* printer) const = 0;
+ virtual void GenerateFixClonedCode(io::Printer* printer) const {}
+
+ protected:
+ const Params& params_;
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGenerator);
+};
+
+// Convenience class which constructs FieldGenerators for a Descriptor.
+class FieldGeneratorMap {
+ public:
+ explicit FieldGeneratorMap(const Descriptor* descriptor, const Params &params);
+ ~FieldGeneratorMap();
+
+ const FieldGenerator& get(const FieldDescriptor* field) const;
+ int total_bits() const { return total_bits_; }
+ bool saved_defaults_needed() const { return saved_defaults_needed_; }
+
+ private:
+ const Descriptor* descriptor_;
+ scoped_array<scoped_ptr<FieldGenerator> > field_generators_;
+ int total_bits_;
+ bool saved_defaults_needed_;
+
+ static FieldGenerator* MakeGenerator(const FieldDescriptor* field,
+ const Params &params, int* next_has_bit_index);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGeneratorMap);
+};
+
+void SetCommonOneofVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables);
+void GenerateOneofFieldEquals(const FieldDescriptor* descriptor,
+ const map<string, string>& variables,
+ io::Printer* printer);
+void GenerateOneofFieldHashCode(const FieldDescriptor* descriptor,
+ const map<string, string>& variables,
+ io::Printer* printer);
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.cc
new file mode 100644
index 0000000000..3676ab9d19
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.cc
@@ -0,0 +1,263 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <iostream>
+
+#include <google/protobuf/compiler/javanano/javanano_file.h>
+#include <google/protobuf/compiler/javanano/javanano_enum.h>
+#include <google/protobuf/compiler/javanano/javanano_extension.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/compiler/javanano/javanano_message.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+namespace {
+
+// Recursively searches the given message to see if it contains any extensions.
+bool UsesExtensions(const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+
+ // We conservatively assume that unknown fields are extensions.
+ if (reflection->GetUnknownFields(message).field_count() > 0) return true;
+
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message, &fields);
+
+ for (int i = 0; i < fields.size(); i++) {
+ if (fields[i]->is_extension()) return true;
+
+ if (fields[i]->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (fields[i]->is_repeated()) {
+ int size = reflection->FieldSize(message, fields[i]);
+ for (int j = 0; j < size; j++) {
+ const Message& sub_message =
+ reflection->GetRepeatedMessage(message, fields[i], j);
+ if (UsesExtensions(sub_message)) return true;
+ }
+ } else {
+ const Message& sub_message = reflection->GetMessage(message, fields[i]);
+ if (UsesExtensions(sub_message)) return true;
+ }
+ }
+ }
+
+ return false;
+}
+
+} // namespace
+
+FileGenerator::FileGenerator(const FileDescriptor* file, const Params& params)
+ : file_(file),
+ params_(params),
+ java_package_(FileJavaPackage(params, file)),
+ classname_(FileClassName(params, file)) {}
+
+FileGenerator::~FileGenerator() {}
+
+bool FileGenerator::Validate(string* error) {
+ // Check for extensions
+ FileDescriptorProto file_proto;
+ file_->CopyTo(&file_proto);
+ if (UsesExtensions(file_proto) && !params_.store_unknown_fields()) {
+ error->assign(file_->name());
+ error->append(
+ ": Java NANO_RUNTIME only supports extensions when the "
+ "'store_unknown_fields' generator option is 'true'.");
+ return false;
+ }
+
+ if (file_->service_count() != 0 && !params_.ignore_services()) {
+ error->assign(file_->name());
+ error->append(
+ ": Java NANO_RUNTIME does not support services\"");
+ return false;
+ }
+
+ if (!IsOuterClassNeeded(params_, file_)) {
+ return true;
+ }
+
+ // Check whether legacy javanano generator would omit the outer class.
+ if (!params_.has_java_outer_classname(file_->name())
+ && file_->message_type_count() == 1
+ && file_->enum_type_count() == 0 && file_->extension_count() == 0) {
+ cout << "INFO: " << file_->name() << ":" << endl;
+ cout << "Javanano generator has changed to align with java generator. "
+ "An outer class will be created for this file and the single message "
+ "in the file will become a nested class. Use java_multiple_files to "
+ "skip generating the outer class, or set an explicit "
+ "java_outer_classname to suppress this message." << endl;
+ }
+
+ // Check that no class name matches the file's class name. This is a common
+ // problem that leads to Java compile errors that can be hard to understand.
+ // It's especially bad when using the java_multiple_files, since we would
+ // end up overwriting the outer class with one of the inner ones.
+ bool found_conflict = false;
+ for (int i = 0; !found_conflict && i < file_->message_type_count(); i++) {
+ if (file_->message_type(i)->name() == classname_) {
+ found_conflict = true;
+ }
+ }
+ if (params_.java_enum_style()) {
+ for (int i = 0; !found_conflict && i < file_->enum_type_count(); i++) {
+ if (file_->enum_type(i)->name() == classname_) {
+ found_conflict = true;
+ }
+ }
+ }
+ if (found_conflict) {
+ error->assign(file_->name());
+ error->append(
+ ": Cannot generate Java output because the file's outer class name, \"");
+ error->append(classname_);
+ error->append(
+ "\", matches the name of one of the types declared inside it. "
+ "Please either rename the type or use the java_outer_classname "
+ "option to specify a different outer class name for the .proto file.");
+ return false;
+ }
+ return true;
+}
+
+void FileGenerator::Generate(io::Printer* printer) {
+ // We don't import anything because we refer to all classes by their
+ // fully-qualified names in the generated source.
+ printer->Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n");
+ if (!java_package_.empty()) {
+ printer->Print(
+ "\n"
+ "package $package$;\n",
+ "package", java_package_);
+ }
+
+ // Note: constants (from enums, emitted in the loop below) may have the same names as constants
+ // in the nested classes. This causes Java warnings, but is not fatal, so we suppress those
+ // warnings here in the top-most class declaration.
+ printer->Print(
+ "\n"
+ "@SuppressWarnings(\"hiding\")\n"
+ "public interface $classname$ {\n",
+ "classname", classname_);
+ printer->Indent();
+
+ // -----------------------------------------------------------------
+
+ // Extensions.
+ for (int i = 0; i < file_->extension_count(); i++) {
+ ExtensionGenerator(file_->extension(i), params_).Generate(printer);
+ }
+
+ // Enums.
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ EnumGenerator(file_->enum_type(i), params_).Generate(printer);
+ }
+
+ // Messages.
+ if (!params_.java_multiple_files(file_->name())) {
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ MessageGenerator(file_->message_type(i), params_).Generate(printer);
+ }
+ }
+
+ // Static variables.
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ // TODO(kenton): Reuse MessageGenerator objects?
+ MessageGenerator(file_->message_type(i), params_).GenerateStaticVariables(printer);
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "}\n");
+}
+
+template<typename GeneratorClass, typename DescriptorClass>
+static void GenerateSibling(const string& package_dir,
+ const string& java_package,
+ const DescriptorClass* descriptor,
+ GeneratorContext* output_directory,
+ vector<string>* file_list,
+ const Params& params) {
+ string filename = package_dir + descriptor->name() + ".java";
+ file_list->push_back(filename);
+
+ scoped_ptr<io::ZeroCopyOutputStream> output(
+ output_directory->Open(filename));
+ io::Printer printer(output.get(), '$');
+
+ printer.Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n");
+ if (!java_package.empty()) {
+ printer.Print(
+ "\n"
+ "package $package$;\n",
+ "package", java_package);
+ }
+
+ GeneratorClass(descriptor, params).Generate(&printer);
+}
+
+void FileGenerator::GenerateSiblings(const string& package_dir,
+ GeneratorContext* output_directory,
+ vector<string>* file_list) {
+ if (params_.java_multiple_files(file_->name())) {
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ GenerateSibling<MessageGenerator>(package_dir, java_package_,
+ file_->message_type(i),
+ output_directory, file_list, params_);
+ }
+
+ if (params_.java_enum_style()) {
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ GenerateSibling<EnumGenerator>(package_dir, java_package_,
+ file_->enum_type(i),
+ output_directory, file_list, params_);
+ }
+ }
+ }
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.h
new file mode 100644
index 0000000000..217eafe2a8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_file.h
@@ -0,0 +1,94 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_FILE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_FILE_H__
+
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+
+namespace google {
+namespace protobuf {
+ class FileDescriptor; // descriptor.h
+ namespace io {
+ class Printer; // printer.h
+ }
+ namespace compiler {
+ class GeneratorContext; // code_generator.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class FileGenerator {
+ public:
+ explicit FileGenerator(const FileDescriptor* file, const Params& params);
+ ~FileGenerator();
+
+ // Checks for problems that would otherwise lead to cryptic compile errors.
+ // Returns true if there are no problems, or writes an error description to
+ // the given string and returns false otherwise.
+ bool Validate(string* error);
+
+ void Generate(io::Printer* printer);
+
+ // If we aren't putting everything into one file, this will write all the
+ // files other than the outer file (i.e. one for each message, enum, and
+ // service type).
+ void GenerateSiblings(const string& package_dir,
+ GeneratorContext* output_directory,
+ vector<string>* file_list);
+
+ const string& java_package() { return java_package_; }
+ const string& classname() { return classname_; }
+
+ private:
+ const FileDescriptor* file_;
+ const Params& params_;
+ string java_package_;
+ string classname_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_FILE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.cc
new file mode 100644
index 0000000000..7c3a04212f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.cc
@@ -0,0 +1,230 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+#include <google/protobuf/compiler/javanano/javanano_generator.h>
+#include <google/protobuf/compiler/javanano/javanano_file.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+namespace {
+
+string TrimString(const string& s) {
+ string::size_type start = s.find_first_not_of(" \n\r\t");
+ if (start == string::npos) {
+ return "";
+ }
+ string::size_type end = s.find_last_not_of(" \n\r\t") + 1;
+ return s.substr(start, end - start);
+}
+
+} // namespace
+
+void UpdateParamsRecursively(Params& params,
+ const FileDescriptor* file) {
+ // Add any parameters for this file
+ if (file->options().has_java_outer_classname()) {
+ params.set_java_outer_classname(
+ file->name(), file->options().java_outer_classname());
+ }
+ if (file->options().has_java_package()) {
+ string result = file->options().java_package();
+ if (!result.empty()) {
+ result += ".";
+ }
+ result += "nano";
+ params.set_java_package(
+ file->name(), result);
+ }
+ if (file->options().has_java_multiple_files()) {
+ params.set_java_multiple_files(
+ file->name(), file->options().java_multiple_files());
+ }
+
+ // Loop through all dependent files recursively
+ // adding dep
+ for (int i = 0; i < file->dependency_count(); i++) {
+ UpdateParamsRecursively(params, file->dependency(i));
+ }
+}
+
+JavaNanoGenerator::JavaNanoGenerator() {}
+JavaNanoGenerator::~JavaNanoGenerator() {}
+
+bool JavaNanoGenerator::Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* output_directory,
+ string* error) const {
+ vector<pair<string, string> > options;
+
+ ParseGeneratorParameter(parameter, &options);
+
+ // -----------------------------------------------------------------
+ // parse generator options
+
+ // Name a file where we will write a list of generated file names, one
+ // per line.
+ string output_list_file;
+ Params params(file->name());
+
+ // Update per file params
+ UpdateParamsRecursively(params, file);
+
+ // Replace any existing options with ones from command line
+ for (int i = 0; i < options.size(); i++) {
+ string option_name = TrimString(options[i].first);
+ string option_value = TrimString(options[i].second);
+ if (option_name == "output_list_file") {
+ output_list_file = option_value;
+ } else if (option_name == "java_package") {
+ vector<string> parts;
+ SplitStringUsing(option_value, "|", &parts);
+ if (parts.size() != 2) {
+ *error = "Bad java_package, expecting filename|PackageName found '"
+ + option_value + "'";
+ return false;
+ }
+ params.set_java_package(parts[0], parts[1]);
+ } else if (option_name == "java_outer_classname") {
+ vector<string> parts;
+ SplitStringUsing(option_value, "|", &parts);
+ if (parts.size() != 2) {
+ *error = "Bad java_outer_classname, "
+ "expecting filename|ClassName found '"
+ + option_value + "'";
+ return false;
+ }
+ params.set_java_outer_classname(parts[0], parts[1]);
+ } else if (option_name == "store_unknown_fields") {
+ params.set_store_unknown_fields(option_value == "true");
+ } else if (option_name == "java_multiple_files") {
+ params.set_override_java_multiple_files(option_value == "true");
+ } else if (option_name == "java_nano_generate_has") {
+ params.set_generate_has(option_value == "true");
+ } else if (option_name == "enum_style") {
+ params.set_java_enum_style(option_value == "java");
+ } else if (option_name == "optional_field_style") {
+ params.set_optional_field_accessors(option_value == "accessors");
+ params.set_use_reference_types_for_primitives(option_value == "reftypes"
+ || option_value == "reftypes_compat_mode");
+ params.set_reftypes_primitive_enums(
+ option_value == "reftypes_compat_mode");
+ if (option_value == "reftypes_compat_mode") {
+ params.set_generate_clear(false);
+ }
+ } else if (option_name == "generate_equals") {
+ params.set_generate_equals(option_value == "true");
+ } else if (option_name == "ignore_services") {
+ params.set_ignore_services(option_value == "true");
+ } else if (option_name == "parcelable_messages") {
+ params.set_parcelable_messages(option_value == "true");
+ } else if (option_name == "generate_clone") {
+ params.set_generate_clone(option_value == "true");
+ } else if (option_name == "generate_intdefs") {
+ params.set_generate_intdefs(option_value == "true");
+ } else if (option_name == "generate_clear") {
+ params.set_generate_clear(option_value == "true");
+ } else {
+ *error = "Ignore unknown javanano generator option: " + option_name;
+ }
+ }
+
+ // Check illegal parameter combinations
+ // Note: the enum-like optional_field_style generator param ensures
+ // that we can never have illegal combinations of field styles
+ // (e.g. reftypes and accessors can't be on at the same time).
+ if (params.generate_has()
+ && (params.optional_field_accessors()
+ || params.use_reference_types_for_primitives())) {
+ error->assign("java_nano_generate_has=true cannot be used in conjunction"
+ " with optional_field_style=accessors or optional_field_style=reftypes");
+ return false;
+ }
+
+ // -----------------------------------------------------------------
+
+ FileGenerator file_generator(file, params);
+ if (!file_generator.Validate(error)) {
+ return false;
+ }
+
+ string package_dir =
+ StringReplace(file_generator.java_package(), ".", "/", true);
+ if (!package_dir.empty()) package_dir += "/";
+
+ vector<string> all_files;
+
+ if (IsOuterClassNeeded(params, file)) {
+ string java_filename = package_dir;
+ java_filename += file_generator.classname();
+ java_filename += ".java";
+ all_files.push_back(java_filename);
+
+ // Generate main java file.
+ scoped_ptr<io::ZeroCopyOutputStream> output(
+ output_directory->Open(java_filename));
+ io::Printer printer(output.get(), '$');
+ file_generator.Generate(&printer);
+ }
+
+ // Generate sibling files.
+ file_generator.GenerateSiblings(package_dir, output_directory, &all_files);
+
+ // Generate output list if requested.
+ if (!output_list_file.empty()) {
+ // Generate output list. This is just a simple text file placed in a
+ // deterministic location which lists the .java files being generated.
+ scoped_ptr<io::ZeroCopyOutputStream> srclist_raw_output(
+ output_directory->Open(output_list_file));
+ io::Printer srclist_printer(srclist_raw_output.get(), '$');
+ for (int i = 0; i < all_files.size(); i++) {
+ srclist_printer.Print("$filename$\n", "filename", all_files[i]);
+ }
+ }
+
+ return true;
+}
+
+} // namespace java
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.h
new file mode 100644
index 0000000000..6f9f7f2a4a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_generator.h
@@ -0,0 +1,72 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+//
+// Generates Java nano code for a given .proto file.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_NANO_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_NANO_GENERATOR_H__
+
+#include <string>
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+// CodeGenerator implementation which generates Java nano code. If you create your
+// own protocol compiler binary and you want it to support Java output for the
+// nano runtime, you can do so by registering an instance of this CodeGenerator with
+// the CommandLineInterface in your main() function.
+class LIBPROTOC_EXPORT JavaNanoGenerator : public CodeGenerator {
+ public:
+ JavaNanoGenerator();
+ ~JavaNanoGenerator();
+
+ // implements CodeGenerator ----------------------------------------
+ bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* output_directory,
+ string* error) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(JavaNanoGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_NANO_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.cc
new file mode 100644
index 0000000000..02811a24dc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.cc
@@ -0,0 +1,591 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <limits>
+#include <vector>
+
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/hash.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+const char kThickSeparator[] =
+ "// ===================================================================\n";
+const char kThinSeparator[] =
+ "// -------------------------------------------------------------------\n";
+
+class RenameKeywords {
+ private:
+ hash_set<string> java_keywords_set_;
+
+ public:
+ RenameKeywords() {
+ static const char* kJavaKeywordsList[] = {
+ // Reserved Java Keywords
+ "abstract", "assert", "boolean", "break", "byte", "case", "catch",
+ "char", "class", "const", "continue", "default", "do", "double", "else",
+ "enum", "extends", "final", "finally", "float", "for", "goto", "if",
+ "implements", "import", "instanceof", "int", "interface", "long",
+ "native", "new", "package", "private", "protected", "public", "return",
+ "short", "static", "strictfp", "super", "switch", "synchronized",
+ "this", "throw", "throws", "transient", "try", "void", "volatile", "while",
+
+ // Reserved Keywords for Literals
+ "false", "null", "true"
+ };
+
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(kJavaKeywordsList); i++) {
+ java_keywords_set_.insert(kJavaKeywordsList[i]);
+ }
+ }
+
+ // Used to rename the a field name if it's a java keyword. Specifically
+ // this is used to rename the ["name"] or ["capitalized_name"] field params.
+ // (http://docs.oracle.com/javase/tutorial/java/nutsandbolts/_keywords.html)
+ string RenameJavaKeywordsImpl(const string& input) {
+ string result = input;
+
+ if (java_keywords_set_.find(result) != java_keywords_set_.end()) {
+ result += "_";
+ }
+
+ return result;
+ }
+
+};
+
+static RenameKeywords sRenameKeywords;
+
+namespace {
+
+const char* kDefaultPackage = "";
+
+const string& FieldName(const FieldDescriptor* field) {
+ // Groups are hacky: The name of the field is just the lower-cased name
+ // of the group type. In Java, though, we would like to retain the original
+ // capitalization of the type name.
+ if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ return field->message_type()->name();
+ } else {
+ return field->name();
+ }
+}
+
+string UnderscoresToCamelCaseImpl(const string& input, bool cap_next_letter) {
+ string result;
+ // Note: I distrust ctype.h due to locales.
+ for (int i = 0; i < input.size(); i++) {
+ if ('a' <= input[i] && input[i] <= 'z') {
+ if (cap_next_letter) {
+ result += input[i] + ('A' - 'a');
+ } else {
+ result += input[i];
+ }
+ cap_next_letter = false;
+ } else if ('A' <= input[i] && input[i] <= 'Z') {
+ if (i == 0 && !cap_next_letter) {
+ // Force first letter to lower-case unless explicitly told to
+ // capitalize it.
+ result += input[i] + ('a' - 'A');
+ } else {
+ // Capital letters after the first are left as-is.
+ result += input[i];
+ }
+ cap_next_letter = false;
+ } else if ('0' <= input[i] && input[i] <= '9') {
+ result += input[i];
+ cap_next_letter = true;
+ } else {
+ cap_next_letter = true;
+ }
+ }
+ return result;
+}
+
+} // namespace
+
+string UnderscoresToCamelCase(const FieldDescriptor* field) {
+ return UnderscoresToCamelCaseImpl(FieldName(field), false);
+}
+
+string UnderscoresToCapitalizedCamelCase(const FieldDescriptor* field) {
+ return UnderscoresToCamelCaseImpl(FieldName(field), true);
+}
+
+string UnderscoresToCamelCase(const MethodDescriptor* method) {
+ return UnderscoresToCamelCaseImpl(method->name(), false);
+}
+
+string UnderscoresToCamelCase(const OneofDescriptor* oneof) {
+ return UnderscoresToCamelCaseImpl(oneof->name(), false);
+}
+
+string UnderscoresToCapitalizedCamelCase(const OneofDescriptor* oneof) {
+ return UnderscoresToCamelCaseImpl(oneof->name(), true);
+}
+
+string RenameJavaKeywords(const string& input) {
+ return sRenameKeywords.RenameJavaKeywordsImpl(input);
+}
+
+string StripProto(const string& filename) {
+ if (HasSuffixString(filename, ".protodevel")) {
+ return StripSuffixString(filename, ".protodevel");
+ } else {
+ return StripSuffixString(filename, ".proto");
+ }
+}
+
+string FileClassName(const Params& params, const FileDescriptor* file) {
+ if (params.has_java_outer_classname(file->name())) {
+ return params.java_outer_classname(file->name());
+ } else {
+ // Use the filename itself with underscores removed
+ // and a CamelCase style name.
+ string basename;
+ string::size_type last_slash = file->name().find_last_of('/');
+ if (last_slash == string::npos) {
+ basename = file->name();
+ } else {
+ basename = file->name().substr(last_slash + 1);
+ }
+ return UnderscoresToCamelCaseImpl(StripProto(basename), true);
+ }
+}
+
+string FileJavaPackage(const Params& params, const FileDescriptor* file) {
+ if (params.has_java_package(file->name())) {
+ return params.java_package(file->name());
+ } else {
+ string result = kDefaultPackage;
+ if (!file->package().empty()) {
+ if (!result.empty()) result += '.';
+ result += file->package();
+ }
+
+ if (!result.empty()) {
+ result += ".";
+ }
+ result += "nano";
+
+ return result;
+ }
+}
+
+bool IsOuterClassNeeded(const Params& params, const FileDescriptor* file) {
+ // If java_multiple_files is false, the outer class is always needed.
+ if (!params.java_multiple_files(file->name())) {
+ return true;
+ }
+
+ // File-scope extensions need the outer class as the scope.
+ if (file->extension_count() != 0) {
+ return true;
+ }
+
+ // If container interfaces are not generated, file-scope enums need the
+ // outer class as the scope.
+ if (file->enum_type_count() != 0 && !params.java_enum_style()) {
+ return true;
+ }
+
+ return false;
+}
+
+string ToJavaName(const Params& params, const string& name, bool is_class,
+ const Descriptor* parent, const FileDescriptor* file) {
+ string result;
+ if (parent != NULL) {
+ result.append(ClassName(params, parent));
+ } else if (is_class && params.java_multiple_files(file->name())) {
+ result.append(FileJavaPackage(params, file));
+ } else {
+ result.append(ClassName(params, file));
+ }
+ if (!result.empty()) result.append(1, '.');
+ result.append(RenameJavaKeywords(name));
+ return result;
+}
+
+string ClassName(const Params& params, const FileDescriptor* descriptor) {
+ string result = FileJavaPackage(params, descriptor);
+ if (!result.empty()) result += '.';
+ result += FileClassName(params, descriptor);
+ return result;
+}
+
+string ClassName(const Params& params, const EnumDescriptor* descriptor) {
+ const Descriptor* parent = descriptor->containing_type();
+ // When using Java enum style, an enum's class name contains the enum name.
+ // Use the standard ToJavaName translation.
+ if (params.java_enum_style()) {
+ return ToJavaName(params, descriptor->name(), true, parent,
+ descriptor->file());
+ }
+ // Otherwise the enum members are accessed from the enclosing class.
+ if (parent != NULL) {
+ return ClassName(params, parent);
+ } else {
+ return ClassName(params, descriptor->file());
+ }
+}
+
+string FieldConstantName(const FieldDescriptor *field) {
+ string name = field->name() + "_FIELD_NUMBER";
+ UpperString(&name);
+ return name;
+}
+
+string FieldDefaultConstantName(const FieldDescriptor *field) {
+ return "_" + RenameJavaKeywords(UnderscoresToCamelCase(field)) + "Default";
+}
+
+void PrintFieldComment(io::Printer* printer, const FieldDescriptor* field) {
+ // We don't want to print group bodies so we cut off after the first line
+ // (the second line for extensions).
+ string def = field->DebugString();
+ string::size_type first_line_end = def.find_first_of('\n');
+ printer->Print("// $def$\n",
+ "def", def.substr(0, first_line_end));
+ if (field->is_extension()) {
+ string::size_type second_line_start = first_line_end + 1;
+ string::size_type second_line_length =
+ def.find('\n', second_line_start) - second_line_start;
+ printer->Print("// $def$\n",
+ "def", def.substr(second_line_start, second_line_length));
+ }
+}
+
+JavaType GetJavaType(FieldDescriptor::Type field_type) {
+ switch (field_type) {
+ case FieldDescriptor::TYPE_INT32:
+ case FieldDescriptor::TYPE_UINT32:
+ case FieldDescriptor::TYPE_SINT32:
+ case FieldDescriptor::TYPE_FIXED32:
+ case FieldDescriptor::TYPE_SFIXED32:
+ return JAVATYPE_INT;
+
+ case FieldDescriptor::TYPE_INT64:
+ case FieldDescriptor::TYPE_UINT64:
+ case FieldDescriptor::TYPE_SINT64:
+ case FieldDescriptor::TYPE_FIXED64:
+ case FieldDescriptor::TYPE_SFIXED64:
+ return JAVATYPE_LONG;
+
+ case FieldDescriptor::TYPE_FLOAT:
+ return JAVATYPE_FLOAT;
+
+ case FieldDescriptor::TYPE_DOUBLE:
+ return JAVATYPE_DOUBLE;
+
+ case FieldDescriptor::TYPE_BOOL:
+ return JAVATYPE_BOOLEAN;
+
+ case FieldDescriptor::TYPE_STRING:
+ return JAVATYPE_STRING;
+
+ case FieldDescriptor::TYPE_BYTES:
+ return JAVATYPE_BYTES;
+
+ case FieldDescriptor::TYPE_ENUM:
+ return JAVATYPE_ENUM;
+
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_MESSAGE:
+ return JAVATYPE_MESSAGE;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return JAVATYPE_INT;
+}
+
+string PrimitiveTypeName(JavaType type) {
+ switch (type) {
+ case JAVATYPE_INT : return "int";
+ case JAVATYPE_LONG : return "long";
+ case JAVATYPE_FLOAT : return "float";
+ case JAVATYPE_DOUBLE : return "double";
+ case JAVATYPE_BOOLEAN: return "boolean";
+ case JAVATYPE_STRING : return "java.lang.String";
+ case JAVATYPE_BYTES : return "byte[]";
+ case JAVATYPE_ENUM : return "int";
+ case JAVATYPE_MESSAGE: return "";
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return "";
+}
+
+string BoxedPrimitiveTypeName(JavaType type) {
+ switch (type) {
+ case JAVATYPE_INT : return "java.lang.Integer";
+ case JAVATYPE_LONG : return "java.lang.Long";
+ case JAVATYPE_FLOAT : return "java.lang.Float";
+ case JAVATYPE_DOUBLE : return "java.lang.Double";
+ case JAVATYPE_BOOLEAN: return "java.lang.Boolean";
+ case JAVATYPE_STRING : return "java.lang.String";
+ case JAVATYPE_BYTES : return "byte[]";
+ case JAVATYPE_ENUM : return "java.lang.Integer";
+ case JAVATYPE_MESSAGE: return "";
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return "";
+}
+
+string EmptyArrayName(const Params& params, const FieldDescriptor* field) {
+ switch (GetJavaType(field)) {
+ case JAVATYPE_INT : return "com.google.protobuf.nano.WireFormatNano.EMPTY_INT_ARRAY";
+ case JAVATYPE_LONG : return "com.google.protobuf.nano.WireFormatNano.EMPTY_LONG_ARRAY";
+ case JAVATYPE_FLOAT : return "com.google.protobuf.nano.WireFormatNano.EMPTY_FLOAT_ARRAY";
+ case JAVATYPE_DOUBLE : return "com.google.protobuf.nano.WireFormatNano.EMPTY_DOUBLE_ARRAY";
+ case JAVATYPE_BOOLEAN: return "com.google.protobuf.nano.WireFormatNano.EMPTY_BOOLEAN_ARRAY";
+ case JAVATYPE_STRING : return "com.google.protobuf.nano.WireFormatNano.EMPTY_STRING_ARRAY";
+ case JAVATYPE_BYTES : return "com.google.protobuf.nano.WireFormatNano.EMPTY_BYTES_ARRAY";
+ case JAVATYPE_ENUM : return "com.google.protobuf.nano.WireFormatNano.EMPTY_INT_ARRAY";
+ case JAVATYPE_MESSAGE: return ClassName(params, field->message_type()) + ".EMPTY_ARRAY";
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return "";
+}
+
+string DefaultValue(const Params& params, const FieldDescriptor* field) {
+ if (field->label() == FieldDescriptor::LABEL_REPEATED) {
+ return EmptyArrayName(params, field);
+ }
+
+ if (params.use_reference_types_for_primitives()) {
+ if (params.reftypes_primitive_enums()
+ && field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ return "Integer.MIN_VALUE";
+ }
+ return "null";
+ }
+
+ // Switch on cpp_type since we need to know which default_value_* method
+ // of FieldDescriptor to call.
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return SimpleItoa(field->default_value_int32());
+ case FieldDescriptor::CPPTYPE_UINT32:
+ // Need to print as a signed int since Java has no unsigned.
+ return SimpleItoa(static_cast<int32>(field->default_value_uint32()));
+ case FieldDescriptor::CPPTYPE_INT64:
+ return SimpleItoa(field->default_value_int64()) + "L";
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return SimpleItoa(static_cast<int64>(field->default_value_uint64())) +
+ "L";
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value = field->default_value_double();
+ if (value == numeric_limits<double>::infinity()) {
+ return "Double.POSITIVE_INFINITY";
+ } else if (value == -numeric_limits<double>::infinity()) {
+ return "Double.NEGATIVE_INFINITY";
+ } else if (value != value) {
+ return "Double.NaN";
+ } else {
+ return SimpleDtoa(value) + "D";
+ }
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ float value = field->default_value_float();
+ if (value == numeric_limits<float>::infinity()) {
+ return "Float.POSITIVE_INFINITY";
+ } else if (value == -numeric_limits<float>::infinity()) {
+ return "Float.NEGATIVE_INFINITY";
+ } else if (value != value) {
+ return "Float.NaN";
+ } else {
+ return SimpleFtoa(value) + "F";
+ }
+ }
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field->default_value_bool() ? "true" : "false";
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (!field->default_value_string().empty()) {
+ // Point it to the static final in the generated code.
+ return FieldDefaultConstantName(field);
+ } else {
+ if (field->type() == FieldDescriptor::TYPE_BYTES) {
+ return "com.google.protobuf.nano.WireFormatNano.EMPTY_BYTES";
+ } else {
+ return "\"\"";
+ }
+ }
+
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return ClassName(params, field->enum_type()) + "." +
+ RenameJavaKeywords(field->default_value_enum()->name());
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return "null";
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return "";
+}
+
+
+static const char* kBitMasks[] = {
+ "0x00000001",
+ "0x00000002",
+ "0x00000004",
+ "0x00000008",
+ "0x00000010",
+ "0x00000020",
+ "0x00000040",
+ "0x00000080",
+
+ "0x00000100",
+ "0x00000200",
+ "0x00000400",
+ "0x00000800",
+ "0x00001000",
+ "0x00002000",
+ "0x00004000",
+ "0x00008000",
+
+ "0x00010000",
+ "0x00020000",
+ "0x00040000",
+ "0x00080000",
+ "0x00100000",
+ "0x00200000",
+ "0x00400000",
+ "0x00800000",
+
+ "0x01000000",
+ "0x02000000",
+ "0x04000000",
+ "0x08000000",
+ "0x10000000",
+ "0x20000000",
+ "0x40000000",
+ "0x80000000",
+};
+
+string GetBitFieldName(int index) {
+ string var_name = "bitField";
+ var_name += SimpleItoa(index);
+ var_name += "_";
+ return var_name;
+}
+
+string GetBitFieldNameForBit(int bit_index) {
+ return GetBitFieldName(bit_index / 32);
+}
+
+string GenerateGetBit(int bit_index) {
+ string var_name = GetBitFieldNameForBit(bit_index);
+ int bit_in_var_index = bit_index % 32;
+
+ string mask = kBitMasks[bit_in_var_index];
+ string result = "((" + var_name + " & " + mask + ") != 0)";
+ return result;
+}
+
+string GenerateSetBit(int bit_index) {
+ string var_name = GetBitFieldNameForBit(bit_index);
+ int bit_in_var_index = bit_index % 32;
+
+ string mask = kBitMasks[bit_in_var_index];
+ string result = var_name + " |= " + mask;
+ return result;
+}
+
+string GenerateClearBit(int bit_index) {
+ string var_name = GetBitFieldNameForBit(bit_index);
+ int bit_in_var_index = bit_index % 32;
+
+ string mask = kBitMasks[bit_in_var_index];
+ string result = var_name + " = (" + var_name + " & ~" + mask + ")";
+ return result;
+}
+
+string GenerateDifferentBit(int bit_index) {
+ string var_name = GetBitFieldNameForBit(bit_index);
+ int bit_in_var_index = bit_index % 32;
+
+ string mask = kBitMasks[bit_in_var_index];
+ string result = "((" + var_name + " & " + mask
+ + ") != (other." + var_name + " & " + mask + "))";
+ return result;
+}
+
+void SetBitOperationVariables(const string name,
+ int bitIndex, map<string, string>* variables) {
+ (*variables)["get_" + name] = GenerateGetBit(bitIndex);
+ (*variables)["set_" + name] = GenerateSetBit(bitIndex);
+ (*variables)["clear_" + name] = GenerateClearBit(bitIndex);
+ (*variables)["different_" + name] = GenerateDifferentBit(bitIndex);
+}
+
+bool HasMapField(const Descriptor* descriptor) {
+ for (int i = 0; i < descriptor->field_count(); ++i) {
+ const FieldDescriptor* field = descriptor->field(i);
+ if (field->type() == FieldDescriptor::TYPE_MESSAGE &&
+ IsMapEntry(field->message_type())) {
+ return true;
+ }
+ }
+ return false;
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.h
new file mode 100644
index 0000000000..014c85aee3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_helpers.h
@@ -0,0 +1,199 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_HELPERS_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_HELPERS_H__
+
+#include <string>
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/printer.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+// Commonly-used separator comments. Thick is a line of '=', thin is a line
+// of '-'.
+extern const char kThickSeparator[];
+extern const char kThinSeparator[];
+
+// Converts the field's name to camel-case, e.g. "foo_bar_baz" becomes
+// "fooBarBaz" or "FooBarBaz", respectively.
+string UnderscoresToCamelCase(const FieldDescriptor* field);
+string UnderscoresToCamelCase(const OneofDescriptor* oneof);
+string UnderscoresToCapitalizedCamelCase(const FieldDescriptor* field);
+string UnderscoresToCapitalizedCamelCase(const OneofDescriptor* oneof);
+
+// Appends an "_" to the end of a field where the name is a reserved java
+// keyword. For example int32 public = 1 will generate int public_.
+string RenameJavaKeywords(const string& input);
+
+// Similar, but for method names. (Typically, this merely has the effect
+// of lower-casing the first letter of the name.)
+string UnderscoresToCamelCase(const MethodDescriptor* method);
+
+// Strips ".proto" or ".protodevel" from the end of a filename.
+string StripProto(const string& filename);
+
+// Gets the unqualified class name for the file. Each .proto file becomes a
+// single Java class, with all its contents nested in that class.
+string FileClassName(const Params& params, const FileDescriptor* file);
+
+// Returns the file's Java package name.
+string FileJavaPackage(const Params& params, const FileDescriptor* file);
+
+// Returns whether the Java outer class is needed, i.e. whether the option
+// java_multiple_files is false, or the proto file contains any file-scope
+// enums/extensions.
+bool IsOuterClassNeeded(const Params& params, const FileDescriptor* file);
+
+// Converts the given simple name of a proto entity to its fully-qualified name
+// in the Java namespace, given that it is in the given file enclosed in the
+// given parent message (or NULL for file-scope entities). Whether the file's
+// outer class name should be included in the return value depends on factors
+// inferrable from the given arguments, including is_class which indicates
+// whether the entity translates to a Java class.
+string ToJavaName(const Params& params, const string& name, bool is_class,
+ const Descriptor* parent, const FileDescriptor* file);
+
+// These return the fully-qualified class name corresponding to the given
+// descriptor.
+inline string ClassName(const Params& params, const Descriptor* descriptor) {
+ return ToJavaName(params, descriptor->name(), true,
+ descriptor->containing_type(), descriptor->file());
+}
+string ClassName(const Params& params, const EnumDescriptor* descriptor);
+inline string ClassName(const Params& params,
+ const ServiceDescriptor* descriptor) {
+ return ToJavaName(params, descriptor->name(), true, NULL, descriptor->file());
+}
+inline string ExtensionIdentifierName(const Params& params,
+ const FieldDescriptor* descriptor) {
+ return ToJavaName(params, descriptor->name(), false,
+ descriptor->extension_scope(), descriptor->file());
+}
+string ClassName(const Params& params, const FileDescriptor* descriptor);
+
+// Get the unqualified name that should be used for a field's field
+// number constant.
+string FieldConstantName(const FieldDescriptor *field);
+
+string FieldDefaultConstantName(const FieldDescriptor *field);
+
+// Print the field's proto-syntax definition as a comment.
+void PrintFieldComment(io::Printer* printer, const FieldDescriptor* field);
+
+enum JavaType {
+ JAVATYPE_INT,
+ JAVATYPE_LONG,
+ JAVATYPE_FLOAT,
+ JAVATYPE_DOUBLE,
+ JAVATYPE_BOOLEAN,
+ JAVATYPE_STRING,
+ JAVATYPE_BYTES,
+ JAVATYPE_ENUM,
+ JAVATYPE_MESSAGE
+};
+
+JavaType GetJavaType(FieldDescriptor::Type field_type);
+
+inline JavaType GetJavaType(const FieldDescriptor* field) {
+ return GetJavaType(field->type());
+}
+
+string PrimitiveTypeName(JavaType type);
+
+// Get the fully-qualified class name for a boxed primitive type, e.g.
+// "java.lang.Integer" for JAVATYPE_INT. Returns NULL for enum and message
+// types.
+string BoxedPrimitiveTypeName(JavaType type);
+
+string EmptyArrayName(const Params& params, const FieldDescriptor* field);
+
+string DefaultValue(const Params& params, const FieldDescriptor* field);
+
+
+// Methods for shared bitfields.
+
+// Gets the name of the shared bitfield for the given field index.
+string GetBitFieldName(int index);
+
+// Gets the name of the shared bitfield for the given bit index.
+// Effectively, GetBitFieldName(bit_index / 32)
+string GetBitFieldNameForBit(int bit_index);
+
+// Generates the java code for the expression that returns whether the bit at
+// the given bit index is set.
+// Example: "((bitField1_ & 0x04000000) != 0)"
+string GenerateGetBit(int bit_index);
+
+// Generates the java code for the expression that sets the bit at the given
+// bit index.
+// Example: "bitField1_ |= 0x04000000"
+string GenerateSetBit(int bit_index);
+
+// Generates the java code for the expression that clears the bit at the given
+// bit index.
+// Example: "bitField1_ = (bitField1_ & ~0x04000000)"
+string GenerateClearBit(int bit_index);
+
+// Generates the java code for the expression that returns whether the bit at
+// the given bit index contains different values in the current object and
+// another object accessible via the variable 'other'.
+// Example: "((bitField1_ & 0x04000000) != (other.bitField1_ & 0x04000000))"
+string GenerateDifferentBit(int bit_index);
+
+// Sets the 'get_*', 'set_*', 'clear_*' and 'different_*' variables, where * is
+// the given name of the bit, to the appropriate Java expressions for the given
+// bit index.
+void SetBitOperationVariables(const string name,
+ int bitIndex, map<string, string>* variables);
+
+inline bool IsMapEntry(const Descriptor* descriptor) {
+ // TODO(liujisi): Add an option to turn on maps for proto2 syntax as well.
+ return descriptor->options().map_entry() &&
+ descriptor->file()->syntax() == FileDescriptor::SYNTAX_PROTO3;
+}
+
+bool HasMapField(const Descriptor* descriptor);
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_HELPERS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.cc
new file mode 100644
index 0000000000..83b2b0ce8f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.cc
@@ -0,0 +1,186 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <google/protobuf/compiler/javanano/javanano_map_field.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+namespace {
+
+string TypeName(const Params& params, const FieldDescriptor* field,
+ bool boxed) {
+ JavaType java_type = GetJavaType(field);
+ switch (java_type) {
+ case JAVATYPE_MESSAGE:
+ return ClassName(params, field->message_type());
+ case JAVATYPE_INT:
+ case JAVATYPE_LONG:
+ case JAVATYPE_FLOAT:
+ case JAVATYPE_DOUBLE:
+ case JAVATYPE_BOOLEAN:
+ case JAVATYPE_STRING:
+ case JAVATYPE_BYTES:
+ case JAVATYPE_ENUM:
+ if (boxed) {
+ return BoxedPrimitiveTypeName(java_type);
+ } else {
+ return PrimitiveTypeName(java_type);
+ }
+ // No default because we want the compiler to complain if any new JavaTypes
+ // are added..
+ }
+
+ GOOGLE_LOG(FATAL) << "should not reach here.";
+ return "";
+}
+
+const FieldDescriptor* KeyField(const FieldDescriptor* descriptor) {
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, descriptor->type());
+ const Descriptor* message = descriptor->message_type();
+ GOOGLE_CHECK(message->options().map_entry());
+ return message->FindFieldByName("key");
+}
+
+const FieldDescriptor* ValueField(const FieldDescriptor* descriptor) {
+ GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, descriptor->type());
+ const Descriptor* message = descriptor->message_type();
+ GOOGLE_CHECK(message->options().map_entry());
+ return message->FindFieldByName("value");
+}
+
+void SetMapVariables(const Params& params,
+ const FieldDescriptor* descriptor, map<string, string>* variables) {
+ const FieldDescriptor* key = KeyField(descriptor);
+ const FieldDescriptor* value = ValueField(descriptor);
+ (*variables)["name"] =
+ RenameJavaKeywords(UnderscoresToCamelCase(descriptor));
+ (*variables)["number"] = SimpleItoa(descriptor->number());
+ (*variables)["key_type"] = TypeName(params, key, false);
+ (*variables)["boxed_key_type"] = TypeName(params,key, true);
+ (*variables)["key_desc_type"] =
+ "TYPE_" + ToUpper(FieldDescriptor::TypeName(key->type()));
+ (*variables)["key_tag"] = SimpleItoa(internal::WireFormat::MakeTag(key));
+ (*variables)["value_type"] = TypeName(params, value, false);
+ (*variables)["boxed_value_type"] = TypeName(params, value, true);
+ (*variables)["value_desc_type"] =
+ "TYPE_" + ToUpper(FieldDescriptor::TypeName(value->type()));
+ (*variables)["value_tag"] = SimpleItoa(internal::WireFormat::MakeTag(value));
+ (*variables)["type_parameters"] =
+ (*variables)["boxed_key_type"] + ", " + (*variables)["boxed_value_type"];
+ (*variables)["value_default"] =
+ value->type() == FieldDescriptor::TYPE_MESSAGE
+ ? "new " + (*variables)["value_type"] + "()"
+ : "null";
+}
+} // namespace
+
+// ===================================================================
+MapFieldGenerator::MapFieldGenerator(const FieldDescriptor* descriptor,
+ const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetMapVariables(params, descriptor, &variables_);
+}
+
+MapFieldGenerator::~MapFieldGenerator() {}
+
+void MapFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /* unused lazy_init */) const {
+ printer->Print(variables_,
+ "public java.util.Map<$type_parameters$> $name$;\n");
+}
+
+void MapFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$ = null;\n");
+}
+
+void MapFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "this.$name$ = com.google.protobuf.nano.InternalNano.mergeMapEntry(\n"
+ " input, this.$name$, mapFactory,\n"
+ " com.google.protobuf.nano.InternalNano.$key_desc_type$,\n"
+ " com.google.protobuf.nano.InternalNano.$value_desc_type$,\n"
+ " $value_default$,\n"
+ " $key_tag$, $value_tag$);\n"
+ "\n");
+}
+
+void MapFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null) {\n"
+ " com.google.protobuf.nano.InternalNano.serializeMapField(\n"
+ " output, this.$name$, $number$,\n"
+ " com.google.protobuf.nano.InternalNano.$key_desc_type$,\n"
+ " com.google.protobuf.nano.InternalNano.$value_desc_type$);\n"
+ "}\n");
+}
+
+void MapFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null) {\n"
+ " size += com.google.protobuf.nano.InternalNano.computeMapFieldSize(\n"
+ " this.$name$, $number$,\n"
+ " com.google.protobuf.nano.InternalNano.$key_desc_type$,\n"
+ " com.google.protobuf.nano.InternalNano.$value_desc_type$);\n"
+ "}\n");
+}
+
+void MapFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!com.google.protobuf.nano.InternalNano.equals(\n"
+ " this.$name$, other.$name$)) {\n"
+ " return false;\n"
+ "}\n");
+}
+
+void MapFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = 31 * result +\n"
+ " com.google.protobuf.nano.InternalNano.hashCode(this.$name$);\n");
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.h
new file mode 100644
index 0000000000..c01bde3815
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_map_field.h
@@ -0,0 +1,70 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_MAP_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_MAP_FIELD_H__
+
+#include <map>
+#include <string>
+#include <vector>
+#include <google/protobuf/compiler/javanano/javanano_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class MapFieldGenerator : public FieldGenerator {
+ public:
+ explicit MapFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params);
+ ~MapFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MapFieldGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_MAP_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.cc
new file mode 100644
index 0000000000..a41da5ae33
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.cc
@@ -0,0 +1,676 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <google/protobuf/compiler/javanano/javanano_message.h>
+#include <google/protobuf/compiler/javanano/javanano_enum.h>
+#include <google/protobuf/compiler/javanano/javanano_extension.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/descriptor.pb.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+struct FieldOrderingByNumber {
+ inline bool operator()(const FieldDescriptor* a,
+ const FieldDescriptor* b) const {
+ return a->number() < b->number();
+ }
+};
+
+// Sort the fields of the given Descriptor by number into a new[]'d array
+// and return it.
+const FieldDescriptor** SortFieldsByNumber(const Descriptor* descriptor) {
+ const FieldDescriptor** fields =
+ new const FieldDescriptor*[descriptor->field_count()];
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ fields[i] = descriptor->field(i);
+ }
+ sort(fields, fields + descriptor->field_count(),
+ FieldOrderingByNumber());
+ return fields;
+}
+
+} // namespace
+
+// ===================================================================
+
+MessageGenerator::MessageGenerator(const Descriptor* descriptor, const Params& params)
+ : params_(params),
+ descriptor_(descriptor),
+ field_generators_(descriptor, params) {
+}
+
+MessageGenerator::~MessageGenerator() {}
+
+void MessageGenerator::GenerateStaticVariables(io::Printer* printer) {
+ // Generate static members for all nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // TODO(kenton): Reuse MessageGenerator objects?
+ if (IsMapEntry(descriptor_->nested_type(i))) continue;
+ MessageGenerator(descriptor_->nested_type(i), params_)
+ .GenerateStaticVariables(printer);
+ }
+}
+
+void MessageGenerator::GenerateStaticVariableInitializers(
+ io::Printer* printer) {
+ // Generate static member initializers for all nested types.
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ // TODO(kenton): Reuse MessageGenerator objects?
+ if (IsMapEntry(descriptor_->nested_type(i))) continue;
+ MessageGenerator(descriptor_->nested_type(i), params_)
+ .GenerateStaticVariableInitializers(printer);
+ }
+}
+
+void MessageGenerator::Generate(io::Printer* printer) {
+ if (!params_.store_unknown_fields() &&
+ (descriptor_->extension_count() != 0 || descriptor_->extension_range_count() != 0)) {
+ GOOGLE_LOG(FATAL) << "Extensions are only supported in NANO_RUNTIME if the "
+ "'store_unknown_fields' generator option is 'true'\n";
+ }
+
+ const string& file_name = descriptor_->file()->name();
+ bool is_own_file =
+ params_.java_multiple_files(file_name)
+ && descriptor_->containing_type() == NULL;
+
+ if (is_own_file) {
+ // Note: constants (from enums and fields requiring stored defaults, emitted in the loop below)
+ // may have the same names as constants in the nested classes. This causes Java warnings, but
+ // is not fatal, so we suppress those warnings here in the top-most class declaration.
+ printer->Print(
+ "\n"
+ "@SuppressWarnings(\"hiding\")\n"
+ "public final class $classname$ extends\n",
+ "classname", descriptor_->name());
+ } else {
+ printer->Print(
+ "\n"
+ "public static final class $classname$ extends\n",
+ "classname", descriptor_->name());
+ }
+ if (params_.store_unknown_fields() && params_.parcelable_messages()) {
+ printer->Print(
+ " com.google.protobuf.nano.android.ParcelableExtendableMessageNano<$classname$>",
+ "classname", descriptor_->name());
+ } else if (params_.store_unknown_fields()) {
+ printer->Print(
+ " com.google.protobuf.nano.ExtendableMessageNano<$classname$>",
+ "classname", descriptor_->name());
+ } else if (params_.parcelable_messages()) {
+ printer->Print(
+ " com.google.protobuf.nano.android.ParcelableMessageNano");
+ } else {
+ printer->Print(
+ " com.google.protobuf.nano.MessageNano");
+ }
+ if (params_.generate_clone()) {
+ printer->Print(" implements java.lang.Cloneable {\n");
+ } else {
+ printer->Print(" {\n");
+ }
+ printer->Indent();
+
+ if (params_.parcelable_messages()) {
+ printer->Print(
+ "\n"
+ "// Used by Parcelable\n"
+ "@SuppressWarnings({\"unused\"})\n"
+ "public static final android.os.Parcelable.Creator<$classname$> CREATOR =\n"
+ " new com.google.protobuf.nano.android.ParcelableMessageNanoCreator<\n"
+ " $classname$>($classname$.class);\n",
+ "classname", descriptor_->name());
+ }
+
+ // Nested types and extensions
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ ExtensionGenerator(descriptor_->extension(i), params_).Generate(printer);
+ }
+
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ EnumGenerator(descriptor_->enum_type(i), params_).Generate(printer);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ if (IsMapEntry(descriptor_->nested_type(i))) continue;
+ MessageGenerator(descriptor_->nested_type(i), params_).Generate(printer);
+ }
+
+ // oneof
+ map<string, string> vars;
+ vars["message_name"] = descriptor_->name();
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ const OneofDescriptor* oneof_desc = descriptor_->oneof_decl(i);
+ vars["oneof_name"] = UnderscoresToCamelCase(oneof_desc);
+ vars["oneof_capitalized_name"] =
+ UnderscoresToCapitalizedCamelCase(oneof_desc);
+ vars["oneof_index"] = SimpleItoa(oneof_desc->index());
+ // Oneof Constants
+ for (int j = 0; j < oneof_desc->field_count(); j++) {
+ const FieldDescriptor* field = oneof_desc->field(j);
+ vars["number"] = SimpleItoa(field->number());
+ vars["cap_field_name"] = ToUpper(field->name());
+ printer->Print(vars,
+ "public static final int $cap_field_name$_FIELD_NUMBER = $number$;\n");
+ }
+ // oneofCase_ and oneof_
+ printer->Print(vars,
+ "private int $oneof_name$Case_ = 0;\n"
+ "private java.lang.Object $oneof_name$_;\n");
+ printer->Print(vars,
+ "public int get$oneof_capitalized_name$Case() {\n"
+ " return this.$oneof_name$Case_;\n"
+ "}\n");
+ // Oneof clear
+ printer->Print(vars,
+ "public $message_name$ clear$oneof_capitalized_name$() {\n"
+ " this.$oneof_name$Case_ = 0;\n"
+ " this.$oneof_name$_ = null;\n"
+ " return this;\n"
+ "}\n");
+ }
+
+ // Lazy initialization of otherwise static final fields can help prevent the
+ // class initializer from being generated. We want to prevent it because it
+ // stops ProGuard from inlining any methods in this class into call sites and
+ // therefore reducing the method count. However, extensions are best kept as
+ // public static final fields with initializers, so with their existence we
+ // won't bother with lazy initialization.
+ bool lazy_init = descriptor_->extension_count() == 0;
+
+ // Empty array
+ if (lazy_init) {
+ printer->Print(
+ "\n"
+ "private static volatile $classname$[] _emptyArray;\n"
+ "public static $classname$[] emptyArray() {\n"
+ " // Lazily initializes the empty array\n"
+ " if (_emptyArray == null) {\n"
+ " synchronized (\n"
+ " com.google.protobuf.nano.InternalNano.LAZY_INIT_LOCK) {\n"
+ " if (_emptyArray == null) {\n"
+ " _emptyArray = new $classname$[0];\n"
+ " }\n"
+ " }\n"
+ " }\n"
+ " return _emptyArray;\n"
+ "}\n",
+ "classname", descriptor_->name());
+ } else {
+ printer->Print(
+ "\n"
+ "private static final $classname$[] EMPTY_ARRAY = {};\n"
+ "public static $classname$[] emptyArray() {\n"
+ " return EMPTY_ARRAY;\n"
+ "}\n",
+ "classname", descriptor_->name());
+ }
+
+ // Integers for bit fields
+ int totalInts = (field_generators_.total_bits() + 31) / 32;
+ if (totalInts > 0) {
+ printer->Print("\n");
+ for (int i = 0; i < totalInts; i++) {
+ printer->Print("private int $bit_field_name$;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+ }
+
+ // Fields and maybe their default values
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ printer->Print("\n");
+ PrintFieldComment(printer, descriptor_->field(i));
+ field_generators_.get(descriptor_->field(i)).GenerateMembers(
+ printer, lazy_init);
+ }
+
+ // Constructor, with lazy init code if needed
+ if (lazy_init && field_generators_.saved_defaults_needed()) {
+ printer->Print(
+ "\n"
+ "private static volatile boolean _classInitialized;\n"
+ "\n"
+ "public $classname$() {\n"
+ " // Lazily initializes the field defaults\n"
+ " if (!_classInitialized) {\n"
+ " synchronized (\n"
+ " com.google.protobuf.nano.InternalNano.LAZY_INIT_LOCK) {\n"
+ " if (!_classInitialized) {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+ printer->Indent();
+ printer->Indent();
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateInitSavedDefaultCode(printer);
+ }
+ printer->Outdent();
+ printer->Outdent();
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " _classInitialized = true;\n"
+ " }\n"
+ " }\n"
+ " }\n");
+ if (params_.generate_clear()) {
+ printer->Print(" clear();\n");
+ }
+ printer->Print("}\n");
+ } else {
+ printer->Print(
+ "\n"
+ "public $classname$() {\n",
+ "classname", descriptor_->name());
+ if (params_.generate_clear()) {
+ printer->Print(" clear();\n");
+ } else {
+ printer->Indent();
+ GenerateFieldInitializers(printer);
+ printer->Outdent();
+ }
+ printer->Print("}\n");
+ }
+
+ // Other methods in this class
+
+ GenerateClear(printer);
+
+ if (params_.generate_clone()) {
+ GenerateClone(printer);
+ }
+
+ if (params_.generate_equals()) {
+ GenerateEquals(printer);
+ GenerateHashCode(printer);
+ }
+
+ GenerateMessageSerializationMethods(printer);
+ GenerateMergeFromMethods(printer);
+ GenerateParseFromMethods(printer);
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+// ===================================================================
+
+void MessageGenerator::
+GenerateMessageSerializationMethods(io::Printer* printer) {
+ // Rely on the parent implementations of writeTo() and getSerializedSize()
+ // if there are no fields to serialize in this message.
+ if (descriptor_->field_count() == 0) {
+ return;
+ }
+
+ scoped_array<const FieldDescriptor*> sorted_fields(
+ SortFieldsByNumber(descriptor_));
+
+ printer->Print(
+ "\n"
+ "@Override\n"
+ "public void writeTo(com.google.protobuf.nano.CodedOutputByteBufferNano output)\n"
+ " throws java.io.IOException {\n");
+ printer->Indent();
+
+ // Output the fields in sorted order
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ GenerateSerializeOneField(printer, sorted_fields[i]);
+ }
+
+ // The parent implementation will write any unknown fields if necessary.
+ printer->Print(
+ "super.writeTo(output);\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+
+ // The parent implementation will get the serialized size for unknown
+ // fields if necessary.
+ printer->Print(
+ "\n"
+ "@Override\n"
+ "protected int computeSerializedSize() {\n"
+ " int size = super.computeSerializedSize();\n");
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(sorted_fields[i]).GenerateSerializedSizeCode(printer);
+ }
+
+ printer->Outdent();
+ printer->Print(
+ " return size;\n"
+ "}\n");
+}
+
+void MessageGenerator::GenerateMergeFromMethods(io::Printer* printer) {
+ scoped_array<const FieldDescriptor*> sorted_fields(
+ SortFieldsByNumber(descriptor_));
+
+ printer->Print(
+ "\n"
+ "@Override\n"
+ "public $classname$ mergeFrom(\n"
+ " com.google.protobuf.nano.CodedInputByteBufferNano input)\n"
+ " throws java.io.IOException {\n",
+ "classname", descriptor_->name());
+
+ printer->Indent();
+ if (HasMapField(descriptor_)) {
+ printer->Print(
+ "com.google.protobuf.nano.MapFactories.MapFactory mapFactory =\n"
+ " com.google.protobuf.nano.MapFactories.getMapFactory();\n");
+ }
+
+ printer->Print(
+ "while (true) {\n");
+ printer->Indent();
+
+ printer->Print(
+ "int tag = input.readTag();\n"
+ "switch (tag) {\n");
+ printer->Indent();
+
+ printer->Print(
+ "case 0:\n" // zero signals EOF / limit reached
+ " return this;\n"
+ "default: {\n");
+
+ printer->Indent();
+ if (params_.store_unknown_fields()) {
+ printer->Print(
+ "if (!storeUnknownField(input, tag)) {\n"
+ " return this;\n"
+ "}\n");
+ } else {
+ printer->Print(
+ "if (!com.google.protobuf.nano.WireFormatNano.parseUnknownField(input, tag)) {\n"
+ " return this;\n" // it's an endgroup tag
+ "}\n");
+ }
+ printer->Print("break;\n");
+ printer->Outdent();
+ printer->Print("}\n");
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = sorted_fields[i];
+ uint32 tag = WireFormatLite::MakeTag(field->number(),
+ WireFormat::WireTypeForFieldType(field->type()));
+
+ printer->Print(
+ "case $tag$: {\n",
+ "tag", SimpleItoa(tag));
+ printer->Indent();
+
+ field_generators_.get(field).GenerateMergingCode(printer);
+
+ printer->Outdent();
+ printer->Print(
+ " break;\n"
+ "}\n");
+
+ if (field->is_packable()) {
+ // To make packed = true wire compatible, we generate parsing code from a
+ // packed version of this field regardless of field->options().packed().
+ uint32 packed_tag = WireFormatLite::MakeTag(field->number(),
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED);
+ printer->Print(
+ "case $tag$: {\n",
+ "tag", SimpleItoa(packed_tag));
+ printer->Indent();
+
+ field_generators_.get(field).GenerateMergingCodeFromPacked(printer);
+
+ printer->Outdent();
+ printer->Print(
+ " break;\n"
+ "}\n");
+ }
+ }
+
+ printer->Outdent();
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " }\n" // switch (tag)
+ " }\n" // while (true)
+ "}\n");
+}
+
+void MessageGenerator::
+GenerateParseFromMethods(io::Printer* printer) {
+ // Note: These are separate from GenerateMessageSerializationMethods()
+ // because they need to be generated even for messages that are optimized
+ // for code size.
+ printer->Print(
+ "\n"
+ "public static $classname$ parseFrom(byte[] data)\n"
+ " throws com.google.protobuf.nano.InvalidProtocolBufferNanoException {\n"
+ " return com.google.protobuf.nano.MessageNano.mergeFrom(new $classname$(), data);\n"
+ "}\n"
+ "\n"
+ "public static $classname$ parseFrom(\n"
+ " com.google.protobuf.nano.CodedInputByteBufferNano input)\n"
+ " throws java.io.IOException {\n"
+ " return new $classname$().mergeFrom(input);\n"
+ "}\n",
+ "classname", descriptor_->name());
+}
+
+void MessageGenerator::GenerateSerializeOneField(
+ io::Printer* printer, const FieldDescriptor* field) {
+ field_generators_.get(field).GenerateSerializationCode(printer);
+}
+
+void MessageGenerator::GenerateClear(io::Printer* printer) {
+ if (!params_.generate_clear()) {
+ return;
+ }
+ printer->Print(
+ "\n"
+ "public $classname$ clear() {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+
+ GenerateFieldInitializers(printer);
+
+ printer->Outdent();
+ printer->Print(
+ " return this;\n"
+ "}\n");
+}
+
+void MessageGenerator::GenerateFieldInitializers(io::Printer* printer) {
+ // Clear bit fields.
+ int totalInts = (field_generators_.total_bits() + 31) / 32;
+ for (int i = 0; i < totalInts; i++) {
+ printer->Print("$bit_field_name$ = 0;\n",
+ "bit_field_name", GetBitFieldName(i));
+ }
+
+ // Call clear for all of the fields.
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ field_generators_.get(field).GenerateClearCode(printer);
+ }
+
+ // Clear oneofs.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ printer->Print(
+ "clear$oneof_capitalized_name$();\n",
+ "oneof_capitalized_name", UnderscoresToCapitalizedCamelCase(
+ descriptor_->oneof_decl(i)));
+ }
+
+ // Clear unknown fields.
+ if (params_.store_unknown_fields()) {
+ printer->Print("unknownFieldData = null;\n");
+ }
+ printer->Print("cachedSize = -1;\n");
+}
+
+void MessageGenerator::GenerateClone(io::Printer* printer) {
+ printer->Print(
+ "@Override\n"
+ "public $classname$ clone() {\n",
+ "classname", descriptor_->name());
+ printer->Indent();
+
+ printer->Print(
+ "$classname$ cloned;\n"
+ "try {\n"
+ " cloned = ($classname$) super.clone();\n"
+ "} catch (java.lang.CloneNotSupportedException e) {\n"
+ " throw new java.lang.AssertionError(e);\n"
+ "}\n",
+ "classname", descriptor_->name());
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i)).GenerateFixClonedCode(printer);
+ }
+
+ printer->Outdent();
+ printer->Print(
+ " return cloned;\n"
+ "}\n"
+ "\n");
+}
+
+void MessageGenerator::GenerateEquals(io::Printer* printer) {
+ // Don't override if there are no fields. We could generate an
+ // equals method that compares types, but often empty messages
+ // are used as namespaces.
+ if (descriptor_->field_count() == 0 && !params_.store_unknown_fields()) {
+ return;
+ }
+
+ printer->Print(
+ "\n"
+ "@Override\n"
+ "public boolean equals(Object o) {\n");
+ printer->Indent();
+ printer->Print(
+ "if (o == this) {\n"
+ " return true;\n"
+ "}\n"
+ "if (!(o instanceof $classname$)) {\n"
+ " return false;\n"
+ "}\n"
+ "$classname$ other = ($classname$) o;\n",
+ "classname", descriptor_->name());
+
+ // Checking oneof case before checking each oneof field.
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ const OneofDescriptor* oneof_desc = descriptor_->oneof_decl(i);
+ printer->Print(
+ "if (this.$oneof_name$Case_ != other.$oneof_name$Case_) {\n"
+ " return false;\n"
+ "}\n",
+ "oneof_name", UnderscoresToCamelCase(oneof_desc));
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ field_generators_.get(field).GenerateEqualsCode(printer);
+ }
+
+ if (params_.store_unknown_fields()) {
+ printer->Print(
+ "if (unknownFieldData == null || unknownFieldData.isEmpty()) {\n"
+ " return other.unknownFieldData == null || other.unknownFieldData.isEmpty();\n"
+ "} else {\n"
+ " return unknownFieldData.equals(other.unknownFieldData);\n"
+ "}");
+ } else {
+ printer->Print(
+ "return true;\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void MessageGenerator::GenerateHashCode(io::Printer* printer) {
+ if (descriptor_->field_count() == 0 && !params_.store_unknown_fields()) {
+ return;
+ }
+
+ printer->Print(
+ "\n"
+ "@Override\n"
+ "public int hashCode() {\n");
+ printer->Indent();
+
+ printer->Print("int result = 17;\n");
+ printer->Print("result = 31 * result + getClass().getName().hashCode();\n");
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ field_generators_.get(field).GenerateHashCodeCode(printer);
+ }
+
+ if (params_.store_unknown_fields()) {
+ printer->Print(
+ "result = 31 * result + \n"
+ " (unknownFieldData == null || unknownFieldData.isEmpty() ? 0 : \n"
+ " unknownFieldData.hashCode());\n");
+ }
+
+ printer->Print("return result;\n");
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+// ===================================================================
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.h
new file mode 100644
index 0000000000..281ec64fdd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message.h
@@ -0,0 +1,97 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_MESSAGE_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_MESSAGE_H__
+
+#include <string>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/compiler/javanano/javanano_field.h>
+#include <google/protobuf/compiler/javanano/javanano_params.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class Printer; // printer.h
+ }
+}
+
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class MessageGenerator {
+ public:
+ explicit MessageGenerator(const Descriptor* descriptor, const Params& params);
+ ~MessageGenerator();
+
+ // All static variables have to be declared at the top-level of the file
+ // so that we can control initialization order, which is important for
+ // DescriptorProto bootstrapping to work.
+ void GenerateStaticVariables(io::Printer* printer);
+
+ // Output code which initializes the static variables generated by
+ // GenerateStaticVariables().
+ void GenerateStaticVariableInitializers(io::Printer* printer);
+
+ // Generate the class itself.
+ void Generate(io::Printer* printer);
+
+ private:
+ void GenerateMessageSerializationMethods(io::Printer* printer);
+ void GenerateMergeFromMethods(io::Printer* printer);
+ void GenerateParseFromMethods(io::Printer* printer);
+ void GenerateSerializeOneField(io::Printer* printer,
+ const FieldDescriptor* field);
+
+ void GenerateClear(io::Printer* printer);
+ void GenerateFieldInitializers(io::Printer* printer);
+ void GenerateEquals(io::Printer* printer);
+ void GenerateHashCode(io::Printer* printer);
+ void GenerateClone(io::Printer* printer);
+
+ const Params& params_;
+ const Descriptor* descriptor_;
+ FieldGeneratorMap field_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.cc
new file mode 100644
index 0000000000..d1d04b52a4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.cc
@@ -0,0 +1,363 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/javanano/javanano_message_field.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+// TODO(kenton): Factor out a "SetCommonFieldVariables()" to get rid of
+// repeat code between this and the other field types.
+void SetMessageVariables(const Params& params,
+ const FieldDescriptor* descriptor, map<string, string>* variables) {
+ (*variables)["name"] =
+ RenameJavaKeywords(UnderscoresToCamelCase(descriptor));
+ (*variables)["capitalized_name"] =
+ RenameJavaKeywords(UnderscoresToCapitalizedCamelCase(descriptor));
+ (*variables)["number"] = SimpleItoa(descriptor->number());
+ (*variables)["type"] = ClassName(params, descriptor->message_type());
+ (*variables)["group_or_message"] =
+ (descriptor->type() == FieldDescriptor::TYPE_GROUP) ?
+ "Group" : "Message";
+ (*variables)["message_name"] = descriptor->containing_type()->name();
+ //(*variables)["message_type"] = descriptor->message_type()->name();
+ (*variables)["tag"] = SimpleItoa(WireFormat::MakeTag(descriptor));
+}
+
+} // namespace
+
+// ===================================================================
+
+MessageFieldGenerator::
+MessageFieldGenerator(const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetMessageVariables(params, descriptor, &variables_);
+}
+
+MessageFieldGenerator::~MessageFieldGenerator() {}
+
+void MessageFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /* unused lazy_init */) const {
+ printer->Print(variables_,
+ "public $type$ $name$;\n");
+}
+
+void MessageFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$ = null;\n");
+}
+
+void MessageFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ == null) {\n"
+ " this.$name$ = new $type$();\n"
+ "}\n");
+
+ if (descriptor_->type() == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "input.readGroup(this.$name$, $number$);\n");
+ } else {
+ printer->Print(variables_,
+ "input.readMessage(this.$name$);\n");
+ }
+}
+
+void MessageFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null) {\n"
+ " output.write$group_or_message$($number$, this.$name$);\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null) {\n"
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$group_or_message$Size($number$, this.$name$);\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::
+GenerateFixClonedCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null) {\n"
+ " cloned.$name$ = this.$name$.clone();\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ == null) { \n"
+ " if (other.$name$ != null) {\n"
+ " return false;\n"
+ " }\n"
+ "} else {\n"
+ " if (!this.$name$.equals(other.$name$)) {\n"
+ " return false;\n"
+ " }\n"
+ "}\n");
+}
+
+void MessageFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = 31 * result +\n"
+ " (this.$name$ == null ? 0 : this.$name$.hashCode());\n");
+}
+// ===================================================================
+
+MessageOneofFieldGenerator::MessageOneofFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetMessageVariables(params, descriptor, &variables_);
+ SetCommonOneofVariables(descriptor, &variables_);
+}
+
+MessageOneofFieldGenerator::~MessageOneofFieldGenerator() {}
+
+void MessageOneofFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /* unused lazy_init */) const {
+ printer->Print(variables_,
+ "public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case$;\n"
+ "}\n"
+ "public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case$) {\n"
+ " return ($type$) this.$oneof_name$_;\n"
+ " }\n"
+ " return null;\n"
+ "}\n"
+ "public $message_name$ set$capitalized_name$($type$ value) {\n"
+ " if (value == null) { throw new java.lang.NullPointerException(); }\n"
+ " $set_oneof_case$;\n"
+ " this.$oneof_name$_ = value;\n"
+ " return this;\n"
+ "}\n");
+}
+
+void MessageOneofFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ // No clear method for oneof fields.
+}
+
+void MessageOneofFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!($has_oneof_case$)) {\n"
+ " this.$oneof_name$_ = new $type$();\n"
+ "}\n"
+ "input.readMessage(\n"
+ " (com.google.protobuf.nano.MessageNano) this.$oneof_name$_);\n"
+ "$set_oneof_case$;\n");
+}
+
+void MessageOneofFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case$) {\n"
+ " output.writeMessage($number$,\n"
+ " (com.google.protobuf.nano.MessageNano) this.$oneof_name$_);\n"
+ "}\n");
+}
+
+void MessageOneofFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case$) {\n"
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .computeMessageSize($number$,\n"
+ " (com.google.protobuf.nano.MessageNano) this.$oneof_name$_);\n"
+ "}\n");
+}
+
+void MessageOneofFieldGenerator::
+GenerateFixClonedCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$oneof_name$ != null) {\n"
+ " cloned.$oneof_name$ = this.$oneof_name$.clone();\n"
+ "}\n");
+}
+
+void MessageOneofFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ GenerateOneofFieldEquals(descriptor_, variables_, printer);
+}
+
+void MessageOneofFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ GenerateOneofFieldHashCode(descriptor_, variables_, printer);
+}
+
+// ===================================================================
+
+RepeatedMessageFieldGenerator::RepeatedMessageFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetMessageVariables(params, descriptor, &variables_);
+}
+
+RepeatedMessageFieldGenerator::~RepeatedMessageFieldGenerator() {}
+
+void RepeatedMessageFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /* unused lazy_init */) const {
+ printer->Print(variables_,
+ "public $type$[] $name$;\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$ = $type$.emptyArray();\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // First, figure out the length of the array, then parse.
+ printer->Print(variables_,
+ "int arrayLength = com.google.protobuf.nano.WireFormatNano\n"
+ " .getRepeatedFieldArrayLength(input, $tag$);\n"
+ "int i = this.$name$ == null ? 0 : this.$name$.length;\n"
+ "$type$[] newArray =\n"
+ " new $type$[i + arrayLength];\n"
+ "if (i != 0) {\n"
+ " java.lang.System.arraycopy(this.$name$, 0, newArray, 0, i);\n"
+ "}\n"
+ "for (; i < newArray.length - 1; i++) {\n"
+ " newArray[i] = new $type$();\n");
+
+ if (descriptor_->type() == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ " input.readGroup(newArray[i], $number$);\n");
+ } else {
+ printer->Print(variables_,
+ " input.readMessage(newArray[i]);\n");
+ }
+
+ printer->Print(variables_,
+ " input.readTag();\n"
+ "}\n"
+ "// Last one without readTag.\n"
+ "newArray[i] = new $type$();\n");
+
+ if (descriptor_->type() == FieldDescriptor::TYPE_GROUP) {
+ printer->Print(variables_,
+ "input.readGroup(newArray[i], $number$);\n");
+ } else {
+ printer->Print(variables_,
+ "input.readMessage(newArray[i]);\n");
+ }
+
+ printer->Print(variables_,
+ "this.$name$ = newArray;\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n"
+ " for (int i = 0; i < this.$name$.length; i++) {\n"
+ " $type$ element = this.$name$[i];\n"
+ " if (element != null) {\n"
+ " output.write$group_or_message$($number$, element);\n"
+ " }\n"
+ " }\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n"
+ " for (int i = 0; i < this.$name$.length; i++) {\n"
+ " $type$ element = this.$name$[i];\n"
+ " if (element != null) {\n"
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$group_or_message$Size($number$, element);\n"
+ " }\n"
+ " }\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateFixClonedCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n"
+ " cloned.$name$ = new $type$[this.$name$.length];\n"
+ " for (int i = 0; i < this.$name$.length; i++) {\n"
+ " if (this.$name$[i] != null) {\n"
+ " cloned.$name$[i] = this.$name$[i].clone();\n"
+ " }\n"
+ " }\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!com.google.protobuf.nano.InternalNano.equals(\n"
+ " this.$name$, other.$name$)) {\n"
+ " return false;\n"
+ "}\n");
+}
+
+void RepeatedMessageFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = 31 * result\n"
+ " + com.google.protobuf.nano.InternalNano.hashCode(this.$name$);\n");
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.h
new file mode 100644
index 0000000000..e074735c70
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_message_field.h
@@ -0,0 +1,121 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_MESSAGE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_MESSAGE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/javanano/javanano_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class MessageFieldGenerator : public FieldGenerator {
+ public:
+ explicit MessageFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params);
+ ~MessageFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+ void GenerateFixClonedCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageFieldGenerator);
+};
+
+class MessageOneofFieldGenerator : public FieldGenerator {
+ public:
+ explicit MessageOneofFieldGenerator(const FieldDescriptor* descriptor,
+ const Params& params);
+ ~MessageOneofFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+ void GenerateFixClonedCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageOneofFieldGenerator);
+};
+
+class RepeatedMessageFieldGenerator : public FieldGenerator {
+ public:
+ explicit RepeatedMessageFieldGenerator(const FieldDescriptor* descriptor,
+ const Params& params);
+ ~RepeatedMessageFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+ void GenerateFixClonedCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedMessageFieldGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_MESSAGE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_params.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_params.h
new file mode 100644
index 0000000000..e3b4bb9368
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_params.h
@@ -0,0 +1,258 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2010 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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: wink@google.com (Wink Saville)
+
+#ifndef PROTOBUF_COMPILER_JAVANANO_JAVANANO_PARAMS_H_
+#define PROTOBUF_COMPILER_JAVANANO_JAVANANO_PARAMS_H_
+
+#include <map>
+#include <set>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+enum eMultipleFiles { JAVANANO_MUL_UNSET, JAVANANO_MUL_FALSE, JAVANANO_MUL_TRUE };
+
+// Parameters for used by the generators
+class Params {
+ public:
+ typedef map<string, string> NameMap;
+ typedef set<string> NameSet;
+ private:
+ string empty_;
+ string base_name_;
+ eMultipleFiles override_java_multiple_files_;
+ bool store_unknown_fields_;
+ NameMap java_packages_;
+ NameMap java_outer_classnames_;
+ NameSet java_multiple_files_;
+ bool generate_has_;
+ bool java_enum_style_;
+ bool optional_field_accessors_;
+ bool use_reference_types_for_primitives_;
+ bool generate_equals_;
+ bool ignore_services_;
+ bool parcelable_messages_;
+ bool reftypes_primitive_enums_;
+ bool generate_clear_;
+ bool generate_clone_;
+ bool generate_intdefs_;
+
+ public:
+ Params(const string & base_name) :
+ empty_(""),
+ base_name_(base_name),
+ override_java_multiple_files_(JAVANANO_MUL_UNSET),
+ store_unknown_fields_(false),
+ generate_has_(false),
+ java_enum_style_(false),
+ optional_field_accessors_(false),
+ use_reference_types_for_primitives_(false),
+ generate_equals_(false),
+ ignore_services_(false),
+ parcelable_messages_(false),
+ reftypes_primitive_enums_(false),
+ generate_clear_(true),
+ generate_clone_(false),
+ generate_intdefs_(false) {
+ }
+
+ const string& base_name() const {
+ return base_name_;
+ }
+
+ bool has_java_package(const string& file_name) const {
+ return java_packages_.find(file_name)
+ != java_packages_.end();
+ }
+ void set_java_package(const string& file_name,
+ const string& java_package) {
+ java_packages_[file_name] = java_package;
+ }
+ const string& java_package(const string& file_name) const {
+ NameMap::const_iterator itr;
+
+ itr = java_packages_.find(file_name);
+ if (itr == java_packages_.end()) {
+ return empty_;
+ } else {
+ return itr->second;
+ }
+ }
+ const NameMap& java_packages() {
+ return java_packages_;
+ }
+
+ bool has_java_outer_classname(const string& file_name) const {
+ return java_outer_classnames_.find(file_name)
+ != java_outer_classnames_.end();
+ }
+ void set_java_outer_classname(const string& file_name,
+ const string& java_outer_classname) {
+ java_outer_classnames_[file_name] = java_outer_classname;
+ }
+ const string& java_outer_classname(const string& file_name) const {
+ NameMap::const_iterator itr;
+
+ itr = java_outer_classnames_.find(file_name);
+ if (itr == java_outer_classnames_.end()) {
+ return empty_;
+ } else {
+ return itr->second;
+ }
+ }
+ const NameMap& java_outer_classnames() {
+ return java_outer_classnames_;
+ }
+
+ void set_override_java_multiple_files(bool java_multiple_files) {
+ if (java_multiple_files) {
+ override_java_multiple_files_ = JAVANANO_MUL_TRUE;
+ } else {
+ override_java_multiple_files_ = JAVANANO_MUL_FALSE;
+ }
+ }
+ void clear_override_java_multiple_files() {
+ override_java_multiple_files_ = JAVANANO_MUL_UNSET;
+ }
+
+ void set_java_multiple_files(const string& file_name, bool value) {
+ if (value) {
+ java_multiple_files_.insert(file_name);
+ } else {
+ java_multiple_files_.erase(file_name);
+ }
+ }
+ bool java_multiple_files(const string& file_name) const {
+ switch (override_java_multiple_files_) {
+ case JAVANANO_MUL_FALSE:
+ return false;
+ case JAVANANO_MUL_TRUE:
+ return true;
+ default:
+ return java_multiple_files_.find(file_name)
+ != java_multiple_files_.end();
+ }
+ }
+
+ void set_store_unknown_fields(bool value) {
+ store_unknown_fields_ = value;
+ }
+ bool store_unknown_fields() const {
+ return store_unknown_fields_;
+ }
+
+ void set_generate_has(bool value) {
+ generate_has_ = value;
+ }
+ bool generate_has() const {
+ return generate_has_;
+ }
+
+ void set_java_enum_style(bool value) {
+ java_enum_style_ = value;
+ }
+ bool java_enum_style() const {
+ return java_enum_style_;
+ }
+
+ void set_optional_field_accessors(bool value) {
+ optional_field_accessors_ = value;
+ }
+ bool optional_field_accessors() const {
+ return optional_field_accessors_;
+ }
+
+ void set_use_reference_types_for_primitives(bool value) {
+ use_reference_types_for_primitives_ = value;
+ }
+ bool use_reference_types_for_primitives() const {
+ return use_reference_types_for_primitives_;
+ }
+
+ void set_generate_equals(bool value) {
+ generate_equals_ = value;
+ }
+ bool generate_equals() const {
+ return generate_equals_;
+ }
+
+ void set_ignore_services(bool value) {
+ ignore_services_ = value;
+ }
+ bool ignore_services() const {
+ return ignore_services_;
+ }
+
+ void set_parcelable_messages(bool value) {
+ parcelable_messages_ = value;
+ }
+ bool parcelable_messages() const {
+ return parcelable_messages_;
+ }
+
+ void set_reftypes_primitive_enums(bool value) {
+ reftypes_primitive_enums_ = value;
+ }
+ bool reftypes_primitive_enums() const {
+ return reftypes_primitive_enums_;
+ }
+
+ void set_generate_clear(bool value) {
+ generate_clear_ = value;
+ }
+ bool generate_clear() const {
+ return generate_clear_;
+ }
+
+ void set_generate_clone(bool value) {
+ generate_clone_ = value;
+ }
+ bool generate_clone() const {
+ return generate_clone_;
+ }
+
+ void set_generate_intdefs(bool value) {
+ generate_intdefs_ = value;
+ }
+ bool generate_intdefs() const {
+ return generate_intdefs_;
+ }
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // PROTOBUF_COMPILER_JAVANANO_JAVANANO_PARAMS_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.cc
new file mode 100644
index 0000000000..978abf2ce4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.cc
@@ -0,0 +1,968 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#include <map>
+#include <math.h>
+#include <string>
+
+#include <google/protobuf/compiler/javanano/javanano_primitive_field.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/javanano/javanano_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+bool IsReferenceType(JavaType type) {
+ switch (type) {
+ case JAVATYPE_INT : return false;
+ case JAVATYPE_LONG : return false;
+ case JAVATYPE_FLOAT : return false;
+ case JAVATYPE_DOUBLE : return false;
+ case JAVATYPE_BOOLEAN: return false;
+ case JAVATYPE_STRING : return true;
+ case JAVATYPE_BYTES : return true;
+ case JAVATYPE_ENUM : return false;
+ case JAVATYPE_MESSAGE: return true;
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return false;
+}
+
+bool IsArrayType(JavaType type) {
+ switch (type) {
+ case JAVATYPE_INT : return false;
+ case JAVATYPE_LONG : return false;
+ case JAVATYPE_FLOAT : return false;
+ case JAVATYPE_DOUBLE : return false;
+ case JAVATYPE_BOOLEAN: return false;
+ case JAVATYPE_STRING : return false;
+ case JAVATYPE_BYTES : return true;
+ case JAVATYPE_ENUM : return false;
+ case JAVATYPE_MESSAGE: return false;
+
+ // No default because we want the compiler to complain if any new
+ // JavaTypes are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return false;
+}
+
+const char* GetCapitalizedType(const FieldDescriptor* field) {
+ switch (field->type()) {
+ case FieldDescriptor::TYPE_INT32 : return "Int32" ;
+ case FieldDescriptor::TYPE_UINT32 : return "UInt32" ;
+ case FieldDescriptor::TYPE_SINT32 : return "SInt32" ;
+ case FieldDescriptor::TYPE_FIXED32 : return "Fixed32" ;
+ case FieldDescriptor::TYPE_SFIXED32: return "SFixed32";
+ case FieldDescriptor::TYPE_INT64 : return "Int64" ;
+ case FieldDescriptor::TYPE_UINT64 : return "UInt64" ;
+ case FieldDescriptor::TYPE_SINT64 : return "SInt64" ;
+ case FieldDescriptor::TYPE_FIXED64 : return "Fixed64" ;
+ case FieldDescriptor::TYPE_SFIXED64: return "SFixed64";
+ case FieldDescriptor::TYPE_FLOAT : return "Float" ;
+ case FieldDescriptor::TYPE_DOUBLE : return "Double" ;
+ case FieldDescriptor::TYPE_BOOL : return "Bool" ;
+ case FieldDescriptor::TYPE_STRING : return "String" ;
+ case FieldDescriptor::TYPE_BYTES : return "Bytes" ;
+ case FieldDescriptor::TYPE_ENUM : return "Enum" ;
+ case FieldDescriptor::TYPE_GROUP : return "Group" ;
+ case FieldDescriptor::TYPE_MESSAGE : return "Message" ;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+// For encodings with fixed sizes, returns that size in bytes. Otherwise
+// returns -1.
+int FixedSize(FieldDescriptor::Type type) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32 : return -1;
+ case FieldDescriptor::TYPE_INT64 : return -1;
+ case FieldDescriptor::TYPE_UINT32 : return -1;
+ case FieldDescriptor::TYPE_UINT64 : return -1;
+ case FieldDescriptor::TYPE_SINT32 : return -1;
+ case FieldDescriptor::TYPE_SINT64 : return -1;
+ case FieldDescriptor::TYPE_FIXED32 : return WireFormatLite::kFixed32Size;
+ case FieldDescriptor::TYPE_FIXED64 : return WireFormatLite::kFixed64Size;
+ case FieldDescriptor::TYPE_SFIXED32: return WireFormatLite::kSFixed32Size;
+ case FieldDescriptor::TYPE_SFIXED64: return WireFormatLite::kSFixed64Size;
+ case FieldDescriptor::TYPE_FLOAT : return WireFormatLite::kFloatSize;
+ case FieldDescriptor::TYPE_DOUBLE : return WireFormatLite::kDoubleSize;
+
+ case FieldDescriptor::TYPE_BOOL : return WireFormatLite::kBoolSize;
+ case FieldDescriptor::TYPE_ENUM : return -1;
+
+ case FieldDescriptor::TYPE_STRING : return -1;
+ case FieldDescriptor::TYPE_BYTES : return -1;
+ case FieldDescriptor::TYPE_GROUP : return -1;
+ case FieldDescriptor::TYPE_MESSAGE : return -1;
+
+ // No default because we want the compiler to complain if any new
+ // types are added.
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return -1;
+}
+
+bool AllAscii(const string& text) {
+ for (int i = 0; i < text.size(); i++) {
+ if ((text[i] & 0x80) != 0) {
+ return false;
+ }
+ }
+ return true;
+}
+
+
+void SetPrimitiveVariables(const FieldDescriptor* descriptor, const Params params,
+ map<string, string>* variables) {
+ (*variables)["name"] =
+ RenameJavaKeywords(UnderscoresToCamelCase(descriptor));
+ (*variables)["capitalized_name"] =
+ RenameJavaKeywords(UnderscoresToCapitalizedCamelCase(descriptor));
+ (*variables)["number"] = SimpleItoa(descriptor->number());
+ if (params.use_reference_types_for_primitives()
+ && !descriptor->is_repeated()) {
+ (*variables)["type"] = BoxedPrimitiveTypeName(GetJavaType(descriptor));
+ } else {
+ (*variables)["type"] = PrimitiveTypeName(GetJavaType(descriptor));
+ }
+ // Deals with defaults. For C++-string types (string and bytes),
+ // we might need to have the generated code do the unicode decoding
+ // (see comments in InternalNano.java for gory details.). We would
+ // like to do this once into a static field and re-use that from
+ // then on.
+ if (descriptor->cpp_type() == FieldDescriptor::CPPTYPE_STRING &&
+ !descriptor->default_value_string().empty() &&
+ !params.use_reference_types_for_primitives()) {
+ if (descriptor->type() == FieldDescriptor::TYPE_BYTES) {
+ (*variables)["default"] = DefaultValue(params, descriptor);
+ (*variables)["default_constant"] = FieldDefaultConstantName(descriptor);
+ (*variables)["default_constant_value"] = strings::Substitute(
+ "com.google.protobuf.nano.InternalNano.bytesDefaultValue(\"$0\")",
+ CEscape(descriptor->default_value_string()));
+ (*variables)["default_copy_if_needed"] =
+ (*variables)["default"] + ".clone()";
+ } else if (AllAscii(descriptor->default_value_string())) {
+ // All chars are ASCII. In this case directly referencing a
+ // CEscape()'d string literal works fine.
+ (*variables)["default"] =
+ "\"" + CEscape(descriptor->default_value_string()) + "\"";
+ (*variables)["default_copy_if_needed"] = (*variables)["default"];
+ } else {
+ // Strings where some chars are non-ASCII. We need to save the
+ // default value.
+ (*variables)["default"] = DefaultValue(params, descriptor);
+ (*variables)["default_constant"] = FieldDefaultConstantName(descriptor);
+ (*variables)["default_constant_value"] = strings::Substitute(
+ "com.google.protobuf.nano.InternalNano.stringDefaultValue(\"$0\")",
+ CEscape(descriptor->default_value_string()));
+ (*variables)["default_copy_if_needed"] = (*variables)["default"];
+ }
+ } else {
+ // Non-string, non-bytes field. Defaults are literals.
+ (*variables)["default"] = DefaultValue(params, descriptor);
+ (*variables)["default_copy_if_needed"] = (*variables)["default"];
+ }
+ (*variables)["boxed_type"] = BoxedPrimitiveTypeName(GetJavaType(descriptor));
+ (*variables)["capitalized_type"] = GetCapitalizedType(descriptor);
+ (*variables)["tag"] = SimpleItoa(WireFormat::MakeTag(descriptor));
+ (*variables)["tag_size"] = SimpleItoa(
+ WireFormat::TagSize(descriptor->number(), descriptor->type()));
+ (*variables)["non_packed_tag"] = SimpleItoa(
+ internal::WireFormatLite::MakeTag(descriptor->number(),
+ internal::WireFormat::WireTypeForFieldType(descriptor->type())));
+ int fixed_size = FixedSize(descriptor->type());
+ if (fixed_size != -1) {
+ (*variables)["fixed_size"] = SimpleItoa(fixed_size);
+ }
+ (*variables)["message_name"] = descriptor->containing_type()->name();
+ (*variables)["empty_array_name"] = EmptyArrayName(params, descriptor);
+}
+} // namespace
+
+// ===================================================================
+
+PrimitiveFieldGenerator::
+PrimitiveFieldGenerator(const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetPrimitiveVariables(descriptor, params, &variables_);
+}
+
+PrimitiveFieldGenerator::~PrimitiveFieldGenerator() {}
+
+bool PrimitiveFieldGenerator::SavedDefaultNeeded() const {
+ return variables_.find("default_constant") != variables_.end();
+}
+
+void PrimitiveFieldGenerator::GenerateInitSavedDefaultCode(io::Printer* printer) const {
+ if (variables_.find("default_constant") != variables_.end()) {
+ printer->Print(variables_,
+ "$default_constant$ = $default_constant_value$;\n");
+ }
+}
+
+void PrimitiveFieldGenerator::
+GenerateMembers(io::Printer* printer, bool lazy_init) const {
+ if (variables_.find("default_constant") != variables_.end()) {
+ // Those primitive types that need a saved default.
+ if (lazy_init) {
+ printer->Print(variables_,
+ "private static $type$ $default_constant$;\n");
+ } else {
+ printer->Print(variables_,
+ "private static final $type$ $default_constant$ =\n"
+ " $default_constant_value$;\n");
+ }
+ }
+
+ printer->Print(variables_,
+ "public $type$ $name$;\n");
+
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "public boolean has$capitalized_name$;\n");
+ }
+}
+
+void PrimitiveFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$ = $default_copy_if_needed$;\n");
+
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "has$capitalized_name$ = false;\n");
+ }
+}
+
+void PrimitiveFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "this.$name$ = input.read$capitalized_type$();\n");
+
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "has$capitalized_name$ = true;\n");
+ }
+}
+
+void PrimitiveFieldGenerator::
+GenerateSerializationConditional(io::Printer* printer) const {
+ if (params_.use_reference_types_for_primitives()) {
+ // For reference type mode, serialize based on equality
+ // to null.
+ printer->Print(variables_,
+ "if (this.$name$ != null) {\n");
+ return;
+ }
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "if (has$capitalized_name$ || ");
+ } else {
+ printer->Print(variables_,
+ "if (");
+ }
+ JavaType java_type = GetJavaType(descriptor_);
+ if (IsArrayType(java_type)) {
+ printer->Print(variables_,
+ "!java.util.Arrays.equals(this.$name$, $default$)) {\n");
+ } else if (IsReferenceType(java_type)) {
+ printer->Print(variables_,
+ "!this.$name$.equals($default$)) {\n");
+ } else if (java_type == JAVATYPE_FLOAT) {
+ printer->Print(variables_,
+ "java.lang.Float.floatToIntBits(this.$name$)\n"
+ " != java.lang.Float.floatToIntBits($default$)) {\n");
+ } else if (java_type == JAVATYPE_DOUBLE) {
+ printer->Print(variables_,
+ "java.lang.Double.doubleToLongBits(this.$name$)\n"
+ " != java.lang.Double.doubleToLongBits($default$)) {\n");
+ } else {
+ printer->Print(variables_,
+ "this.$name$ != $default$) {\n");
+ }
+}
+
+void PrimitiveFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ if (descriptor_->is_required() && !params_.generate_has()) {
+ // Always serialize a required field if we don't have the 'has' signal.
+ printer->Print(variables_,
+ "output.write$capitalized_type$($number$, this.$name$);\n");
+ } else {
+ GenerateSerializationConditional(printer);
+ printer->Print(variables_,
+ " output.write$capitalized_type$($number$, this.$name$);\n"
+ "}\n");
+ }
+}
+
+void PrimitiveFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ if (descriptor_->is_required() && !params_.generate_has()) {
+ printer->Print(variables_,
+ "size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$capitalized_type$Size($number$, this.$name$);\n");
+ } else {
+ GenerateSerializationConditional(printer);
+ printer->Print(variables_,
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$capitalized_type$Size($number$, this.$name$);\n"
+ "}\n");
+ }
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateFixClonedCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n"
+ " cloned.$name$ = this.$name$.clone();\n"
+ "}\n");
+}
+
+void PrimitiveFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ // We define equality as serialized form equality. If generate_has(),
+ // then if the field value equals the default value in both messages,
+ // but one's 'has' field is set and the other's is not, the serialized
+ // forms are different and we should return false.
+ JavaType java_type = GetJavaType(descriptor_);
+ if (java_type == JAVATYPE_BYTES) {
+ printer->Print(variables_,
+ "if (!java.util.Arrays.equals(this.$name$, other.$name$)");
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "\n"
+ " || (java.util.Arrays.equals(this.$name$, $default$)\n"
+ " && this.has$capitalized_name$ != other.has$capitalized_name$)");
+ }
+ printer->Print(") {\n"
+ " return false;\n"
+ "}\n");
+ } else if (java_type == JAVATYPE_STRING
+ || params_.use_reference_types_for_primitives()) {
+ printer->Print(variables_,
+ "if (this.$name$ == null) {\n"
+ " if (other.$name$ != null) {\n"
+ " return false;\n"
+ " }\n"
+ "} else if (!this.$name$.equals(other.$name$)");
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "\n"
+ " || (this.$name$.equals($default$)\n"
+ " && this.has$capitalized_name$ != other.has$capitalized_name$)");
+ }
+ printer->Print(") {\n"
+ " return false;\n"
+ "}\n");
+ } else if (java_type == JAVATYPE_FLOAT) {
+ printer->Print(variables_,
+ "{\n"
+ " int bits = java.lang.Float.floatToIntBits(this.$name$);\n"
+ " if (bits != java.lang.Float.floatToIntBits(other.$name$)");
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "\n"
+ " || (bits == java.lang.Float.floatToIntBits($default$)\n"
+ " && this.has$capitalized_name$ != other.has$capitalized_name$)");
+ }
+ printer->Print(") {\n"
+ " return false;\n"
+ " }\n"
+ "}\n");
+ } else if (java_type == JAVATYPE_DOUBLE) {
+ printer->Print(variables_,
+ "{\n"
+ " long bits = java.lang.Double.doubleToLongBits(this.$name$);\n"
+ " if (bits != java.lang.Double.doubleToLongBits(other.$name$)");
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "\n"
+ " || (bits == java.lang.Double.doubleToLongBits($default$)\n"
+ " && this.has$capitalized_name$ != other.has$capitalized_name$)");
+ }
+ printer->Print(") {\n"
+ " return false;\n"
+ " }\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "if (this.$name$ != other.$name$");
+ if (params_.generate_has()) {
+ printer->Print(variables_,
+ "\n"
+ " || (this.$name$ == $default$\n"
+ " && this.has$capitalized_name$ != other.has$capitalized_name$)");
+ }
+ printer->Print(") {\n"
+ " return false;\n"
+ "}\n");
+ }
+}
+
+void PrimitiveFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ JavaType java_type = GetJavaType(descriptor_);
+ if (java_type == JAVATYPE_BYTES) {
+ printer->Print(variables_,
+ "result = 31 * result + java.util.Arrays.hashCode(this.$name$);\n");
+ } else if (java_type == JAVATYPE_STRING
+ || params_.use_reference_types_for_primitives()) {
+ printer->Print(variables_,
+ "result = 31 * result\n"
+ " + (this.$name$ == null ? 0 : this.$name$.hashCode());\n");
+ } else {
+ switch (java_type) {
+ // For all Java primitive types below, the hash codes match the
+ // results of BoxedType.valueOf(primitiveValue).hashCode().
+ case JAVATYPE_INT:
+ printer->Print(variables_,
+ "result = 31 * result + this.$name$;\n");
+ break;
+ case JAVATYPE_LONG:
+ printer->Print(variables_,
+ "result = 31 * result\n"
+ " + (int) (this.$name$ ^ (this.$name$ >>> 32));\n");
+ break;
+ case JAVATYPE_FLOAT:
+ printer->Print(variables_,
+ "result = 31 * result\n"
+ " + java.lang.Float.floatToIntBits(this.$name$);\n");
+ break;
+ case JAVATYPE_DOUBLE:
+ printer->Print(variables_,
+ "{\n"
+ " long v = java.lang.Double.doubleToLongBits(this.$name$);\n"
+ " result = 31 * result + (int) (v ^ (v >>> 32));\n"
+ "}\n");
+ break;
+ case JAVATYPE_BOOLEAN:
+ printer->Print(variables_,
+ "result = 31 * result + (this.$name$ ? 1231 : 1237);\n");
+ break;
+ default:
+ GOOGLE_LOG(ERROR) << "unknown java type for primitive field";
+ break;
+ }
+ }
+}
+
+// ===================================================================
+
+AccessorPrimitiveFieldGenerator::
+AccessorPrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ const Params& params, int has_bit_index)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetPrimitiveVariables(descriptor, params, &variables_);
+ SetBitOperationVariables("has", has_bit_index, &variables_);
+}
+
+AccessorPrimitiveFieldGenerator::~AccessorPrimitiveFieldGenerator() {}
+
+bool AccessorPrimitiveFieldGenerator::SavedDefaultNeeded() const {
+ return variables_.find("default_constant") != variables_.end();
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateInitSavedDefaultCode(io::Printer* printer) const {
+ if (variables_.find("default_constant") != variables_.end()) {
+ printer->Print(variables_,
+ "$default_constant$ = $default_constant_value$;\n");
+ }
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateMembers(io::Printer* printer, bool lazy_init) const {
+ if (variables_.find("default_constant") != variables_.end()) {
+ // Those primitive types that need a saved default.
+ if (lazy_init) {
+ printer->Print(variables_,
+ "private static $type$ $default_constant$;\n");
+ } else {
+ printer->Print(variables_,
+ "private static final $type$ $default_constant$ =\n"
+ " $default_constant_value$;\n");
+ }
+ }
+ printer->Print(variables_,
+ "private $type$ $name$_;\n"
+ "public $type$ get$capitalized_name$() {\n"
+ " return $name$_;\n"
+ "}\n"
+ "public $message_name$ set$capitalized_name$($type$ value) {\n");
+ if (IsReferenceType(GetJavaType(descriptor_))) {
+ printer->Print(variables_,
+ " if (value == null) {\n"
+ " throw new java.lang.NullPointerException();\n"
+ " }\n");
+ }
+ printer->Print(variables_,
+ " $name$_ = value;\n"
+ " $set_has$;\n"
+ " return this;\n"
+ "}\n"
+ "public boolean has$capitalized_name$() {\n"
+ " return $get_has$;\n"
+ "}\n"
+ "public $message_name$ clear$capitalized_name$() {\n"
+ " $name$_ = $default_copy_if_needed$;\n"
+ " $clear_has$;\n"
+ " return this;\n"
+ "}\n");
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = $default_copy_if_needed$;\n");
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$_ = input.read$capitalized_type$();\n"
+ "$set_has$;\n");
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_has$) {\n"
+ " output.write$capitalized_type$($number$, $name$_);\n"
+ "}\n");
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($get_has$) {\n"
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$capitalized_type$Size($number$, $name$_);\n"
+ "}\n");
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ switch (GetJavaType(descriptor_)) {
+ // For all Java primitive types below, the equality checks match the
+ // results of BoxedType.valueOf(primitiveValue).equals(otherValue).
+ case JAVATYPE_FLOAT:
+ printer->Print(variables_,
+ "if ($different_has$\n"
+ " || java.lang.Float.floatToIntBits($name$_)\n"
+ " != java.lang.Float.floatToIntBits(other.$name$_)) {\n"
+ " return false;\n"
+ "}\n");
+ break;
+ case JAVATYPE_DOUBLE:
+ printer->Print(variables_,
+ "if ($different_has$\n"
+ " || java.lang.Double.doubleToLongBits($name$_)\n"
+ " != java.lang.Double.doubleToLongBits(other.$name$_)) {\n"
+ " return false;\n"
+ "}\n");
+ break;
+ case JAVATYPE_INT:
+ case JAVATYPE_LONG:
+ case JAVATYPE_BOOLEAN:
+ printer->Print(variables_,
+ "if ($different_has$\n"
+ " || $name$_ != other.$name$_) {\n"
+ " return false;\n"
+ "}\n");
+ break;
+ case JAVATYPE_STRING:
+ // Accessor style would guarantee $name$_ non-null
+ printer->Print(variables_,
+ "if ($different_has$\n"
+ " || !$name$_.equals(other.$name$_)) {\n"
+ " return false;\n"
+ "}\n");
+ break;
+ case JAVATYPE_BYTES:
+ // Accessor style would guarantee $name$_ non-null
+ printer->Print(variables_,
+ "if ($different_has$\n"
+ " || !java.util.Arrays.equals($name$_, other.$name$_)) {\n"
+ " return false;\n"
+ "}\n");
+ break;
+ default:
+ GOOGLE_LOG(ERROR) << "unknown java type for primitive field";
+ break;
+ }
+}
+
+void AccessorPrimitiveFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ switch (GetJavaType(descriptor_)) {
+ // For all Java primitive types below, the hash codes match the
+ // results of BoxedType.valueOf(primitiveValue).hashCode().
+ case JAVATYPE_INT:
+ printer->Print(variables_,
+ "result = 31 * result + $name$_;\n");
+ break;
+ case JAVATYPE_LONG:
+ printer->Print(variables_,
+ "result = 31 * result + (int) ($name$_ ^ ($name$_ >>> 32));\n");
+ break;
+ case JAVATYPE_FLOAT:
+ printer->Print(variables_,
+ "result = 31 * result +\n"
+ " java.lang.Float.floatToIntBits($name$_);\n");
+ break;
+ case JAVATYPE_DOUBLE:
+ printer->Print(variables_,
+ "{\n"
+ " long v = java.lang.Double.doubleToLongBits($name$_);\n"
+ " result = 31 * result + (int) (v ^ (v >>> 32));\n"
+ "}\n");
+ break;
+ case JAVATYPE_BOOLEAN:
+ printer->Print(variables_,
+ "result = 31 * result + ($name$_ ? 1231 : 1237);\n");
+ break;
+ case JAVATYPE_STRING:
+ // Accessor style would guarantee $name$_ non-null
+ printer->Print(variables_,
+ "result = 31 * result + $name$_.hashCode();\n");
+ break;
+ case JAVATYPE_BYTES:
+ // Accessor style would guarantee $name$_ non-null
+ printer->Print(variables_,
+ "result = 31 * result + java.util.Arrays.hashCode($name$_);\n");
+ break;
+ default:
+ GOOGLE_LOG(ERROR) << "unknown java type for primitive field";
+ break;
+ }
+}
+
+// ===================================================================
+
+PrimitiveOneofFieldGenerator::PrimitiveOneofFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetPrimitiveVariables(descriptor, params, &variables_);
+ SetCommonOneofVariables(descriptor, &variables_);
+}
+
+PrimitiveOneofFieldGenerator::~PrimitiveOneofFieldGenerator() {}
+
+void PrimitiveOneofFieldGenerator::GenerateMembers(
+ io::Printer* printer, bool /*unused lazy_init*/) const {
+ printer->Print(variables_,
+ "public boolean has$capitalized_name$() {\n"
+ " return $has_oneof_case$;\n"
+ "}\n"
+ "public $type$ get$capitalized_name$() {\n"
+ " if ($has_oneof_case$) {\n"
+ " return ($type$) ($boxed_type$) this.$oneof_name$_;\n"
+ " }\n"
+ " return $default$;\n"
+ "}\n"
+ "public $message_name$ set$capitalized_name$($type$ value) {\n"
+ " $set_oneof_case$;\n"
+ " this.$oneof_name$_ = value;\n"
+ " return this;\n"
+ "}\n");
+}
+
+void PrimitiveOneofFieldGenerator::GenerateClearCode(
+ io::Printer* printer) const {
+ // No clear method for oneof fields.
+}
+
+void PrimitiveOneofFieldGenerator::GenerateMergingCode(
+ io::Printer* printer) const {
+ printer->Print(variables_,
+ "this.$oneof_name$_ = input.read$capitalized_type$();\n"
+ "$set_oneof_case$;\n");
+}
+
+void PrimitiveOneofFieldGenerator::GenerateSerializationCode(
+ io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case$) {\n"
+ " output.write$capitalized_type$(\n"
+ " $number$, ($boxed_type$) this.$oneof_name$_);\n"
+ "}\n");
+}
+
+void PrimitiveOneofFieldGenerator::GenerateSerializedSizeCode(
+ io::Printer* printer) const {
+ printer->Print(variables_,
+ "if ($has_oneof_case$) {\n"
+ " size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$capitalized_type$Size(\n"
+ " $number$, ($boxed_type$) this.$oneof_name$_);\n"
+ "}\n");
+}
+
+void PrimitiveOneofFieldGenerator::GenerateEqualsCode(
+ io::Printer* printer) const {
+ GenerateOneofFieldEquals(descriptor_, variables_, printer);
+}
+
+void PrimitiveOneofFieldGenerator::GenerateHashCodeCode(
+ io::Printer* printer) const {
+ GenerateOneofFieldHashCode(descriptor_, variables_, printer);
+}
+
+// ===================================================================
+
+RepeatedPrimitiveFieldGenerator::RepeatedPrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params)
+ : FieldGenerator(params), descriptor_(descriptor) {
+ SetPrimitiveVariables(descriptor, params, &variables_);
+}
+
+RepeatedPrimitiveFieldGenerator::~RepeatedPrimitiveFieldGenerator() {}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateMembers(io::Printer* printer, bool /*unused init_defaults*/) const {
+ printer->Print(variables_,
+ "public $type$[] $name$;\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateClearCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "$name$ = $default$;\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateMergingCode(io::Printer* printer) const {
+ // First, figure out the length of the array, then parse.
+ printer->Print(variables_,
+ "int arrayLength = com.google.protobuf.nano.WireFormatNano\n"
+ " .getRepeatedFieldArrayLength(input, $non_packed_tag$);\n"
+ "int i = this.$name$ == null ? 0 : this.$name$.length;\n");
+
+ if (GetJavaType(descriptor_) == JAVATYPE_BYTES) {
+ printer->Print(variables_,
+ "byte[][] newArray = new byte[i + arrayLength][];\n");
+ } else {
+ printer->Print(variables_,
+ "$type$[] newArray = new $type$[i + arrayLength];\n");
+ }
+ printer->Print(variables_,
+ "if (i != 0) {\n"
+ " java.lang.System.arraycopy(this.$name$, 0, newArray, 0, i);\n"
+ "}\n"
+ "for (; i < newArray.length - 1; i++) {\n"
+ " newArray[i] = input.read$capitalized_type$();\n"
+ " input.readTag();\n"
+ "}\n"
+ "// Last one without readTag.\n"
+ "newArray[i] = input.read$capitalized_type$();\n"
+ "this.$name$ = newArray;\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateMergingCodeFromPacked(io::Printer* printer) const {
+ printer->Print(
+ "int length = input.readRawVarint32();\n"
+ "int limit = input.pushLimit(length);\n");
+
+ // If we know the elements will all be of the same size, the arrayLength
+ // can be calculated much more easily. However, FixedSize() returns 1 for
+ // repeated bool fields, which are guaranteed to have the fixed size of
+ // 1 byte per value only if we control the output. On the wire they can
+ // legally appear as variable-size integers, so we need to use the slow
+ // way for repeated bool fields.
+ if (descriptor_->type() == FieldDescriptor::TYPE_BOOL
+ || FixedSize(descriptor_->type()) == -1) {
+ printer->Print(variables_,
+ "// First pass to compute array length.\n"
+ "int arrayLength = 0;\n"
+ "int startPos = input.getPosition();\n"
+ "while (input.getBytesUntilLimit() > 0) {\n"
+ " input.read$capitalized_type$();\n"
+ " arrayLength++;\n"
+ "}\n"
+ "input.rewindToPosition(startPos);\n");
+ } else {
+ printer->Print(variables_,
+ "int arrayLength = length / $fixed_size$;\n");
+ }
+
+ printer->Print(variables_,
+ "int i = this.$name$ == null ? 0 : this.$name$.length;\n"
+ "$type$[] newArray = new $type$[i + arrayLength];\n"
+ "if (i != 0) {\n"
+ " java.lang.System.arraycopy(this.$name$, 0, newArray, 0, i);\n"
+ "}\n"
+ "for (; i < newArray.length; i++) {\n"
+ " newArray[i] = input.read$capitalized_type$();\n"
+ "}\n"
+ "this.$name$ = newArray;\n"
+ "input.popLimit(limit);\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateRepeatedDataSizeCode(io::Printer* printer) const {
+ // Creates a variable dataSize and puts the serialized size in there.
+ // If the element type is a Java reference type, also generates
+ // dataCount which stores the number of non-null elements in the field.
+ if (IsReferenceType(GetJavaType(descriptor_))) {
+ printer->Print(variables_,
+ "int dataCount = 0;\n"
+ "int dataSize = 0;\n"
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " $type$ element = this.$name$[i];\n"
+ " if (element != null) {\n"
+ " dataCount++;\n"
+ " dataSize += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$capitalized_type$SizeNoTag(element);\n"
+ " }\n"
+ "}\n");
+ } else if (FixedSize(descriptor_->type()) == -1) {
+ printer->Print(variables_,
+ "int dataSize = 0;\n"
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " $type$ element = this.$name$[i];\n"
+ " dataSize += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .compute$capitalized_type$SizeNoTag(element);\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "int dataSize = $fixed_size$ * this.$name$.length;\n");
+ }
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateSerializationCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n");
+ printer->Indent();
+
+ if (descriptor_->is_packable() && descriptor_->options().packed()) {
+ GenerateRepeatedDataSizeCode(printer);
+ printer->Print(variables_,
+ "output.writeRawVarint32($tag$);\n"
+ "output.writeRawVarint32(dataSize);\n"
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " output.write$capitalized_type$NoTag(this.$name$[i]);\n"
+ "}\n");
+ } else if (IsReferenceType(GetJavaType(descriptor_))) {
+ printer->Print(variables_,
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " $type$ element = this.$name$[i];\n"
+ " if (element != null) {\n"
+ " output.write$capitalized_type$($number$, element);\n"
+ " }\n"
+ "}\n");
+ } else {
+ printer->Print(variables_,
+ "for (int i = 0; i < this.$name$.length; i++) {\n"
+ " output.write$capitalized_type$($number$, this.$name$[i]);\n"
+ "}\n");
+ }
+
+ printer->Outdent();
+ printer->Print("}\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateSerializedSizeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (this.$name$ != null && this.$name$.length > 0) {\n");
+ printer->Indent();
+
+ GenerateRepeatedDataSizeCode(printer);
+
+ printer->Print(
+ "size += dataSize;\n");
+ if (descriptor_->is_packable() && descriptor_->options().packed()) {
+ printer->Print(variables_,
+ "size += $tag_size$;\n"
+ "size += com.google.protobuf.nano.CodedOutputByteBufferNano\n"
+ " .computeRawVarint32Size(dataSize);\n");
+ } else if (IsReferenceType(GetJavaType(descriptor_))) {
+ printer->Print(variables_,
+ "size += $tag_size$ * dataCount;\n");
+ } else {
+ printer->Print(variables_,
+ "size += $tag_size$ * this.$name$.length;\n");
+ }
+
+ printer->Outdent();
+
+ printer->Print(
+ "}\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateEqualsCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "if (!com.google.protobuf.nano.InternalNano.equals(\n"
+ " this.$name$, other.$name$)) {\n"
+ " return false;\n"
+ "}\n");
+}
+
+void RepeatedPrimitiveFieldGenerator::
+GenerateHashCodeCode(io::Printer* printer) const {
+ printer->Print(variables_,
+ "result = 31 * result\n"
+ " + com.google.protobuf.nano.InternalNano.hashCode(this.$name$);\n");
+}
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.h
new file mode 100644
index 0000000000..a01981dd48
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/javanano/javanano_primitive_field.h
@@ -0,0 +1,150 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// http://code.google.com/p/protobuf/
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JAVANANO_PRIMITIVE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_JAVANANO_PRIMITIVE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/javanano/javanano_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace javanano {
+
+class PrimitiveFieldGenerator : public FieldGenerator {
+ public:
+ explicit PrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params);
+ ~PrimitiveFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ bool SavedDefaultNeeded() const;
+ void GenerateInitSavedDefaultCode(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+
+ private:
+ void GenerateSerializationConditional(io::Printer* printer) const;
+
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveFieldGenerator);
+};
+
+class AccessorPrimitiveFieldGenerator : public FieldGenerator {
+ public:
+ explicit AccessorPrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ const Params &params, int has_bit_index);
+ ~AccessorPrimitiveFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ bool SavedDefaultNeeded() const;
+ void GenerateInitSavedDefaultCode(io::Printer* printer) const;
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(AccessorPrimitiveFieldGenerator);
+};
+
+class PrimitiveOneofFieldGenerator : public FieldGenerator {
+ public:
+ explicit PrimitiveOneofFieldGenerator(
+ const FieldDescriptor* descriptor, const Params& params);
+ ~PrimitiveOneofFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+
+ private:
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveOneofFieldGenerator);
+};
+
+class RepeatedPrimitiveFieldGenerator : public FieldGenerator {
+ public:
+ explicit RepeatedPrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ const Params& params);
+ ~RepeatedPrimitiveFieldGenerator();
+
+ // implements FieldGenerator ---------------------------------------
+ void GenerateMembers(io::Printer* printer, bool lazy_init) const;
+ void GenerateClearCode(io::Printer* printer) const;
+ void GenerateMergingCode(io::Printer* printer) const;
+ void GenerateMergingCodeFromPacked(io::Printer* printer) const;
+ void GenerateSerializationCode(io::Printer* printer) const;
+ void GenerateSerializedSizeCode(io::Printer* printer) const;
+ void GenerateEqualsCode(io::Printer* printer) const;
+ void GenerateHashCodeCode(io::Printer* printer) const;
+ void GenerateFixClonedCode(io::Printer* printer) const;
+
+ private:
+ void GenerateRepeatedDataSizeCode(io::Printer* printer) const;
+
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedPrimitiveFieldGenerator);
+};
+
+} // namespace javanano
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JAVANANO_PRIMITIVE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.cc
new file mode 100755
index 0000000000..58c77d007c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.cc
@@ -0,0 +1,3307 @@
+// 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.
+
+#include "google/protobuf/compiler/js/js_generator.h"
+
+#include <assert.h>
+#include <algorithm>
+#include <limits>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace js {
+
+// Sorted list of JavaScript keywords. These cannot be used as names. If they
+// appear, we prefix them with "pb_".
+const char* kKeyword[] = {
+ "abstract",
+ "boolean",
+ "break",
+ "byte",
+ "case",
+ "catch",
+ "char",
+ "class",
+ "const",
+ "continue",
+ "debugger",
+ "default",
+ "delete",
+ "do",
+ "double",
+ "else",
+ "enum",
+ "export",
+ "extends",
+ "false",
+ "final",
+ "finally",
+ "float",
+ "for",
+ "function",
+ "goto",
+ "if",
+ "implements",
+ "import",
+ "in",
+ "instanceof",
+ "int",
+ "interface",
+ "long",
+ "native",
+ "new",
+ "null",
+ "package",
+ "private",
+ "protected",
+ "public",
+ "return",
+ "short",
+ "static",
+ "super",
+ "switch",
+ "synchronized",
+ "this",
+ "throw",
+ "throws",
+ "transient",
+ "try",
+ "typeof",
+ "var",
+ "void",
+ "volatile",
+ "while",
+ "with",
+};
+
+static const int kNumKeyword = sizeof(kKeyword) / sizeof(char*);
+
+namespace {
+
+// The mode of operation for bytes fields. Historically JSPB always carried
+// bytes as JS {string}, containing base64 content by convention. With binary
+// and proto3 serialization the new convention is to represent it as binary
+// data in Uint8Array. See b/26173701 for background on the migration.
+enum BytesMode {
+ BYTES_DEFAULT, // Default type for getBytesField to return.
+ BYTES_B64, // Explicitly coerce to base64 string where needed.
+ BYTES_U8, // Explicitly coerce to Uint8Array where needed.
+};
+
+bool IsReserved(const string& ident) {
+ for (int i = 0; i < kNumKeyword; i++) {
+ if (ident == kKeyword[i]) {
+ return true;
+ }
+ }
+ return false;
+}
+
+// Returns a copy of |filename| with any trailing ".protodevel" or ".proto
+// suffix stripped.
+// TODO(haberman): Unify with copy in compiler/cpp/internal/helpers.cc.
+string StripProto(const string& filename) {
+ const char* suffix = HasSuffixString(filename, ".protodevel")
+ ? ".protodevel" : ".proto";
+ return StripSuffixString(filename, suffix);
+}
+
+// Given a filename like foo/bar/baz.proto, returns the corresponding JavaScript
+// file foo/bar/baz.js.
+string GetJSFilename(const string& filename) {
+ return StripProto(filename) + "_pb.js";
+}
+
+// Given a filename like foo/bar/baz.proto, returns the root directory
+// path ../../
+string GetRootPath(const string& from_filename, const string& to_filename) {
+ if (to_filename.find("google/protobuf") == 0) {
+ // Well-known types (.proto files in the google/protobuf directory) are
+ // assumed to come from the 'google-protobuf' npm package. We may want to
+ // generalize this exception later by letting others put generated code in
+ // their own npm packages.
+ return "google-protobuf/";
+ }
+
+ size_t slashes = std::count(from_filename.begin(), from_filename.end(), '/');
+ if (slashes == 0) {
+ return "./";
+ }
+ string result = "";
+ for (size_t i = 0; i < slashes; i++) {
+ result += "../";
+ }
+ return result;
+}
+
+// Returns the alias we assign to the module of the given .proto filename
+// when importing.
+string ModuleAlias(const string& filename) {
+ // This scheme could technically cause problems if a file includes any 2 of:
+ // foo/bar_baz.proto
+ // foo_bar_baz.proto
+ // foo_bar/baz.proto
+ //
+ // We'll worry about this problem if/when we actually see it. This name isn't
+ // exposed to users so we can change it later if we need to.
+ string basename = StripProto(filename);
+ StripString(&basename, "-", '$');
+ StripString(&basename, "/", '_');
+ return basename + "_pb";
+}
+
+// Returns the fully normalized JavaScript path for the given
+// file descriptor's package.
+string GetPath(const GeneratorOptions& options,
+ const FileDescriptor* file) {
+ if (!options.namespace_prefix.empty()) {
+ return options.namespace_prefix;
+ } else if (!file->package().empty()) {
+ return "proto." + file->package();
+ } else {
+ return "proto";
+ }
+}
+
+// Forward declare, so that GetPrefix can call this method,
+// which in turn, calls GetPrefix.
+string GetPath(const GeneratorOptions& options,
+ const Descriptor* descriptor);
+
+// Returns the path prefix for a message or enumeration that
+// lives under the given file and containing type.
+string GetPrefix(const GeneratorOptions& options,
+ const FileDescriptor* file_descriptor,
+ const Descriptor* containing_type) {
+ string prefix = "";
+
+ if (containing_type == NULL) {
+ prefix = GetPath(options, file_descriptor);
+ } else {
+ prefix = GetPath(options, containing_type);
+ }
+
+ if (!prefix.empty()) {
+ prefix += ".";
+ }
+
+ return prefix;
+}
+
+
+// Returns the fully normalized JavaScript path for the given
+// message descriptor.
+string GetPath(const GeneratorOptions& options,
+ const Descriptor* descriptor) {
+ return GetPrefix(
+ options, descriptor->file(),
+ descriptor->containing_type()) + descriptor->name();
+}
+
+
+// Returns the fully normalized JavaScript path for the given
+// field's containing message descriptor.
+string GetPath(const GeneratorOptions& options,
+ const FieldDescriptor* descriptor) {
+ return GetPath(options, descriptor->containing_type());
+}
+
+// Returns the fully normalized JavaScript path for the given
+// enumeration descriptor.
+string GetPath(const GeneratorOptions& options,
+ const EnumDescriptor* enum_descriptor) {
+ return GetPrefix(
+ options, enum_descriptor->file(),
+ enum_descriptor->containing_type()) + enum_descriptor->name();
+}
+
+
+// Returns the fully normalized JavaScript path for the given
+// enumeration value descriptor.
+string GetPath(const GeneratorOptions& options,
+ const EnumValueDescriptor* value_descriptor) {
+ return GetPath(
+ options,
+ value_descriptor->type()) + "." + value_descriptor->name();
+}
+
+string MaybeCrossFileRef(const GeneratorOptions& options,
+ const FileDescriptor* from_file,
+ const Descriptor* to_message) {
+ if (options.import_style == GeneratorOptions::IMPORT_COMMONJS &&
+ from_file != to_message->file()) {
+ // Cross-file ref in CommonJS needs to use the module alias instead of
+ // the global name.
+ return ModuleAlias(to_message->file()->name()) + "." + to_message->name();
+ } else {
+ // Within a single file we use a full name.
+ return GetPath(options, to_message);
+ }
+}
+
+string SubmessageTypeRef(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ GOOGLE_CHECK(field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE);
+ return MaybeCrossFileRef(options, field->file(), field->message_type());
+}
+
+// - Object field name: LOWER_UNDERSCORE -> LOWER_CAMEL, except for group fields
+// (UPPER_CAMEL -> LOWER_CAMEL), with "List" (or "Map") appended if appropriate,
+// and with reserved words triggering a "pb_" prefix.
+// - Getters/setters: LOWER_UNDERSCORE -> UPPER_CAMEL, except for group fields
+// (use the name directly), then append "List" if appropriate, then append "$"
+// if resulting name is equal to a reserved word.
+// - Enums: just uppercase.
+
+// Locale-independent version of ToLower that deals only with ASCII A-Z.
+char ToLowerASCII(char c) {
+ if (c >= 'A' && c <= 'Z') {
+ return (c - 'A') + 'a';
+ } else {
+ return c;
+ }
+}
+
+vector<string> ParseLowerUnderscore(const string& input) {
+ vector<string> words;
+ string running = "";
+ for (int i = 0; i < input.size(); i++) {
+ if (input[i] == '_') {
+ if (!running.empty()) {
+ words.push_back(running);
+ running.clear();
+ }
+ } else {
+ running += ToLowerASCII(input[i]);
+ }
+ }
+ if (!running.empty()) {
+ words.push_back(running);
+ }
+ return words;
+}
+
+vector<string> ParseUpperCamel(const string& input) {
+ vector<string> words;
+ string running = "";
+ for (int i = 0; i < input.size(); i++) {
+ if (input[i] >= 'A' && input[i] <= 'Z' && !running.empty()) {
+ words.push_back(running);
+ running.clear();
+ }
+ running += ToLowerASCII(input[i]);
+ }
+ if (!running.empty()) {
+ words.push_back(running);
+ }
+ return words;
+}
+
+string ToLowerCamel(const vector<string>& words) {
+ string result;
+ for (int i = 0; i < words.size(); i++) {
+ string word = words[i];
+ if (i == 0 && (word[0] >= 'A' && word[0] <= 'Z')) {
+ word[0] = (word[0] - 'A') + 'a';
+ } else if (i != 0 && (word[0] >= 'a' && word[0] <= 'z')) {
+ word[0] = (word[0] - 'a') + 'A';
+ }
+ result += word;
+ }
+ return result;
+}
+
+string ToUpperCamel(const vector<string>& words) {
+ string result;
+ for (int i = 0; i < words.size(); i++) {
+ string word = words[i];
+ if (word[0] >= 'a' && word[0] <= 'z') {
+ word[0] = (word[0] - 'a') + 'A';
+ }
+ result += word;
+ }
+ return result;
+}
+
+// Based on code from descriptor.cc (Thanks Kenton!)
+// Uppercases the entire string, turning ValueName into
+// VALUENAME.
+string ToEnumCase(const string& input) {
+ string result;
+ result.reserve(input.size());
+
+ for (int i = 0; i < input.size(); i++) {
+ if ('a' <= input[i] && input[i] <= 'z') {
+ result.push_back(input[i] - 'a' + 'A');
+ } else {
+ result.push_back(input[i]);
+ }
+ }
+
+ return result;
+}
+
+string ToFileName(const string& input) {
+ string result;
+ result.reserve(input.size());
+
+ for (int i = 0; i < input.size(); i++) {
+ if ('A' <= input[i] && input[i] <= 'Z') {
+ result.push_back(input[i] - 'A' + 'a');
+ } else {
+ result.push_back(input[i]);
+ }
+ }
+
+ return result;
+}
+
+// When we're generating one output file per type name, this is the filename
+// that top-level extensions should go in.
+string GetExtensionFileName(const GeneratorOptions& options,
+ const FileDescriptor* file) {
+ return options.output_dir + "/" + ToFileName(GetPath(options, file)) + ".js";
+}
+
+// When we're generating one output file per type name, this is the filename
+// that a top-level message should go in.
+string GetMessageFileName(const GeneratorOptions& options,
+ const Descriptor* desc) {
+ return options.output_dir + "/" + ToFileName(desc->name()) + ".js";
+}
+
+// When we're generating one output file per type name, this is the filename
+// that a top-level message should go in.
+string GetEnumFileName(const GeneratorOptions& options,
+ const EnumDescriptor* desc) {
+ return options.output_dir + "/" + ToFileName(desc->name()) + ".js";
+}
+
+// Returns the message/response ID, if set.
+string GetMessageId(const Descriptor* desc) {
+ return string();
+}
+
+bool IgnoreExtensionField(const FieldDescriptor* field) {
+ // Exclude descriptor extensions from output "to avoid clutter" (from original
+ // codegen).
+ return field->is_extension() &&
+ field->containing_type()->file()->name() ==
+ "google/protobuf/descriptor.proto";
+}
+
+
+// Used inside Google only -- do not remove.
+bool IsResponse(const Descriptor* desc) { return false; }
+
+bool IgnoreField(const FieldDescriptor* field) {
+ return IgnoreExtensionField(field);
+}
+
+
+// Do we ignore this message type?
+bool IgnoreMessage(const GeneratorOptions& options, const Descriptor* d) {
+ return d->options().map_entry();
+}
+
+// Does JSPB ignore this entire oneof? True only if all fields are ignored.
+bool IgnoreOneof(const OneofDescriptor* oneof) {
+ for (int i = 0; i < oneof->field_count(); i++) {
+ if (!IgnoreField(oneof->field(i))) {
+ return false;
+ }
+ }
+ return true;
+}
+
+string JSIdent(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ bool is_upper_camel,
+ bool is_map) {
+ string result;
+ if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ result = is_upper_camel ?
+ ToUpperCamel(ParseUpperCamel(field->message_type()->name())) :
+ ToLowerCamel(ParseUpperCamel(field->message_type()->name()));
+ } else {
+ result = is_upper_camel ?
+ ToUpperCamel(ParseLowerUnderscore(field->name())) :
+ ToLowerCamel(ParseLowerUnderscore(field->name()));
+ }
+ if (is_map || (field->is_map())) {
+ // JSPB-style or proto3-style map.
+ result += "Map";
+ } else if (field->is_repeated()) {
+ // Repeated field.
+ result += "List";
+ }
+ return result;
+}
+
+string JSObjectFieldName(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ string name = JSIdent(
+ options,
+ field,
+ /* is_upper_camel = */ false,
+ /* is_map = */ false);
+ if (IsReserved(name)) {
+ name = "pb_" + name;
+ }
+ return name;
+}
+
+string JSByteGetterSuffix(BytesMode bytes_mode) {
+ switch (bytes_mode) {
+ case BYTES_DEFAULT:
+ return "";
+ case BYTES_B64:
+ return "B64";
+ case BYTES_U8:
+ return "U8";
+ default:
+ assert(false);
+ }
+ return "";
+}
+
+// Returns the field name as a capitalized portion of a getter/setter method
+// name, e.g. MyField for .getMyField().
+string JSGetterName(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ BytesMode bytes_mode = BYTES_DEFAULT) {
+ string name = JSIdent(options, field,
+ /* is_upper_camel = */ true,
+ /* is_map = */ false);
+ if (field->type() == FieldDescriptor::TYPE_BYTES) {
+ string suffix = JSByteGetterSuffix(bytes_mode);
+ if (!suffix.empty()) {
+ name += "_as" + suffix;
+ }
+ }
+ if (name == "Extension" || name == "JsPbMessageId") {
+ // Avoid conflicts with base-class names.
+ name += "$";
+ }
+ return name;
+}
+
+string JSMapGetterName(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ return JSIdent(options, field,
+ /* is_upper_camel = */ true,
+ /* is_map = */ true);
+}
+
+
+
+string JSOneofName(const OneofDescriptor* oneof) {
+ return ToUpperCamel(ParseLowerUnderscore(oneof->name()));
+}
+
+// Returns the index corresponding to this field in the JSPB array (underlying
+// data storage array).
+string JSFieldIndex(const FieldDescriptor* field) {
+ // Determine whether this field is a member of a group. Group fields are a bit
+ // wonky: their "containing type" is a message type created just for the
+ // group, and that type's parent type has a field with the group-message type
+ // as its message type and TYPE_GROUP as its field type. For such fields, the
+ // index we use is relative to the field number of the group submessage field.
+ // For all other fields, we just use the field number.
+ const Descriptor* containing_type = field->containing_type();
+ const Descriptor* parent_type = containing_type->containing_type();
+ if (parent_type != NULL) {
+ for (int i = 0; i < parent_type->field_count(); i++) {
+ if (parent_type->field(i)->type() == FieldDescriptor::TYPE_GROUP &&
+ parent_type->field(i)->message_type() == containing_type) {
+ return SimpleItoa(field->number() - parent_type->field(i)->number());
+ }
+ }
+ }
+ return SimpleItoa(field->number());
+}
+
+string JSOneofIndex(const OneofDescriptor* oneof) {
+ int index = -1;
+ for (int i = 0; i < oneof->containing_type()->oneof_decl_count(); i++) {
+ const OneofDescriptor* o = oneof->containing_type()->oneof_decl(i);
+ // If at least one field in this oneof is not JSPB-ignored, count the oneof.
+ for (int j = 0; j < o->field_count(); j++) {
+ const FieldDescriptor* f = o->field(j);
+ if (!IgnoreField(f)) {
+ index++;
+ break; // inner loop
+ }
+ }
+ if (o == oneof) {
+ break;
+ }
+ }
+ return SimpleItoa(index);
+}
+
+// Decodes a codepoint in \x0000 -- \xFFFF.
+uint16 DecodeUTF8Codepoint(uint8* bytes, size_t* length) {
+ if (*length == 0) {
+ return 0;
+ }
+ size_t expected = 0;
+ if ((*bytes & 0x80) == 0) {
+ expected = 1;
+ } else if ((*bytes & 0xe0) == 0xc0) {
+ expected = 2;
+ } else if ((*bytes & 0xf0) == 0xe0) {
+ expected = 3;
+ } else {
+ // Too long -- don't accept.
+ *length = 0;
+ return 0;
+ }
+
+ if (*length < expected) {
+ // Not enough bytes -- don't accept.
+ *length = 0;
+ return 0;
+ }
+
+ *length = expected;
+ switch (expected) {
+ case 1: return bytes[0];
+ case 2: return ((bytes[0] & 0x1F) << 6) |
+ ((bytes[1] & 0x3F) << 0);
+ case 3: return ((bytes[0] & 0x0F) << 12) |
+ ((bytes[1] & 0x3F) << 6) |
+ ((bytes[2] & 0x3F) << 0);
+ default: return 0;
+ }
+}
+
+// Escapes the contents of a string to be included within double-quotes ("") in
+// JavaScript. The input data should be a UTF-8 encoded C++ string of chars.
+// Returns false if |out| was truncated because |in| contained invalid UTF-8 or
+// codepoints outside the BMP.
+// TODO(lukestebbing): Support codepoints outside the BMP.
+bool EscapeJSString(const string& in, string* out) {
+ size_t decoded = 0;
+ for (size_t i = 0; i < in.size(); i += decoded) {
+ uint16 codepoint = 0;
+ // Decode the next UTF-8 codepoint.
+ size_t have_bytes = in.size() - i;
+ uint8 bytes[3] = {
+ static_cast<uint8>(in[i]),
+ static_cast<uint8>(((i + 1) < in.size()) ? in[i + 1] : 0),
+ static_cast<uint8>(((i + 2) < in.size()) ? in[i + 2] : 0),
+ };
+ codepoint = DecodeUTF8Codepoint(bytes, &have_bytes);
+ if (have_bytes == 0) {
+ return false;
+ }
+ decoded = have_bytes;
+
+ switch (codepoint) {
+ case '\'': *out += "\\x27"; break;
+ case '"': *out += "\\x22"; break;
+ case '<': *out += "\\x3c"; break;
+ case '=': *out += "\\x3d"; break;
+ case '>': *out += "\\x3e"; break;
+ case '&': *out += "\\x26"; break;
+ case '\b': *out += "\\b"; break;
+ case '\t': *out += "\\t"; break;
+ case '\n': *out += "\\n"; break;
+ case '\f': *out += "\\f"; break;
+ case '\r': *out += "\\r"; break;
+ case '\\': *out += "\\\\"; break;
+ default:
+ // TODO(lukestebbing): Once we're supporting codepoints outside the BMP,
+ // use a single Unicode codepoint escape if the output language is
+ // ECMAScript 2015 or above. Otherwise, use a surrogate pair.
+ // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Lexical_grammar#String_literals
+ if (codepoint >= 0x20 && codepoint <= 0x7e) {
+ *out += static_cast<char>(codepoint);
+ } else if (codepoint >= 0x100) {
+ *out += StringPrintf("\\u%04x", codepoint);
+ } else {
+ *out += StringPrintf("\\x%02x", codepoint);
+ }
+ break;
+ }
+ }
+ return true;
+}
+
+string EscapeBase64(const string& in) {
+ static const char* kAlphabet =
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+ string result;
+
+ for (size_t i = 0; i < in.size(); i += 3) {
+ int value = (in[i] << 16) |
+ (((i + 1) < in.size()) ? (in[i + 1] << 8) : 0) |
+ (((i + 2) < in.size()) ? (in[i + 2] << 0) : 0);
+ result += kAlphabet[(value >> 18) & 0x3f];
+ result += kAlphabet[(value >> 12) & 0x3f];
+ if ((i + 1) < in.size()) {
+ result += kAlphabet[(value >> 6) & 0x3f];
+ } else {
+ result += '=';
+ }
+ if ((i + 2) < in.size()) {
+ result += kAlphabet[(value >> 0) & 0x3f];
+ } else {
+ result += '=';
+ }
+ }
+
+ return result;
+}
+
+// Post-process the result of SimpleFtoa/SimpleDtoa to *exactly* match the
+// original codegen's formatting (which is just .toString() on java.lang.Double
+// or java.lang.Float).
+string PostProcessFloat(string result) {
+ // If inf, -inf or nan, replace with +Infinity, -Infinity or NaN.
+ if (result == "inf") {
+ return "Infinity";
+ } else if (result == "-inf") {
+ return "-Infinity";
+ } else if (result == "nan") {
+ return "NaN";
+ }
+
+ // If scientific notation (e.g., "1e10"), (i) capitalize the "e", (ii)
+ // ensure that the mantissa (portion prior to the "e") has at least one
+ // fractional digit (after the decimal point), and (iii) strip any unnecessary
+ // leading zeroes and/or '+' signs from the exponent.
+ string::size_type exp_pos = result.find('e');
+ if (exp_pos != string::npos) {
+ string mantissa = result.substr(0, exp_pos);
+ string exponent = result.substr(exp_pos + 1);
+
+ // Add ".0" to mantissa if no fractional part exists.
+ if (mantissa.find('.') == string::npos) {
+ mantissa += ".0";
+ }
+
+ // Strip the sign off the exponent and store as |exp_neg|.
+ bool exp_neg = false;
+ if (!exponent.empty() && exponent[0] == '+') {
+ exponent = exponent.substr(1);
+ } else if (!exponent.empty() && exponent[0] == '-') {
+ exp_neg = true;
+ exponent = exponent.substr(1);
+ }
+
+ // Strip any leading zeroes off the exponent.
+ while (exponent.size() > 1 && exponent[0] == '0') {
+ exponent = exponent.substr(1);
+ }
+
+ return mantissa + "E" + string(exp_neg ? "-" : "") + exponent;
+ }
+
+ // Otherwise, this is an ordinary decimal number. Append ".0" if result has no
+ // decimal/fractional part in order to match output of original codegen.
+ if (result.find('.') == string::npos) {
+ result += ".0";
+ }
+
+ return result;
+}
+
+string FloatToString(float value) {
+ string result = SimpleFtoa(value);
+ return PostProcessFloat(result);
+}
+
+string DoubleToString(double value) {
+ string result = SimpleDtoa(value);
+ return PostProcessFloat(result);
+}
+
+string MaybeNumberString(const FieldDescriptor* field, const string& orig) {
+ return orig;
+}
+
+string JSFieldDefault(const FieldDescriptor* field) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return MaybeNumberString(
+ field, SimpleItoa(field->default_value_int32()));
+ case FieldDescriptor::CPPTYPE_UINT32:
+ // The original codegen is in Java, and Java protobufs store unsigned
+ // integer values as signed integer values. In order to exactly match the
+ // output, we need to reinterpret as base-2 signed. Ugh.
+ return MaybeNumberString(
+ field, SimpleItoa(static_cast<int32>(field->default_value_uint32())));
+ case FieldDescriptor::CPPTYPE_INT64:
+ return MaybeNumberString(
+ field, SimpleItoa(field->default_value_int64()));
+ case FieldDescriptor::CPPTYPE_UINT64:
+ // See above note for uint32 -- reinterpreting as signed.
+ return MaybeNumberString(
+ field, SimpleItoa(static_cast<int64>(field->default_value_uint64())));
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return SimpleItoa(field->default_value_enum()->number());
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field->default_value_bool() ? "true" : "false";
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return FloatToString(field->default_value_float());
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return DoubleToString(field->default_value_double());
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (field->type() == FieldDescriptor::TYPE_STRING) {
+ string out;
+ bool is_valid = EscapeJSString(field->default_value_string(), &out);
+ if (!is_valid) {
+ // TODO(lukestebbing): Decide whether this should be a hard error.
+ GOOGLE_LOG(WARNING) << "The default value for field " << field->full_name()
+ << " was truncated since it contained invalid UTF-8 or"
+ " codepoints outside the basic multilingual plane.";
+ }
+ return "\"" + out + "\"";
+ } else { // Bytes
+ return "\"" + EscapeBase64(field->default_value_string()) + "\"";
+ }
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return "null";
+ }
+ GOOGLE_LOG(FATAL) << "Shouldn't reach here.";
+ return "";
+}
+
+string ProtoTypeName(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ switch (field->type()) {
+ case FieldDescriptor::TYPE_BOOL:
+ return "bool";
+ case FieldDescriptor::TYPE_INT32:
+ return "int32";
+ case FieldDescriptor::TYPE_UINT32:
+ return "uint32";
+ case FieldDescriptor::TYPE_SINT32:
+ return "sint32";
+ case FieldDescriptor::TYPE_FIXED32:
+ return "fixed32";
+ case FieldDescriptor::TYPE_SFIXED32:
+ return "sfixed32";
+ case FieldDescriptor::TYPE_INT64:
+ return "int64";
+ case FieldDescriptor::TYPE_UINT64:
+ return "uint64";
+ case FieldDescriptor::TYPE_SINT64:
+ return "sint64";
+ case FieldDescriptor::TYPE_FIXED64:
+ return "fixed64";
+ case FieldDescriptor::TYPE_SFIXED64:
+ return "sfixed64";
+ case FieldDescriptor::TYPE_FLOAT:
+ return "float";
+ case FieldDescriptor::TYPE_DOUBLE:
+ return "double";
+ case FieldDescriptor::TYPE_STRING:
+ return "string";
+ case FieldDescriptor::TYPE_BYTES:
+ return "bytes";
+ case FieldDescriptor::TYPE_GROUP:
+ return GetPath(options, field->message_type());
+ case FieldDescriptor::TYPE_ENUM:
+ return GetPath(options, field->enum_type());
+ case FieldDescriptor::TYPE_MESSAGE:
+ return GetPath(options, field->message_type());
+ default:
+ return "";
+ }
+}
+
+string JSIntegerTypeName(const FieldDescriptor* field) {
+ return "number";
+}
+
+string JSStringTypeName(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ BytesMode bytes_mode) {
+ if (field->type() == FieldDescriptor::TYPE_BYTES) {
+ switch (bytes_mode) {
+ case BYTES_DEFAULT:
+ return "(string|Uint8Array)";
+ case BYTES_B64:
+ return "string";
+ case BYTES_U8:
+ return "Uint8Array";
+ default:
+ assert(false);
+ }
+ }
+ return "string";
+}
+
+string JSTypeName(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ BytesMode bytes_mode) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return "boolean";
+ case FieldDescriptor::CPPTYPE_INT32:
+ return JSIntegerTypeName(field);
+ case FieldDescriptor::CPPTYPE_INT64:
+ return JSIntegerTypeName(field);
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return JSIntegerTypeName(field);
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return JSIntegerTypeName(field);
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return "number";
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return "number";
+ case FieldDescriptor::CPPTYPE_STRING:
+ return JSStringTypeName(options, field, bytes_mode);
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return GetPath(options, field->enum_type());
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return GetPath(options, field->message_type());
+ default:
+ return "";
+ }
+}
+
+bool HasFieldPresence(const FieldDescriptor* field);
+
+string JSFieldTypeAnnotation(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ bool force_optional,
+ bool force_present,
+ bool singular_if_not_packed,
+ BytesMode bytes_mode = BYTES_DEFAULT) {
+ bool is_primitive =
+ (field->cpp_type() != FieldDescriptor::CPPTYPE_ENUM &&
+ field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE &&
+ (field->type() != FieldDescriptor::TYPE_BYTES ||
+ bytes_mode == BYTES_B64));
+
+ string jstype = JSTypeName(options, field, bytes_mode);
+
+ if (field->is_repeated() &&
+ (field->is_packed() || !singular_if_not_packed)) {
+ if (field->type() == FieldDescriptor::TYPE_BYTES &&
+ bytes_mode == BYTES_DEFAULT) {
+ jstype = "(Array<!Uint8Array>|Array<string>)";
+ } else {
+ if (!is_primitive) {
+ jstype = "!" + jstype;
+ }
+ jstype = "Array.<" + jstype + ">";
+ }
+ if (!force_optional) {
+ jstype = "!" + jstype;
+ }
+ }
+
+ if (field->is_optional() && is_primitive &&
+ force_optional && !force_present) {
+ jstype += "?";
+ } else if (field->is_required() && !is_primitive && !force_optional) {
+ jstype = "!" + jstype;
+ }
+
+ if (force_optional && HasFieldPresence(field)) {
+ jstype += "|undefined";
+ }
+ if (force_present && jstype[0] != '!' && !is_primitive) {
+ jstype = "!" + jstype;
+ }
+
+ return jstype;
+}
+
+string JSBinaryReaderMethodType(const FieldDescriptor* field) {
+ string name = field->type_name();
+ if (name[0] >= 'a' && name[0] <= 'z') {
+ name[0] = (name[0] - 'a') + 'A';
+ }
+
+ return name;
+}
+
+string JSBinaryReadWriteMethodName(const FieldDescriptor* field,
+ bool is_writer) {
+ string name = JSBinaryReaderMethodType(field);
+ if (field->is_packed()) {
+ name = "Packed" + name;
+ } else if (is_writer && field->is_repeated()) {
+ name = "Repeated" + name;
+ }
+ return name;
+}
+
+string JSBinaryReaderMethodName(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ if (options.binary) {
+ return "jspb.BinaryReader.prototype.read" +
+ JSBinaryReadWriteMethodName(field, /* is_writer = */ false);
+ } else {
+ return "null";
+ }
+}
+
+string JSBinaryWriterMethodName(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ if (options.binary) {
+ return "jspb.BinaryWriter.prototype.write" +
+ JSBinaryReadWriteMethodName(field, /* is_writer = */ true);
+ } else {
+ return "null";
+ }
+}
+
+string JSReturnClause(const FieldDescriptor* desc) {
+ return "";
+}
+
+string JSReturnDoc(const GeneratorOptions& options,
+ const FieldDescriptor* desc) {
+ return "";
+}
+
+bool HasRepeatedFields(const Descriptor* desc) {
+ for (int i = 0; i < desc->field_count(); i++) {
+ if (desc->field(i)->is_repeated() && !desc->field(i)->is_map()) {
+ return true;
+ }
+ }
+ return false;
+}
+
+static const char* kRepeatedFieldArrayName = ".repeatedFields_";
+
+string RepeatedFieldsArrayName(const GeneratorOptions& options,
+ const Descriptor* desc) {
+ return HasRepeatedFields(desc) ?
+ (GetPath(options, desc) + kRepeatedFieldArrayName) : "null";
+}
+
+bool HasOneofFields(const Descriptor* desc) {
+ for (int i = 0; i < desc->field_count(); i++) {
+ if (desc->field(i)->containing_oneof()) {
+ return true;
+ }
+ }
+ return false;
+}
+
+static const char* kOneofGroupArrayName = ".oneofGroups_";
+
+string OneofFieldsArrayName(const GeneratorOptions& options,
+ const Descriptor* desc) {
+ return HasOneofFields(desc) ?
+ (GetPath(options, desc) + kOneofGroupArrayName) : "null";
+}
+
+string RepeatedFieldNumberList(const Descriptor* desc) {
+ std::vector<string> numbers;
+ for (int i = 0; i < desc->field_count(); i++) {
+ if (desc->field(i)->is_repeated() && !desc->field(i)->is_map()) {
+ numbers.push_back(JSFieldIndex(desc->field(i)));
+ }
+ }
+ return "[" + Join(numbers, ",") + "]";
+}
+
+string OneofGroupList(const Descriptor* desc) {
+ // List of arrays (one per oneof), each of which is a list of field indices
+ std::vector<string> oneof_entries;
+ for (int i = 0; i < desc->oneof_decl_count(); i++) {
+ const OneofDescriptor* oneof = desc->oneof_decl(i);
+ if (IgnoreOneof(oneof)) {
+ continue;
+ }
+
+ std::vector<string> oneof_fields;
+ for (int j = 0; j < oneof->field_count(); j++) {
+ if (IgnoreField(oneof->field(j))) {
+ continue;
+ }
+ oneof_fields.push_back(JSFieldIndex(oneof->field(j)));
+ }
+ oneof_entries.push_back("[" + Join(oneof_fields, ",") + "]");
+ }
+ return "[" + Join(oneof_entries, ",") + "]";
+}
+
+string JSOneofArray(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ return OneofFieldsArrayName(options, field->containing_type()) + "[" +
+ JSOneofIndex(field->containing_oneof()) + "]";
+}
+
+string RelativeTypeName(const FieldDescriptor* field) {
+ assert(field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM ||
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE);
+ // For a field with an enum or message type, compute a name relative to the
+ // path name of the message type containing this field.
+ string package = field->file()->package();
+ string containing_type = field->containing_type()->full_name() + ".";
+ string type = (field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) ?
+ field->enum_type()->full_name() : field->message_type()->full_name();
+
+ // |prefix| is advanced as we find separators '.' past the common package
+ // prefix that yield common prefixes in the containing type's name and this
+ // type's name.
+ int prefix = 0;
+ for (int i = 0; i < type.size() && i < containing_type.size(); i++) {
+ if (type[i] != containing_type[i]) {
+ break;
+ }
+ if (type[i] == '.' && i >= package.size()) {
+ prefix = i + 1;
+ }
+ }
+
+ return type.substr(prefix);
+}
+
+string JSExtensionsObjectName(const GeneratorOptions& options,
+ const FileDescriptor* from_file,
+ const Descriptor* desc) {
+ if (desc->full_name() == "google.protobuf.bridge.MessageSet") {
+ // TODO(haberman): fix this for the IMPORT_COMMONJS case.
+ return "jspb.Message.messageSetExtensions";
+ } else {
+ return MaybeCrossFileRef(options, from_file, desc) + ".extensions";
+ }
+}
+
+static const int kMapKeyField = 1;
+static const int kMapValueField = 2;
+
+const FieldDescriptor* MapFieldKey(const FieldDescriptor* field) {
+ assert(field->is_map());
+ return field->message_type()->FindFieldByNumber(kMapKeyField);
+}
+
+const FieldDescriptor* MapFieldValue(const FieldDescriptor* field) {
+ assert(field->is_map());
+ return field->message_type()->FindFieldByNumber(kMapValueField);
+}
+
+string FieldDefinition(const GeneratorOptions& options,
+ const FieldDescriptor* field) {
+ if (field->is_map()) {
+ const FieldDescriptor* key_field = MapFieldKey(field);
+ const FieldDescriptor* value_field = MapFieldValue(field);
+ string key_type = ProtoTypeName(options, key_field);
+ string value_type;
+ if (value_field->type() == FieldDescriptor::TYPE_ENUM ||
+ value_field->type() == FieldDescriptor::TYPE_MESSAGE) {
+ value_type = RelativeTypeName(value_field);
+ } else {
+ value_type = ProtoTypeName(options, value_field);
+ }
+ return StringPrintf("map<%s, %s> %s = %d;",
+ key_type.c_str(),
+ value_type.c_str(),
+ field->name().c_str(),
+ field->number());
+ } else {
+ string qualifier = field->is_repeated() ? "repeated" :
+ (field->is_optional() ? "optional" : "required");
+ string type, name;
+ if (field->type() == FieldDescriptor::TYPE_ENUM ||
+ field->type() == FieldDescriptor::TYPE_MESSAGE) {
+ type = RelativeTypeName(field);
+ name = field->name();
+ } else if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ type = "group";
+ name = field->message_type()->name();
+ } else {
+ type = ProtoTypeName(options, field);
+ name = field->name();
+ }
+ return StringPrintf("%s %s %s = %d;",
+ qualifier.c_str(),
+ type.c_str(),
+ name.c_str(),
+ field->number());
+ }
+}
+
+string FieldComments(const FieldDescriptor* field, BytesMode bytes_mode) {
+ string comments;
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_BOOL) {
+ comments +=
+ " * Note that Boolean fields may be set to 0/1 when serialized from "
+ "a Java server.\n"
+ " * You should avoid comparisons like {@code val === true/false} in "
+ "those cases.\n";
+ }
+ if (field->is_repeated()) {
+ comments +=
+ " * If you change this array by adding, removing or replacing "
+ "elements, or if you\n"
+ " * replace the array itself, then you must call the setter to "
+ "update it.\n";
+ }
+ if (field->type() == FieldDescriptor::TYPE_BYTES && bytes_mode == BYTES_U8) {
+ comments +=
+ " * Note that Uint8Array is not supported on all browsers.\n"
+ " * @see http://caniuse.com/Uint8Array\n";
+ }
+ return comments;
+}
+
+bool ShouldGenerateExtension(const FieldDescriptor* field) {
+ return
+ field->is_extension() &&
+ !IgnoreField(field);
+}
+
+bool HasExtensions(const Descriptor* desc) {
+ for (int i = 0; i < desc->extension_count(); i++) {
+ if (ShouldGenerateExtension(desc->extension(i))) {
+ return true;
+ }
+ }
+ for (int i = 0; i < desc->nested_type_count(); i++) {
+ if (HasExtensions(desc->nested_type(i))) {
+ return true;
+ }
+ }
+ return false;
+}
+
+bool HasExtensions(const FileDescriptor* file) {
+ for (int i = 0; i < file->extension_count(); i++) {
+ if (ShouldGenerateExtension(file->extension(i))) {
+ return true;
+ }
+ }
+ for (int i = 0; i < file->message_type_count(); i++) {
+ if (HasExtensions(file->message_type(i))) {
+ return true;
+ }
+ }
+ return false;
+}
+
+bool IsExtendable(const Descriptor* desc) {
+ return desc->extension_range_count() > 0;
+}
+
+// Returns the max index in the underlying data storage array beyond which the
+// extension object is used.
+string GetPivot(const Descriptor* desc) {
+ static const int kDefaultPivot = (1 << 29); // max field number (29 bits)
+
+ // Find the max field number
+ int max_field_number = 0;
+ for (int i = 0; i < desc->field_count(); i++) {
+ if (!IgnoreField(desc->field(i)) &&
+ desc->field(i)->number() > max_field_number) {
+ max_field_number = desc->field(i)->number();
+ }
+ }
+
+ int pivot = -1;
+ if (IsExtendable(desc)) {
+ pivot = ((max_field_number + 1) < kDefaultPivot) ?
+ (max_field_number + 1) : kDefaultPivot;
+ }
+
+ return SimpleItoa(pivot);
+}
+
+// Returns true for fields that represent "null" as distinct from the default
+// value. See http://go/proto3#heading=h.kozewqqcqhuz for more information.
+bool HasFieldPresence(const FieldDescriptor* field) {
+ if (field->is_repeated()) {
+ return false;
+ }
+
+ return
+ (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) ||
+ (field->containing_oneof() != NULL) ||
+ (field->file()->syntax() != FileDescriptor::SYNTAX_PROTO3);
+}
+
+// For proto3 fields without presence, returns a string representing the default
+// value in JavaScript. See http://go/proto3#heading=h.kozewqqcqhuz for more
+// information.
+string Proto3PrimitiveFieldDefault(const FieldDescriptor* field) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ case FieldDescriptor::CPPTYPE_INT64:
+ case FieldDescriptor::CPPTYPE_UINT32:
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ return "0";
+ }
+
+ case FieldDescriptor::CPPTYPE_ENUM:
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return "0";
+
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return "false";
+
+ case FieldDescriptor::CPPTYPE_STRING: // includes BYTES
+ return "\"\"";
+
+ default:
+ // MESSAGE is handled separately.
+ assert(false);
+ return "";
+ }
+}
+
+// We use this to implement the semantics that same file can be generated
+// multiple times, but the last one wins. We never actually write the files,
+// but we keep a set of which descriptors were the final one for a given
+// filename.
+class FileDeduplicator {
+ public:
+ explicit FileDeduplicator(const GeneratorOptions& options)
+ : error_on_conflict_(options.error_on_name_conflict) {}
+
+ bool AddFile(const string& filename, const void* desc, string* error) {
+ if (descs_by_filename_.find(filename) != descs_by_filename_.end()) {
+ if (error_on_conflict_) {
+ *error = "Name conflict: file name " + filename +
+ " would be generated by two descriptors";
+ return false;
+ }
+ allowed_descs_.erase(descs_by_filename_[filename]);
+ }
+
+ descs_by_filename_[filename] = desc;
+ allowed_descs_.insert(desc);
+ return true;
+ }
+
+ void GetAllowedSet(set<const void*>* allowed_set) {
+ *allowed_set = allowed_descs_;
+ }
+
+ private:
+ bool error_on_conflict_;
+ map<string, const void*> descs_by_filename_;
+ set<const void*> allowed_descs_;
+};
+
+void DepthFirstSearch(const FileDescriptor* file,
+ vector<const FileDescriptor*>* list,
+ set<const FileDescriptor*>* seen) {
+ if (!seen->insert(file).second) {
+ return;
+ }
+
+ // Add all dependencies.
+ for (int i = 0; i < file->dependency_count(); i++) {
+ DepthFirstSearch(file->dependency(i), list, seen);
+ }
+
+ // Add this file.
+ list->push_back(file);
+}
+
+// A functor for the predicate to remove_if() below. Returns true if a given
+// FileDescriptor is not in the given set.
+class NotInSet {
+ public:
+ explicit NotInSet(const set<const FileDescriptor*>& file_set)
+ : file_set_(file_set) {}
+
+ bool operator()(const FileDescriptor* file) {
+ return file_set_.count(file) == 0;
+ }
+
+ private:
+ const set<const FileDescriptor*>& file_set_;
+};
+
+// This function generates an ordering of the input FileDescriptors that matches
+// the logic of the old code generator. The order is significant because two
+// different input files can generate the same output file, and the last one
+// needs to win.
+void GenerateJspbFileOrder(const vector<const FileDescriptor*>& input,
+ vector<const FileDescriptor*>* ordered) {
+ // First generate an ordering of all reachable files (including dependencies)
+ // with depth-first search. This mimics the behavior of --include_imports,
+ // which is what the old codegen used.
+ ordered->clear();
+ set<const FileDescriptor*> seen;
+ set<const FileDescriptor*> input_set;
+ for (int i = 0; i < input.size(); i++) {
+ DepthFirstSearch(input[i], ordered, &seen);
+ input_set.insert(input[i]);
+ }
+
+ // Now remove the entries that are not actually in our input list.
+ ordered->erase(
+ std::remove_if(ordered->begin(), ordered->end(), NotInSet(input_set)),
+ ordered->end());
+}
+
+// If we're generating code in file-per-type mode, avoid overwriting files
+// by choosing the last descriptor that writes each filename and permitting
+// only those to generate code.
+
+bool GenerateJspbAllowedSet(const GeneratorOptions& options,
+ const vector<const FileDescriptor*>& files,
+ set<const void*>* allowed_set,
+ string* error) {
+ vector<const FileDescriptor*> files_ordered;
+ GenerateJspbFileOrder(files, &files_ordered);
+
+ // Choose the last descriptor for each filename.
+ FileDeduplicator dedup(options);
+ for (int i = 0; i < files_ordered.size(); i++) {
+ for (int j = 0; j < files_ordered[i]->message_type_count(); j++) {
+ const Descriptor* desc = files_ordered[i]->message_type(j);
+ if (!dedup.AddFile(GetMessageFileName(options, desc), desc, error)) {
+ return false;
+ }
+ }
+ for (int j = 0; j < files_ordered[i]->enum_type_count(); j++) {
+ const EnumDescriptor* desc = files_ordered[i]->enum_type(j);
+ if (!dedup.AddFile(GetEnumFileName(options, desc), desc, error)) {
+ return false;
+ }
+ }
+
+ // Pull out all free-floating extensions and generate files for those too.
+ bool has_extension = false;
+
+ for (int j = 0; j < files_ordered[i]->extension_count(); j++) {
+ if (ShouldGenerateExtension(files_ordered[i]->extension(j))) {
+ has_extension = true;
+ }
+ }
+
+ if (has_extension) {
+ if (!dedup.AddFile(GetExtensionFileName(options, files_ordered[i]),
+ files_ordered[i], error)) {
+ return false;
+ }
+ }
+ }
+
+ dedup.GetAllowedSet(allowed_set);
+
+ return true;
+}
+
+} // anonymous namespace
+
+void Generator::GenerateHeader(const GeneratorOptions& options,
+ io::Printer* printer) const {
+ printer->Print("/**\n"
+ " * @fileoverview\n"
+ " * @enhanceable\n"
+ " * @public\n"
+ " */\n"
+ "// GENERATED CODE -- DO NOT EDIT!\n"
+ "\n");
+}
+
+void Generator::FindProvidesForFile(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* file,
+ std::set<string>* provided) const {
+ for (int i = 0; i < file->message_type_count(); i++) {
+ FindProvidesForMessage(options, printer, file->message_type(i), provided);
+ }
+ for (int i = 0; i < file->enum_type_count(); i++) {
+ FindProvidesForEnum(options, printer, file->enum_type(i), provided);
+ }
+}
+
+void Generator::FindProvides(const GeneratorOptions& options,
+ io::Printer* printer,
+ const vector<const FileDescriptor*>& files,
+ std::set<string>* provided) const {
+ for (int i = 0; i < files.size(); i++) {
+ FindProvidesForFile(options, printer, files[i], provided);
+ }
+
+ printer->Print("\n");
+}
+
+void Generator::FindProvidesForMessage(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc,
+ std::set<string>* provided) const {
+ if (IgnoreMessage(options, desc)) {
+ return;
+ }
+
+ string name = GetPath(options, desc);
+ provided->insert(name);
+
+ for (int i = 0; i < desc->enum_type_count(); i++) {
+ FindProvidesForEnum(options, printer, desc->enum_type(i),
+ provided);
+ }
+ for (int i = 0; i < desc->nested_type_count(); i++) {
+ FindProvidesForMessage(options, printer, desc->nested_type(i),
+ provided);
+ }
+}
+
+void Generator::FindProvidesForEnum(const GeneratorOptions& options,
+ io::Printer* printer,
+ const EnumDescriptor* enumdesc,
+ std::set<string>* provided) const {
+ string name = GetPath(options, enumdesc);
+ provided->insert(name);
+}
+
+void Generator::FindProvidesForFields(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const vector<const FieldDescriptor*>& fields,
+ std::set<string>* provided) const {
+ for (int i = 0; i < fields.size(); i++) {
+ const FieldDescriptor* field = fields[i];
+
+ if (IgnoreField(field)) {
+ continue;
+ }
+
+ string name =
+ GetPath(options, field->file()) + "." +
+ JSObjectFieldName(options, field);
+ provided->insert(name);
+ }
+}
+
+void Generator::GenerateProvides(const GeneratorOptions& options,
+ io::Printer* printer,
+ std::set<string>* provided) const {
+ for (std::set<string>::iterator it = provided->begin();
+ it != provided->end(); ++it) {
+ printer->Print("goog.provide('$name$');\n",
+ "name", *it);
+ }
+}
+
+void Generator::GenerateRequiresForMessage(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc,
+ std::set<string>* provided) const {
+ std::set<string> required;
+ std::set<string> forwards;
+ bool have_message = false;
+ FindRequiresForMessage(options, desc,
+ &required, &forwards, &have_message);
+
+ GenerateRequiresImpl(options, printer, &required, &forwards, provided,
+ /* require_jspb = */ have_message,
+ /* require_extension = */ HasExtensions(desc));
+}
+
+void Generator::GenerateRequiresForLibrary(
+ const GeneratorOptions& options, io::Printer* printer,
+ const vector<const FileDescriptor*>& files,
+ std::set<string>* provided) const {
+ GOOGLE_CHECK_EQ(options.import_style, GeneratorOptions::IMPORT_CLOSURE);
+ // For Closure imports we need to import every message type individually.
+ std::set<string> required;
+ std::set<string> forwards;
+ bool have_extensions = false;
+ bool have_message = false;
+
+ for (int i = 0; i < files.size(); i++) {
+ for (int j = 0; j < files[i]->message_type_count(); j++) {
+ const Descriptor* desc = files[i]->message_type(j);
+ if (!IgnoreMessage(options, desc)) {
+ FindRequiresForMessage(options, desc, &required, &forwards,
+ &have_message);
+ }
+ }
+
+ if (!have_extensions && HasExtensions(files[i])) {
+ have_extensions = true;
+ }
+
+ for (int j = 0; j < files[i]->extension_count(); j++) {
+ const FieldDescriptor* extension = files[i]->extension(j);
+ if (IgnoreField(extension)) {
+ continue;
+ }
+ if (extension->containing_type()->full_name() !=
+ "google.protobuf.bridge.MessageSet") {
+ required.insert(GetPath(options, extension->containing_type()));
+ }
+ FindRequiresForField(options, extension, &required, &forwards);
+ have_extensions = true;
+ }
+ }
+
+ GenerateRequiresImpl(options, printer, &required, &forwards, provided,
+ /* require_jspb = */ have_message,
+ /* require_extension = */ have_extensions);
+}
+
+void Generator::GenerateRequiresForExtensions(
+ const GeneratorOptions& options, io::Printer* printer,
+ const vector<const FieldDescriptor*>& fields,
+ std::set<string>* provided) const {
+ std::set<string> required;
+ std::set<string> forwards;
+ for (int i = 0; i < fields.size(); i++) {
+ const FieldDescriptor* field = fields[i];
+ if (IgnoreField(field)) {
+ continue;
+ }
+ FindRequiresForExtension(options, field, &required, &forwards);
+ }
+
+ GenerateRequiresImpl(options, printer, &required, &forwards, provided,
+ /* require_jspb = */ false,
+ /* require_extension = */ fields.size() > 0);
+}
+
+void Generator::GenerateRequiresImpl(const GeneratorOptions& options,
+ io::Printer* printer,
+ std::set<string>* required,
+ std::set<string>* forwards,
+ std::set<string>* provided,
+ bool require_jspb,
+ bool require_extension) const {
+ if (require_jspb) {
+ printer->Print(
+ "goog.require('jspb.Message');\n");
+ if (options.binary) {
+ printer->Print(
+ "goog.require('jspb.BinaryReader');\n"
+ "goog.require('jspb.BinaryWriter');\n");
+ }
+ }
+ if (require_extension) {
+ printer->Print(
+ "goog.require('jspb.ExtensionFieldInfo');\n");
+ }
+
+ std::set<string>::iterator it;
+ for (it = required->begin(); it != required->end(); ++it) {
+ if (provided->find(*it) != provided->end()) {
+ continue;
+ }
+ printer->Print("goog.require('$name$');\n",
+ "name", *it);
+ }
+
+ printer->Print("\n");
+
+ for (it = forwards->begin(); it != forwards->end(); ++it) {
+ if (provided->find(*it) != provided->end()) {
+ continue;
+ }
+ printer->Print("goog.forwardDeclare('$name$');\n",
+ "name", *it);
+ }
+}
+
+bool NamespaceOnly(const Descriptor* desc) {
+ return false;
+}
+
+void Generator::FindRequiresForMessage(
+ const GeneratorOptions& options,
+ const Descriptor* desc,
+ std::set<string>* required,
+ std::set<string>* forwards,
+ bool* have_message) const {
+
+
+ if (!NamespaceOnly(desc)) {
+ *have_message = true;
+ for (int i = 0; i < desc->field_count(); i++) {
+ const FieldDescriptor* field = desc->field(i);
+ if (IgnoreField(field)) {
+ continue;
+ }
+ FindRequiresForField(options, field, required, forwards);
+ }
+ }
+
+ for (int i = 0; i < desc->extension_count(); i++) {
+ const FieldDescriptor* field = desc->extension(i);
+ if (IgnoreField(field)) {
+ continue;
+ }
+ FindRequiresForExtension(options, field, required, forwards);
+ }
+
+ for (int i = 0; i < desc->nested_type_count(); i++) {
+ FindRequiresForMessage(options, desc->nested_type(i), required, forwards,
+ have_message);
+ }
+}
+
+void Generator::FindRequiresForField(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ std::set<string>* required,
+ std::set<string>* forwards) const {
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM &&
+ // N.B.: file-level extensions with enum type do *not* create
+ // dependencies, as per original codegen.
+ !(field->is_extension() && field->extension_scope() == NULL)) {
+ if (options.add_require_for_enums) {
+ required->insert(GetPath(options, field->enum_type()));
+ } else {
+ forwards->insert(GetPath(options, field->enum_type()));
+ }
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (!IgnoreMessage(options, field->message_type())) {
+ required->insert(GetPath(options, field->message_type()));
+ }
+ }
+}
+
+void Generator::FindRequiresForExtension(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ std::set<string>* required,
+ std::set<string>* forwards) const {
+ if (field->containing_type()->full_name() != "google.protobuf.bridge.MessageSet") {
+ required->insert(GetPath(options, field->containing_type()));
+ }
+ FindRequiresForField(options, field, required, forwards);
+}
+
+void Generator::GenerateTestOnly(const GeneratorOptions& options,
+ io::Printer* printer) const {
+ if (options.testonly) {
+ printer->Print("goog.setTestOnly();\n\n");
+ }
+ printer->Print("\n");
+}
+
+void Generator::GenerateClassesAndEnums(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* file) const {
+ for (int i = 0; i < file->message_type_count(); i++) {
+ GenerateClass(options, printer, file->message_type(i));
+ }
+ for (int i = 0; i < file->enum_type_count(); i++) {
+ GenerateEnum(options, printer, file->enum_type(i));
+ }
+}
+
+void Generator::GenerateClass(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ if (IgnoreMessage(options, desc)) {
+ return;
+ }
+
+ if (!NamespaceOnly(desc)) {
+ printer->Print("\n");
+ GenerateClassConstructor(options, printer, desc);
+ GenerateClassFieldInfo(options, printer, desc);
+
+
+ GenerateClassToObject(options, printer, desc);
+ if (options.binary) {
+ // These must come *before* the extension-field info generation in
+ // GenerateClassRegistration so that references to the binary
+ // serialization/deserialization functions may be placed in the extension
+ // objects.
+ GenerateClassDeserializeBinary(options, printer, desc);
+ GenerateClassSerializeBinary(options, printer, desc);
+ }
+ GenerateClassClone(options, printer, desc);
+ GenerateClassRegistration(options, printer, desc);
+ GenerateClassFields(options, printer, desc);
+ if (IsExtendable(desc) && desc->full_name() != "google.protobuf.bridge.MessageSet") {
+ GenerateClassExtensionFieldInfo(options, printer, desc);
+ }
+
+ if (options.import_style != GeneratorOptions:: IMPORT_CLOSURE) {
+ for (int i = 0; i < desc->extension_count(); i++) {
+ GenerateExtension(options, printer, desc->extension(i));
+ }
+ }
+ }
+
+ // Recurse on nested types.
+ for (int i = 0; i < desc->enum_type_count(); i++) {
+ GenerateEnum(options, printer, desc->enum_type(i));
+ }
+ for (int i = 0; i < desc->nested_type_count(); i++) {
+ GenerateClass(options, printer, desc->nested_type(i));
+ }
+}
+
+void Generator::GenerateClassConstructor(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ printer->Print(
+ "/**\n"
+ " * Generated by JsPbCodeGenerator.\n"
+ " * @param {Array=} opt_data Optional initial data array, typically "
+ "from a\n"
+ " * server response, or constructed directly in Javascript. The array "
+ "is used\n"
+ " * in place and becomes part of the constructed object. It is not "
+ "cloned.\n"
+ " * If no data is provided, the constructed object will be empty, but "
+ "still\n"
+ " * valid.\n"
+ " * @extends {jspb.Message}\n"
+ " * @constructor\n"
+ " */\n"
+ "$classname$ = function(opt_data) {\n",
+ "classname", GetPath(options, desc));
+ string message_id = GetMessageId(desc);
+ printer->Print(
+ " jspb.Message.initialize(this, opt_data, $messageId$, $pivot$, "
+ "$rptfields$, $oneoffields$);\n",
+ "messageId", !message_id.empty() ?
+ ("'" + message_id + "'") :
+ (IsResponse(desc) ? "''" : "0"),
+ "pivot", GetPivot(desc),
+ "rptfields", RepeatedFieldsArrayName(options, desc),
+ "oneoffields", OneofFieldsArrayName(options, desc));
+ printer->Print(
+ "};\n"
+ "goog.inherits($classname$, jspb.Message);\n"
+ "if (goog.DEBUG && !COMPILED) {\n"
+ " $classname$.displayName = '$classname$';\n"
+ "}\n",
+ "classname", GetPath(options, desc));
+}
+
+void Generator::GenerateClassFieldInfo(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ if (HasRepeatedFields(desc)) {
+ printer->Print(
+ "/**\n"
+ " * List of repeated fields within this message type.\n"
+ " * @private {!Array<number>}\n"
+ " * @const\n"
+ " */\n"
+ "$classname$$rptfieldarray$ = $rptfields$;\n"
+ "\n",
+ "classname", GetPath(options, desc),
+ "rptfieldarray", kRepeatedFieldArrayName,
+ "rptfields", RepeatedFieldNumberList(desc));
+ }
+
+ if (HasOneofFields(desc)) {
+ printer->Print(
+ "/**\n"
+ " * Oneof group definitions for this message. Each group defines the "
+ "field\n"
+ " * numbers belonging to that group. When of these fields' value is "
+ "set, all\n"
+ " * other fields in the group are cleared. During deserialization, if "
+ "multiple\n"
+ " * fields are encountered for a group, only the last value seen will "
+ "be kept.\n"
+ " * @private {!Array<!Array<number>>}\n"
+ " * @const\n"
+ " */\n"
+ "$classname$$oneofgrouparray$ = $oneofgroups$;\n"
+ "\n",
+ "classname", GetPath(options, desc),
+ "oneofgrouparray", kOneofGroupArrayName,
+ "oneofgroups", OneofGroupList(desc));
+
+ for (int i = 0; i < desc->oneof_decl_count(); i++) {
+ if (IgnoreOneof(desc->oneof_decl(i))) {
+ continue;
+ }
+ GenerateOneofCaseDefinition(options, printer, desc->oneof_decl(i));
+ }
+ }
+}
+
+void Generator::GenerateClassXid(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ printer->Print(
+ "\n"
+ "\n"
+ "$class$.prototype.messageXid = xid('$class$');\n",
+ "class", GetPath(options, desc));
+}
+
+void Generator::GenerateOneofCaseDefinition(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const OneofDescriptor* oneof) const {
+ printer->Print(
+ "/**\n"
+ " * @enum {number}\n"
+ " */\n"
+ "$classname$.$oneof$Case = {\n"
+ " $upcase$_NOT_SET: 0",
+ "classname", GetPath(options, oneof->containing_type()),
+ "oneof", JSOneofName(oneof),
+ "upcase", ToEnumCase(oneof->name()));
+
+ for (int i = 0; i < oneof->field_count(); i++) {
+ if (IgnoreField(oneof->field(i))) {
+ continue;
+ }
+
+ printer->Print(
+ ",\n"
+ " $upcase$: $number$",
+ "upcase", ToEnumCase(oneof->field(i)->name()),
+ "number", JSFieldIndex(oneof->field(i)));
+ }
+
+ printer->Print(
+ "\n"
+ "};\n"
+ "\n"
+ "/**\n"
+ " * @return {$class$.$oneof$Case}\n"
+ " */\n"
+ "$class$.prototype.get$oneof$Case = function() {\n"
+ " return /** @type {$class$.$oneof$Case} */(jspb.Message."
+ "computeOneofCase(this, $class$.oneofGroups_[$oneofindex$]));\n"
+ "};\n"
+ "\n",
+ "class", GetPath(options, oneof->containing_type()),
+ "oneof", JSOneofName(oneof),
+ "oneofindex", JSOneofIndex(oneof));
+}
+
+void Generator::GenerateClassToObject(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ printer->Print(
+ "\n"
+ "\n"
+ "if (jspb.Message.GENERATE_TO_OBJECT) {\n"
+ "/**\n"
+ " * Creates an object representation of this proto suitable for use in "
+ "Soy templates.\n"
+ " * Field names that are reserved in JavaScript and will be renamed to "
+ "pb_name.\n"
+ " * To access a reserved field use, foo.pb_<name>, eg, foo.pb_default.\n"
+ " * For the list of reserved names please see:\n"
+ " * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.\n"
+ " * @param {boolean=} opt_includeInstance Whether to include the JSPB "
+ "instance\n"
+ " * for transitional soy proto support: http://goto/soy-param-"
+ "migration\n"
+ " * @return {!Object}\n"
+ " */\n"
+ "$classname$.prototype.toObject = function(opt_includeInstance) {\n"
+ " return $classname$.toObject(opt_includeInstance, this);\n"
+ "};\n"
+ "\n"
+ "\n"
+ "/**\n"
+ " * Static version of the {@see toObject} method.\n"
+ " * @param {boolean|undefined} includeInstance Whether to include the "
+ "JSPB\n"
+ " * instance for transitional soy proto support:\n"
+ " * http://goto/soy-param-migration\n"
+ " * @param {!$classname$} msg The msg instance to transform.\n"
+ " * @return {!Object}\n"
+ " */\n"
+ "$classname$.toObject = function(includeInstance, msg) {\n"
+ " var f, obj = {",
+ "classname", GetPath(options, desc));
+
+ bool first = true;
+ for (int i = 0; i < desc->field_count(); i++) {
+ const FieldDescriptor* field = desc->field(i);
+ if (IgnoreField(field)) {
+ continue;
+ }
+
+ if (!first) {
+ printer->Print(",\n ");
+ } else {
+ printer->Print("\n ");
+ first = false;
+ }
+
+ GenerateClassFieldToObject(options, printer, field);
+ }
+
+ if (!first) {
+ printer->Print("\n };\n\n");
+ } else {
+ printer->Print("\n\n };\n\n");
+ }
+
+ if (IsExtendable(desc)) {
+ printer->Print(
+ " jspb.Message.toObjectExtension(/** @type {!jspb.Message} */ (msg), "
+ "obj,\n"
+ " $extObject$, $class$.prototype.getExtension,\n"
+ " includeInstance);\n",
+ "extObject", JSExtensionsObjectName(options, desc->file(), desc),
+ "class", GetPath(options, desc));
+ }
+
+ printer->Print(
+ " if (includeInstance) {\n"
+ " obj.$$jspbMessageInstance = msg;\n"
+ " }\n"
+ " return obj;\n"
+ "};\n"
+ "}\n"
+ "\n"
+ "\n",
+ "classname", GetPath(options, desc));
+}
+
+void Generator::GenerateClassFieldToObject(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const {
+ printer->Print("$fieldname$: ",
+ "fieldname", JSObjectFieldName(options, field));
+
+ if (field->is_map()) {
+ printer->Print("(f = msg.get$name$(true)) ? f.toArray() : []",
+ "name", JSGetterName(options, field));
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Message field.
+ if (field->is_repeated()) {
+ {
+ printer->Print("jspb.Message.toObjectList(msg.get$getter$(),\n"
+ " $type$.toObject, includeInstance)",
+ "getter", JSGetterName(options, field),
+ "type", SubmessageTypeRef(options, field));
+ }
+ } else {
+ printer->Print("(f = msg.get$getter$()) && "
+ "$type$.toObject(includeInstance, f)",
+ "getter", JSGetterName(options, field),
+ "type", SubmessageTypeRef(options, field));
+ }
+ } else {
+ // Simple field (singular or repeated).
+ if ((!HasFieldPresence(field) && !field->is_repeated()) ||
+ field->type() == FieldDescriptor::TYPE_BYTES) {
+ // Delegate to the generated get<field>() method in order not to duplicate
+ // the proto3-field-default-value or byte-coercion logic here.
+ printer->Print("msg.get$getter$()",
+ "getter", JSGetterName(options, field, BYTES_B64));
+ } else {
+ if (field->has_default_value()) {
+ printer->Print("!msg.has$name$() ? $defaultValue$ : ",
+ "name", JSGetterName(options, field),
+ "defaultValue", JSFieldDefault(field));
+ }
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_FLOAT ||
+ field->cpp_type() == FieldDescriptor::CPPTYPE_DOUBLE) {
+ if (field->is_repeated()) {
+ printer->Print("jspb.Message.getRepeatedFloatingPointField("
+ "msg, $index$)",
+ "index", JSFieldIndex(field));
+ } else if (field->is_optional() && !field->has_default_value()) {
+ printer->Print("jspb.Message.getOptionalFloatingPointField("
+ "msg, $index$)",
+ "index", JSFieldIndex(field));
+ } else {
+ // Convert "NaN" to NaN.
+ printer->Print("+jspb.Message.getField(msg, $index$)",
+ "index", JSFieldIndex(field));
+ }
+ } else {
+ printer->Print("jspb.Message.getField(msg, $index$)",
+ "index", JSFieldIndex(field));
+ }
+ }
+ }
+}
+
+void Generator::GenerateClassFromObject(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ printer->Print(
+ "if (jspb.Message.GENERATE_FROM_OBJECT) {\n"
+ "/**\n"
+ " * Loads data from an object into a new instance of this proto.\n"
+ " * @param {!Object} obj The object representation of this proto to\n"
+ " * load the data from.\n"
+ " * @return {!$classname$}\n"
+ " */\n"
+ "$classname$.fromObject = function(obj) {\n"
+ " var f, msg = new $classname$();\n",
+ "classname", GetPath(options, desc));
+
+ for (int i = 0; i < desc->field_count(); i++) {
+ const FieldDescriptor* field = desc->field(i);
+ GenerateClassFieldFromObject(options, printer, field);
+ }
+
+ printer->Print(
+ " return msg;\n"
+ "};\n"
+ "}\n");
+}
+
+void Generator::GenerateClassFieldFromObject(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const {
+
+ if (field->is_map()) {
+ // `msg` is a newly-constructed message object that has not yet built any
+ // map containers wrapping underlying arrays, so we can simply directly set
+ // the array here without fear of a stale wrapper.
+ printer->Print(
+ " goog.isDef(obj.$name$) && "
+ "jspb.Message.setField(msg, $index$, obj.$name$);\n",
+ "name", JSObjectFieldName(options, field),
+ "index", JSFieldIndex(field));
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Message field (singular or repeated)
+ if (field->is_repeated()) {
+ {
+ printer->Print(
+ " goog.isDef(obj.$name$) && "
+ "jspb.Message.setRepeatedWrapperField(\n"
+ " msg, $index$, goog.array.map(obj.$name$, function(i) {\n"
+ " return $fieldclass$.fromObject(i);\n"
+ " }));\n",
+ "name", JSObjectFieldName(options, field),
+ "index", JSFieldIndex(field),
+ "fieldclass", SubmessageTypeRef(options, field));
+ }
+ } else {
+ printer->Print(
+ " goog.isDef(obj.$name$) && jspb.Message.setWrapperField(\n"
+ " msg, $index$, $fieldclass$.fromObject(obj.$name$));\n",
+ "name", JSObjectFieldName(options, field),
+ "index", JSFieldIndex(field),
+ "fieldclass", SubmessageTypeRef(options, field));
+ }
+ } else {
+ // Simple (primitive) field.
+ printer->Print(
+ " goog.isDef(obj.$name$) && jspb.Message.setField(msg, $index$, "
+ "obj.$name$);\n",
+ "name", JSObjectFieldName(options, field),
+ "index", JSFieldIndex(field));
+ }
+}
+
+void Generator::GenerateClassClone(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ printer->Print(
+ "/**\n"
+ " * Creates a deep clone of this proto. No data is shared with the "
+ "original.\n"
+ " * @return {!$name$} The clone.\n"
+ " */\n"
+ "$name$.prototype.cloneMessage = function() {\n"
+ " return /** @type {!$name$} */ (jspb.Message.cloneMessage(this));\n"
+ "};\n\n\n",
+ "name", GetPath(options, desc));
+}
+
+void Generator::GenerateClassRegistration(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ // Register any extensions defined inside this message type.
+ for (int i = 0; i < desc->extension_count(); i++) {
+ const FieldDescriptor* extension = desc->extension(i);
+ if (ShouldGenerateExtension(extension)) {
+ GenerateExtension(options, printer, extension);
+ }
+ }
+
+}
+
+void Generator::GenerateClassFields(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ for (int i = 0; i < desc->field_count(); i++) {
+ if (!IgnoreField(desc->field(i))) {
+ GenerateClassField(options, printer, desc->field(i));
+ }
+ }
+}
+
+void GenerateBytesWrapper(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field,
+ BytesMode bytes_mode) {
+ string type =
+ JSFieldTypeAnnotation(options, field,
+ /* force_optional = */ false,
+ /* force_present = */ !HasFieldPresence(field),
+ /* singular_if_not_packed = */ false,
+ bytes_mode);
+ printer->Print(
+ "/**\n"
+ " * $fielddef$\n"
+ "$comment$"
+ " * This is a type-conversion wrapper around `get$defname$()`\n"
+ " * @return {$type$}\n"
+ " */\n"
+ "$class$.prototype.get$name$ = function() {\n"
+ " return /** @type {$type$} */ (jspb.Message.bytes$list$As$suffix$(\n"
+ " this.get$defname$()));\n"
+ "};\n"
+ "\n"
+ "\n",
+ "fielddef", FieldDefinition(options, field),
+ "comment", FieldComments(field, bytes_mode),
+ "type", type,
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field, bytes_mode),
+ "list", field->is_repeated() ? "List" : "",
+ "suffix", JSByteGetterSuffix(bytes_mode),
+ "defname", JSGetterName(options, field, BYTES_DEFAULT));
+}
+
+
+void Generator::GenerateClassField(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const {
+ if (field->is_map()) {
+ const FieldDescriptor* key_field = MapFieldKey(field);
+ const FieldDescriptor* value_field = MapFieldValue(field);
+ // Map field: special handling to instantiate the map object on demand.
+ string key_type =
+ JSFieldTypeAnnotation(
+ options, key_field,
+ /* force_optional = */ false,
+ /* force_present = */ true,
+ /* singular_if_not_packed = */ false);
+ string value_type =
+ JSFieldTypeAnnotation(
+ options, value_field,
+ /* force_optional = */ false,
+ /* force_present = */ true,
+ /* singular_if_not_packed = */ false);
+
+ printer->Print(
+ "/**\n"
+ " * $fielddef$\n"
+ " * @param {boolean=} opt_noLazyCreate Do not create the map if\n"
+ " * empty, instead returning `undefined`\n"
+ " * @return {!jspb.Map<$keytype$,$valuetype$>}\n"
+ " */\n",
+ "fielddef", FieldDefinition(options, field),
+ "keytype", key_type,
+ "valuetype", value_type);
+ printer->Print(
+ "$class$.prototype.get$name$ = function(opt_noLazyCreate) {\n"
+ " return /** @type {!jspb.Map<$keytype$,$valuetype$>} */ (\n",
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field),
+ "keytype", key_type,
+ "valuetype", value_type);
+ printer->Print(
+ " jspb.Message.getMapField(this, $index$, opt_noLazyCreate",
+ "index", JSFieldIndex(field));
+
+ if (value_field->type() == FieldDescriptor::TYPE_MESSAGE) {
+ printer->Print(",\n"
+ " $messageType$",
+ "messageType", GetPath(options, value_field->message_type()));
+ } else if (options.binary) {
+ printer->Print(",\n"
+ " null");
+ }
+
+ printer->Print(
+ "));\n");
+
+ printer->Print(
+ "};\n"
+ "\n"
+ "\n");
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Message field: special handling in order to wrap the underlying data
+ // array with a message object.
+
+ printer->Print(
+ "/**\n"
+ " * $fielddef$\n"
+ "$comment$"
+ " * @return {$type$}\n"
+ " */\n",
+ "fielddef", FieldDefinition(options, field),
+ "comment", FieldComments(field, BYTES_DEFAULT),
+ "type", JSFieldTypeAnnotation(options, field,
+ /* force_optional = */ false,
+ /* force_present = */ false,
+ /* singular_if_not_packed = */ false));
+ printer->Print(
+ "$class$.prototype.get$name$ = function() {\n"
+ " return /** @type{$type$} */ (\n"
+ " jspb.Message.get$rpt$WrapperField(this, $wrapperclass$, "
+ "$index$$required$));\n"
+ "};\n"
+ "\n"
+ "\n",
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field),
+ "type", JSFieldTypeAnnotation(options, field,
+ /* force_optional = */ false,
+ /* force_present = */ false,
+ /* singular_if_not_packed = */ false),
+ "rpt", (field->is_repeated() ? "Repeated" : ""),
+ "index", JSFieldIndex(field),
+ "wrapperclass", SubmessageTypeRef(options, field),
+ "required", (field->label() == FieldDescriptor::LABEL_REQUIRED ?
+ ", 1" : ""));
+ printer->Print(
+ "/** @param {$optionaltype$} value $returndoc$ */\n"
+ "$class$.prototype.set$name$ = function(value) {\n"
+ " jspb.Message.set$oneoftag$$repeatedtag$WrapperField(",
+ "optionaltype",
+ JSFieldTypeAnnotation(options, field,
+ /* force_optional = */ true,
+ /* force_present = */ false,
+ /* singular_if_not_packed = */ false),
+ "returndoc", JSReturnDoc(options, field),
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field),
+ "oneoftag", (field->containing_oneof() ? "Oneof" : ""),
+ "repeatedtag", (field->is_repeated() ? "Repeated" : ""));
+
+ printer->Print(
+ "this, $index$$oneofgroup$, value);$returnvalue$\n"
+ "};\n"
+ "\n"
+ "\n",
+ "index", JSFieldIndex(field),
+ "oneofgroup", (field->containing_oneof() ?
+ (", " + JSOneofArray(options, field)) : ""),
+ "returnvalue", JSReturnClause(field));
+
+ printer->Print(
+ "$class$.prototype.clear$name$ = function() {\n"
+ " this.set$name$($clearedvalue$);$returnvalue$\n"
+ "};\n"
+ "\n"
+ "\n",
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field),
+ "clearedvalue", (field->is_repeated() ? "[]" : "undefined"),
+ "returnvalue", JSReturnClause(field));
+
+ } else {
+ bool untyped =
+ false;
+
+ // Simple (primitive) field, either singular or repeated.
+
+ // TODO(b/26173701): Always use BYTES_DEFAULT for the getter return type;
+ // at this point we "lie" to non-binary users and tell the the return
+ // type is always base64 string, pending a LSC to migrate to typed getters.
+ BytesMode bytes_mode =
+ field->type() == FieldDescriptor::TYPE_BYTES && !options.binary ?
+ BYTES_B64 : BYTES_DEFAULT;
+ string typed_annotation =
+ JSFieldTypeAnnotation(options, field,
+ /* force_optional = */ false,
+ /* force_present = */ !HasFieldPresence(field),
+ /* singular_if_not_packed = */ false,
+ /* bytes_mode = */ bytes_mode);
+ if (untyped) {
+ printer->Print(
+ "/**\n"
+ " * @return {?} Raw field, untyped.\n"
+ " */\n");
+ } else {
+ printer->Print(
+ "/**\n"
+ " * $fielddef$\n"
+ "$comment$"
+ " * @return {$type$}\n"
+ " */\n",
+ "fielddef", FieldDefinition(options, field),
+ "comment", FieldComments(field, bytes_mode),
+ "type", typed_annotation);
+ }
+
+ printer->Print(
+ "$class$.prototype.get$name$ = function() {\n",
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field));
+
+ if (untyped) {
+ printer->Print(
+ " return ");
+ } else {
+ printer->Print(
+ " return /** @type {$type$} */ (",
+ "type", typed_annotation);
+ }
+
+ // For proto3 fields without presence, use special getters that will return
+ // defaults when the field is unset, possibly constructing a value if
+ // required.
+ if (!HasFieldPresence(field) && !field->is_repeated()) {
+ printer->Print("jspb.Message.getFieldProto3(this, $index$, $default$)",
+ "index", JSFieldIndex(field),
+ "default", Proto3PrimitiveFieldDefault(field));
+ } else {
+ if (!field->is_repeated()) {
+ printer->Print("!this.has$name$() ? $defaultValue$ : ",
+ "name", JSGetterName(options, field),
+ "defaultValue", JSFieldDefault(field));
+ }
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_FLOAT ||
+ field->cpp_type() == FieldDescriptor::CPPTYPE_DOUBLE) {
+ if (field->is_repeated()) {
+ printer->Print("jspb.Message.getRepeatedFloatingPointField("
+ "this, $index$)",
+ "index", JSFieldIndex(field));
+ } else {
+ // Convert "NaN" to NaN.
+ printer->Print("+jspb.Message.getField(this, $index$)",
+ "index", JSFieldIndex(field));
+ }
+ } else {
+ printer->Print("jspb.Message.getField(this, $index$)",
+ "index", JSFieldIndex(field));
+ }
+ }
+
+ if (untyped) {
+ printer->Print(
+ ";\n"
+ "};\n"
+ "\n"
+ "\n");
+ } else {
+ printer->Print(
+ ");\n"
+ "};\n"
+ "\n"
+ "\n");
+ }
+
+ if (field->type() == FieldDescriptor::TYPE_BYTES && !untyped) {
+ GenerateBytesWrapper(options, printer, field, BYTES_B64);
+ GenerateBytesWrapper(options, printer, field, BYTES_U8);
+ }
+
+ if (untyped) {
+ printer->Print(
+ "/**\n"
+ " * @param {*} value $returndoc$\n"
+ " */\n",
+ "returndoc", JSReturnDoc(options, field));
+ } else {
+ printer->Print(
+ "/** @param {$optionaltype$} value $returndoc$ */\n",
+ "optionaltype",
+ JSFieldTypeAnnotation(options, field,
+ /* force_optional = */ true,
+ /* force_present = */ !HasFieldPresence(field),
+ /* singular_if_not_packed = */ false),
+ "returndoc", JSReturnDoc(options, field));
+ }
+ printer->Print(
+ "$class$.prototype.set$name$ = function(value) {\n"
+ " jspb.Message.set$oneoftag$Field(this, $index$",
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field),
+ "oneoftag", (field->containing_oneof() ? "Oneof" : ""),
+ "index", JSFieldIndex(field));
+ printer->Print(
+ "$oneofgroup$, $type$value$rptvalueinit$$typeclose$);$returnvalue$\n"
+ "};\n"
+ "\n"
+ "\n",
+ "type",
+ untyped ? "/** @type{string|number|boolean|Array|undefined} */(" : "",
+ "typeclose", untyped ? ")" : "",
+ "oneofgroup",
+ (field->containing_oneof() ? (", " + JSOneofArray(options, field))
+ : ""),
+ "returnvalue", JSReturnClause(field), "rptvalueinit",
+ (field->is_repeated() ? " || []" : ""));
+
+ if (untyped) {
+ printer->Print(
+ "/**\n"
+ " * Clears the value. $returndoc$\n"
+ " */\n",
+ "returndoc", JSReturnDoc(options, field));
+ }
+
+ if (HasFieldPresence(field) || field->is_repeated()) {
+ printer->Print(
+ "$class$.prototype.clear$name$ = function() {\n"
+ " jspb.Message.set$oneoftag$Field(this, $index$$oneofgroup$, ",
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field),
+ "oneoftag", (field->containing_oneof() ? "Oneof" : ""),
+ "oneofgroup", (field->containing_oneof() ?
+ (", " + JSOneofArray(options, field)) : ""),
+ "index", JSFieldIndex(field));
+ printer->Print(
+ "$clearedvalue$);$returnvalue$\n"
+ "};\n"
+ "\n"
+ "\n",
+ "clearedvalue", (field->is_repeated() ? "[]" : "undefined"),
+ "returnvalue", JSReturnClause(field));
+ }
+ }
+
+ if (HasFieldPresence(field)) {
+ printer->Print(
+ "/**\n"
+ " * Returns whether this field is set.\n"
+ " * @return{!boolean}\n"
+ " */\n"
+ "$class$.prototype.has$name$ = function() {\n"
+ " return jspb.Message.getField(this, $index$) != null;\n"
+ "};\n"
+ "\n"
+ "\n",
+ "class", GetPath(options, field->containing_type()),
+ "name", JSGetterName(options, field),
+ "index", JSFieldIndex(field));
+ }
+}
+
+void Generator::GenerateClassExtensionFieldInfo(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ if (IsExtendable(desc)) {
+ printer->Print(
+ "\n"
+ "/**\n"
+ " * The extensions registered with this message class. This is a "
+ "map of\n"
+ " * extension field number to fieldInfo object.\n"
+ " *\n"
+ " * For example:\n"
+ " * { 123: {fieldIndex: 123, fieldName: {my_field_name: 0}, "
+ "ctor: proto.example.MyMessage} }\n"
+ " *\n"
+ " * fieldName contains the JsCompiler renamed field name property "
+ "so that it\n"
+ " * works in OPTIMIZED mode.\n"
+ " *\n"
+ " * @type {!Object.<number, jspb.ExtensionFieldInfo>}\n"
+ " */\n"
+ "$class$.extensions = {};\n"
+ "\n",
+ "class", GetPath(options, desc));
+
+ if (options.binary) {
+ printer->Print(
+ "\n"
+ "/**\n"
+ " * The extensions registered with this message class. This is a "
+ "map of\n"
+ " * extension field number to fieldInfo object.\n"
+ " *\n"
+ " * For example:\n"
+ " * { 123: {fieldIndex: 123, fieldName: {my_field_name: 0}, "
+ "ctor: proto.example.MyMessage} }\n"
+ " *\n"
+ " * fieldName contains the JsCompiler renamed field name property "
+ "so that it\n"
+ " * works in OPTIMIZED mode.\n"
+ " *\n"
+ " * @type {!Object.<number, jspb.ExtensionFieldInfo>}\n"
+ " */\n"
+ "$class$.extensionsBinary = {};\n"
+ "\n",
+ "class", GetPath(options, desc));
+ }
+ }
+}
+
+
+void Generator::GenerateClassDeserializeBinary(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ // TODO(cfallin): Handle lazy decoding when requested by field option and/or
+ // by default for 'bytes' fields and packed repeated fields.
+
+ printer->Print(
+ "/**\n"
+ " * Deserializes binary data (in protobuf wire format).\n"
+ " * @param {jspb.ByteSource} bytes The bytes to deserialize.\n"
+ " * @return {!$class$}\n"
+ " */\n"
+ "$class$.deserializeBinary = function(bytes) {\n"
+ " var reader = new jspb.BinaryReader(bytes);\n"
+ " var msg = new $class$;\n"
+ " return $class$.deserializeBinaryFromReader(msg, reader);\n"
+ "};\n"
+ "\n"
+ "\n"
+ "/**\n"
+ " * Deserializes binary data (in protobuf wire format) from the\n"
+ " * given reader into the given message object.\n"
+ " * @param {!$class$} msg The message object to deserialize into.\n"
+ " * @param {!jspb.BinaryReader} reader The BinaryReader to use.\n"
+ " * @return {!$class$}\n"
+ " */\n"
+ "$class$.deserializeBinaryFromReader = function(msg, reader) {\n"
+ " while (reader.nextField()) {\n"
+ " if (reader.isEndGroup()) {\n"
+ " break;\n"
+ " }\n"
+ " var field = reader.getFieldNumber();\n"
+ " switch (field) {\n",
+ "class", GetPath(options, desc));
+
+ for (int i = 0; i < desc->field_count(); i++) {
+ GenerateClassDeserializeBinaryField(options, printer, desc->field(i));
+ }
+
+ printer->Print(
+ " default:\n");
+ if (IsExtendable(desc)) {
+ printer->Print(
+ " jspb.Message.readBinaryExtension(msg, reader, $extobj$Binary,\n"
+ " $class$.prototype.getExtension,\n"
+ " $class$.prototype.setExtension);\n"
+ " break;\n",
+ "extobj", JSExtensionsObjectName(options, desc->file(), desc),
+ "class", GetPath(options, desc));
+ } else {
+ printer->Print(
+ " reader.skipField();\n"
+ " break;\n");
+ }
+
+ printer->Print(
+ " }\n"
+ " }\n"
+ " return msg;\n"
+ "};\n"
+ "\n"
+ "\n");
+}
+
+void Generator::GenerateClassDeserializeBinaryField(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const {
+
+ printer->Print(" case $num$:\n",
+ "num", SimpleItoa(field->number()));
+
+ if (field->is_map()) {
+ const FieldDescriptor* key_field = MapFieldKey(field);
+ const FieldDescriptor* value_field = MapFieldValue(field);
+ printer->Print(
+ " var value = msg.get$name$();\n"
+ " reader.readMessage(value, function(message, reader) {\n",
+ "name", JSGetterName(options, field));
+
+ printer->Print(" jspb.Map.deserializeBinary(message, reader, "
+ "$keyReaderFn$, $valueReaderFn$",
+ "keyReaderFn", JSBinaryReaderMethodName(options, key_field),
+ "valueReaderFn", JSBinaryReaderMethodName(options, value_field));
+
+ if (value_field->type() == FieldDescriptor::TYPE_MESSAGE) {
+ printer->Print(", $messageType$.deserializeBinaryFromReader",
+ "messageType", GetPath(options, value_field->message_type()));
+ }
+
+ printer->Print(");\n");
+ printer->Print(" });\n");
+ } else {
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ printer->Print(
+ " var value = new $fieldclass$;\n"
+ " reader.read$msgOrGroup$($grpfield$value,"
+ "$fieldclass$.deserializeBinaryFromReader);\n",
+ "fieldclass", SubmessageTypeRef(options, field),
+ "msgOrGroup", (field->type() == FieldDescriptor::TYPE_GROUP) ?
+ "Group" : "Message",
+ "grpfield", (field->type() == FieldDescriptor::TYPE_GROUP) ?
+ (SimpleItoa(field->number()) + ", ") : "");
+ } else {
+ printer->Print(
+ " var value = /** @type {$fieldtype$} */ "
+ "(reader.read$reader$());\n",
+ "fieldtype", JSFieldTypeAnnotation(options, field, false, true,
+ /* singular_if_not_packed */ true,
+ BYTES_U8),
+ "reader",
+ JSBinaryReadWriteMethodName(field, /* is_writer = */ false));
+ }
+
+ if (field->is_repeated() && !field->is_packed()) {
+ // Repeated fields receive a |value| one at at a time; append to array
+ // returned by get$name$(). Annoyingly, we have to call 'set' after
+ // changing the array.
+ printer->Print(" msg.get$name$().push(value);\n", "name",
+ JSGetterName(options, field));
+ printer->Print(" msg.set$name$(msg.get$name$());\n", "name",
+ JSGetterName(options, field));
+ } else {
+ // Singular fields, and packed repeated fields, receive a |value| either
+ // as the field's value or as the array of all the field's values; set
+ // this as the field's value directly.
+ printer->Print(
+ " msg.set$name$(value);\n",
+ "name", JSGetterName(options, field));
+ }
+ }
+
+ printer->Print(" break;\n");
+}
+
+void Generator::GenerateClassSerializeBinary(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const {
+ printer->Print(
+ "/**\n"
+ " * Class method variant: serializes the given message to binary data\n"
+ " * (in protobuf wire format), writing to the given BinaryWriter.\n"
+ " * @param {!$class$} message\n"
+ " * @param {!jspb.BinaryWriter} writer\n"
+ " */\n"
+ "$class$.serializeBinaryToWriter = function(message, "
+ "writer) {\n"
+ " message.serializeBinaryToWriter(writer);\n"
+ "};\n"
+ "\n"
+ "\n"
+ "/**\n"
+ " * Serializes the message to binary data (in protobuf wire format).\n"
+ " * @return {!Uint8Array}\n"
+ " */\n"
+ "$class$.prototype.serializeBinary = function() {\n"
+ " var writer = new jspb.BinaryWriter();\n"
+ " this.serializeBinaryToWriter(writer);\n"
+ " return writer.getResultBuffer();\n"
+ "};\n"
+ "\n"
+ "\n"
+ "/**\n"
+ " * Serializes the message to binary data (in protobuf wire format),\n"
+ " * writing to the given BinaryWriter.\n"
+ " * @param {!jspb.BinaryWriter} writer\n"
+ " */\n"
+ "$class$.prototype.serializeBinaryToWriter = function (writer) {\n"
+ " var f = undefined;\n",
+ "class", GetPath(options, desc));
+
+ for (int i = 0; i < desc->field_count(); i++) {
+ GenerateClassSerializeBinaryField(options, printer, desc->field(i));
+ }
+
+ if (IsExtendable(desc)) {
+ printer->Print(
+ " jspb.Message.serializeBinaryExtensions(this, writer,\n"
+ " $extobj$Binary, $class$.prototype.getExtension);\n",
+ "extobj", JSExtensionsObjectName(options, desc->file(), desc),
+ "class", GetPath(options, desc));
+ }
+
+ printer->Print(
+ "};\n"
+ "\n"
+ "\n");
+}
+
+void Generator::GenerateClassSerializeBinaryField(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const {
+ if (HasFieldPresence(field) &&
+ field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ printer->Print(
+ " f = jspb.Message.getField(this, $index$);\n",
+ "index", JSFieldIndex(field));
+ } else {
+ printer->Print(
+ " f = this.get$name$($nolazy$);\n",
+ "name", JSGetterName(options, field, BYTES_U8),
+ // No lazy creation for maps containers -- fastpath the empty case.
+ "nolazy", (field->is_map()) ? "true" : "");
+ }
+
+
+ // Print an `if (condition)` statement that evaluates to true if the field
+ // goes on the wire.
+ if (field->is_map()) {
+ printer->Print(
+ " if (f && f.getLength() > 0) {\n");
+ } else if (field->is_repeated()) {
+ printer->Print(
+ " if (f.length > 0) {\n");
+ } else {
+ if (HasFieldPresence(field)) {
+ printer->Print(
+ " if (f != null) {\n");
+ } else {
+ // No field presence: serialize onto the wire only if value is
+ // non-default. Defaults are documented here:
+ // https://goto.google.com/lhdfm
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ case FieldDescriptor::CPPTYPE_INT64:
+ case FieldDescriptor::CPPTYPE_UINT32:
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ {
+ printer->Print(" if (f !== 0) {\n");
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_ENUM:
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ printer->Print(
+ " if (f !== 0.0) {\n");
+ break;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ printer->Print(
+ " if (f) {\n");
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ printer->Print(
+ " if (f.length > 0) {\n");
+ break;
+ default:
+ assert(false);
+ break;
+ }
+ }
+ }
+
+ // Write the field on the wire.
+ if (field->is_map()) {
+ const FieldDescriptor* key_field = MapFieldKey(field);
+ const FieldDescriptor* value_field = MapFieldValue(field);
+ printer->Print(
+ " f.serializeBinary($index$, writer, "
+ "$keyWriterFn$, $valueWriterFn$",
+ "index", SimpleItoa(field->number()),
+ "keyWriterFn", JSBinaryWriterMethodName(options, key_field),
+ "valueWriterFn", JSBinaryWriterMethodName(options, value_field));
+
+ if (value_field->type() == FieldDescriptor::TYPE_MESSAGE) {
+ printer->Print(", $messageType$.serializeBinaryToWriter",
+ "messageType", GetPath(options, value_field->message_type()));
+ }
+
+ printer->Print(");\n");
+ } else {
+ printer->Print(
+ " writer.write$method$(\n"
+ " $index$,\n"
+ " f",
+ "method", JSBinaryReadWriteMethodName(field, /* is_writer = */ true),
+ "index", SimpleItoa(field->number()));
+
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ !(field->is_map())) {
+ printer->Print(
+ ",\n"
+ " $submsg$.serializeBinaryToWriter\n",
+ "submsg", SubmessageTypeRef(options, field));
+ } else {
+ printer->Print("\n");
+ }
+
+ printer->Print(
+ " );\n");
+ }
+
+ // Close the `if`.
+ printer->Print(
+ " }\n");
+}
+
+void Generator::GenerateEnum(const GeneratorOptions& options,
+ io::Printer* printer,
+ const EnumDescriptor* enumdesc) const {
+ printer->Print(
+ "/**\n"
+ " * @enum {number}\n"
+ " */\n"
+ "$name$ = {\n",
+ "name", GetPath(options, enumdesc));
+
+ for (int i = 0; i < enumdesc->value_count(); i++) {
+ const EnumValueDescriptor* value = enumdesc->value(i);
+ printer->Print(
+ " $name$: $value$$comma$\n",
+ "name", ToEnumCase(value->name()),
+ "value", SimpleItoa(value->number()),
+ "comma", (i == enumdesc->value_count() - 1) ? "" : ",");
+ }
+
+ printer->Print(
+ "};\n"
+ "\n");
+}
+
+void Generator::GenerateExtension(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const {
+ string extension_scope =
+ (field->extension_scope() ?
+ GetPath(options, field->extension_scope()) :
+ GetPath(options, field->file()));
+
+ printer->Print(
+ "\n"
+ "/**\n"
+ " * A tuple of {field number, class constructor} for the extension\n"
+ " * field named `$name$`.\n"
+ " * @type {!jspb.ExtensionFieldInfo.<$extensionType$>}\n"
+ " */\n"
+ "$class$.$name$ = new jspb.ExtensionFieldInfo(\n",
+ "name", JSObjectFieldName(options, field),
+ "class", extension_scope,
+ "extensionType", JSFieldTypeAnnotation(
+ options, field,
+ /* force_optional = */ false,
+ /* force_present = */ true,
+ /* singular_if_not_packed = */ false));
+ printer->Print(
+ " $index$,\n"
+ " {$name$: 0},\n"
+ " $ctor$,\n"
+ " /** @type {?function((boolean|undefined),!jspb.Message=): "
+ "!Object} */ (\n"
+ " $toObject$),\n"
+ " $repeated$);\n",
+ "index", SimpleItoa(field->number()),
+ "name", JSObjectFieldName(options, field),
+ "ctor", (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE ?
+ SubmessageTypeRef(options, field) : string("null")),
+ "toObject", (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE ?
+ (SubmessageTypeRef(options, field) + ".toObject") :
+ string("null")),
+ "repeated", (field->is_repeated() ? "1" : "0"));
+
+ if (options.binary) {
+ printer->Print(
+ "\n"
+ "$extendName$Binary[$index$] = new jspb.ExtensionFieldBinaryInfo(\n"
+ " $class$.$name$,\n"
+ " $binaryReaderFn$,\n"
+ " $binaryWriterFn$,\n"
+ " $binaryMessageSerializeFn$,\n"
+ " $binaryMessageDeserializeFn$,\n",
+ "extendName", JSExtensionsObjectName(options, field->file(),
+ field->containing_type()),
+ "index", SimpleItoa(field->number()),
+ "class", extension_scope,
+ "name", JSObjectFieldName(options, field),
+ "binaryReaderFn", JSBinaryReaderMethodName(options, field),
+ "binaryWriterFn", JSBinaryWriterMethodName(options, field),
+ "binaryMessageSerializeFn",
+ (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) ?
+ (SubmessageTypeRef(options, field) +
+ ".serializeBinaryToWriter") : "null",
+ "binaryMessageDeserializeFn",
+ (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) ?
+ (SubmessageTypeRef(options, field) +
+ ".deserializeBinaryFromReader") : "null");
+
+ printer->Print(
+ " $isPacked$);\n",
+ "isPacked", (field->is_packed() ? "true" : "false"));
+ }
+
+ printer->Print(
+ "// This registers the extension field with the extended class, so that\n"
+ "// toObject() will function correctly.\n"
+ "$extendName$[$index$] = $class$.$name$;\n"
+ "\n",
+ "extendName", JSExtensionsObjectName(options, field->file(),
+ field->containing_type()),
+ "index", SimpleItoa(field->number()),
+ "class", extension_scope,
+ "name", JSObjectFieldName(options, field));
+}
+
+bool GeneratorOptions::ParseFromOptions(
+ const vector< pair< string, string > >& options,
+ string* error) {
+ for (int i = 0; i < options.size(); i++) {
+ if (options[i].first == "add_require_for_enums") {
+ if (options[i].second != "") {
+ *error = "Unexpected option value for add_require_for_enums";
+ return false;
+ }
+ add_require_for_enums = true;
+ } else if (options[i].first == "binary") {
+ if (options[i].second != "") {
+ *error = "Unexpected option value for binary";
+ return false;
+ }
+ binary = true;
+ } else if (options[i].first == "testonly") {
+ if (options[i].second != "") {
+ *error = "Unexpected option value for testonly";
+ return false;
+ }
+ testonly = true;
+ } else if (options[i].first == "error_on_name_conflict") {
+ if (options[i].second != "") {
+ *error = "Unexpected option value for error_on_name_conflict";
+ return false;
+ }
+ error_on_name_conflict = true;
+ } else if (options[i].first == "output_dir") {
+ output_dir = options[i].second;
+ } else if (options[i].first == "namespace_prefix") {
+ namespace_prefix = options[i].second;
+ } else if (options[i].first == "library") {
+ library = options[i].second;
+ } else if (options[i].first == "import_style") {
+ if (options[i].second == "closure") {
+ import_style = IMPORT_CLOSURE;
+ } else if (options[i].second == "commonjs") {
+ import_style = IMPORT_COMMONJS;
+ } else if (options[i].second == "browser") {
+ import_style = IMPORT_BROWSER;
+ } else if (options[i].second == "es6") {
+ import_style = IMPORT_ES6;
+ } else {
+ *error = "Unknown import style " + options[i].second + ", expected " +
+ "one of: closure, commonjs, browser, es6.";
+ }
+ } else {
+ // Assume any other option is an output directory, as long as it is a bare
+ // `key` rather than a `key=value` option.
+ if (options[i].second != "") {
+ *error = "Unknown option: " + options[i].first;
+ return false;
+ }
+ output_dir = options[i].first;
+ }
+ }
+
+ if (!library.empty() && import_style != IMPORT_CLOSURE) {
+ *error = "The library option should only be used for "
+ "import_style=closure";
+ }
+
+ return true;
+}
+
+void Generator::GenerateFilesInDepOrder(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const vector<const FileDescriptor*>& files) const {
+ // Build a std::set over all files so that the DFS can detect when it recurses
+ // into a dep not specified in the user's command line.
+ std::set<const FileDescriptor*> all_files(files.begin(), files.end());
+ // Track the in-progress set of files that have been generated already.
+ std::set<const FileDescriptor*> generated;
+ for (int i = 0; i < files.size(); i++) {
+ GenerateFileAndDeps(options, printer, files[i], &all_files, &generated);
+ }
+}
+
+void Generator::GenerateFileAndDeps(
+ const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* root,
+ std::set<const FileDescriptor*>* all_files,
+ std::set<const FileDescriptor*>* generated) const {
+ // Skip if already generated.
+ if (generated->find(root) != generated->end()) {
+ return;
+ }
+ generated->insert(root);
+
+ // Generate all dependencies before this file's content.
+ for (int i = 0; i < root->dependency_count(); i++) {
+ const FileDescriptor* dep = root->dependency(i);
+ GenerateFileAndDeps(options, printer, dep, all_files, generated);
+ }
+
+ // Generate this file's content. Only generate if the file is part of the
+ // original set requested to be generated; i.e., don't take all transitive
+ // deps down to the roots.
+ if (all_files->find(root) != all_files->end()) {
+ GenerateClassesAndEnums(options, printer, root);
+ }
+}
+
+void Generator::GenerateFile(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* file) const {
+ GenerateHeader(options, printer);
+
+ // Generate "require" statements.
+ if (options.import_style == GeneratorOptions::IMPORT_COMMONJS) {
+ printer->Print("var jspb = require('google-protobuf');\n");
+ printer->Print("var goog = jspb;\n");
+ printer->Print("var global = Function('return this')();\n\n");
+
+ for (int i = 0; i < file->dependency_count(); i++) {
+ const string& name = file->dependency(i)->name();
+ printer->Print(
+ "var $alias$ = require('$file$');\n",
+ "alias", ModuleAlias(name),
+ "file", GetRootPath(file->name(), name) + GetJSFilename(name));
+ }
+ }
+
+ // We aren't using Closure's import system, but we use goog.exportSymbol()
+ // to construct the expected tree of objects, eg.
+ //
+ // goog.exportSymbol('foo.bar.Baz', null, this);
+ //
+ // // Later generated code expects foo.bar = {} to exist:
+ // foo.bar.Baz = function() { /* ... */ }
+ set<string> provided;
+
+ // Cover the case where this file declares extensions but no messages.
+ // This will ensure that the file-level object will be declared to hold
+ // the extensions.
+ for (int i = 0; i < file->extension_count(); i++) {
+ provided.insert(file->extension(i)->full_name());
+ }
+
+ FindProvidesForFile(options, printer, file, &provided);
+ for (std::set<string>::iterator it = provided.begin();
+ it != provided.end(); ++it) {
+ printer->Print("goog.exportSymbol('$name$', null, global);\n",
+ "name", *it);
+ }
+
+ GenerateClassesAndEnums(options, printer, file);
+
+ // Extensions nested inside messages are emitted inside
+ // GenerateClassesAndEnums().
+ for (int i = 0; i < file->extension_count(); i++) {
+ GenerateExtension(options, printer, file->extension(i));
+ }
+
+ if (options.import_style == GeneratorOptions::IMPORT_COMMONJS) {
+ printer->Print("goog.object.extend(exports, $package$);\n",
+ "package", GetPath(options, file));
+ }
+}
+
+bool Generator::GenerateAll(const vector<const FileDescriptor*>& files,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ vector< pair< string, string > > option_pairs;
+ ParseGeneratorParameter(parameter, &option_pairs);
+ GeneratorOptions options;
+ if (!options.ParseFromOptions(option_pairs, error)) {
+ return false;
+ }
+
+
+ // There are three schemes for where output files go:
+ //
+ // - import_style = IMPORT_CLOSURE, library non-empty: all output in one file
+ // - import_style = IMPORT_CLOSURE, library empty: one output file per type
+ // - import_style != IMPORT_CLOSURE: one output file per .proto file
+ if (options.import_style == GeneratorOptions::IMPORT_CLOSURE &&
+ options.library != "") {
+ // All output should go in a single file.
+ string filename = options.output_dir + "/" + options.library + ".js";
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(filename));
+ GOOGLE_CHECK(output.get());
+ io::Printer printer(output.get(), '$');
+
+ // Pull out all extensions -- we need these to generate all
+ // provides/requires.
+ vector<const FieldDescriptor*> extensions;
+ for (int i = 0; i < files.size(); i++) {
+ for (int j = 0; j < files[i]->extension_count(); j++) {
+ const FieldDescriptor* extension = files[i]->extension(j);
+ extensions.push_back(extension);
+ }
+ }
+
+ GenerateHeader(options, &printer);
+
+ std::set<string> provided;
+ FindProvides(options, &printer, files, &provided);
+ FindProvidesForFields(options, &printer, extensions, &provided);
+ GenerateProvides(options, &printer, &provided);
+ GenerateTestOnly(options, &printer);
+ GenerateRequiresForLibrary(options, &printer, files, &provided);
+
+ GenerateFilesInDepOrder(options, &printer, files);
+
+ for (int i = 0; i < extensions.size(); i++) {
+ if (ShouldGenerateExtension(extensions[i])) {
+ GenerateExtension(options, &printer, extensions[i]);
+ }
+ }
+
+ if (printer.failed()) {
+ return false;
+ }
+ } else if (options.import_style == GeneratorOptions::IMPORT_CLOSURE) {
+ set<const void*> allowed_set;
+ if (!GenerateJspbAllowedSet(options, files, &allowed_set, error)) {
+ return false;
+ }
+
+ for (int i = 0; i < files.size(); i++) {
+ const FileDescriptor* file = files[i];
+ for (int j = 0; j < file->message_type_count(); j++) {
+ const Descriptor* desc = file->message_type(j);
+ if (allowed_set.count(desc) == 0) {
+ continue;
+ }
+
+ string filename = GetMessageFileName(options, desc);
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->Open(filename));
+ GOOGLE_CHECK(output.get());
+ io::Printer printer(output.get(), '$');
+
+ GenerateHeader(options, &printer);
+
+ std::set<string> provided;
+ FindProvidesForMessage(options, &printer, desc, &provided);
+ GenerateProvides(options, &printer, &provided);
+ GenerateTestOnly(options, &printer);
+ GenerateRequiresForMessage(options, &printer, desc, &provided);
+
+ GenerateClass(options, &printer, desc);
+
+ if (printer.failed()) {
+ return false;
+ }
+ }
+ for (int j = 0; j < file->enum_type_count(); j++) {
+ const EnumDescriptor* enumdesc = file->enum_type(j);
+ if (allowed_set.count(enumdesc) == 0) {
+ continue;
+ }
+
+ string filename = GetEnumFileName(options, enumdesc);
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->Open(filename));
+ GOOGLE_CHECK(output.get());
+ io::Printer printer(output.get(), '$');
+
+ GenerateHeader(options, &printer);
+
+ std::set<string> provided;
+ FindProvidesForEnum(options, &printer, enumdesc, &provided);
+ GenerateProvides(options, &printer, &provided);
+ GenerateTestOnly(options, &printer);
+
+ GenerateEnum(options, &printer, enumdesc);
+
+ if (printer.failed()) {
+ return false;
+ }
+ }
+ // File-level extensions (message-level extensions are generated under
+ // the enclosing message).
+ if (allowed_set.count(file) == 1) {
+ string filename = GetExtensionFileName(options, file);
+
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->Open(filename));
+ GOOGLE_CHECK(output.get());
+ io::Printer printer(output.get(), '$');
+
+ GenerateHeader(options, &printer);
+
+ std::set<string> provided;
+ vector<const FieldDescriptor*> fields;
+
+ for (int j = 0; j < files[i]->extension_count(); j++) {
+ if (ShouldGenerateExtension(files[i]->extension(j))) {
+ fields.push_back(files[i]->extension(j));
+ }
+ }
+
+ FindProvidesForFields(options, &printer, fields, &provided);
+ GenerateProvides(options, &printer, &provided);
+ GenerateTestOnly(options, &printer);
+ GenerateRequiresForExtensions(options, &printer, fields, &provided);
+
+ for (int j = 0; j < files[i]->extension_count(); j++) {
+ if (ShouldGenerateExtension(files[i]->extension(j))) {
+ GenerateExtension(options, &printer, files[i]->extension(j));
+ }
+ }
+ }
+ }
+ } else {
+ // Generate one output file per input (.proto) file.
+
+ for (int i = 0; i < files.size(); i++) {
+ const google::protobuf::FileDescriptor* file = files[i];
+
+ string filename = options.output_dir + "/" + GetJSFilename(file->name());
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(filename));
+ GOOGLE_CHECK(output.get());
+ io::Printer printer(output.get(), '$');
+
+ GenerateFile(options, &printer, file);
+
+ if (printer.failed()) {
+ return false;
+ }
+ }
+ }
+
+ return true;
+}
+
+} // namespace js
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.h
new file mode 100755
index 0000000000..6fd7ca5070
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/js/js_generator.h
@@ -0,0 +1,281 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_JS_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_JS_GENERATOR_H__
+
+#include <string>
+#include <set>
+
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+
+class Descriptor;
+class EnumDescriptor;
+class FieldDescriptor;
+class OneofDescriptor;
+class FileDescriptor;
+
+namespace io { class Printer; }
+
+namespace compiler {
+namespace js {
+
+struct GeneratorOptions {
+ // Add a `goog.requires()` call for each enum type used. If not set, a forward
+ // declaration with `goog.forwardDeclare` is produced instead.
+ bool add_require_for_enums;
+ // Set this as a test-only module via `goog.setTestOnly();`.
+ bool testonly;
+ // Output path.
+ string output_dir;
+ // Namespace prefix.
+ string namespace_prefix;
+ // Create a library with name <name>_lib.js rather than a separate .js file
+ // per type?
+ string library;
+ // Error if there are two types that would generate the same output file?
+ bool error_on_name_conflict;
+ // Enable binary-format support?
+ bool binary;
+ // What style of imports should be used.
+ enum ImportStyle {
+ IMPORT_CLOSURE, // goog.require()
+ IMPORT_COMMONJS, // require()
+ IMPORT_BROWSER, // no import statements
+ IMPORT_ES6, // import { member } from ''
+ } import_style;
+
+ GeneratorOptions()
+ : add_require_for_enums(false),
+ testonly(false),
+ output_dir("."),
+ namespace_prefix(""),
+ library(""),
+ error_on_name_conflict(false),
+ binary(false),
+ import_style(IMPORT_CLOSURE) {}
+
+ bool ParseFromOptions(
+ const vector< pair< string, string > >& options,
+ string* error);
+};
+
+class LIBPROTOC_EXPORT Generator : public CodeGenerator {
+ public:
+ Generator() {}
+ virtual ~Generator() {}
+
+ virtual bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ *error = "Unimplemented Generate() method. Call GenerateAll() instead.";
+ return false;
+ }
+
+ virtual bool HasGenerateAll() const { return true; }
+
+ virtual bool GenerateAll(const vector<const FileDescriptor*>& files,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const;
+
+ private:
+ void GenerateHeader(const GeneratorOptions& options,
+ io::Printer* printer) const;
+
+ // Generate goog.provides() calls.
+ void FindProvides(const GeneratorOptions& options,
+ io::Printer* printer,
+ const vector<const FileDescriptor*>& file,
+ std::set<string>* provided) const;
+ void FindProvidesForFile(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* file,
+ std::set<string>* provided) const;
+ void FindProvidesForMessage(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc,
+ std::set<string>* provided) const;
+ void FindProvidesForEnum(const GeneratorOptions& options,
+ io::Printer* printer,
+ const EnumDescriptor* enumdesc,
+ std::set<string>* provided) const;
+ // For extension fields at file scope.
+ void FindProvidesForFields(const GeneratorOptions& options,
+ io::Printer* printer,
+ const vector<const FieldDescriptor*>& fields,
+ std::set<string>* provided) const;
+ // Print the goog.provides() found by the methods above.
+ void GenerateProvides(const GeneratorOptions& options,
+ io::Printer* printer,
+ std::set<string>* provided) const;
+
+ // Generate goog.setTestOnly() if indicated.
+ void GenerateTestOnly(const GeneratorOptions& options,
+ io::Printer* printer) const;
+
+ // Generate goog.requires() calls.
+ void GenerateRequiresForLibrary(const GeneratorOptions& options,
+ io::Printer* printer,
+ const vector<const FileDescriptor*>& files,
+ std::set<string>* provided) const;
+ void GenerateRequiresForMessage(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc,
+ std::set<string>* provided) const;
+ // For extension fields at file scope.
+ void GenerateRequiresForExtensions(
+ const GeneratorOptions& options, io::Printer* printer,
+ const vector<const FieldDescriptor*>& fields,
+ std::set<string>* provided) const;
+ void GenerateRequiresImpl(const GeneratorOptions& options,
+ io::Printer* printer,
+ std::set<string>* required,
+ std::set<string>* forwards,
+ std::set<string>* provided,
+ bool require_jspb,
+ bool require_extension) const;
+ void FindRequiresForMessage(const GeneratorOptions& options,
+ const Descriptor* desc,
+ std::set<string>* required,
+ std::set<string>* forwards,
+ bool* have_message) const;
+ void FindRequiresForField(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ std::set<string>* required,
+ std::set<string>* forwards) const;
+ void FindRequiresForExtension(const GeneratorOptions& options,
+ const FieldDescriptor* field,
+ std::set<string>* required,
+ std::set<string>* forwards) const;
+
+ void GenerateFile(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* file) const;
+
+ // Generate definitions for all message classes and enums in all files,
+ // processing the files in dependence order.
+ void GenerateFilesInDepOrder(const GeneratorOptions& options,
+ io::Printer* printer,
+ const vector<const FileDescriptor*>& file) const;
+ // Helper for above.
+ void GenerateFileAndDeps(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* root,
+ std::set<const FileDescriptor*>* all_files,
+ std::set<const FileDescriptor*>* generated) const;
+
+ // Generate definitions for all message classes and enums.
+ void GenerateClassesAndEnums(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FileDescriptor* file) const;
+
+ // Generate definition for one class.
+ void GenerateClass(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassConstructor(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassFieldInfo(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassXid(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateOneofCaseDefinition(const GeneratorOptions& options,
+ io::Printer* printer,
+ const OneofDescriptor* oneof) const;
+ void GenerateClassToObject(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassFieldToObject(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const;
+ void GenerateClassFromObject(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassFieldFromObject(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const;
+ void GenerateClassClone(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassRegistration(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassFields(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassField(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* desc) const;
+ void GenerateClassExtensionFieldInfo(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassDeserialize(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassDeserializeBinary(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassDeserializeBinaryField(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const;
+ void GenerateClassSerializeBinary(const GeneratorOptions& options,
+ io::Printer* printer,
+ const Descriptor* desc) const;
+ void GenerateClassSerializeBinaryField(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const;
+
+ // Generate definition for one enum.
+ void GenerateEnum(const GeneratorOptions& options,
+ io::Printer* printer,
+ const EnumDescriptor* enumdesc) const;
+
+ // Generate an extension definition.
+ void GenerateExtension(const GeneratorOptions& options,
+ io::Printer* printer,
+ const FieldDescriptor* field) const;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Generator);
+};
+
+} // namespace js
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_JS_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/main.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/main.cc
new file mode 100644
index 0000000000..2f3c5b8f94
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/main.cc
@@ -0,0 +1,98 @@
+// 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)
+
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/compiler/cpp/cpp_generator.h>
+#include <google/protobuf/compiler/python/python_generator.h>
+#include <google/protobuf/compiler/java/java_generator.h>
+#include <google/protobuf/compiler/javanano/javanano_generator.h>
+// TODO(teboring): Add it back when php implementation is ready
+// #include <google/protobuf/compiler/php/php_generator.h>
+#include <google/protobuf/compiler/ruby/ruby_generator.h>
+#include <google/protobuf/compiler/csharp/csharp_generator.h>
+#include <google/protobuf/compiler/objectivec/objectivec_generator.h>
+#include <google/protobuf/compiler/js/js_generator.h>
+
+int main(int argc, char* argv[]) {
+
+ google::protobuf::compiler::CommandLineInterface cli;
+ cli.AllowPlugins("protoc-");
+
+ // Proto2 C++
+ google::protobuf::compiler::cpp::CppGenerator cpp_generator;
+ cli.RegisterGenerator("--cpp_out", "--cpp_opt", &cpp_generator,
+ "Generate C++ header and source.");
+
+ // Proto2 Java
+ google::protobuf::compiler::java::JavaGenerator java_generator;
+ cli.RegisterGenerator("--java_out", &java_generator,
+ "Generate Java source file.");
+
+
+ // Proto2 Python
+ google::protobuf::compiler::python::Generator py_generator;
+ cli.RegisterGenerator("--python_out", &py_generator,
+ "Generate Python source file.");
+
+ // Java Nano
+ google::protobuf::compiler::javanano::JavaNanoGenerator javanano_generator;
+ cli.RegisterGenerator("--javanano_out", &javanano_generator,
+ "Generate Java Nano source file.");
+
+ // TODO(teboring): Add it back when php implementation is ready
+ // PHP
+ // google::protobuf::compiler::php::Generator php_generator;
+ // cli.RegisterGenerator("--php_out", &php_generator,
+ // "Generate PHP source file.");
+
+ // Ruby
+ google::protobuf::compiler::ruby::Generator rb_generator;
+ cli.RegisterGenerator("--ruby_out", &rb_generator,
+ "Generate Ruby source file.");
+
+ // CSharp
+ google::protobuf::compiler::csharp::Generator csharp_generator;
+ cli.RegisterGenerator("--csharp_out", "--csharp_opt", &csharp_generator,
+ "Generate C# source file.");
+
+ // Objective C
+ google::protobuf::compiler::objectivec::ObjectiveCGenerator objc_generator;
+ cli.RegisterGenerator("--objc_out", "--objc_opt", &objc_generator,
+ "Generate Objective C header and source.");
+
+ // JavaScript
+ google::protobuf::compiler::js::Generator js_generator;
+ cli.RegisterGenerator("--js_out", &js_generator,
+ "Generate JavaScript source.");
+
+ return cli.Run(argc, argv);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.cc
new file mode 100644
index 0000000000..82bb342747
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.cc
@@ -0,0 +1,255 @@
+// 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)
+
+#include <google/protobuf/compiler/mock_code_generator.h>
+
+#include <stdlib.h>
+#include <iostream>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+// Returns the list of the names of files in all_files in the form of a
+// comma-separated string.
+string CommaSeparatedList(const vector<const FileDescriptor*> all_files) {
+ vector<string> names;
+ for (int i = 0; i < all_files.size(); i++) {
+ names.push_back(all_files[i]->name());
+ }
+ return Join(names, ",");
+}
+
+static const char* kFirstInsertionPointName = "first_mock_insertion_point";
+static const char* kSecondInsertionPointName = "second_mock_insertion_point";
+static const char* kFirstInsertionPoint =
+ "# @@protoc_insertion_point(first_mock_insertion_point) is here\n";
+static const char* kSecondInsertionPoint =
+ " # @@protoc_insertion_point(second_mock_insertion_point) is here\n";
+
+MockCodeGenerator::MockCodeGenerator(const string& name)
+ : name_(name) {}
+
+MockCodeGenerator::~MockCodeGenerator() {}
+
+void MockCodeGenerator::ExpectGenerated(
+ const string& name,
+ const string& parameter,
+ const string& insertions,
+ const string& file,
+ const string& first_message_name,
+ const string& first_parsed_file_name,
+ const string& output_directory) {
+ string content;
+ GOOGLE_CHECK_OK(
+ File::GetContents(output_directory + "/" + GetOutputFileName(name, file),
+ &content, true));
+
+ vector<string> lines = Split(content, "\n", true);
+
+ while (!lines.empty() && lines.back().empty()) {
+ lines.pop_back();
+ }
+ for (int i = 0; i < lines.size(); i++) {
+ lines[i] += "\n";
+ }
+
+ vector<string> insertion_list;
+ if (!insertions.empty()) {
+ SplitStringUsing(insertions, ",", &insertion_list);
+ }
+
+ EXPECT_EQ(lines.size(), 3 + insertion_list.size() * 2);
+ EXPECT_EQ(GetOutputFileContent(name, parameter, file,
+ first_parsed_file_name, first_message_name),
+ lines[0]);
+
+ EXPECT_EQ(kFirstInsertionPoint, lines[1 + insertion_list.size()]);
+ EXPECT_EQ(kSecondInsertionPoint, lines[2 + insertion_list.size() * 2]);
+
+ for (int i = 0; i < insertion_list.size(); i++) {
+ EXPECT_EQ(GetOutputFileContent(insertion_list[i], "first_insert",
+ file, file, first_message_name),
+ lines[1 + i]);
+ // Second insertion point is indented, so the inserted text should
+ // automatically be indented too.
+ EXPECT_EQ(" " + GetOutputFileContent(insertion_list[i], "second_insert",
+ file, file, first_message_name),
+ lines[2 + insertion_list.size() + i]);
+ }
+}
+
+bool MockCodeGenerator::Generate(
+ const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ for (int i = 0; i < file->message_type_count(); i++) {
+ if (HasPrefixString(file->message_type(i)->name(), "MockCodeGenerator_")) {
+ string command = StripPrefixString(file->message_type(i)->name(),
+ "MockCodeGenerator_");
+ if (command == "Error") {
+ *error = "Saw message type MockCodeGenerator_Error.";
+ return false;
+ } else if (command == "Exit") {
+ std::cerr << "Saw message type MockCodeGenerator_Exit." << std::endl;
+ exit(123);
+ } else if (command == "Abort") {
+ std::cerr << "Saw message type MockCodeGenerator_Abort." << std::endl;
+ abort();
+ } else if (command == "HasSourceCodeInfo") {
+ FileDescriptorProto file_descriptor_proto;
+ file->CopySourceCodeInfoTo(&file_descriptor_proto);
+ bool has_source_code_info =
+ file_descriptor_proto.has_source_code_info() &&
+ file_descriptor_proto.source_code_info().location_size() > 0;
+ std::cerr << "Saw message type MockCodeGenerator_HasSourceCodeInfo: "
+ << has_source_code_info << "." << std::endl;
+ abort();
+ } else if (command == "HasJsonName") {
+ FieldDescriptorProto field_descriptor_proto;
+ file->message_type(i)->field(0)->CopyTo(&field_descriptor_proto);
+ std::cerr << "Saw json_name: "
+ << field_descriptor_proto.has_json_name() << std::endl;
+ abort();
+ } else {
+ GOOGLE_LOG(FATAL) << "Unknown MockCodeGenerator command: " << command;
+ }
+ }
+ }
+
+ if (HasPrefixString(parameter, "insert=")) {
+ vector<string> insert_into;
+ SplitStringUsing(StripPrefixString(parameter, "insert="),
+ ",", &insert_into);
+
+ for (int i = 0; i < insert_into.size(); i++) {
+ {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->OpenForInsert(
+ GetOutputFileName(insert_into[i], file), kFirstInsertionPointName));
+ io::Printer printer(output.get(), '$');
+ printer.PrintRaw(GetOutputFileContent(name_, "first_insert",
+ file, context));
+ if (printer.failed()) {
+ *error = "MockCodeGenerator detected write error.";
+ return false;
+ }
+ }
+
+ {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->OpenForInsert(GetOutputFileName(insert_into[i], file),
+ kSecondInsertionPointName));
+ io::Printer printer(output.get(), '$');
+ printer.PrintRaw(GetOutputFileContent(name_, "second_insert",
+ file, context));
+ if (printer.failed()) {
+ *error = "MockCodeGenerator detected write error.";
+ return false;
+ }
+ }
+ }
+ } else {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->Open(GetOutputFileName(name_, file)));
+
+ io::Printer printer(output.get(), '$');
+ printer.PrintRaw(GetOutputFileContent(name_, parameter,
+ file, context));
+ printer.PrintRaw(kFirstInsertionPoint);
+ printer.PrintRaw(kSecondInsertionPoint);
+
+ if (printer.failed()) {
+ *error = "MockCodeGenerator detected write error.";
+ return false;
+ }
+ }
+
+ return true;
+}
+
+string MockCodeGenerator::GetOutputFileName(const string& generator_name,
+ const FileDescriptor* file) {
+ return GetOutputFileName(generator_name, file->name());
+}
+
+string MockCodeGenerator::GetOutputFileName(const string& generator_name,
+ const string& file) {
+ return file + ".MockCodeGenerator." + generator_name;
+}
+
+string MockCodeGenerator::GetOutputFileContent(
+ const string& generator_name,
+ const string& parameter,
+ const FileDescriptor* file,
+ GeneratorContext *context) {
+ vector<const FileDescriptor*> all_files;
+ context->ListParsedFiles(&all_files);
+ return GetOutputFileContent(
+ generator_name, parameter, file->name(),
+ CommaSeparatedList(all_files),
+ file->message_type_count() > 0 ?
+ file->message_type(0)->name() : "(none)");
+}
+
+string MockCodeGenerator::GetOutputFileContent(
+ const string& generator_name,
+ const string& parameter,
+ const string& file,
+ const string& parsed_file_list,
+ const string& first_message_name) {
+ return strings::Substitute("$0: $1, $2, $3, $4\n",
+ generator_name, parameter, file,
+ first_message_name, parsed_file_list);
+}
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.h
new file mode 100644
index 0000000000..e1665f88ce
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/mock_code_generator.h
@@ -0,0 +1,122 @@
+// 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)
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_MOCK_CODE_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_MOCK_CODE_GENERATOR_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+class FileDescriptor;
+} // namespace protobuf
+
+namespace protobuf {
+namespace compiler {
+
+// A mock CodeGenerator, used by command_line_interface_unittest. This is in
+// its own file so that it can be used both directly and as a plugin.
+//
+// Generate() produces some output which can be checked by ExpectCalled(). The
+// generator can run in a different process (e.g. a plugin).
+//
+// If the parameter is "insert=NAMES", the MockCodeGenerator will insert lines
+// into the files generated by other MockCodeGenerators instead of creating
+// its own file. NAMES is a comma-separated list of the names of those other
+// MockCodeGenerators.
+//
+// MockCodeGenerator will also modify its behavior slightly if the input file
+// contains a message type with one of the following names:
+// MockCodeGenerator_Error: Causes Generate() to return false and set the
+// error message to "Saw message type MockCodeGenerator_Error."
+// MockCodeGenerator_Exit: Generate() prints "Saw message type
+// MockCodeGenerator_Exit." to stderr and then calls exit(123).
+// MockCodeGenerator_Abort: Generate() prints "Saw message type
+// MockCodeGenerator_Abort." to stderr and then calls abort().
+// MockCodeGenerator_HasSourceCodeInfo: Causes Generate() to abort after
+// printing "Saw message type MockCodeGenerator_HasSourceCodeInfo: FOO." to
+// stderr, where FOO is "1" if the supplied FileDescriptorProto has source
+// code info, and "0" otherwise.
+class MockCodeGenerator : public CodeGenerator {
+ public:
+ MockCodeGenerator(const string& name);
+ virtual ~MockCodeGenerator();
+
+ // Expect (via gTest) that a MockCodeGenerator with the given name was called
+ // with the given parameters by inspecting the output location.
+ //
+ // |insertions| is a comma-separated list of names of MockCodeGenerators which
+ // should have inserted lines into this file.
+ // |parsed_file_list| is a comma-separated list of names of the files
+ // that are being compiled together in this run.
+ static void ExpectGenerated(const string& name,
+ const string& parameter,
+ const string& insertions,
+ const string& file,
+ const string& first_message_name,
+ const string& parsed_file_list,
+ const string& output_directory);
+
+ // Get the name of the file which would be written by the given generator.
+ static string GetOutputFileName(const string& generator_name,
+ const FileDescriptor* file);
+ static string GetOutputFileName(const string& generator_name,
+ const string& file);
+
+ // implements CodeGenerator ----------------------------------------
+
+ virtual bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const;
+
+ private:
+ string name_;
+
+ static string GetOutputFileContent(const string& generator_name,
+ const string& parameter,
+ const FileDescriptor* file,
+ GeneratorContext *context);
+ static string GetOutputFileContent(const string& generator_name,
+ const string& parameter,
+ const string& file,
+ const string& parsed_file_list,
+ const string& first_message_name);
+};
+
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_MOCK_CODE_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.cc
new file mode 100644
index 0000000000..e76f8e9915
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.cc
@@ -0,0 +1,219 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/objectivec/objectivec_enum.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+EnumGenerator::EnumGenerator(const EnumDescriptor* descriptor)
+ : descriptor_(descriptor),
+ name_(EnumName(descriptor_)) {
+ for (int i = 0; i < descriptor_->value_count(); i++) {
+ const EnumValueDescriptor* value = descriptor_->value(i);
+ const EnumValueDescriptor* canonical_value =
+ descriptor_->FindValueByNumber(value->number());
+
+ if (value == canonical_value) {
+ base_values_.push_back(value);
+ }
+ all_values_.push_back(value);
+ }
+}
+
+EnumGenerator::~EnumGenerator() {}
+
+void EnumGenerator::GenerateHeader(io::Printer* printer) {
+ string enum_comments;
+ SourceLocation location;
+ if (descriptor_->GetSourceLocation(&location)) {
+ enum_comments = BuildCommentsString(location);
+ } else {
+ enum_comments = "";
+ }
+
+ printer->Print(
+ "#pragma mark - Enum $name$\n"
+ "\n",
+ "name", name_);
+
+ printer->Print("$comments$typedef$deprecated_attribute$ GPB_ENUM($name$) {\n",
+ "comments", enum_comments,
+ "deprecated_attribute", GetOptionalDeprecatedAttribute(descriptor_),
+ "name", name_);
+ printer->Indent();
+
+ if (HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ // Include the unknown value.
+ printer->Print(
+ "/// Value used if any message's field encounters a value that is not defined\n"
+ "/// by this enum. The message will also have C functions to get/set the rawValue\n"
+ "/// of the field.\n"
+ "$name$_GPBUnrecognizedEnumeratorValue = kGPBUnrecognizedEnumeratorValue,\n",
+ "name", name_);
+ }
+ for (int i = 0; i < all_values_.size(); i++) {
+ SourceLocation location;
+ if (all_values_[i]->GetSourceLocation(&location)) {
+ string comments = BuildCommentsString(location).c_str();
+ if (comments.length() > 0) {
+ if (i > 0) {
+ printer->Print("\n");
+ }
+ printer->Print(comments.c_str());
+ }
+ }
+
+ printer->Print(
+ "$name$$deprecated_attribute$ = $value$,\n",
+ "name", EnumValueName(all_values_[i]),
+ "deprecated_attribute", GetOptionalDeprecatedAttribute(all_values_[i]),
+ "value", SimpleItoa(all_values_[i]->number()));
+ }
+ printer->Outdent();
+ printer->Print(
+ "};\n"
+ "\n"
+ "GPBEnumDescriptor *$name$_EnumDescriptor(void);\n"
+ "\n"
+ "/// Checks to see if the given value is defined by the enum or was not known at\n"
+ "/// the time this source was generated.\n"
+ "BOOL $name$_IsValidValue(int32_t value);\n"
+ "\n",
+ "name", name_);
+}
+
+void EnumGenerator::GenerateSource(io::Printer* printer) {
+ printer->Print(
+ "#pragma mark - Enum $name$\n"
+ "\n",
+ "name", name_);
+
+ // Note: For the TextFormat decode info, we can't use the enum value as
+ // the key because protocol buffer enums have 'allow_alias', which lets
+ // a value be used more than once. Instead, the index into the list of
+ // enum value descriptions is used. Note: start with -1 so the first one
+ // will be zero.
+ TextFormatDecodeData text_format_decode_data;
+ int enum_value_description_key = -1;
+ string text_blob;
+
+ for (int i = 0; i < all_values_.size(); i++) {
+ ++enum_value_description_key;
+ string short_name(EnumValueShortName(all_values_[i]));
+ text_blob += short_name + '\0';
+ if (UnCamelCaseEnumShortName(short_name) != all_values_[i]->name()) {
+ text_format_decode_data.AddString(enum_value_description_key, short_name,
+ all_values_[i]->name());
+ }
+ }
+
+ printer->Print(
+ "GPBEnumDescriptor *$name$_EnumDescriptor(void) {\n"
+ " static GPBEnumDescriptor *descriptor = NULL;\n"
+ " if (!descriptor) {\n",
+ "name", name_);
+
+ static const int kBytesPerLine = 40; // allow for escaping
+ printer->Print(
+ " static const char *valueNames =");
+ for (int i = 0; i < text_blob.size(); i += kBytesPerLine) {
+ printer->Print(
+ "\n \"$data$\"",
+ "data", EscapeTrigraphs(CEscape(text_blob.substr(i, kBytesPerLine))));
+ }
+ printer->Print(
+ ";\n"
+ " static const int32_t values[] = {\n");
+ for (int i = 0; i < all_values_.size(); i++) {
+ printer->Print(" $name$,\n", "name", EnumValueName(all_values_[i]));
+ }
+ printer->Print(" };\n");
+
+ if (text_format_decode_data.num_entries() == 0) {
+ printer->Print(
+ " GPBEnumDescriptor *worker =\n"
+ " [GPBEnumDescriptor allocDescriptorForName:GPBNSStringifySymbol($name$)\n"
+ " valueNames:valueNames\n"
+ " values:values\n"
+ " count:(uint32_t)(sizeof(values) / sizeof(int32_t))\n"
+ " enumVerifier:$name$_IsValidValue];\n",
+ "name", name_);
+ } else {
+ printer->Print(
+ " static const char *extraTextFormatInfo = \"$extraTextFormatInfo$\";\n"
+ " GPBEnumDescriptor *worker =\n"
+ " [GPBEnumDescriptor allocDescriptorForName:GPBNSStringifySymbol($name$)\n"
+ " valueNames:valueNames\n"
+ " values:values\n"
+ " count:(uint32_t)(sizeof(values) / sizeof(int32_t))\n"
+ " enumVerifier:$name$_IsValidValue\n"
+ " extraTextFormatInfo:extraTextFormatInfo];\n",
+ "name", name_,
+ "extraTextFormatInfo", CEscape(text_format_decode_data.Data()));
+ }
+ printer->Print(
+ " if (!OSAtomicCompareAndSwapPtrBarrier(nil, worker, (void * volatile *)&descriptor)) {\n"
+ " [worker release];\n"
+ " }\n"
+ " }\n"
+ " return descriptor;\n"
+ "}\n\n");
+
+ printer->Print(
+ "BOOL $name$_IsValidValue(int32_t value__) {\n"
+ " switch (value__) {\n",
+ "name", name_);
+
+ for (int i = 0; i < base_values_.size(); i++) {
+ printer->Print(
+ " case $name$:\n",
+ "name", EnumValueName(base_values_[i]));
+ }
+
+ printer->Print(
+ " return YES;\n"
+ " default:\n"
+ " return NO;\n"
+ " }\n"
+ "}\n\n");
+}
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.h
new file mode 100644
index 0000000000..0b41cf7352
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum.h
@@ -0,0 +1,73 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ENUM_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ENUM_H__
+
+#include <string>
+#include <set>
+#include <vector>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+class Printer; // printer.h
+}
+}
+
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class EnumGenerator {
+ public:
+ explicit EnumGenerator(const EnumDescriptor* descriptor);
+ ~EnumGenerator();
+
+ void GenerateHeader(io::Printer* printer);
+ void GenerateSource(io::Printer* printer);
+
+ const string& name() const { return name_; }
+
+ private:
+ const EnumDescriptor* descriptor_;
+ vector<const EnumValueDescriptor*> base_values_;
+ vector<const EnumValueDescriptor*> all_values_;
+ const string name_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ENUM_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.cc
new file mode 100644
index 0000000000..b63bc0de63
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.cc
@@ -0,0 +1,147 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/objectivec/objectivec_enum_field.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+namespace {
+
+void SetEnumVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables) {
+ string type = EnumName(descriptor->enum_type());
+ (*variables)["storage_type"] = type;
+ // For non repeated fields, if it was defined in a different file, the
+ // property decls need to use "enum NAME" rather than just "NAME" to support
+ // the forward declaration of the enums.
+ if (!descriptor->is_repeated() &&
+ (descriptor->file() != descriptor->enum_type()->file())) {
+ (*variables)["property_type"] = "enum " + type;
+ }
+ (*variables)["enum_verifier"] = type + "_IsValidValue";
+ (*variables)["enum_desc_func"] = type + "_EnumDescriptor";
+
+ (*variables)["dataTypeSpecific_name"] = "enumDescFunc";
+ (*variables)["dataTypeSpecific_value"] = (*variables)["enum_desc_func"];
+
+ const Descriptor* msg_descriptor = descriptor->containing_type();
+ (*variables)["owning_message_class"] = ClassName(msg_descriptor);
+}
+} // namespace
+
+EnumFieldGenerator::EnumFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : SingleFieldGenerator(descriptor, options) {
+ SetEnumVariables(descriptor, &variables_);
+}
+
+EnumFieldGenerator::~EnumFieldGenerator() {}
+
+void EnumFieldGenerator::GenerateCFunctionDeclarations(
+ io::Printer* printer) const {
+ if (!HasPreservingUnknownEnumSemantics(descriptor_->file())) {
+ return;
+ }
+
+ printer->Print(
+ variables_,
+ "/// Fetches the raw value of a @c $owning_message_class$'s @c $name$ property, even\n"
+ "/// if the value was not defined by the enum at the time the code was generated.\n"
+ "int32_t $owning_message_class$_$capitalized_name$_RawValue($owning_message_class$ *message);\n"
+ "/// Sets the raw value of an @c $owning_message_class$'s @c $name$ property, allowing\n"
+ "/// it to be set to a value that was not defined by the enum at the time the code\n"
+ "/// was generated.\n"
+ "void Set$owning_message_class$_$capitalized_name$_RawValue($owning_message_class$ *message, int32_t value);\n"
+ "\n");
+}
+
+void EnumFieldGenerator::GenerateCFunctionImplementations(
+ io::Printer* printer) const {
+ if (!HasPreservingUnknownEnumSemantics(descriptor_->file())) return;
+
+ printer->Print(
+ variables_,
+ "int32_t $owning_message_class$_$capitalized_name$_RawValue($owning_message_class$ *message) {\n"
+ " GPBDescriptor *descriptor = [$owning_message_class$ descriptor];\n"
+ " GPBFieldDescriptor *field = [descriptor fieldWithNumber:$field_number_name$];\n"
+ " return GPBGetMessageInt32Field(message, field);\n"
+ "}\n"
+ "\n"
+ "void Set$owning_message_class$_$capitalized_name$_RawValue($owning_message_class$ *message, int32_t value) {\n"
+ " GPBDescriptor *descriptor = [$owning_message_class$ descriptor];\n"
+ " GPBFieldDescriptor *field = [descriptor fieldWithNumber:$field_number_name$];\n"
+ " GPBSetInt32IvarWithFieldInternal(message, field, value, descriptor.file.syntax);\n"
+ "}\n"
+ "\n");
+}
+
+void EnumFieldGenerator::DetermineForwardDeclarations(
+ set<string>* fwd_decls) const {
+ SingleFieldGenerator::DetermineForwardDeclarations(fwd_decls);
+ // If it is an enum defined in a different file, then we'll need a forward
+ // declaration for it. When it is in our file, all the enums are output
+ // before the message, so it will be declared before it is needed.
+ if (descriptor_->file() != descriptor_->enum_type()->file()) {
+ // Enum name is already in "storage_type".
+ const string& name = variable("storage_type");
+ fwd_decls->insert("GPB_ENUM_FWD_DECLARE(" + name + ")");
+ }
+}
+
+RepeatedEnumFieldGenerator::RepeatedEnumFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : RepeatedFieldGenerator(descriptor, options) {
+ SetEnumVariables(descriptor, &variables_);
+ variables_["array_storage_type"] = "GPBEnumArray";
+}
+
+RepeatedEnumFieldGenerator::~RepeatedEnumFieldGenerator() {}
+
+void RepeatedEnumFieldGenerator::FinishInitialization(void) {
+ RepeatedFieldGenerator::FinishInitialization();
+ variables_["array_comment"] =
+ "// |" + variables_["name"] + "| contains |" + variables_["storage_type"] + "|\n";
+}
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.h
new file mode 100644
index 0000000000..946faa819a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_enum_field.h
@@ -0,0 +1,80 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ENUM_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ENUM_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/objectivec/objectivec_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class EnumFieldGenerator : public SingleFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ public:
+ virtual void GenerateCFunctionDeclarations(io::Printer* printer) const;
+ virtual void GenerateCFunctionImplementations(io::Printer* printer) const;
+ virtual void DetermineForwardDeclarations(set<string>* fwd_decls) const;
+
+ protected:
+ EnumFieldGenerator(const FieldDescriptor* descriptor, const Options& options);
+ virtual ~EnumFieldGenerator();
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumFieldGenerator);
+};
+
+class RepeatedEnumFieldGenerator : public RepeatedFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ public:
+ virtual void FinishInitialization();
+
+ protected:
+ RepeatedEnumFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual ~RepeatedEnumFieldGenerator();
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedEnumFieldGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ENUM_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.cc
new file mode 100644
index 0000000000..3f7ab9d392
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.cc
@@ -0,0 +1,136 @@
+// 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.
+
+#include <iostream>
+
+#include <google/protobuf/compiler/objectivec/objectivec_extension.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/io/printer.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+ExtensionGenerator::ExtensionGenerator(const string& root_class_name,
+ const FieldDescriptor* descriptor)
+ : method_name_(ExtensionMethodName(descriptor)),
+ root_class_and_method_name_(root_class_name + "_" + method_name_),
+ descriptor_(descriptor) {
+ if (descriptor->is_map()) {
+ // NOTE: src/google/protobuf/compiler/plugin.cc makes use of cerr for some
+ // error cases, so it seems to be ok to use as a back door for errors.
+ cerr << "error: Extension is a map<>!"
+ << " That used to be blocked by the compiler." << endl;
+ cerr.flush();
+ abort();
+ }
+}
+
+ExtensionGenerator::~ExtensionGenerator() {}
+
+void ExtensionGenerator::GenerateMembersHeader(io::Printer* printer) {
+ map<string, string> vars;
+ vars["method_name"] = method_name_;
+ SourceLocation location;
+ if (descriptor_->GetSourceLocation(&location)) {
+ vars["comments"] = BuildCommentsString(location);
+ } else {
+ vars["comments"] = "";
+ }
+ printer->Print(vars,
+ "$comments$"
+ "+ (GPBExtensionDescriptor *)$method_name$;\n");
+}
+
+void ExtensionGenerator::GenerateStaticVariablesInitialization(
+ io::Printer* printer) {
+ map<string, string> vars;
+ vars["root_class_and_method_name"] = root_class_and_method_name_;
+ vars["extended_type"] = ClassName(descriptor_->containing_type());
+ vars["number"] = SimpleItoa(descriptor_->number());
+
+ std::vector<string> options;
+ if (descriptor_->is_repeated()) options.push_back("GPBExtensionRepeated");
+ if (descriptor_->is_packed()) options.push_back("GPBExtensionPacked");
+ if (descriptor_->containing_type()->options().message_set_wire_format())
+ options.push_back("GPBExtensionSetWireFormat");
+
+ vars["options"] = BuildFlagsString(options);
+
+ ObjectiveCType objc_type = GetObjectiveCType(descriptor_);
+ string singular_type;
+ if (objc_type == OBJECTIVECTYPE_MESSAGE) {
+ vars["type"] = string("GPBStringifySymbol(") +
+ ClassName(descriptor_->message_type()) + ")";
+ } else {
+ vars["type"] = "NULL";
+ }
+
+ vars["default_name"] = GPBGenericValueFieldName(descriptor_);
+ if (descriptor_->is_repeated()) {
+ vars["default"] = "nil";
+ } else {
+ vars["default"] = DefaultValue(descriptor_);
+ }
+ string type = GetCapitalizedType(descriptor_);
+ vars["extension_type"] = string("GPBDataType") + type;
+
+ if (objc_type == OBJECTIVECTYPE_ENUM) {
+ vars["enum_desc_func_name"] =
+ EnumName(descriptor_->enum_type()) + "_EnumDescriptor";
+ } else {
+ vars["enum_desc_func_name"] = "NULL";
+ }
+
+ printer->Print(vars,
+ "{\n"
+ " .defaultValue.$default_name$ = $default$,\n"
+ " .singletonName = GPBStringifySymbol($root_class_and_method_name$),\n"
+ " .extendedClass = GPBStringifySymbol($extended_type$),\n"
+ " .messageOrGroupClassName = $type$,\n"
+ " .enumDescriptorFunc = $enum_desc_func_name$,\n"
+ " .fieldNumber = $number$,\n"
+ " .dataType = $extension_type$,\n"
+ " .options = $options$,\n"
+ "},\n");
+}
+
+void ExtensionGenerator::GenerateRegistrationSource(io::Printer* printer) {
+ printer->Print(
+ "[registry addExtension:$root_class_and_method_name$];\n",
+ "root_class_and_method_name", root_class_and_method_name_);
+}
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.h
new file mode 100644
index 0000000000..e361e639bd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_extension.h
@@ -0,0 +1,69 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_EXTENSION_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_EXTENSION_H__
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+class FieldDescriptor; // descriptor.h
+namespace io {
+class Printer; // printer.h
+}
+}
+
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class ExtensionGenerator {
+ public:
+ ExtensionGenerator(const string& root_class_name,
+ const FieldDescriptor* descriptor);
+ ~ExtensionGenerator();
+
+ void GenerateMembersHeader(io::Printer* printer);
+ void GenerateStaticVariablesInitialization(io::Printer* printer);
+ void GenerateRegistrationSource(io::Printer* printer);
+
+ private:
+ string method_name_;
+ string root_class_and_method_name_;
+ const FieldDescriptor* descriptor_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionGenerator);
+};
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.cc
new file mode 100644
index 0000000000..812b4a1c13
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.cc
@@ -0,0 +1,477 @@
+// 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.
+
+#include <iostream>
+
+#include <google/protobuf/compiler/objectivec/objectivec_field.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/compiler/objectivec/objectivec_enum_field.h>
+#include <google/protobuf/compiler/objectivec/objectivec_map_field.h>
+#include <google/protobuf/compiler/objectivec/objectivec_message_field.h>
+#include <google/protobuf/compiler/objectivec/objectivec_primitive_field.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+namespace {
+
+void SetCommonFieldVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables) {
+ string camel_case_name = FieldName(descriptor);
+ string raw_field_name;
+ if (descriptor->type() == FieldDescriptor::TYPE_GROUP) {
+ raw_field_name = descriptor->message_type()->name();
+ } else {
+ raw_field_name = descriptor->name();
+ }
+ // The logic here has to match -[GGPBFieldDescriptor textFormatName].
+ const string un_camel_case_name(
+ UnCamelCaseFieldName(camel_case_name, descriptor));
+ const bool needs_custom_name = (raw_field_name != un_camel_case_name);
+
+ SourceLocation location;
+ if (descriptor->GetSourceLocation(&location)) {
+ (*variables)["comments"] = BuildCommentsString(location);
+ } else {
+ (*variables)["comments"] = "\n";
+ }
+ const string& classname = ClassName(descriptor->containing_type());
+ (*variables)["classname"] = classname;
+ (*variables)["name"] = camel_case_name;
+ const string& capitalized_name = FieldNameCapitalized(descriptor);
+ (*variables)["capitalized_name"] = capitalized_name;
+ (*variables)["raw_field_name"] = raw_field_name;
+ (*variables)["field_number_name"] =
+ classname + "_FieldNumber_" + capitalized_name;
+ (*variables)["field_number"] = SimpleItoa(descriptor->number());
+ (*variables)["field_type"] = GetCapitalizedType(descriptor);
+ (*variables)["deprecated_attribute"] = GetOptionalDeprecatedAttribute(descriptor);
+ std::vector<string> field_flags;
+ if (descriptor->is_repeated()) field_flags.push_back("GPBFieldRepeated");
+ if (descriptor->is_required()) field_flags.push_back("GPBFieldRequired");
+ if (descriptor->is_optional()) field_flags.push_back("GPBFieldOptional");
+ if (descriptor->is_packed()) field_flags.push_back("GPBFieldPacked");
+
+ // ObjC custom flags.
+ if (descriptor->has_default_value())
+ field_flags.push_back("GPBFieldHasDefaultValue");
+ if (needs_custom_name) field_flags.push_back("GPBFieldTextFormatNameCustom");
+ if (descriptor->type() == FieldDescriptor::TYPE_ENUM) {
+ field_flags.push_back("GPBFieldHasEnumDescriptor");
+ }
+
+ (*variables)["fieldflags"] = BuildFlagsString(field_flags);
+
+ (*variables)["default"] = DefaultValue(descriptor);
+ (*variables)["default_name"] = GPBGenericValueFieldName(descriptor);
+
+ (*variables)["dataTypeSpecific_name"] = "className";
+ (*variables)["dataTypeSpecific_value"] = "NULL";
+
+ (*variables)["storage_offset_value"] =
+ "(uint32_t)offsetof(" + classname + "__storage_, " + camel_case_name + ")";
+ (*variables)["storage_offset_comment"] = "";
+
+ // Clear some common things so they can be set just when needed.
+ (*variables)["storage_attribute"] = "";
+}
+
+} // namespace
+
+FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options) {
+ FieldGenerator* result = NULL;
+ if (field->is_repeated()) {
+ switch (GetObjectiveCType(field)) {
+ case OBJECTIVECTYPE_MESSAGE: {
+ if (field->is_map()) {
+ result = new MapFieldGenerator(field, options);
+ } else {
+ result = new RepeatedMessageFieldGenerator(field, options);
+ }
+ break;
+ }
+ case OBJECTIVECTYPE_ENUM:
+ result = new RepeatedEnumFieldGenerator(field, options);
+ break;
+ default:
+ result = new RepeatedPrimitiveFieldGenerator(field, options);
+ break;
+ }
+ } else {
+ switch (GetObjectiveCType(field)) {
+ case OBJECTIVECTYPE_MESSAGE: {
+ result = new MessageFieldGenerator(field, options);
+ break;
+ }
+ case OBJECTIVECTYPE_ENUM:
+ result = new EnumFieldGenerator(field, options);
+ break;
+ default:
+ if (IsReferenceType(field)) {
+ result = new PrimitiveObjFieldGenerator(field, options);
+ } else {
+ result = new PrimitiveFieldGenerator(field, options);
+ }
+ break;
+ }
+ }
+ result->FinishInitialization();
+ return result;
+}
+
+FieldGenerator::FieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : descriptor_(descriptor) {
+ SetCommonFieldVariables(descriptor, &variables_);
+}
+
+FieldGenerator::~FieldGenerator() {}
+
+void FieldGenerator::GenerateFieldNumberConstant(io::Printer* printer) const {
+ printer->Print(
+ variables_,
+ "$field_number_name$ = $field_number$,\n");
+}
+
+void FieldGenerator::GenerateCFunctionDeclarations(
+ io::Printer* printer) const {
+ // Nothing
+}
+
+void FieldGenerator::GenerateCFunctionImplementations(
+ io::Printer* printer) const {
+ // Nothing
+}
+
+void FieldGenerator::DetermineForwardDeclarations(
+ set<string>* fwd_decls) const {
+ // Nothing
+}
+
+void FieldGenerator::GenerateFieldDescription(
+ io::Printer* printer, bool include_default) const {
+ // Printed in the same order as the structure decl.
+ if (include_default) {
+ printer->Print(
+ variables_,
+ "{\n"
+ " .defaultValue.$default_name$ = $default$,\n"
+ " .core.name = \"$name$\",\n"
+ " .core.dataTypeSpecific.$dataTypeSpecific_name$ = $dataTypeSpecific_value$,\n"
+ " .core.number = $field_number_name$,\n"
+ " .core.hasIndex = $has_index$,\n"
+ " .core.offset = $storage_offset_value$,$storage_offset_comment$\n"
+ " .core.flags = $fieldflags$,\n"
+ " .core.dataType = GPBDataType$field_type$,\n"
+ "},\n");
+ } else {
+ printer->Print(
+ variables_,
+ "{\n"
+ " .name = \"$name$\",\n"
+ " .dataTypeSpecific.$dataTypeSpecific_name$ = $dataTypeSpecific_value$,\n"
+ " .number = $field_number_name$,\n"
+ " .hasIndex = $has_index$,\n"
+ " .offset = $storage_offset_value$,$storage_offset_comment$\n"
+ " .flags = $fieldflags$,\n"
+ " .dataType = GPBDataType$field_type$,\n"
+ "},\n");
+ }
+}
+
+void FieldGenerator::SetRuntimeHasBit(int has_index) {
+ variables_["has_index"] = SimpleItoa(has_index);
+}
+
+void FieldGenerator::SetNoHasBit(void) {
+ variables_["has_index"] = "GPBNoHasBit";
+}
+
+int FieldGenerator::ExtraRuntimeHasBitsNeeded(void) const {
+ return 0;
+}
+
+void FieldGenerator::SetExtraRuntimeHasBitsBase(int index_base) {
+ // NOTE: src/google/protobuf/compiler/plugin.cc makes use of cerr for some
+ // error cases, so it seems to be ok to use as a back door for errors.
+ cerr << "Error: should have overridden SetExtraRuntimeHasBitsBase()." << endl;
+ cerr.flush();
+ abort();
+}
+
+void FieldGenerator::SetOneofIndexBase(int index_base) {
+ if (descriptor_->containing_oneof() != NULL) {
+ int index = descriptor_->containing_oneof()->index() + index_base;
+ // Flip the sign to mark it as a oneof.
+ variables_["has_index"] = SimpleItoa(-index);
+ }
+}
+
+void FieldGenerator::FinishInitialization(void) {
+ // If "property_type" wasn't set, make it "storage_type".
+ if ((variables_.find("property_type") == variables_.end()) &&
+ (variables_.find("storage_type") != variables_.end())) {
+ variables_["property_type"] = variable("storage_type");
+ }
+}
+
+SingleFieldGenerator::SingleFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : FieldGenerator(descriptor, options) {
+ // Nothing
+}
+
+SingleFieldGenerator::~SingleFieldGenerator() {}
+
+void SingleFieldGenerator::GenerateFieldStorageDeclaration(
+ io::Printer* printer) const {
+ printer->Print(variables_, "$storage_type$ $name$;\n");
+}
+
+void SingleFieldGenerator::GeneratePropertyDeclaration(
+ io::Printer* printer) const {
+ printer->Print(variables_, "$comments$");
+ printer->Print(
+ variables_,
+ "@property(nonatomic, readwrite) $property_type$ $name$$deprecated_attribute$;\n"
+ "\n");
+ if (WantsHasProperty()) {
+ printer->Print(
+ variables_,
+ "@property(nonatomic, readwrite) BOOL has$capitalized_name$$deprecated_attribute$;\n");
+ }
+}
+
+void SingleFieldGenerator::GeneratePropertyImplementation(
+ io::Printer* printer) const {
+ if (WantsHasProperty()) {
+ printer->Print(variables_, "@dynamic has$capitalized_name$, $name$;\n");
+ } else {
+ printer->Print(variables_, "@dynamic $name$;\n");
+ }
+}
+
+bool SingleFieldGenerator::WantsHasProperty(void) const {
+ if (descriptor_->containing_oneof() != NULL) {
+ // If in a oneof, it uses the oneofcase instead of a has bit.
+ return false;
+ }
+ if (HasFieldPresence(descriptor_->file())) {
+ // In proto1/proto2, every field has a has_$name$() method.
+ return true;
+ }
+ return false;
+}
+
+bool SingleFieldGenerator::RuntimeUsesHasBit(void) const {
+ if (descriptor_->containing_oneof() != NULL) {
+ // The oneof tracks what is set instead.
+ return false;
+ }
+ return true;
+}
+
+ObjCObjFieldGenerator::ObjCObjFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : SingleFieldGenerator(descriptor, options) {
+ variables_["property_storage_attribute"] = "strong";
+ if (IsRetainedName(variables_["name"])) {
+ variables_["storage_attribute"] = " NS_RETURNS_NOT_RETAINED";
+ }
+}
+
+ObjCObjFieldGenerator::~ObjCObjFieldGenerator() {}
+
+void ObjCObjFieldGenerator::GenerateFieldStorageDeclaration(
+ io::Printer* printer) const {
+ printer->Print(variables_, "$storage_type$ *$name$;\n");
+}
+
+void ObjCObjFieldGenerator::GeneratePropertyDeclaration(
+ io::Printer* printer) const {
+
+ // Differs from SingleFieldGenerator::GeneratePropertyDeclaration() in that
+ // it uses pointers and deals with Objective C's rules around storage name
+ // conventions (init*, new*, etc.)
+
+ printer->Print(variables_, "$comments$");
+ printer->Print(
+ variables_,
+ "@property(nonatomic, readwrite, $property_storage_attribute$, null_resettable) $property_type$ *$name$$storage_attribute$$deprecated_attribute$;\n");
+ if (WantsHasProperty()) {
+ printer->Print(
+ variables_,
+ "/// Test to see if @c $name$ has been set.\n"
+ "@property(nonatomic, readwrite) BOOL has$capitalized_name$$deprecated_attribute$;\n");
+ }
+ if (IsInitName(variables_.find("name")->second)) {
+ // If property name starts with init we need to annotate it to get past ARC.
+ // http://stackoverflow.com/questions/18723226/how-do-i-annotate-an-objective-c-property-with-an-objc-method-family/18723227#18723227
+ printer->Print(variables_,
+ "- ($property_type$ *)$name$ GPB_METHOD_FAMILY_NONE$deprecated_attribute$;\n");
+ }
+ printer->Print("\n");
+}
+
+RepeatedFieldGenerator::RepeatedFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : ObjCObjFieldGenerator(descriptor, options) {
+ // Default to no comment and let the cases needing it fill it in.
+ variables_["array_comment"] = "";
+}
+
+RepeatedFieldGenerator::~RepeatedFieldGenerator() {}
+
+void RepeatedFieldGenerator::FinishInitialization(void) {
+ FieldGenerator::FinishInitialization();
+ if (variables_.find("array_property_type") == variables_.end()) {
+ variables_["array_property_type"] = variable("array_storage_type");
+ }
+}
+
+void RepeatedFieldGenerator::GenerateFieldStorageDeclaration(
+ io::Printer* printer) const {
+ printer->Print(variables_, "$array_storage_type$ *$name$;\n");
+}
+
+void RepeatedFieldGenerator::GeneratePropertyImplementation(
+ io::Printer* printer) const {
+ printer->Print(variables_, "@dynamic $name$, $name$_Count;\n");
+}
+
+void RepeatedFieldGenerator::GeneratePropertyDeclaration(
+ io::Printer* printer) const {
+
+ // Repeated fields don't need the has* properties, but they do expose a
+ // *Count (to check without autocreation). So for the field property we need
+ // the same logic as ObjCObjFieldGenerator::GeneratePropertyDeclaration() for
+ // dealing with needing Objective C's rules around storage name conventions
+ // (init*, new*, etc.)
+
+ printer->Print(
+ variables_,
+ "$comments$"
+ "$array_comment$"
+ "@property(nonatomic, readwrite, strong, null_resettable) $array_property_type$ *$name$$storage_attribute$$deprecated_attribute$;\n"
+ "/// The number of items in @c $name$ without causing the array to be created.\n"
+ "@property(nonatomic, readonly) NSUInteger $name$_Count$deprecated_attribute$;\n");
+ if (IsInitName(variables_.find("name")->second)) {
+ // If property name starts with init we need to annotate it to get past ARC.
+ // http://stackoverflow.com/questions/18723226/how-do-i-annotate-an-objective-c-property-with-an-objc-method-family/18723227#18723227
+ printer->Print(variables_,
+ "- ($array_property_type$ *)$name$ GPB_METHOD_FAMILY_NONE$deprecated_attribute$;\n");
+ }
+ printer->Print("\n");
+}
+
+bool RepeatedFieldGenerator::WantsHasProperty(void) const {
+ // Consumer check the array size/existance rather than a has bit.
+ return false;
+}
+
+bool RepeatedFieldGenerator::RuntimeUsesHasBit(void) const {
+ return false; // The array having anything is what is used.
+}
+
+FieldGeneratorMap::FieldGeneratorMap(const Descriptor* descriptor,
+ const Options& options)
+ : descriptor_(descriptor),
+ field_generators_(
+ new scoped_ptr<FieldGenerator>[descriptor->field_count()]),
+ extension_generators_(
+ new scoped_ptr<FieldGenerator>[descriptor->extension_count()]) {
+ // Construct all the FieldGenerators.
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ field_generators_[i].reset(
+ FieldGenerator::Make(descriptor->field(i), options));
+ }
+ for (int i = 0; i < descriptor->extension_count(); i++) {
+ extension_generators_[i].reset(
+ FieldGenerator::Make(descriptor->extension(i), options));
+ }
+}
+
+FieldGeneratorMap::~FieldGeneratorMap() {}
+
+const FieldGenerator& FieldGeneratorMap::get(
+ const FieldDescriptor* field) const {
+ GOOGLE_CHECK_EQ(field->containing_type(), descriptor_);
+ return *field_generators_[field->index()];
+}
+
+const FieldGenerator& FieldGeneratorMap::get_extension(int index) const {
+ return *extension_generators_[index];
+}
+
+int FieldGeneratorMap::CalculateHasBits(void) {
+ int total_bits = 0;
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (field_generators_[i]->RuntimeUsesHasBit()) {
+ field_generators_[i]->SetRuntimeHasBit(total_bits);
+ ++total_bits;
+ } else {
+ field_generators_[i]->SetNoHasBit();
+ }
+ int extra_bits = field_generators_[i]->ExtraRuntimeHasBitsNeeded();
+ if (extra_bits) {
+ field_generators_[i]->SetExtraRuntimeHasBitsBase(total_bits);
+ total_bits += extra_bits;
+ }
+ }
+ return total_bits;
+}
+
+void FieldGeneratorMap::SetOneofIndexBase(int index_base) {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_[i]->SetOneofIndexBase(index_base);
+ }
+}
+
+bool FieldGeneratorMap::DoesAnyFieldHaveNonZeroDefault(void) const {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ if (HasNonZeroDefaultValue(descriptor_->field(i))) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.h
new file mode 100644
index 0000000000..a3a4b1b6e2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_field.h
@@ -0,0 +1,194 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+
+namespace io {
+class Printer; // printer.h
+} // namespace io
+
+namespace compiler {
+namespace objectivec {
+
+class FieldGenerator {
+ public:
+ static FieldGenerator* Make(const FieldDescriptor* field,
+ const Options& options);
+
+ virtual ~FieldGenerator();
+
+ // Exposed for subclasses to fill in.
+ virtual void GenerateFieldStorageDeclaration(io::Printer* printer) const = 0;
+ virtual void GeneratePropertyDeclaration(io::Printer* printer) const = 0;
+ virtual void GeneratePropertyImplementation(io::Printer* printer) const = 0;
+
+ // Called by GenerateFieldDescription, exposed for classes that need custom
+ // generation.
+
+ // Exposed for subclasses to extend, base does nothing.
+ virtual void GenerateCFunctionDeclarations(io::Printer* printer) const;
+ virtual void GenerateCFunctionImplementations(io::Printer* printer) const;
+
+ // Exposed for subclasses, should always call it on the parent class also.
+ virtual void DetermineForwardDeclarations(set<string>* fwd_decls) const;
+
+ // Used during generation, not intended to be extended by subclasses.
+ void GenerateFieldDescription(
+ io::Printer* printer, bool include_default) const;
+ void GenerateFieldNumberConstant(io::Printer* printer) const;
+
+ // Exposed to get and set the has bits information.
+ virtual bool RuntimeUsesHasBit(void) const = 0;
+ void SetRuntimeHasBit(int has_index);
+ void SetNoHasBit(void);
+ virtual int ExtraRuntimeHasBitsNeeded(void) const;
+ virtual void SetExtraRuntimeHasBitsBase(int index_base);
+ void SetOneofIndexBase(int index_base);
+
+ string variable(const char* key) const {
+ return variables_.find(key)->second;
+ }
+
+ bool needs_textformat_name_support() const {
+ const string& field_flags = variable("fieldflags");
+ return field_flags.find("GPBFieldTextFormatNameCustom") != string::npos;
+ }
+ string generated_objc_name() const { return variable("name"); }
+ string raw_field_name() const { return variable("raw_field_name"); }
+
+ protected:
+ FieldGenerator(const FieldDescriptor* descriptor, const Options& options);
+
+ virtual void FinishInitialization(void);
+ virtual bool WantsHasProperty(void) const = 0;
+
+ const FieldDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGenerator);
+};
+
+class SingleFieldGenerator : public FieldGenerator {
+ public:
+ virtual ~SingleFieldGenerator();
+
+ virtual void GenerateFieldStorageDeclaration(io::Printer* printer) const;
+ virtual void GeneratePropertyDeclaration(io::Printer* printer) const;
+
+ virtual void GeneratePropertyImplementation(io::Printer* printer) const;
+
+ virtual bool RuntimeUsesHasBit(void) const;
+
+ protected:
+ SingleFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual bool WantsHasProperty(void) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(SingleFieldGenerator);
+};
+
+// Subclass with common support for when the field ends up as an ObjC Object.
+class ObjCObjFieldGenerator : public SingleFieldGenerator {
+ public:
+ virtual ~ObjCObjFieldGenerator();
+
+ virtual void GenerateFieldStorageDeclaration(io::Printer* printer) const;
+ virtual void GeneratePropertyDeclaration(io::Printer* printer) const;
+
+ protected:
+ ObjCObjFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ObjCObjFieldGenerator);
+};
+
+class RepeatedFieldGenerator : public ObjCObjFieldGenerator {
+ public:
+ virtual ~RepeatedFieldGenerator();
+
+ virtual void GenerateFieldStorageDeclaration(io::Printer* printer) const;
+ virtual void GeneratePropertyDeclaration(io::Printer* printer) const;
+
+ virtual void GeneratePropertyImplementation(io::Printer* printer) const;
+
+ virtual bool RuntimeUsesHasBit(void) const;
+
+ protected:
+ RepeatedFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual void FinishInitialization(void);
+ virtual bool WantsHasProperty(void) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedFieldGenerator);
+};
+
+// Convenience class which constructs FieldGenerators for a Descriptor.
+class FieldGeneratorMap {
+ public:
+ FieldGeneratorMap(const Descriptor* descriptor, const Options& options);
+ ~FieldGeneratorMap();
+
+ const FieldGenerator& get(const FieldDescriptor* field) const;
+ const FieldGenerator& get_extension(int index) const;
+
+ // Assigns the has bits and returns the number of bits needed.
+ int CalculateHasBits(void);
+
+ void SetOneofIndexBase(int index_base);
+
+ // Check if any field of this message has a non zero default.
+ bool DoesAnyFieldHaveNonZeroDefault(void) const;
+
+ private:
+ const Descriptor* descriptor_;
+ scoped_array<scoped_ptr<FieldGenerator> > field_generators_;
+ scoped_array<scoped_ptr<FieldGenerator> > extension_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGeneratorMap);
+};
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.cc
new file mode 100644
index 0000000000..b864ef129e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.cc
@@ -0,0 +1,637 @@
+// 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.
+
+#include <google/protobuf/compiler/objectivec/objectivec_file.h>
+#include <google/protobuf/compiler/objectivec/objectivec_enum.h>
+#include <google/protobuf/compiler/objectivec/objectivec_extension.h>
+#include <google/protobuf/compiler/objectivec/objectivec_message.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/stubs/stl_util.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <iostream>
+#include <sstream>
+
+// NOTE: src/google/protobuf/compiler/plugin.cc makes use of cerr for some
+// error cases, so it seems to be ok to use as a back door for errors.
+
+namespace google {
+namespace protobuf {
+
+// This is also found in GPBBootstrap.h, and needs to be kept in sync. It
+// is the version check done to ensure generated code works with the current
+// runtime being used.
+const int32 GOOGLE_PROTOBUF_OBJC_GEN_VERSION = 30001;
+
+namespace compiler {
+namespace objectivec {
+
+namespace {
+
+class ImportWriter {
+ public:
+ ImportWriter(const Options& options)
+ : options_(options),
+ need_to_parse_mapping_file_(true) {}
+
+ void AddFile(const FileGenerator* file);
+ void Print(io::Printer *printer) const;
+
+ private:
+ class ProtoFrameworkCollector : public LineConsumer {
+ public:
+ ProtoFrameworkCollector(map<string, string>* inout_proto_file_to_framework_name)
+ : map_(inout_proto_file_to_framework_name) {}
+
+ virtual bool ConsumeLine(const StringPiece& line, string* out_error);
+
+ private:
+ map<string, string>* map_;
+ };
+
+ void ParseFrameworkMappings();
+
+ const Options options_;
+ map<string, string> proto_file_to_framework_name_;
+ bool need_to_parse_mapping_file_;
+
+ vector<string> protobuf_framework_imports_;
+ vector<string> protobuf_non_framework_imports_;
+ vector<string> other_framework_imports_;
+ vector<string> other_imports_;
+};
+
+void ImportWriter::AddFile(const FileGenerator* file) {
+ const FileDescriptor* file_descriptor = file->Descriptor();
+ const string extension(".pbobjc.h");
+
+ if (IsProtobufLibraryBundledProtoFile(file_descriptor)) {
+ protobuf_framework_imports_.push_back(
+ FilePathBasename(file_descriptor) + extension);
+ protobuf_non_framework_imports_.push_back(file->Path() + extension);
+ return;
+ }
+
+ // Lazy parse any mappings.
+ if (need_to_parse_mapping_file_) {
+ ParseFrameworkMappings();
+ }
+
+ map<string, string>::iterator proto_lookup =
+ proto_file_to_framework_name_.find(file_descriptor->name());
+ if (proto_lookup != proto_file_to_framework_name_.end()) {
+ other_framework_imports_.push_back(
+ proto_lookup->second + "/" +
+ FilePathBasename(file_descriptor) + extension);
+ return;
+ }
+
+ if (!options_.generate_for_named_framework.empty()) {
+ other_framework_imports_.push_back(
+ options_.generate_for_named_framework + "/" +
+ FilePathBasename(file_descriptor) + extension);
+ return;
+ }
+
+ other_imports_.push_back(file->Path() + extension);
+}
+
+void ImportWriter::Print(io::Printer* printer) const {
+ assert(protobuf_non_framework_imports_.size() ==
+ protobuf_framework_imports_.size());
+
+ bool add_blank_line = false;
+
+ if (protobuf_framework_imports_.size() > 0) {
+ const string framework_name(ProtobufLibraryFrameworkName);
+ const string cpp_symbol(ProtobufFrameworkImportSymbol(framework_name));
+
+ printer->Print(
+ "#if $cpp_symbol$\n",
+ "cpp_symbol", cpp_symbol);
+ for (vector<string>::const_iterator iter = protobuf_framework_imports_.begin();
+ iter != protobuf_framework_imports_.end(); ++iter) {
+ printer->Print(
+ " #import <$framework_name$/$header$>\n",
+ "framework_name", framework_name,
+ "header", *iter);
+ }
+ printer->Print(
+ "#else\n");
+ for (vector<string>::const_iterator iter = protobuf_non_framework_imports_.begin();
+ iter != protobuf_non_framework_imports_.end(); ++iter) {
+ printer->Print(
+ " #import \"$header$\"\n",
+ "header", *iter);
+ }
+ printer->Print(
+ "#endif\n");
+
+ add_blank_line = true;
+ }
+
+ if (other_framework_imports_.size() > 0) {
+ if (add_blank_line) {
+ printer->Print("\n");
+ }
+
+ for (vector<string>::const_iterator iter = other_framework_imports_.begin();
+ iter != other_framework_imports_.end(); ++iter) {
+ printer->Print(
+ " #import <$header$>\n",
+ "header", *iter);
+ }
+
+ add_blank_line = true;
+ }
+
+ if (other_imports_.size() > 0) {
+ if (add_blank_line) {
+ printer->Print("\n");
+ }
+
+ for (vector<string>::const_iterator iter = other_imports_.begin();
+ iter != other_imports_.end(); ++iter) {
+ printer->Print(
+ " #import \"$header$\"\n",
+ "header", *iter);
+ }
+ }
+}
+
+void ImportWriter::ParseFrameworkMappings() {
+ need_to_parse_mapping_file_ = false;
+ if (options_.named_framework_to_proto_path_mappings_path.empty()) {
+ return; // Nothing to do.
+ }
+
+ ProtoFrameworkCollector collector(&proto_file_to_framework_name_);
+ string parse_error;
+ if (!ParseSimpleFile(options_.named_framework_to_proto_path_mappings_path,
+ &collector, &parse_error)) {
+ cerr << "error parsing " << options_.named_framework_to_proto_path_mappings_path
+ << " : " << parse_error << endl;
+ cerr.flush();
+ }
+}
+
+bool ImportWriter::ProtoFrameworkCollector::ConsumeLine(
+ const StringPiece& line, string* out_error) {
+ int offset = line.find(':');
+ if (offset == StringPiece::npos) {
+ *out_error =
+ string("Framework/proto file mapping line without colon sign: '") +
+ line.ToString() + "'.";
+ return false;
+ }
+ StringPiece framework_name(line, 0, offset);
+ StringPiece proto_file_list(line, offset + 1, line.length() - offset - 1);
+ StringPieceTrimWhitespace(&framework_name);
+
+ int start = 0;
+ while (start < proto_file_list.length()) {
+ offset = proto_file_list.find(',', start);
+ if (offset == StringPiece::npos) {
+ offset = proto_file_list.length();
+ }
+
+ StringPiece proto_file(proto_file_list, start, offset - start);
+ StringPieceTrimWhitespace(&proto_file);
+ if (proto_file.size() != 0) {
+ map<string, string>::iterator existing_entry =
+ map_->find(proto_file.ToString());
+ if (existing_entry != map_->end()) {
+ cerr << "warning: duplicate proto file reference, replacing framework entry for '"
+ << proto_file.ToString() << "' with '" << framework_name.ToString()
+ << "' (was '" << existing_entry->second << "')." << endl;
+ cerr.flush();
+ }
+
+ if (proto_file.find(' ') != StringPiece::npos) {
+ cerr << "note: framework mapping file had a proto file with a space in, hopefully that isn't a missing comma: '"
+ << proto_file.ToString() << "'" << endl;
+ cerr.flush();
+ }
+
+ (*map_)[proto_file.ToString()] = framework_name.ToString();
+ }
+
+ start = offset + 1;
+ }
+
+ return true;
+}
+
+} // namespace
+
+
+FileGenerator::FileGenerator(const FileDescriptor *file, const Options& options)
+ : file_(file),
+ root_class_name_(FileClassName(file)),
+ is_public_dep_(false),
+ options_(options) {
+ for (int i = 0; i < file_->enum_type_count(); i++) {
+ EnumGenerator *generator = new EnumGenerator(file_->enum_type(i));
+ enum_generators_.push_back(generator);
+ }
+ for (int i = 0; i < file_->message_type_count(); i++) {
+ MessageGenerator *generator =
+ new MessageGenerator(root_class_name_, file_->message_type(i), options_);
+ message_generators_.push_back(generator);
+ }
+ for (int i = 0; i < file_->extension_count(); i++) {
+ ExtensionGenerator *generator =
+ new ExtensionGenerator(root_class_name_, file_->extension(i));
+ extension_generators_.push_back(generator);
+ }
+}
+
+FileGenerator::~FileGenerator() {
+ STLDeleteContainerPointers(dependency_generators_.begin(),
+ dependency_generators_.end());
+ STLDeleteContainerPointers(enum_generators_.begin(), enum_generators_.end());
+ STLDeleteContainerPointers(message_generators_.begin(),
+ message_generators_.end());
+ STLDeleteContainerPointers(extension_generators_.begin(),
+ extension_generators_.end());
+}
+
+void FileGenerator::GenerateHeader(io::Printer *printer) {
+ PrintFileRuntimePreamble(printer, "GPBProtocolBuffers.h");
+
+ // Add some verification that the generated code matches the source the
+ // code is being compiled with.
+ printer->Print(
+ "#if GOOGLE_PROTOBUF_OBJC_GEN_VERSION != $protoc_gen_objc_version$\n"
+ "#error This file was generated by a different version of protoc which is incompatible with your Protocol Buffer library sources.\n"
+ "#endif\n"
+ "\n",
+ "protoc_gen_objc_version",
+ SimpleItoa(GOOGLE_PROTOBUF_OBJC_GEN_VERSION));
+
+ // #import any headers for "public imports" in the proto file.
+ {
+ ImportWriter import_writer(options_);
+ const vector<FileGenerator *> &dependency_generators = DependencyGenerators();
+ for (vector<FileGenerator *>::const_iterator iter =
+ dependency_generators.begin();
+ iter != dependency_generators.end(); ++iter) {
+ if ((*iter)->IsPublicDependency()) {
+ import_writer.AddFile(*iter);
+ }
+ }
+ import_writer.Print(printer);
+ }
+
+ // Note:
+ // deprecated-declarations suppression is only needed if some place in this
+ // proto file is something deprecated or if it references something from
+ // another file that is deprecated.
+ printer->Print(
+ "// @@protoc_insertion_point(imports)\n"
+ "\n"
+ "#pragma clang diagnostic push\n"
+ "#pragma clang diagnostic ignored \"-Wdeprecated-declarations\"\n"
+ "\n"
+ "CF_EXTERN_C_BEGIN\n"
+ "\n");
+
+ set<string> fwd_decls;
+ for (vector<MessageGenerator *>::iterator iter = message_generators_.begin();
+ iter != message_generators_.end(); ++iter) {
+ (*iter)->DetermineForwardDeclarations(&fwd_decls);
+ }
+ for (set<string>::const_iterator i(fwd_decls.begin());
+ i != fwd_decls.end(); ++i) {
+ printer->Print("$value$;\n", "value", *i);
+ }
+ if (fwd_decls.begin() != fwd_decls.end()) {
+ printer->Print("\n");
+ }
+
+ printer->Print(
+ "NS_ASSUME_NONNULL_BEGIN\n"
+ "\n");
+
+ // need to write out all enums first
+ for (vector<EnumGenerator *>::iterator iter = enum_generators_.begin();
+ iter != enum_generators_.end(); ++iter) {
+ (*iter)->GenerateHeader(printer);
+ }
+
+ for (vector<MessageGenerator *>::iterator iter = message_generators_.begin();
+ iter != message_generators_.end(); ++iter) {
+ (*iter)->GenerateEnumHeader(printer);
+ }
+
+ // For extensions to chain together, the Root gets created even if there
+ // are no extensions.
+ printer->Print(
+ "#pragma mark - $root_class_name$\n"
+ "\n"
+ "/// Exposes the extension registry for this file.\n"
+ "///\n"
+ "/// The base class provides:\n"
+ "/// @code\n"
+ "/// + (GPBExtensionRegistry *)extensionRegistry;\n"
+ "/// @endcode\n"
+ "/// which is a @c GPBExtensionRegistry that includes all the extensions defined by\n"
+ "/// this file and all files that it depends on.\n"
+ "@interface $root_class_name$ : GPBRootObject\n"
+ "@end\n"
+ "\n",
+ "root_class_name", root_class_name_);
+
+ if (extension_generators_.size() > 0) {
+ // The dynamic methods block is only needed if there are extensions.
+ printer->Print(
+ "@interface $root_class_name$ (DynamicMethods)\n",
+ "root_class_name", root_class_name_);
+
+ for (vector<ExtensionGenerator *>::iterator iter =
+ extension_generators_.begin();
+ iter != extension_generators_.end(); ++iter) {
+ (*iter)->GenerateMembersHeader(printer);
+ }
+
+ printer->Print("@end\n\n");
+ } // extension_generators_.size() > 0
+
+ for (vector<MessageGenerator *>::iterator iter = message_generators_.begin();
+ iter != message_generators_.end(); ++iter) {
+ (*iter)->GenerateMessageHeader(printer);
+ }
+
+ printer->Print(
+ "NS_ASSUME_NONNULL_END\n"
+ "\n"
+ "CF_EXTERN_C_END\n"
+ "\n"
+ "#pragma clang diagnostic pop\n"
+ "\n"
+ "// @@protoc_insertion_point(global_scope)\n");
+}
+
+void FileGenerator::GenerateSource(io::Printer *printer) {
+ // #import the runtime support.
+ PrintFileRuntimePreamble(printer, "GPBProtocolBuffers_RuntimeSupport.h");
+
+ {
+ ImportWriter import_writer(options_);
+
+ // #import the header for this proto file.
+ import_writer.AddFile(this);
+
+ // #import the headers for anything that a plain dependency of this proto
+ // file (that means they were just an include, not a "public" include).
+ const vector<FileGenerator *> &dependency_generators =
+ DependencyGenerators();
+ for (vector<FileGenerator *>::const_iterator iter =
+ dependency_generators.begin();
+ iter != dependency_generators.end(); ++iter) {
+ if (!(*iter)->IsPublicDependency()) {
+ import_writer.AddFile(*iter);
+ }
+ }
+
+ import_writer.Print(printer);
+ }
+
+ bool includes_oneof = false;
+ for (vector<MessageGenerator *>::iterator iter = message_generators_.begin();
+ iter != message_generators_.end(); ++iter) {
+ if ((*iter)->IncludesOneOfDefinition()) {
+ includes_oneof = true;
+ break;
+ }
+ }
+
+ // Note:
+ // deprecated-declarations suppression is only needed if some place in this
+ // proto file is something deprecated or if it references something from
+ // another file that is deprecated.
+ printer->Print(
+ "// @@protoc_insertion_point(imports)\n"
+ "\n"
+ "#pragma clang diagnostic push\n"
+ "#pragma clang diagnostic ignored \"-Wdeprecated-declarations\"\n");
+ if (includes_oneof) {
+ // The generated code for oneof's uses direct ivar access, suppress the
+ // warning incase developer turn that on in the context they compile the
+ // generated code.
+ printer->Print(
+ "#pragma clang diagnostic ignored \"-Wdirect-ivar-access\"\n");
+ }
+
+ printer->Print(
+ "\n"
+ "#pragma mark - $root_class_name$\n"
+ "\n"
+ "@implementation $root_class_name$\n\n",
+ "root_class_name", root_class_name_);
+
+ // Generate the extension initialization structures for the top level and
+ // any nested messages.
+ ostringstream extensions_stringstream;
+ if (file_->extension_count() + file_->message_type_count() > 0) {
+ io::OstreamOutputStream extensions_outputstream(&extensions_stringstream);
+ io::Printer extensions_printer(&extensions_outputstream, '$');
+ for (vector<ExtensionGenerator *>::iterator iter =
+ extension_generators_.begin();
+ iter != extension_generators_.end(); ++iter) {
+ (*iter)->GenerateStaticVariablesInitialization(&extensions_printer);
+ }
+ for (vector<MessageGenerator *>::iterator iter =
+ message_generators_.begin();
+ iter != message_generators_.end(); ++iter) {
+ (*iter)->GenerateStaticVariablesInitialization(&extensions_printer);
+ }
+ extensions_stringstream.flush();
+ }
+
+ // If there were any extensions or this file has any dependencies, output
+ // a registry to override to create the file specific registry.
+ const string& extensions_str = extensions_stringstream.str();
+ if (extensions_str.length() > 0 || file_->dependency_count() > 0) {
+ printer->Print(
+ "+ (GPBExtensionRegistry*)extensionRegistry {\n"
+ " // This is called by +initialize so there is no need to worry\n"
+ " // about thread safety and initialization of registry.\n"
+ " static GPBExtensionRegistry* registry = nil;\n"
+ " if (!registry) {\n"
+ " GPBDebugCheckRuntimeVersion();\n"
+ " registry = [[GPBExtensionRegistry alloc] init];\n");
+
+ printer->Indent();
+ printer->Indent();
+
+ if (extensions_str.length() > 0) {
+ printer->Print(
+ "static GPBExtensionDescription descriptions[] = {\n");
+ printer->Indent();
+ printer->Print(extensions_str.c_str());
+ printer->Outdent();
+ printer->Print(
+ "};\n"
+ "for (size_t i = 0; i < sizeof(descriptions) / sizeof(descriptions[0]); ++i) {\n"
+ " GPBExtensionDescriptor *extension =\n"
+ " [[GPBExtensionDescriptor alloc] initWithExtensionDescription:&descriptions[i]];\n"
+ " [registry addExtension:extension];\n"
+ " [self globallyRegisterExtension:extension];\n"
+ " [extension release];\n"
+ "}\n");
+ }
+
+ const vector<FileGenerator *> &dependency_generators =
+ DependencyGenerators();
+ for (vector<FileGenerator *>::const_iterator iter =
+ dependency_generators.begin();
+ iter != dependency_generators.end(); ++iter) {
+ printer->Print(
+ "[registry addExtensions:[$dependency$ extensionRegistry]];\n",
+ "dependency", (*iter)->RootClassName());
+ }
+
+ printer->Outdent();
+ printer->Outdent();
+
+ printer->Print(
+ " }\n"
+ " return registry;\n"
+ "}\n"
+ "\n");
+ }
+
+ printer->Print("@end\n\n");
+
+ // File descriptor only needed if there are messages to use it.
+ if (message_generators_.size() > 0) {
+ string syntax;
+ switch (file_->syntax()) {
+ case FileDescriptor::SYNTAX_UNKNOWN:
+ syntax = "GPBFileSyntaxUnknown";
+ break;
+ case FileDescriptor::SYNTAX_PROTO2:
+ syntax = "GPBFileSyntaxProto2";
+ break;
+ case FileDescriptor::SYNTAX_PROTO3:
+ syntax = "GPBFileSyntaxProto3";
+ break;
+ }
+ printer->Print(
+ "#pragma mark - $root_class_name$_FileDescriptor\n"
+ "\n"
+ "static GPBFileDescriptor *$root_class_name$_FileDescriptor(void) {\n"
+ " // This is called by +initialize so there is no need to worry\n"
+ " // about thread safety of the singleton.\n"
+ " static GPBFileDescriptor *descriptor = NULL;\n"
+ " if (!descriptor) {\n"
+ " GPBDebugCheckRuntimeVersion();\n"
+ " descriptor = [[GPBFileDescriptor alloc] initWithPackage:@\"$package$\"\n"
+ " syntax:$syntax$];\n"
+ " }\n"
+ " return descriptor;\n"
+ "}\n"
+ "\n",
+ "root_class_name", root_class_name_,
+ "package", file_->package(),
+ "syntax", syntax);
+ }
+
+ for (vector<EnumGenerator *>::iterator iter = enum_generators_.begin();
+ iter != enum_generators_.end(); ++iter) {
+ (*iter)->GenerateSource(printer);
+ }
+ for (vector<MessageGenerator *>::iterator iter = message_generators_.begin();
+ iter != message_generators_.end(); ++iter) {
+ (*iter)->GenerateSource(printer);
+ }
+
+ printer->Print(
+ "\n"
+ "#pragma clang diagnostic pop\n"
+ "\n"
+ "// @@protoc_insertion_point(global_scope)\n");
+}
+
+const vector<FileGenerator *> &FileGenerator::DependencyGenerators() {
+ if (file_->dependency_count() != dependency_generators_.size()) {
+ set<string> public_import_names;
+ for (int i = 0; i < file_->public_dependency_count(); i++) {
+ public_import_names.insert(file_->public_dependency(i)->name());
+ }
+ for (int i = 0; i < file_->dependency_count(); i++) {
+ FileGenerator *generator =
+ new FileGenerator(file_->dependency(i), options_);
+ const string& name = file_->dependency(i)->name();
+ bool public_import = (public_import_names.count(name) != 0);
+ generator->SetIsPublicDependency(public_import);
+ dependency_generators_.push_back(generator);
+ }
+ }
+ return dependency_generators_;
+}
+
+// Helper to print the import of the runtime support at the top of generated
+// files. This currently only supports the runtime coming from a framework
+// as defined by the official CocoaPod.
+void FileGenerator::PrintFileRuntimePreamble(
+ io::Printer* printer, const string& header_to_import) const {
+ printer->Print(
+ "// Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "// source: $filename$\n"
+ "\n",
+ "filename", file_->name());
+
+ const string framework_name(ProtobufLibraryFrameworkName);
+ const string cpp_symbol(ProtobufFrameworkImportSymbol(framework_name));
+ printer->Print(
+ "// This CPP symbol can be defined to use imports that match up to the framework\n"
+ "// imports needed when using CocoaPods.\n"
+ "#if !defined($cpp_symbol$)\n"
+ " #define $cpp_symbol$ 0\n"
+ "#endif\n"
+ "\n"
+ "#if $cpp_symbol$\n"
+ " #import <$framework_name$/$header$>\n"
+ "#else\n"
+ " #import \"$header$\"\n"
+ "#endif\n"
+ "\n",
+ "cpp_symbol", cpp_symbol,
+ "header", header_to_import,
+ "framework_name", framework_name);
+}
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.h
new file mode 100644
index 0000000000..8e4388d8d2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_file.h
@@ -0,0 +1,102 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_FILE_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_FILE_H__
+
+#include <string>
+#include <set>
+#include <vector>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+class FileDescriptor; // descriptor.h
+namespace io {
+class Printer; // printer.h
+}
+}
+
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class EnumGenerator;
+class ExtensionGenerator;
+class MessageGenerator;
+
+class FileGenerator {
+ public:
+ FileGenerator(const FileDescriptor* file, const Options& options);
+ ~FileGenerator();
+
+ void GenerateSource(io::Printer* printer);
+ void GenerateHeader(io::Printer* printer);
+
+ const string& RootClassName() const { return root_class_name_; }
+ const string Path() const { return FilePath(file_); }
+ const FileDescriptor* Descriptor() const { return file_; }
+
+ bool IsPublicDependency() const { return is_public_dep_; }
+
+ protected:
+ void SetIsPublicDependency(bool is_public_dep) {
+ is_public_dep_ = is_public_dep;
+ }
+
+ private:
+ const FileDescriptor* file_;
+ string root_class_name_;
+
+ // Access this field through the DependencyGenerators accessor call below.
+ // Do not reference it directly.
+ vector<FileGenerator*> dependency_generators_;
+
+ vector<EnumGenerator*> enum_generators_;
+ vector<MessageGenerator*> message_generators_;
+ vector<ExtensionGenerator*> extension_generators_;
+ bool is_public_dep_;
+
+ const Options options_;
+
+ const vector<FileGenerator*>& DependencyGenerators();
+ void PrintFileRuntimePreamble(
+ io::Printer* printer, const string& header_to_import) const;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_FILE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.cc
new file mode 100644
index 0000000000..a0b6d6cb6c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.cc
@@ -0,0 +1,151 @@
+// 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.
+
+#include <iostream>
+#include <google/protobuf/compiler/objectivec/objectivec_generator.h>
+#include <google/protobuf/compiler/objectivec/objectivec_file.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+ObjectiveCGenerator::ObjectiveCGenerator() {}
+
+ObjectiveCGenerator::~ObjectiveCGenerator() {}
+
+bool ObjectiveCGenerator::Generate(const FileDescriptor* file,
+ const string& parameter,
+ OutputDirectory* output_directory,
+ string* error) const {
+ // -----------------------------------------------------------------
+ // Parse generator options. These options are passed to the compiler using the
+ // --objc_opt flag. The options are passed as a comma separated list of
+ // options along with their values. If the option appears multiple times, only
+ // the last value will be considered.
+ //
+ // e.g. protoc ... --objc_opt=expected_prefixes=file.txt,generate_for_named_framework=MyFramework
+
+ Options generation_options;
+
+ vector<pair<string, string> > options;
+ ParseGeneratorParameter(parameter, &options);
+ for (int i = 0; i < options.size(); i++) {
+ if (options[i].first == "expected_prefixes_path") {
+ // Path to find a file containing the expected prefixes
+ // (objc_class_prefix "PREFIX") for proto packages (package NAME). The
+ // generator will then issue warnings/errors if in the proto files being
+ // generated the option is not listed/wrong/etc in the file.
+ //
+ // The format of the file is:
+ // - An entry is a line of "package=prefix".
+ // - Comments start with "#".
+ // - A comment can go on a line after a expected package/prefix pair.
+ // (i.e. - "package=prefix # comment")
+ //
+ // There is no validation that the prefixes are good prefixes, it is
+ // assumed that they are when you create the file.
+ generation_options.expected_prefixes_path = options[i].second;
+ } else if (options[i].first == "generate_for_named_framework") {
+ // The name of the framework that protos are being generated for. This
+ // will cause the #import statements to be framework based using this
+ // name (i.e. - "#import <NAME/proto.pbobjc.h>).
+ //
+ // NOTE: If this option is used with
+ // named_framework_to_proto_path_mappings_path, then this is effectively
+ // the "default" framework name used for everything that wasn't mapped by
+ // the mapping file.
+ generation_options.generate_for_named_framework = options[i].second;
+ } else if (options[i].first == "named_framework_to_proto_path_mappings_path") {
+ // Path to find a file containing the list of framework names and proto
+ // files. The generator uses this to decide if a proto file
+ // referenced should use a framework style import vs. a user level import
+ // (#import <FRAMEWORK/file.pbobjc.h> vs #import "dir/file.pbobjc.h").
+ //
+ // The format of the file is:
+ // - An entry is a line of "frameworkName: file.proto, dir/file2.proto".
+ // - Comments start with "#".
+ // - A comment can go on a line after a expected package/prefix pair.
+ // (i.e. - "frameworkName: file.proto # comment")
+ //
+ // Any number of files can be listed for a framework, just separate them
+ // with commas.
+ //
+ // There can be multiple lines listing the same frameworkName incase it
+ // has a lot of proto files included in it; having multiple lines makes
+ // things easier to read. If a proto file is not configured in the
+ // mappings file, it will use the default framework name if one was passed
+ // with generate_for_named_framework, or the relative path to it's include
+ // path otherwise.
+ generation_options.named_framework_to_proto_path_mappings_path = options[i].second;
+ } else {
+ *error = "error: Unknown generator option: " + options[i].first;
+ return false;
+ }
+ }
+
+ // -----------------------------------------------------------------
+
+ // Validate the objc prefix/package pairing.
+ if (!ValidateObjCClassPrefix(file, generation_options, error)) {
+ // *error will have been filled in.
+ return false;
+ }
+
+ FileGenerator file_generator(file, generation_options);
+ string filepath = FilePath(file);
+
+ // Generate header.
+ {
+ scoped_ptr<io::ZeroCopyOutputStream> output(
+ output_directory->Open(filepath + ".pbobjc.h"));
+ io::Printer printer(output.get(), '$');
+ file_generator.GenerateHeader(&printer);
+ }
+
+ // Generate m file.
+ {
+ scoped_ptr<io::ZeroCopyOutputStream> output(
+ output_directory->Open(filepath + ".pbobjc.m"));
+ io::Printer printer(output.get(), '$');
+ file_generator.GenerateSource(&printer);
+ }
+
+ return true;
+}
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.h
new file mode 100644
index 0000000000..09266b042f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_generator.h
@@ -0,0 +1,61 @@
+// 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.
+
+// Generates ObjectiveC code for a given .proto file.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_GENERATOR_H__
+
+#include <string>
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class LIBPROTOC_EXPORT ObjectiveCGenerator : public CodeGenerator {
+ public:
+ ObjectiveCGenerator();
+ ~ObjectiveCGenerator();
+
+ // implements CodeGenerator ----------------------------------------
+ bool Generate(const FileDescriptor* file, const string& parameter,
+ OutputDirectory* output_directory, string* error) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ObjectiveCGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.cc
new file mode 100644
index 0000000000..22c7a883d0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.cc
@@ -0,0 +1,1375 @@
+// 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.
+
+#ifdef _MSC_VER
+#include <io.h>
+#else
+#include <unistd.h>
+#endif
+#include <climits>
+#include <errno.h>
+#include <fcntl.h>
+#include <fstream>
+#include <iostream>
+#include <sstream>
+#include <stdlib.h>
+#include <vector>
+
+#include <google/protobuf/stubs/hash.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+
+// NOTE: src/google/protobuf/compiler/plugin.cc makes use of cerr for some
+// error cases, so it seems to be ok to use as a back door for errors.
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+Options::Options() {
+ // Default is the value of the env for the package prefixes.
+ const char* file_path = getenv("GPB_OBJC_EXPECTED_PACKAGE_PREFIXES");
+ if (file_path) {
+ expected_prefixes_path = file_path;
+ }
+}
+
+namespace {
+
+hash_set<string> MakeWordsMap(const char* const words[], size_t num_words) {
+ hash_set<string> result;
+ for (int i = 0; i < num_words; i++) {
+ result.insert(words[i]);
+ }
+ return result;
+}
+
+const char* const kUpperSegmentsList[] = {"url", "http", "https"};
+
+hash_set<string> kUpperSegments =
+ MakeWordsMap(kUpperSegmentsList, GOOGLE_ARRAYSIZE(kUpperSegmentsList));
+
+bool ascii_isnewline(char c) {
+ return c == '\n' || c == '\r';
+}
+
+// Internal helper for name handing.
+// Do not expose this outside of helpers, stick to having functions for specific
+// cases (ClassName(), FieldName()), so there is always consistent suffix rules.
+string UnderscoresToCamelCase(const string& input, bool first_capitalized) {
+ vector<string> values;
+ string current;
+
+ bool last_char_was_number = false;
+ bool last_char_was_lower = false;
+ bool last_char_was_upper = false;
+ for (int i = 0; i < input.size(); i++) {
+ char c = input[i];
+ if (ascii_isdigit(c)) {
+ if (!last_char_was_number) {
+ values.push_back(current);
+ current = "";
+ }
+ current += c;
+ last_char_was_number = last_char_was_lower = last_char_was_upper = false;
+ last_char_was_number = true;
+ } else if (ascii_islower(c)) {
+ // lowercase letter can follow a lowercase or uppercase letter
+ if (!last_char_was_lower && !last_char_was_upper) {
+ values.push_back(current);
+ current = "";
+ }
+ current += c; // already lower
+ last_char_was_number = last_char_was_lower = last_char_was_upper = false;
+ last_char_was_lower = true;
+ } else if (ascii_isupper(c)) {
+ if (!last_char_was_upper) {
+ values.push_back(current);
+ current = "";
+ }
+ current += ascii_tolower(c);
+ last_char_was_number = last_char_was_lower = last_char_was_upper = false;
+ last_char_was_upper = true;
+ } else {
+ last_char_was_number = last_char_was_lower = last_char_was_upper = false;
+ }
+ }
+ values.push_back(current);
+
+ string result;
+ bool first_segment_forces_upper = false;
+ for (vector<string>::iterator i = values.begin(); i != values.end(); ++i) {
+ string value = *i;
+ bool all_upper = (kUpperSegments.count(value) > 0);
+ if (all_upper && (result.length() == 0)) {
+ first_segment_forces_upper = true;
+ }
+ for (int j = 0; j < value.length(); j++) {
+ if (j == 0 || all_upper) {
+ value[j] = ascii_toupper(value[j]);
+ } else {
+ // Nothing, already in lower.
+ }
+ }
+ result += value;
+ }
+ if ((result.length() != 0) &&
+ !first_capitalized &&
+ !first_segment_forces_upper) {
+ result[0] = ascii_tolower(result[0]);
+ }
+ return result;
+}
+
+const char* const kReservedWordList[] = {
+ // Objective C "keywords" that aren't in C
+ // From
+ // http://stackoverflow.com/questions/1873630/reserved-keywords-in-objective-c
+ "id", "_cmd", "super", "in", "out", "inout", "bycopy", "byref", "oneway",
+ "self",
+
+ // C/C++ keywords (Incl C++ 0x11)
+ // From http://en.cppreference.com/w/cpp/keywords
+ "and", "and_eq", "alignas", "alignof", "asm", "auto", "bitand", "bitor",
+ "bool", "break", "case", "catch", "char", "char16_t", "char32_t", "class",
+ "compl", "const", "constexpr", "const_cast", "continue", "decltype",
+ "default", "delete", "double", "dynamic_cast", "else", "enum", "explicit",
+ "export", "extern ", "false", "float", "for", "friend", "goto", "if",
+ "inline", "int", "long", "mutable", "namespace", "new", "noexcept", "not",
+ "not_eq", "nullptr", "operator", "or", "or_eq", "private", "protected",
+ "public", "register", "reinterpret_cast", "return", "short", "signed",
+ "sizeof", "static", "static_assert", "static_cast", "struct", "switch",
+ "template", "this", "thread_local", "throw", "true", "try", "typedef",
+ "typeid", "typename", "union", "unsigned", "using", "virtual", "void",
+ "volatile", "wchar_t", "while", "xor", "xor_eq",
+
+ // C99 keywords
+ // From
+ // http://publib.boulder.ibm.com/infocenter/lnxpcomp/v8v101/index.jsp?topic=%2Fcom.ibm.xlcpp8l.doc%2Flanguage%2Fref%2Fkeyw.htm
+ "restrict",
+
+ // Objective-C Runtime typedefs
+ // From <obc/runtime.h>
+ "Category", "Ivar", "Method", "Protocol",
+
+ // NSObject Methods
+ // new is covered by C++ keywords.
+ "description", "debugDescription", "finalize", "hash", "dealloc", "init",
+ "class", "superclass", "retain", "release", "autorelease", "retainCount",
+ "zone", "isProxy", "copy", "mutableCopy", "classForCoder",
+
+ // GPBMessage Methods
+ // Only need to add instance methods that may conflict with
+ // method declared in protos. The main cases are methods
+ // that take no arguments, or setFoo:/hasFoo: type methods.
+ "clear", "data", "delimitedData", "descriptor", "extensionRegistry",
+ "extensionsCurrentlySet", "isInitialized", "serializedSize",
+ "sortedExtensionsInUse", "unknownFields",
+
+ // MacTypes.h names
+ "Fixed", "Fract", "Size", "LogicalAddress", "PhysicalAddress", "ByteCount",
+ "ByteOffset", "Duration", "AbsoluteTime", "OptionBits", "ItemCount",
+ "PBVersion", "ScriptCode", "LangCode", "RegionCode", "OSType",
+ "ProcessSerialNumber", "Point", "Rect", "FixedPoint", "FixedRect", "Style",
+ "StyleParameter", "StyleField", "TimeScale", "TimeBase", "TimeRecord",
+};
+
+hash_set<string> kReservedWords =
+ MakeWordsMap(kReservedWordList, GOOGLE_ARRAYSIZE(kReservedWordList));
+
+string SanitizeNameForObjC(const string& input, const string& extension) {
+ if (kReservedWords.count(input) > 0) {
+ return input + extension;
+ }
+ return input;
+}
+
+string NameFromFieldDescriptor(const FieldDescriptor* field) {
+ if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ return field->message_type()->name();
+ } else {
+ return field->name();
+ }
+}
+
+void PathSplit(const string& path, string* directory, string* basename) {
+ string::size_type last_slash = path.rfind('/');
+ if (last_slash == string::npos) {
+ if (directory) {
+ *directory = "";
+ }
+ if (basename) {
+ *basename = path;
+ }
+ } else {
+ if (directory) {
+ *directory = path.substr(0, last_slash);
+ }
+ if (basename) {
+ *basename = path.substr(last_slash + 1);
+ }
+ }
+}
+
+bool IsSpecialName(const string& name, const string* special_names,
+ size_t count) {
+ for (size_t i = 0; i < count; ++i) {
+ size_t length = special_names[i].length();
+ if (name.compare(0, length, special_names[i]) == 0) {
+ if (name.length() > length) {
+ // If name is longer than the retained_name[i] that it matches
+ // the next character must be not lower case (newton vs newTon vs
+ // new_ton).
+ return !ascii_islower(name[length]);
+ } else {
+ return true;
+ }
+ }
+ }
+ return false;
+}
+
+} // namespace
+
+// Escape C++ trigraphs by escaping question marks to \?
+string EscapeTrigraphs(const string& to_escape) {
+ return StringReplace(to_escape, "?", "\\?", true);
+}
+
+string StripProto(const string& filename) {
+ if (HasSuffixString(filename, ".protodevel")) {
+ return StripSuffixString(filename, ".protodevel");
+ } else {
+ return StripSuffixString(filename, ".proto");
+ }
+}
+
+void StringPieceTrimWhitespace(StringPiece* input) {
+ while (!input->empty() && ascii_isspace(*input->data())) {
+ input->remove_prefix(1);
+ }
+ while (!input->empty() && ascii_isspace((*input)[input->length() - 1])) {
+ input->remove_suffix(1);
+ }
+}
+
+
+bool IsRetainedName(const string& name) {
+ // List of prefixes from
+ // http://developer.apple.com/library/mac/#documentation/Cocoa/Conceptual/MemoryMgmt/Articles/mmRules.html
+ static const string retained_names[] = {"new", "alloc", "copy",
+ "mutableCopy"};
+ return IsSpecialName(name, retained_names,
+ sizeof(retained_names) / sizeof(retained_names[0]));
+}
+
+bool IsInitName(const string& name) {
+ static const string init_names[] = {"init"};
+ return IsSpecialName(name, init_names,
+ sizeof(init_names) / sizeof(init_names[0]));
+}
+
+string BaseFileName(const FileDescriptor* file) {
+ string basename;
+ PathSplit(file->name(), NULL, &basename);
+ return basename;
+}
+
+string FilePath(const FileDescriptor* file) {
+ string output;
+ string basename;
+ string directory;
+ PathSplit(file->name(), &directory, &basename);
+ if (directory.length() > 0) {
+ output = directory + "/";
+ }
+ basename = StripProto(basename);
+
+ // CamelCase to be more ObjC friendly.
+ basename = UnderscoresToCamelCase(basename, true);
+
+ output += basename;
+ return output;
+}
+
+string FilePathBasename(const FileDescriptor* file) {
+ string output;
+ string basename;
+ string directory;
+ PathSplit(file->name(), &directory, &basename);
+ basename = StripProto(basename);
+
+ // CamelCase to be more ObjC friendly.
+ output = UnderscoresToCamelCase(basename, true);
+
+ return output;
+}
+
+string FileClassPrefix(const FileDescriptor* file) {
+ // Default is empty string, no need to check has_objc_class_prefix.
+ string result = file->options().objc_class_prefix();
+ return result;
+}
+
+string FileClassName(const FileDescriptor* file) {
+ string name = FileClassPrefix(file);
+ name += UnderscoresToCamelCase(StripProto(BaseFileName(file)), true);
+ name += "Root";
+ // There aren't really any reserved words that end in "Root", but playing
+ // it safe and checking.
+ return SanitizeNameForObjC(name, "_RootClass");
+}
+
+string ClassNameWorker(const Descriptor* descriptor) {
+ string name;
+ if (descriptor->containing_type() != NULL) {
+ name = ClassNameWorker(descriptor->containing_type());
+ name += "_";
+ }
+ return name + descriptor->name();
+}
+
+string ClassNameWorker(const EnumDescriptor* descriptor) {
+ string name;
+ if (descriptor->containing_type() != NULL) {
+ name = ClassNameWorker(descriptor->containing_type());
+ name += "_";
+ }
+ return name + descriptor->name();
+}
+
+string ClassName(const Descriptor* descriptor) {
+ // 1. Message names are used as is (style calls for CamelCase, trust it).
+ // 2. Check for reserved word at the very end and then suffix things.
+ string prefix = FileClassPrefix(descriptor->file());
+ string name = ClassNameWorker(descriptor);
+ return SanitizeNameForObjC(prefix + name, "_Class");
+}
+
+string EnumName(const EnumDescriptor* descriptor) {
+ // 1. Enum names are used as is (style calls for CamelCase, trust it).
+ // 2. Check for reserved word at the every end and then suffix things.
+ // message Fixed {
+ // message Size {...}
+ // enum Mumble {...}
+ // ...
+ // }
+ // yields Fixed_Class, Fixed_Size.
+ string name = FileClassPrefix(descriptor->file());
+ name += ClassNameWorker(descriptor);
+ return SanitizeNameForObjC(name, "_Enum");
+}
+
+string EnumValueName(const EnumValueDescriptor* descriptor) {
+ // Because of the Switch enum compatibility, the name on the enum has to have
+ // the suffix handing, so it slightly diverges from how nested classes work.
+ // enum Fixed {
+ // FOO = 1
+ // }
+ // yields Fixed_Enum and Fixed_Enum_Foo (not Fixed_Foo).
+ const string& class_name = EnumName(descriptor->type());
+ const string& value_str = UnderscoresToCamelCase(descriptor->name(), true);
+ const string& name = class_name + "_" + value_str;
+ // There aren't really any reserved words with an underscore and a leading
+ // capital letter, but playing it safe and checking.
+ return SanitizeNameForObjC(name, "_Value");
+}
+
+string EnumValueShortName(const EnumValueDescriptor* descriptor) {
+ // Enum value names (EnumValueName above) are the enum name turned into
+ // a class name and then the value name is CamelCased and concatenated; the
+ // whole thing then gets sanitized for reserved words.
+ // The "short name" is intended to be the final leaf, the value name; but
+ // you can't simply send that off to sanitize as that could result in it
+ // getting modified when the full name didn't. For example enum
+ // "StorageModes" has a value "retain". So the full name is
+ // "StorageModes_Retain", but if we sanitize "retain" it would become
+ // "RetainValue".
+ // So the right way to get the short name is to take the full enum name
+ // and then strip off the enum name (leaving the value name and anything
+ // done by sanitize).
+ const string& class_name = EnumName(descriptor->type());
+ const string& long_name_prefix = class_name + "_";
+ const string& long_name = EnumValueName(descriptor);
+ return StripPrefixString(long_name, long_name_prefix);
+}
+
+string UnCamelCaseEnumShortName(const string& name) {
+ string result;
+ for (int i = 0; i < name.size(); i++) {
+ char c = name[i];
+ if (i > 0 && ascii_isupper(c)) {
+ result += '_';
+ }
+ result += ascii_toupper(c);
+ }
+ return result;
+}
+
+string ExtensionMethodName(const FieldDescriptor* descriptor) {
+ const string& name = NameFromFieldDescriptor(descriptor);
+ const string& result = UnderscoresToCamelCase(name, false);
+ return SanitizeNameForObjC(result, "_Extension");
+}
+
+string FieldName(const FieldDescriptor* field) {
+ const string& name = NameFromFieldDescriptor(field);
+ string result = UnderscoresToCamelCase(name, false);
+ if (field->is_repeated() && !field->is_map()) {
+ // Add "Array" before do check for reserved worlds.
+ result += "Array";
+ } else {
+ // If it wasn't repeated, but ends in "Array", force on the _p suffix.
+ if (HasSuffixString(result, "Array")) {
+ result += "_p";
+ }
+ }
+ return SanitizeNameForObjC(result, "_p");
+}
+
+string FieldNameCapitalized(const FieldDescriptor* field) {
+ // Want the same suffix handling, so upcase the first letter of the other
+ // name.
+ string result = FieldName(field);
+ if (result.length() > 0) {
+ result[0] = ascii_toupper(result[0]);
+ }
+ return result;
+}
+
+string OneofEnumName(const OneofDescriptor* descriptor) {
+ const Descriptor* fieldDescriptor = descriptor->containing_type();
+ string name = ClassName(fieldDescriptor);
+ name += "_" + UnderscoresToCamelCase(descriptor->name(), true) + "_OneOfCase";
+ // No sanitize needed because the OS never has names that end in _OneOfCase.
+ return name;
+}
+
+string OneofName(const OneofDescriptor* descriptor) {
+ string name = UnderscoresToCamelCase(descriptor->name(), false);
+ // No sanitize needed because it gets OneOfCase added and that shouldn't
+ // ever conflict.
+ return name;
+}
+
+string OneofNameCapitalized(const OneofDescriptor* descriptor) {
+ // Use the common handling and then up-case the first letter.
+ string result = OneofName(descriptor);
+ if (result.length() > 0) {
+ result[0] = ascii_toupper(result[0]);
+ }
+ return result;
+}
+
+string UnCamelCaseFieldName(const string& name, const FieldDescriptor* field) {
+ string worker(name);
+ if (HasSuffixString(worker, "_p")) {
+ worker = StripSuffixString(worker, "_p");
+ }
+ if (field->is_repeated() && HasSuffixString(worker, "Array")) {
+ worker = StripSuffixString(worker, "Array");
+ }
+ if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ if (worker.length() > 0) {
+ if (ascii_islower(worker[0])) {
+ worker[0] = ascii_toupper(worker[0]);
+ }
+ }
+ return worker;
+ } else {
+ string result;
+ for (int i = 0; i < worker.size(); i++) {
+ char c = worker[i];
+ if (ascii_isupper(c)) {
+ if (i > 0) {
+ result += '_';
+ }
+ result += ascii_tolower(c);
+ } else {
+ result += c;
+ }
+ }
+ return result;
+ }
+}
+
+string GetCapitalizedType(const FieldDescriptor* field) {
+ switch (field->type()) {
+ case FieldDescriptor::TYPE_INT32:
+ return "Int32";
+ case FieldDescriptor::TYPE_UINT32:
+ return "UInt32";
+ case FieldDescriptor::TYPE_SINT32:
+ return "SInt32";
+ case FieldDescriptor::TYPE_FIXED32:
+ return "Fixed32";
+ case FieldDescriptor::TYPE_SFIXED32:
+ return "SFixed32";
+ case FieldDescriptor::TYPE_INT64:
+ return "Int64";
+ case FieldDescriptor::TYPE_UINT64:
+ return "UInt64";
+ case FieldDescriptor::TYPE_SINT64:
+ return "SInt64";
+ case FieldDescriptor::TYPE_FIXED64:
+ return "Fixed64";
+ case FieldDescriptor::TYPE_SFIXED64:
+ return "SFixed64";
+ case FieldDescriptor::TYPE_FLOAT:
+ return "Float";
+ case FieldDescriptor::TYPE_DOUBLE:
+ return "Double";
+ case FieldDescriptor::TYPE_BOOL:
+ return "Bool";
+ case FieldDescriptor::TYPE_STRING:
+ return "String";
+ case FieldDescriptor::TYPE_BYTES:
+ return "Bytes";
+ case FieldDescriptor::TYPE_ENUM:
+ return "Enum";
+ case FieldDescriptor::TYPE_GROUP:
+ return "Group";
+ case FieldDescriptor::TYPE_MESSAGE:
+ return "Message";
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+ObjectiveCType GetObjectiveCType(FieldDescriptor::Type field_type) {
+ switch (field_type) {
+ case FieldDescriptor::TYPE_INT32:
+ case FieldDescriptor::TYPE_SINT32:
+ case FieldDescriptor::TYPE_SFIXED32:
+ return OBJECTIVECTYPE_INT32;
+
+ case FieldDescriptor::TYPE_UINT32:
+ case FieldDescriptor::TYPE_FIXED32:
+ return OBJECTIVECTYPE_UINT32;
+
+ case FieldDescriptor::TYPE_INT64:
+ case FieldDescriptor::TYPE_SINT64:
+ case FieldDescriptor::TYPE_SFIXED64:
+ return OBJECTIVECTYPE_INT64;
+
+ case FieldDescriptor::TYPE_UINT64:
+ case FieldDescriptor::TYPE_FIXED64:
+ return OBJECTIVECTYPE_UINT64;
+
+ case FieldDescriptor::TYPE_FLOAT:
+ return OBJECTIVECTYPE_FLOAT;
+
+ case FieldDescriptor::TYPE_DOUBLE:
+ return OBJECTIVECTYPE_DOUBLE;
+
+ case FieldDescriptor::TYPE_BOOL:
+ return OBJECTIVECTYPE_BOOLEAN;
+
+ case FieldDescriptor::TYPE_STRING:
+ return OBJECTIVECTYPE_STRING;
+
+ case FieldDescriptor::TYPE_BYTES:
+ return OBJECTIVECTYPE_DATA;
+
+ case FieldDescriptor::TYPE_ENUM:
+ return OBJECTIVECTYPE_ENUM;
+
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_MESSAGE:
+ return OBJECTIVECTYPE_MESSAGE;
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return OBJECTIVECTYPE_INT32;
+}
+
+bool IsPrimitiveType(const FieldDescriptor* field) {
+ ObjectiveCType type = GetObjectiveCType(field);
+ switch (type) {
+ case OBJECTIVECTYPE_INT32:
+ case OBJECTIVECTYPE_UINT32:
+ case OBJECTIVECTYPE_INT64:
+ case OBJECTIVECTYPE_UINT64:
+ case OBJECTIVECTYPE_FLOAT:
+ case OBJECTIVECTYPE_DOUBLE:
+ case OBJECTIVECTYPE_BOOLEAN:
+ case OBJECTIVECTYPE_ENUM:
+ return true;
+ break;
+ default:
+ return false;
+ }
+}
+
+bool IsReferenceType(const FieldDescriptor* field) {
+ return !IsPrimitiveType(field);
+}
+
+static string HandleExtremeFloatingPoint(string val, bool add_float_suffix) {
+ if (val == "nan") {
+ return "NAN";
+ } else if (val == "inf") {
+ return "INFINITY";
+ } else if (val == "-inf") {
+ return "-INFINITY";
+ } else {
+ // float strings with ., e or E need to have f appended
+ if (add_float_suffix &&
+ (val.find(".") != string::npos || val.find("e") != string::npos ||
+ val.find("E") != string::npos)) {
+ val += "f";
+ }
+ return val;
+ }
+}
+
+string GPBGenericValueFieldName(const FieldDescriptor* field) {
+ // Returns the field within the GPBGenericValue union to use for the given
+ // field.
+ if (field->is_repeated()) {
+ return "valueMessage";
+ }
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return "valueInt32";
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return "valueUInt32";
+ case FieldDescriptor::CPPTYPE_INT64:
+ return "valueInt64";
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return "valueUInt64";
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return "valueFloat";
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return "valueDouble";
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return "valueBool";
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (field->type() == FieldDescriptor::TYPE_BYTES) {
+ return "valueData";
+ } else {
+ return "valueString";
+ }
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return "valueEnum";
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return "valueMessage";
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+
+string DefaultValue(const FieldDescriptor* field) {
+ // Repeated fields don't have defaults.
+ if (field->is_repeated()) {
+ return "nil";
+ }
+
+ // Switch on cpp_type since we need to know which default_value_* method
+ // of FieldDescriptor to call.
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ // gcc and llvm reject the decimal form of kint32min and kint64min.
+ if (field->default_value_int32() == INT_MIN) {
+ return "-0x80000000";
+ }
+ return SimpleItoa(field->default_value_int32());
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return SimpleItoa(field->default_value_uint32()) + "U";
+ case FieldDescriptor::CPPTYPE_INT64:
+ // gcc and llvm reject the decimal form of kint32min and kint64min.
+ if (field->default_value_int64() == LLONG_MIN) {
+ return "-0x8000000000000000LL";
+ }
+ return SimpleItoa(field->default_value_int64()) + "LL";
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return SimpleItoa(field->default_value_uint64()) + "ULL";
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return HandleExtremeFloatingPoint(
+ SimpleDtoa(field->default_value_double()), false);
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return HandleExtremeFloatingPoint(
+ SimpleFtoa(field->default_value_float()), true);
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field->default_value_bool() ? "YES" : "NO";
+ case FieldDescriptor::CPPTYPE_STRING: {
+ const bool has_default_value = field->has_default_value();
+ const string& default_string = field->default_value_string();
+ if (!has_default_value || default_string.length() == 0) {
+ // If the field is defined as being the empty string,
+ // then we will just assign to nil, as the empty string is the
+ // default for both strings and data.
+ return "nil";
+ }
+ if (field->type() == FieldDescriptor::TYPE_BYTES) {
+ // We want constant fields in our data structures so we can
+ // declare them as static. To achieve this we cheat and stuff
+ // a escaped c string (prefixed with a length) into the data
+ // field, and cast it to an (NSData*) so it will compile.
+ // The runtime library knows how to handle it.
+
+ // Must convert to a standard byte order for packing length into
+ // a cstring.
+ uint32 length = ghtonl(default_string.length());
+ string bytes((const char*)&length, sizeof(length));
+ bytes.append(default_string);
+ return "(NSData*)\"" + EscapeTrigraphs(CEscape(bytes)) + "\"";
+ } else {
+ return "@\"" + EscapeTrigraphs(CEscape(default_string)) + "\"";
+ }
+ }
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return EnumValueName(field->default_value_enum());
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return "nil";
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+bool HasNonZeroDefaultValue(const FieldDescriptor* field) {
+ // Repeated fields don't have defaults.
+ if (field->is_repeated()) {
+ return false;
+ }
+
+ // As much as checking field->has_default_value() seems useful, it isn't
+ // because of enums. proto2 syntax allows the first item in an enum (the
+ // default) to be non zero. So checking field->has_default_value() would
+ // result in missing this non zero default. See MessageWithOneBasedEnum in
+ // objectivec/Tests/unittest_objc.proto for a test Message to confirm this.
+
+ // Some proto file set the default to the zero value, so make sure the value
+ // isn't the zero case.
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return field->default_value_int32() != 0;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return field->default_value_uint32() != 0U;
+ case FieldDescriptor::CPPTYPE_INT64:
+ return field->default_value_int64() != 0LL;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return field->default_value_uint64() != 0ULL;
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return field->default_value_double() != 0.0;
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return field->default_value_float() != 0.0f;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field->default_value_bool();
+ case FieldDescriptor::CPPTYPE_STRING: {
+ const string& default_string = field->default_value_string();
+ return default_string.length() != 0;
+ }
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return field->default_value_enum()->number() != 0;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return false;
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return false;
+}
+
+string BuildFlagsString(const vector<string>& strings) {
+ if (strings.size() == 0) {
+ return "0";
+ }
+ string string;
+ for (size_t i = 0; i != strings.size(); ++i) {
+ if (i > 0) {
+ string.append(" | ");
+ }
+ string.append(strings[i]);
+ }
+ return string;
+}
+
+string BuildCommentsString(const SourceLocation& location) {
+ const string& comments = location.leading_comments.empty()
+ ? location.trailing_comments
+ : location.leading_comments;
+ vector<string> lines;
+ SplitStringAllowEmpty(comments, "\n", &lines);
+ while (!lines.empty() && lines.back().empty()) {
+ lines.pop_back();
+ }
+ string prefix("///");
+ string suffix("\n");
+ string final_comments;
+ for (int i = 0; i < lines.size(); i++) {
+ // HeaderDoc uses '\' and '@' for markers; escape them.
+ const string line = StringReplace(lines[i], "\\", "\\\\", true);
+ final_comments +=
+ prefix + StringReplace(line, "@", "\\@", true) + suffix;
+ }
+ return final_comments;
+}
+
+// Making these a generator option for folks that don't use CocoaPods, but do
+// want to put the library in a framework is an interesting question. The
+// problem is it means changing sources shipped with the library to actually
+// use a different value; so it isn't as simple as a option.
+const char* const ProtobufLibraryFrameworkName = "Protobuf";
+
+string ProtobufFrameworkImportSymbol(const string& framework_name) {
+ // GPB_USE_[framework_name]_FRAMEWORK_IMPORTS
+ string result = string("GPB_USE_");
+ result += ToUpper(framework_name);
+ result += "_FRAMEWORK_IMPORTS";
+ return result;
+}
+
+bool IsProtobufLibraryBundledProtoFile(const FileDescriptor* file) {
+ // We don't check the name prefix or proto package because some files
+ // (descriptor.proto), aren't shipped generated by the library, so this
+ // seems to be the safest way to only catch the ones shipped.
+ const string name = file->name();
+ if (name == "google/protobuf/any.proto" ||
+ name == "google/protobuf/api.proto" ||
+ name == "google/protobuf/duration.proto" ||
+ name == "google/protobuf/empty.proto" ||
+ name == "google/protobuf/field_mask.proto" ||
+ name == "google/protobuf/source_context.proto" ||
+ name == "google/protobuf/struct.proto" ||
+ name == "google/protobuf/timestamp.proto" ||
+ name == "google/protobuf/type.proto" ||
+ name == "google/protobuf/wrappers.proto") {
+ return true;
+ }
+ return false;
+}
+
+bool ReadLine(StringPiece* input, StringPiece* line) {
+ for (int len = 0; len < input->size(); ++len) {
+ if (ascii_isnewline((*input)[len])) {
+ *line = StringPiece(input->data(), len);
+ ++len; // advance over the newline
+ *input = StringPiece(input->data() + len, input->size() - len);
+ return true;
+ }
+ }
+ return false; // Ran out of input with no newline.
+}
+
+void RemoveComment(StringPiece* input) {
+ int offset = input->find('#');
+ if (offset != StringPiece::npos) {
+ input->remove_suffix(input->length() - offset);
+ }
+}
+
+namespace {
+
+class ExpectedPrefixesCollector : public LineConsumer {
+ public:
+ ExpectedPrefixesCollector(map<string, string>* inout_package_to_prefix_map)
+ : prefix_map_(inout_package_to_prefix_map) {}
+
+ virtual bool ConsumeLine(const StringPiece& line, string* out_error);
+
+ private:
+ map<string, string>* prefix_map_;
+};
+
+bool ExpectedPrefixesCollector::ConsumeLine(
+ const StringPiece& line, string* out_error) {
+ int offset = line.find('=');
+ if (offset == StringPiece::npos) {
+ *out_error =
+ string("Expected prefixes file line without equal sign: '") +
+ line.ToString() + "'.";
+ return false;
+ }
+ StringPiece package(line, 0, offset);
+ StringPiece prefix(line, offset + 1, line.length() - offset - 1);
+ StringPieceTrimWhitespace(&package);
+ StringPieceTrimWhitespace(&prefix);
+ // Don't really worry about error checking the package/prefix for
+ // being valid. Assume the file is validated when it is created/edited.
+ (*prefix_map_)[package.ToString()] = prefix.ToString();
+ return true;
+}
+
+bool LoadExpectedPackagePrefixes(const Options &generation_options,
+ map<string, string>* prefix_map,
+ string* out_error) {
+ if (generation_options.expected_prefixes_path.empty()) {
+ return true;
+ }
+
+ ExpectedPrefixesCollector collector(prefix_map);
+ return ParseSimpleFile(
+ generation_options.expected_prefixes_path, &collector, out_error);
+}
+
+} // namespace
+
+bool ValidateObjCClassPrefix(const FileDescriptor* file,
+ const Options& generation_options,
+ string* out_error) {
+ const string prefix = file->options().objc_class_prefix();
+ const string package = file->package();
+
+ // NOTE: src/google/protobuf/compiler/plugin.cc makes use of cerr for some
+ // error cases, so it seems to be ok to use as a back door for warnings.
+
+ // Load any expected package prefixes to validate against those.
+ map<string, string> expected_package_prefixes;
+ if (!LoadExpectedPackagePrefixes(generation_options,
+ &expected_package_prefixes,
+ out_error)) {
+ return false;
+ }
+
+ // Check: Error - See if there was an expected prefix for the package and
+ // report if it doesn't match (wrong or missing).
+ map<string, string>::iterator package_match =
+ expected_package_prefixes.find(package);
+ if (package_match != expected_package_prefixes.end()) {
+ // There was an entry, and...
+ if (package_match->second == prefix) {
+ // ...it matches. All good, out of here!
+ return true;
+ } else {
+ // ...it didn't match!
+ *out_error = "error: Expected 'option objc_class_prefix = \"" +
+ package_match->second + "\";' for package '" + package +
+ "' in '" + file->name() + "'";
+ if (prefix.length()) {
+ *out_error += "; but found '" + prefix + "' instead";
+ }
+ *out_error += ".";
+ return false;
+ }
+ }
+
+ // If there was no prefix option, we're done at this point.
+ if (prefix.length() == 0) {
+ // No prefix, nothing left to check.
+ return true;
+ }
+
+ // Check: Error - Make sure the prefix wasn't expected for a different
+ // package (overlap is allowed, but it has to be listed as an expected
+ // overlap).
+ for (map<string, string>::iterator i = expected_package_prefixes.begin();
+ i != expected_package_prefixes.end(); ++i) {
+ if (i->second == prefix) {
+ *out_error =
+ "error: Found 'option objc_class_prefix = \"" + prefix +
+ "\";' in '" + file->name() +
+ "'; that prefix is already used for 'package " + i->first +
+ ";'. It can only be reused by listing it in the expected file (" +
+ generation_options.expected_prefixes_path + ").";
+ return false; // Only report first usage of the prefix.
+ }
+ }
+
+ // Check: Warning - Make sure the prefix is is a reasonable value according
+ // to Apple's rules (the checks above implicitly whitelist anything that
+ // doesn't meet these rules).
+ if (!ascii_isupper(prefix[0])) {
+ cerr << endl
+ << "protoc:0: warning: Invalid 'option objc_class_prefix = \""
+ << prefix << "\";' in '" << file->name() << "';"
+ << " it should start with a capital letter." << endl;
+ cerr.flush();
+ }
+ if (prefix.length() < 3) {
+ // Apple reserves 2 character prefixes for themselves. They do use some
+ // 3 character prefixes, but they haven't updated the rules/docs.
+ cerr << endl
+ << "protoc:0: warning: Invalid 'option objc_class_prefix = \""
+ << prefix << "\";' in '" << file->name() << "';"
+ << " Apple recommends they should be at least 3 characters long."
+ << endl;
+ cerr.flush();
+ }
+
+ // Check: Warning - If the given package/prefix pair wasn't expected, issue a
+ // warning issue a warning suggesting it gets added to the file.
+ if (!expected_package_prefixes.empty()) {
+ cerr << endl
+ << "protoc:0: warning: Found unexpected 'option objc_class_prefix = \""
+ << prefix << "\";' in '" << file->name() << "';"
+ << " consider adding it to the expected prefixes file ("
+ << generation_options.expected_prefixes_path << ")." << endl;
+ cerr.flush();
+ }
+
+ return true;
+}
+
+TextFormatDecodeData::TextFormatDecodeData() { }
+
+TextFormatDecodeData::~TextFormatDecodeData() { }
+
+void TextFormatDecodeData::AddString(int32 key,
+ const string& input_for_decode,
+ const string& desired_output) {
+ for (vector<DataEntry>::const_iterator i = entries_.begin();
+ i != entries_.end(); ++i) {
+ if (i->first == key) {
+ cerr << "error: duplicate key (" << key
+ << ") making TextFormat data, input: \"" << input_for_decode
+ << "\", desired: \"" << desired_output << "\"." << endl;
+ cerr.flush();
+ abort();
+ }
+ }
+
+ const string& data = TextFormatDecodeData::DecodeDataForString(
+ input_for_decode, desired_output);
+ entries_.push_back(DataEntry(key, data));
+}
+
+string TextFormatDecodeData::Data() const {
+ ostringstream data_stringstream;
+
+ if (num_entries() > 0) {
+ io::OstreamOutputStream data_outputstream(&data_stringstream);
+ io::CodedOutputStream output_stream(&data_outputstream);
+
+ output_stream.WriteVarint32(num_entries());
+ for (vector<DataEntry>::const_iterator i = entries_.begin();
+ i != entries_.end(); ++i) {
+ output_stream.WriteVarint32(i->first);
+ output_stream.WriteString(i->second);
+ }
+ }
+
+ data_stringstream.flush();
+ return data_stringstream.str();
+}
+
+namespace {
+
+// Helper to build up the decode data for a string.
+class DecodeDataBuilder {
+ public:
+ DecodeDataBuilder() { Reset(); }
+
+ bool AddCharacter(const char desired, const char input);
+ void AddUnderscore() {
+ Push();
+ need_underscore_ = true;
+ }
+ string Finish() {
+ Push();
+ return decode_data_;
+ }
+
+ private:
+ static const uint8 kAddUnderscore = 0x80;
+
+ static const uint8 kOpAsIs = 0x00;
+ static const uint8 kOpFirstUpper = 0x40;
+ static const uint8 kOpFirstLower = 0x20;
+ static const uint8 kOpAllUpper = 0x60;
+
+ static const int kMaxSegmentLen = 0x1f;
+
+ void AddChar(const char desired) {
+ ++segment_len_;
+ is_all_upper_ &= ascii_isupper(desired);
+ }
+
+ void Push() {
+ uint8 op = (op_ | segment_len_);
+ if (need_underscore_) op |= kAddUnderscore;
+ if (op != 0) {
+ decode_data_ += (char)op;
+ }
+ Reset();
+ }
+
+ bool AddFirst(const char desired, const char input) {
+ if (desired == input) {
+ op_ = kOpAsIs;
+ } else if (desired == ascii_toupper(input)) {
+ op_ = kOpFirstUpper;
+ } else if (desired == ascii_tolower(input)) {
+ op_ = kOpFirstLower;
+ } else {
+ // Can't be transformed to match.
+ return false;
+ }
+ AddChar(desired);
+ return true;
+ }
+
+ void Reset() {
+ need_underscore_ = false;
+ op_ = 0;
+ segment_len_ = 0;
+ is_all_upper_ = true;
+ }
+
+ bool need_underscore_;
+ bool is_all_upper_;
+ uint8 op_;
+ int segment_len_;
+
+ string decode_data_;
+};
+
+bool DecodeDataBuilder::AddCharacter(const char desired, const char input) {
+ // If we've hit the max size, push to start a new segment.
+ if (segment_len_ == kMaxSegmentLen) {
+ Push();
+ }
+ if (segment_len_ == 0) {
+ return AddFirst(desired, input);
+ }
+
+ // Desired and input match...
+ if (desired == input) {
+ // If we aren't transforming it, or we're upper casing it and it is
+ // supposed to be uppercase; just add it to the segment.
+ if ((op_ != kOpAllUpper) || ascii_isupper(desired)) {
+ AddChar(desired);
+ return true;
+ }
+
+ // Add the current segment, and start the next one.
+ Push();
+ return AddFirst(desired, input);
+ }
+
+ // If we need to uppercase, and everything so far has been uppercase,
+ // promote op to AllUpper.
+ if ((desired == ascii_toupper(input)) && is_all_upper_) {
+ op_ = kOpAllUpper;
+ AddChar(desired);
+ return true;
+ }
+
+ // Give up, push and start a new segment.
+ Push();
+ return AddFirst(desired, input);
+}
+
+// If decode data can't be generated, a directive for the raw string
+// is used instead.
+string DirectDecodeString(const string& str) {
+ string result;
+ result += (char)'\0'; // Marker for full string.
+ result += str;
+ result += (char)'\0'; // End of string.
+ return result;
+}
+
+} // namespace
+
+// static
+string TextFormatDecodeData::DecodeDataForString(const string& input_for_decode,
+ const string& desired_output) {
+ if ((input_for_decode.size() == 0) || (desired_output.size() == 0)) {
+ cerr << "error: got empty string for making TextFormat data, input: \""
+ << input_for_decode << "\", desired: \"" << desired_output << "\"."
+ << endl;
+ cerr.flush();
+ abort();
+ }
+ if ((input_for_decode.find('\0') != string::npos) ||
+ (desired_output.find('\0') != string::npos)) {
+ cerr << "error: got a null char in a string for making TextFormat data,"
+ << " input: \"" << CEscape(input_for_decode) << "\", desired: \""
+ << CEscape(desired_output) << "\"." << endl;
+ cerr.flush();
+ abort();
+ }
+
+ DecodeDataBuilder builder;
+
+ // Walk the output building it from the input.
+ int x = 0;
+ for (int y = 0; y < desired_output.size(); y++) {
+ const char d = desired_output[y];
+ if (d == '_') {
+ builder.AddUnderscore();
+ continue;
+ }
+
+ if (x >= input_for_decode.size()) {
+ // Out of input, no way to encode it, just return a full decode.
+ return DirectDecodeString(desired_output);
+ }
+ if (builder.AddCharacter(d, input_for_decode[x])) {
+ ++x; // Consumed one input
+ } else {
+ // Couldn't transform for the next character, just return a full decode.
+ return DirectDecodeString(desired_output);
+ }
+ }
+
+ if (x != input_for_decode.size()) {
+ // Extra input (suffix from name sanitizing?), just return a full decode.
+ return DirectDecodeString(desired_output);
+ }
+
+ // Add the end marker.
+ return builder.Finish() + (char)'\0';
+}
+
+namespace {
+
+class Parser {
+ public:
+ Parser(LineConsumer* line_consumer)
+ : line_consumer_(line_consumer), line_(0) {}
+
+ // Parses a check of input, returning success/failure.
+ bool ParseChunk(StringPiece chunk);
+
+ // Should be called to finish parsing (after all input has been provided via
+ // ParseChunk()). Returns success/failure.
+ bool Finish();
+
+ int last_line() const { return line_; }
+ string error_str() const { return error_str_; }
+
+ private:
+ bool ParseLoop();
+
+ LineConsumer* line_consumer_;
+ int line_;
+ string error_str_;
+ StringPiece p_;
+ string leftover_;
+};
+
+bool Parser::ParseChunk(StringPiece chunk) {
+ if (!leftover_.empty()) {
+ chunk.AppendToString(&leftover_);
+ p_ = StringPiece(leftover_);
+ } else {
+ p_ = chunk;
+ }
+ bool result = ParseLoop();
+ if (p_.empty()) {
+ leftover_.clear();
+ } else {
+ leftover_ = p_.ToString();
+ }
+ return result;
+}
+
+bool Parser::Finish() {
+ if (leftover_.empty()) {
+ return true;
+ }
+ // Force a newline onto the end to finish parsing.
+ leftover_ += "\n";
+ p_ = StringPiece(leftover_);
+ if (!ParseLoop()) {
+ return false;
+ }
+ return p_.empty(); // Everything used?
+}
+
+bool Parser::ParseLoop() {
+ StringPiece line;
+ while (ReadLine(&p_, &line)) {
+ ++line_;
+ RemoveComment(&line);
+ StringPieceTrimWhitespace(&line);
+ if (line.size() == 0) {
+ continue; // Blank line.
+ }
+ if (!line_consumer_->ConsumeLine(line, &error_str_)) {
+ return false;
+ }
+ }
+ return true;
+}
+
+} // namespace
+
+LineConsumer::LineConsumer() {}
+
+LineConsumer::~LineConsumer() {}
+
+bool ParseSimpleFile(
+ const string& path, LineConsumer* line_consumer, string* out_error) {
+ int fd;
+ do {
+ fd = open(path.c_str(), O_RDONLY);
+ } while (fd < 0 && errno == EINTR);
+ if (fd < 0) {
+ *out_error =
+ string("error: Unable to open \"") + path + "\", " + strerror(errno);
+ return false;
+ }
+ io::FileInputStream file_stream(fd);
+ file_stream.SetCloseOnDelete(true);
+
+ Parser parser(line_consumer);
+ const void* buf;
+ int buf_len;
+ while (file_stream.Next(&buf, &buf_len)) {
+ if (buf_len == 0) {
+ continue;
+ }
+
+ if (!parser.ParseChunk(StringPiece(static_cast<const char*>(buf), buf_len))) {
+ *out_error =
+ string("error: ") + path +
+ " Line " + SimpleItoa(parser.last_line()) + ", " + parser.error_str();
+ return false;
+ }
+ }
+ return parser.Finish();
+}
+
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.h
new file mode 100644
index 0000000000..be20beeea5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers.h
@@ -0,0 +1,230 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_HELPERS_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_HELPERS_H__
+
+#include <string>
+#include <vector>
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+// Generator options (see objectivec_generator.cc for a description of each):
+struct Options {
+ Options();
+ string expected_prefixes_path;
+ string generate_for_named_framework;
+ string named_framework_to_proto_path_mappings_path;
+};
+
+// Escape C++ trigraphs by escaping question marks to "\?".
+string EscapeTrigraphs(const string& to_escape);
+
+// Strips ".proto" or ".protodevel" from the end of a filename.
+string StripProto(const string& filename);
+
+// Remove white space from either end of a StringPiece.
+void StringPieceTrimWhitespace(StringPiece* input);
+
+// Returns true if the name requires a ns_returns_not_retained attribute applied
+// to it.
+bool IsRetainedName(const string& name);
+
+// Returns true if the name starts with "init" and will need to have special
+// handling under ARC.
+bool IsInitName(const string& name);
+
+// Gets the path of the file we're going to generate (sans the .pb.h
+// extension). The path will be dependent on the objectivec package
+// declared in the proto package.
+string FilePath(const FileDescriptor* file);
+
+// Just like FilePath(), but without the directory part.
+string FilePathBasename(const FileDescriptor* file);
+
+// Gets the name of the root class we'll generate in the file. This class
+// is not meant for external consumption, but instead contains helpers that
+// the rest of the classes need
+string FileClassName(const FileDescriptor* file);
+
+// These return the fully-qualified class name corresponding to the given
+// descriptor.
+string ClassName(const Descriptor* descriptor);
+string EnumName(const EnumDescriptor* descriptor);
+
+// Returns the fully-qualified name of the enum value corresponding to the
+// the descriptor.
+string EnumValueName(const EnumValueDescriptor* descriptor);
+
+// Returns the name of the enum value corresponding to the descriptor.
+string EnumValueShortName(const EnumValueDescriptor* descriptor);
+
+// Reverse what an enum does.
+string UnCamelCaseEnumShortName(const string& name);
+
+// Returns the name to use for the extension (used as the method off the file's
+// Root class).
+string ExtensionMethodName(const FieldDescriptor* descriptor);
+
+// Returns the transformed field name.
+string FieldName(const FieldDescriptor* field);
+string FieldNameCapitalized(const FieldDescriptor* field);
+
+// Returns the transformed oneof name.
+string OneofEnumName(const OneofDescriptor* descriptor);
+string OneofName(const OneofDescriptor* descriptor);
+string OneofNameCapitalized(const OneofDescriptor* descriptor);
+
+inline bool HasFieldPresence(const FileDescriptor* file) {
+ return file->syntax() != FileDescriptor::SYNTAX_PROTO3;
+}
+
+inline bool HasPreservingUnknownEnumSemantics(const FileDescriptor* file) {
+ return file->syntax() == FileDescriptor::SYNTAX_PROTO3;
+}
+
+inline bool IsMapEntryMessage(const Descriptor* descriptor) {
+ return descriptor->options().map_entry();
+}
+
+// Reverse of the above.
+string UnCamelCaseFieldName(const string& name, const FieldDescriptor* field);
+
+enum ObjectiveCType {
+ OBJECTIVECTYPE_INT32,
+ OBJECTIVECTYPE_UINT32,
+ OBJECTIVECTYPE_INT64,
+ OBJECTIVECTYPE_UINT64,
+ OBJECTIVECTYPE_FLOAT,
+ OBJECTIVECTYPE_DOUBLE,
+ OBJECTIVECTYPE_BOOLEAN,
+ OBJECTIVECTYPE_STRING,
+ OBJECTIVECTYPE_DATA,
+ OBJECTIVECTYPE_ENUM,
+ OBJECTIVECTYPE_MESSAGE
+};
+
+template<class TDescriptor>
+string GetOptionalDeprecatedAttribute(const TDescriptor* descriptor, bool preSpace = true, bool postNewline = false) {
+ if (descriptor->options().deprecated()) {
+ string result = "DEPRECATED_ATTRIBUTE";
+ if (preSpace) {
+ result.insert(0, " ");
+ }
+ if (postNewline) {
+ result.append("\n");
+ }
+ return result;
+ } else {
+ return "";
+ }
+}
+
+string GetCapitalizedType(const FieldDescriptor* field);
+
+ObjectiveCType GetObjectiveCType(FieldDescriptor::Type field_type);
+
+inline ObjectiveCType GetObjectiveCType(const FieldDescriptor* field) {
+ return GetObjectiveCType(field->type());
+}
+
+bool IsPrimitiveType(const FieldDescriptor* field);
+bool IsReferenceType(const FieldDescriptor* field);
+
+string GPBGenericValueFieldName(const FieldDescriptor* field);
+string DefaultValue(const FieldDescriptor* field);
+bool HasNonZeroDefaultValue(const FieldDescriptor* field);
+
+string BuildFlagsString(const vector<string>& strings);
+
+// Builds a HeaderDoc style comment out of the comments in the .proto file.
+string BuildCommentsString(const SourceLocation& location);
+
+// The name the commonly used by the library when built as a framework.
+// This lines up to the name used in the CocoaPod.
+extern const char* const ProtobufLibraryFrameworkName;
+// Returns the CPP symbol name to use as the gate for framework style imports
+// for the given framework name to use.
+string ProtobufFrameworkImportSymbol(const string& framework_name);
+
+// Checks if the file is one of the proto's bundled with the library.
+bool IsProtobufLibraryBundledProtoFile(const FileDescriptor* file);
+
+// Checks the prefix for a given file and outputs any warnings needed, if
+// there are flat out errors, then out_error is filled in and the result is
+// false.
+bool ValidateObjCClassPrefix(const FileDescriptor* file,
+ const Options& generation_options,
+ string* out_error);
+
+// Generate decode data needed for ObjC's GPBDecodeTextFormatName() to transform
+// the input into the expected output.
+class LIBPROTOC_EXPORT TextFormatDecodeData {
+ public:
+ TextFormatDecodeData();
+ ~TextFormatDecodeData();
+
+ void AddString(int32 key, const string& input_for_decode,
+ const string& desired_output);
+ size_t num_entries() const { return entries_.size(); }
+ string Data() const;
+
+ static string DecodeDataForString(const string& input_for_decode,
+ const string& desired_output);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TextFormatDecodeData);
+
+ typedef std::pair<int32, string> DataEntry;
+ vector<DataEntry> entries_;
+};
+
+// Helper for parsing simple files.
+class LIBPROTOC_EXPORT LineConsumer {
+ public:
+ LineConsumer();
+ virtual ~LineConsumer();
+ virtual bool ConsumeLine(const StringPiece& line, string* out_error) = 0;
+};
+
+bool ParseSimpleFile(
+ const string& path, LineConsumer* line_consumer, string* out_error);
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_HELPERS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers_unittest.cc
new file mode 100644
index 0000000000..dc1cef556f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_helpers_unittest.cc
@@ -0,0 +1,257 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+namespace {
+
+TEST(ObjCHelper, TextFormatDecodeData_DecodeDataForString_RawStrings) {
+ string input_for_decode("abcdefghIJ");
+ string desired_output_for_decode;
+ string expected;
+ string result;
+
+ // Different data, can't transform.
+
+ desired_output_for_decode = "zbcdefghIJ";
+ expected = string("\0zbcdefghIJ\0", 12);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+
+ desired_output_for_decode = "abcdezghIJ";
+ expected = string("\0abcdezghIJ\0", 12);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+
+ // Shortened data, can't transform.
+
+ desired_output_for_decode = "abcdefghI";
+ expected = string("\0abcdefghI\0", 11);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+
+ // Extra data, can't transform.
+
+ desired_output_for_decode = "abcdefghIJz";
+ expected = string("\0abcdefghIJz\0", 13);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+}
+
+TEST(ObjCHelper, TextFormatDecodeData_DecodeDataForString_ByteCodes) {
+ string input_for_decode("abcdefghIJ");
+ string desired_output_for_decode;
+ string expected;
+ string result;
+
+ desired_output_for_decode = "abcdefghIJ";
+ expected = string("\x0A\x0", 2);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+
+ desired_output_for_decode = "_AbcdefghIJ";
+ expected = string("\xCA\x0", 2);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+
+ desired_output_for_decode = "ABCD__EfghI_j";
+ expected = string("\x64\x80\xC5\xA1\x0", 5);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+
+ // Long name so multiple decode ops are needed.
+
+ input_for_decode =
+ "longFieldNameIsLooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong1000";
+ desired_output_for_decode =
+ "long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_1000";
+ expected = string("\x04\xA5\xA4\xA2\xBF\x1F\x0E\x84\x0", 9);
+ result = TextFormatDecodeData::DecodeDataForString(input_for_decode,
+ desired_output_for_decode);
+ EXPECT_EQ(expected, result);
+}
+
+// Death tests do not work on Windows as of yet.
+#ifdef PROTOBUF_HAS_DEATH_TEST
+TEST(ObjCHelperDeathTest, TextFormatDecodeData_DecodeDataForString_Failures) {
+ // Empty inputs.
+
+ EXPECT_EXIT(TextFormatDecodeData::DecodeDataForString("", ""),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got empty string for making TextFormat data, input:");
+ EXPECT_EXIT(TextFormatDecodeData::DecodeDataForString("a", ""),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got empty string for making TextFormat data, input:");
+ EXPECT_EXIT(TextFormatDecodeData::DecodeDataForString("", "a"),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got empty string for making TextFormat data, input:");
+
+ // Null char in the string.
+
+ string str_with_null_char("ab\0c", 4);
+ EXPECT_EXIT(
+ TextFormatDecodeData::DecodeDataForString(str_with_null_char, "def"),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got a null char in a string for making TextFormat data, input:");
+ EXPECT_EXIT(
+ TextFormatDecodeData::DecodeDataForString("def", str_with_null_char),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got a null char in a string for making TextFormat data, input:");
+}
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST(ObjCHelper, TextFormatDecodeData_RawStrings) {
+ TextFormatDecodeData decode_data;
+
+ // Different data, can't transform.
+ decode_data.AddString(1, "abcdefghIJ", "zbcdefghIJ");
+ decode_data.AddString(3, "abcdefghIJ", "abcdezghIJ");
+ // Shortened data, can't transform.
+ decode_data.AddString(2, "abcdefghIJ", "abcdefghI");
+ // Extra data, can't transform.
+ decode_data.AddString(4, "abcdefghIJ", "abcdefghIJz");
+
+ EXPECT_EQ(4, decode_data.num_entries());
+
+ uint8 expected_data[] = {
+ 0x4,
+ 0x1, 0x0, 'z', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'I', 'J', 0x0,
+ 0x3, 0x0, 'a', 'b', 'c', 'd', 'e', 'z', 'g', 'h', 'I', 'J', 0x0,
+ 0x2, 0x0, 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'I', 0x0,
+ 0x4, 0x0, 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'I', 'J', 'z', 0x0,
+ };
+ string expected((const char*)expected_data, sizeof(expected_data));
+
+ EXPECT_EQ(expected, decode_data.Data());
+}
+
+TEST(ObjCHelper, TextFormatDecodeData_ByteCodes) {
+ TextFormatDecodeData decode_data;
+
+ decode_data.AddString(1, "abcdefghIJ", "abcdefghIJ");
+ decode_data.AddString(3, "abcdefghIJ", "_AbcdefghIJ");
+ decode_data.AddString(2, "abcdefghIJ", "Abcd_EfghIJ");
+ decode_data.AddString(4, "abcdefghIJ", "ABCD__EfghI_j");
+ decode_data.AddString(1000,
+ "longFieldNameIsLooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong1000",
+ "long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_1000");
+
+ EXPECT_EQ(5, decode_data.num_entries());
+
+ uint8 expected_data[] = {
+ 0x5,
+ // All as is (00 op)
+ 0x1, 0x0A, 0x0,
+ // Underscore, upper + 9 (10 op)
+ 0x3, 0xCA, 0x0,
+ // Upper + 3 (10 op), underscore, upper + 5 (10 op)
+ 0x2, 0x44, 0xC6, 0x0,
+ // All Upper for 4 (11 op), underscore, underscore, upper + 5 (10 op),
+ // underscore, lower + 0 (01 op)
+ 0x4, 0x64, 0x80, 0xC5, 0xA1, 0x0,
+ // 2 byte key: as is + 3 (00 op), underscore, lower + 4 (01 op),
+ // underscore, lower + 3 (01 op), underscore, lower + 1 (01 op),
+ // underscore, lower + 30 (01 op), as is + 30 (00 op), as is + 13 (00
+ // op),
+ // underscore, as is + 3 (00 op)
+ 0xE8, 0x07, 0x04, 0xA5, 0xA4, 0xA2, 0xBF, 0x1F, 0x0E, 0x84, 0x0,
+ };
+ string expected((const char*)expected_data, sizeof(expected_data));
+
+ EXPECT_EQ(expected, decode_data.Data());
+}
+
+
+// Death tests do not work on Windows as of yet.
+#ifdef PROTOBUF_HAS_DEATH_TEST
+TEST(ObjCHelperDeathTest, TextFormatDecodeData_Failures) {
+ TextFormatDecodeData decode_data;
+
+ // Empty inputs.
+
+ EXPECT_EXIT(decode_data.AddString(1, "", ""),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got empty string for making TextFormat data, input:");
+ EXPECT_EXIT(decode_data.AddString(1, "a", ""),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got empty string for making TextFormat data, input:");
+ EXPECT_EXIT(decode_data.AddString(1, "", "a"),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got empty string for making TextFormat data, input:");
+
+ // Null char in the string.
+
+ string str_with_null_char("ab\0c", 4);
+ EXPECT_EXIT(
+ decode_data.AddString(1, str_with_null_char, "def"),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got a null char in a string for making TextFormat data, input:");
+ EXPECT_EXIT(
+ decode_data.AddString(1, "def", str_with_null_char),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: got a null char in a string for making TextFormat data, input:");
+
+ // Duplicate keys
+
+ decode_data.AddString(1, "abcdefghIJ", "abcdefghIJ");
+ decode_data.AddString(3, "abcdefghIJ", "_AbcdefghIJ");
+ decode_data.AddString(2, "abcdefghIJ", "Abcd_EfghIJ");
+ EXPECT_EXIT(decode_data.AddString(2, "xyz", "x_yz"),
+ ::testing::KilledBySignal(SIGABRT),
+ "error: duplicate key \\(2\\) making TextFormat data, input:");
+}
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+// TODO(thomasvl): Should probably add some unittests for all the special cases
+// of name mangling (class name, field name, enum names). Rather than doing
+// this with an ObjC test in the objectivec directory, we should be able to
+// use src/google/protobuf/compiler/importer* (like other tests) to support a
+// virtual file system to feed in protos, once we have the Descriptor tree, the
+// tests could use the helper methods for generating names and validate the
+// right things are happening.
+
+} // namespace
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.cc
new file mode 100644
index 0000000000..ac5d8aea21
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.cc
@@ -0,0 +1,180 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2015 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/objectivec/objectivec_map_field.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+// MapFieldGenerator uses RepeatedFieldGenerator as the parent because it
+// provides a bunch of things (no has* methods, comments for contained type,
+// etc.).
+
+namespace {
+
+const char* MapEntryTypeName(const FieldDescriptor* descriptor, bool isKey) {
+ ObjectiveCType type = GetObjectiveCType(descriptor);
+ switch (type) {
+ case OBJECTIVECTYPE_INT32:
+ return "Int32";
+ case OBJECTIVECTYPE_UINT32:
+ return "UInt32";
+ case OBJECTIVECTYPE_INT64:
+ return "Int64";
+ case OBJECTIVECTYPE_UINT64:
+ return "UInt64";
+ case OBJECTIVECTYPE_FLOAT:
+ return "Float";
+ case OBJECTIVECTYPE_DOUBLE:
+ return "Double";
+ case OBJECTIVECTYPE_BOOLEAN:
+ return "Bool";
+ case OBJECTIVECTYPE_STRING:
+ return (isKey ? "String" : "Object");
+ case OBJECTIVECTYPE_DATA:
+ return "Object";
+ case OBJECTIVECTYPE_ENUM:
+ return "Enum";
+ case OBJECTIVECTYPE_MESSAGE:
+ return "Object";
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+} // namespace
+
+MapFieldGenerator::MapFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : RepeatedFieldGenerator(descriptor, options) {
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ value_field_generator_.reset(FieldGenerator::Make(value_descriptor, options));
+
+ // Pull over some variables_ from the value.
+ variables_["field_type"] = value_field_generator_->variable("field_type");
+ variables_["default"] = value_field_generator_->variable("default");
+ variables_["default_name"] = value_field_generator_->variable("default_name");
+
+ // Build custom field flags.
+ std::vector<string> field_flags;
+ field_flags.push_back("GPBFieldMapKey" + GetCapitalizedType(key_descriptor));
+ // Pull over the current text format custom name values that was calculated.
+ if (variables_["fieldflags"].find("GPBFieldTextFormatNameCustom") !=
+ string::npos) {
+ field_flags.push_back("GPBFieldTextFormatNameCustom");
+ }
+ // Pull over some info from the value's flags.
+ const string& value_field_flags =
+ value_field_generator_->variable("fieldflags");
+ if (value_field_flags.find("GPBFieldHasDefaultValue") != string::npos) {
+ field_flags.push_back("GPBFieldHasDefaultValue");
+ }
+ if (value_field_flags.find("GPBFieldHasEnumDescriptor") != string::npos) {
+ field_flags.push_back("GPBFieldHasEnumDescriptor");
+ }
+ variables_["fieldflags"] = BuildFlagsString(field_flags);
+
+ ObjectiveCType value_objc_type = GetObjectiveCType(value_descriptor);
+ const bool value_is_object_type =
+ ((value_objc_type == OBJECTIVECTYPE_STRING) ||
+ (value_objc_type == OBJECTIVECTYPE_DATA) ||
+ (value_objc_type == OBJECTIVECTYPE_MESSAGE));
+ if ((GetObjectiveCType(key_descriptor) == OBJECTIVECTYPE_STRING) &&
+ value_is_object_type) {
+ variables_["array_storage_type"] = "NSMutableDictionary";
+ variables_["array_property_type"] =
+ "NSMutableDictionary<NSString*, " +
+ value_field_generator_->variable("storage_type") + "*>";
+ } else {
+ string class_name("GPB");
+ class_name += MapEntryTypeName(key_descriptor, true);
+ class_name += MapEntryTypeName(value_descriptor, false);
+ class_name += "Dictionary";
+ variables_["array_storage_type"] = class_name;
+ if (value_is_object_type) {
+ variables_["array_property_type"] =
+ class_name + "<" +
+ value_field_generator_->variable("storage_type") + "*>";
+ }
+ }
+
+ variables_["dataTypeSpecific_name"] =
+ value_field_generator_->variable("dataTypeSpecific_name");
+ variables_["dataTypeSpecific_value"] =
+ value_field_generator_->variable("dataTypeSpecific_value");
+}
+
+MapFieldGenerator::~MapFieldGenerator() {}
+
+void MapFieldGenerator::FinishInitialization(void) {
+ RepeatedFieldGenerator::FinishInitialization();
+ // Use the array_comment support in RepeatedFieldGenerator to output what the
+ // values in the map are.
+ const FieldDescriptor* value_descriptor =
+ descriptor_->message_type()->FindFieldByName("value");
+ if (GetObjectiveCType(value_descriptor) == OBJECTIVECTYPE_ENUM) {
+ variables_["array_comment"] =
+ "// |" + variables_["name"] + "| values are |" + value_field_generator_->variable("storage_type") + "|\n";
+ }
+}
+
+void MapFieldGenerator::DetermineForwardDeclarations(
+ set<string>* fwd_decls) const {
+ RepeatedFieldGenerator::DetermineForwardDeclarations(fwd_decls);
+ const FieldDescriptor* value_descriptor =
+ descriptor_->message_type()->FindFieldByName("value");
+ if (GetObjectiveCType(value_descriptor) == OBJECTIVECTYPE_MESSAGE) {
+ const string& value_storage_type =
+ value_field_generator_->variable("storage_type");
+ fwd_decls->insert("@class " + value_storage_type);
+ }
+}
+
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.h
new file mode 100644
index 0000000000..bc68a6829f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_map_field.h
@@ -0,0 +1,67 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2015 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MAP_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MAP_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/objectivec/objectivec_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class MapFieldGenerator : public RepeatedFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ public:
+ virtual void FinishInitialization(void);
+
+ protected:
+ MapFieldGenerator(const FieldDescriptor* descriptor, const Options& options);
+ virtual ~MapFieldGenerator();
+
+ virtual void DetermineForwardDeclarations(set<string>* fwd_decls) const;
+
+ private:
+ scoped_ptr<FieldGenerator> value_field_generator_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MapFieldGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MAP_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.cc
new file mode 100644
index 0000000000..e1a7861971
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.cc
@@ -0,0 +1,616 @@
+// 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.
+
+#include <algorithm>
+#include <iostream>
+#include <sstream>
+
+#include <google/protobuf/stubs/hash.h>
+#include <google/protobuf/compiler/objectivec/objectivec_message.h>
+#include <google/protobuf/compiler/objectivec/objectivec_enum.h>
+#include <google/protobuf/compiler/objectivec/objectivec_extension.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/stubs/stl_util.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/descriptor.pb.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+struct FieldOrderingByNumber {
+ inline bool operator()(const FieldDescriptor* a,
+ const FieldDescriptor* b) const {
+ return a->number() < b->number();
+ }
+};
+
+int OrderGroupForFieldDescriptor(const FieldDescriptor* descriptor) {
+ // The first item in the object structure is our uint32[] for has bits.
+ // We then want to order things to make the instances as small as
+ // possible. So we follow the has bits with:
+ // 1. Anything always 4 bytes - float, *32, enums
+ // 2. Anything that is always a pointer (they will be 8 bytes on 64 bit
+ // builds and 4 bytes on 32bit builds.
+ // 3. Anything always 8 bytes - double, *64
+ //
+ // NOTE: Bools aren't listed, they were stored in the has bits.
+ //
+ // Why? Using 64bit builds as an example, this means worse case, we have
+ // enough bools that we overflow 1 byte from 4 byte alignment, so 3 bytes
+ // are wasted before the 4 byte values. Then if we have an odd number of
+ // those 4 byte values, the 8 byte values will be pushed down by 32bits to
+ // keep them aligned. But the structure will end 8 byte aligned, so no
+ // waste on the end. If you did the reverse order, you could waste 4 bytes
+ // before the first 8 byte value (after the has array), then a single
+ // bool on the end would need 7 bytes of padding to make the overall
+ // structure 8 byte aligned; so 11 bytes, wasted total.
+
+ // Anything repeated is a GPB*Array/NSArray, so pointer.
+ if (descriptor->is_repeated()) {
+ return 3;
+ }
+
+ switch (descriptor->type()) {
+ // All always 8 bytes.
+ case FieldDescriptor::TYPE_DOUBLE:
+ case FieldDescriptor::TYPE_INT64:
+ case FieldDescriptor::TYPE_SINT64:
+ case FieldDescriptor::TYPE_UINT64:
+ case FieldDescriptor::TYPE_SFIXED64:
+ case FieldDescriptor::TYPE_FIXED64:
+ return 4;
+
+ // Pointers (string and bytes are NSString and NSData); 8 or 4 bytes
+ // depending on the build architecture.
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_MESSAGE:
+ case FieldDescriptor::TYPE_STRING:
+ case FieldDescriptor::TYPE_BYTES:
+ return 3;
+
+ // All always 4 bytes (enums are int32s).
+ case FieldDescriptor::TYPE_FLOAT:
+ case FieldDescriptor::TYPE_INT32:
+ case FieldDescriptor::TYPE_SINT32:
+ case FieldDescriptor::TYPE_UINT32:
+ case FieldDescriptor::TYPE_SFIXED32:
+ case FieldDescriptor::TYPE_FIXED32:
+ case FieldDescriptor::TYPE_ENUM:
+ return 2;
+
+ // 0 bytes. Stored in the has bits.
+ case FieldDescriptor::TYPE_BOOL:
+ return 99; // End of the list (doesn't really matter).
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return 0;
+}
+
+struct FieldOrderingByStorageSize {
+ inline bool operator()(const FieldDescriptor* a,
+ const FieldDescriptor* b) const {
+ // Order by grouping.
+ const int order_group_a = OrderGroupForFieldDescriptor(a);
+ const int order_group_b = OrderGroupForFieldDescriptor(b);
+ if (order_group_a != order_group_b) {
+ return order_group_a < order_group_b;
+ }
+ // Within the group, order by field number (provides stable ordering).
+ return a->number() < b->number();
+ }
+};
+
+struct ExtensionRangeOrdering {
+ bool operator()(const Descriptor::ExtensionRange* a,
+ const Descriptor::ExtensionRange* b) const {
+ return a->start < b->start;
+ }
+};
+
+// Sort the fields of the given Descriptor by number into a new[]'d array
+// and return it.
+const FieldDescriptor** SortFieldsByNumber(const Descriptor* descriptor) {
+ const FieldDescriptor** fields =
+ new const FieldDescriptor* [descriptor->field_count()];
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ fields[i] = descriptor->field(i);
+ }
+ sort(fields, fields + descriptor->field_count(), FieldOrderingByNumber());
+ return fields;
+}
+
+// Sort the fields of the given Descriptor by storage size into a new[]'d
+// array and return it.
+const FieldDescriptor** SortFieldsByStorageSize(const Descriptor* descriptor) {
+ const FieldDescriptor** fields =
+ new const FieldDescriptor* [descriptor->field_count()];
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ fields[i] = descriptor->field(i);
+ }
+ sort(fields, fields + descriptor->field_count(),
+ FieldOrderingByStorageSize());
+ return fields;
+}
+} // namespace
+
+MessageGenerator::MessageGenerator(const string& root_classname,
+ const Descriptor* descriptor,
+ const Options& options)
+ : root_classname_(root_classname),
+ descriptor_(descriptor),
+ field_generators_(descriptor, options),
+ class_name_(ClassName(descriptor_)) {
+ for (int i = 0; i < descriptor_->extension_count(); i++) {
+ extension_generators_.push_back(
+ new ExtensionGenerator(class_name_, descriptor_->extension(i)));
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ OneofGenerator* generator = new OneofGenerator(descriptor_->oneof_decl(i));
+ oneof_generators_.push_back(generator);
+ }
+
+ for (int i = 0; i < descriptor_->enum_type_count(); i++) {
+ EnumGenerator* generator = new EnumGenerator(descriptor_->enum_type(i));
+ enum_generators_.push_back(generator);
+ }
+
+ for (int i = 0; i < descriptor_->nested_type_count(); i++) {
+ MessageGenerator* generator =
+ new MessageGenerator(root_classname_,
+ descriptor_->nested_type(i),
+ options);
+ nested_message_generators_.push_back(generator);
+ }
+}
+
+MessageGenerator::~MessageGenerator() {
+ STLDeleteContainerPointers(extension_generators_.begin(),
+ extension_generators_.end());
+ STLDeleteContainerPointers(enum_generators_.begin(), enum_generators_.end());
+ STLDeleteContainerPointers(nested_message_generators_.begin(),
+ nested_message_generators_.end());
+ STLDeleteContainerPointers(oneof_generators_.begin(),
+ oneof_generators_.end());
+}
+
+void MessageGenerator::GenerateStaticVariablesInitialization(
+ io::Printer* printer) {
+ for (vector<ExtensionGenerator*>::iterator iter =
+ extension_generators_.begin();
+ iter != extension_generators_.end(); ++iter) {
+ (*iter)->GenerateStaticVariablesInitialization(printer);
+ }
+
+ for (vector<MessageGenerator*>::iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ (*iter)->GenerateStaticVariablesInitialization(printer);
+ }
+}
+
+void MessageGenerator::DetermineForwardDeclarations(set<string>* fwd_decls) {
+ if (!IsMapEntryMessage(descriptor_)) {
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* fieldDescriptor = descriptor_->field(i);
+ field_generators_.get(fieldDescriptor)
+ .DetermineForwardDeclarations(fwd_decls);
+ }
+ }
+
+ for (vector<MessageGenerator*>::iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ (*iter)->DetermineForwardDeclarations(fwd_decls);
+ }
+}
+
+bool MessageGenerator::IncludesOneOfDefinition() const {
+ if (!oneof_generators_.empty()) {
+ return true;
+ }
+
+ for (vector<MessageGenerator*>::const_iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ if ((*iter)->IncludesOneOfDefinition()) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+void MessageGenerator::GenerateEnumHeader(io::Printer* printer) {
+ for (vector<EnumGenerator*>::iterator iter = enum_generators_.begin();
+ iter != enum_generators_.end(); ++iter) {
+ (*iter)->GenerateHeader(printer);
+ }
+
+ for (vector<MessageGenerator*>::iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ (*iter)->GenerateEnumHeader(printer);
+ }
+}
+
+void MessageGenerator::GenerateExtensionRegistrationSource(
+ io::Printer* printer) {
+ for (vector<ExtensionGenerator*>::iterator iter =
+ extension_generators_.begin();
+ iter != extension_generators_.end(); ++iter) {
+ (*iter)->GenerateRegistrationSource(printer);
+ }
+
+ for (vector<MessageGenerator*>::iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ (*iter)->GenerateExtensionRegistrationSource(printer);
+ }
+}
+
+void MessageGenerator::GenerateMessageHeader(io::Printer* printer) {
+ // This a a map entry message, just recurse and do nothing directly.
+ if (IsMapEntryMessage(descriptor_)) {
+ for (vector<MessageGenerator*>::iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ (*iter)->GenerateMessageHeader(printer);
+ }
+ return;
+ }
+
+ printer->Print(
+ "#pragma mark - $classname$\n"
+ "\n",
+ "classname", class_name_);
+
+ if (descriptor_->field_count()) {
+ scoped_array<const FieldDescriptor*> sorted_fields(
+ SortFieldsByNumber(descriptor_));
+
+ printer->Print("typedef GPB_ENUM($classname$_FieldNumber) {\n",
+ "classname", class_name_);
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(sorted_fields[i])
+ .GenerateFieldNumberConstant(printer);
+ }
+
+ printer->Outdent();
+ printer->Print("};\n\n");
+ }
+
+ for (vector<OneofGenerator*>::iterator iter = oneof_generators_.begin();
+ iter != oneof_generators_.end(); ++iter) {
+ (*iter)->GenerateCaseEnum(printer);
+ }
+
+ string message_comments;
+ SourceLocation location;
+ if (descriptor_->GetSourceLocation(&location)) {
+ message_comments = BuildCommentsString(location);
+ } else {
+ message_comments = "";
+ }
+
+ printer->Print(
+ "$comments$$deprecated_attribute$@interface $classname$ : GPBMessage\n\n",
+ "classname", class_name_,
+ "deprecated_attribute", GetOptionalDeprecatedAttribute(descriptor_, false, true),
+ "comments", message_comments);
+
+ vector<char> seen_oneofs(descriptor_->oneof_decl_count(), 0);
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (field->containing_oneof() != NULL) {
+ const int oneof_index = field->containing_oneof()->index();
+ if (!seen_oneofs[oneof_index]) {
+ seen_oneofs[oneof_index] = 1;
+ oneof_generators_[oneof_index]->GeneratePublicCasePropertyDeclaration(
+ printer);
+ }
+ }
+ field_generators_.get(field).GeneratePropertyDeclaration(printer);
+ }
+
+ printer->Print("@end\n\n");
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateCFunctionDeclarations(printer);
+ }
+
+ if (!oneof_generators_.empty()) {
+ for (vector<OneofGenerator*>::iterator iter = oneof_generators_.begin();
+ iter != oneof_generators_.end(); ++iter) {
+ (*iter)->GenerateClearFunctionDeclaration(printer);
+ }
+ printer->Print("\n");
+ }
+
+ if (descriptor_->extension_count() > 0) {
+ printer->Print("@interface $classname$ (DynamicMethods)\n\n",
+ "classname", class_name_);
+ for (vector<ExtensionGenerator*>::iterator iter =
+ extension_generators_.begin();
+ iter != extension_generators_.end(); ++iter) {
+ (*iter)->GenerateMembersHeader(printer);
+ }
+ printer->Print("@end\n\n");
+ }
+
+ for (vector<MessageGenerator*>::iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ (*iter)->GenerateMessageHeader(printer);
+ }
+}
+
+void MessageGenerator::GenerateSource(io::Printer* printer) {
+ if (!IsMapEntryMessage(descriptor_)) {
+ printer->Print(
+ "#pragma mark - $classname$\n"
+ "\n",
+ "classname", class_name_);
+
+ printer->Print("@implementation $classname$\n\n",
+ "classname", class_name_);
+
+ for (vector<OneofGenerator*>::iterator iter = oneof_generators_.begin();
+ iter != oneof_generators_.end(); ++iter) {
+ (*iter)->GeneratePropertyImplementation(printer);
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GeneratePropertyImplementation(printer);
+ }
+
+ scoped_array<const FieldDescriptor*> sorted_fields(
+ SortFieldsByNumber(descriptor_));
+ scoped_array<const FieldDescriptor*> size_order_fields(
+ SortFieldsByStorageSize(descriptor_));
+
+ vector<const Descriptor::ExtensionRange*> sorted_extensions;
+ for (int i = 0; i < descriptor_->extension_range_count(); ++i) {
+ sorted_extensions.push_back(descriptor_->extension_range(i));
+ }
+
+ sort(sorted_extensions.begin(), sorted_extensions.end(),
+ ExtensionRangeOrdering());
+
+ // Assign has bits:
+ // 1. FieldGeneratorMap::CalculateHasBits() loops through the fields seeing
+ // who needs has bits and assigning them.
+ // 2. FieldGenerator::SetOneofIndexBase() overrides has_bit with a negative
+ // index that groups all the elements in the oneof.
+ size_t num_has_bits = field_generators_.CalculateHasBits();
+ size_t sizeof_has_storage = (num_has_bits + 31) / 32;
+ if (sizeof_has_storage == 0) {
+ // In the case where no field needs has bits, don't let the _has_storage_
+ // end up as zero length (zero length arrays are sort of a grey area
+ // since it has to be at the start of the struct). This also ensures a
+ // field with only oneofs keeps the required negative indices they need.
+ sizeof_has_storage = 1;
+ }
+ // Tell all the fields the oneof base.
+ for (vector<OneofGenerator*>::iterator iter = oneof_generators_.begin();
+ iter != oneof_generators_.end(); ++iter) {
+ (*iter)->SetOneofIndexBase(sizeof_has_storage);
+ }
+ field_generators_.SetOneofIndexBase(sizeof_has_storage);
+ // sizeof_has_storage needs enough bits for the single fields that aren't in
+ // any oneof, and then one int32 for each oneof (to store the field number).
+ sizeof_has_storage += descriptor_->oneof_decl_count();
+
+ printer->Print(
+ "\n"
+ "typedef struct $classname$__storage_ {\n"
+ " uint32_t _has_storage_[$sizeof_has_storage$];\n",
+ "classname", class_name_,
+ "sizeof_has_storage", SimpleItoa(sizeof_has_storage));
+ printer->Indent();
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(size_order_fields[i])
+ .GenerateFieldStorageDeclaration(printer);
+ }
+ printer->Outdent();
+
+ printer->Print("} $classname$__storage_;\n\n", "classname", class_name_);
+
+
+ printer->Print(
+ "// This method is threadsafe because it is initially called\n"
+ "// in +initialize for each subclass.\n"
+ "+ (GPBDescriptor *)descriptor {\n"
+ " static GPBDescriptor *descriptor = nil;\n"
+ " if (!descriptor) {\n");
+
+ TextFormatDecodeData text_format_decode_data;
+ bool has_fields = descriptor_->field_count() > 0;
+ bool need_defaults = field_generators_.DoesAnyFieldHaveNonZeroDefault();
+ string field_description_type;
+ if (need_defaults) {
+ field_description_type = "GPBMessageFieldDescriptionWithDefault";
+ } else {
+ field_description_type = "GPBMessageFieldDescription";
+ }
+ if (has_fields) {
+ printer->Print(
+ " static $field_description_type$ fields[] = {\n",
+ "field_description_type", field_description_type);
+ printer->Indent();
+ printer->Indent();
+ printer->Indent();
+ for (int i = 0; i < descriptor_->field_count(); ++i) {
+ const FieldGenerator& field_generator =
+ field_generators_.get(sorted_fields[i]);
+ field_generator.GenerateFieldDescription(printer, need_defaults);
+ if (field_generator.needs_textformat_name_support()) {
+ text_format_decode_data.AddString(sorted_fields[i]->number(),
+ field_generator.generated_objc_name(),
+ field_generator.raw_field_name());
+ }
+ }
+ printer->Outdent();
+ printer->Outdent();
+ printer->Outdent();
+ printer->Print(
+ " };\n");
+ }
+
+ map<string, string> vars;
+ vars["classname"] = class_name_;
+ vars["rootclassname"] = root_classname_;
+ vars["fields"] = has_fields ? "fields" : "NULL";
+ if (has_fields) {
+ vars["fields_count"] =
+ "(uint32_t)(sizeof(fields) / sizeof(" + field_description_type + "))";
+ } else {
+ vars["fields_count"] = "0";
+ }
+
+ std::vector<string> init_flags;
+ if (need_defaults) {
+ init_flags.push_back("GPBDescriptorInitializationFlag_FieldsWithDefault");
+ }
+ if (descriptor_->options().message_set_wire_format()) {
+ init_flags.push_back("GPBDescriptorInitializationFlag_WireFormat");
+ }
+ vars["init_flags"] = BuildFlagsString(init_flags);
+
+ printer->Print(
+ vars,
+ " GPBDescriptor *localDescriptor =\n"
+ " [GPBDescriptor allocDescriptorForClass:[$classname$ class]\n"
+ " rootClass:[$rootclassname$ class]\n"
+ " file:$rootclassname$_FileDescriptor()\n"
+ " fields:$fields$\n"
+ " fieldCount:$fields_count$\n"
+ " storageSize:sizeof($classname$__storage_)\n"
+ " flags:$init_flags$];\n");
+ if (oneof_generators_.size() != 0) {
+ printer->Print(
+ " static const char *oneofs[] = {\n");
+ for (vector<OneofGenerator*>::iterator iter = oneof_generators_.begin();
+ iter != oneof_generators_.end(); ++iter) {
+ printer->Print(
+ " \"$name$\",\n",
+ "name", (*iter)->DescriptorName());
+ }
+ printer->Print(
+ " };\n"
+ " [localDescriptor setupOneofs:oneofs\n"
+ " count:(uint32_t)(sizeof(oneofs) / sizeof(char*))\n"
+ " firstHasIndex:$first_has_index$];\n",
+ "first_has_index", oneof_generators_[0]->HasIndexAsString());
+ }
+ if (text_format_decode_data.num_entries() != 0) {
+ const string text_format_data_str(text_format_decode_data.Data());
+ printer->Print(
+ "#if !GPBOBJC_SKIP_MESSAGE_TEXTFORMAT_EXTRAS\n"
+ " static const char *extraTextFormatInfo =");
+ static const int kBytesPerLine = 40; // allow for escaping
+ for (int i = 0; i < text_format_data_str.size(); i += kBytesPerLine) {
+ printer->Print(
+ "\n \"$data$\"",
+ "data", EscapeTrigraphs(
+ CEscape(text_format_data_str.substr(i, kBytesPerLine))));
+ }
+ printer->Print(
+ ";\n"
+ " [localDescriptor setupExtraTextInfo:extraTextFormatInfo];\n"
+ "#endif // !GPBOBJC_SKIP_MESSAGE_TEXTFORMAT_EXTRAS\n");
+ }
+ if (sorted_extensions.size() != 0) {
+ printer->Print(
+ " static const GPBExtensionRange ranges[] = {\n");
+ for (int i = 0; i < sorted_extensions.size(); i++) {
+ printer->Print(" { .start = $start$, .end = $end$ },\n",
+ "start", SimpleItoa(sorted_extensions[i]->start),
+ "end", SimpleItoa(sorted_extensions[i]->end));
+ }
+ printer->Print(
+ " };\n"
+ " [localDescriptor setupExtensionRanges:ranges\n"
+ " count:(uint32_t)(sizeof(ranges) / sizeof(GPBExtensionRange))];\n");
+ }
+ printer->Print(
+ " NSAssert(descriptor == nil, @\"Startup recursed!\");\n"
+ " descriptor = localDescriptor;\n"
+ " }\n"
+ " return descriptor;\n"
+ "}\n\n"
+ "@end\n\n");
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ field_generators_.get(descriptor_->field(i))
+ .GenerateCFunctionImplementations(printer);
+ }
+
+ for (vector<OneofGenerator*>::iterator iter = oneof_generators_.begin();
+ iter != oneof_generators_.end(); ++iter) {
+ (*iter)->GenerateClearFunctionImplementation(printer);
+ }
+ }
+
+ for (vector<EnumGenerator*>::iterator iter = enum_generators_.begin();
+ iter != enum_generators_.end(); ++iter) {
+ (*iter)->GenerateSource(printer);
+ }
+
+ for (vector<MessageGenerator*>::iterator iter =
+ nested_message_generators_.begin();
+ iter != nested_message_generators_.end(); ++iter) {
+ (*iter)->GenerateSource(printer);
+ }
+}
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.h
new file mode 100644
index 0000000000..910535ace3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message.h
@@ -0,0 +1,99 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MESSAGE_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MESSAGE_H__
+
+#include <string>
+#include <set>
+#include <vector>
+#include <google/protobuf/compiler/objectivec/objectivec_field.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/compiler/objectivec/objectivec_oneof.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+namespace io {
+class Printer; // printer.h
+} // namespace io
+
+namespace compiler {
+namespace objectivec {
+
+class ExtensionGenerator;
+class EnumGenerator;
+
+class MessageGenerator {
+ public:
+ MessageGenerator(const string& root_classname,
+ const Descriptor* descriptor,
+ const Options& options);
+ ~MessageGenerator();
+
+ void GenerateStaticVariablesInitialization(io::Printer* printer);
+ void GenerateEnumHeader(io::Printer* printer);
+ void GenerateMessageHeader(io::Printer* printer);
+ void GenerateSource(io::Printer* printer);
+ void GenerateExtensionRegistrationSource(io::Printer* printer);
+ void DetermineForwardDeclarations(set<string>* fwd_decls);
+
+ // Checks if the message or a nested message includes a oneof definition.
+ bool IncludesOneOfDefinition() const;
+
+ private:
+ void GenerateParseFromMethodsHeader(io::Printer* printer);
+
+ void GenerateSerializeOneFieldSource(io::Printer* printer,
+ const FieldDescriptor* field);
+ void GenerateSerializeOneExtensionRangeSource(
+ io::Printer* printer, const Descriptor::ExtensionRange* range);
+
+ void GenerateMessageDescriptionSource(io::Printer* printer);
+ void GenerateDescriptionOneFieldSource(io::Printer* printer,
+ const FieldDescriptor* field);
+
+ const string root_classname_;
+ const Descriptor* descriptor_;
+ FieldGeneratorMap field_generators_;
+ const string class_name_;
+ vector<ExtensionGenerator*> extension_generators_;
+ vector<EnumGenerator*> enum_generators_;
+ vector<MessageGenerator*> nested_message_generators_;
+ vector<OneofGenerator*> oneof_generators_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageGenerator);
+};
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.cc
new file mode 100644
index 0000000000..d6ccd6d1e7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.cc
@@ -0,0 +1,108 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/objectivec/objectivec_message_field.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+namespace {
+
+void SetMessageVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables) {
+ const string& message_type = ClassName(descriptor->message_type());
+ (*variables)["type"] = message_type;
+ (*variables)["containing_class"] = ClassName(descriptor->containing_type());
+ (*variables)["storage_type"] = message_type;
+ (*variables)["group_or_message"] =
+ (descriptor->type() == FieldDescriptor::TYPE_GROUP) ? "Group" : "Message";
+
+ (*variables)["dataTypeSpecific_value"] = "GPBStringifySymbol(" + message_type + ")";
+}
+
+} // namespace
+
+MessageFieldGenerator::MessageFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options)
+ : ObjCObjFieldGenerator(descriptor, options) {
+ SetMessageVariables(descriptor, &variables_);
+}
+
+MessageFieldGenerator::~MessageFieldGenerator() {}
+
+void MessageFieldGenerator::DetermineForwardDeclarations(
+ set<string>* fwd_decls) const {
+ ObjCObjFieldGenerator::DetermineForwardDeclarations(fwd_decls);
+ // Class name is already in "storage_type".
+ fwd_decls->insert("@class " + variable("storage_type"));
+}
+
+bool MessageFieldGenerator::WantsHasProperty(void) const {
+ if (descriptor_->containing_oneof() != NULL) {
+ // If in a oneof, it uses the oneofcase instead of a has bit.
+ return false;
+ }
+ // In both proto2 & proto3, message fields have a has* property to tell
+ // when it is a non default value.
+ return true;
+}
+
+RepeatedMessageFieldGenerator::RepeatedMessageFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : RepeatedFieldGenerator(descriptor, options) {
+ SetMessageVariables(descriptor, &variables_);
+ variables_["array_storage_type"] = "NSMutableArray";
+ variables_["array_property_type"] =
+ "NSMutableArray<" + variables_["storage_type"] + "*>";
+}
+
+RepeatedMessageFieldGenerator::~RepeatedMessageFieldGenerator() {}
+
+void RepeatedMessageFieldGenerator::DetermineForwardDeclarations(
+ set<string>* fwd_decls) const {
+ RepeatedFieldGenerator::DetermineForwardDeclarations(fwd_decls);
+ // Class name is already in "storage_type".
+ fwd_decls->insert("@class " + variable("storage_type"));
+}
+
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.h
new file mode 100644
index 0000000000..d2dba15334
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_message_field.h
@@ -0,0 +1,81 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MESSAGE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MESSAGE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/objectivec/objectivec_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class MessageFieldGenerator : public ObjCObjFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ protected:
+ MessageFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual ~MessageFieldGenerator();
+ virtual bool WantsHasProperty(void) const;
+
+ public:
+ virtual void DetermineForwardDeclarations(set<string>* fwd_decls) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageFieldGenerator);
+};
+
+class RepeatedMessageFieldGenerator : public RepeatedFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ protected:
+ RepeatedMessageFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual ~RepeatedMessageFieldGenerator();
+
+ public:
+ virtual void DetermineForwardDeclarations(set<string>* fwd_decls) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedMessageFieldGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_MESSAGE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.cc
new file mode 100644
index 0000000000..3dda903bbf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.cc
@@ -0,0 +1,138 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/objectivec/objectivec_oneof.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+OneofGenerator::OneofGenerator(const OneofDescriptor* descriptor)
+ : descriptor_(descriptor) {
+ variables_["enum_name"] = OneofEnumName(descriptor_);
+ variables_["name"] = OneofName(descriptor_);
+ variables_["capitalized_name"] = OneofNameCapitalized(descriptor_);
+ variables_["raw_index"] = SimpleItoa(descriptor_->index());
+ const Descriptor* msg_descriptor = descriptor_->containing_type();
+ variables_["owning_message_class"] = ClassName(msg_descriptor);
+
+ string comments;
+ SourceLocation location;
+ if (descriptor_->GetSourceLocation(&location)) {
+ comments = BuildCommentsString(location);
+ } else {
+ comments = "";
+ }
+ variables_["comments"] = comments;
+}
+
+OneofGenerator::~OneofGenerator() {}
+
+void OneofGenerator::SetOneofIndexBase(int index_base) {
+ int index = descriptor_->index() + index_base;
+ // Flip the sign to mark it as a oneof.
+ variables_["index"] = SimpleItoa(-index);
+}
+
+void OneofGenerator::GenerateCaseEnum(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "typedef GPB_ENUM($enum_name$) {\n");
+ printer->Indent();
+ printer->Print(
+ variables_,
+ "$enum_name$_GPBUnsetOneOfCase = 0,\n");
+ string enum_name = variables_["enum_name"];
+ for (int j = 0; j < descriptor_->field_count(); j++) {
+ const FieldDescriptor* field = descriptor_->field(j);
+ string field_name = FieldNameCapitalized(field);
+ printer->Print(
+ "$enum_name$_$field_name$ = $field_number$,\n",
+ "enum_name", enum_name,
+ "field_name", field_name,
+ "field_number", SimpleItoa(field->number()));
+ }
+ printer->Outdent();
+ printer->Print(
+ "};\n"
+ "\n");
+}
+
+void OneofGenerator::GeneratePublicCasePropertyDeclaration(
+ io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "$comments$"
+ "@property(nonatomic, readonly) $enum_name$ $name$OneOfCase;\n"
+ "\n");
+}
+
+void OneofGenerator::GenerateClearFunctionDeclaration(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "/// Clears whatever value was set for the oneof '$name$'.\n"
+ "void $owning_message_class$_Clear$capitalized_name$OneOfCase($owning_message_class$ *message);\n");
+}
+
+void OneofGenerator::GeneratePropertyImplementation(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "@dynamic $name$OneOfCase;\n");
+}
+
+void OneofGenerator::GenerateClearFunctionImplementation(io::Printer* printer) {
+ printer->Print(
+ variables_,
+ "void $owning_message_class$_Clear$capitalized_name$OneOfCase($owning_message_class$ *message) {\n"
+ " GPBDescriptor *descriptor = [message descriptor];\n"
+ " GPBOneofDescriptor *oneof = [descriptor.oneofs objectAtIndex:$raw_index$];\n"
+ " GPBMaybeClearOneof(message, oneof, $index$, 0);\n"
+ "}\n");
+}
+
+string OneofGenerator::DescriptorName(void) const {
+ return variables_.find("name")->second;
+}
+
+string OneofGenerator::HasIndexAsString(void) const {
+ return variables_.find("index")->second;
+}
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.h
new file mode 100644
index 0000000000..3d9df4dbf4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_oneof.h
@@ -0,0 +1,79 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ONEOF_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ONEOF_H__
+
+#include <string>
+#include <set>
+#include <vector>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+class Printer; // printer.h
+}
+}
+
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class OneofGenerator {
+ public:
+ explicit OneofGenerator(const OneofDescriptor* descriptor);
+ ~OneofGenerator();
+
+ void SetOneofIndexBase(int index_base);
+
+ void GenerateCaseEnum(io::Printer* printer);
+
+ void GeneratePublicCasePropertyDeclaration(io::Printer* printer);
+ void GenerateClearFunctionDeclaration(io::Printer* printer);
+
+ void GeneratePropertyImplementation(io::Printer* printer);
+ void GenerateClearFunctionImplementation(io::Printer* printer);
+
+ string DescriptorName(void) const;
+ string HasIndexAsString(void) const;
+
+ private:
+ const OneofDescriptor* descriptor_;
+ map<string, string> variables_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(OneofGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_ONEOF_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.cc
new file mode 100644
index 0000000000..d49350f4b7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.cc
@@ -0,0 +1,192 @@
+// 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.
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/compiler/objectivec/objectivec_primitive_field.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+using internal::WireFormat;
+using internal::WireFormatLite;
+
+namespace {
+
+const char* PrimitiveTypeName(const FieldDescriptor* descriptor) {
+ ObjectiveCType type = GetObjectiveCType(descriptor);
+ switch (type) {
+ case OBJECTIVECTYPE_INT32:
+ return "int32_t";
+ case OBJECTIVECTYPE_UINT32:
+ return "uint32_t";
+ case OBJECTIVECTYPE_INT64:
+ return "int64_t";
+ case OBJECTIVECTYPE_UINT64:
+ return "uint64_t";
+ case OBJECTIVECTYPE_FLOAT:
+ return "float";
+ case OBJECTIVECTYPE_DOUBLE:
+ return "double";
+ case OBJECTIVECTYPE_BOOLEAN:
+ return "BOOL";
+ case OBJECTIVECTYPE_STRING:
+ return "NSString";
+ case OBJECTIVECTYPE_DATA:
+ return "NSData";
+ case OBJECTIVECTYPE_ENUM:
+ return "int32_t";
+ case OBJECTIVECTYPE_MESSAGE:
+ return NULL; // Messages go through objectivec_message_field.cc|h.
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+const char* PrimitiveArrayTypeName(const FieldDescriptor* descriptor) {
+ ObjectiveCType type = GetObjectiveCType(descriptor);
+ switch (type) {
+ case OBJECTIVECTYPE_INT32:
+ return "Int32";
+ case OBJECTIVECTYPE_UINT32:
+ return "UInt32";
+ case OBJECTIVECTYPE_INT64:
+ return "Int64";
+ case OBJECTIVECTYPE_UINT64:
+ return "UInt64";
+ case OBJECTIVECTYPE_FLOAT:
+ return "Float";
+ case OBJECTIVECTYPE_DOUBLE:
+ return "Double";
+ case OBJECTIVECTYPE_BOOLEAN:
+ return "Bool";
+ case OBJECTIVECTYPE_STRING:
+ return ""; // Want NSArray
+ case OBJECTIVECTYPE_DATA:
+ return ""; // Want NSArray
+ case OBJECTIVECTYPE_ENUM:
+ return "Enum";
+ case OBJECTIVECTYPE_MESSAGE:
+ // Want NSArray (but goes through objectivec_message_field.cc|h).
+ return "";
+ }
+
+ // Some compilers report reaching end of function even though all cases of
+ // the enum are handed in the switch.
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+}
+
+void SetPrimitiveVariables(const FieldDescriptor* descriptor,
+ map<string, string>* variables) {
+ std::string primitive_name = PrimitiveTypeName(descriptor);
+ (*variables)["type"] = primitive_name;
+ (*variables)["storage_type"] = primitive_name;
+}
+
+} // namespace
+
+PrimitiveFieldGenerator::PrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : SingleFieldGenerator(descriptor, options) {
+ SetPrimitiveVariables(descriptor, &variables_);
+}
+
+PrimitiveFieldGenerator::~PrimitiveFieldGenerator() {}
+
+void PrimitiveFieldGenerator::GenerateFieldStorageDeclaration(
+ io::Printer* printer) const {
+ if (GetObjectiveCType(descriptor_) == OBJECTIVECTYPE_BOOLEAN) {
+ // Nothing, BOOLs are stored in the has bits.
+ } else {
+ SingleFieldGenerator::GenerateFieldStorageDeclaration(printer);
+ }
+}
+
+int PrimitiveFieldGenerator::ExtraRuntimeHasBitsNeeded(void) const {
+ if (GetObjectiveCType(descriptor_) == OBJECTIVECTYPE_BOOLEAN) {
+ // Reserve a bit for the storage of the boolean.
+ return 1;
+ }
+ return 0;
+}
+
+void PrimitiveFieldGenerator::SetExtraRuntimeHasBitsBase(int has_base) {
+ if (GetObjectiveCType(descriptor_) == OBJECTIVECTYPE_BOOLEAN) {
+ // Set into the offset the has bit to use for the actual value.
+ variables_["storage_offset_value"] = SimpleItoa(has_base);
+ variables_["storage_offset_comment"] =
+ " // Stored in _has_storage_ to save space.";
+ }
+}
+
+PrimitiveObjFieldGenerator::PrimitiveObjFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : ObjCObjFieldGenerator(descriptor, options) {
+ SetPrimitiveVariables(descriptor, &variables_);
+ variables_["property_storage_attribute"] = "copy";
+}
+
+PrimitiveObjFieldGenerator::~PrimitiveObjFieldGenerator() {}
+
+RepeatedPrimitiveFieldGenerator::RepeatedPrimitiveFieldGenerator(
+ const FieldDescriptor* descriptor, const Options& options)
+ : RepeatedFieldGenerator(descriptor, options) {
+ SetPrimitiveVariables(descriptor, &variables_);
+
+ string base_name = PrimitiveArrayTypeName(descriptor);
+ if (base_name.length()) {
+ variables_["array_storage_type"] = "GPB" + base_name + "Array";
+ } else {
+ variables_["array_storage_type"] = "NSMutableArray";
+ variables_["array_property_type"] =
+ "NSMutableArray<" + variables_["storage_type"] + "*>";
+ }
+}
+
+RepeatedPrimitiveFieldGenerator::~RepeatedPrimitiveFieldGenerator() {}
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.h
new file mode 100644
index 0000000000..69bb1fddc1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/objectivec/objectivec_primitive_field.h
@@ -0,0 +1,92 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_PRIMITIVE_FIELD_H__
+#define GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_PRIMITIVE_FIELD_H__
+
+#include <map>
+#include <string>
+#include <google/protobuf/compiler/objectivec/objectivec_field.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace objectivec {
+
+class PrimitiveFieldGenerator : public SingleFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ protected:
+ PrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual ~PrimitiveFieldGenerator();
+
+ virtual void GenerateFieldStorageDeclaration(io::Printer* printer) const;
+
+ virtual int ExtraRuntimeHasBitsNeeded(void) const;
+ virtual void SetExtraRuntimeHasBitsBase(int index_base);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveFieldGenerator);
+};
+
+class PrimitiveObjFieldGenerator : public ObjCObjFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ protected:
+ PrimitiveObjFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual ~PrimitiveObjFieldGenerator();
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveObjFieldGenerator);
+};
+
+class RepeatedPrimitiveFieldGenerator : public RepeatedFieldGenerator {
+ friend FieldGenerator* FieldGenerator::Make(const FieldDescriptor* field,
+ const Options& options);
+
+ protected:
+ RepeatedPrimitiveFieldGenerator(const FieldDescriptor* descriptor,
+ const Options& options);
+ virtual ~RepeatedPrimitiveFieldGenerator();
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedPrimitiveFieldGenerator);
+};
+
+} // namespace objectivec
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_OBJECTIVEC_PRIMITIVE_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/package_info.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/package_info.h
new file mode 100644
index 0000000000..fb6b473e1c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/package_info.h
@@ -0,0 +1,64 @@
+// 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 exists solely to document the google::protobuf::compiler namespace.
+// It is not compiled into anything, but it may be read by an automated
+// documentation generator.
+
+namespace google {
+
+namespace protobuf {
+
+// Implementation of the Protocol Buffer compiler.
+//
+// This package contains code for parsing .proto files and generating code
+// based on them. There are two reasons you might be interested in this
+// package:
+// - You want to parse .proto files at runtime. In this case, you should
+// look at importer.h. Since this functionality is widely useful, it is
+// included in the libprotobuf base library; you do not have to link against
+// libprotoc.
+// - You want to write a custom protocol compiler which generates different
+// kinds of code, e.g. code in a different language which is not supported
+// by the official compiler. For this purpose, command_line_interface.h
+// provides you with a complete compiler front-end, so all you need to do
+// is write a custom implementation of CodeGenerator and a trivial main()
+// function. You can even make your compiler support the official languages
+// in addition to your own. Since this functionality is only useful to those
+// writing custom compilers, it is in a separate library called "libprotoc"
+// which you will have to link against.
+namespace compiler {}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.cc
new file mode 100644
index 0000000000..214d7c9cd9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.cc
@@ -0,0 +1,2119 @@
+// 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.
+//
+// Recursive descent FTW.
+
+#include <float.h>
+#include <google/protobuf/stubs/hash.h>
+#include <limits>
+
+
+#include <google/protobuf/compiler/parser.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+using internal::WireFormat;
+
+namespace {
+
+typedef hash_map<string, FieldDescriptorProto::Type> TypeNameMap;
+
+TypeNameMap MakeTypeNameTable() {
+ TypeNameMap result;
+
+ result["double" ] = FieldDescriptorProto::TYPE_DOUBLE;
+ result["float" ] = FieldDescriptorProto::TYPE_FLOAT;
+ result["uint64" ] = FieldDescriptorProto::TYPE_UINT64;
+ result["fixed64" ] = FieldDescriptorProto::TYPE_FIXED64;
+ result["fixed32" ] = FieldDescriptorProto::TYPE_FIXED32;
+ result["bool" ] = FieldDescriptorProto::TYPE_BOOL;
+ result["string" ] = FieldDescriptorProto::TYPE_STRING;
+ result["group" ] = FieldDescriptorProto::TYPE_GROUP;
+
+ result["bytes" ] = FieldDescriptorProto::TYPE_BYTES;
+ result["uint32" ] = FieldDescriptorProto::TYPE_UINT32;
+ result["sfixed32"] = FieldDescriptorProto::TYPE_SFIXED32;
+ result["sfixed64"] = FieldDescriptorProto::TYPE_SFIXED64;
+ result["int32" ] = FieldDescriptorProto::TYPE_INT32;
+ result["int64" ] = FieldDescriptorProto::TYPE_INT64;
+ result["sint32" ] = FieldDescriptorProto::TYPE_SINT32;
+ result["sint64" ] = FieldDescriptorProto::TYPE_SINT64;
+
+ return result;
+}
+
+const TypeNameMap kTypeNames = MakeTypeNameTable();
+
+// Camel-case the field name and append "Entry" for generated map entry name.
+// e.g. map<KeyType, ValueType> foo_map => FooMapEntry
+string MapEntryName(const string& field_name) {
+ string result;
+ static const char kSuffix[] = "Entry";
+ result.reserve(field_name.size() + sizeof(kSuffix));
+ bool cap_next = true;
+ for (int i = 0; i < field_name.size(); ++i) {
+ if (field_name[i] == '_') {
+ cap_next = true;
+ } else if (cap_next) {
+ // Note: Do not use ctype.h due to locales.
+ if ('a' <= field_name[i] && field_name[i] <= 'z') {
+ result.push_back(field_name[i] - 'a' + 'A');
+ } else {
+ result.push_back(field_name[i]);
+ }
+ cap_next = false;
+ } else {
+ result.push_back(field_name[i]);
+ }
+ }
+ result.append(kSuffix);
+ return result;
+}
+
+} // anonymous namespace
+
+// Makes code slightly more readable. The meaning of "DO(foo)" is
+// "Execute foo and fail if it fails.", where failure is indicated by
+// returning false.
+#define DO(STATEMENT) if (STATEMENT) {} else return false
+
+// ===================================================================
+
+Parser::Parser()
+ : input_(NULL),
+ error_collector_(NULL),
+ source_location_table_(NULL),
+ had_errors_(false),
+ require_syntax_identifier_(false),
+ stop_after_syntax_identifier_(false) {
+}
+
+Parser::~Parser() {
+}
+
+// ===================================================================
+
+inline bool Parser::LookingAt(const char* text) {
+ return input_->current().text == text;
+}
+
+inline bool Parser::LookingAtType(io::Tokenizer::TokenType token_type) {
+ return input_->current().type == token_type;
+}
+
+inline bool Parser::AtEnd() {
+ return LookingAtType(io::Tokenizer::TYPE_END);
+}
+
+bool Parser::TryConsume(const char* text) {
+ if (LookingAt(text)) {
+ input_->Next();
+ return true;
+ } else {
+ return false;
+ }
+}
+
+bool Parser::Consume(const char* text, const char* error) {
+ if (TryConsume(text)) {
+ return true;
+ } else {
+ AddError(error);
+ return false;
+ }
+}
+
+bool Parser::Consume(const char* text) {
+ if (TryConsume(text)) {
+ return true;
+ } else {
+ AddError("Expected \"" + string(text) + "\".");
+ return false;
+ }
+}
+
+bool Parser::ConsumeIdentifier(string* output, const char* error) {
+ if (LookingAtType(io::Tokenizer::TYPE_IDENTIFIER)) {
+ *output = input_->current().text;
+ input_->Next();
+ return true;
+ } else {
+ AddError(error);
+ return false;
+ }
+}
+
+bool Parser::ConsumeInteger(int* output, const char* error) {
+ if (LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ uint64 value = 0;
+ if (!io::Tokenizer::ParseInteger(input_->current().text,
+ kint32max, &value)) {
+ AddError("Integer out of range.");
+ // We still return true because we did, in fact, parse an integer.
+ }
+ *output = value;
+ input_->Next();
+ return true;
+ } else {
+ AddError(error);
+ return false;
+ }
+}
+
+bool Parser::ConsumeSignedInteger(int* output, const char* error) {
+ bool is_negative = false;
+ uint64 max_value = kint32max;
+ if (TryConsume("-")) {
+ is_negative = true;
+ max_value += 1;
+ }
+ uint64 value = 0;
+ DO(ConsumeInteger64(max_value, &value, error));
+ if (is_negative) value *= -1;
+ *output = value;
+ return true;
+}
+
+bool Parser::ConsumeInteger64(uint64 max_value, uint64* output,
+ const char* error) {
+ if (LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ if (!io::Tokenizer::ParseInteger(input_->current().text, max_value,
+ output)) {
+ AddError("Integer out of range.");
+ // We still return true because we did, in fact, parse an integer.
+ *output = 0;
+ }
+ input_->Next();
+ return true;
+ } else {
+ AddError(error);
+ return false;
+ }
+}
+
+bool Parser::ConsumeNumber(double* output, const char* error) {
+ if (LookingAtType(io::Tokenizer::TYPE_FLOAT)) {
+ *output = io::Tokenizer::ParseFloat(input_->current().text);
+ input_->Next();
+ return true;
+ } else if (LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ // Also accept integers.
+ uint64 value = 0;
+ if (!io::Tokenizer::ParseInteger(input_->current().text,
+ kuint64max, &value)) {
+ AddError("Integer out of range.");
+ // We still return true because we did, in fact, parse a number.
+ }
+ *output = value;
+ input_->Next();
+ return true;
+ } else if (LookingAt("inf")) {
+ *output = numeric_limits<double>::infinity();
+ input_->Next();
+ return true;
+ } else if (LookingAt("nan")) {
+ *output = numeric_limits<double>::quiet_NaN();
+ input_->Next();
+ return true;
+ } else {
+ AddError(error);
+ return false;
+ }
+}
+
+bool Parser::ConsumeString(string* output, const char* error) {
+ if (LookingAtType(io::Tokenizer::TYPE_STRING)) {
+ io::Tokenizer::ParseString(input_->current().text, output);
+ input_->Next();
+ // Allow C++ like concatenation of adjacent string tokens.
+ while (LookingAtType(io::Tokenizer::TYPE_STRING)) {
+ io::Tokenizer::ParseStringAppend(input_->current().text, output);
+ input_->Next();
+ }
+ return true;
+ } else {
+ AddError(error);
+ return false;
+ }
+}
+
+bool Parser::TryConsumeEndOfDeclaration(
+ const char* text, const LocationRecorder* location) {
+ if (LookingAt(text)) {
+ string leading, trailing;
+ vector<string> detached;
+ input_->NextWithComments(&trailing, &detached, &leading);
+
+ // Save the leading comments for next time, and recall the leading comments
+ // from last time.
+ leading.swap(upcoming_doc_comments_);
+
+ if (location != NULL) {
+ upcoming_detached_comments_.swap(detached);
+ location->AttachComments(&leading, &trailing, &detached);
+ } else if (strcmp(text, "}") == 0) {
+ // If the current location is null and we are finishing the current scope,
+ // drop pending upcoming detached comments.
+ upcoming_detached_comments_.swap(detached);
+ } else {
+ // Otherwise, append the new detached comments to the existing upcoming
+ // detached comments.
+ upcoming_detached_comments_.insert(upcoming_detached_comments_.end(),
+ detached.begin(), detached.end());
+ }
+
+ return true;
+ } else {
+ return false;
+ }
+}
+
+bool Parser::ConsumeEndOfDeclaration(
+ const char* text, const LocationRecorder* location) {
+ if (TryConsumeEndOfDeclaration(text, location)) {
+ return true;
+ } else {
+ AddError("Expected \"" + string(text) + "\".");
+ return false;
+ }
+}
+
+// -------------------------------------------------------------------
+
+void Parser::AddError(int line, int column, const string& error) {
+ if (error_collector_ != NULL) {
+ error_collector_->AddError(line, column, error);
+ }
+ had_errors_ = true;
+}
+
+void Parser::AddError(const string& error) {
+ AddError(input_->current().line, input_->current().column, error);
+}
+
+// -------------------------------------------------------------------
+
+Parser::LocationRecorder::LocationRecorder(Parser* parser)
+ : parser_(parser),
+ location_(parser_->source_code_info_->add_location()) {
+ location_->add_span(parser_->input_->current().line);
+ location_->add_span(parser_->input_->current().column);
+}
+
+Parser::LocationRecorder::LocationRecorder(const LocationRecorder& parent) {
+ Init(parent);
+}
+
+Parser::LocationRecorder::LocationRecorder(const LocationRecorder& parent,
+ int path1) {
+ Init(parent);
+ AddPath(path1);
+}
+
+Parser::LocationRecorder::LocationRecorder(const LocationRecorder& parent,
+ int path1, int path2) {
+ Init(parent);
+ AddPath(path1);
+ AddPath(path2);
+}
+
+void Parser::LocationRecorder::Init(const LocationRecorder& parent) {
+ parser_ = parent.parser_;
+ location_ = parser_->source_code_info_->add_location();
+ location_->mutable_path()->CopyFrom(parent.location_->path());
+
+ location_->add_span(parser_->input_->current().line);
+ location_->add_span(parser_->input_->current().column);
+}
+
+Parser::LocationRecorder::~LocationRecorder() {
+ if (location_->span_size() <= 2) {
+ EndAt(parser_->input_->previous());
+ }
+}
+
+void Parser::LocationRecorder::AddPath(int path_component) {
+ location_->add_path(path_component);
+}
+
+void Parser::LocationRecorder::StartAt(const io::Tokenizer::Token& token) {
+ location_->set_span(0, token.line);
+ location_->set_span(1, token.column);
+}
+
+void Parser::LocationRecorder::StartAt(const LocationRecorder& other) {
+ location_->set_span(0, other.location_->span(0));
+ location_->set_span(1, other.location_->span(1));
+}
+
+void Parser::LocationRecorder::EndAt(const io::Tokenizer::Token& token) {
+ if (token.line != location_->span(0)) {
+ location_->add_span(token.line);
+ }
+ location_->add_span(token.end_column);
+}
+
+void Parser::LocationRecorder::RecordLegacyLocation(const Message* descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location) {
+ if (parser_->source_location_table_ != NULL) {
+ parser_->source_location_table_->Add(
+ descriptor, location, location_->span(0), location_->span(1));
+ }
+}
+
+void Parser::LocationRecorder::AttachComments(
+ string* leading, string* trailing,
+ vector<string>* detached_comments) const {
+ GOOGLE_CHECK(!location_->has_leading_comments());
+ GOOGLE_CHECK(!location_->has_trailing_comments());
+
+ if (!leading->empty()) {
+ location_->mutable_leading_comments()->swap(*leading);
+ }
+ if (!trailing->empty()) {
+ location_->mutable_trailing_comments()->swap(*trailing);
+ }
+ for (int i = 0; i < detached_comments->size(); ++i) {
+ location_->add_leading_detached_comments()->swap(
+ (*detached_comments)[i]);
+ }
+ detached_comments->clear();
+}
+
+// -------------------------------------------------------------------
+
+void Parser::SkipStatement() {
+ while (true) {
+ if (AtEnd()) {
+ return;
+ } else if (LookingAtType(io::Tokenizer::TYPE_SYMBOL)) {
+ if (TryConsumeEndOfDeclaration(";", NULL)) {
+ return;
+ } else if (TryConsume("{")) {
+ SkipRestOfBlock();
+ return;
+ } else if (LookingAt("}")) {
+ return;
+ }
+ }
+ input_->Next();
+ }
+}
+
+void Parser::SkipRestOfBlock() {
+ while (true) {
+ if (AtEnd()) {
+ return;
+ } else if (LookingAtType(io::Tokenizer::TYPE_SYMBOL)) {
+ if (TryConsumeEndOfDeclaration("}", NULL)) {
+ return;
+ } else if (TryConsume("{")) {
+ SkipRestOfBlock();
+ }
+ }
+ input_->Next();
+ }
+}
+
+// ===================================================================
+
+bool Parser::ValidateEnum(const EnumDescriptorProto* proto) {
+ bool has_allow_alias = false;
+ bool allow_alias = false;
+
+ for (int i = 0; i < proto->options().uninterpreted_option_size(); i++) {
+ const UninterpretedOption option = proto->options().uninterpreted_option(i);
+ if (option.name_size() > 1) {
+ continue;
+ }
+ if (!option.name(0).is_extension() &&
+ option.name(0).name_part() == "allow_alias") {
+ has_allow_alias = true;
+ if (option.identifier_value() == "true") {
+ allow_alias = true;
+ }
+ break;
+ }
+ }
+
+ if (has_allow_alias && !allow_alias) {
+ string error =
+ "\"" + proto->name() +
+ "\" declares 'option allow_alias = false;' which has no effect. "
+ "Please remove the declaration.";
+ // This needlessly clutters declarations with nops.
+ AddError(error);
+ return false;
+ }
+
+ set<int> used_values;
+ bool has_duplicates = false;
+ for (int i = 0; i < proto->value_size(); ++i) {
+ const EnumValueDescriptorProto enum_value = proto->value(i);
+ if (used_values.find(enum_value.number()) != used_values.end()) {
+ has_duplicates = true;
+ break;
+ } else {
+ used_values.insert(enum_value.number());
+ }
+ }
+ if (allow_alias && !has_duplicates) {
+ string error =
+ "\"" + proto->name() +
+ "\" declares support for enum aliases but no enum values share field "
+ "numbers. Please remove the unnecessary 'option allow_alias = true;' "
+ "declaration.";
+ // Generate an error if an enum declares support for duplicate enum values
+ // and does not use it protect future authors.
+ AddError(error);
+ return false;
+ }
+
+ return true;
+}
+
+bool Parser::Parse(io::Tokenizer* input, FileDescriptorProto* file) {
+ input_ = input;
+ had_errors_ = false;
+ syntax_identifier_.clear();
+
+ // Note that |file| could be NULL at this point if
+ // stop_after_syntax_identifier_ is true. So, we conservatively allocate
+ // SourceCodeInfo on the stack, then swap it into the FileDescriptorProto
+ // later on.
+ SourceCodeInfo source_code_info;
+ source_code_info_ = &source_code_info;
+
+ vector<string> top_doc_comments;
+ if (LookingAtType(io::Tokenizer::TYPE_START)) {
+ // Advance to first token.
+ input_->NextWithComments(NULL, &upcoming_detached_comments_,
+ &upcoming_doc_comments_);
+ }
+
+ {
+ LocationRecorder root_location(this);
+
+ if (require_syntax_identifier_ || LookingAt("syntax")) {
+ if (!ParseSyntaxIdentifier(root_location)) {
+ // Don't attempt to parse the file if we didn't recognize the syntax
+ // identifier.
+ return false;
+ }
+ // Store the syntax into the file.
+ if (file != NULL) file->set_syntax(syntax_identifier_);
+ } else if (!stop_after_syntax_identifier_) {
+ GOOGLE_LOG(WARNING) << "No syntax specified for the proto file: "
+ << file->name() << ". Please use 'syntax = \"proto2\";' "
+ << "or 'syntax = \"proto3\";' to specify a syntax "
+ << "version. (Defaulted to proto2 syntax.)";
+ syntax_identifier_ = "proto2";
+ }
+
+ if (stop_after_syntax_identifier_) return !had_errors_;
+
+ // Repeatedly parse statements until we reach the end of the file.
+ while (!AtEnd()) {
+ if (!ParseTopLevelStatement(file, root_location)) {
+ // This statement failed to parse. Skip it, but keep looping to parse
+ // other statements.
+ SkipStatement();
+
+ if (LookingAt("}")) {
+ AddError("Unmatched \"}\".");
+ input_->NextWithComments(NULL, &upcoming_detached_comments_,
+ &upcoming_doc_comments_);
+ }
+ }
+ }
+ }
+
+ input_ = NULL;
+ source_code_info_ = NULL;
+ source_code_info.Swap(file->mutable_source_code_info());
+ return !had_errors_;
+}
+
+bool Parser::ParseSyntaxIdentifier(const LocationRecorder& parent) {
+ LocationRecorder syntax_location(parent,
+ FileDescriptorProto::kSyntaxFieldNumber);
+ DO(Consume(
+ "syntax",
+ "File must begin with a syntax statement, e.g. 'syntax = \"proto2\";'."));
+ DO(Consume("="));
+ io::Tokenizer::Token syntax_token = input_->current();
+ string syntax;
+ DO(ConsumeString(&syntax, "Expected syntax identifier."));
+ DO(ConsumeEndOfDeclaration(";", &syntax_location));
+
+ syntax_identifier_ = syntax;
+
+ if (syntax != "proto2" && syntax != "proto3" &&
+ !stop_after_syntax_identifier_) {
+ AddError(syntax_token.line, syntax_token.column,
+ "Unrecognized syntax identifier \"" + syntax + "\". This parser "
+ "only recognizes \"proto2\" and \"proto3\".");
+ return false;
+ }
+
+ return true;
+}
+
+bool Parser::ParseTopLevelStatement(FileDescriptorProto* file,
+ const LocationRecorder& root_location) {
+ if (TryConsumeEndOfDeclaration(";", NULL)) {
+ // empty statement; ignore
+ return true;
+ } else if (LookingAt("message")) {
+ LocationRecorder location(root_location,
+ FileDescriptorProto::kMessageTypeFieldNumber, file->message_type_size());
+ return ParseMessageDefinition(file->add_message_type(), location, file);
+ } else if (LookingAt("enum")) {
+ LocationRecorder location(root_location,
+ FileDescriptorProto::kEnumTypeFieldNumber, file->enum_type_size());
+ return ParseEnumDefinition(file->add_enum_type(), location, file);
+ } else if (LookingAt("service")) {
+ LocationRecorder location(root_location,
+ FileDescriptorProto::kServiceFieldNumber, file->service_size());
+ return ParseServiceDefinition(file->add_service(), location, file);
+ } else if (LookingAt("extend")) {
+ LocationRecorder location(root_location,
+ FileDescriptorProto::kExtensionFieldNumber);
+ return ParseExtend(file->mutable_extension(),
+ file->mutable_message_type(),
+ root_location,
+ FileDescriptorProto::kMessageTypeFieldNumber,
+ location, file);
+ } else if (LookingAt("import")) {
+ return ParseImport(file->mutable_dependency(),
+ file->mutable_public_dependency(),
+ file->mutable_weak_dependency(),
+ root_location, file);
+ } else if (LookingAt("package")) {
+ return ParsePackage(file, root_location, file);
+ } else if (LookingAt("option")) {
+ LocationRecorder location(root_location,
+ FileDescriptorProto::kOptionsFieldNumber);
+ return ParseOption(file->mutable_options(), location, file,
+ OPTION_STATEMENT);
+ } else {
+ AddError("Expected top-level statement (e.g. \"message\").");
+ return false;
+ }
+}
+
+// -------------------------------------------------------------------
+// Messages
+
+bool Parser::ParseMessageDefinition(
+ DescriptorProto* message,
+ const LocationRecorder& message_location,
+ const FileDescriptorProto* containing_file) {
+ DO(Consume("message"));
+ {
+ LocationRecorder location(message_location,
+ DescriptorProto::kNameFieldNumber);
+ location.RecordLegacyLocation(
+ message, DescriptorPool::ErrorCollector::NAME);
+ DO(ConsumeIdentifier(message->mutable_name(), "Expected message name."));
+ }
+ DO(ParseMessageBlock(message, message_location, containing_file));
+ return true;
+}
+
+namespace {
+
+const int kMaxExtensionRangeSentinel = -1;
+
+bool IsMessageSetWireFormatMessage(const DescriptorProto& message) {
+ const MessageOptions& options = message.options();
+ for (int i = 0; i < options.uninterpreted_option_size(); ++i) {
+ const UninterpretedOption& uninterpreted = options.uninterpreted_option(i);
+ if (uninterpreted.name_size() == 1 &&
+ uninterpreted.name(0).name_part() == "message_set_wire_format" &&
+ uninterpreted.identifier_value() == "true") {
+ return true;
+ }
+ }
+ return false;
+}
+
+// Modifies any extension ranges that specified 'max' as the end of the
+// extension range, and sets them to the type-specific maximum. The actual max
+// tag number can only be determined after all options have been parsed.
+void AdjustExtensionRangesWithMaxEndNumber(DescriptorProto* message) {
+ const bool is_message_set = IsMessageSetWireFormatMessage(*message);
+ const int max_extension_number = is_message_set ?
+ kint32max :
+ FieldDescriptor::kMaxNumber + 1;
+ for (int i = 0; i < message->extension_range_size(); ++i) {
+ if (message->extension_range(i).end() == kMaxExtensionRangeSentinel) {
+ message->mutable_extension_range(i)->set_end(max_extension_number);
+ }
+ }
+}
+
+} // namespace
+
+bool Parser::ParseMessageBlock(DescriptorProto* message,
+ const LocationRecorder& message_location,
+ const FileDescriptorProto* containing_file) {
+ DO(ConsumeEndOfDeclaration("{", &message_location));
+
+ while (!TryConsumeEndOfDeclaration("}", NULL)) {
+ if (AtEnd()) {
+ AddError("Reached end of input in message definition (missing '}').");
+ return false;
+ }
+
+ if (!ParseMessageStatement(message, message_location, containing_file)) {
+ // This statement failed to parse. Skip it, but keep looping to parse
+ // other statements.
+ SkipStatement();
+ }
+ }
+
+ if (message->extension_range_size() > 0) {
+ AdjustExtensionRangesWithMaxEndNumber(message);
+ }
+ return true;
+}
+
+bool Parser::ParseMessageStatement(DescriptorProto* message,
+ const LocationRecorder& message_location,
+ const FileDescriptorProto* containing_file) {
+ if (TryConsumeEndOfDeclaration(";", NULL)) {
+ // empty statement; ignore
+ return true;
+ } else if (LookingAt("message")) {
+ LocationRecorder location(message_location,
+ DescriptorProto::kNestedTypeFieldNumber,
+ message->nested_type_size());
+ return ParseMessageDefinition(message->add_nested_type(), location,
+ containing_file);
+ } else if (LookingAt("enum")) {
+ LocationRecorder location(message_location,
+ DescriptorProto::kEnumTypeFieldNumber,
+ message->enum_type_size());
+ return ParseEnumDefinition(message->add_enum_type(), location,
+ containing_file);
+ } else if (LookingAt("extensions")) {
+ LocationRecorder location(message_location,
+ DescriptorProto::kExtensionRangeFieldNumber);
+ return ParseExtensions(message, location, containing_file);
+ } else if (LookingAt("reserved")) {
+ return ParseReserved(message, message_location);
+ } else if (LookingAt("extend")) {
+ LocationRecorder location(message_location,
+ DescriptorProto::kExtensionFieldNumber);
+ return ParseExtend(message->mutable_extension(),
+ message->mutable_nested_type(),
+ message_location,
+ DescriptorProto::kNestedTypeFieldNumber,
+ location, containing_file);
+ } else if (LookingAt("option")) {
+ LocationRecorder location(message_location,
+ DescriptorProto::kOptionsFieldNumber);
+ return ParseOption(message->mutable_options(), location,
+ containing_file, OPTION_STATEMENT);
+ } else if (LookingAt("oneof")) {
+ int oneof_index = message->oneof_decl_size();
+ LocationRecorder oneof_location(message_location,
+ DescriptorProto::kOneofDeclFieldNumber,
+ oneof_index);
+
+ return ParseOneof(message->add_oneof_decl(), message,
+ oneof_index, oneof_location, message_location,
+ containing_file);
+ } else {
+ LocationRecorder location(message_location,
+ DescriptorProto::kFieldFieldNumber,
+ message->field_size());
+ return ParseMessageField(message->add_field(),
+ message->mutable_nested_type(),
+ message_location,
+ DescriptorProto::kNestedTypeFieldNumber,
+ location,
+ containing_file);
+ }
+}
+
+bool Parser::ParseMessageField(FieldDescriptorProto* field,
+ RepeatedPtrField<DescriptorProto>* messages,
+ const LocationRecorder& parent_location,
+ int location_field_number_for_nested_type,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file) {
+ {
+ LocationRecorder location(field_location,
+ FieldDescriptorProto::kLabelFieldNumber);
+ FieldDescriptorProto::Label label;
+ if (ParseLabel(&label, containing_file)) {
+ field->set_label(label);
+ if (label == FieldDescriptorProto::LABEL_OPTIONAL &&
+ syntax_identifier_ == "proto3") {
+ AddError(
+ "Explicit 'optional' labels are disallowed in the Proto3 syntax. "
+ "To define 'optional' fields in Proto3, simply remove the "
+ "'optional' label, as fields are 'optional' by default.");
+ }
+ }
+ }
+
+ return ParseMessageFieldNoLabel(field, messages, parent_location,
+ location_field_number_for_nested_type,
+ field_location,
+ containing_file);
+}
+
+bool Parser::ParseMessageFieldNoLabel(
+ FieldDescriptorProto* field,
+ RepeatedPtrField<DescriptorProto>* messages,
+ const LocationRecorder& parent_location,
+ int location_field_number_for_nested_type,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file) {
+ MapField map_field;
+ // Parse type.
+ {
+ LocationRecorder location(field_location); // add path later
+ location.RecordLegacyLocation(field, DescriptorPool::ErrorCollector::TYPE);
+
+ bool type_parsed = false;
+ FieldDescriptorProto::Type type = FieldDescriptorProto::TYPE_INT32;
+ string type_name;
+
+ // Special case map field. We only treat the field as a map field if the
+ // field type name starts with the word "map" with a following "<".
+ if (TryConsume("map")) {
+ if (LookingAt("<")) {
+ map_field.is_map_field = true;
+ } else {
+ // False positive
+ type_parsed = true;
+ type_name = "map";
+ }
+ }
+ if (map_field.is_map_field) {
+ if (field->has_oneof_index()) {
+ AddError("Map fields are not allowed in oneofs.");
+ return false;
+ }
+ if (field->has_label()) {
+ AddError(
+ "Field labels (required/optional/repeated) are not allowed on "
+ "map fields.");
+ return false;
+ }
+ if (field->has_extendee()) {
+ AddError("Map fields are not allowed to be extensions.");
+ return false;
+ }
+ field->set_label(FieldDescriptorProto::LABEL_REPEATED);
+ DO(Consume("<"));
+ DO(ParseType(&map_field.key_type, &map_field.key_type_name));
+ DO(Consume(","));
+ DO(ParseType(&map_field.value_type, &map_field.value_type_name));
+ DO(Consume(">"));
+ // Defer setting of the type name of the map field until the
+ // field name is parsed. Add the source location though.
+ location.AddPath(FieldDescriptorProto::kTypeNameFieldNumber);
+ } else {
+ // Handle the case where no explicit label is given for a non-map field.
+ if (!field->has_label() && DefaultToOptionalFields()) {
+ field->set_label(FieldDescriptorProto::LABEL_OPTIONAL);
+ }
+ if (!field->has_label()) {
+ AddError("Expected \"required\", \"optional\", or \"repeated\".");
+ // We can actually reasonably recover here by just assuming the user
+ // forgot the label altogether.
+ field->set_label(FieldDescriptorProto::LABEL_OPTIONAL);
+ }
+
+ // Handle the case where the actual type is a message or enum named "map",
+ // which we already consumed in the code above.
+ if (!type_parsed) {
+ DO(ParseType(&type, &type_name));
+ }
+ if (type_name.empty()) {
+ location.AddPath(FieldDescriptorProto::kTypeFieldNumber);
+ field->set_type(type);
+ } else {
+ location.AddPath(FieldDescriptorProto::kTypeNameFieldNumber);
+ field->set_type_name(type_name);
+ }
+ }
+ }
+
+ // Parse name and '='.
+ io::Tokenizer::Token name_token = input_->current();
+ {
+ LocationRecorder location(field_location,
+ FieldDescriptorProto::kNameFieldNumber);
+ location.RecordLegacyLocation(field, DescriptorPool::ErrorCollector::NAME);
+ DO(ConsumeIdentifier(field->mutable_name(), "Expected field name."));
+ }
+ DO(Consume("=", "Missing field number."));
+
+ // Parse field number.
+ {
+ LocationRecorder location(field_location,
+ FieldDescriptorProto::kNumberFieldNumber);
+ location.RecordLegacyLocation(
+ field, DescriptorPool::ErrorCollector::NUMBER);
+ int number;
+ DO(ConsumeInteger(&number, "Expected field number."));
+ field->set_number(number);
+ }
+
+ // Parse options.
+ DO(ParseFieldOptions(field, field_location, containing_file));
+
+ // Deal with groups.
+ if (field->has_type() && field->type() == FieldDescriptorProto::TYPE_GROUP) {
+ // Awkward: Since a group declares both a message type and a field, we
+ // have to create overlapping locations.
+ LocationRecorder group_location(parent_location);
+ group_location.StartAt(field_location);
+ group_location.AddPath(location_field_number_for_nested_type);
+ group_location.AddPath(messages->size());
+
+ DescriptorProto* group = messages->Add();
+ group->set_name(field->name());
+
+ // Record name location to match the field name's location.
+ {
+ LocationRecorder location(group_location,
+ DescriptorProto::kNameFieldNumber);
+ location.StartAt(name_token);
+ location.EndAt(name_token);
+ location.RecordLegacyLocation(
+ group, DescriptorPool::ErrorCollector::NAME);
+ }
+
+ // The field's type_name also comes from the name. Confusing!
+ {
+ LocationRecorder location(field_location,
+ FieldDescriptorProto::kTypeNameFieldNumber);
+ location.StartAt(name_token);
+ location.EndAt(name_token);
+ }
+
+ // As a hack for backwards-compatibility, we force the group name to start
+ // with a capital letter and lower-case the field name. New code should
+ // not use groups; it should use nested messages.
+ if (group->name()[0] < 'A' || 'Z' < group->name()[0]) {
+ AddError(name_token.line, name_token.column,
+ "Group names must start with a capital letter.");
+ }
+ LowerString(field->mutable_name());
+
+ field->set_type_name(group->name());
+ if (LookingAt("{")) {
+ DO(ParseMessageBlock(group, group_location, containing_file));
+ } else {
+ AddError("Missing group body.");
+ return false;
+ }
+ } else {
+ DO(ConsumeEndOfDeclaration(";", &field_location));
+ }
+
+ // Create a map entry type if this is a map field.
+ if (map_field.is_map_field) {
+ GenerateMapEntry(map_field, field, messages);
+ }
+
+ return true;
+}
+
+void Parser::GenerateMapEntry(const MapField& map_field,
+ FieldDescriptorProto* field,
+ RepeatedPtrField<DescriptorProto>* messages) {
+ DescriptorProto* entry = messages->Add();
+ string entry_name = MapEntryName(field->name());
+ field->set_type_name(entry_name);
+ entry->set_name(entry_name);
+ entry->mutable_options()->set_map_entry(true);
+ FieldDescriptorProto* key_field = entry->add_field();
+ key_field->set_name("key");
+ key_field->set_label(FieldDescriptorProto::LABEL_OPTIONAL);
+ key_field->set_number(1);
+ if (map_field.key_type_name.empty()) {
+ key_field->set_type(map_field.key_type);
+ } else {
+ key_field->set_type_name(map_field.key_type_name);
+ }
+ FieldDescriptorProto* value_field = entry->add_field();
+ value_field->set_name("value");
+ value_field->set_label(FieldDescriptorProto::LABEL_OPTIONAL);
+ value_field->set_number(2);
+ if (map_field.value_type_name.empty()) {
+ value_field->set_type(map_field.value_type);
+ } else {
+ value_field->set_type_name(map_field.value_type_name);
+ }
+ // Propagate the "enforce_utf8" option to key and value fields if they
+ // are strings. This helps simplify the implementation of code generators
+ // and also reflection-based parsing code.
+ //
+ // The following definition:
+ // message Foo {
+ // map<string, string> value = 1 [enforce_utf8 = false];
+ // }
+ // will be interpreted as:
+ // message Foo {
+ // message ValueEntry {
+ // option map_entry = true;
+ // string key = 1 [enforce_utf8 = false];
+ // string value = 2 [enforce_utf8 = false];
+ // }
+ // repeated ValueEntry value = 1 [enforce_utf8 = false];
+ // }
+ //
+ // TODO(xiaofeng): Remove this when the "enforce_utf8" option is removed
+ // from protocol compiler.
+ for (int i = 0; i < field->options().uninterpreted_option_size(); ++i) {
+ const UninterpretedOption& option =
+ field->options().uninterpreted_option(i);
+ if (option.name_size() == 1 &&
+ option.name(0).name_part() == "enforce_utf8" &&
+ !option.name(0).is_extension()) {
+ if (key_field->type() == FieldDescriptorProto::TYPE_STRING) {
+ key_field->mutable_options()->add_uninterpreted_option()
+ ->CopyFrom(option);
+ }
+ if (value_field->type() == FieldDescriptorProto::TYPE_STRING) {
+ value_field->mutable_options()->add_uninterpreted_option()
+ ->CopyFrom(option);
+ }
+ }
+ }
+}
+
+bool Parser::ParseFieldOptions(FieldDescriptorProto* field,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file) {
+ if (!LookingAt("[")) return true;
+
+ LocationRecorder location(field_location,
+ FieldDescriptorProto::kOptionsFieldNumber);
+
+ DO(Consume("["));
+
+ // Parse field options.
+ do {
+ if (LookingAt("default")) {
+ // We intentionally pass field_location rather than location here, since
+ // the default value is not actually an option.
+ DO(ParseDefaultAssignment(field, field_location, containing_file));
+ } else if (LookingAt("json_name")) {
+ // Like default value, this "json_name" is not an actual option.
+ DO(ParseJsonName(field, field_location, containing_file));
+ } else {
+ DO(ParseOption(field->mutable_options(), location,
+ containing_file, OPTION_ASSIGNMENT));
+ }
+ } while (TryConsume(","));
+
+ DO(Consume("]"));
+ return true;
+}
+
+bool Parser::ParseDefaultAssignment(
+ FieldDescriptorProto* field,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file) {
+ if (field->has_default_value()) {
+ AddError("Already set option \"default\".");
+ field->clear_default_value();
+ }
+
+ DO(Consume("default"));
+ DO(Consume("="));
+
+ LocationRecorder location(field_location,
+ FieldDescriptorProto::kDefaultValueFieldNumber);
+ location.RecordLegacyLocation(
+ field, DescriptorPool::ErrorCollector::DEFAULT_VALUE);
+ string* default_value = field->mutable_default_value();
+
+ if (!field->has_type()) {
+ // The field has a type name, but we don't know if it is a message or an
+ // enum yet. (If it were a primitive type, |field| would have a type set
+ // already.) In this case, simply take the current string as the default
+ // value; we will catch the error later if it is not a valid enum value.
+ // (N.B. that we do not check whether the current token is an identifier:
+ // doing so throws strange errors when the user mistypes a primitive
+ // typename and we assume it's an enum. E.g.: "optional int foo = 1 [default
+ // = 42]". In such a case the fundamental error is really that "int" is not
+ // a type, not that "42" is not an identifier. See b/12533582.)
+ *default_value = input_->current().text;
+ input_->Next();
+ return true;
+ }
+
+ switch (field->type()) {
+ case FieldDescriptorProto::TYPE_INT32:
+ case FieldDescriptorProto::TYPE_INT64:
+ case FieldDescriptorProto::TYPE_SINT32:
+ case FieldDescriptorProto::TYPE_SINT64:
+ case FieldDescriptorProto::TYPE_SFIXED32:
+ case FieldDescriptorProto::TYPE_SFIXED64: {
+ uint64 max_value = kint64max;
+ if (field->type() == FieldDescriptorProto::TYPE_INT32 ||
+ field->type() == FieldDescriptorProto::TYPE_SINT32 ||
+ field->type() == FieldDescriptorProto::TYPE_SFIXED32) {
+ max_value = kint32max;
+ }
+
+ // These types can be negative.
+ if (TryConsume("-")) {
+ default_value->append("-");
+ // Two's complement always has one more negative value than positive.
+ ++max_value;
+ }
+ // Parse the integer to verify that it is not out-of-range.
+ uint64 value;
+ DO(ConsumeInteger64(max_value, &value,
+ "Expected integer for field default value."));
+ // And stringify it again.
+ default_value->append(SimpleItoa(value));
+ break;
+ }
+
+ case FieldDescriptorProto::TYPE_UINT32:
+ case FieldDescriptorProto::TYPE_UINT64:
+ case FieldDescriptorProto::TYPE_FIXED32:
+ case FieldDescriptorProto::TYPE_FIXED64: {
+ uint64 max_value = kuint64max;
+ if (field->type() == FieldDescriptorProto::TYPE_UINT32 ||
+ field->type() == FieldDescriptorProto::TYPE_FIXED32) {
+ max_value = kuint32max;
+ }
+
+ // Numeric, not negative.
+ if (TryConsume("-")) {
+ AddError("Unsigned field can't have negative default value.");
+ }
+ // Parse the integer to verify that it is not out-of-range.
+ uint64 value;
+ DO(ConsumeInteger64(max_value, &value,
+ "Expected integer for field default value."));
+ // And stringify it again.
+ default_value->append(SimpleItoa(value));
+ break;
+ }
+
+ case FieldDescriptorProto::TYPE_FLOAT:
+ case FieldDescriptorProto::TYPE_DOUBLE:
+ // These types can be negative.
+ if (TryConsume("-")) {
+ default_value->append("-");
+ }
+ // Parse the integer because we have to convert hex integers to decimal
+ // floats.
+ double value;
+ DO(ConsumeNumber(&value, "Expected number."));
+ // And stringify it again.
+ default_value->append(SimpleDtoa(value));
+ break;
+
+ case FieldDescriptorProto::TYPE_BOOL:
+ if (TryConsume("true")) {
+ default_value->assign("true");
+ } else if (TryConsume("false")) {
+ default_value->assign("false");
+ } else {
+ AddError("Expected \"true\" or \"false\".");
+ return false;
+ }
+ break;
+
+ case FieldDescriptorProto::TYPE_STRING:
+ // Note: When file opton java_string_check_utf8 is true, if a
+ // non-string representation (eg byte[]) is later supported, it must
+ // be checked for UTF-8-ness.
+ DO(ConsumeString(default_value, "Expected string for field default "
+ "value."));
+ break;
+
+ case FieldDescriptorProto::TYPE_BYTES:
+ DO(ConsumeString(default_value, "Expected string."));
+ *default_value = CEscape(*default_value);
+ break;
+
+ case FieldDescriptorProto::TYPE_ENUM:
+ DO(ConsumeIdentifier(default_value, "Expected enum identifier for field "
+ "default value."));
+ break;
+
+ case FieldDescriptorProto::TYPE_MESSAGE:
+ case FieldDescriptorProto::TYPE_GROUP:
+ AddError("Messages can't have default values.");
+ return false;
+ }
+
+ return true;
+}
+
+bool Parser::ParseJsonName(
+ FieldDescriptorProto* field,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file) {
+ if (field->has_json_name()) {
+ AddError("Already set option \"json_name\".");
+ field->clear_json_name();
+ }
+
+ DO(Consume("json_name"));
+ DO(Consume("="));
+
+ LocationRecorder location(field_location,
+ FieldDescriptorProto::kJsonNameFieldNumber);
+ location.RecordLegacyLocation(
+ field, DescriptorPool::ErrorCollector::OPTION_VALUE);
+ DO(ConsumeString(field->mutable_json_name(),
+ "Expected string for JSON name."));
+ return true;
+}
+
+
+bool Parser::ParseOptionNamePart(UninterpretedOption* uninterpreted_option,
+ const LocationRecorder& part_location,
+ const FileDescriptorProto* containing_file) {
+ UninterpretedOption::NamePart* name = uninterpreted_option->add_name();
+ string identifier; // We parse identifiers into this string.
+ if (LookingAt("(")) { // This is an extension.
+ DO(Consume("("));
+
+ {
+ LocationRecorder location(
+ part_location, UninterpretedOption::NamePart::kNamePartFieldNumber);
+ // An extension name consists of dot-separated identifiers, and may begin
+ // with a dot.
+ if (LookingAtType(io::Tokenizer::TYPE_IDENTIFIER)) {
+ DO(ConsumeIdentifier(&identifier, "Expected identifier."));
+ name->mutable_name_part()->append(identifier);
+ }
+ while (LookingAt(".")) {
+ DO(Consume("."));
+ name->mutable_name_part()->append(".");
+ DO(ConsumeIdentifier(&identifier, "Expected identifier."));
+ name->mutable_name_part()->append(identifier);
+ }
+ }
+
+ DO(Consume(")"));
+ name->set_is_extension(true);
+ } else { // This is a regular field.
+ LocationRecorder location(
+ part_location, UninterpretedOption::NamePart::kNamePartFieldNumber);
+ DO(ConsumeIdentifier(&identifier, "Expected identifier."));
+ name->mutable_name_part()->append(identifier);
+ name->set_is_extension(false);
+ }
+ return true;
+}
+
+bool Parser::ParseUninterpretedBlock(string* value) {
+ // Note that enclosing braces are not added to *value.
+ // We do NOT use ConsumeEndOfStatement for this brace because it's delimiting
+ // an expression, not a block of statements.
+ DO(Consume("{"));
+ int brace_depth = 1;
+ while (!AtEnd()) {
+ if (LookingAt("{")) {
+ brace_depth++;
+ } else if (LookingAt("}")) {
+ brace_depth--;
+ if (brace_depth == 0) {
+ input_->Next();
+ return true;
+ }
+ }
+ // TODO(sanjay): Interpret line/column numbers to preserve formatting
+ if (!value->empty()) value->push_back(' ');
+ value->append(input_->current().text);
+ input_->Next();
+ }
+ AddError("Unexpected end of stream while parsing aggregate value.");
+ return false;
+}
+
+// We don't interpret the option here. Instead we store it in an
+// UninterpretedOption, to be interpreted later.
+bool Parser::ParseOption(Message* options,
+ const LocationRecorder& options_location,
+ const FileDescriptorProto* containing_file,
+ OptionStyle style) {
+ // Create an entry in the uninterpreted_option field.
+ const FieldDescriptor* uninterpreted_option_field = options->GetDescriptor()->
+ FindFieldByName("uninterpreted_option");
+ GOOGLE_CHECK(uninterpreted_option_field != NULL)
+ << "No field named \"uninterpreted_option\" in the Options proto.";
+
+ const Reflection* reflection = options->GetReflection();
+
+ LocationRecorder location(
+ options_location, uninterpreted_option_field->number(),
+ reflection->FieldSize(*options, uninterpreted_option_field));
+
+ if (style == OPTION_STATEMENT) {
+ DO(Consume("option"));
+ }
+
+ UninterpretedOption* uninterpreted_option = down_cast<UninterpretedOption*>(
+ options->GetReflection()->AddMessage(options,
+ uninterpreted_option_field));
+
+ // Parse dot-separated name.
+ {
+ LocationRecorder name_location(location,
+ UninterpretedOption::kNameFieldNumber);
+ name_location.RecordLegacyLocation(
+ uninterpreted_option, DescriptorPool::ErrorCollector::OPTION_NAME);
+
+ {
+ LocationRecorder part_location(name_location,
+ uninterpreted_option->name_size());
+ DO(ParseOptionNamePart(uninterpreted_option, part_location,
+ containing_file));
+ }
+
+ while (LookingAt(".")) {
+ DO(Consume("."));
+ LocationRecorder part_location(name_location,
+ uninterpreted_option->name_size());
+ DO(ParseOptionNamePart(uninterpreted_option, part_location,
+ containing_file));
+ }
+ }
+
+ DO(Consume("="));
+
+ {
+ LocationRecorder value_location(location);
+ value_location.RecordLegacyLocation(
+ uninterpreted_option, DescriptorPool::ErrorCollector::OPTION_VALUE);
+
+ // All values are a single token, except for negative numbers, which consist
+ // of a single '-' symbol, followed by a positive number.
+ bool is_negative = TryConsume("-");
+
+ switch (input_->current().type) {
+ case io::Tokenizer::TYPE_START:
+ GOOGLE_LOG(FATAL) << "Trying to read value before any tokens have been read.";
+ return false;
+
+ case io::Tokenizer::TYPE_END:
+ AddError("Unexpected end of stream while parsing option value.");
+ return false;
+
+ case io::Tokenizer::TYPE_IDENTIFIER: {
+ value_location.AddPath(
+ UninterpretedOption::kIdentifierValueFieldNumber);
+ if (is_negative) {
+ AddError("Invalid '-' symbol before identifier.");
+ return false;
+ }
+ string value;
+ DO(ConsumeIdentifier(&value, "Expected identifier."));
+ uninterpreted_option->set_identifier_value(value);
+ break;
+ }
+
+ case io::Tokenizer::TYPE_INTEGER: {
+ uint64 value;
+ uint64 max_value =
+ is_negative ? static_cast<uint64>(kint64max) + 1 : kuint64max;
+ DO(ConsumeInteger64(max_value, &value, "Expected integer."));
+ if (is_negative) {
+ value_location.AddPath(
+ UninterpretedOption::kNegativeIntValueFieldNumber);
+ uninterpreted_option->set_negative_int_value(
+ -static_cast<int64>(value));
+ } else {
+ value_location.AddPath(
+ UninterpretedOption::kPositiveIntValueFieldNumber);
+ uninterpreted_option->set_positive_int_value(value);
+ }
+ break;
+ }
+
+ case io::Tokenizer::TYPE_FLOAT: {
+ value_location.AddPath(UninterpretedOption::kDoubleValueFieldNumber);
+ double value;
+ DO(ConsumeNumber(&value, "Expected number."));
+ uninterpreted_option->set_double_value(is_negative ? -value : value);
+ break;
+ }
+
+ case io::Tokenizer::TYPE_STRING: {
+ value_location.AddPath(UninterpretedOption::kStringValueFieldNumber);
+ if (is_negative) {
+ AddError("Invalid '-' symbol before string.");
+ return false;
+ }
+ string value;
+ DO(ConsumeString(&value, "Expected string."));
+ uninterpreted_option->set_string_value(value);
+ break;
+ }
+
+ case io::Tokenizer::TYPE_SYMBOL:
+ if (LookingAt("{")) {
+ value_location.AddPath(
+ UninterpretedOption::kAggregateValueFieldNumber);
+ DO(ParseUninterpretedBlock(
+ uninterpreted_option->mutable_aggregate_value()));
+ } else {
+ AddError("Expected option value.");
+ return false;
+ }
+ break;
+ }
+ }
+
+ if (style == OPTION_STATEMENT) {
+ DO(ConsumeEndOfDeclaration(";", &location));
+ }
+
+ return true;
+}
+
+bool Parser::ParseExtensions(DescriptorProto* message,
+ const LocationRecorder& extensions_location,
+ const FileDescriptorProto* containing_file) {
+ // Parse the declaration.
+ DO(Consume("extensions"));
+
+ do {
+ // Note that kExtensionRangeFieldNumber was already pushed by the parent.
+ LocationRecorder location(extensions_location,
+ message->extension_range_size());
+
+ DescriptorProto::ExtensionRange* range = message->add_extension_range();
+ location.RecordLegacyLocation(
+ range, DescriptorPool::ErrorCollector::NUMBER);
+
+ int start, end;
+ io::Tokenizer::Token start_token;
+
+ {
+ LocationRecorder start_location(
+ location, DescriptorProto::ExtensionRange::kStartFieldNumber);
+ start_token = input_->current();
+ DO(ConsumeInteger(&start, "Expected field number range."));
+ }
+
+ if (TryConsume("to")) {
+ LocationRecorder end_location(
+ location, DescriptorProto::ExtensionRange::kEndFieldNumber);
+ if (TryConsume("max")) {
+ // Set to the sentinel value - 1 since we increment the value below.
+ // The actual value of the end of the range should be set with
+ // AdjustExtensionRangesWithMaxEndNumber.
+ end = kMaxExtensionRangeSentinel - 1;
+ } else {
+ DO(ConsumeInteger(&end, "Expected integer."));
+ }
+ } else {
+ LocationRecorder end_location(
+ location, DescriptorProto::ExtensionRange::kEndFieldNumber);
+ end_location.StartAt(start_token);
+ end_location.EndAt(start_token);
+ end = start;
+ }
+
+ // Users like to specify inclusive ranges, but in code we like the end
+ // number to be exclusive.
+ ++end;
+
+ range->set_start(start);
+ range->set_end(end);
+ } while (TryConsume(","));
+
+ DO(ConsumeEndOfDeclaration(";", &extensions_location));
+ return true;
+}
+
+// This is similar to extension range parsing, except that "max" is not
+// supported, and accepts field name literals.
+bool Parser::ParseReserved(DescriptorProto* message,
+ const LocationRecorder& message_location) {
+ // Parse the declaration.
+ DO(Consume("reserved"));
+ if (LookingAtType(io::Tokenizer::TYPE_STRING)) {
+ LocationRecorder location(message_location,
+ DescriptorProto::kReservedNameFieldNumber);
+ return ParseReservedNames(message, location);
+ } else {
+ LocationRecorder location(message_location,
+ DescriptorProto::kReservedRangeFieldNumber);
+ return ParseReservedNumbers(message, location);
+ }
+}
+
+
+bool Parser::ParseReservedNames(DescriptorProto* message,
+ const LocationRecorder& parent_location) {
+ do {
+ LocationRecorder location(parent_location, message->reserved_name_size());
+ DO(ConsumeString(message->add_reserved_name(), "Expected field name."));
+ } while (TryConsume(","));
+ DO(ConsumeEndOfDeclaration(";", &parent_location));
+ return true;
+}
+
+bool Parser::ParseReservedNumbers(DescriptorProto* message,
+ const LocationRecorder& parent_location) {
+ bool first = true;
+ do {
+ LocationRecorder location(parent_location, message->reserved_range_size());
+
+ DescriptorProto::ReservedRange* range = message->add_reserved_range();
+ int start, end;
+ io::Tokenizer::Token start_token;
+ {
+ LocationRecorder start_location(
+ location, DescriptorProto::ReservedRange::kStartFieldNumber);
+ start_token = input_->current();
+ DO(ConsumeInteger(&start, (first ?
+ "Expected field name or number range." :
+ "Expected field number range.")));
+ }
+
+ if (TryConsume("to")) {
+ LocationRecorder end_location(
+ location, DescriptorProto::ReservedRange::kEndFieldNumber);
+ DO(ConsumeInteger(&end, "Expected integer."));
+ } else {
+ LocationRecorder end_location(
+ location, DescriptorProto::ReservedRange::kEndFieldNumber);
+ end_location.StartAt(start_token);
+ end_location.EndAt(start_token);
+ end = start;
+ }
+
+ // Users like to specify inclusive ranges, but in code we like the end
+ // number to be exclusive.
+ ++end;
+
+ range->set_start(start);
+ range->set_end(end);
+ first = false;
+ } while (TryConsume(","));
+
+ DO(ConsumeEndOfDeclaration(";", &parent_location));
+ return true;
+}
+
+bool Parser::ParseExtend(RepeatedPtrField<FieldDescriptorProto>* extensions,
+ RepeatedPtrField<DescriptorProto>* messages,
+ const LocationRecorder& parent_location,
+ int location_field_number_for_nested_type,
+ const LocationRecorder& extend_location,
+ const FileDescriptorProto* containing_file) {
+ DO(Consume("extend"));
+
+ // Parse the extendee type.
+ io::Tokenizer::Token extendee_start = input_->current();
+ string extendee;
+ DO(ParseUserDefinedType(&extendee));
+ io::Tokenizer::Token extendee_end = input_->previous();
+
+ // Parse the block.
+ DO(ConsumeEndOfDeclaration("{", &extend_location));
+
+ bool is_first = true;
+
+ do {
+ if (AtEnd()) {
+ AddError("Reached end of input in extend definition (missing '}').");
+ return false;
+ }
+
+ // Note that kExtensionFieldNumber was already pushed by the parent.
+ LocationRecorder location(extend_location, extensions->size());
+
+ FieldDescriptorProto* field = extensions->Add();
+
+ {
+ LocationRecorder extendee_location(
+ location, FieldDescriptorProto::kExtendeeFieldNumber);
+ extendee_location.StartAt(extendee_start);
+ extendee_location.EndAt(extendee_end);
+
+ if (is_first) {
+ extendee_location.RecordLegacyLocation(
+ field, DescriptorPool::ErrorCollector::EXTENDEE);
+ is_first = false;
+ }
+ }
+
+ field->set_extendee(extendee);
+
+ if (!ParseMessageField(field, messages, parent_location,
+ location_field_number_for_nested_type,
+ location,
+ containing_file)) {
+ // This statement failed to parse. Skip it, but keep looping to parse
+ // other statements.
+ SkipStatement();
+ }
+ } while (!TryConsumeEndOfDeclaration("}", NULL));
+
+ return true;
+}
+
+bool Parser::ParseOneof(OneofDescriptorProto* oneof_decl,
+ DescriptorProto* containing_type,
+ int oneof_index,
+ const LocationRecorder& oneof_location,
+ const LocationRecorder& containing_type_location,
+ const FileDescriptorProto* containing_file) {
+ DO(Consume("oneof"));
+
+ {
+ LocationRecorder name_location(oneof_location,
+ OneofDescriptorProto::kNameFieldNumber);
+ DO(ConsumeIdentifier(oneof_decl->mutable_name(), "Expected oneof name."));
+ }
+
+ DO(ConsumeEndOfDeclaration("{", &oneof_location));
+
+ do {
+ if (AtEnd()) {
+ AddError("Reached end of input in oneof definition (missing '}').");
+ return false;
+ }
+
+ if (LookingAt("option")) {
+ LocationRecorder option_location(
+ oneof_location, OneofDescriptorProto::kOptionsFieldNumber);
+ if (!ParseOption(oneof_decl->mutable_options(), option_location,
+ containing_file, OPTION_STATEMENT)) {
+ return false;
+ }
+ continue;
+ }
+
+ // Print a nice error if the user accidentally tries to place a label
+ // on an individual member of a oneof.
+ if (LookingAt("required") ||
+ LookingAt("optional") ||
+ LookingAt("repeated")) {
+ AddError("Fields in oneofs must not have labels (required / optional "
+ "/ repeated).");
+ // We can continue parsing here because we understand what the user
+ // meant. The error report will still make parsing fail overall.
+ input_->Next();
+ }
+
+ LocationRecorder field_location(containing_type_location,
+ DescriptorProto::kFieldFieldNumber,
+ containing_type->field_size());
+
+ FieldDescriptorProto* field = containing_type->add_field();
+ field->set_label(FieldDescriptorProto::LABEL_OPTIONAL);
+ field->set_oneof_index(oneof_index);
+
+ if (!ParseMessageFieldNoLabel(field,
+ containing_type->mutable_nested_type(),
+ containing_type_location,
+ DescriptorProto::kNestedTypeFieldNumber,
+ field_location,
+ containing_file)) {
+ // This statement failed to parse. Skip it, but keep looping to parse
+ // other statements.
+ SkipStatement();
+ }
+ } while (!TryConsumeEndOfDeclaration("}", NULL));
+
+ return true;
+}
+
+// -------------------------------------------------------------------
+// Enums
+
+bool Parser::ParseEnumDefinition(EnumDescriptorProto* enum_type,
+ const LocationRecorder& enum_location,
+ const FileDescriptorProto* containing_file) {
+ DO(Consume("enum"));
+
+ {
+ LocationRecorder location(enum_location,
+ EnumDescriptorProto::kNameFieldNumber);
+ location.RecordLegacyLocation(
+ enum_type, DescriptorPool::ErrorCollector::NAME);
+ DO(ConsumeIdentifier(enum_type->mutable_name(), "Expected enum name."));
+ }
+
+ DO(ParseEnumBlock(enum_type, enum_location, containing_file));
+
+ DO(ValidateEnum(enum_type));
+
+ return true;
+}
+
+bool Parser::ParseEnumBlock(EnumDescriptorProto* enum_type,
+ const LocationRecorder& enum_location,
+ const FileDescriptorProto* containing_file) {
+ DO(ConsumeEndOfDeclaration("{", &enum_location));
+
+ while (!TryConsumeEndOfDeclaration("}", NULL)) {
+ if (AtEnd()) {
+ AddError("Reached end of input in enum definition (missing '}').");
+ return false;
+ }
+
+ if (!ParseEnumStatement(enum_type, enum_location, containing_file)) {
+ // This statement failed to parse. Skip it, but keep looping to parse
+ // other statements.
+ SkipStatement();
+ }
+ }
+
+ return true;
+}
+
+bool Parser::ParseEnumStatement(EnumDescriptorProto* enum_type,
+ const LocationRecorder& enum_location,
+ const FileDescriptorProto* containing_file) {
+ if (TryConsumeEndOfDeclaration(";", NULL)) {
+ // empty statement; ignore
+ return true;
+ } else if (LookingAt("option")) {
+ LocationRecorder location(enum_location,
+ EnumDescriptorProto::kOptionsFieldNumber);
+ return ParseOption(enum_type->mutable_options(), location,
+ containing_file, OPTION_STATEMENT);
+ } else {
+ LocationRecorder location(enum_location,
+ EnumDescriptorProto::kValueFieldNumber, enum_type->value_size());
+ return ParseEnumConstant(enum_type->add_value(), location, containing_file);
+ }
+}
+
+bool Parser::ParseEnumConstant(EnumValueDescriptorProto* enum_value,
+ const LocationRecorder& enum_value_location,
+ const FileDescriptorProto* containing_file) {
+ // Parse name.
+ {
+ LocationRecorder location(enum_value_location,
+ EnumValueDescriptorProto::kNameFieldNumber);
+ location.RecordLegacyLocation(
+ enum_value, DescriptorPool::ErrorCollector::NAME);
+ DO(ConsumeIdentifier(enum_value->mutable_name(),
+ "Expected enum constant name."));
+ }
+
+ DO(Consume("=", "Missing numeric value for enum constant."));
+
+ // Parse value.
+ {
+ LocationRecorder location(
+ enum_value_location, EnumValueDescriptorProto::kNumberFieldNumber);
+ location.RecordLegacyLocation(
+ enum_value, DescriptorPool::ErrorCollector::NUMBER);
+
+ int number;
+ DO(ConsumeSignedInteger(&number, "Expected integer."));
+ enum_value->set_number(number);
+ }
+
+ DO(ParseEnumConstantOptions(enum_value, enum_value_location,
+ containing_file));
+
+ DO(ConsumeEndOfDeclaration(";", &enum_value_location));
+
+ return true;
+}
+
+bool Parser::ParseEnumConstantOptions(
+ EnumValueDescriptorProto* value,
+ const LocationRecorder& enum_value_location,
+ const FileDescriptorProto* containing_file) {
+ if (!LookingAt("[")) return true;
+
+ LocationRecorder location(
+ enum_value_location, EnumValueDescriptorProto::kOptionsFieldNumber);
+
+ DO(Consume("["));
+
+ do {
+ DO(ParseOption(value->mutable_options(), location,
+ containing_file, OPTION_ASSIGNMENT));
+ } while (TryConsume(","));
+
+ DO(Consume("]"));
+ return true;
+}
+
+// -------------------------------------------------------------------
+// Services
+
+bool Parser::ParseServiceDefinition(
+ ServiceDescriptorProto* service,
+ const LocationRecorder& service_location,
+ const FileDescriptorProto* containing_file) {
+ DO(Consume("service"));
+
+ {
+ LocationRecorder location(service_location,
+ ServiceDescriptorProto::kNameFieldNumber);
+ location.RecordLegacyLocation(
+ service, DescriptorPool::ErrorCollector::NAME);
+ DO(ConsumeIdentifier(service->mutable_name(), "Expected service name."));
+ }
+
+ DO(ParseServiceBlock(service, service_location, containing_file));
+ return true;
+}
+
+bool Parser::ParseServiceBlock(ServiceDescriptorProto* service,
+ const LocationRecorder& service_location,
+ const FileDescriptorProto* containing_file) {
+ DO(ConsumeEndOfDeclaration("{", &service_location));
+
+ while (!TryConsumeEndOfDeclaration("}", NULL)) {
+ if (AtEnd()) {
+ AddError("Reached end of input in service definition (missing '}').");
+ return false;
+ }
+
+ if (!ParseServiceStatement(service, service_location, containing_file)) {
+ // This statement failed to parse. Skip it, but keep looping to parse
+ // other statements.
+ SkipStatement();
+ }
+ }
+
+ return true;
+}
+
+bool Parser::ParseServiceStatement(ServiceDescriptorProto* service,
+ const LocationRecorder& service_location,
+ const FileDescriptorProto* containing_file) {
+ if (TryConsumeEndOfDeclaration(";", NULL)) {
+ // empty statement; ignore
+ return true;
+ } else if (LookingAt("option")) {
+ LocationRecorder location(
+ service_location, ServiceDescriptorProto::kOptionsFieldNumber);
+ return ParseOption(service->mutable_options(), location,
+ containing_file, OPTION_STATEMENT);
+ } else {
+ LocationRecorder location(service_location,
+ ServiceDescriptorProto::kMethodFieldNumber, service->method_size());
+ return ParseServiceMethod(service->add_method(), location, containing_file);
+ }
+}
+
+bool Parser::ParseServiceMethod(MethodDescriptorProto* method,
+ const LocationRecorder& method_location,
+ const FileDescriptorProto* containing_file) {
+ DO(Consume("rpc"));
+
+ {
+ LocationRecorder location(method_location,
+ MethodDescriptorProto::kNameFieldNumber);
+ location.RecordLegacyLocation(
+ method, DescriptorPool::ErrorCollector::NAME);
+ DO(ConsumeIdentifier(method->mutable_name(), "Expected method name."));
+ }
+
+ // Parse input type.
+ DO(Consume("("));
+ {
+ if (LookingAt("stream")) {
+ LocationRecorder location(
+ method_location, MethodDescriptorProto::kClientStreamingFieldNumber);
+ location.RecordLegacyLocation(
+ method, DescriptorPool::ErrorCollector::OTHER);
+ method->set_client_streaming(true);
+ DO(Consume("stream"));
+
+ }
+ LocationRecorder location(method_location,
+ MethodDescriptorProto::kInputTypeFieldNumber);
+ location.RecordLegacyLocation(
+ method, DescriptorPool::ErrorCollector::INPUT_TYPE);
+ DO(ParseUserDefinedType(method->mutable_input_type()));
+ }
+ DO(Consume(")"));
+
+ // Parse output type.
+ DO(Consume("returns"));
+ DO(Consume("("));
+ {
+ if (LookingAt("stream")) {
+ LocationRecorder location(
+ method_location, MethodDescriptorProto::kServerStreamingFieldNumber);
+ location.RecordLegacyLocation(
+ method, DescriptorPool::ErrorCollector::OTHER);
+ DO(Consume("stream"));
+ method->set_server_streaming(true);
+
+ }
+ LocationRecorder location(method_location,
+ MethodDescriptorProto::kOutputTypeFieldNumber);
+ location.RecordLegacyLocation(
+ method, DescriptorPool::ErrorCollector::OUTPUT_TYPE);
+ DO(ParseUserDefinedType(method->mutable_output_type()));
+ }
+ DO(Consume(")"));
+
+ if (LookingAt("{")) {
+ // Options!
+ DO(ParseMethodOptions(method_location, containing_file,
+ MethodDescriptorProto::kOptionsFieldNumber,
+ method->mutable_options()));
+ } else {
+ DO(ConsumeEndOfDeclaration(";", &method_location));
+ }
+
+ return true;
+}
+
+
+bool Parser::ParseMethodOptions(const LocationRecorder& parent_location,
+ const FileDescriptorProto* containing_file,
+ const int optionsFieldNumber,
+ Message* mutable_options) {
+ // Options!
+ ConsumeEndOfDeclaration("{", &parent_location);
+ while (!TryConsumeEndOfDeclaration("}", NULL)) {
+ if (AtEnd()) {
+ AddError("Reached end of input in method options (missing '}').");
+ return false;
+ }
+
+ if (TryConsumeEndOfDeclaration(";", NULL)) {
+ // empty statement; ignore
+ } else {
+ LocationRecorder location(parent_location,
+ optionsFieldNumber);
+ if (!ParseOption(mutable_options, location,
+ containing_file, OPTION_STATEMENT)) {
+ // This statement failed to parse. Skip it, but keep looping to
+ // parse other statements.
+ SkipStatement();
+ }
+ }
+ }
+
+ return true;
+}
+
+// -------------------------------------------------------------------
+
+bool Parser::ParseLabel(FieldDescriptorProto::Label* label,
+ const FileDescriptorProto* containing_file) {
+ if (TryConsume("optional")) {
+ *label = FieldDescriptorProto::LABEL_OPTIONAL;
+ return true;
+ } else if (TryConsume("repeated")) {
+ *label = FieldDescriptorProto::LABEL_REPEATED;
+ return true;
+ } else if (TryConsume("required")) {
+ *label = FieldDescriptorProto::LABEL_REQUIRED;
+ return true;
+ }
+ return false;
+}
+
+bool Parser::ParseType(FieldDescriptorProto::Type* type,
+ string* type_name) {
+ TypeNameMap::const_iterator iter = kTypeNames.find(input_->current().text);
+ if (iter != kTypeNames.end()) {
+ *type = iter->second;
+ input_->Next();
+ } else {
+ DO(ParseUserDefinedType(type_name));
+ }
+ return true;
+}
+
+bool Parser::ParseUserDefinedType(string* type_name) {
+ type_name->clear();
+
+ TypeNameMap::const_iterator iter = kTypeNames.find(input_->current().text);
+ if (iter != kTypeNames.end()) {
+ // Note: The only place enum types are allowed is for field types, but
+ // if we are parsing a field type then we would not get here because
+ // primitives are allowed there as well. So this error message doesn't
+ // need to account for enums.
+ AddError("Expected message type.");
+
+ // Pretend to accept this type so that we can go on parsing.
+ *type_name = input_->current().text;
+ input_->Next();
+ return true;
+ }
+
+ // A leading "." means the name is fully-qualified.
+ if (TryConsume(".")) type_name->append(".");
+
+ // Consume the first part of the name.
+ string identifier;
+ DO(ConsumeIdentifier(&identifier, "Expected type name."));
+ type_name->append(identifier);
+
+ // Consume more parts.
+ while (TryConsume(".")) {
+ type_name->append(".");
+ DO(ConsumeIdentifier(&identifier, "Expected identifier."));
+ type_name->append(identifier);
+ }
+
+ return true;
+}
+
+// ===================================================================
+
+bool Parser::ParsePackage(FileDescriptorProto* file,
+ const LocationRecorder& root_location,
+ const FileDescriptorProto* containing_file) {
+ if (file->has_package()) {
+ AddError("Multiple package definitions.");
+ // Don't append the new package to the old one. Just replace it. Not
+ // that it really matters since this is an error anyway.
+ file->clear_package();
+ }
+
+ DO(Consume("package"));
+
+ {
+ LocationRecorder location(root_location,
+ FileDescriptorProto::kPackageFieldNumber);
+ location.RecordLegacyLocation(file, DescriptorPool::ErrorCollector::NAME);
+
+ while (true) {
+ string identifier;
+ DO(ConsumeIdentifier(&identifier, "Expected identifier."));
+ file->mutable_package()->append(identifier);
+ if (!TryConsume(".")) break;
+ file->mutable_package()->append(".");
+ }
+
+ location.EndAt(input_->previous());
+
+ DO(ConsumeEndOfDeclaration(";", &location));
+ }
+
+ return true;
+}
+
+bool Parser::ParseImport(RepeatedPtrField<string>* dependency,
+ RepeatedField<int32>* public_dependency,
+ RepeatedField<int32>* weak_dependency,
+ const LocationRecorder& root_location,
+ const FileDescriptorProto* containing_file) {
+ DO(Consume("import"));
+ if (LookingAt("public")) {
+ LocationRecorder location(
+ root_location, FileDescriptorProto::kPublicDependencyFieldNumber,
+ public_dependency->size());
+ DO(Consume("public"));
+ *public_dependency->Add() = dependency->size();
+ } else if (LookingAt("weak")) {
+ LocationRecorder location(
+ root_location, FileDescriptorProto::kWeakDependencyFieldNumber,
+ weak_dependency->size());
+ DO(Consume("weak"));
+ *weak_dependency->Add() = dependency->size();
+ }
+ {
+ LocationRecorder location(root_location,
+ FileDescriptorProto::kDependencyFieldNumber,
+ dependency->size());
+ DO(ConsumeString(dependency->Add(),
+ "Expected a string naming the file to import."));
+
+ location.EndAt(input_->previous());
+
+ DO(ConsumeEndOfDeclaration(";", &location));
+ }
+ return true;
+}
+
+// ===================================================================
+
+SourceLocationTable::SourceLocationTable() {}
+SourceLocationTable::~SourceLocationTable() {}
+
+bool SourceLocationTable::Find(
+ const Message* descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ int* line, int* column) const {
+ const pair<int, int>* result =
+ FindOrNull(location_map_, std::make_pair(descriptor, location));
+ if (result == NULL) {
+ *line = -1;
+ *column = 0;
+ return false;
+ } else {
+ *line = result->first;
+ *column = result->second;
+ return true;
+ }
+}
+
+void SourceLocationTable::Add(
+ const Message* descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ int line, int column) {
+ location_map_[std::make_pair(descriptor, location)] =
+ std::make_pair(line, column);
+}
+
+void SourceLocationTable::Clear() {
+ location_map_.clear();
+}
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.h
new file mode 100644
index 0000000000..0f80e78b98
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser.h
@@ -0,0 +1,569 @@
+// 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.
+//
+// Implements parsing of .proto files to FileDescriptorProtos.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_PARSER_H__
+#define GOOGLE_PROTOBUF_COMPILER_PARSER_H__
+
+#include <map>
+#include <string>
+#include <utility>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/io/tokenizer.h>
+
+namespace google {
+namespace protobuf { class Message; }
+
+namespace protobuf {
+namespace compiler {
+
+// Defined in this file.
+class Parser;
+class SourceLocationTable;
+
+// Implements parsing of protocol definitions (such as .proto files).
+//
+// Note that most users will be more interested in the Importer class.
+// Parser is a lower-level class which simply converts a single .proto file
+// to a FileDescriptorProto. It does not resolve import directives or perform
+// many other kinds of validation needed to construct a complete
+// FileDescriptor.
+class LIBPROTOBUF_EXPORT Parser {
+ public:
+ Parser();
+ ~Parser();
+
+ // Parse the entire input and construct a FileDescriptorProto representing
+ // it. Returns true if no errors occurred, false otherwise.
+ bool Parse(io::Tokenizer* input, FileDescriptorProto* file);
+
+ // Optional features:
+
+ // DEPRECATED: New code should use the SourceCodeInfo embedded in the
+ // FileDescriptorProto.
+ //
+ // Requests that locations of certain definitions be recorded to the given
+ // SourceLocationTable while parsing. This can be used to look up exact line
+ // and column numbers for errors reported by DescriptorPool during validation.
+ // Set to NULL (the default) to discard source location information.
+ void RecordSourceLocationsTo(SourceLocationTable* location_table) {
+ source_location_table_ = location_table;
+ }
+
+ // Requests that errors be recorded to the given ErrorCollector while
+ // parsing. Set to NULL (the default) to discard error messages.
+ void RecordErrorsTo(io::ErrorCollector* error_collector) {
+ error_collector_ = error_collector;
+ }
+
+ // Returns the identifier used in the "syntax = " declaration, if one was
+ // seen during the last call to Parse(), or the empty string otherwise.
+ const string& GetSyntaxIdentifier() { return syntax_identifier_; }
+
+ // If set true, input files will be required to begin with a syntax
+ // identifier. Otherwise, files may omit this. If a syntax identifier
+ // is provided, it must be 'syntax = "proto2";' and must appear at the
+ // top of this file regardless of whether or not it was required.
+ void SetRequireSyntaxIdentifier(bool value) {
+ require_syntax_identifier_ = value;
+ }
+
+ // Call SetStopAfterSyntaxIdentifier(true) to tell the parser to stop
+ // parsing as soon as it has seen the syntax identifier, or lack thereof.
+ // This is useful for quickly identifying the syntax of the file without
+ // parsing the whole thing. If this is enabled, no error will be recorded
+ // if the syntax identifier is something other than "proto2" (since
+ // presumably the caller intends to deal with that), but other kinds of
+ // errors (e.g. parse errors) will still be reported. When this is enabled,
+ // you may pass a NULL FileDescriptorProto to Parse().
+ void SetStopAfterSyntaxIdentifier(bool value) {
+ stop_after_syntax_identifier_ = value;
+ }
+
+ private:
+ class LocationRecorder;
+
+ // =================================================================
+ // Error recovery helpers
+
+ // Consume the rest of the current statement. This consumes tokens
+ // until it sees one of:
+ // ';' Consumes the token and returns.
+ // '{' Consumes the brace then calls SkipRestOfBlock().
+ // '}' Returns without consuming.
+ // EOF Returns (can't consume).
+ // The Parser often calls SkipStatement() after encountering a syntax
+ // error. This allows it to go on parsing the following lines, allowing
+ // it to report more than just one error in the file.
+ void SkipStatement();
+
+ // Consume the rest of the current block, including nested blocks,
+ // ending after the closing '}' is encountered and consumed, or at EOF.
+ void SkipRestOfBlock();
+
+ // -----------------------------------------------------------------
+ // Single-token consuming helpers
+ //
+ // These make parsing code more readable.
+
+ // True if the current token is TYPE_END.
+ inline bool AtEnd();
+
+ // True if the next token matches the given text.
+ inline bool LookingAt(const char* text);
+ // True if the next token is of the given type.
+ inline bool LookingAtType(io::Tokenizer::TokenType token_type);
+
+ // If the next token exactly matches the text given, consume it and return
+ // true. Otherwise, return false without logging an error.
+ bool TryConsume(const char* text);
+
+ // These attempt to read some kind of token from the input. If successful,
+ // they return true. Otherwise they return false and add the given error
+ // to the error list.
+
+ // Consume a token with the exact text given.
+ bool Consume(const char* text, const char* error);
+ // Same as above, but automatically generates the error "Expected \"text\".",
+ // where "text" is the expected token text.
+ bool Consume(const char* text);
+ // Consume a token of type IDENTIFIER and store its text in "output".
+ bool ConsumeIdentifier(string* output, const char* error);
+ // Consume an integer and store its value in "output".
+ bool ConsumeInteger(int* output, const char* error);
+ // Consume a signed integer and store its value in "output".
+ bool ConsumeSignedInteger(int* output, const char* error);
+ // Consume a 64-bit integer and store its value in "output". If the value
+ // is greater than max_value, an error will be reported.
+ bool ConsumeInteger64(uint64 max_value, uint64* output, const char* error);
+ // Consume a number and store its value in "output". This will accept
+ // tokens of either INTEGER or FLOAT type.
+ bool ConsumeNumber(double* output, const char* error);
+ // Consume a string literal and store its (unescaped) value in "output".
+ bool ConsumeString(string* output, const char* error);
+
+ // Consume a token representing the end of the statement. Comments between
+ // this token and the next will be harvested for documentation. The given
+ // LocationRecorder should refer to the declaration that was just parsed;
+ // it will be populated with these comments.
+ //
+ // TODO(kenton): The LocationRecorder is const because historically locations
+ // have been passed around by const reference, for no particularly good
+ // reason. We should probably go through and change them all to mutable
+ // pointer to make this more intuitive.
+ bool TryConsumeEndOfDeclaration(
+ const char* text, const LocationRecorder* location);
+ bool TryConsumeEndOfDeclarationFinishScope(
+ const char* text, const LocationRecorder* location);
+
+ bool ConsumeEndOfDeclaration(
+ const char* text, const LocationRecorder* location);
+
+ // -----------------------------------------------------------------
+ // Error logging helpers
+
+ // Invokes error_collector_->AddError(), if error_collector_ is not NULL.
+ void AddError(int line, int column, const string& error);
+
+ // Invokes error_collector_->AddError() with the line and column number
+ // of the current token.
+ void AddError(const string& error);
+
+ // Records a location in the SourceCodeInfo.location table (see
+ // descriptor.proto). We use RAII to ensure that the start and end locations
+ // are recorded -- the constructor records the start location and the
+ // destructor records the end location. Since the parser is
+ // recursive-descent, this works out beautifully.
+ class LIBPROTOBUF_EXPORT LocationRecorder {
+ public:
+ // Construct the file's "root" location.
+ LocationRecorder(Parser* parser);
+
+ // Construct a location that represents a declaration nested within the
+ // given parent. E.g. a field's location is nested within the location
+ // for a message type. The parent's path will be copied, so you should
+ // call AddPath() only to add the path components leading from the parent
+ // to the child (as opposed to leading from the root to the child).
+ LocationRecorder(const LocationRecorder& parent);
+
+ // Convenience constructors that call AddPath() one or two times.
+ LocationRecorder(const LocationRecorder& parent, int path1);
+ LocationRecorder(const LocationRecorder& parent, int path1, int path2);
+
+ ~LocationRecorder();
+
+ // Add a path component. See SourceCodeInfo.Location.path in
+ // descriptor.proto.
+ void AddPath(int path_component);
+
+ // By default the location is considered to start at the current token at
+ // the time the LocationRecorder is created. StartAt() sets the start
+ // location to the given token instead.
+ void StartAt(const io::Tokenizer::Token& token);
+
+ // Start at the same location as some other LocationRecorder.
+ void StartAt(const LocationRecorder& other);
+
+ // By default the location is considered to end at the previous token at
+ // the time the LocationRecorder is destroyed. EndAt() sets the end
+ // location to the given token instead.
+ void EndAt(const io::Tokenizer::Token& token);
+
+ // Records the start point of this location to the SourceLocationTable that
+ // was passed to RecordSourceLocationsTo(), if any. SourceLocationTable
+ // is an older way of keeping track of source locations which is still
+ // used in some places.
+ void RecordLegacyLocation(const Message* descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location);
+
+ // Attaches leading and trailing comments to the location. The two strings
+ // will be swapped into place, so after this is called *leading and
+ // *trailing will be empty.
+ //
+ // TODO(kenton): See comment on TryConsumeEndOfDeclaration(), above, for
+ // why this is const.
+ void AttachComments(string* leading, string* trailing,
+ vector<string>* detached_comments) const;
+
+ private:
+ // Indexes of parent and current location in the parent
+ // SourceCodeInfo.location repeated field. For top-level elements,
+ // parent_index_ is -1.
+ Parser* parser_;
+ SourceCodeInfo::Location* location_;
+
+ void Init(const LocationRecorder& parent);
+ };
+
+ // =================================================================
+ // Parsers for various language constructs
+
+ // Parses the "syntax = \"proto2\";" line at the top of the file. Returns
+ // false if it failed to parse or if the syntax identifier was not
+ // recognized.
+ bool ParseSyntaxIdentifier(const LocationRecorder& parent);
+
+ // These methods parse various individual bits of code. They return
+ // false if they completely fail to parse the construct. In this case,
+ // it is probably necessary to skip the rest of the statement to recover.
+ // However, if these methods return true, it does NOT mean that there
+ // were no errors; only that there were no *syntax* errors. For instance,
+ // if a service method is defined using proper syntax but uses a primitive
+ // type as its input or output, ParseMethodField() still returns true
+ // and only reports the error by calling AddError(). In practice, this
+ // makes logic much simpler for the caller.
+
+ // Parse a top-level message, enum, service, etc.
+ bool ParseTopLevelStatement(FileDescriptorProto* file,
+ const LocationRecorder& root_location);
+
+ // Parse various language high-level language construrcts.
+ bool ParseMessageDefinition(DescriptorProto* message,
+ const LocationRecorder& message_location,
+ const FileDescriptorProto* containing_file);
+ bool ParseEnumDefinition(EnumDescriptorProto* enum_type,
+ const LocationRecorder& enum_location,
+ const FileDescriptorProto* containing_file);
+ bool ParseServiceDefinition(ServiceDescriptorProto* service,
+ const LocationRecorder& service_location,
+ const FileDescriptorProto* containing_file);
+ bool ParsePackage(FileDescriptorProto* file,
+ const LocationRecorder& root_location,
+ const FileDescriptorProto* containing_file);
+ bool ParseImport(RepeatedPtrField<string>* dependency,
+ RepeatedField<int32>* public_dependency,
+ RepeatedField<int32>* weak_dependency,
+ const LocationRecorder& root_location,
+ const FileDescriptorProto* containing_file);
+
+ // These methods parse the contents of a message, enum, or service type and
+ // add them to the given object. They consume the entire block including
+ // the beginning and ending brace.
+ bool ParseMessageBlock(DescriptorProto* message,
+ const LocationRecorder& message_location,
+ const FileDescriptorProto* containing_file);
+ bool ParseEnumBlock(EnumDescriptorProto* enum_type,
+ const LocationRecorder& enum_location,
+ const FileDescriptorProto* containing_file);
+ bool ParseServiceBlock(ServiceDescriptorProto* service,
+ const LocationRecorder& service_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse one statement within a message, enum, or service block, including
+ // final semicolon.
+ bool ParseMessageStatement(DescriptorProto* message,
+ const LocationRecorder& message_location,
+ const FileDescriptorProto* containing_file);
+ bool ParseEnumStatement(EnumDescriptorProto* message,
+ const LocationRecorder& enum_location,
+ const FileDescriptorProto* containing_file);
+ bool ParseServiceStatement(ServiceDescriptorProto* message,
+ const LocationRecorder& service_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse a field of a message. If the field is a group, its type will be
+ // added to "messages".
+ //
+ // parent_location and location_field_number_for_nested_type are needed when
+ // parsing groups -- we need to generate a nested message type within the
+ // parent and record its location accordingly. Since the parent could be
+ // either a FileDescriptorProto or a DescriptorProto, we must pass in the
+ // correct field number to use.
+ bool ParseMessageField(FieldDescriptorProto* field,
+ RepeatedPtrField<DescriptorProto>* messages,
+ const LocationRecorder& parent_location,
+ int location_field_number_for_nested_type,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file);
+
+ // Like ParseMessageField() but expects the label has already been filled in
+ // by the caller.
+ bool ParseMessageFieldNoLabel(FieldDescriptorProto* field,
+ RepeatedPtrField<DescriptorProto>* messages,
+ const LocationRecorder& parent_location,
+ int location_field_number_for_nested_type,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse an "extensions" declaration.
+ bool ParseExtensions(DescriptorProto* message,
+ const LocationRecorder& extensions_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse a "reserved" declaration.
+ bool ParseReserved(DescriptorProto* message,
+ const LocationRecorder& message_location);
+ bool ParseReservedNames(DescriptorProto* message,
+ const LocationRecorder& parent_location);
+ bool ParseReservedNumbers(DescriptorProto* message,
+ const LocationRecorder& parent_location);
+
+ // Parse an "extend" declaration. (See also comments for
+ // ParseMessageField().)
+ bool ParseExtend(RepeatedPtrField<FieldDescriptorProto>* extensions,
+ RepeatedPtrField<DescriptorProto>* messages,
+ const LocationRecorder& parent_location,
+ int location_field_number_for_nested_type,
+ const LocationRecorder& extend_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse a "oneof" declaration. The caller is responsible for setting
+ // oneof_decl->label() since it will have had to parse the label before it
+ // knew it was parsing a oneof.
+ bool ParseOneof(OneofDescriptorProto* oneof_decl,
+ DescriptorProto* containing_type,
+ int oneof_index,
+ const LocationRecorder& oneof_location,
+ const LocationRecorder& containing_type_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse a single enum value within an enum block.
+ bool ParseEnumConstant(EnumValueDescriptorProto* enum_value,
+ const LocationRecorder& enum_value_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse enum constant options, i.e. the list in square brackets at the end
+ // of the enum constant value definition.
+ bool ParseEnumConstantOptions(EnumValueDescriptorProto* value,
+ const LocationRecorder& enum_value_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse a single method within a service definition.
+ bool ParseServiceMethod(MethodDescriptorProto* method,
+ const LocationRecorder& method_location,
+ const FileDescriptorProto* containing_file);
+
+
+ // Parse options of a single method or stream.
+ bool ParseMethodOptions(const LocationRecorder& parent_location,
+ const FileDescriptorProto* containing_file,
+ const int optionsFieldNumber,
+ Message* mutable_options);
+
+ // Parse "required", "optional", or "repeated" and fill in "label"
+ // with the value. Returns true if such a label is consumed.
+ bool ParseLabel(FieldDescriptorProto::Label* label,
+ const FileDescriptorProto* containing_file);
+
+ // Parse a type name and fill in "type" (if it is a primitive) or
+ // "type_name" (if it is not) with the type parsed.
+ bool ParseType(FieldDescriptorProto::Type* type,
+ string* type_name);
+ // Parse a user-defined type and fill in "type_name" with the name.
+ // If a primitive type is named, it is treated as an error.
+ bool ParseUserDefinedType(string* type_name);
+
+ // Parses field options, i.e. the stuff in square brackets at the end
+ // of a field definition. Also parses default value.
+ bool ParseFieldOptions(FieldDescriptorProto* field,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parse the "default" option. This needs special handling because its
+ // type is the field's type.
+ bool ParseDefaultAssignment(FieldDescriptorProto* field,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file);
+
+ bool ParseJsonName(FieldDescriptorProto* field,
+ const LocationRecorder& field_location,
+ const FileDescriptorProto* containing_file);
+
+ enum OptionStyle {
+ OPTION_ASSIGNMENT, // just "name = value"
+ OPTION_STATEMENT // "option name = value;"
+ };
+
+ // Parse a single option name/value pair, e.g. "ctype = CORD". The name
+ // identifies a field of the given Message, and the value of that field
+ // is set to the parsed value.
+ bool ParseOption(Message* options,
+ const LocationRecorder& options_location,
+ const FileDescriptorProto* containing_file,
+ OptionStyle style);
+
+ // Parses a single part of a multipart option name. A multipart name consists
+ // of names separated by dots. Each name is either an identifier or a series
+ // of identifiers separated by dots and enclosed in parentheses. E.g.,
+ // "foo.(bar.baz).qux".
+ bool ParseOptionNamePart(UninterpretedOption* uninterpreted_option,
+ const LocationRecorder& part_location,
+ const FileDescriptorProto* containing_file);
+
+ // Parses a string surrounded by balanced braces. Strips off the outer
+ // braces and stores the enclosed string in *value.
+ // E.g.,
+ // { foo } *value gets 'foo'
+ // { foo { bar: box } } *value gets 'foo { bar: box }'
+ // {} *value gets ''
+ //
+ // REQUIRES: LookingAt("{")
+ // When finished successfully, we are looking at the first token past
+ // the ending brace.
+ bool ParseUninterpretedBlock(string* value);
+
+ struct MapField {
+ // Whether the field is a map field.
+ bool is_map_field;
+ // The types of the key and value if they are primitive types.
+ FieldDescriptorProto::Type key_type;
+ FieldDescriptorProto::Type value_type;
+ // Or the type names string if the types are customized types.
+ string key_type_name;
+ string value_type_name;
+
+ MapField() : is_map_field(false) {}
+ };
+ // Desugar the map syntax to generate a nested map entry message.
+ void GenerateMapEntry(const MapField& map_field, FieldDescriptorProto* field,
+ RepeatedPtrField<DescriptorProto>* messages);
+
+ // Whether fields without label default to optional fields.
+ bool DefaultToOptionalFields() const {
+ return syntax_identifier_ == "proto3";
+ }
+
+
+ bool ValidateEnum(const EnumDescriptorProto* proto);
+
+ // =================================================================
+
+ io::Tokenizer* input_;
+ io::ErrorCollector* error_collector_;
+ SourceCodeInfo* source_code_info_;
+ SourceLocationTable* source_location_table_; // legacy
+ bool had_errors_;
+ bool require_syntax_identifier_;
+ bool stop_after_syntax_identifier_;
+ string syntax_identifier_;
+
+ // Leading doc comments for the next declaration. These are not complete
+ // yet; use ConsumeEndOfDeclaration() to get the complete comments.
+ string upcoming_doc_comments_;
+
+ // Detached comments are not connected to any syntax entities. Elements in
+ // this vector are paragraphs of comments separated by empty lines. The
+ // detached comments will be put into the leading_detached_comments field for
+ // the next element (See SourceCodeInfo.Location in descriptor.proto), when
+ // ConsumeEndOfDeclaration() is called.
+ vector<string> upcoming_detached_comments_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Parser);
+};
+
+// A table mapping (descriptor, ErrorLocation) pairs -- as reported by
+// DescriptorPool when validating descriptors -- to line and column numbers
+// within the original source code.
+//
+// This is semi-obsolete: FileDescriptorProto.source_code_info now contains
+// far more complete information about source locations. However, as of this
+// writing you still need to use SourceLocationTable when integrating with
+// DescriptorPool.
+class LIBPROTOBUF_EXPORT SourceLocationTable {
+ public:
+ SourceLocationTable();
+ ~SourceLocationTable();
+
+ // Finds the precise location of the given error and fills in *line and
+ // *column with the line and column numbers. If not found, sets *line to
+ // -1 and *column to 0 (since line = -1 is used to mean "error has no exact
+ // location" in the ErrorCollector interface). Returns true if found, false
+ // otherwise.
+ bool Find(const Message* descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ int* line, int* column) const;
+
+ // Adds a location to the table.
+ void Add(const Message* descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ int line, int column);
+
+ // Clears the contents of the table.
+ void Clear();
+
+ private:
+ typedef map<
+ pair<const Message*, DescriptorPool::ErrorCollector::ErrorLocation>,
+ pair<int, int> > LocationMap;
+ LocationMap location_map_;
+};
+
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_PARSER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser_unittest.cc
new file mode 100644
index 0000000000..1d623dd90b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/parser_unittest.cc
@@ -0,0 +1,3157 @@
+// 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.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+#include <algorithm>
+#include <map>
+
+#include <google/protobuf/compiler/parser.h>
+
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_custom_options.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/stubs/map_util.h>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+namespace {
+
+class MockErrorCollector : public io::ErrorCollector {
+ public:
+ MockErrorCollector() {}
+ ~MockErrorCollector() {}
+
+ string text_;
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(int line, int column, const string& message) {
+ strings::SubstituteAndAppend(&text_, "$0:$1: $2\n",
+ line, column, message);
+ }
+};
+
+class MockValidationErrorCollector : public DescriptorPool::ErrorCollector {
+ public:
+ MockValidationErrorCollector(const SourceLocationTable& source_locations,
+ io::ErrorCollector* wrapped_collector)
+ : source_locations_(source_locations),
+ wrapped_collector_(wrapped_collector) {}
+ ~MockValidationErrorCollector() {}
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(const string& filename,
+ const string& element_name,
+ const Message* descriptor,
+ ErrorLocation location,
+ const string& message) {
+ int line, column;
+ source_locations_.Find(descriptor, location, &line, &column);
+ wrapped_collector_->AddError(line, column, message);
+ }
+
+ private:
+ const SourceLocationTable& source_locations_;
+ io::ErrorCollector* wrapped_collector_;
+};
+
+class ParserTest : public testing::Test {
+ protected:
+ ParserTest()
+ : require_syntax_identifier_(false) {}
+
+ // Set up the parser to parse the given text.
+ void SetupParser(const char* text) {
+ raw_input_.reset(new io::ArrayInputStream(text, strlen(text)));
+ input_.reset(new io::Tokenizer(raw_input_.get(), &error_collector_));
+ parser_.reset(new Parser());
+ parser_->RecordErrorsTo(&error_collector_);
+ parser_->SetRequireSyntaxIdentifier(require_syntax_identifier_);
+ }
+
+ // Parse the input and expect that the resulting FileDescriptorProto matches
+ // the given output. The output is a FileDescriptorProto in protocol buffer
+ // text format.
+ void ExpectParsesTo(const char* input, const char* output) {
+ SetupParser(input);
+ FileDescriptorProto actual, expected;
+
+ parser_->Parse(input_.get(), &actual);
+ EXPECT_EQ(io::Tokenizer::TYPE_END, input_->current().type);
+ ASSERT_EQ("", error_collector_.text_);
+
+ // We don't cover SourceCodeInfo in these tests.
+ actual.clear_source_code_info();
+
+ // Parse the ASCII representation in order to canonicalize it. We could
+ // just compare directly to actual.DebugString(), but that would require
+ // that the caller precisely match the formatting that DebugString()
+ // produces.
+ ASSERT_TRUE(TextFormat::ParseFromString(output, &expected));
+
+ // Compare by comparing debug strings.
+ // TODO(kenton): Use differencer, once it is available.
+ EXPECT_EQ(expected.DebugString(), actual.DebugString());
+ }
+
+ // Parse the text and expect that the given errors are reported.
+ void ExpectHasErrors(const char* text, const char* expected_errors) {
+ ExpectHasEarlyExitErrors(text, expected_errors);
+ EXPECT_EQ(io::Tokenizer::TYPE_END, input_->current().type);
+ }
+
+ // Same as above but does not expect that the parser parses the complete
+ // input.
+ void ExpectHasEarlyExitErrors(const char* text, const char* expected_errors) {
+ SetupParser(text);
+ FileDescriptorProto file;
+ parser_->Parse(input_.get(), &file);
+ EXPECT_EQ(expected_errors, error_collector_.text_);
+ }
+
+ // Parse the text as a file and validate it (with a DescriptorPool), and
+ // expect that the validation step reports the given errors.
+ void ExpectHasValidationErrors(const char* text,
+ const char* expected_errors) {
+ SetupParser(text);
+ SourceLocationTable source_locations;
+ parser_->RecordSourceLocationsTo(&source_locations);
+
+ FileDescriptorProto file;
+ file.set_name("foo.proto");
+ parser_->Parse(input_.get(), &file);
+ EXPECT_EQ(io::Tokenizer::TYPE_END, input_->current().type);
+ ASSERT_EQ("", error_collector_.text_);
+
+ MockValidationErrorCollector validation_error_collector(
+ source_locations, &error_collector_);
+ EXPECT_TRUE(pool_.BuildFileCollectingErrors(
+ file, &validation_error_collector) == NULL);
+ EXPECT_EQ(expected_errors, error_collector_.text_);
+ }
+
+ MockErrorCollector error_collector_;
+ DescriptorPool pool_;
+
+ google::protobuf::scoped_ptr<io::ZeroCopyInputStream> raw_input_;
+ google::protobuf::scoped_ptr<io::Tokenizer> input_;
+ google::protobuf::scoped_ptr<Parser> parser_;
+ bool require_syntax_identifier_;
+};
+
+// ===================================================================
+
+TEST_F(ParserTest, StopAfterSyntaxIdentifier) {
+ SetupParser(
+ "// blah\n"
+ "syntax = \"foobar\";\n"
+ "this line will not be parsed\n");
+ parser_->SetStopAfterSyntaxIdentifier(true);
+ EXPECT_TRUE(parser_->Parse(input_.get(), NULL));
+ EXPECT_EQ("", error_collector_.text_);
+ EXPECT_EQ("foobar", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParserTest, StopAfterOmittedSyntaxIdentifier) {
+ SetupParser(
+ "// blah\n"
+ "this line will not be parsed\n");
+ parser_->SetStopAfterSyntaxIdentifier(true);
+ EXPECT_TRUE(parser_->Parse(input_.get(), NULL));
+ EXPECT_EQ("", error_collector_.text_);
+ EXPECT_EQ("", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParserTest, StopAfterSyntaxIdentifierWithErrors) {
+ SetupParser(
+ "// blah\n"
+ "syntax = error;\n");
+ parser_->SetStopAfterSyntaxIdentifier(true);
+ EXPECT_FALSE(parser_->Parse(input_.get(), NULL));
+ EXPECT_EQ("1:9: Expected syntax identifier.\n", error_collector_.text_);
+}
+
+TEST_F(ParserTest, WarnIfSyntaxIdentifierOmmitted) {
+ SetupParser("message A {}");
+ FileDescriptorProto file;
+ CaptureTestStderr();
+ EXPECT_TRUE(parser_->Parse(input_.get(), &file));
+ EXPECT_TRUE(
+ GetCapturedTestStderr().find("No syntax specified") != string::npos);
+}
+
+// ===================================================================
+
+typedef ParserTest ParseMessageTest;
+
+TEST_F(ParseMessageTest, IgnoreBOM) {
+ char input[] = " message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ "}\n";
+ // Set UTF-8 BOM.
+ input[0] = (char)0xEF;
+ input[1] = (char)0xBB;
+ input[2] = (char)0xBF;
+ ExpectParsesTo(input,
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:1 }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, BOMError) {
+ char input[] = " message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ "}\n";
+ input[0] = (char)0xEF;
+ ExpectHasErrors(input,
+ "0:1: Proto file starts with 0xEF but not UTF-8 BOM. "
+ "Only UTF-8 is accepted for proto file.\n"
+ "0:0: Expected top-level statement (e.g. \"message\").\n");
+}
+
+TEST_F(ParseMessageTest, SimpleMessage) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:1 }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, ImplicitSyntaxIdentifier) {
+ require_syntax_identifier_ = false;
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:1 }"
+ "}");
+ EXPECT_EQ("proto2", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParseMessageTest, ExplicitSyntaxIdentifier) {
+ ExpectParsesTo(
+ "syntax = \"proto2\";\n"
+ "message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ "}\n",
+
+ "syntax: 'proto2' "
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:1 }"
+ "}");
+ EXPECT_EQ("proto2", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParseMessageTest, ExplicitRequiredSyntaxIdentifier) {
+ require_syntax_identifier_ = true;
+ ExpectParsesTo(
+ "syntax = \"proto2\";\n"
+ "message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ "}\n",
+
+ "syntax: 'proto2' "
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:1 }"
+ "}");
+ EXPECT_EQ("proto2", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParseMessageTest, SimpleFields) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " required int32 foo = 15;\n"
+ " optional int32 bar = 34;\n"
+ " repeated int32 baz = 3;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:15 }"
+ " field { name:\"bar\" label:LABEL_OPTIONAL type:TYPE_INT32 number:34 }"
+ " field { name:\"baz\" label:LABEL_REPEATED type:TYPE_INT32 number:3 }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, PrimitiveFieldTypes) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ " required int64 foo = 1;\n"
+ " required uint32 foo = 1;\n"
+ " required uint64 foo = 1;\n"
+ " required sint32 foo = 1;\n"
+ " required sint64 foo = 1;\n"
+ " required fixed32 foo = 1;\n"
+ " required fixed64 foo = 1;\n"
+ " required sfixed32 foo = 1;\n"
+ " required sfixed64 foo = 1;\n"
+ " required float foo = 1;\n"
+ " required double foo = 1;\n"
+ " required string foo = 1;\n"
+ " required bytes foo = 1;\n"
+ " required bool foo = 1;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT64 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_UINT32 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_UINT64 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_SINT32 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_SINT64 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_FIXED32 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_FIXED64 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_SFIXED32 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_SFIXED64 number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_FLOAT number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_DOUBLE number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_STRING number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_BYTES number:1 }"
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_BOOL number:1 }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, FieldDefaults) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " required int32 foo = 1 [default= 1 ];\n"
+ " required int32 foo = 1 [default= -2 ];\n"
+ " required int64 foo = 1 [default= 3 ];\n"
+ " required int64 foo = 1 [default= -4 ];\n"
+ " required uint32 foo = 1 [default= 5 ];\n"
+ " required uint64 foo = 1 [default= 6 ];\n"
+ " required float foo = 1 [default= 7.5];\n"
+ " required float foo = 1 [default= -8.5];\n"
+ " required float foo = 1 [default= 9 ];\n"
+ " required double foo = 1 [default= 10.5];\n"
+ " required double foo = 1 [default=-11.5];\n"
+ " required double foo = 1 [default= 12 ];\n"
+ " required double foo = 1 [default= inf ];\n"
+ " required double foo = 1 [default=-inf ];\n"
+ " required double foo = 1 [default= nan ];\n"
+ " required string foo = 1 [default='13\\001'];\n"
+ " required string foo = 1 [default='a' \"b\" \n \"c\"];\n"
+ " required bytes foo = 1 [default='14\\002'];\n"
+ " required bytes foo = 1 [default='a' \"b\" \n 'c'];\n"
+ " required bool foo = 1 [default=true ];\n"
+ " required Foo foo = 1 [default=FOO ];\n"
+
+ " required int32 foo = 1 [default= 0x7FFFFFFF];\n"
+ " required int32 foo = 1 [default=-0x80000000];\n"
+ " required uint32 foo = 1 [default= 0xFFFFFFFF];\n"
+ " required int64 foo = 1 [default= 0x7FFFFFFFFFFFFFFF];\n"
+ " required int64 foo = 1 [default=-0x8000000000000000];\n"
+ " required uint64 foo = 1 [default= 0xFFFFFFFFFFFFFFFF];\n"
+ " required double foo = 1 [default= 0xabcd];\n"
+ "}\n",
+
+#define ETC "name:\"foo\" label:LABEL_REQUIRED number:1"
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { type:TYPE_INT32 default_value:\"1\" " ETC " }"
+ " field { type:TYPE_INT32 default_value:\"-2\" " ETC " }"
+ " field { type:TYPE_INT64 default_value:\"3\" " ETC " }"
+ " field { type:TYPE_INT64 default_value:\"-4\" " ETC " }"
+ " field { type:TYPE_UINT32 default_value:\"5\" " ETC " }"
+ " field { type:TYPE_UINT64 default_value:\"6\" " ETC " }"
+ " field { type:TYPE_FLOAT default_value:\"7.5\" " ETC " }"
+ " field { type:TYPE_FLOAT default_value:\"-8.5\" " ETC " }"
+ " field { type:TYPE_FLOAT default_value:\"9\" " ETC " }"
+ " field { type:TYPE_DOUBLE default_value:\"10.5\" " ETC " }"
+ " field { type:TYPE_DOUBLE default_value:\"-11.5\" " ETC " }"
+ " field { type:TYPE_DOUBLE default_value:\"12\" " ETC " }"
+ " field { type:TYPE_DOUBLE default_value:\"inf\" " ETC " }"
+ " field { type:TYPE_DOUBLE default_value:\"-inf\" " ETC " }"
+ " field { type:TYPE_DOUBLE default_value:\"nan\" " ETC " }"
+ " field { type:TYPE_STRING default_value:\"13\\001\" " ETC " }"
+ " field { type:TYPE_STRING default_value:\"abc\" " ETC " }"
+ " field { type:TYPE_BYTES default_value:\"14\\\\002\" " ETC " }"
+ " field { type:TYPE_BYTES default_value:\"abc\" " ETC " }"
+ " field { type:TYPE_BOOL default_value:\"true\" " ETC " }"
+ " field { type_name:\"Foo\" default_value:\"FOO\" " ETC " }"
+
+ " field {"
+ " type:TYPE_INT32 default_value:\"2147483647\" " ETC
+ " }"
+ " field {"
+ " type:TYPE_INT32 default_value:\"-2147483648\" " ETC
+ " }"
+ " field {"
+ " type:TYPE_UINT32 default_value:\"4294967295\" " ETC
+ " }"
+ " field {"
+ " type:TYPE_INT64 default_value:\"9223372036854775807\" " ETC
+ " }"
+ " field {"
+ " type:TYPE_INT64 default_value:\"-9223372036854775808\" " ETC
+ " }"
+ " field {"
+ " type:TYPE_UINT64 default_value:\"18446744073709551615\" " ETC
+ " }"
+ " field {"
+ " type:TYPE_DOUBLE default_value:\"43981\" " ETC
+ " }"
+ "}");
+#undef ETC
+}
+
+TEST_F(ParseMessageTest, FieldJsonName) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " optional string foo = 1 [json_name = \"@type\"];\n"
+ "}\n",
+ "message_type {"
+ " name: \"TestMessage\""
+ " field {\n"
+ " name: \"foo\" label: LABEL_OPTIONAL type: TYPE_STRING number: 1"
+ " json_name: \"@type\"\n"
+ " }\n"
+ "}\n");
+}
+
+TEST_F(ParseMessageTest, FieldOptions) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " optional string foo = 1\n"
+ " [ctype=CORD, (foo)=7, foo.(.bar.baz).qux.quux.(corge)=-33, \n"
+ " (quux)=\"x\040y\", (baz.qux)=hey];\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name: \"foo\" label: LABEL_OPTIONAL type: TYPE_STRING number: 1"
+ " options { uninterpreted_option: { name { name_part: \"ctype\" "
+ " is_extension: false } "
+ " identifier_value: \"CORD\" }"
+ " uninterpreted_option: { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " positive_int_value: 7 }"
+ " uninterpreted_option: { name { name_part: \"foo\" "
+ " is_extension: false } "
+ " name { name_part: \".bar.baz\""
+ " is_extension: true } "
+ " name { name_part: \"qux\" "
+ " is_extension: false } "
+ " name { name_part: \"quux\" "
+ " is_extension: false } "
+ " name { name_part: \"corge\" "
+ " is_extension: true } "
+ " negative_int_value: -33 }"
+ " uninterpreted_option: { name { name_part: \"quux\" "
+ " is_extension: true } "
+ " string_value: \"x y\" }"
+ " uninterpreted_option: { name { name_part: \"baz.qux\" "
+ " is_extension: true } "
+ " identifier_value: \"hey\" }"
+ " }"
+ " }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, Oneof) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " oneof foo {\n"
+ " int32 a = 1;\n"
+ " string b = 2;\n"
+ " TestMessage c = 3;\n"
+ " group D = 4 { optional int32 i = 5; }\n"
+ " }\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"a\" label:LABEL_OPTIONAL type:TYPE_INT32 number:1 "
+ " oneof_index:0 }"
+ " field { name:\"b\" label:LABEL_OPTIONAL type:TYPE_STRING number:2 "
+ " oneof_index:0 }"
+ " field { name:\"c\" label:LABEL_OPTIONAL type_name:\"TestMessage\" "
+ " number:3 oneof_index:0 }"
+ " field { name:\"d\" label:LABEL_OPTIONAL type:TYPE_GROUP "
+ " type_name:\"D\" number:4 oneof_index:0 }"
+ " oneof_decl {"
+ " name: \"foo\""
+ " }"
+ " nested_type {"
+ " name: \"D\""
+ " field { name:\"i\" label:LABEL_OPTIONAL type:TYPE_INT32 number:5 }"
+ " }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, MultipleOneofs) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " oneof foo {\n"
+ " int32 a = 1;\n"
+ " string b = 2;\n"
+ " }\n"
+ " oneof bar {\n"
+ " int32 c = 3;\n"
+ " string d = 4;\n"
+ " }\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"a\" label:LABEL_OPTIONAL type:TYPE_INT32 number:1 "
+ " oneof_index:0 }"
+ " field { name:\"b\" label:LABEL_OPTIONAL type:TYPE_STRING number:2 "
+ " oneof_index:0 }"
+ " field { name:\"c\" label:LABEL_OPTIONAL type:TYPE_INT32 number:3 "
+ " oneof_index:1 }"
+ " field { name:\"d\" label:LABEL_OPTIONAL type:TYPE_STRING number:4 "
+ " oneof_index:1 }"
+ " oneof_decl {"
+ " name: \"foo\""
+ " }"
+ " oneof_decl {"
+ " name: \"bar\""
+ " }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, Maps) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " map<int32, string> primitive_type_map = 1;\n"
+ " map<KeyType, ValueType> composite_type_map = 2;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " nested_type {"
+ " name: \"PrimitiveTypeMapEntry\""
+ " field { "
+ " name: \"key\" number: 1 label:LABEL_OPTIONAL"
+ " type:TYPE_INT32"
+ " }"
+ " field { "
+ " name: \"value\" number: 2 label:LABEL_OPTIONAL"
+ " type:TYPE_STRING"
+ " }"
+ " options { map_entry: true }"
+ " }"
+ " nested_type {"
+ " name: \"CompositeTypeMapEntry\""
+ " field { "
+ " name: \"key\" number: 1 label:LABEL_OPTIONAL"
+ " type_name: \"KeyType\""
+ " }"
+ " field { "
+ " name: \"value\" number: 2 label:LABEL_OPTIONAL"
+ " type_name: \"ValueType\""
+ " }"
+ " options { map_entry: true }"
+ " }"
+ " field {"
+ " name: \"primitive_type_map\""
+ " label: LABEL_REPEATED"
+ " type_name: \"PrimitiveTypeMapEntry\""
+ " number: 1"
+ " }"
+ " field {"
+ " name: \"composite_type_map\""
+ " label: LABEL_REPEATED"
+ " type_name: \"CompositeTypeMapEntry\""
+ " number: 2"
+ " }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, Group) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " optional group TestGroup = 1 {};\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " nested_type { name: \"TestGroup\" }"
+ " field { name:\"testgroup\" label:LABEL_OPTIONAL number:1"
+ " type:TYPE_GROUP type_name: \"TestGroup\" }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, NestedMessage) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " message Nested {}\n"
+ " optional Nested test_nested = 1;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " nested_type { name: \"Nested\" }"
+ " field { name:\"test_nested\" label:LABEL_OPTIONAL number:1"
+ " type_name: \"Nested\" }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, NestedEnum) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " enum NestedEnum {}\n"
+ " optional NestedEnum test_enum = 1;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " enum_type { name: \"NestedEnum\" }"
+ " field { name:\"test_enum\" label:LABEL_OPTIONAL number:1"
+ " type_name: \"NestedEnum\" }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, ReservedRange) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " required int32 foo = 1;\n"
+ " reserved 2, 15, 9 to 11, 3;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_REQUIRED type:TYPE_INT32 number:1 }"
+ " reserved_range { start:2 end:3 }"
+ " reserved_range { start:15 end:16 }"
+ " reserved_range { start:9 end:12 }"
+ " reserved_range { start:3 end:4 }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, ReservedNames) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " reserved \"foo\", \"bar\";\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " reserved_name: \"foo\""
+ " reserved_name: \"bar\""
+ "}");
+}
+
+TEST_F(ParseMessageTest, ExtensionRange) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " extensions 10 to 19;\n"
+ " extensions 30 to max;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " extension_range { start:10 end:20 }"
+ " extension_range { start:30 end:536870912 }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, CompoundExtensionRange) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " extensions 2, 15, 9 to 11, 100 to max, 3;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " extension_range { start:2 end:3 }"
+ " extension_range { start:15 end:16 }"
+ " extension_range { start:9 end:12 }"
+ " extension_range { start:100 end:536870912 }"
+ " extension_range { start:3 end:4 }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, LargerMaxForMessageSetWireFormatMessages) {
+ // Messages using the message_set_wire_format option can accept larger
+ // extension numbers, as the numbers are not encoded as int32 field values
+ // rather than tags.
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " extensions 4 to max;\n"
+ " option message_set_wire_format = true;\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " extension_range { start:4 end: 0x7fffffff }"
+ " options {\n"
+ " uninterpreted_option { \n"
+ " name {\n"
+ " name_part: \"message_set_wire_format\"\n"
+ " is_extension: false\n"
+ " }\n"
+ " identifier_value: \"true\"\n"
+ " }\n"
+ " }\n"
+ "}");
+}
+
+TEST_F(ParseMessageTest, Extensions) {
+ ExpectParsesTo(
+ "extend Extendee1 { optional int32 foo = 12; }\n"
+ "extend Extendee2 { repeated TestMessage bar = 22; }\n",
+
+ "extension { name:\"foo\" label:LABEL_OPTIONAL type:TYPE_INT32 number:12"
+ " extendee: \"Extendee1\" } "
+ "extension { name:\"bar\" label:LABEL_REPEATED number:22"
+ " type_name:\"TestMessage\" extendee: \"Extendee2\" }");
+}
+
+TEST_F(ParseMessageTest, ExtensionsInMessageScope) {
+ ExpectParsesTo(
+ "message TestMessage {\n"
+ " extend Extendee1 { optional int32 foo = 12; }\n"
+ " extend Extendee2 { repeated TestMessage bar = 22; }\n"
+ "}\n",
+
+ "message_type {"
+ " name: \"TestMessage\""
+ " extension { name:\"foo\" label:LABEL_OPTIONAL type:TYPE_INT32 number:12"
+ " extendee: \"Extendee1\" }"
+ " extension { name:\"bar\" label:LABEL_REPEATED number:22"
+ " type_name:\"TestMessage\" extendee: \"Extendee2\" }"
+ "}");
+}
+
+TEST_F(ParseMessageTest, MultipleExtensionsOneExtendee) {
+ ExpectParsesTo(
+ "extend Extendee1 {\n"
+ " optional int32 foo = 12;\n"
+ " repeated TestMessage bar = 22;\n"
+ "}\n",
+
+ "extension { name:\"foo\" label:LABEL_OPTIONAL type:TYPE_INT32 number:12"
+ " extendee: \"Extendee1\" } "
+ "extension { name:\"bar\" label:LABEL_REPEATED number:22"
+ " type_name:\"TestMessage\" extendee: \"Extendee1\" }");
+}
+
+TEST_F(ParseMessageTest, OptionalLabelProto3) {
+ ExpectParsesTo(
+ "syntax = \"proto3\";\n"
+ "message TestMessage {\n"
+ " int32 foo = 1;\n"
+ "}\n",
+
+ "syntax: \"proto3\" "
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_OPTIONAL type:TYPE_INT32 number:1 } }");
+}
+
+// ===================================================================
+
+typedef ParserTest ParseEnumTest;
+
+TEST_F(ParseEnumTest, SimpleEnum) {
+ ExpectParsesTo(
+ "enum TestEnum {\n"
+ " FOO = 0;\n"
+ "}\n",
+
+ "enum_type {"
+ " name: \"TestEnum\""
+ " value { name:\"FOO\" number:0 }"
+ "}");
+}
+
+TEST_F(ParseEnumTest, Values) {
+ ExpectParsesTo(
+ "enum TestEnum {\n"
+ " FOO = 13;\n"
+ " BAR = -10;\n"
+ " BAZ = 500;\n"
+ " HEX_MAX = 0x7FFFFFFF;\n"
+ " HEX_MIN = -0x80000000;\n"
+ " INT_MAX = 2147483647;\n"
+ " INT_MIN = -2147483648;\n"
+ "}\n",
+
+ "enum_type {"
+ " name: \"TestEnum\""
+ " value { name:\"FOO\" number:13 }"
+ " value { name:\"BAR\" number:-10 }"
+ " value { name:\"BAZ\" number:500 }"
+ " value { name:\"HEX_MAX\" number:2147483647 }"
+ " value { name:\"HEX_MIN\" number:-2147483648 }"
+ " value { name:\"INT_MAX\" number:2147483647 }"
+ " value { name:\"INT_MIN\" number:-2147483648 }"
+ "}");
+}
+
+TEST_F(ParseEnumTest, ValueOptions) {
+ ExpectParsesTo(
+ "enum TestEnum {\n"
+ " FOO = 13;\n"
+ " BAR = -10 [ (something.text) = 'abc' ];\n"
+ " BAZ = 500 [ (something.text) = 'def', other = 1 ];\n"
+ "}\n",
+
+ "enum_type {"
+ " name: \"TestEnum\""
+ " value { name: \"FOO\" number: 13 }"
+ " value { name: \"BAR\" number: -10 "
+ " options { "
+ " uninterpreted_option { "
+ " name { name_part: \"something.text\" is_extension: true } "
+ " string_value: \"abc\" "
+ " } "
+ " } "
+ " } "
+ " value { name: \"BAZ\" number: 500 "
+ " options { "
+ " uninterpreted_option { "
+ " name { name_part: \"something.text\" is_extension: true } "
+ " string_value: \"def\" "
+ " } "
+ " uninterpreted_option { "
+ " name { name_part: \"other\" is_extension: false } "
+ " positive_int_value: 1 "
+ " } "
+ " } "
+ " } "
+ "}");
+}
+
+// ===================================================================
+
+typedef ParserTest ParseServiceTest;
+
+TEST_F(ParseServiceTest, SimpleService) {
+ ExpectParsesTo(
+ "service TestService {\n"
+ " rpc Foo(In) returns (Out);\n"
+ "}\n",
+
+ "service {"
+ " name: \"TestService\""
+ " method { name:\"Foo\" input_type:\"In\" output_type:\"Out\" }"
+ "}");
+}
+
+TEST_F(ParseServiceTest, MethodsAndStreams) {
+ ExpectParsesTo(
+ "service TestService {\n"
+ " rpc Foo(In1) returns (Out1);\n"
+ " rpc Bar(In2) returns (Out2);\n"
+ " rpc Baz(In3) returns (Out3);\n"
+ "}\n",
+
+ "service {"
+ " name: \"TestService\""
+ " method { name:\"Foo\" input_type:\"In1\" output_type:\"Out1\" }"
+ " method { name:\"Bar\" input_type:\"In2\" output_type:\"Out2\" }"
+ " method { name:\"Baz\" input_type:\"In3\" output_type:\"Out3\" }"
+ "}");
+}
+
+
+
+// ===================================================================
+// imports and packages
+
+typedef ParserTest ParseMiscTest;
+
+TEST_F(ParseMiscTest, ParseImport) {
+ ExpectParsesTo(
+ "import \"foo/bar/baz.proto\";\n",
+ "dependency: \"foo/bar/baz.proto\"");
+}
+
+TEST_F(ParseMiscTest, ParseMultipleImports) {
+ ExpectParsesTo(
+ "import \"foo.proto\";\n"
+ "import \"bar.proto\";\n"
+ "import \"baz.proto\";\n",
+ "dependency: \"foo.proto\""
+ "dependency: \"bar.proto\""
+ "dependency: \"baz.proto\"");
+}
+
+TEST_F(ParseMiscTest, ParsePublicImports) {
+ ExpectParsesTo(
+ "import \"foo.proto\";\n"
+ "import public \"bar.proto\";\n"
+ "import \"baz.proto\";\n"
+ "import public \"qux.proto\";\n",
+ "dependency: \"foo.proto\""
+ "dependency: \"bar.proto\""
+ "dependency: \"baz.proto\""
+ "dependency: \"qux.proto\""
+ "public_dependency: 1 "
+ "public_dependency: 3 ");
+}
+
+TEST_F(ParseMiscTest, ParsePackage) {
+ ExpectParsesTo(
+ "package foo.bar.baz;\n",
+ "package: \"foo.bar.baz\"");
+}
+
+TEST_F(ParseMiscTest, ParsePackageWithSpaces) {
+ ExpectParsesTo(
+ "package foo . bar. \n"
+ " baz;\n",
+ "package: \"foo.bar.baz\"");
+}
+
+// ===================================================================
+// options
+
+TEST_F(ParseMiscTest, ParseFileOptions) {
+ ExpectParsesTo(
+ "option java_package = \"com.google.foo\";\n"
+ "option optimize_for = CODE_SIZE;",
+
+ "options {"
+ "uninterpreted_option { name { name_part: \"java_package\" "
+ " is_extension: false }"
+ " string_value: \"com.google.foo\"} "
+ "uninterpreted_option { name { name_part: \"optimize_for\" "
+ " is_extension: false }"
+ " identifier_value: \"CODE_SIZE\" } "
+ "}");
+}
+
+// ===================================================================
+// Error tests
+//
+// There are a very large number of possible errors that the parser could
+// report, so it's infeasible to test every single one of them. Instead,
+// we test each unique call to AddError() in parser.h. This does not mean
+// we are testing every possible error that Parser can generate because
+// each variant of the Consume() helper only counts as one unique call to
+// AddError().
+
+typedef ParserTest ParseErrorTest;
+
+TEST_F(ParseErrorTest, MissingSyntaxIdentifier) {
+ require_syntax_identifier_ = true;
+ ExpectHasEarlyExitErrors("message TestMessage {}",
+ "0:0: File must begin with a syntax statement, e.g. "
+ "'syntax = \"proto2\";'.\n");
+ EXPECT_EQ("", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParseErrorTest, UnknownSyntaxIdentifier) {
+ ExpectHasEarlyExitErrors(
+ "syntax = \"no_such_syntax\";",
+ "0:9: Unrecognized syntax identifier \"no_such_syntax\". This parser "
+ "only recognizes \"proto2\" and \"proto3\".\n");
+ EXPECT_EQ("no_such_syntax", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParseErrorTest, SimpleSyntaxError) {
+ ExpectHasErrors(
+ "message TestMessage @#$ { blah }",
+ "0:20: Expected \"{\".\n");
+ EXPECT_EQ("proto2", parser_->GetSyntaxIdentifier());
+}
+
+TEST_F(ParseErrorTest, ExpectedTopLevel) {
+ ExpectHasErrors(
+ "blah;",
+ "0:0: Expected top-level statement (e.g. \"message\").\n");
+}
+
+TEST_F(ParseErrorTest, UnmatchedCloseBrace) {
+ // This used to cause an infinite loop. Doh.
+ ExpectHasErrors(
+ "}",
+ "0:0: Expected top-level statement (e.g. \"message\").\n"
+ "0:0: Unmatched \"}\".\n");
+}
+
+// -------------------------------------------------------------------
+// Message errors
+
+TEST_F(ParseErrorTest, MessageMissingName) {
+ ExpectHasErrors(
+ "message {}",
+ "0:8: Expected message name.\n");
+}
+
+TEST_F(ParseErrorTest, MessageMissingBody) {
+ ExpectHasErrors(
+ "message TestMessage;",
+ "0:19: Expected \"{\".\n");
+}
+
+TEST_F(ParseErrorTest, EofInMessage) {
+ ExpectHasErrors(
+ "message TestMessage {",
+ "0:21: Reached end of input in message definition (missing '}').\n");
+}
+
+TEST_F(ParseErrorTest, MissingFieldNumber) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional int32 foo;\n"
+ "}\n",
+ "1:20: Missing field number.\n");
+}
+
+TEST_F(ParseErrorTest, ExpectedFieldNumber) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional int32 foo = ;\n"
+ "}\n",
+ "1:23: Expected field number.\n");
+}
+
+TEST_F(ParseErrorTest, FieldNumberOutOfRange) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional int32 foo = 0x100000000;\n"
+ "}\n",
+ "1:23: Integer out of range.\n");
+}
+
+TEST_F(ParseErrorTest, MissingLabel) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " int32 foo = 1;\n"
+ "}\n",
+ "1:2: Expected \"required\", \"optional\", or \"repeated\".\n");
+}
+
+TEST_F(ParseErrorTest, ExpectedOptionName) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional uint32 foo = 1 [];\n"
+ "}\n",
+ "1:27: Expected identifier.\n");
+}
+
+TEST_F(ParseErrorTest, NonExtensionOptionNameBeginningWithDot) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional uint32 foo = 1 [.foo=1];\n"
+ "}\n",
+ "1:27: Expected identifier.\n");
+}
+
+TEST_F(ParseErrorTest, DefaultValueTypeMismatch) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional uint32 foo = 1 [default=true];\n"
+ "}\n",
+ "1:35: Expected integer for field default value.\n");
+}
+
+TEST_F(ParseErrorTest, DefaultValueNotBoolean) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional bool foo = 1 [default=blah];\n"
+ "}\n",
+ "1:33: Expected \"true\" or \"false\".\n");
+}
+
+TEST_F(ParseErrorTest, DefaultValueNotString) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional string foo = 1 [default=1];\n"
+ "}\n",
+ "1:35: Expected string for field default value.\n");
+}
+
+TEST_F(ParseErrorTest, DefaultValueUnsignedNegative) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional uint32 foo = 1 [default=-1];\n"
+ "}\n",
+ "1:36: Unsigned field can't have negative default value.\n");
+}
+
+TEST_F(ParseErrorTest, DefaultValueTooLarge) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional int32 foo = 1 [default= 0x80000000];\n"
+ " optional int32 foo = 1 [default=-0x80000001];\n"
+ " optional uint32 foo = 1 [default= 0x100000000];\n"
+ " optional int64 foo = 1 [default= 0x80000000000000000];\n"
+ " optional int64 foo = 1 [default=-0x80000000000000001];\n"
+ " optional uint64 foo = 1 [default= 0x100000000000000000];\n"
+ "}\n",
+ "1:36: Integer out of range.\n"
+ "2:36: Integer out of range.\n"
+ "3:36: Integer out of range.\n"
+ "4:36: Integer out of range.\n"
+ "5:36: Integer out of range.\n"
+ "6:36: Integer out of range.\n");
+}
+
+TEST_F(ParseErrorTest, JsonNameNotString) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional string foo = 1 [json_name=1];\n"
+ "}\n",
+ "1:37: Expected string for JSON name.\n");
+}
+
+TEST_F(ParseErrorTest, DuplicateJsonName) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional uint32 foo = 1 [json_name=\"a\",json_name=\"b\"];\n"
+ "}\n",
+ "1:41: Already set option \"json_name\".\n");
+}
+
+TEST_F(ParseErrorTest, EnumValueOutOfRange) {
+ ExpectHasErrors(
+ "enum TestEnum {\n"
+ " HEX_TOO_BIG = 0x80000000;\n"
+ " HEX_TOO_SMALL = -0x80000001;\n"
+ " INT_TOO_BIG = 2147483648;\n"
+ " INT_TOO_SMALL = -2147483649;\n"
+ "}\n",
+ "1:19: Integer out of range.\n"
+ "2:19: Integer out of range.\n"
+ "3:19: Integer out of range.\n"
+ "4:19: Integer out of range.\n");
+}
+
+TEST_F(ParseErrorTest, EnumAllowAliasFalse) {
+ ExpectHasErrors(
+ "enum Foo {\n"
+ " option allow_alias = false;\n"
+ " BAR = 1;\n"
+ " BAZ = 2;\n"
+ "}\n",
+ "5:0: \"Foo\" declares 'option allow_alias = false;' which has no effect. "
+ "Please remove the declaration.\n");
+}
+
+TEST_F(ParseErrorTest, UnnecessaryEnumAllowAlias) {
+ ExpectHasErrors(
+ "enum Foo {\n"
+ " option allow_alias = true;\n"
+ " BAR = 1;\n"
+ " BAZ = 2;\n"
+ "}\n",
+ "5:0: \"Foo\" declares support for enum aliases but no enum values share "
+ "field numbers. Please remove the unnecessary 'option allow_alias = true;' "
+ "declaration.\n");
+}
+
+TEST_F(ParseErrorTest, DefaultValueMissing) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional uint32 foo = 1 [default=];\n"
+ "}\n",
+ "1:35: Expected integer for field default value.\n");
+}
+
+TEST_F(ParseErrorTest, DefaultValueForGroup) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional group Foo = 1 [default=blah] {}\n"
+ "}\n",
+ "1:34: Messages can't have default values.\n");
+}
+
+TEST_F(ParseErrorTest, DuplicateDefaultValue) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional uint32 foo = 1 [default=1,default=2];\n"
+ "}\n",
+ "1:37: Already set option \"default\".\n");
+}
+
+TEST_F(ParseErrorTest, MissingOneofName) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " oneof {\n"
+ " int32 bar = 1;\n"
+ " }\n"
+ "}\n",
+ "1:8: Expected oneof name.\n");
+}
+
+TEST_F(ParseErrorTest, LabelInOneof) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " oneof foo {\n"
+ " optional int32 bar = 1;\n"
+ " }\n"
+ "}\n",
+ "2:4: Fields in oneofs must not have labels (required / optional "
+ "/ repeated).\n");
+}
+
+TEST_F(ParseErrorTest, MapInOneof) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " oneof foo {\n"
+ " map<int32, int32> foo_map = 1;\n"
+ " map message_field = 2;\n" // a normal message field is OK
+ " }\n"
+ "}\n",
+ "2:7: Map fields are not allowed in oneofs.\n");
+}
+
+TEST_F(ParseErrorTest, LabelForMap) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional map<int32, int32> int_map = 1;\n"
+ " required map<int32, int32> int_map2 = 2;\n"
+ " repeated map<int32, int32> int_map3 = 3;\n"
+ " optional map map_message = 4;\n" // a normal message field is OK
+ "}\n",
+ "1:14: Field labels (required/optional/repeated) are not allowed on map "
+ "fields.\n"
+ "2:14: Field labels (required/optional/repeated) are not allowed on map "
+ "fields.\n"
+ "3:14: Field labels (required/optional/repeated) are not allowed on map "
+ "fields.\n");
+}
+
+TEST_F(ParseErrorTest, MalformedMaps) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " map map_message = 1;\n" // a normal message field lacking label
+ " map<string> str_map = 2;\n"
+ " map<string,> str_map2 = 3;\n"
+ " map<,string> str_map3 = 4;\n"
+ " map<> empty_map = 5;\n"
+ " map<string,string str_map6 = 6;\n"
+ "}"
+ "extend SomeMessage {\n"
+ " map<int32, int32> int_map = 1;\n"
+ "}",
+ "1:6: Expected \"required\", \"optional\", or \"repeated\".\n"
+ "2:12: Expected \",\".\n"
+ "3:13: Expected type name.\n"
+ "4:6: Expected type name.\n"
+ "5:6: Expected type name.\n"
+ "6:20: Expected \">\".\n"
+ "8:5: Map fields are not allowed to be extensions.\n");
+}
+
+TEST_F(ParseErrorTest, GroupNotCapitalized) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional group foo = 1 {}\n"
+ "}\n",
+ "1:17: Group names must start with a capital letter.\n");
+}
+
+TEST_F(ParseErrorTest, GroupMissingBody) {
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional group Foo = 1;\n"
+ "}\n",
+ "1:24: Missing group body.\n");
+}
+
+TEST_F(ParseErrorTest, ExtendingPrimitive) {
+ ExpectHasErrors(
+ "extend int32 { optional string foo = 4; }\n",
+ "0:7: Expected message type.\n");
+}
+
+TEST_F(ParseErrorTest, ErrorInExtension) {
+ ExpectHasErrors(
+ "message Foo { extensions 100 to 199; }\n"
+ "extend Foo { optional string foo; }\n",
+ "1:32: Missing field number.\n");
+}
+
+TEST_F(ParseErrorTest, MultipleParseErrors) {
+ // When a statement has a parse error, the parser should be able to continue
+ // parsing at the next statement.
+ ExpectHasErrors(
+ "message TestMessage {\n"
+ " optional int32 foo;\n"
+ " !invalid statement ending in a block { blah blah { blah } blah }\n"
+ " optional int32 bar = 3 {}\n"
+ "}\n",
+ "1:20: Missing field number.\n"
+ "2:2: Expected \"required\", \"optional\", or \"repeated\".\n"
+ "2:2: Expected type name.\n"
+ "3:25: Expected \";\".\n");
+}
+
+TEST_F(ParseErrorTest, EofInAggregateValue) {
+ ExpectHasErrors(
+ "option (fileopt) = { i:100\n",
+ "1:0: Unexpected end of stream while parsing aggregate value.\n");
+}
+
+TEST_F(ParseErrorTest, ExplicitOptionalLabelProto3) {
+ ExpectHasErrors(
+ "syntax = 'proto3';\n"
+ "message TestMessage {\n"
+ " optional int32 foo = 1;\n"
+ "}\n",
+ "2:11: Explicit 'optional' labels are disallowed in the Proto3 syntax. "
+ "To define 'optional' fields in Proto3, simply remove the 'optional' "
+ "label, as fields are 'optional' by default.\n");
+}
+
+
+// -------------------------------------------------------------------
+// Enum errors
+
+TEST_F(ParseErrorTest, EofInEnum) {
+ ExpectHasErrors(
+ "enum TestEnum {",
+ "0:15: Reached end of input in enum definition (missing '}').\n");
+}
+
+TEST_F(ParseErrorTest, EnumValueMissingNumber) {
+ ExpectHasErrors(
+ "enum TestEnum {\n"
+ " FOO;\n"
+ "}\n",
+ "1:5: Missing numeric value for enum constant.\n");
+}
+
+// -------------------------------------------------------------------
+// Reserved field number errors
+
+TEST_F(ParseErrorTest, ReservedMaxNotAllowed) {
+ ExpectHasErrors(
+ "message Foo {\n"
+ " reserved 10 to max;\n"
+ "}\n",
+ "1:17: Expected integer.\n");
+}
+
+TEST_F(ParseErrorTest, ReservedMixNameAndNumber) {
+ ExpectHasErrors(
+ "message Foo {\n"
+ " reserved 10, \"foo\";\n"
+ "}\n",
+ "1:15: Expected field number range.\n");
+}
+
+TEST_F(ParseErrorTest, ReservedMissingQuotes) {
+ ExpectHasErrors(
+ "message Foo {\n"
+ " reserved foo;\n"
+ "}\n",
+ "1:11: Expected field name or number range.\n");
+}
+
+// -------------------------------------------------------------------
+// Service errors
+
+TEST_F(ParseErrorTest, EofInService) {
+ ExpectHasErrors(
+ "service TestService {",
+ "0:21: Reached end of input in service definition (missing '}').\n");
+}
+
+TEST_F(ParseErrorTest, ServiceMethodPrimitiveParams) {
+ ExpectHasErrors(
+ "service TestService {\n"
+ " rpc Foo(int32) returns (string);\n"
+ "}\n",
+ "1:10: Expected message type.\n"
+ "1:26: Expected message type.\n");
+}
+
+
+TEST_F(ParseErrorTest, EofInMethodOptions) {
+ ExpectHasErrors(
+ "service TestService {\n"
+ " rpc Foo(Bar) returns(Bar) {",
+ "1:29: Reached end of input in method options (missing '}').\n"
+ "1:29: Reached end of input in service definition (missing '}').\n");
+}
+
+
+TEST_F(ParseErrorTest, PrimitiveMethodInput) {
+ ExpectHasErrors(
+ "service TestService {\n"
+ " rpc Foo(int32) returns(Bar);\n"
+ "}\n",
+ "1:10: Expected message type.\n");
+}
+
+
+TEST_F(ParseErrorTest, MethodOptionTypeError) {
+ // This used to cause an infinite loop.
+ ExpectHasErrors(
+ "message Baz {}\n"
+ "service Foo {\n"
+ " rpc Bar(Baz) returns(Baz) { option invalid syntax; }\n"
+ "}\n",
+ "2:45: Expected \"=\".\n");
+}
+
+
+// -------------------------------------------------------------------
+// Import and package errors
+
+TEST_F(ParseErrorTest, ImportNotQuoted) {
+ ExpectHasErrors(
+ "import foo;\n",
+ "0:7: Expected a string naming the file to import.\n");
+}
+
+TEST_F(ParseErrorTest, MultiplePackagesInFile) {
+ ExpectHasErrors(
+ "package foo;\n"
+ "package bar;\n",
+ "1:0: Multiple package definitions.\n");
+}
+
+// ===================================================================
+// Test that errors detected by DescriptorPool correctly report line and
+// column numbers. We have one test for every call to RecordLocation() in
+// parser.cc.
+
+typedef ParserTest ParserValidationErrorTest;
+
+TEST_F(ParserValidationErrorTest, PackageNameError) {
+ // Create another file which defines symbol "foo".
+ FileDescriptorProto other_file;
+ other_file.set_name("bar.proto");
+ other_file.add_message_type()->set_name("foo");
+ EXPECT_TRUE(pool_.BuildFile(other_file) != NULL);
+
+ // Now try to define it as a package.
+ ExpectHasValidationErrors(
+ "package foo.bar;",
+ "0:8: \"foo\" is already defined (as something other than a package) "
+ "in file \"bar.proto\".\n");
+}
+
+TEST_F(ParserValidationErrorTest, MessageNameError) {
+ ExpectHasValidationErrors(
+ "message Foo {}\n"
+ "message Foo {}\n",
+ "1:8: \"Foo\" is already defined.\n");
+}
+
+TEST_F(ParserValidationErrorTest, FieldNameError) {
+ ExpectHasValidationErrors(
+ "message Foo {\n"
+ " optional int32 bar = 1;\n"
+ " optional int32 bar = 2;\n"
+ "}\n",
+ "2:17: \"bar\" is already defined in \"Foo\".\n");
+}
+
+TEST_F(ParserValidationErrorTest, FieldTypeError) {
+ ExpectHasValidationErrors(
+ "message Foo {\n"
+ " optional Baz bar = 1;\n"
+ "}\n",
+ "1:11: \"Baz\" is not defined.\n");
+}
+
+TEST_F(ParserValidationErrorTest, FieldNumberError) {
+ ExpectHasValidationErrors(
+ "message Foo {\n"
+ " optional int32 bar = 0;\n"
+ "}\n",
+ "1:23: Field numbers must be positive integers.\n");
+}
+
+TEST_F(ParserValidationErrorTest, FieldExtendeeError) {
+ ExpectHasValidationErrors(
+ "extend Baz { optional int32 bar = 1; }\n",
+ "0:7: \"Baz\" is not defined.\n");
+}
+
+TEST_F(ParserValidationErrorTest, FieldDefaultValueError) {
+ ExpectHasValidationErrors(
+ "enum Baz { QUX = 1; }\n"
+ "message Foo {\n"
+ " optional Baz bar = 1 [default=NO_SUCH_VALUE];\n"
+ "}\n",
+ "2:32: Enum type \"Baz\" has no value named \"NO_SUCH_VALUE\".\n");
+}
+
+TEST_F(ParserValidationErrorTest, FileOptionNameError) {
+ ExpectHasValidationErrors(
+ "option foo = 5;",
+ "0:7: Option \"foo\" unknown.\n");
+}
+
+TEST_F(ParserValidationErrorTest, FileOptionValueError) {
+ ExpectHasValidationErrors(
+ "option java_outer_classname = 5;",
+ "0:30: Value must be quoted string for string option "
+ "\"google.protobuf.FileOptions.java_outer_classname\".\n");
+}
+
+TEST_F(ParserValidationErrorTest, FieldOptionNameError) {
+ ExpectHasValidationErrors(
+ "message Foo {\n"
+ " optional bool bar = 1 [foo=1];\n"
+ "}\n",
+ "1:25: Option \"foo\" unknown.\n");
+}
+
+TEST_F(ParserValidationErrorTest, FieldOptionValueError) {
+ ExpectHasValidationErrors(
+ "message Foo {\n"
+ " optional int32 bar = 1 [ctype=1];\n"
+ "}\n",
+ "1:32: Value must be identifier for enum-valued option "
+ "\"google.protobuf.FieldOptions.ctype\".\n");
+}
+
+TEST_F(ParserValidationErrorTest, ExtensionRangeNumberError) {
+ ExpectHasValidationErrors(
+ "message Foo {\n"
+ " extensions 0;\n"
+ "}\n",
+ "1:13: Extension numbers must be positive integers.\n");
+}
+
+TEST_F(ParserValidationErrorTest, EnumNameError) {
+ ExpectHasValidationErrors(
+ "enum Foo {A = 1;}\n"
+ "enum Foo {B = 1;}\n",
+ "1:5: \"Foo\" is already defined.\n");
+}
+
+TEST_F(ParserValidationErrorTest, EnumValueNameError) {
+ ExpectHasValidationErrors(
+ "enum Foo {\n"
+ " BAR = 1;\n"
+ " BAR = 1;\n"
+ "}\n",
+ "2:2: \"BAR\" is already defined.\n");
+}
+
+TEST_F(ParserValidationErrorTest, ServiceNameError) {
+ ExpectHasValidationErrors(
+ "service Foo {}\n"
+ "service Foo {}\n",
+ "1:8: \"Foo\" is already defined.\n");
+}
+
+TEST_F(ParserValidationErrorTest, MethodNameError) {
+ ExpectHasValidationErrors(
+ "message Baz {}\n"
+ "service Foo {\n"
+ " rpc Bar(Baz) returns(Baz);\n"
+ " rpc Bar(Baz) returns(Baz);\n"
+ "}\n",
+ "3:6: \"Bar\" is already defined in \"Foo\".\n");
+}
+
+
+TEST_F(ParserValidationErrorTest, MethodInputTypeError) {
+ ExpectHasValidationErrors(
+ "message Baz {}\n"
+ "service Foo {\n"
+ " rpc Bar(Qux) returns(Baz);\n"
+ "}\n",
+ "2:10: \"Qux\" is not defined.\n");
+}
+
+
+TEST_F(ParserValidationErrorTest, MethodOutputTypeError) {
+ ExpectHasValidationErrors(
+ "message Baz {}\n"
+ "service Foo {\n"
+ " rpc Bar(Baz) returns(Qux);\n"
+ "}\n",
+ "2:23: \"Qux\" is not defined.\n");
+}
+
+
+TEST_F(ParserValidationErrorTest, ResovledUndefinedError) {
+ // Create another file which defines symbol ".base.bar".
+ FileDescriptorProto other_file;
+ other_file.set_name("base.proto");
+ other_file.set_package("base");
+ other_file.add_message_type()->set_name("bar");
+ EXPECT_TRUE(pool_.BuildFile(other_file) != NULL);
+
+ // Define "foo.base" and try "base.bar".
+ // "base.bar" is resolved to "foo.base.bar" which is not defined.
+ ExpectHasValidationErrors(
+ "package foo.base;\n"
+ "import \"base.proto\";\n"
+ "message qux {\n"
+ " optional base.bar baz = 1;\n"
+ " optional .base.bar quz = 2;\n"
+ "}\n",
+ "3:11: \"base.bar\" is resolved to \"foo.base.bar\","
+ " which is not defined. The innermost scope is searched first "
+ "in name resolution. Consider using a leading '.'(i.e., \".base.bar\")"
+ " to start from the outermost scope.\n");
+}
+
+TEST_F(ParserValidationErrorTest, ResovledUndefinedOptionError) {
+ // Build descriptor message in test pool
+ FileDescriptorProto descriptor_proto;
+ DescriptorProto::descriptor()->file()->CopyTo(&descriptor_proto);
+ ASSERT_TRUE(pool_.BuildFile(descriptor_proto) != NULL);
+
+ // base2.proto:
+ // package baz
+ // import google/protobuf/descriptor.proto
+ // message Bar { optional int32 foo = 1; }
+ // extend FileOptions { optional Bar bar = 7672757; }
+ FileDescriptorProto other_file;
+ other_file.set_name("base2.proto");
+ other_file.set_package("baz");
+ other_file.add_dependency();
+ other_file.set_dependency(0, descriptor_proto.name());
+
+ DescriptorProto* message(other_file.add_message_type());
+ message->set_name("Bar");
+ FieldDescriptorProto* field(message->add_field());
+ field->set_name("foo");
+ field->set_number(1);
+ field->set_label(FieldDescriptorProto_Label_LABEL_OPTIONAL);
+ field->set_type(FieldDescriptorProto_Type_TYPE_INT32);
+
+ FieldDescriptorProto* extension(other_file.add_extension());
+ extension->set_name("bar");
+ extension->set_number(7672757);
+ extension->set_label(FieldDescriptorProto_Label_LABEL_OPTIONAL);
+ extension->set_type(FieldDescriptorProto_Type_TYPE_MESSAGE);
+ extension->set_type_name("Bar");
+ extension->set_extendee("google.protobuf.FileOptions");
+
+ EXPECT_TRUE(pool_.BuildFile(other_file) != NULL);
+
+ // qux.proto:
+ // package qux.baz
+ // option (baz.bar).foo = 1;
+ //
+ // Although "baz.bar" is already defined, the lookup code will try
+ // "qux.baz.bar", since it's the match from the innermost scope,
+ // which will cause a symbol not defined error.
+ ExpectHasValidationErrors(
+ "package qux.baz;\n"
+ "import \"base2.proto\";\n"
+ "option (baz.bar).foo = 1;\n",
+ "2:7: Option \"(baz.bar)\" is resolved to \"(qux.baz.bar)\","
+ " which is not defined. The innermost scope is searched first "
+ "in name resolution. Consider using a leading '.'(i.e., \"(.baz.bar)\")"
+ " to start from the outermost scope.\n");
+}
+
+// ===================================================================
+// Test that the output from FileDescriptor::DebugString() (and all other
+// descriptor types) is parseable, and results in the same Descriptor
+// definitions again afoter parsing (note, however, that the order of messages
+// cannot be guaranteed to be the same)
+
+typedef ParserTest ParseDescriptorDebugTest;
+
+class CompareDescriptorNames {
+ public:
+ bool operator()(const DescriptorProto* left,
+ const DescriptorProto* right) const {
+ return left->name() < right->name();
+ }
+};
+
+// Sorts nested DescriptorProtos of a DescriptoProto, by name.
+void SortMessages(DescriptorProto *descriptor_proto) {
+ int size = descriptor_proto->nested_type_size();
+ // recursively sort; we can't guarantee the order of nested messages either
+ for (int i = 0; i < size; ++i) {
+ SortMessages(descriptor_proto->mutable_nested_type(i));
+ }
+ DescriptorProto **data =
+ descriptor_proto->mutable_nested_type()->mutable_data();
+ std::sort(data, data + size, CompareDescriptorNames());
+}
+
+// Sorts DescriptorProtos belonging to a FileDescriptorProto, by name.
+void SortMessages(FileDescriptorProto *file_descriptor_proto) {
+ int size = file_descriptor_proto->message_type_size();
+ // recursively sort; we can't guarantee the order of nested messages either
+ for (int i = 0; i < size; ++i) {
+ SortMessages(file_descriptor_proto->mutable_message_type(i));
+ }
+ DescriptorProto **data =
+ file_descriptor_proto->mutable_message_type()->mutable_data();
+ std::sort(data, data + size, CompareDescriptorNames());
+}
+
+// Strips the message and enum field type names for comparison purpose only.
+void StripFieldTypeName(DescriptorProto* proto) {
+ for (int i = 0; i < proto->field_size(); ++i) {
+ string type_name = proto->field(i).type_name();
+ string::size_type pos = type_name.find_last_of(".");
+ if (pos != string::npos) {
+ proto->mutable_field(i)->mutable_type_name()->assign(
+ type_name.begin() + pos + 1, type_name.end());
+ }
+ }
+ for (int i = 0; i < proto->nested_type_size(); ++i) {
+ StripFieldTypeName(proto->mutable_nested_type(i));
+ }
+}
+
+void StripFieldTypeName(FileDescriptorProto* file_proto) {
+ for (int i = 0; i < file_proto->message_type_size(); ++i) {
+ StripFieldTypeName(file_proto->mutable_message_type(i));
+ }
+}
+
+TEST_F(ParseDescriptorDebugTest, TestAllDescriptorTypes) {
+ const FileDescriptor* original_file =
+ protobuf_unittest::TestAllTypes::descriptor()->file();
+ FileDescriptorProto expected;
+ original_file->CopyTo(&expected);
+
+ // Get the DebugString of the unittest.proto FileDecriptor, which includes
+ // all other descriptor types
+ string debug_string = original_file->DebugString();
+
+ // Parse the debug string
+ SetupParser(debug_string.c_str());
+ FileDescriptorProto parsed;
+ parser_->Parse(input_.get(), &parsed);
+ EXPECT_EQ(io::Tokenizer::TYPE_END, input_->current().type);
+ ASSERT_EQ("", error_collector_.text_)
+ << "Failed to parse:\n" << debug_string;
+
+ // We now have a FileDescriptorProto, but to compare with the expected we
+ // need to link to a FileDecriptor, then output back to a proto. We'll
+ // also need to give it the same name as the original.
+ parsed.set_name("google/protobuf/unittest.proto");
+ // We need the imported dependency before we can build our parsed proto
+ const FileDescriptor* public_import =
+ protobuf_unittest_import::PublicImportMessage::descriptor()->file();
+ FileDescriptorProto public_import_proto;
+ public_import->CopyTo(&public_import_proto);
+ ASSERT_TRUE(pool_.BuildFile(public_import_proto) != NULL);
+ const FileDescriptor* import =
+ protobuf_unittest_import::ImportMessage::descriptor()->file();
+ FileDescriptorProto import_proto;
+ import->CopyTo(&import_proto);
+ ASSERT_TRUE(pool_.BuildFile(import_proto) != NULL);
+ const FileDescriptor* actual = pool_.BuildFile(parsed);
+ parsed.Clear();
+ ASSERT_TRUE(actual != NULL)
+ << "Failed to validate:\n" << debug_string;
+ actual->CopyTo(&parsed);
+ ASSERT_TRUE(actual != NULL);
+
+ // The messages might be in different orders, making them hard to compare.
+ // So, sort the messages in the descriptor protos (including nested messages,
+ // recursively).
+ SortMessages(&expected);
+ SortMessages(&parsed);
+
+ // I really wanted to use StringDiff here for the debug output on fail,
+ // but the strings are too long for it, and if I increase its max size,
+ // we get a memory allocation failure :(
+ EXPECT_EQ(expected.DebugString(), parsed.DebugString());
+}
+
+TEST_F(ParseDescriptorDebugTest, TestCustomOptions) {
+ const FileDescriptor* original_file =
+ protobuf_unittest::AggregateMessage::descriptor()->file();
+ FileDescriptorProto expected;
+ original_file->CopyTo(&expected);
+
+ string debug_string = original_file->DebugString();
+
+ // Parse the debug string
+ SetupParser(debug_string.c_str());
+ FileDescriptorProto parsed;
+ parser_->Parse(input_.get(), &parsed);
+ EXPECT_EQ(io::Tokenizer::TYPE_END, input_->current().type);
+ ASSERT_EQ("", error_collector_.text_);
+
+ // We now have a FileDescriptorProto, but to compare with the expected we
+ // need to link to a FileDecriptor, then output back to a proto. We'll
+ // also need to give it the same name as the original.
+ parsed.set_name(original_file->name());
+
+ // unittest_custom_options.proto depends on descriptor.proto.
+ const FileDescriptor* import = FileDescriptorProto::descriptor()->file();
+ FileDescriptorProto import_proto;
+ import->CopyTo(&import_proto);
+ ASSERT_TRUE(pool_.BuildFile(import_proto) != NULL);
+ const FileDescriptor* actual = pool_.BuildFile(parsed);
+ ASSERT_TRUE(actual != NULL);
+ parsed.Clear();
+ actual->CopyTo(&parsed);
+
+ // The messages might be in different orders, making them hard to compare.
+ // So, sort the messages in the descriptor protos (including nested messages,
+ // recursively).
+ SortMessages(&expected);
+ SortMessages(&parsed);
+
+ EXPECT_EQ(expected.DebugString(), parsed.DebugString());
+}
+
+// Ensure that DebugStringWithOptions(), with |include_comments| set to true,
+// includes comments from the original parser input in all of the appropriate
+// places.
+TEST_F(ParseDescriptorDebugTest, TestCommentsInDebugString) {
+ SetupParser(
+ "// Detached comment before syntax.\n"
+ "\n"
+ "// Syntax comment.\n"
+ "syntax = \"proto2\";\n"
+ "\n"
+ "// Detached comment before package.\n"
+ "\n"
+ "// Package comment.\n"
+ "package comment_test;\n"
+ "\n"
+ "// Detached comment before TestMessage1.\n"
+ "\n"
+ "// Message comment.\n"
+ "//\n"
+ "// More detail in message comment.\n"
+ "message TestMessage1 {\n"
+ "\n"
+ " // Detached comment before foo.\n"
+ "\n"
+ " // Field comment.\n"
+ " optional int32 foo = 1;\n"
+ "\n"
+ " // Detached comment before NestedMessage.\n"
+ "\n"
+ " // Nested-message comment.\n"
+ " message NestedMessage {\n"
+ " optional int32 bar = 1;\n"
+ " }\n"
+ "}\n"
+ "\n"
+ "// Detached comment before MyEnumType.\n"
+ "\n"
+ "// Enum comment.\n"
+ "enum MyEnumType {\n"
+ "\n"
+ " // Detached comment before ASDF.\n"
+ "\n"
+ " // Enum-value comment.\n"
+ " ASDF = 1;\n"
+ "}\n"
+ "\n"
+ "// Detached comment before MyService.\n"
+ "\n"
+ "// Service comment.\n"
+ "service MyService {\n"
+ "\n"
+ " // Detached comment before MyRPCCall.\n"
+ "\n"
+ " // RPC comment.\n"
+ " rpc MyRPCCall(TestMessage1) returns (TestMessage1) { }\n"
+ "}\n");
+
+ FileDescriptorProto parsed_desc;
+ parsed_desc.set_name("foo.proto");
+ SourceLocationTable source_locations;
+ parser_->RecordSourceLocationsTo(&source_locations);
+ parser_->Parse(input_.get(), &parsed_desc);
+ EXPECT_EQ(io::Tokenizer::TYPE_END, input_->current().type);
+ ASSERT_EQ("", error_collector_.text_);
+
+ // We need to import the FileDescriptorProto to get a FileDescriptor.
+ MockValidationErrorCollector collector(source_locations, &error_collector_);
+ const FileDescriptor* descriptor =
+ pool_.BuildFileCollectingErrors(parsed_desc, &collector);
+ ASSERT_TRUE(descriptor != NULL);
+
+ // Ensure that each of the comments appears somewhere in the DebugString().
+ // We don't test the exact comment placement or formatting, because we do not
+ // want to be too fragile here.
+ const char* expected_comments[] = {
+ "Detached comment before syntax.",
+ "Syntax comment.",
+ "Detached comment before package.",
+ "Package comment.",
+ "Detached comment before TestMessage1.",
+ "Message comment.",
+ "More detail in message comment.",
+ "Detached comment before foo.",
+ "Field comment",
+ "Detached comment before NestedMessage.",
+ "Nested-message comment",
+ "Detached comment before MyEnumType.",
+ "Enum comment",
+ "Detached comment before ASDF.",
+ "Enum-value comment",
+ "Detached comment before MyService.",
+ "Service comment",
+ "Detached comment before MyRPCCall.",
+ "RPC comment",
+ };
+
+ DebugStringOptions debug_string_options;
+ debug_string_options.include_comments = true;
+
+ {
+ const string debug_string =
+ descriptor->DebugStringWithOptions(debug_string_options);
+
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(expected_comments); ++i) {
+ string::size_type found_pos = debug_string.find(expected_comments[i]);
+ EXPECT_TRUE(found_pos != string::npos)
+ << "\"" << expected_comments[i] << "\" not found.";
+ }
+
+ // Result of DebugStringWithOptions should be parseable.
+ SetupParser(debug_string.c_str());
+ FileDescriptorProto parsed;
+ parser_->Parse(input_.get(), &parsed);
+ EXPECT_EQ(io::Tokenizer::TYPE_END, input_->current().type);
+ ASSERT_EQ("", error_collector_.text_)
+ << "Failed to parse:\n" << debug_string;
+ }
+
+}
+
+TEST_F(ParseDescriptorDebugTest, TestMaps) {
+ SetupParser(
+ "syntax = \"proto3\"; "
+ "message Foo { "
+ " message Bar { } "
+ " map<int32, Bar> enum_message_map = 1; "
+ " map<string, float> primitive_map = 2; "
+ "} ");
+ FileDescriptorProto original;
+ EXPECT_TRUE(parser_->Parse(input_.get(), &original));
+ original.set_name("foo.proto");
+ const FileDescriptor* file = pool_.BuildFile(original);
+ ASSERT_TRUE(file != NULL);
+
+ // Make sure the debug string uses map syntax and does not have the auto
+ // generated entry.
+ string debug_string = file->DebugString();
+ EXPECT_TRUE(debug_string.find("map<") != string::npos);
+ EXPECT_TRUE(debug_string.find("option map_entry") == string::npos);
+ EXPECT_TRUE(debug_string.find("MapEntry") == string::npos);
+
+ // Make sure the descriptor debug string is parsable.
+ FileDescriptorProto parsed;
+ SetupParser(debug_string.c_str());
+ parsed.set_name("foo.proto");
+ ASSERT_TRUE(parser_->Parse(input_.get(), &parsed));
+
+ original.clear_source_code_info();
+ parsed.clear_source_code_info();
+ StripFieldTypeName(&original);
+ StripFieldTypeName(&parsed);
+ EXPECT_EQ(original.DebugString(), parsed.DebugString());
+}
+
+// ===================================================================
+// SourceCodeInfo tests.
+
+// Follows a path -- as defined by SourceCodeInfo.Location.path -- from a
+// message to a particular sub-field.
+// * If the target is itself a message, sets *output_message to point at it,
+// *output_field to NULL, and *output_index to -1.
+// * Otherwise, if the target is an element of a repeated field, sets
+// *output_message to the containing message, *output_field to the descriptor
+// of the field, and *output_index to the index of the element.
+// * Otherwise, the target is a field (possibly a repeated field, but not any
+// one element). Sets *output_message to the containing message,
+// *output_field to the descriptor of the field, and *output_index to -1.
+// Returns true if the path was valid, false otherwise. A gTest failure is
+// recorded before returning false.
+bool FollowPath(const Message& root,
+ const int* path_begin, const int* path_end,
+ const Message** output_message,
+ const FieldDescriptor** output_field,
+ int* output_index) {
+ if (path_begin == path_end) {
+ // Path refers to this whole message.
+ *output_message = &root;
+ *output_field = NULL;
+ *output_index = -1;
+ return true;
+ }
+
+ const Descriptor* descriptor = root.GetDescriptor();
+ const Reflection* reflection = root.GetReflection();
+
+ const FieldDescriptor* field = descriptor->FindFieldByNumber(*path_begin);
+
+ if (field == NULL) {
+ ADD_FAILURE() << descriptor->name() << " has no field number: "
+ << *path_begin;
+ return false;
+ }
+
+ ++path_begin;
+
+ if (field->is_repeated()) {
+ if (path_begin == path_end) {
+ // Path refers to the whole repeated field.
+ *output_message = &root;
+ *output_field = field;
+ *output_index = -1;
+ return true;
+ }
+
+ int index = *path_begin++;
+ int size = reflection->FieldSize(root, field);
+
+ if (index >= size) {
+ ADD_FAILURE() << descriptor->name() << "." << field->name()
+ << " has size " << size << ", but path contained index: "
+ << index;
+ return false;
+ }
+
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Descend into child message.
+ const Message& child = reflection->GetRepeatedMessage(root, field, index);
+ return FollowPath(child, path_begin, path_end,
+ output_message, output_field, output_index);
+ } else if (path_begin == path_end) {
+ // Path refers to this element.
+ *output_message = &root;
+ *output_field = field;
+ *output_index = index;
+ return true;
+ } else {
+ ADD_FAILURE() << descriptor->name() << "." << field->name()
+ << " is not a message; cannot descend into it.";
+ return false;
+ }
+ } else {
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ const Message& child = reflection->GetMessage(root, field);
+ return FollowPath(child, path_begin, path_end,
+ output_message, output_field, output_index);
+ } else if (path_begin == path_end) {
+ // Path refers to this field.
+ *output_message = &root;
+ *output_field = field;
+ *output_index = -1;
+ return true;
+ } else {
+ ADD_FAILURE() << descriptor->name() << "." << field->name()
+ << " is not a message; cannot descend into it.";
+ return false;
+ }
+ }
+}
+
+// Check if two spans are equal.
+bool CompareSpans(const RepeatedField<int>& span1,
+ const RepeatedField<int>& span2) {
+ if (span1.size() != span2.size()) return false;
+ for (int i = 0; i < span1.size(); i++) {
+ if (span1.Get(i) != span2.Get(i)) return false;
+ }
+ return true;
+}
+
+// Test fixture for source info tests, which check that source locations are
+// recorded correctly in FileDescriptorProto.source_code_info.location.
+class SourceInfoTest : public ParserTest {
+ protected:
+ // The parsed file (initialized by Parse()).
+ FileDescriptorProto file_;
+
+ // Parse the given text as a .proto file and populate the spans_ map with
+ // all the source location spans in its SourceCodeInfo table.
+ bool Parse(const char* text) {
+ ExtractMarkers(text);
+ SetupParser(text_without_markers_.c_str());
+ if (!parser_->Parse(input_.get(), &file_)) {
+ return false;
+ }
+
+ const SourceCodeInfo& source_info = file_.source_code_info();
+ for (int i = 0; i < source_info.location_size(); i++) {
+ const SourceCodeInfo::Location& location = source_info.location(i);
+ const Message* descriptor_proto = NULL;
+ const FieldDescriptor* field = NULL;
+ int index = 0;
+ if (!FollowPath(file_, location.path().begin(), location.path().end(),
+ &descriptor_proto, &field, &index)) {
+ return false;
+ }
+
+ spans_.insert(
+ std::make_pair(SpanKey(*descriptor_proto, field, index), &location));
+ }
+
+ return true;
+ }
+
+ virtual void TearDown() {
+ EXPECT_TRUE(spans_.empty())
+ << "Forgot to call HasSpan() for:\n"
+ << spans_.begin()->second->DebugString();
+ }
+
+ // -----------------------------------------------------------------
+ // HasSpan() checks that the span of source code delimited by the given
+ // tags (comments) correspond via the SourceCodeInfo table to the given
+ // part of the FileDescriptorProto. (If unclear, look at the actual tests;
+ // it should quickly become obvious.)
+
+ bool HasSpan(char start_marker, char end_marker,
+ const Message& descriptor_proto) {
+ return HasSpanWithComment(
+ start_marker, end_marker, descriptor_proto, NULL, -1, NULL, NULL, NULL);
+ }
+
+ bool HasSpanWithComment(char start_marker, char end_marker,
+ const Message& descriptor_proto,
+ const char* expected_leading_comments,
+ const char* expected_trailing_comments,
+ const char* expected_leading_detached_comments) {
+ return HasSpanWithComment(
+ start_marker, end_marker, descriptor_proto, NULL, -1,
+ expected_leading_comments, expected_trailing_comments,
+ expected_leading_detached_comments);
+ }
+
+ bool HasSpan(char start_marker, char end_marker,
+ const Message& descriptor_proto, const string& field_name) {
+ return HasSpan(start_marker, end_marker, descriptor_proto, field_name, -1);
+ }
+
+ bool HasSpan(char start_marker, char end_marker,
+ const Message& descriptor_proto, const string& field_name,
+ int index) {
+ return HasSpan(start_marker, end_marker, descriptor_proto,
+ field_name, index, NULL, NULL, NULL);
+ }
+
+ bool HasSpan(char start_marker, char end_marker,
+ const Message& descriptor_proto,
+ const string& field_name, int index,
+ const char* expected_leading_comments,
+ const char* expected_trailing_comments,
+ const char* expected_leading_detached_comments) {
+ const FieldDescriptor* field =
+ descriptor_proto.GetDescriptor()->FindFieldByName(field_name);
+ if (field == NULL) {
+ ADD_FAILURE() << descriptor_proto.GetDescriptor()->name()
+ << " has no such field: " << field_name;
+ return false;
+ }
+
+ return HasSpanWithComment(
+ start_marker, end_marker, descriptor_proto, field, index,
+ expected_leading_comments, expected_trailing_comments,
+ expected_leading_detached_comments);
+ }
+
+ bool HasSpan(const Message& descriptor_proto) {
+ return HasSpanWithComment(
+ '\0', '\0', descriptor_proto, NULL, -1, NULL, NULL, NULL);
+ }
+
+ bool HasSpan(const Message& descriptor_proto, const string& field_name) {
+ return HasSpan('\0', '\0', descriptor_proto, field_name, -1);
+ }
+
+ bool HasSpan(const Message& descriptor_proto, const string& field_name,
+ int index) {
+ return HasSpan('\0', '\0', descriptor_proto, field_name, index);
+ }
+
+ bool HasSpanWithComment(
+ char start_marker, char end_marker, const Message& descriptor_proto,
+ const FieldDescriptor* field, int index,
+ const char* expected_leading_comments,
+ const char* expected_trailing_comments,
+ const char* expected_leading_detached_comments) {
+ pair<SpanMap::iterator, SpanMap::iterator> range =
+ spans_.equal_range(SpanKey(descriptor_proto, field, index));
+
+ if (start_marker == '\0') {
+ if (range.first == range.second) {
+ return false;
+ } else {
+ spans_.erase(range.first);
+ return true;
+ }
+ } else {
+ pair<int, int> start_pos = FindOrDie(markers_, start_marker);
+ pair<int, int> end_pos = FindOrDie(markers_, end_marker);
+
+ RepeatedField<int> expected_span;
+ expected_span.Add(start_pos.first);
+ expected_span.Add(start_pos.second);
+ if (end_pos.first != start_pos.first) {
+ expected_span.Add(end_pos.first);
+ }
+ expected_span.Add(end_pos.second);
+
+ for (SpanMap::iterator iter = range.first; iter != range.second; ++iter) {
+ if (CompareSpans(expected_span, iter->second->span())) {
+ if (expected_leading_comments == NULL) {
+ EXPECT_FALSE(iter->second->has_leading_comments());
+ } else {
+ EXPECT_TRUE(iter->second->has_leading_comments());
+ EXPECT_EQ(expected_leading_comments,
+ iter->second->leading_comments());
+ }
+ if (expected_trailing_comments == NULL) {
+ EXPECT_FALSE(iter->second->has_trailing_comments());
+ } else {
+ EXPECT_TRUE(iter->second->has_trailing_comments());
+ EXPECT_EQ(expected_trailing_comments,
+ iter->second->trailing_comments());
+ }
+ if (expected_leading_detached_comments == NULL) {
+ EXPECT_EQ(0, iter->second->leading_detached_comments_size());
+ } else {
+ EXPECT_EQ(
+ expected_leading_detached_comments,
+ Join(iter->second->leading_detached_comments(), "\n"));
+ }
+
+ spans_.erase(iter);
+ return true;
+ }
+ }
+
+ return false;
+ }
+ }
+
+ private:
+ struct SpanKey {
+ const Message* descriptor_proto;
+ const FieldDescriptor* field;
+ int index;
+
+ inline SpanKey() {}
+ inline SpanKey(const Message& descriptor_proto_param,
+ const FieldDescriptor* field_param,
+ int index_param)
+ : descriptor_proto(&descriptor_proto_param), field(field_param),
+ index(index_param) {}
+
+ inline bool operator<(const SpanKey& other) const {
+ if (descriptor_proto < other.descriptor_proto) return true;
+ if (descriptor_proto > other.descriptor_proto) return false;
+ if (field < other.field) return true;
+ if (field > other.field) return false;
+ return index < other.index;
+ }
+ };
+
+ typedef multimap<SpanKey, const SourceCodeInfo::Location*> SpanMap;
+ SpanMap spans_;
+ map<char, pair<int, int> > markers_;
+ string text_without_markers_;
+
+ void ExtractMarkers(const char* text) {
+ markers_.clear();
+ text_without_markers_.clear();
+ int line = 0;
+ int column = 0;
+ while (*text != '\0') {
+ if (*text == '$') {
+ ++text;
+ GOOGLE_CHECK_NE('\0', *text);
+ if (*text == '$') {
+ text_without_markers_ += '$';
+ ++column;
+ } else {
+ markers_[*text] = std::make_pair(line, column);
+ ++text;
+ GOOGLE_CHECK_EQ('$', *text);
+ }
+ } else if (*text == '\n') {
+ ++line;
+ column = 0;
+ text_without_markers_ += *text;
+ } else {
+ text_without_markers_ += *text;
+ ++column;
+ }
+ ++text;
+ }
+ }
+};
+
+TEST_F(SourceInfoTest, BasicFileDecls) {
+ EXPECT_TRUE(Parse(
+ "$a$syntax = \"proto2\";$i$\n"
+ "package $b$foo.bar$c$;\n"
+ "import $d$\"baz.proto\"$e$;\n"
+ "import $f$\"qux.proto\"$g$;$h$\n"
+ "\n"
+ "// comment ignored\n"));
+
+ EXPECT_TRUE(HasSpan('a', 'h', file_));
+ EXPECT_TRUE(HasSpan('b', 'c', file_, "package"));
+ EXPECT_TRUE(HasSpan('d', 'e', file_, "dependency", 0));
+ EXPECT_TRUE(HasSpan('f', 'g', file_, "dependency", 1));
+ EXPECT_TRUE(HasSpan('a', 'i', file_, "syntax"));
+}
+
+TEST_F(SourceInfoTest, Messages) {
+ EXPECT_TRUE(Parse(
+ "$a$message $b$Foo$c$ {}$d$\n"
+ "$e$message $f$Bar$g$ {}$h$\n"));
+
+ EXPECT_TRUE(HasSpan('a', 'd', file_.message_type(0)));
+ EXPECT_TRUE(HasSpan('b', 'c', file_.message_type(0), "name"));
+ EXPECT_TRUE(HasSpan('e', 'h', file_.message_type(1)));
+ EXPECT_TRUE(HasSpan('f', 'g', file_.message_type(1), "name"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+}
+
+TEST_F(SourceInfoTest, Fields) {
+ EXPECT_TRUE(Parse(
+ "message Foo {\n"
+ " $a$optional$b$ $c$int32$d$ $e$bar$f$ = $g$1$h$;$i$\n"
+ " $j$repeated$k$ $l$X.Y$m$ $n$baz$o$ = $p$2$q$;$r$\n"
+ "}\n"));
+
+ const FieldDescriptorProto& field1 = file_.message_type(0).field(0);
+ const FieldDescriptorProto& field2 = file_.message_type(0).field(1);
+
+ EXPECT_TRUE(HasSpan('a', 'i', field1));
+ EXPECT_TRUE(HasSpan('a', 'b', field1, "label"));
+ EXPECT_TRUE(HasSpan('c', 'd', field1, "type"));
+ EXPECT_TRUE(HasSpan('e', 'f', field1, "name"));
+ EXPECT_TRUE(HasSpan('g', 'h', field1, "number"));
+
+ EXPECT_TRUE(HasSpan('j', 'r', field2));
+ EXPECT_TRUE(HasSpan('j', 'k', field2, "label"));
+ EXPECT_TRUE(HasSpan('l', 'm', field2, "type_name"));
+ EXPECT_TRUE(HasSpan('n', 'o', field2, "name"));
+ EXPECT_TRUE(HasSpan('p', 'q', field2, "number"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+}
+
+TEST_F(SourceInfoTest, Extensions) {
+ EXPECT_TRUE(Parse(
+ "$a$extend $b$Foo$c$ {\n"
+ " $d$optional$e$ int32 bar = 1;$f$\n"
+ " $g$repeated$h$ X.Y baz = 2;$i$\n"
+ "}$j$\n"
+ "$k$extend $l$Bar$m$ {\n"
+ " $n$optional int32 qux = 1;$o$\n"
+ "}$p$\n"));
+
+ const FieldDescriptorProto& field1 = file_.extension(0);
+ const FieldDescriptorProto& field2 = file_.extension(1);
+ const FieldDescriptorProto& field3 = file_.extension(2);
+
+ EXPECT_TRUE(HasSpan('a', 'j', file_, "extension"));
+ EXPECT_TRUE(HasSpan('k', 'p', file_, "extension"));
+
+ EXPECT_TRUE(HasSpan('d', 'f', field1));
+ EXPECT_TRUE(HasSpan('d', 'e', field1, "label"));
+ EXPECT_TRUE(HasSpan('b', 'c', field1, "extendee"));
+
+ EXPECT_TRUE(HasSpan('g', 'i', field2));
+ EXPECT_TRUE(HasSpan('g', 'h', field2, "label"));
+ EXPECT_TRUE(HasSpan('b', 'c', field2, "extendee"));
+
+ EXPECT_TRUE(HasSpan('n', 'o', field3));
+ EXPECT_TRUE(HasSpan('l', 'm', field3, "extendee"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(field1, "type"));
+ EXPECT_TRUE(HasSpan(field1, "name"));
+ EXPECT_TRUE(HasSpan(field1, "number"));
+ EXPECT_TRUE(HasSpan(field2, "type_name"));
+ EXPECT_TRUE(HasSpan(field2, "name"));
+ EXPECT_TRUE(HasSpan(field2, "number"));
+ EXPECT_TRUE(HasSpan(field3, "label"));
+ EXPECT_TRUE(HasSpan(field3, "type"));
+ EXPECT_TRUE(HasSpan(field3, "name"));
+ EXPECT_TRUE(HasSpan(field3, "number"));
+}
+
+TEST_F(SourceInfoTest, NestedExtensions) {
+ EXPECT_TRUE(Parse(
+ "message Message {\n"
+ " $a$extend $b$Foo$c$ {\n"
+ " $d$optional$e$ int32 bar = 1;$f$\n"
+ " $g$repeated$h$ X.Y baz = 2;$i$\n"
+ " }$j$\n"
+ " $k$extend $l$Bar$m$ {\n"
+ " $n$optional int32 qux = 1;$o$\n"
+ " }$p$\n"
+ "}\n"));
+
+ const FieldDescriptorProto& field1 = file_.message_type(0).extension(0);
+ const FieldDescriptorProto& field2 = file_.message_type(0).extension(1);
+ const FieldDescriptorProto& field3 = file_.message_type(0).extension(2);
+
+ EXPECT_TRUE(HasSpan('a', 'j', file_.message_type(0), "extension"));
+ EXPECT_TRUE(HasSpan('k', 'p', file_.message_type(0), "extension"));
+
+ EXPECT_TRUE(HasSpan('d', 'f', field1));
+ EXPECT_TRUE(HasSpan('d', 'e', field1, "label"));
+ EXPECT_TRUE(HasSpan('b', 'c', field1, "extendee"));
+
+ EXPECT_TRUE(HasSpan('g', 'i', field2));
+ EXPECT_TRUE(HasSpan('g', 'h', field2, "label"));
+ EXPECT_TRUE(HasSpan('b', 'c', field2, "extendee"));
+
+ EXPECT_TRUE(HasSpan('n', 'o', field3));
+ EXPECT_TRUE(HasSpan('l', 'm', field3, "extendee"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+ EXPECT_TRUE(HasSpan(field1, "type"));
+ EXPECT_TRUE(HasSpan(field1, "name"));
+ EXPECT_TRUE(HasSpan(field1, "number"));
+ EXPECT_TRUE(HasSpan(field2, "type_name"));
+ EXPECT_TRUE(HasSpan(field2, "name"));
+ EXPECT_TRUE(HasSpan(field2, "number"));
+ EXPECT_TRUE(HasSpan(field3, "label"));
+ EXPECT_TRUE(HasSpan(field3, "type"));
+ EXPECT_TRUE(HasSpan(field3, "name"));
+ EXPECT_TRUE(HasSpan(field3, "number"));
+}
+
+TEST_F(SourceInfoTest, ExtensionRanges) {
+ EXPECT_TRUE(Parse(
+ "message Message {\n"
+ " $a$extensions $b$1$c$ to $d$4$e$, $f$6$g$;$h$\n"
+ " $i$extensions $j$8$k$ to $l$max$m$;$n$\n"
+ "}\n"));
+
+ const DescriptorProto::ExtensionRange& range1 =
+ file_.message_type(0).extension_range(0);
+ const DescriptorProto::ExtensionRange& range2 =
+ file_.message_type(0).extension_range(1);
+ const DescriptorProto::ExtensionRange& range3 =
+ file_.message_type(0).extension_range(2);
+
+ EXPECT_TRUE(HasSpan('a', 'h', file_.message_type(0), "extension_range"));
+ EXPECT_TRUE(HasSpan('i', 'n', file_.message_type(0), "extension_range"));
+
+ EXPECT_TRUE(HasSpan('b', 'e', range1));
+ EXPECT_TRUE(HasSpan('b', 'c', range1, "start"));
+ EXPECT_TRUE(HasSpan('d', 'e', range1, "end"));
+
+ EXPECT_TRUE(HasSpan('f', 'g', range2));
+ EXPECT_TRUE(HasSpan('f', 'g', range2, "start"));
+ EXPECT_TRUE(HasSpan('f', 'g', range2, "end"));
+
+ EXPECT_TRUE(HasSpan('j', 'm', range3));
+ EXPECT_TRUE(HasSpan('j', 'k', range3, "start"));
+ EXPECT_TRUE(HasSpan('l', 'm', range3, "end"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+}
+
+TEST_F(SourceInfoTest, Oneofs) {
+ EXPECT_TRUE(Parse(
+ "message Foo {\n"
+ " $a$oneof $c$foo$d$ {\n"
+ " $e$int32$f$ $g$a$h$ = $i$1$j$;$k$\n"
+ " }$r$\n"
+ "}\n"));
+
+ const OneofDescriptorProto& oneof_decl = file_.message_type(0).oneof_decl(0);
+ const FieldDescriptorProto& field = file_.message_type(0).field(0);
+
+ EXPECT_TRUE(HasSpan('a', 'r', oneof_decl));
+ EXPECT_TRUE(HasSpan('c', 'd', oneof_decl, "name"));
+
+ EXPECT_TRUE(HasSpan('e', 'k', field));
+ EXPECT_TRUE(HasSpan('e', 'f', field, "type"));
+ EXPECT_TRUE(HasSpan('g', 'h', field, "name"));
+ EXPECT_TRUE(HasSpan('i', 'j', field, "number"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+}
+
+TEST_F(SourceInfoTest, NestedMessages) {
+ EXPECT_TRUE(Parse(
+ "message Foo {\n"
+ " $a$message $b$Bar$c$ {\n"
+ " $d$message $e$Baz$f$ {}$g$\n"
+ " }$h$\n"
+ " $i$message $j$Qux$k$ {}$l$\n"
+ "}\n"));
+
+ const DescriptorProto& bar = file_.message_type(0).nested_type(0);
+ const DescriptorProto& baz = bar.nested_type(0);
+ const DescriptorProto& qux = file_.message_type(0).nested_type(1);
+
+ EXPECT_TRUE(HasSpan('a', 'h', bar));
+ EXPECT_TRUE(HasSpan('b', 'c', bar, "name"));
+ EXPECT_TRUE(HasSpan('d', 'g', baz));
+ EXPECT_TRUE(HasSpan('e', 'f', baz, "name"));
+ EXPECT_TRUE(HasSpan('i', 'l', qux));
+ EXPECT_TRUE(HasSpan('j', 'k', qux, "name"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+}
+
+TEST_F(SourceInfoTest, Groups) {
+ EXPECT_TRUE(Parse(
+ "message Foo {\n"
+ " message Bar {}\n"
+ " $a$optional$b$ $c$group$d$ $e$Baz$f$ = $g$1$h$ {\n"
+ " $i$message Qux {}$j$\n"
+ " }$k$\n"
+ "}\n"));
+
+ const DescriptorProto& bar = file_.message_type(0).nested_type(0);
+ const DescriptorProto& baz = file_.message_type(0).nested_type(1);
+ const DescriptorProto& qux = baz.nested_type(0);
+ const FieldDescriptorProto& field = file_.message_type(0).field(0);
+
+ EXPECT_TRUE(HasSpan('a', 'k', field));
+ EXPECT_TRUE(HasSpan('a', 'b', field, "label"));
+ EXPECT_TRUE(HasSpan('c', 'd', field, "type"));
+ EXPECT_TRUE(HasSpan('e', 'f', field, "name"));
+ EXPECT_TRUE(HasSpan('e', 'f', field, "type_name"));
+ EXPECT_TRUE(HasSpan('g', 'h', field, "number"));
+
+ EXPECT_TRUE(HasSpan('a', 'k', baz));
+ EXPECT_TRUE(HasSpan('e', 'f', baz, "name"));
+ EXPECT_TRUE(HasSpan('i', 'j', qux));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+ EXPECT_TRUE(HasSpan(bar));
+ EXPECT_TRUE(HasSpan(bar, "name"));
+ EXPECT_TRUE(HasSpan(qux, "name"));
+}
+
+TEST_F(SourceInfoTest, Enums) {
+ EXPECT_TRUE(Parse(
+ "$a$enum $b$Foo$c$ {}$d$\n"
+ "$e$enum $f$Bar$g$ {}$h$\n"));
+
+ EXPECT_TRUE(HasSpan('a', 'd', file_.enum_type(0)));
+ EXPECT_TRUE(HasSpan('b', 'c', file_.enum_type(0), "name"));
+ EXPECT_TRUE(HasSpan('e', 'h', file_.enum_type(1)));
+ EXPECT_TRUE(HasSpan('f', 'g', file_.enum_type(1), "name"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+}
+
+TEST_F(SourceInfoTest, EnumValues) {
+ EXPECT_TRUE(Parse(
+ "enum Foo {\n"
+ " $a$BAR$b$ = $c$1$d$;$e$\n"
+ " $f$BAZ$g$ = $h$2$i$;$j$\n"
+ "}"));
+
+ const EnumValueDescriptorProto& bar = file_.enum_type(0).value(0);
+ const EnumValueDescriptorProto& baz = file_.enum_type(0).value(1);
+
+ EXPECT_TRUE(HasSpan('a', 'e', bar));
+ EXPECT_TRUE(HasSpan('a', 'b', bar, "name"));
+ EXPECT_TRUE(HasSpan('c', 'd', bar, "number"));
+ EXPECT_TRUE(HasSpan('f', 'j', baz));
+ EXPECT_TRUE(HasSpan('f', 'g', baz, "name"));
+ EXPECT_TRUE(HasSpan('h', 'i', baz, "number"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0)));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0), "name"));
+}
+
+TEST_F(SourceInfoTest, NestedEnums) {
+ EXPECT_TRUE(Parse(
+ "message Foo {\n"
+ " $a$enum $b$Bar$c$ {}$d$\n"
+ " $e$enum $f$Baz$g$ {}$h$\n"
+ "}\n"));
+
+ const EnumDescriptorProto& bar = file_.message_type(0).enum_type(0);
+ const EnumDescriptorProto& baz = file_.message_type(0).enum_type(1);
+
+ EXPECT_TRUE(HasSpan('a', 'd', bar));
+ EXPECT_TRUE(HasSpan('b', 'c', bar, "name"));
+ EXPECT_TRUE(HasSpan('e', 'h', baz));
+ EXPECT_TRUE(HasSpan('f', 'g', baz, "name"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+}
+
+TEST_F(SourceInfoTest, Services) {
+ EXPECT_TRUE(Parse(
+ "$a$service $b$Foo$c$ {}$d$\n"
+ "$e$service $f$Bar$g$ {}$h$\n"));
+
+ EXPECT_TRUE(HasSpan('a', 'd', file_.service(0)));
+ EXPECT_TRUE(HasSpan('b', 'c', file_.service(0), "name"));
+ EXPECT_TRUE(HasSpan('e', 'h', file_.service(1)));
+ EXPECT_TRUE(HasSpan('f', 'g', file_.service(1), "name"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+}
+
+TEST_F(SourceInfoTest, MethodsAndStreams) {
+ EXPECT_TRUE(Parse(
+ "service Foo {\n"
+ " $a$rpc $b$Bar$c$($d$X$e$) returns($f$Y$g$);$h$"
+ " $i$rpc $j$Baz$k$($l$Z$m$) returns($n$W$o$);$p$"
+ "}"));
+
+ const MethodDescriptorProto& bar = file_.service(0).method(0);
+ const MethodDescriptorProto& baz = file_.service(0).method(1);
+
+ EXPECT_TRUE(HasSpan('a', 'h', bar));
+ EXPECT_TRUE(HasSpan('b', 'c', bar, "name"));
+ EXPECT_TRUE(HasSpan('d', 'e', bar, "input_type"));
+ EXPECT_TRUE(HasSpan('f', 'g', bar, "output_type"));
+
+ EXPECT_TRUE(HasSpan('i', 'p', baz));
+ EXPECT_TRUE(HasSpan('j', 'k', baz, "name"));
+ EXPECT_TRUE(HasSpan('l', 'm', baz, "input_type"));
+ EXPECT_TRUE(HasSpan('n', 'o', baz, "output_type"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.service(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0), "name"));
+}
+
+
+TEST_F(SourceInfoTest, Options) {
+ EXPECT_TRUE(Parse(
+ "$a$option $b$foo$c$.$d$($e$bar.baz$f$)$g$ = "
+ "$h$123$i$;$j$\n"
+ "$k$option qux = $l$-123$m$;$n$\n"
+ "$o$option corge = $p$abc$q$;$r$\n"
+ "$s$option grault = $t$'blah'$u$;$v$\n"
+ "$w$option garply = $x${ yadda yadda }$y$;$z$\n"
+ "$0$option waldo = $1$123.0$2$;$3$\n"
+ ));
+
+ const UninterpretedOption& option1 = file_.options().uninterpreted_option(0);
+ const UninterpretedOption& option2 = file_.options().uninterpreted_option(1);
+ const UninterpretedOption& option3 = file_.options().uninterpreted_option(2);
+ const UninterpretedOption& option4 = file_.options().uninterpreted_option(3);
+ const UninterpretedOption& option5 = file_.options().uninterpreted_option(4);
+ const UninterpretedOption& option6 = file_.options().uninterpreted_option(5);
+
+ EXPECT_TRUE(HasSpan('a', 'j', file_.options()));
+ EXPECT_TRUE(HasSpan('a', 'j', option1));
+ EXPECT_TRUE(HasSpan('b', 'g', option1, "name"));
+ EXPECT_TRUE(HasSpan('b', 'c', option1.name(0)));
+ EXPECT_TRUE(HasSpan('b', 'c', option1.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan('d', 'g', option1.name(1)));
+ EXPECT_TRUE(HasSpan('e', 'f', option1.name(1), "name_part"));
+ EXPECT_TRUE(HasSpan('h', 'i', option1, "positive_int_value"));
+
+ EXPECT_TRUE(HasSpan('k', 'n', file_.options()));
+ EXPECT_TRUE(HasSpan('l', 'm', option2, "negative_int_value"));
+
+ EXPECT_TRUE(HasSpan('o', 'r', file_.options()));
+ EXPECT_TRUE(HasSpan('p', 'q', option3, "identifier_value"));
+
+ EXPECT_TRUE(HasSpan('s', 'v', file_.options()));
+ EXPECT_TRUE(HasSpan('t', 'u', option4, "string_value"));
+
+ EXPECT_TRUE(HasSpan('w', 'z', file_.options()));
+ EXPECT_TRUE(HasSpan('x', 'y', option5, "aggregate_value"));
+
+ EXPECT_TRUE(HasSpan('0', '3', file_.options()));
+ EXPECT_TRUE(HasSpan('1', '2', option6, "double_value"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(option2));
+ EXPECT_TRUE(HasSpan(option3));
+ EXPECT_TRUE(HasSpan(option4));
+ EXPECT_TRUE(HasSpan(option5));
+ EXPECT_TRUE(HasSpan(option6));
+ EXPECT_TRUE(HasSpan(option2, "name"));
+ EXPECT_TRUE(HasSpan(option3, "name"));
+ EXPECT_TRUE(HasSpan(option4, "name"));
+ EXPECT_TRUE(HasSpan(option5, "name"));
+ EXPECT_TRUE(HasSpan(option6, "name"));
+ EXPECT_TRUE(HasSpan(option2.name(0)));
+ EXPECT_TRUE(HasSpan(option3.name(0)));
+ EXPECT_TRUE(HasSpan(option4.name(0)));
+ EXPECT_TRUE(HasSpan(option5.name(0)));
+ EXPECT_TRUE(HasSpan(option6.name(0)));
+ EXPECT_TRUE(HasSpan(option2.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option3.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option4.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option5.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option6.name(0), "name_part"));
+}
+
+TEST_F(SourceInfoTest, ScopedOptions) {
+ EXPECT_TRUE(Parse(
+ "message Foo {\n"
+ " $a$option mopt = 1;$b$\n"
+ "}\n"
+ "enum Bar {\n"
+ " $c$option eopt = 1;$d$\n"
+ "}\n"
+ "service Baz {\n"
+ " $e$option sopt = 1;$f$\n"
+ " rpc M(X) returns(Y) {\n"
+ " $g$option mopt = 1;$h$\n"
+ " }\n"
+ " rpc MS4($1$stream$2$ X) returns($3$stream$4$ Y) {\n"
+ " $k$option mopt = 1;$l$\n"
+ " }\n"
+ "}\n"));
+
+ EXPECT_TRUE(HasSpan('a', 'b', file_.message_type(0).options()));
+ EXPECT_TRUE(HasSpan('c', 'd', file_.enum_type(0).options()));
+ EXPECT_TRUE(HasSpan('e', 'f', file_.service(0).options()));
+ EXPECT_TRUE(HasSpan('g', 'h', file_.service(0).method(0).options()));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.message_type(0).options()
+ .uninterpreted_option(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0).options()
+ .uninterpreted_option(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.message_type(0).options()
+ .uninterpreted_option(0).name(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0).options()
+ .uninterpreted_option(0).name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(file_.message_type(0).options()
+ .uninterpreted_option(0), "positive_int_value"));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0)));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0).options()
+ .uninterpreted_option(0)));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0).options()
+ .uninterpreted_option(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0).options()
+ .uninterpreted_option(0).name(0)));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0).options()
+ .uninterpreted_option(0).name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0).options()
+ .uninterpreted_option(0), "positive_int_value"));
+ EXPECT_TRUE(HasSpan(file_.service(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0).options()
+ .uninterpreted_option(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0).options()
+ .uninterpreted_option(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.service(0).options()
+ .uninterpreted_option(0).name(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0).options()
+ .uninterpreted_option(0).name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(file_.service(0).options()
+ .uninterpreted_option(0), "positive_int_value"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0), "input_type"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0), "output_type"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0).options()
+ .uninterpreted_option(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0).options()
+ .uninterpreted_option(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0).options()
+ .uninterpreted_option(0).name(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0).options()
+ .uninterpreted_option(0).name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(0).options()
+ .uninterpreted_option(0), "positive_int_value"));
+
+ EXPECT_TRUE(HasSpan('k', 'l', file_.service(0).method(1).options()));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1)));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1), "name"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1), "input_type"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1), "output_type"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1).options()
+ .uninterpreted_option(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1).options()
+ .uninterpreted_option(0), "name"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1).options()
+ .uninterpreted_option(0).name(0)));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1).options()
+ .uninterpreted_option(0).name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(file_.service(0).method(1).options()
+ .uninterpreted_option(0), "positive_int_value"));
+ EXPECT_TRUE(HasSpan('1', '2', file_.service(0).method(1),
+ "client_streaming"));
+ EXPECT_TRUE(HasSpan('3', '4', file_.service(0).method(1),
+ "server_streaming"));
+}
+
+TEST_F(SourceInfoTest, FieldOptions) {
+ // The actual "name = value" pairs are parsed by the same code as for
+ // top-level options so we won't re-test that -- just make sure that the
+ // syntax used for field options is understood.
+ EXPECT_TRUE(Parse(
+ "message Foo {"
+ " optional int32 bar = 1 "
+ "$a$[default=$b$123$c$,$d$opt1=123$e$,"
+ "$f$opt2='hi'$g$]$h$;"
+ "}\n"
+ ));
+
+ const FieldDescriptorProto& field = file_.message_type(0).field(0);
+ const UninterpretedOption& option1 = field.options().uninterpreted_option(0);
+ const UninterpretedOption& option2 = field.options().uninterpreted_option(1);
+
+ EXPECT_TRUE(HasSpan('a', 'h', field.options()));
+ EXPECT_TRUE(HasSpan('b', 'c', field, "default_value"));
+ EXPECT_TRUE(HasSpan('d', 'e', option1));
+ EXPECT_TRUE(HasSpan('f', 'g', option2));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.message_type(0)));
+ EXPECT_TRUE(HasSpan(file_.message_type(0), "name"));
+ EXPECT_TRUE(HasSpan(field));
+ EXPECT_TRUE(HasSpan(field, "label"));
+ EXPECT_TRUE(HasSpan(field, "type"));
+ EXPECT_TRUE(HasSpan(field, "name"));
+ EXPECT_TRUE(HasSpan(field, "number"));
+ EXPECT_TRUE(HasSpan(option1, "name"));
+ EXPECT_TRUE(HasSpan(option2, "name"));
+ EXPECT_TRUE(HasSpan(option1.name(0)));
+ EXPECT_TRUE(HasSpan(option2.name(0)));
+ EXPECT_TRUE(HasSpan(option1.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option2.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option1, "positive_int_value"));
+ EXPECT_TRUE(HasSpan(option2, "string_value"));
+}
+
+TEST_F(SourceInfoTest, EnumValueOptions) {
+ // The actual "name = value" pairs are parsed by the same code as for
+ // top-level options so we won't re-test that -- just make sure that the
+ // syntax used for enum options is understood.
+ EXPECT_TRUE(Parse(
+ "enum Foo {"
+ " BAR = 1 $a$[$b$opt1=123$c$,$d$opt2='hi'$e$]$f$;"
+ "}\n"
+ ));
+
+ const EnumValueDescriptorProto& value = file_.enum_type(0).value(0);
+ const UninterpretedOption& option1 = value.options().uninterpreted_option(0);
+ const UninterpretedOption& option2 = value.options().uninterpreted_option(1);
+
+ EXPECT_TRUE(HasSpan('a', 'f', value.options()));
+ EXPECT_TRUE(HasSpan('b', 'c', option1));
+ EXPECT_TRUE(HasSpan('d', 'e', option2));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0)));
+ EXPECT_TRUE(HasSpan(file_.enum_type(0), "name"));
+ EXPECT_TRUE(HasSpan(value));
+ EXPECT_TRUE(HasSpan(value, "name"));
+ EXPECT_TRUE(HasSpan(value, "number"));
+ EXPECT_TRUE(HasSpan(option1, "name"));
+ EXPECT_TRUE(HasSpan(option2, "name"));
+ EXPECT_TRUE(HasSpan(option1.name(0)));
+ EXPECT_TRUE(HasSpan(option2.name(0)));
+ EXPECT_TRUE(HasSpan(option1.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option2.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(option1, "positive_int_value"));
+ EXPECT_TRUE(HasSpan(option2, "string_value"));
+}
+
+TEST_F(SourceInfoTest, DocComments) {
+ EXPECT_TRUE(Parse(
+ "// Foo leading\n"
+ "// line 2\n"
+ "$a$message Foo {\n"
+ " // Foo trailing\n"
+ " // line 2\n"
+ "\n"
+ " // detached\n"
+ "\n"
+ " // bar leading\n"
+ " $b$optional int32 bar = 1;$c$\n"
+ " // bar trailing\n"
+ "}$d$\n"
+ "// ignored\n"
+ ));
+
+ const DescriptorProto& foo = file_.message_type(0);
+ const FieldDescriptorProto& bar = foo.field(0);
+
+ EXPECT_TRUE(HasSpanWithComment('a', 'd', foo,
+ " Foo leading\n line 2\n",
+ " Foo trailing\n line 2\n",
+ NULL));
+ EXPECT_TRUE(HasSpanWithComment('b', 'c', bar,
+ " bar leading\n",
+ " bar trailing\n",
+ " detached\n"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(foo, "name"));
+ EXPECT_TRUE(HasSpan(bar, "label"));
+ EXPECT_TRUE(HasSpan(bar, "type"));
+ EXPECT_TRUE(HasSpan(bar, "name"));
+ EXPECT_TRUE(HasSpan(bar, "number"));
+}
+
+TEST_F(SourceInfoTest, DocComments2) {
+ EXPECT_TRUE(Parse(
+ "// detached before message.\n"
+ "\n"
+ "// Foo leading\n"
+ "// line 2\n"
+ "$a$message Foo {\n"
+ " /* Foo trailing\n"
+ " * line 2 */\n"
+ " // detached\n"
+ " /* bar leading\n"
+ " */"
+ " $b$optional int32 bar = 1;$c$ // bar trailing\n"
+ " // ignored detached\n"
+ "}$d$\n"
+ "// ignored\n"
+ "\n"
+ "// detached before option\n"
+ "\n"
+ "// option leading\n"
+ "$e$option baz = 123;$f$\n"
+ "// option trailing\n"
+ ));
+
+ const DescriptorProto& foo = file_.message_type(0);
+ const FieldDescriptorProto& bar = foo.field(0);
+ const UninterpretedOption& baz = file_.options().uninterpreted_option(0);
+
+ EXPECT_TRUE(HasSpanWithComment('a', 'd', foo,
+ " Foo leading\n line 2\n",
+ " Foo trailing\n line 2 ",
+ " detached before message.\n"));
+ EXPECT_TRUE(HasSpanWithComment('b', 'c', bar,
+ " bar leading\n",
+ " bar trailing\n",
+ " detached\n"));
+ EXPECT_TRUE(HasSpanWithComment('e', 'f', baz,
+ " option leading\n",
+ " option trailing\n",
+ " detached before option\n"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(foo, "name"));
+ EXPECT_TRUE(HasSpan(bar, "label"));
+ EXPECT_TRUE(HasSpan(bar, "type"));
+ EXPECT_TRUE(HasSpan(bar, "name"));
+ EXPECT_TRUE(HasSpan(bar, "number"));
+ EXPECT_TRUE(HasSpan(file_.options()));
+ EXPECT_TRUE(HasSpan(baz, "name"));
+ EXPECT_TRUE(HasSpan(baz.name(0)));
+ EXPECT_TRUE(HasSpan(baz.name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(baz, "positive_int_value"));
+}
+
+TEST_F(SourceInfoTest, DocComments3) {
+ EXPECT_TRUE(Parse(
+ "$a$message Foo {\n"
+ " // bar leading\n"
+ " $b$optional int32 bar = 1 [(baz.qux) = {}];$c$\n"
+ " // bar trailing\n"
+ "}$d$\n"
+ "// ignored\n"
+ ));
+
+ const DescriptorProto& foo = file_.message_type(0);
+ const FieldDescriptorProto& bar = foo.field(0);
+
+ EXPECT_TRUE(HasSpanWithComment('b', 'c', bar,
+ " bar leading\n",
+ " bar trailing\n",
+ NULL));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(foo));
+ EXPECT_TRUE(HasSpan(foo, "name"));
+ EXPECT_TRUE(HasSpan(bar, "label"));
+ EXPECT_TRUE(HasSpan(bar, "type"));
+ EXPECT_TRUE(HasSpan(bar, "name"));
+ EXPECT_TRUE(HasSpan(bar, "number"));
+ EXPECT_TRUE(HasSpan(bar.options()));
+ EXPECT_TRUE(HasSpan(bar.options().uninterpreted_option(0)));
+ EXPECT_TRUE(HasSpan(bar.options().uninterpreted_option(0), "name"));
+ EXPECT_TRUE(HasSpan(bar.options().uninterpreted_option(0).name(0)));
+ EXPECT_TRUE(HasSpan(
+ bar.options().uninterpreted_option(0).name(0), "name_part"));
+ EXPECT_TRUE(HasSpan(
+ bar.options().uninterpreted_option(0), "aggregate_value"));
+}
+
+TEST_F(SourceInfoTest, DocCommentsTopLevel) {
+ EXPECT_TRUE(Parse(
+ "// detached before syntax paragraph 1\n"
+ "\n"
+ "// detached before syntax paragraph 2\n"
+ "\n"
+ "// syntax leading\n"
+ "$a$syntax = \"proto2\";$b$\n"
+ "// syntax trailing\n"
+ "\n"
+ "// syntax-package detached comments\n"
+ "\n"
+ ";\n"
+ "\n"
+ "// detached after empty before package\n"
+ "\n"
+ "// package leading\n"
+ "package $c$foo$d$;\n"
+ "// package trailing\n"
+ "\n"
+ "// ignored detach\n"
+ "\n"));
+
+ EXPECT_TRUE(HasSpan('a', 'b', file_, "syntax", -1,
+ " syntax leading\n",
+ " syntax trailing\n",
+ " detached before syntax paragraph 1\n"
+ "\n"
+ " detached before syntax paragraph 2\n"));
+ EXPECT_TRUE(HasSpan('c', 'd', file_, "package", -1,
+ " package leading\n",
+ " package trailing\n",
+ " syntax-package detached comments\n"
+ "\n"
+ " detached after empty before package\n"));
+
+ // ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+}
+
+TEST_F(SourceInfoTest, DocCommentsOneof) {
+ EXPECT_TRUE(Parse(
+ "// Foo leading\n"
+ "$a$message Foo {\n"
+ " /* Foo trailing\n"
+ " */\n"
+ " // detached before oneof\n"
+ " /* bar leading\n"
+ " * line 2 */\n"
+ " $b$oneof bar {\n"
+ " /* bar trailing\n"
+ " * line 2 */\n"
+ " // detached before bar_int\n"
+ " /* bar_int leading\n"
+ " */\n"
+ " $c$int32 bar_int = 1;$d$ // bar_int trailing\n"
+ " // detach comment ignored\n"
+ " }$e$\n"
+ "}$f$\n"));
+
+ const DescriptorProto& foo = file_.message_type(0);
+ const OneofDescriptorProto& bar = foo.oneof_decl(0);
+ const FieldDescriptorProto& bar_int = foo.field(0);
+
+ EXPECT_TRUE(HasSpanWithComment('a', 'f', foo,
+ " Foo leading\n",
+ " Foo trailing\n",
+ NULL));
+ EXPECT_TRUE(HasSpanWithComment('b', 'e', bar,
+ " bar leading\n line 2 ",
+ " bar trailing\n line 2 ",
+ " detached before oneof\n"));
+ EXPECT_TRUE(HasSpanWithComment('c', 'd', bar_int,
+ " bar_int leading\n",
+ " bar_int trailing\n",
+ " detached before bar_int\n"));
+
+ // Ignore these.
+ EXPECT_TRUE(HasSpan(file_));
+ EXPECT_TRUE(HasSpan(foo, "name"));
+ EXPECT_TRUE(HasSpan(bar, "name"));
+ EXPECT_TRUE(HasSpan(bar_int, "type"));
+ EXPECT_TRUE(HasSpan(bar_int, "name"));
+ EXPECT_TRUE(HasSpan(bar_int, "number"));
+}
+
+// ===================================================================
+
+} // anonymous namespace
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.cc
new file mode 100644
index 0000000000..2ff50f61f4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.cc
@@ -0,0 +1,194 @@
+// 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)
+
+#include <google/protobuf/compiler/plugin.h>
+
+#include <iostream>
+#include <set>
+
+#ifdef _WIN32
+#include <io.h>
+#include <fcntl.h>
+#ifndef STDIN_FILENO
+#define STDIN_FILENO 0
+#endif
+#ifndef STDOUT_FILENO
+#define STDOUT_FILENO 1
+#endif
+#else
+#include <unistd.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/compiler/plugin.pb.h>
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+class GeneratorResponseContext : public GeneratorContext {
+ public:
+ GeneratorResponseContext(CodeGeneratorResponse* response,
+ const vector<const FileDescriptor*>& parsed_files)
+ : response_(response),
+ parsed_files_(parsed_files) {}
+ virtual ~GeneratorResponseContext() {}
+
+ // implements GeneratorContext --------------------------------------
+
+ virtual io::ZeroCopyOutputStream* Open(const string& filename) {
+ CodeGeneratorResponse::File* file = response_->add_file();
+ file->set_name(filename);
+ return new io::StringOutputStream(file->mutable_content());
+ }
+
+ virtual io::ZeroCopyOutputStream* OpenForInsert(
+ const string& filename, const string& insertion_point) {
+ CodeGeneratorResponse::File* file = response_->add_file();
+ file->set_name(filename);
+ file->set_insertion_point(insertion_point);
+ return new io::StringOutputStream(file->mutable_content());
+ }
+
+ void ListParsedFiles(vector<const FileDescriptor*>* output) {
+ *output = parsed_files_;
+ }
+
+ private:
+ CodeGeneratorResponse* response_;
+ const vector<const FileDescriptor*>& parsed_files_;
+};
+
+bool GenerateCode(const CodeGeneratorRequest& request,
+ const CodeGenerator& generator, CodeGeneratorResponse* response,
+ string* error_msg) {
+ DescriptorPool pool;
+ for (int i = 0; i < request.proto_file_size(); i++) {
+ const FileDescriptor* file = pool.BuildFile(request.proto_file(i));
+ if (file == NULL) {
+ // BuildFile() already wrote an error message.
+ return false;
+ }
+ }
+
+ vector<const FileDescriptor*> parsed_files;
+ for (int i = 0; i < request.file_to_generate_size(); i++) {
+ parsed_files.push_back(pool.FindFileByName(request.file_to_generate(i)));
+ if (parsed_files.back() == NULL) {
+ *error_msg = "protoc asked plugin to generate a file but "
+ "did not provide a descriptor for the file: " +
+ request.file_to_generate(i);
+ return false;
+ }
+ }
+
+ GeneratorResponseContext context(response, parsed_files);
+
+ if (generator.HasGenerateAll()) {
+ string error;
+ bool succeeded = generator.GenerateAll(
+ parsed_files, request.parameter(), &context, &error);
+
+ if (!succeeded && error.empty()) {
+ error = "Code generator returned false but provided no error "
+ "description.";
+ }
+ if (!error.empty()) {
+ response->set_error(error);
+ }
+ } else {
+ for (int i = 0; i < parsed_files.size(); i++) {
+ const FileDescriptor* file = parsed_files[i];
+
+ string error;
+ bool succeeded = generator.Generate(
+ file, request.parameter(), &context, &error);
+
+ if (!succeeded && error.empty()) {
+ error = "Code generator returned false but provided no error "
+ "description.";
+ }
+ if (!error.empty()) {
+ response->set_error(file->name() + ": " + error);
+ break;
+ }
+ }
+ }
+
+ return true;
+}
+
+int PluginMain(int argc, char* argv[], const CodeGenerator* generator) {
+
+ if (argc > 1) {
+ std::cerr << argv[0] << ": Unknown option: " << argv[1] << std::endl;
+ return 1;
+ }
+
+#ifdef _WIN32
+ _setmode(STDIN_FILENO, _O_BINARY);
+ _setmode(STDOUT_FILENO, _O_BINARY);
+#endif
+
+ CodeGeneratorRequest request;
+ if (!request.ParseFromFileDescriptor(STDIN_FILENO)) {
+ std::cerr << argv[0] << ": protoc sent unparseable request to plugin."
+ << std::endl;
+ return 1;
+ }
+
+ string error_msg;
+ CodeGeneratorResponse response;
+
+ if (GenerateCode(request, *generator, &response, &error_msg)) {
+ if (!response.SerializeToFileDescriptor(STDOUT_FILENO)) {
+ std::cerr << argv[0] << ": Error writing to stdout." << std::endl;
+ return 1;
+ }
+ } else {
+ if (!error_msg.empty()) {
+ std::cerr << argv[0] << ": " << error_msg << std::endl;
+ }
+ return 1;
+ }
+
+ return 0;
+}
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.h
new file mode 100644
index 0000000000..d2793a9ff1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.h
@@ -0,0 +1,90 @@
+// 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)
+//
+// Front-end for protoc code generator plugins written in C++.
+//
+// To implement a protoc plugin in C++, simply write an implementation of
+// CodeGenerator, then create a main() function like:
+// int main(int argc, char* argv[]) {
+// MyCodeGenerator generator;
+// return google::protobuf::compiler::PluginMain(argc, argv, &generator);
+// }
+// You must link your plugin against libprotobuf and libprotoc.
+//
+// The core part of PluginMain is to invoke the given CodeGenerator on a
+// CodeGeneratorRequest to generate a CodeGeneratorResponse. This part is
+// abstracted out and made into function GenerateCode so that it can be reused,
+// for example, to implement a variant of PluginMain that does some
+// preprocessing on the input CodeGeneratorRequest before feeding the request
+// to the given code generator.
+//
+// To get protoc to use the plugin, do one of the following:
+// * Place the plugin binary somewhere in the PATH and give it the name
+// "protoc-gen-NAME" (replacing "NAME" with the name of your plugin). If you
+// then invoke protoc with the parameter --NAME_out=OUT_DIR (again, replace
+// "NAME" with your plugin's name), protoc will invoke your plugin to generate
+// the output, which will be placed in OUT_DIR.
+// * Place the plugin binary anywhere, with any name, and pass the --plugin
+// parameter to protoc to direct it to your plugin like so:
+// protoc --plugin=protoc-gen-NAME=path/to/mybinary --NAME_out=OUT_DIR
+// On Windows, make sure to include the .exe suffix:
+// protoc --plugin=protoc-gen-NAME=path/to/mybinary.exe --NAME_out=OUT_DIR
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_PLUGIN_H__
+#define GOOGLE_PROTOBUF_COMPILER_PLUGIN_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+class CodeGenerator; // code_generator.h
+class CodeGeneratorRequest;
+class CodeGeneratorResponse;
+
+// Implements main() for a protoc plugin exposing the given code generator.
+LIBPROTOC_EXPORT int PluginMain(int argc, char* argv[], const CodeGenerator* generator);
+
+// Generates code using the given code generator. Returns true if the code
+// generation is successful. If the code geneartion fails, error_msg may be
+// populated to describe the failure cause.
+bool GenerateCode(const CodeGeneratorRequest& request,
+ const CodeGenerator& generator, CodeGeneratorResponse* response,
+ string* error_msg);
+
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_PLUGIN_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.cc
new file mode 100644
index 0000000000..9064c38234
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.cc
@@ -0,0 +1,1605 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/compiler/plugin.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/compiler/plugin.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+namespace {
+
+const ::google::protobuf::Descriptor* CodeGeneratorRequest_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ CodeGeneratorRequest_reflection_ = NULL;
+const ::google::protobuf::Descriptor* CodeGeneratorResponse_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ CodeGeneratorResponse_reflection_ = NULL;
+const ::google::protobuf::Descriptor* CodeGeneratorResponse_File_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ CodeGeneratorResponse_File_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/compiler/plugin.proto");
+ GOOGLE_CHECK(file != NULL);
+ CodeGeneratorRequest_descriptor_ = file->message_type(0);
+ static const int CodeGeneratorRequest_offsets_[3] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorRequest, file_to_generate_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorRequest, parameter_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorRequest, proto_file_),
+ };
+ CodeGeneratorRequest_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ CodeGeneratorRequest_descriptor_,
+ CodeGeneratorRequest::default_instance_,
+ CodeGeneratorRequest_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorRequest, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(CodeGeneratorRequest),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorRequest, _internal_metadata_),
+ -1);
+ CodeGeneratorResponse_descriptor_ = file->message_type(1);
+ static const int CodeGeneratorResponse_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse, error_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse, file_),
+ };
+ CodeGeneratorResponse_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ CodeGeneratorResponse_descriptor_,
+ CodeGeneratorResponse::default_instance_,
+ CodeGeneratorResponse_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(CodeGeneratorResponse),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse, _internal_metadata_),
+ -1);
+ CodeGeneratorResponse_File_descriptor_ = CodeGeneratorResponse_descriptor_->nested_type(0);
+ static const int CodeGeneratorResponse_File_offsets_[3] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse_File, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse_File, insertion_point_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse_File, content_),
+ };
+ CodeGeneratorResponse_File_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ CodeGeneratorResponse_File_descriptor_,
+ CodeGeneratorResponse_File::default_instance_,
+ CodeGeneratorResponse_File_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse_File, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(CodeGeneratorResponse_File),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(CodeGeneratorResponse_File, _internal_metadata_),
+ -1);
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ CodeGeneratorRequest_descriptor_, &CodeGeneratorRequest::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ CodeGeneratorResponse_descriptor_, &CodeGeneratorResponse::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ CodeGeneratorResponse_File_descriptor_, &CodeGeneratorResponse_File::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fcompiler_2fplugin_2eproto() {
+ delete CodeGeneratorRequest::default_instance_;
+ delete CodeGeneratorRequest_reflection_;
+ delete CodeGeneratorResponse::default_instance_;
+ delete CodeGeneratorResponse_reflection_;
+ delete CodeGeneratorResponse_File::default_instance_;
+ delete CodeGeneratorResponse_File_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n%google/protobuf/compiler/plugin.proto\022"
+ "\030google.protobuf.compiler\032 google/protob"
+ "uf/descriptor.proto\"}\n\024CodeGeneratorRequ"
+ "est\022\030\n\020file_to_generate\030\001 \003(\t\022\021\n\tparamet"
+ "er\030\002 \001(\t\0228\n\nproto_file\030\017 \003(\0132$.google.pr"
+ "otobuf.FileDescriptorProto\"\252\001\n\025CodeGener"
+ "atorResponse\022\r\n\005error\030\001 \001(\t\022B\n\004file\030\017 \003("
+ "\01324.google.protobuf.compiler.CodeGenerat"
+ "orResponse.File\032>\n\004File\022\014\n\004name\030\001 \001(\t\022\027\n"
+ "\017insertion_point\030\002 \001(\t\022\017\n\007content\030\017 \001(\tB"
+ "7\n\034com.google.protobuf.compilerB\014PluginP"
+ "rotosZ\tplugin_go", 456);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/compiler/plugin.proto", &protobuf_RegisterTypes);
+ CodeGeneratorRequest::default_instance_ = new CodeGeneratorRequest();
+ CodeGeneratorResponse::default_instance_ = new CodeGeneratorResponse();
+ CodeGeneratorResponse_File::default_instance_ = new CodeGeneratorResponse_File();
+ CodeGeneratorRequest::default_instance_->InitAsDefaultInstance();
+ CodeGeneratorResponse::default_instance_->InitAsDefaultInstance();
+ CodeGeneratorResponse_File::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fcompiler_2fplugin_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fcompiler_2fplugin_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fcompiler_2fplugin_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fcompiler_2fplugin_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int CodeGeneratorRequest::kFileToGenerateFieldNumber;
+const int CodeGeneratorRequest::kParameterFieldNumber;
+const int CodeGeneratorRequest::kProtoFileFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+CodeGeneratorRequest::CodeGeneratorRequest()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.compiler.CodeGeneratorRequest)
+}
+
+void CodeGeneratorRequest::InitAsDefaultInstance() {
+}
+
+CodeGeneratorRequest::CodeGeneratorRequest(const CodeGeneratorRequest& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.compiler.CodeGeneratorRequest)
+}
+
+void CodeGeneratorRequest::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ parameter_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+CodeGeneratorRequest::~CodeGeneratorRequest() {
+ // @@protoc_insertion_point(destructor:google.protobuf.compiler.CodeGeneratorRequest)
+ SharedDtor();
+}
+
+void CodeGeneratorRequest::SharedDtor() {
+ parameter_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void CodeGeneratorRequest::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* CodeGeneratorRequest::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return CodeGeneratorRequest_descriptor_;
+}
+
+const CodeGeneratorRequest& CodeGeneratorRequest::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ return *default_instance_;
+}
+
+CodeGeneratorRequest* CodeGeneratorRequest::default_instance_ = NULL;
+
+CodeGeneratorRequest* CodeGeneratorRequest::New(::google::protobuf::Arena* arena) const {
+ CodeGeneratorRequest* n = new CodeGeneratorRequest;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void CodeGeneratorRequest::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.compiler.CodeGeneratorRequest)
+ if (has_parameter()) {
+ parameter_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ file_to_generate_.Clear();
+ proto_file_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool CodeGeneratorRequest::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.compiler.CodeGeneratorRequest)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated string file_to_generate = 1;
+ case 1: {
+ if (tag == 10) {
+ parse_file_to_generate:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->add_file_to_generate()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->file_to_generate(this->file_to_generate_size() - 1).data(),
+ this->file_to_generate(this->file_to_generate_size() - 1).length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.compiler.CodeGeneratorRequest.file_to_generate");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(10)) goto parse_file_to_generate;
+ if (input->ExpectTag(18)) goto parse_parameter;
+ break;
+ }
+
+ // optional string parameter = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_parameter:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_parameter()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->parameter().data(), this->parameter().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.compiler.CodeGeneratorRequest.parameter");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(122)) goto parse_proto_file;
+ break;
+ }
+
+ // repeated .google.protobuf.FileDescriptorProto proto_file = 15;
+ case 15: {
+ if (tag == 122) {
+ parse_proto_file:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_proto_file:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_proto_file()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(122)) goto parse_loop_proto_file;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.compiler.CodeGeneratorRequest)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.compiler.CodeGeneratorRequest)
+ return false;
+#undef DO_
+}
+
+void CodeGeneratorRequest::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.compiler.CodeGeneratorRequest)
+ // repeated string file_to_generate = 1;
+ for (int i = 0; i < this->file_to_generate_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->file_to_generate(i).data(), this->file_to_generate(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorRequest.file_to_generate");
+ ::google::protobuf::internal::WireFormatLite::WriteString(
+ 1, this->file_to_generate(i), output);
+ }
+
+ // optional string parameter = 2;
+ if (has_parameter()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->parameter().data(), this->parameter().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorRequest.parameter");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->parameter(), output);
+ }
+
+ // repeated .google.protobuf.FileDescriptorProto proto_file = 15;
+ for (unsigned int i = 0, n = this->proto_file_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 15, this->proto_file(i), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.compiler.CodeGeneratorRequest)
+}
+
+::google::protobuf::uint8* CodeGeneratorRequest::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.compiler.CodeGeneratorRequest)
+ // repeated string file_to_generate = 1;
+ for (int i = 0; i < this->file_to_generate_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->file_to_generate(i).data(), this->file_to_generate(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorRequest.file_to_generate");
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteStringToArray(1, this->file_to_generate(i), target);
+ }
+
+ // optional string parameter = 2;
+ if (has_parameter()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->parameter().data(), this->parameter().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorRequest.parameter");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->parameter(), target);
+ }
+
+ // repeated .google.protobuf.FileDescriptorProto proto_file = 15;
+ for (unsigned int i = 0, n = this->proto_file_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 15, this->proto_file(i), false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.compiler.CodeGeneratorRequest)
+ return target;
+}
+
+int CodeGeneratorRequest::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.compiler.CodeGeneratorRequest)
+ int total_size = 0;
+
+ // optional string parameter = 2;
+ if (has_parameter()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->parameter());
+ }
+
+ // repeated string file_to_generate = 1;
+ total_size += 1 * this->file_to_generate_size();
+ for (int i = 0; i < this->file_to_generate_size(); i++) {
+ total_size += ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->file_to_generate(i));
+ }
+
+ // repeated .google.protobuf.FileDescriptorProto proto_file = 15;
+ total_size += 1 * this->proto_file_size();
+ for (int i = 0; i < this->proto_file_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->proto_file(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void CodeGeneratorRequest::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.compiler.CodeGeneratorRequest)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const CodeGeneratorRequest* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const CodeGeneratorRequest>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.compiler.CodeGeneratorRequest)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.compiler.CodeGeneratorRequest)
+ MergeFrom(*source);
+ }
+}
+
+void CodeGeneratorRequest::MergeFrom(const CodeGeneratorRequest& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.compiler.CodeGeneratorRequest)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ file_to_generate_.MergeFrom(from.file_to_generate_);
+ proto_file_.MergeFrom(from.proto_file_);
+ if (from._has_bits_[1 / 32] & (0xffu << (1 % 32))) {
+ if (from.has_parameter()) {
+ set_has_parameter();
+ parameter_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.parameter_);
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void CodeGeneratorRequest::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.compiler.CodeGeneratorRequest)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void CodeGeneratorRequest::CopyFrom(const CodeGeneratorRequest& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.compiler.CodeGeneratorRequest)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool CodeGeneratorRequest::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->proto_file())) return false;
+ return true;
+}
+
+void CodeGeneratorRequest::Swap(CodeGeneratorRequest* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void CodeGeneratorRequest::InternalSwap(CodeGeneratorRequest* other) {
+ file_to_generate_.UnsafeArenaSwap(&other->file_to_generate_);
+ parameter_.Swap(&other->parameter_);
+ proto_file_.UnsafeArenaSwap(&other->proto_file_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata CodeGeneratorRequest::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = CodeGeneratorRequest_descriptor_;
+ metadata.reflection = CodeGeneratorRequest_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// CodeGeneratorRequest
+
+// repeated string file_to_generate = 1;
+int CodeGeneratorRequest::file_to_generate_size() const {
+ return file_to_generate_.size();
+}
+void CodeGeneratorRequest::clear_file_to_generate() {
+ file_to_generate_.Clear();
+}
+ const ::std::string& CodeGeneratorRequest::file_to_generate(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_.Get(index);
+}
+ ::std::string* CodeGeneratorRequest::mutable_file_to_generate(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_.Mutable(index);
+}
+ void CodeGeneratorRequest::set_file_to_generate(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ file_to_generate_.Mutable(index)->assign(value);
+}
+ void CodeGeneratorRequest::set_file_to_generate(int index, const char* value) {
+ file_to_generate_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+ void CodeGeneratorRequest::set_file_to_generate(int index, const char* value, size_t size) {
+ file_to_generate_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+ ::std::string* CodeGeneratorRequest::add_file_to_generate() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_.Add();
+}
+ void CodeGeneratorRequest::add_file_to_generate(const ::std::string& value) {
+ file_to_generate_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+ void CodeGeneratorRequest::add_file_to_generate(const char* value) {
+ file_to_generate_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+ void CodeGeneratorRequest::add_file_to_generate(const char* value, size_t size) {
+ file_to_generate_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+ const ::google::protobuf::RepeatedPtrField< ::std::string>&
+CodeGeneratorRequest::file_to_generate() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_;
+}
+ ::google::protobuf::RepeatedPtrField< ::std::string>*
+CodeGeneratorRequest::mutable_file_to_generate() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return &file_to_generate_;
+}
+
+// optional string parameter = 2;
+bool CodeGeneratorRequest::has_parameter() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void CodeGeneratorRequest::set_has_parameter() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void CodeGeneratorRequest::clear_has_parameter() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void CodeGeneratorRequest::clear_parameter() {
+ parameter_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_parameter();
+}
+ const ::std::string& CodeGeneratorRequest::parameter() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+ return parameter_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorRequest::set_parameter(const ::std::string& value) {
+ set_has_parameter();
+ parameter_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+ void CodeGeneratorRequest::set_parameter(const char* value) {
+ set_has_parameter();
+ parameter_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+ void CodeGeneratorRequest::set_parameter(const char* value, size_t size) {
+ set_has_parameter();
+ parameter_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+ ::std::string* CodeGeneratorRequest::mutable_parameter() {
+ set_has_parameter();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+ return parameter_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* CodeGeneratorRequest::release_parameter() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+ clear_has_parameter();
+ return parameter_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorRequest::set_allocated_parameter(::std::string* parameter) {
+ if (parameter != NULL) {
+ set_has_parameter();
+ } else {
+ clear_has_parameter();
+ }
+ parameter_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), parameter);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+
+// repeated .google.protobuf.FileDescriptorProto proto_file = 15;
+int CodeGeneratorRequest::proto_file_size() const {
+ return proto_file_.size();
+}
+void CodeGeneratorRequest::clear_proto_file() {
+ proto_file_.Clear();
+}
+const ::google::protobuf::FileDescriptorProto& CodeGeneratorRequest::proto_file(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_.Get(index);
+}
+::google::protobuf::FileDescriptorProto* CodeGeneratorRequest::mutable_proto_file(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_.Mutable(index);
+}
+::google::protobuf::FileDescriptorProto* CodeGeneratorRequest::add_proto_file() {
+ // @@protoc_insertion_point(field_add:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >*
+CodeGeneratorRequest::mutable_proto_file() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return &proto_file_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >&
+CodeGeneratorRequest::proto_file() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int CodeGeneratorResponse_File::kNameFieldNumber;
+const int CodeGeneratorResponse_File::kInsertionPointFieldNumber;
+const int CodeGeneratorResponse_File::kContentFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+CodeGeneratorResponse_File::CodeGeneratorResponse_File()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.compiler.CodeGeneratorResponse.File)
+}
+
+void CodeGeneratorResponse_File::InitAsDefaultInstance() {
+}
+
+CodeGeneratorResponse_File::CodeGeneratorResponse_File(const CodeGeneratorResponse_File& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.compiler.CodeGeneratorResponse.File)
+}
+
+void CodeGeneratorResponse_File::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ insertion_point_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ content_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+CodeGeneratorResponse_File::~CodeGeneratorResponse_File() {
+ // @@protoc_insertion_point(destructor:google.protobuf.compiler.CodeGeneratorResponse.File)
+ SharedDtor();
+}
+
+void CodeGeneratorResponse_File::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ insertion_point_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ content_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void CodeGeneratorResponse_File::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* CodeGeneratorResponse_File::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return CodeGeneratorResponse_File_descriptor_;
+}
+
+const CodeGeneratorResponse_File& CodeGeneratorResponse_File::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ return *default_instance_;
+}
+
+CodeGeneratorResponse_File* CodeGeneratorResponse_File::default_instance_ = NULL;
+
+CodeGeneratorResponse_File* CodeGeneratorResponse_File::New(::google::protobuf::Arena* arena) const {
+ CodeGeneratorResponse_File* n = new CodeGeneratorResponse_File;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void CodeGeneratorResponse_File::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ if (_has_bits_[0 / 32] & 7u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_insertion_point()) {
+ insertion_point_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_content()) {
+ content_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool CodeGeneratorResponse_File::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_insertion_point;
+ break;
+ }
+
+ // optional string insertion_point = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_insertion_point:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_insertion_point()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->insertion_point().data(), this->insertion_point().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(122)) goto parse_content;
+ break;
+ }
+
+ // optional string content = 15;
+ case 15: {
+ if (tag == 122) {
+ parse_content:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_content()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->content().data(), this->content().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.content");
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.compiler.CodeGeneratorResponse.File)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.compiler.CodeGeneratorResponse.File)
+ return false;
+#undef DO_
+}
+
+void CodeGeneratorResponse_File::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional string insertion_point = 2;
+ if (has_insertion_point()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->insertion_point().data(), this->insertion_point().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->insertion_point(), output);
+ }
+
+ // optional string content = 15;
+ if (has_content()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->content().data(), this->content().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.content");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 15, this->content(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.compiler.CodeGeneratorResponse.File)
+}
+
+::google::protobuf::uint8* CodeGeneratorResponse_File::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional string insertion_point = 2;
+ if (has_insertion_point()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->insertion_point().data(), this->insertion_point().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->insertion_point(), target);
+ }
+
+ // optional string content = 15;
+ if (has_content()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->content().data(), this->content().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.File.content");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 15, this->content(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.compiler.CodeGeneratorResponse.File)
+ return target;
+}
+
+int CodeGeneratorResponse_File::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 7u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional string insertion_point = 2;
+ if (has_insertion_point()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->insertion_point());
+ }
+
+ // optional string content = 15;
+ if (has_content()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->content());
+ }
+
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void CodeGeneratorResponse_File::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const CodeGeneratorResponse_File* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const CodeGeneratorResponse_File>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.compiler.CodeGeneratorResponse.File)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.compiler.CodeGeneratorResponse.File)
+ MergeFrom(*source);
+ }
+}
+
+void CodeGeneratorResponse_File::MergeFrom(const CodeGeneratorResponse_File& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_insertion_point()) {
+ set_has_insertion_point();
+ insertion_point_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.insertion_point_);
+ }
+ if (from.has_content()) {
+ set_has_content();
+ content_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.content_);
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void CodeGeneratorResponse_File::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void CodeGeneratorResponse_File::CopyFrom(const CodeGeneratorResponse_File& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.compiler.CodeGeneratorResponse.File)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool CodeGeneratorResponse_File::IsInitialized() const {
+
+ return true;
+}
+
+void CodeGeneratorResponse_File::Swap(CodeGeneratorResponse_File* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void CodeGeneratorResponse_File::InternalSwap(CodeGeneratorResponse_File* other) {
+ name_.Swap(&other->name_);
+ insertion_point_.Swap(&other->insertion_point_);
+ content_.Swap(&other->content_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata CodeGeneratorResponse_File::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = CodeGeneratorResponse_File_descriptor_;
+ metadata.reflection = CodeGeneratorResponse_File_reflection_;
+ return metadata;
+}
+
+
+// -------------------------------------------------------------------
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int CodeGeneratorResponse::kErrorFieldNumber;
+const int CodeGeneratorResponse::kFileFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+CodeGeneratorResponse::CodeGeneratorResponse()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.compiler.CodeGeneratorResponse)
+}
+
+void CodeGeneratorResponse::InitAsDefaultInstance() {
+}
+
+CodeGeneratorResponse::CodeGeneratorResponse(const CodeGeneratorResponse& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.compiler.CodeGeneratorResponse)
+}
+
+void CodeGeneratorResponse::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ error_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+CodeGeneratorResponse::~CodeGeneratorResponse() {
+ // @@protoc_insertion_point(destructor:google.protobuf.compiler.CodeGeneratorResponse)
+ SharedDtor();
+}
+
+void CodeGeneratorResponse::SharedDtor() {
+ error_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void CodeGeneratorResponse::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* CodeGeneratorResponse::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return CodeGeneratorResponse_descriptor_;
+}
+
+const CodeGeneratorResponse& CodeGeneratorResponse::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ return *default_instance_;
+}
+
+CodeGeneratorResponse* CodeGeneratorResponse::default_instance_ = NULL;
+
+CodeGeneratorResponse* CodeGeneratorResponse::New(::google::protobuf::Arena* arena) const {
+ CodeGeneratorResponse* n = new CodeGeneratorResponse;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void CodeGeneratorResponse::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.compiler.CodeGeneratorResponse)
+ if (has_error()) {
+ error_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ file_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool CodeGeneratorResponse::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.compiler.CodeGeneratorResponse)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string error = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_error()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->error().data(), this->error().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.compiler.CodeGeneratorResponse.error");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(122)) goto parse_file;
+ break;
+ }
+
+ // repeated .google.protobuf.compiler.CodeGeneratorResponse.File file = 15;
+ case 15: {
+ if (tag == 122) {
+ parse_file:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_file:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_file()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(122)) goto parse_loop_file;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.compiler.CodeGeneratorResponse)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.compiler.CodeGeneratorResponse)
+ return false;
+#undef DO_
+}
+
+void CodeGeneratorResponse::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.compiler.CodeGeneratorResponse)
+ // optional string error = 1;
+ if (has_error()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->error().data(), this->error().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.error");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->error(), output);
+ }
+
+ // repeated .google.protobuf.compiler.CodeGeneratorResponse.File file = 15;
+ for (unsigned int i = 0, n = this->file_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 15, this->file(i), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.compiler.CodeGeneratorResponse)
+}
+
+::google::protobuf::uint8* CodeGeneratorResponse::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.compiler.CodeGeneratorResponse)
+ // optional string error = 1;
+ if (has_error()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->error().data(), this->error().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.compiler.CodeGeneratorResponse.error");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->error(), target);
+ }
+
+ // repeated .google.protobuf.compiler.CodeGeneratorResponse.File file = 15;
+ for (unsigned int i = 0, n = this->file_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 15, this->file(i), false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.compiler.CodeGeneratorResponse)
+ return target;
+}
+
+int CodeGeneratorResponse::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.compiler.CodeGeneratorResponse)
+ int total_size = 0;
+
+ // optional string error = 1;
+ if (has_error()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->error());
+ }
+
+ // repeated .google.protobuf.compiler.CodeGeneratorResponse.File file = 15;
+ total_size += 1 * this->file_size();
+ for (int i = 0; i < this->file_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->file(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void CodeGeneratorResponse::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.compiler.CodeGeneratorResponse)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const CodeGeneratorResponse* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const CodeGeneratorResponse>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.compiler.CodeGeneratorResponse)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.compiler.CodeGeneratorResponse)
+ MergeFrom(*source);
+ }
+}
+
+void CodeGeneratorResponse::MergeFrom(const CodeGeneratorResponse& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.compiler.CodeGeneratorResponse)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ file_.MergeFrom(from.file_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_error()) {
+ set_has_error();
+ error_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.error_);
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void CodeGeneratorResponse::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.compiler.CodeGeneratorResponse)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void CodeGeneratorResponse::CopyFrom(const CodeGeneratorResponse& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.compiler.CodeGeneratorResponse)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool CodeGeneratorResponse::IsInitialized() const {
+
+ return true;
+}
+
+void CodeGeneratorResponse::Swap(CodeGeneratorResponse* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void CodeGeneratorResponse::InternalSwap(CodeGeneratorResponse* other) {
+ error_.Swap(&other->error_);
+ file_.UnsafeArenaSwap(&other->file_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata CodeGeneratorResponse::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = CodeGeneratorResponse_descriptor_;
+ metadata.reflection = CodeGeneratorResponse_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// CodeGeneratorResponse_File
+
+// optional string name = 1;
+bool CodeGeneratorResponse_File::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void CodeGeneratorResponse_File::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void CodeGeneratorResponse_File::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void CodeGeneratorResponse_File::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& CodeGeneratorResponse_File::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse_File::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+ void CodeGeneratorResponse_File::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+ void CodeGeneratorResponse_File::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+ ::std::string* CodeGeneratorResponse_File::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* CodeGeneratorResponse_File::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse_File::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+
+// optional string insertion_point = 2;
+bool CodeGeneratorResponse_File::has_insertion_point() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void CodeGeneratorResponse_File::set_has_insertion_point() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void CodeGeneratorResponse_File::clear_has_insertion_point() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void CodeGeneratorResponse_File::clear_insertion_point() {
+ insertion_point_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_insertion_point();
+}
+ const ::std::string& CodeGeneratorResponse_File::insertion_point() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+ return insertion_point_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse_File::set_insertion_point(const ::std::string& value) {
+ set_has_insertion_point();
+ insertion_point_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+ void CodeGeneratorResponse_File::set_insertion_point(const char* value) {
+ set_has_insertion_point();
+ insertion_point_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+ void CodeGeneratorResponse_File::set_insertion_point(const char* value, size_t size) {
+ set_has_insertion_point();
+ insertion_point_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+ ::std::string* CodeGeneratorResponse_File::mutable_insertion_point() {
+ set_has_insertion_point();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+ return insertion_point_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* CodeGeneratorResponse_File::release_insertion_point() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+ clear_has_insertion_point();
+ return insertion_point_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse_File::set_allocated_insertion_point(::std::string* insertion_point) {
+ if (insertion_point != NULL) {
+ set_has_insertion_point();
+ } else {
+ clear_has_insertion_point();
+ }
+ insertion_point_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), insertion_point);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+
+// optional string content = 15;
+bool CodeGeneratorResponse_File::has_content() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void CodeGeneratorResponse_File::set_has_content() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void CodeGeneratorResponse_File::clear_has_content() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void CodeGeneratorResponse_File::clear_content() {
+ content_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_content();
+}
+ const ::std::string& CodeGeneratorResponse_File::content() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+ return content_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse_File::set_content(const ::std::string& value) {
+ set_has_content();
+ content_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+ void CodeGeneratorResponse_File::set_content(const char* value) {
+ set_has_content();
+ content_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+ void CodeGeneratorResponse_File::set_content(const char* value, size_t size) {
+ set_has_content();
+ content_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+ ::std::string* CodeGeneratorResponse_File::mutable_content() {
+ set_has_content();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+ return content_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* CodeGeneratorResponse_File::release_content() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+ clear_has_content();
+ return content_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse_File::set_allocated_content(::std::string* content) {
+ if (content != NULL) {
+ set_has_content();
+ } else {
+ clear_has_content();
+ }
+ content_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), content);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+
+// -------------------------------------------------------------------
+
+// CodeGeneratorResponse
+
+// optional string error = 1;
+bool CodeGeneratorResponse::has_error() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void CodeGeneratorResponse::set_has_error() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void CodeGeneratorResponse::clear_has_error() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void CodeGeneratorResponse::clear_error() {
+ error_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_error();
+}
+ const ::std::string& CodeGeneratorResponse::error() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.error)
+ return error_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse::set_error(const ::std::string& value) {
+ set_has_error();
+ error_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+ void CodeGeneratorResponse::set_error(const char* value) {
+ set_has_error();
+ error_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+ void CodeGeneratorResponse::set_error(const char* value, size_t size) {
+ set_has_error();
+ error_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+ ::std::string* CodeGeneratorResponse::mutable_error() {
+ set_has_error();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.error)
+ return error_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* CodeGeneratorResponse::release_error() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.error)
+ clear_has_error();
+ return error_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void CodeGeneratorResponse::set_allocated_error(::std::string* error) {
+ if (error != NULL) {
+ set_has_error();
+ } else {
+ clear_has_error();
+ }
+ error_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), error);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+
+// repeated .google.protobuf.compiler.CodeGeneratorResponse.File file = 15;
+int CodeGeneratorResponse::file_size() const {
+ return file_.size();
+}
+void CodeGeneratorResponse::clear_file() {
+ file_.Clear();
+}
+const ::google::protobuf::compiler::CodeGeneratorResponse_File& CodeGeneratorResponse::file(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_.Get(index);
+}
+::google::protobuf::compiler::CodeGeneratorResponse_File* CodeGeneratorResponse::mutable_file(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_.Mutable(index);
+}
+::google::protobuf::compiler::CodeGeneratorResponse_File* CodeGeneratorResponse::add_file() {
+ // @@protoc_insertion_point(field_add:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::compiler::CodeGeneratorResponse_File >*
+CodeGeneratorResponse::mutable_file() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return &file_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::compiler::CodeGeneratorResponse_File >&
+CodeGeneratorResponse::file() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.h
new file mode 100644
index 0000000000..13eeb69f62
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.pb.h
@@ -0,0 +1,830 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/compiler/plugin.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fcompiler_2fplugin_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fcompiler_2fplugin_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/descriptor.pb.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOC_EXPORT protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+
+class CodeGeneratorRequest;
+class CodeGeneratorResponse;
+class CodeGeneratorResponse_File;
+
+// ===================================================================
+
+class LIBPROTOC_EXPORT CodeGeneratorRequest : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.compiler.CodeGeneratorRequest) */ {
+ public:
+ CodeGeneratorRequest();
+ virtual ~CodeGeneratorRequest();
+
+ CodeGeneratorRequest(const CodeGeneratorRequest& from);
+
+ inline CodeGeneratorRequest& operator=(const CodeGeneratorRequest& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const CodeGeneratorRequest& default_instance();
+
+ void Swap(CodeGeneratorRequest* other);
+
+ // implements Message ----------------------------------------------
+
+ inline CodeGeneratorRequest* New() const { return New(NULL); }
+
+ CodeGeneratorRequest* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const CodeGeneratorRequest& from);
+ void MergeFrom(const CodeGeneratorRequest& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(CodeGeneratorRequest* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // repeated string file_to_generate = 1;
+ int file_to_generate_size() const;
+ void clear_file_to_generate();
+ static const int kFileToGenerateFieldNumber = 1;
+ const ::std::string& file_to_generate(int index) const;
+ ::std::string* mutable_file_to_generate(int index);
+ void set_file_to_generate(int index, const ::std::string& value);
+ void set_file_to_generate(int index, const char* value);
+ void set_file_to_generate(int index, const char* value, size_t size);
+ ::std::string* add_file_to_generate();
+ void add_file_to_generate(const ::std::string& value);
+ void add_file_to_generate(const char* value);
+ void add_file_to_generate(const char* value, size_t size);
+ const ::google::protobuf::RepeatedPtrField< ::std::string>& file_to_generate() const;
+ ::google::protobuf::RepeatedPtrField< ::std::string>* mutable_file_to_generate();
+
+ // optional string parameter = 2;
+ bool has_parameter() const;
+ void clear_parameter();
+ static const int kParameterFieldNumber = 2;
+ const ::std::string& parameter() const;
+ void set_parameter(const ::std::string& value);
+ void set_parameter(const char* value);
+ void set_parameter(const char* value, size_t size);
+ ::std::string* mutable_parameter();
+ ::std::string* release_parameter();
+ void set_allocated_parameter(::std::string* parameter);
+
+ // repeated .google.protobuf.FileDescriptorProto proto_file = 15;
+ int proto_file_size() const;
+ void clear_proto_file();
+ static const int kProtoFileFieldNumber = 15;
+ const ::google::protobuf::FileDescriptorProto& proto_file(int index) const;
+ ::google::protobuf::FileDescriptorProto* mutable_proto_file(int index);
+ ::google::protobuf::FileDescriptorProto* add_proto_file();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >*
+ mutable_proto_file();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >&
+ proto_file() const;
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.compiler.CodeGeneratorRequest)
+ private:
+ inline void set_has_parameter();
+ inline void clear_has_parameter();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::std::string> file_to_generate_;
+ ::google::protobuf::internal::ArenaStringPtr parameter_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto > proto_file_;
+ friend void LIBPROTOC_EXPORT protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+
+ void InitAsDefaultInstance();
+ static CodeGeneratorRequest* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOC_EXPORT CodeGeneratorResponse_File : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.compiler.CodeGeneratorResponse.File) */ {
+ public:
+ CodeGeneratorResponse_File();
+ virtual ~CodeGeneratorResponse_File();
+
+ CodeGeneratorResponse_File(const CodeGeneratorResponse_File& from);
+
+ inline CodeGeneratorResponse_File& operator=(const CodeGeneratorResponse_File& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const CodeGeneratorResponse_File& default_instance();
+
+ void Swap(CodeGeneratorResponse_File* other);
+
+ // implements Message ----------------------------------------------
+
+ inline CodeGeneratorResponse_File* New() const { return New(NULL); }
+
+ CodeGeneratorResponse_File* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const CodeGeneratorResponse_File& from);
+ void MergeFrom(const CodeGeneratorResponse_File& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(CodeGeneratorResponse_File* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional string insertion_point = 2;
+ bool has_insertion_point() const;
+ void clear_insertion_point();
+ static const int kInsertionPointFieldNumber = 2;
+ const ::std::string& insertion_point() const;
+ void set_insertion_point(const ::std::string& value);
+ void set_insertion_point(const char* value);
+ void set_insertion_point(const char* value, size_t size);
+ ::std::string* mutable_insertion_point();
+ ::std::string* release_insertion_point();
+ void set_allocated_insertion_point(::std::string* insertion_point);
+
+ // optional string content = 15;
+ bool has_content() const;
+ void clear_content();
+ static const int kContentFieldNumber = 15;
+ const ::std::string& content() const;
+ void set_content(const ::std::string& value);
+ void set_content(const char* value);
+ void set_content(const char* value, size_t size);
+ ::std::string* mutable_content();
+ ::std::string* release_content();
+ void set_allocated_content(::std::string* content);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.compiler.CodeGeneratorResponse.File)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_insertion_point();
+ inline void clear_has_insertion_point();
+ inline void set_has_content();
+ inline void clear_has_content();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::internal::ArenaStringPtr insertion_point_;
+ ::google::protobuf::internal::ArenaStringPtr content_;
+ friend void LIBPROTOC_EXPORT protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+
+ void InitAsDefaultInstance();
+ static CodeGeneratorResponse_File* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOC_EXPORT CodeGeneratorResponse : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.compiler.CodeGeneratorResponse) */ {
+ public:
+ CodeGeneratorResponse();
+ virtual ~CodeGeneratorResponse();
+
+ CodeGeneratorResponse(const CodeGeneratorResponse& from);
+
+ inline CodeGeneratorResponse& operator=(const CodeGeneratorResponse& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const CodeGeneratorResponse& default_instance();
+
+ void Swap(CodeGeneratorResponse* other);
+
+ // implements Message ----------------------------------------------
+
+ inline CodeGeneratorResponse* New() const { return New(NULL); }
+
+ CodeGeneratorResponse* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const CodeGeneratorResponse& from);
+ void MergeFrom(const CodeGeneratorResponse& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(CodeGeneratorResponse* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef CodeGeneratorResponse_File File;
+
+ // accessors -------------------------------------------------------
+
+ // optional string error = 1;
+ bool has_error() const;
+ void clear_error();
+ static const int kErrorFieldNumber = 1;
+ const ::std::string& error() const;
+ void set_error(const ::std::string& value);
+ void set_error(const char* value);
+ void set_error(const char* value, size_t size);
+ ::std::string* mutable_error();
+ ::std::string* release_error();
+ void set_allocated_error(::std::string* error);
+
+ // repeated .google.protobuf.compiler.CodeGeneratorResponse.File file = 15;
+ int file_size() const;
+ void clear_file();
+ static const int kFileFieldNumber = 15;
+ const ::google::protobuf::compiler::CodeGeneratorResponse_File& file(int index) const;
+ ::google::protobuf::compiler::CodeGeneratorResponse_File* mutable_file(int index);
+ ::google::protobuf::compiler::CodeGeneratorResponse_File* add_file();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::compiler::CodeGeneratorResponse_File >*
+ mutable_file();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::compiler::CodeGeneratorResponse_File >&
+ file() const;
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.compiler.CodeGeneratorResponse)
+ private:
+ inline void set_has_error();
+ inline void clear_has_error();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr error_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::compiler::CodeGeneratorResponse_File > file_;
+ friend void LIBPROTOC_EXPORT protobuf_AddDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fcompiler_2fplugin_2eproto();
+
+ void InitAsDefaultInstance();
+ static CodeGeneratorResponse* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// CodeGeneratorRequest
+
+// repeated string file_to_generate = 1;
+inline int CodeGeneratorRequest::file_to_generate_size() const {
+ return file_to_generate_.size();
+}
+inline void CodeGeneratorRequest::clear_file_to_generate() {
+ file_to_generate_.Clear();
+}
+inline const ::std::string& CodeGeneratorRequest::file_to_generate(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_.Get(index);
+}
+inline ::std::string* CodeGeneratorRequest::mutable_file_to_generate(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_.Mutable(index);
+}
+inline void CodeGeneratorRequest::set_file_to_generate(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ file_to_generate_.Mutable(index)->assign(value);
+}
+inline void CodeGeneratorRequest::set_file_to_generate(int index, const char* value) {
+ file_to_generate_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+inline void CodeGeneratorRequest::set_file_to_generate(int index, const char* value, size_t size) {
+ file_to_generate_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+inline ::std::string* CodeGeneratorRequest::add_file_to_generate() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_.Add();
+}
+inline void CodeGeneratorRequest::add_file_to_generate(const ::std::string& value) {
+ file_to_generate_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+inline void CodeGeneratorRequest::add_file_to_generate(const char* value) {
+ file_to_generate_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+inline void CodeGeneratorRequest::add_file_to_generate(const char* value, size_t size) {
+ file_to_generate_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+}
+inline const ::google::protobuf::RepeatedPtrField< ::std::string>&
+CodeGeneratorRequest::file_to_generate() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return file_to_generate_;
+}
+inline ::google::protobuf::RepeatedPtrField< ::std::string>*
+CodeGeneratorRequest::mutable_file_to_generate() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.compiler.CodeGeneratorRequest.file_to_generate)
+ return &file_to_generate_;
+}
+
+// optional string parameter = 2;
+inline bool CodeGeneratorRequest::has_parameter() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void CodeGeneratorRequest::set_has_parameter() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void CodeGeneratorRequest::clear_has_parameter() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void CodeGeneratorRequest::clear_parameter() {
+ parameter_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_parameter();
+}
+inline const ::std::string& CodeGeneratorRequest::parameter() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+ return parameter_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorRequest::set_parameter(const ::std::string& value) {
+ set_has_parameter();
+ parameter_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+inline void CodeGeneratorRequest::set_parameter(const char* value) {
+ set_has_parameter();
+ parameter_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+inline void CodeGeneratorRequest::set_parameter(const char* value, size_t size) {
+ set_has_parameter();
+ parameter_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+inline ::std::string* CodeGeneratorRequest::mutable_parameter() {
+ set_has_parameter();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+ return parameter_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* CodeGeneratorRequest::release_parameter() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+ clear_has_parameter();
+ return parameter_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorRequest::set_allocated_parameter(::std::string* parameter) {
+ if (parameter != NULL) {
+ set_has_parameter();
+ } else {
+ clear_has_parameter();
+ }
+ parameter_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), parameter);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorRequest.parameter)
+}
+
+// repeated .google.protobuf.FileDescriptorProto proto_file = 15;
+inline int CodeGeneratorRequest::proto_file_size() const {
+ return proto_file_.size();
+}
+inline void CodeGeneratorRequest::clear_proto_file() {
+ proto_file_.Clear();
+}
+inline const ::google::protobuf::FileDescriptorProto& CodeGeneratorRequest::proto_file(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_.Get(index);
+}
+inline ::google::protobuf::FileDescriptorProto* CodeGeneratorRequest::mutable_proto_file(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_.Mutable(index);
+}
+inline ::google::protobuf::FileDescriptorProto* CodeGeneratorRequest::add_proto_file() {
+ // @@protoc_insertion_point(field_add:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >*
+CodeGeneratorRequest::mutable_proto_file() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return &proto_file_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >&
+CodeGeneratorRequest::proto_file() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.compiler.CodeGeneratorRequest.proto_file)
+ return proto_file_;
+}
+
+// -------------------------------------------------------------------
+
+// CodeGeneratorResponse_File
+
+// optional string name = 1;
+inline bool CodeGeneratorResponse_File::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void CodeGeneratorResponse_File::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void CodeGeneratorResponse_File::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void CodeGeneratorResponse_File::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& CodeGeneratorResponse_File::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse_File::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+inline void CodeGeneratorResponse_File::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+inline void CodeGeneratorResponse_File::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+inline ::std::string* CodeGeneratorResponse_File::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* CodeGeneratorResponse_File::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse_File::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.File.name)
+}
+
+// optional string insertion_point = 2;
+inline bool CodeGeneratorResponse_File::has_insertion_point() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void CodeGeneratorResponse_File::set_has_insertion_point() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void CodeGeneratorResponse_File::clear_has_insertion_point() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void CodeGeneratorResponse_File::clear_insertion_point() {
+ insertion_point_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_insertion_point();
+}
+inline const ::std::string& CodeGeneratorResponse_File::insertion_point() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+ return insertion_point_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse_File::set_insertion_point(const ::std::string& value) {
+ set_has_insertion_point();
+ insertion_point_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+inline void CodeGeneratorResponse_File::set_insertion_point(const char* value) {
+ set_has_insertion_point();
+ insertion_point_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+inline void CodeGeneratorResponse_File::set_insertion_point(const char* value, size_t size) {
+ set_has_insertion_point();
+ insertion_point_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+inline ::std::string* CodeGeneratorResponse_File::mutable_insertion_point() {
+ set_has_insertion_point();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+ return insertion_point_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* CodeGeneratorResponse_File::release_insertion_point() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+ clear_has_insertion_point();
+ return insertion_point_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse_File::set_allocated_insertion_point(::std::string* insertion_point) {
+ if (insertion_point != NULL) {
+ set_has_insertion_point();
+ } else {
+ clear_has_insertion_point();
+ }
+ insertion_point_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), insertion_point);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.File.insertion_point)
+}
+
+// optional string content = 15;
+inline bool CodeGeneratorResponse_File::has_content() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void CodeGeneratorResponse_File::set_has_content() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void CodeGeneratorResponse_File::clear_has_content() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void CodeGeneratorResponse_File::clear_content() {
+ content_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_content();
+}
+inline const ::std::string& CodeGeneratorResponse_File::content() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+ return content_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse_File::set_content(const ::std::string& value) {
+ set_has_content();
+ content_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+inline void CodeGeneratorResponse_File::set_content(const char* value) {
+ set_has_content();
+ content_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+inline void CodeGeneratorResponse_File::set_content(const char* value, size_t size) {
+ set_has_content();
+ content_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+inline ::std::string* CodeGeneratorResponse_File::mutable_content() {
+ set_has_content();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+ return content_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* CodeGeneratorResponse_File::release_content() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+ clear_has_content();
+ return content_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse_File::set_allocated_content(::std::string* content) {
+ if (content != NULL) {
+ set_has_content();
+ } else {
+ clear_has_content();
+ }
+ content_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), content);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.File.content)
+}
+
+// -------------------------------------------------------------------
+
+// CodeGeneratorResponse
+
+// optional string error = 1;
+inline bool CodeGeneratorResponse::has_error() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void CodeGeneratorResponse::set_has_error() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void CodeGeneratorResponse::clear_has_error() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void CodeGeneratorResponse::clear_error() {
+ error_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_error();
+}
+inline const ::std::string& CodeGeneratorResponse::error() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.error)
+ return error_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse::set_error(const ::std::string& value) {
+ set_has_error();
+ error_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+inline void CodeGeneratorResponse::set_error(const char* value) {
+ set_has_error();
+ error_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+inline void CodeGeneratorResponse::set_error(const char* value, size_t size) {
+ set_has_error();
+ error_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+inline ::std::string* CodeGeneratorResponse::mutable_error() {
+ set_has_error();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.error)
+ return error_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* CodeGeneratorResponse::release_error() {
+ // @@protoc_insertion_point(field_release:google.protobuf.compiler.CodeGeneratorResponse.error)
+ clear_has_error();
+ return error_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void CodeGeneratorResponse::set_allocated_error(::std::string* error) {
+ if (error != NULL) {
+ set_has_error();
+ } else {
+ clear_has_error();
+ }
+ error_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), error);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.compiler.CodeGeneratorResponse.error)
+}
+
+// repeated .google.protobuf.compiler.CodeGeneratorResponse.File file = 15;
+inline int CodeGeneratorResponse::file_size() const {
+ return file_.size();
+}
+inline void CodeGeneratorResponse::clear_file() {
+ file_.Clear();
+}
+inline const ::google::protobuf::compiler::CodeGeneratorResponse_File& CodeGeneratorResponse::file(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_.Get(index);
+}
+inline ::google::protobuf::compiler::CodeGeneratorResponse_File* CodeGeneratorResponse::mutable_file(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_.Mutable(index);
+}
+inline ::google::protobuf::compiler::CodeGeneratorResponse_File* CodeGeneratorResponse::add_file() {
+ // @@protoc_insertion_point(field_add:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::compiler::CodeGeneratorResponse_File >*
+CodeGeneratorResponse::mutable_file() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return &file_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::compiler::CodeGeneratorResponse_File >&
+CodeGeneratorResponse::file() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.compiler.CodeGeneratorResponse.file)
+ return file_;
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fcompiler_2fplugin_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.proto b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.proto
new file mode 100644
index 0000000000..acaee1f494
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/plugin.proto
@@ -0,0 +1,150 @@
+// 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)
+//
+// WARNING: The plugin interface is currently EXPERIMENTAL and is subject to
+// change.
+//
+// protoc (aka the Protocol Compiler) can be extended via plugins. A plugin is
+// just a program that reads a CodeGeneratorRequest from stdin and writes a
+// CodeGeneratorResponse to stdout.
+//
+// Plugins written using C++ can use google/protobuf/compiler/plugin.h instead
+// of dealing with the raw protocol defined here.
+//
+// A plugin executable needs only to be placed somewhere in the path. The
+// plugin should be named "protoc-gen-$NAME", and will then be used when the
+// flag "--${NAME}_out" is passed to protoc.
+
+syntax = "proto2";
+package google.protobuf.compiler;
+option java_package = "com.google.protobuf.compiler";
+option java_outer_classname = "PluginProtos";
+
+option go_package = "plugin_go";
+
+import "google/protobuf/descriptor.proto";
+
+// An encoded CodeGeneratorRequest is written to the plugin's stdin.
+message CodeGeneratorRequest {
+ // The .proto files that were explicitly listed on the command-line. The
+ // code generator should generate code only for these files. Each file's
+ // descriptor will be included in proto_file, below.
+ repeated string file_to_generate = 1;
+
+ // The generator parameter passed on the command-line.
+ optional string parameter = 2;
+
+ // FileDescriptorProtos for all files in files_to_generate and everything
+ // they import. The files will appear in topological order, so each file
+ // appears before any file that imports it.
+ //
+ // protoc guarantees that all proto_files will be written after
+ // the fields above, even though this is not technically guaranteed by the
+ // protobuf wire format. This theoretically could allow a plugin to stream
+ // in the FileDescriptorProtos and handle them one by one rather than read
+ // the entire set into memory at once. However, as of this writing, this
+ // is not similarly optimized on protoc's end -- it will store all fields in
+ // memory at once before sending them to the plugin.
+ repeated FileDescriptorProto proto_file = 15;
+}
+
+// The plugin writes an encoded CodeGeneratorResponse to stdout.
+message CodeGeneratorResponse {
+ // Error message. If non-empty, code generation failed. The plugin process
+ // should exit with status code zero even if it reports an error in this way.
+ //
+ // This should be used to indicate errors in .proto files which prevent the
+ // code generator from generating correct code. Errors which indicate a
+ // problem in protoc itself -- such as the input CodeGeneratorRequest being
+ // unparseable -- should be reported by writing a message to stderr and
+ // exiting with a non-zero status code.
+ optional string error = 1;
+
+ // Represents a single generated file.
+ message File {
+ // The file name, relative to the output directory. The name must not
+ // contain "." or ".." components and must be relative, not be absolute (so,
+ // the file cannot lie outside the output directory). "/" must be used as
+ // the path separator, not "\".
+ //
+ // If the name is omitted, the content will be appended to the previous
+ // file. This allows the generator to break large files into small chunks,
+ // and allows the generated text to be streamed back to protoc so that large
+ // files need not reside completely in memory at one time. Note that as of
+ // this writing protoc does not optimize for this -- it will read the entire
+ // CodeGeneratorResponse before writing files to disk.
+ optional string name = 1;
+
+ // If non-empty, indicates that the named file should already exist, and the
+ // content here is to be inserted into that file at a defined insertion
+ // point. This feature allows a code generator to extend the output
+ // produced by another code generator. The original generator may provide
+ // insertion points by placing special annotations in the file that look
+ // like:
+ // @@protoc_insertion_point(NAME)
+ // The annotation can have arbitrary text before and after it on the line,
+ // which allows it to be placed in a comment. NAME should be replaced with
+ // an identifier naming the point -- this is what other generators will use
+ // as the insertion_point. Code inserted at this point will be placed
+ // immediately above the line containing the insertion point (thus multiple
+ // insertions to the same point will come out in the order they were added).
+ // The double-@ is intended to make it unlikely that the generated code
+ // could contain things that look like insertion points by accident.
+ //
+ // For example, the C++ code generator places the following line in the
+ // .pb.h files that it generates:
+ // // @@protoc_insertion_point(namespace_scope)
+ // This line appears within the scope of the file's package namespace, but
+ // outside of any particular class. Another plugin can then specify the
+ // insertion_point "namespace_scope" to generate additional classes or
+ // other declarations that should be placed in this scope.
+ //
+ // Note that if the line containing the insertion point begins with
+ // whitespace, the same whitespace will be added to every line of the
+ // inserted text. This is useful for languages like Python, where
+ // indentation matters. In these languages, the insertion point comment
+ // should be indented the same amount as any inserted code will need to be
+ // in order to work correctly in that context.
+ //
+ // The code generator that generates the initial file and the one which
+ // inserts into it must both run as part of a single invocation of protoc.
+ // Code generators are executed in the order in which they appear on the
+ // command line.
+ //
+ // If |insertion_point| is present, |name| must also be present.
+ optional string insertion_point = 2;
+
+ // The file contents.
+ optional string content = 15;
+ }
+ repeated File file = 15;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.cc
new file mode 100644
index 0000000000..d5468a0cb0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.cc
@@ -0,0 +1,1382 @@
+// 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.
+
+//#PY25 compatible generated code for GAE.
+// Copyright 2007 Google Inc. All Rights Reserved.
+// Author: robinson@google.com (Will Robinson)
+//
+// This module outputs pure-Python protocol message classes that will
+// largely be constructed at runtime via the metaclass in reflection.py.
+// In other words, our job is basically to output a Python equivalent
+// of the C++ *Descriptor objects, and fix up all circular references
+// within these objects.
+//
+// Note that the runtime performance of protocol message classes created in
+// this way is expected to be lousy. The plan is to create an alternate
+// generator that outputs a Python/C extension module that lets
+// performance-minded Python code leverage the fast C++ implementation
+// directly.
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <limits>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <google/protobuf/compiler/python/python_generator.h>
+#include <google/protobuf/descriptor.pb.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace python {
+
+namespace {
+
+// Returns a copy of |filename| with any trailing ".protodevel" or ".proto
+// suffix stripped.
+// TODO(robinson): Unify with copy in compiler/cpp/internal/helpers.cc.
+string StripProto(const string& filename) {
+ const char* suffix = HasSuffixString(filename, ".protodevel")
+ ? ".protodevel" : ".proto";
+ return StripSuffixString(filename, suffix);
+}
+
+
+// Returns the Python module name expected for a given .proto filename.
+string ModuleName(const string& filename) {
+ string basename = StripProto(filename);
+ StripString(&basename, "-", '_');
+ StripString(&basename, "/", '.');
+ return basename + "_pb2";
+}
+
+
+// Returns the alias we assign to the module of the given .proto filename
+// when importing. See testPackageInitializationImport in
+// google/protobuf/python/reflection_test.py
+// to see why we need the alias.
+string ModuleAlias(const string& filename) {
+ string module_name = ModuleName(filename);
+ // We can't have dots in the module name, so we replace each with _dot_.
+ // But that could lead to a collision between a.b and a_dot_b, so we also
+ // duplicate each underscore.
+ GlobalReplaceSubstring("_", "__", &module_name);
+ GlobalReplaceSubstring(".", "_dot_", &module_name);
+ return module_name;
+}
+
+// Keywords reserved by the Python language.
+const char* const kKeywords[] = {
+ "False", "None", "True", "and", "as", "assert", "break",
+ "class", "continue", "def", "del", "elif", "else", "except",
+ "finally", "for", "from", "global", "if", "import", "in",
+ "is", "lambda", "nonlocal", "not", "or", "pass", "raise",
+ "return", "try", "while", "with", "yield",
+};
+const char* const* kKeywordsEnd =
+ kKeywords + (sizeof(kKeywords) / sizeof(kKeywords[0]));
+
+bool ContainsPythonKeyword(const string& module_name) {
+ vector<string> tokens = Split(module_name, ".");
+ for (int i = 0; i < tokens.size(); ++i) {
+ if (std::find(kKeywords, kKeywordsEnd, tokens[i]) != kKeywordsEnd) {
+ return true;
+ }
+ }
+ return false;
+}
+
+
+// Returns the name of all containing types for descriptor,
+// in order from outermost to innermost, followed by descriptor's
+// own name. Each name is separated by |separator|.
+template <typename DescriptorT>
+string NamePrefixedWithNestedTypes(const DescriptorT& descriptor,
+ const string& separator) {
+ string name = descriptor.name();
+ for (const Descriptor* current = descriptor.containing_type();
+ current != NULL; current = current->containing_type()) {
+ name = current->name() + separator + name;
+ }
+ return name;
+}
+
+
+// Name of the class attribute where we store the Python
+// descriptor.Descriptor instance for the generated class.
+// Must stay consistent with the _DESCRIPTOR_KEY constant
+// in proto2/public/reflection.py.
+const char kDescriptorKey[] = "DESCRIPTOR";
+
+
+// Does the file have top-level enums?
+inline bool HasTopLevelEnums(const FileDescriptor *file) {
+ return file->enum_type_count() > 0;
+}
+
+
+// Should we generate generic services for this file?
+inline bool HasGenericServices(const FileDescriptor *file) {
+ return file->service_count() > 0 &&
+ file->options().py_generic_services();
+}
+
+
+// Prints the common boilerplate needed at the top of every .py
+// file output by this generator.
+void PrintTopBoilerplate(
+ io::Printer* printer, const FileDescriptor* file, bool descriptor_proto) {
+ // TODO(robinson): Allow parameterization of Python version?
+ printer->Print(
+ "# Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "# source: $filename$\n"
+ "\nimport sys\n_b=sys.version_info[0]<3 and (lambda x:x) or (lambda x:x.encode('latin1'))" //##PY25
+ "\n",
+ "filename", file->name());
+ if (HasTopLevelEnums(file)) {
+ printer->Print(
+ "from google.protobuf.internal import enum_type_wrapper\n");
+ }
+ printer->Print(
+ "from google.protobuf import descriptor as _descriptor\n"
+ "from google.protobuf import message as _message\n"
+ "from google.protobuf import reflection as _reflection\n"
+ "from google.protobuf import symbol_database as "
+ "_symbol_database\n");
+ if (HasGenericServices(file)) {
+ printer->Print(
+ "from google.protobuf import service as _service\n"
+ "from google.protobuf import service_reflection\n");
+ }
+
+ // Avoid circular imports if this module is descriptor_pb2.
+ if (!descriptor_proto) {
+ printer->Print(
+ "from google.protobuf import descriptor_pb2\n");
+ }
+ printer->Print(
+ "# @@protoc_insertion_point(imports)\n\n"
+ "_sym_db = _symbol_database.Default()\n");
+ printer->Print("\n\n");
+}
+
+
+// Returns a Python literal giving the default value for a field.
+// If the field specifies no explicit default value, we'll return
+// the default default value for the field type (zero for numbers,
+// empty string for strings, empty list for repeated fields, and
+// None for non-repeated, composite fields).
+//
+// TODO(robinson): Unify with code from
+// //compiler/cpp/internal/primitive_field.cc
+// //compiler/cpp/internal/enum_field.cc
+// //compiler/cpp/internal/string_field.cc
+string StringifyDefaultValue(const FieldDescriptor& field) {
+ if (field.is_repeated()) {
+ return "[]";
+ }
+
+ switch (field.cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return SimpleItoa(field.default_value_int32());
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return SimpleItoa(field.default_value_uint32());
+ case FieldDescriptor::CPPTYPE_INT64:
+ return SimpleItoa(field.default_value_int64());
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return SimpleItoa(field.default_value_uint64());
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value = field.default_value_double();
+ if (value == numeric_limits<double>::infinity()) {
+ // Python pre-2.6 on Windows does not parse "inf" correctly. However,
+ // a numeric literal that is too big for a double will become infinity.
+ return "1e10000";
+ } else if (value == -numeric_limits<double>::infinity()) {
+ // See above.
+ return "-1e10000";
+ } else if (value != value) {
+ // infinity * 0 = nan
+ return "(1e10000 * 0)";
+ } else {
+ return "float(" + SimpleDtoa(value) + ")";
+ }
+ }
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ float value = field.default_value_float();
+ if (value == numeric_limits<float>::infinity()) {
+ // Python pre-2.6 on Windows does not parse "inf" correctly. However,
+ // a numeric literal that is too big for a double will become infinity.
+ return "1e10000";
+ } else if (value == -numeric_limits<float>::infinity()) {
+ // See above.
+ return "-1e10000";
+ } else if (value != value) {
+ // infinity - infinity = nan
+ return "(1e10000 * 0)";
+ } else {
+ return "float(" + SimpleFtoa(value) + ")";
+ }
+ }
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return field.default_value_bool() ? "True" : "False";
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return SimpleItoa(field.default_value_enum()->number());
+ case FieldDescriptor::CPPTYPE_STRING:
+//##!PY25 return "b\"" + CEscape(field.default_value_string()) +
+//##!PY25 (field.type() != FieldDescriptor::TYPE_STRING ? "\"" :
+//##!PY25 "\".decode('utf-8')");
+ return "_b(\"" + CEscape(field.default_value_string()) + //##PY25
+ (field.type() != FieldDescriptor::TYPE_STRING ? "\")" : //##PY25
+ "\").decode('utf-8')"); //##PY25
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return "None";
+ }
+ // (We could add a default case above but then we wouldn't get the nice
+ // compiler warning when a new type is added.)
+ GOOGLE_LOG(FATAL) << "Not reached.";
+ return "";
+}
+
+string StringifySyntax(FileDescriptor::Syntax syntax) {
+ switch (syntax) {
+ case FileDescriptor::SYNTAX_PROTO2:
+ return "proto2";
+ case FileDescriptor::SYNTAX_PROTO3:
+ return "proto3";
+ case FileDescriptor::SYNTAX_UNKNOWN:
+ default:
+ GOOGLE_LOG(FATAL) << "Unsupported syntax; this generator only supports proto2 "
+ "and proto3 syntax.";
+ return "";
+ }
+}
+
+
+} // namespace
+
+
+Generator::Generator() : file_(NULL) {
+}
+
+Generator::~Generator() {
+}
+
+bool Generator::Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+
+ // Completely serialize all Generate() calls on this instance. The
+ // thread-safety constraints of the CodeGenerator interface aren't clear so
+ // just be as conservative as possible. It's easier to relax this later if
+ // we need to, but I doubt it will be an issue.
+ // TODO(kenton): The proper thing to do would be to allocate any state on
+ // the stack and use that, so that the Generator class itself does not need
+ // to have any mutable members. Then it is implicitly thread-safe.
+ MutexLock lock(&mutex_);
+ file_ = file;
+ string module_name = ModuleName(file->name());
+ string filename = module_name;
+ StripString(&filename, ".", '/');
+ filename += ".py";
+
+ FileDescriptorProto fdp;
+ file_->CopyTo(&fdp);
+ fdp.SerializeToString(&file_descriptor_serialized_);
+
+
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(filename));
+ GOOGLE_CHECK(output.get());
+ io::Printer printer(output.get(), '$');
+ printer_ = &printer;
+
+ PrintTopBoilerplate(printer_, file_, GeneratingDescriptorProto());
+ PrintImports();
+ PrintFileDescriptor();
+ PrintTopLevelEnums();
+ PrintTopLevelExtensions();
+ PrintAllNestedEnumsInFile();
+ PrintMessageDescriptors();
+ FixForeignFieldsInDescriptors();
+ PrintMessages();
+ // We have to fix up the extensions after the message classes themselves,
+ // since they need to call static RegisterExtension() methods on these
+ // classes.
+ FixForeignFieldsInExtensions();
+ // Descriptor options may have custom extensions. These custom options
+ // can only be successfully parsed after we register corresponding
+ // extensions. Therefore we parse all options again here to recognize
+ // custom options that may be unknown when we define the descriptors.
+ FixAllDescriptorOptions();
+ if (HasGenericServices(file)) {
+ PrintServices();
+ }
+
+ printer.Print(
+ "# @@protoc_insertion_point(module_scope)\n");
+
+ return !printer.failed();
+}
+
+// Prints Python imports for all modules imported by |file|.
+void Generator::PrintImports() const {
+ for (int i = 0; i < file_->dependency_count(); ++i) {
+ const string& filename = file_->dependency(i)->name();
+
+ string module_name = ModuleName(filename);
+ string module_alias = ModuleAlias(filename);
+ if (ContainsPythonKeyword(module_name)) {
+ // If the module path contains a Python keyword, we have to quote the
+ // module name and import it using importlib. Otherwise the usual kind of
+ // import statement would result in a syntax error from the presence of
+ // the keyword.
+ printer_->Print("import importlib\n");
+ printer_->Print("$alias$ = importlib.import_module('$name$')\n", "alias",
+ module_alias, "name", module_name);
+ } else {
+ int last_dot_pos = module_name.rfind('.');
+ string import_statement;
+ if (last_dot_pos == string::npos) {
+ // NOTE(petya): this is not tested as it would require a protocol buffer
+ // outside of any package, and I don't think that is easily achievable.
+ import_statement = "import " + module_name;
+ } else {
+ import_statement = "from " + module_name.substr(0, last_dot_pos) +
+ " import " + module_name.substr(last_dot_pos + 1);
+ }
+ printer_->Print("$statement$ as $alias$\n", "statement", import_statement,
+ "alias", module_alias);
+ }
+
+ CopyPublicDependenciesAliases(module_alias, file_->dependency(i));
+ }
+ printer_->Print("\n");
+
+ // Print public imports.
+ for (int i = 0; i < file_->public_dependency_count(); ++i) {
+ string module_name = ModuleName(file_->public_dependency(i)->name());
+ printer_->Print("from $module$ import *\n", "module", module_name);
+ }
+ printer_->Print("\n");
+}
+
+// Prints the single file descriptor for this file.
+void Generator::PrintFileDescriptor() const {
+ map<string, string> m;
+ m["descriptor_name"] = kDescriptorKey;
+ m["name"] = file_->name();
+ m["package"] = file_->package();
+ m["syntax"] = StringifySyntax(file_->syntax());
+ const char file_descriptor_template[] =
+ "$descriptor_name$ = _descriptor.FileDescriptor(\n"
+ " name='$name$',\n"
+ " package='$package$',\n"
+ " syntax='$syntax$',\n";
+ printer_->Print(m, file_descriptor_template);
+ printer_->Indent();
+ printer_->Print(
+//##!PY25 "serialized_pb=b'$value$'\n",
+ "serialized_pb=_b('$value$')\n", //##PY25
+ "value", strings::CHexEscape(file_descriptor_serialized_));
+ if (file_->dependency_count() != 0) {
+ printer_->Print(",\ndependencies=[");
+ for (int i = 0; i < file_->dependency_count(); ++i) {
+ string module_alias = ModuleAlias(file_->dependency(i)->name());
+ printer_->Print("$module_alias$.DESCRIPTOR,", "module_alias",
+ module_alias);
+ }
+ printer_->Print("]");
+ }
+
+ // TODO(falk): Also print options and fix the message_type, enum_type,
+ // service and extension later in the generation.
+
+ printer_->Outdent();
+ printer_->Print(")\n");
+ printer_->Print("_sym_db.RegisterFileDescriptor($name$)\n", "name",
+ kDescriptorKey);
+ printer_->Print("\n");
+}
+
+// Prints descriptors and module-level constants for all top-level
+// enums defined in |file|.
+void Generator::PrintTopLevelEnums() const {
+ vector<pair<string, int> > top_level_enum_values;
+ for (int i = 0; i < file_->enum_type_count(); ++i) {
+ const EnumDescriptor& enum_descriptor = *file_->enum_type(i);
+ PrintEnum(enum_descriptor);
+ printer_->Print("$name$ = "
+ "enum_type_wrapper.EnumTypeWrapper($descriptor_name$)",
+ "name", enum_descriptor.name(),
+ "descriptor_name",
+ ModuleLevelDescriptorName(enum_descriptor));
+ printer_->Print("\n");
+
+ for (int j = 0; j < enum_descriptor.value_count(); ++j) {
+ const EnumValueDescriptor& value_descriptor = *enum_descriptor.value(j);
+ top_level_enum_values.push_back(
+ std::make_pair(value_descriptor.name(), value_descriptor.number()));
+ }
+ }
+
+ for (int i = 0; i < top_level_enum_values.size(); ++i) {
+ printer_->Print("$name$ = $value$\n",
+ "name", top_level_enum_values[i].first,
+ "value", SimpleItoa(top_level_enum_values[i].second));
+ }
+ printer_->Print("\n");
+}
+
+// Prints all enums contained in all message types in |file|.
+void Generator::PrintAllNestedEnumsInFile() const {
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ PrintNestedEnums(*file_->message_type(i));
+ }
+}
+
+// Prints a Python statement assigning the appropriate module-level
+// enum name to a Python EnumDescriptor object equivalent to
+// enum_descriptor.
+void Generator::PrintEnum(const EnumDescriptor& enum_descriptor) const {
+ map<string, string> m;
+ string module_level_descriptor_name =
+ ModuleLevelDescriptorName(enum_descriptor);
+ m["descriptor_name"] = module_level_descriptor_name;
+ m["name"] = enum_descriptor.name();
+ m["full_name"] = enum_descriptor.full_name();
+ m["file"] = kDescriptorKey;
+ const char enum_descriptor_template[] =
+ "$descriptor_name$ = _descriptor.EnumDescriptor(\n"
+ " name='$name$',\n"
+ " full_name='$full_name$',\n"
+ " filename=None,\n"
+ " file=$file$,\n"
+ " values=[\n";
+ string options_string;
+ enum_descriptor.options().SerializeToString(&options_string);
+ printer_->Print(m, enum_descriptor_template);
+ printer_->Indent();
+ printer_->Indent();
+ for (int i = 0; i < enum_descriptor.value_count(); ++i) {
+ PrintEnumValueDescriptor(*enum_descriptor.value(i));
+ printer_->Print(",\n");
+ }
+ printer_->Outdent();
+ printer_->Print("],\n");
+ printer_->Print("containing_type=None,\n");
+ printer_->Print("options=$options_value$,\n",
+ "options_value",
+ OptionsValue("EnumOptions", options_string));
+ EnumDescriptorProto edp;
+ PrintSerializedPbInterval(enum_descriptor, edp);
+ printer_->Outdent();
+ printer_->Print(")\n");
+ printer_->Print("_sym_db.RegisterEnumDescriptor($name$)\n", "name",
+ module_level_descriptor_name);
+ printer_->Print("\n");
+}
+
+// Recursively prints enums in nested types within descriptor, then
+// prints enums contained at the top level in descriptor.
+void Generator::PrintNestedEnums(const Descriptor& descriptor) const {
+ for (int i = 0; i < descriptor.nested_type_count(); ++i) {
+ PrintNestedEnums(*descriptor.nested_type(i));
+ }
+
+ for (int i = 0; i < descriptor.enum_type_count(); ++i) {
+ PrintEnum(*descriptor.enum_type(i));
+ }
+}
+
+void Generator::PrintTopLevelExtensions() const {
+ const bool is_extension = true;
+ for (int i = 0; i < file_->extension_count(); ++i) {
+ const FieldDescriptor& extension_field = *file_->extension(i);
+ string constant_name = extension_field.name() + "_FIELD_NUMBER";
+ UpperString(&constant_name);
+ printer_->Print("$constant_name$ = $number$\n",
+ "constant_name", constant_name,
+ "number", SimpleItoa(extension_field.number()));
+ printer_->Print("$name$ = ", "name", extension_field.name());
+ PrintFieldDescriptor(extension_field, is_extension);
+ printer_->Print("\n");
+ }
+ printer_->Print("\n");
+}
+
+// Prints Python equivalents of all Descriptors in |file|.
+void Generator::PrintMessageDescriptors() const {
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ PrintDescriptor(*file_->message_type(i));
+ printer_->Print("\n");
+ }
+}
+
+void Generator::PrintServices() const {
+ for (int i = 0; i < file_->service_count(); ++i) {
+ PrintServiceDescriptor(*file_->service(i));
+ PrintServiceClass(*file_->service(i));
+ PrintServiceStub(*file_->service(i));
+ printer_->Print("\n");
+ }
+}
+
+void Generator::PrintServiceDescriptor(
+ const ServiceDescriptor& descriptor) const {
+ printer_->Print("\n");
+ string service_name = ModuleLevelServiceDescriptorName(descriptor);
+ string options_string;
+ descriptor.options().SerializeToString(&options_string);
+
+ printer_->Print(
+ "$service_name$ = _descriptor.ServiceDescriptor(\n",
+ "service_name", service_name);
+ printer_->Indent();
+ map<string, string> m;
+ m["name"] = descriptor.name();
+ m["full_name"] = descriptor.full_name();
+ m["file"] = kDescriptorKey;
+ m["index"] = SimpleItoa(descriptor.index());
+ m["options_value"] = OptionsValue("ServiceOptions", options_string);
+ const char required_function_arguments[] =
+ "name='$name$',\n"
+ "full_name='$full_name$',\n"
+ "file=$file$,\n"
+ "index=$index$,\n"
+ "options=$options_value$,\n";
+ printer_->Print(m, required_function_arguments);
+
+ ServiceDescriptorProto sdp;
+ PrintSerializedPbInterval(descriptor, sdp);
+
+ printer_->Print("methods=[\n");
+ for (int i = 0; i < descriptor.method_count(); ++i) {
+ const MethodDescriptor* method = descriptor.method(i);
+ method->options().SerializeToString(&options_string);
+
+ m.clear();
+ m["name"] = method->name();
+ m["full_name"] = method->full_name();
+ m["index"] = SimpleItoa(method->index());
+ m["serialized_options"] = CEscape(options_string);
+ m["input_type"] = ModuleLevelDescriptorName(*(method->input_type()));
+ m["output_type"] = ModuleLevelDescriptorName(*(method->output_type()));
+ m["options_value"] = OptionsValue("MethodOptions", options_string);
+ printer_->Print("_descriptor.MethodDescriptor(\n");
+ printer_->Indent();
+ printer_->Print(
+ m,
+ "name='$name$',\n"
+ "full_name='$full_name$',\n"
+ "index=$index$,\n"
+ "containing_service=None,\n"
+ "input_type=$input_type$,\n"
+ "output_type=$output_type$,\n"
+ "options=$options_value$,\n");
+ printer_->Outdent();
+ printer_->Print("),\n");
+ }
+
+ printer_->Outdent();
+ printer_->Print("])\n\n");
+}
+
+
+void Generator::PrintDescriptorKeyAndModuleName(
+ const ServiceDescriptor& descriptor) const {
+ printer_->Print(
+ "$descriptor_key$ = $descriptor_name$,\n",
+ "descriptor_key", kDescriptorKey,
+ "descriptor_name", ModuleLevelServiceDescriptorName(descriptor));
+ printer_->Print(
+ "__module__ = '$module_name$'\n",
+ "module_name", ModuleName(file_->name()));
+}
+
+void Generator::PrintServiceClass(const ServiceDescriptor& descriptor) const {
+ // Print the service.
+ printer_->Print("$class_name$ = service_reflection.GeneratedServiceType("
+ "'$class_name$', (_service.Service,), dict(\n",
+ "class_name", descriptor.name());
+ printer_->Indent();
+ Generator::PrintDescriptorKeyAndModuleName(descriptor);
+ printer_->Print("))\n\n");
+ printer_->Outdent();
+}
+
+void Generator::PrintServiceStub(const ServiceDescriptor& descriptor) const {
+ // Print the service stub.
+ printer_->Print("$class_name$_Stub = "
+ "service_reflection.GeneratedServiceStubType("
+ "'$class_name$_Stub', ($class_name$,), dict(\n",
+ "class_name", descriptor.name());
+ printer_->Indent();
+ Generator::PrintDescriptorKeyAndModuleName(descriptor);
+ printer_->Print("))\n\n");
+ printer_->Outdent();
+}
+
+// Prints statement assigning ModuleLevelDescriptorName(message_descriptor)
+// to a Python Descriptor object for message_descriptor.
+//
+// Mutually recursive with PrintNestedDescriptors().
+void Generator::PrintDescriptor(const Descriptor& message_descriptor) const {
+ PrintNestedDescriptors(message_descriptor);
+
+ printer_->Print("\n");
+ printer_->Print("$descriptor_name$ = _descriptor.Descriptor(\n",
+ "descriptor_name",
+ ModuleLevelDescriptorName(message_descriptor));
+ printer_->Indent();
+ map<string, string> m;
+ m["name"] = message_descriptor.name();
+ m["full_name"] = message_descriptor.full_name();
+ m["file"] = kDescriptorKey;
+ const char required_function_arguments[] =
+ "name='$name$',\n"
+ "full_name='$full_name$',\n"
+ "filename=None,\n"
+ "file=$file$,\n"
+ "containing_type=None,\n";
+ printer_->Print(m, required_function_arguments);
+ PrintFieldsInDescriptor(message_descriptor);
+ PrintExtensionsInDescriptor(message_descriptor);
+
+ // Nested types
+ printer_->Print("nested_types=[");
+ for (int i = 0; i < message_descriptor.nested_type_count(); ++i) {
+ const string nested_name = ModuleLevelDescriptorName(
+ *message_descriptor.nested_type(i));
+ printer_->Print("$name$, ", "name", nested_name);
+ }
+ printer_->Print("],\n");
+
+ // Enum types
+ printer_->Print("enum_types=[\n");
+ printer_->Indent();
+ for (int i = 0; i < message_descriptor.enum_type_count(); ++i) {
+ const string descriptor_name = ModuleLevelDescriptorName(
+ *message_descriptor.enum_type(i));
+ printer_->Print(descriptor_name.c_str());
+ printer_->Print(",\n");
+ }
+ printer_->Outdent();
+ printer_->Print("],\n");
+ string options_string;
+ message_descriptor.options().SerializeToString(&options_string);
+ printer_->Print(
+ "options=$options_value$,\n"
+ "is_extendable=$extendable$,\n"
+ "syntax='$syntax$'",
+ "options_value", OptionsValue("MessageOptions", options_string),
+ "extendable", message_descriptor.extension_range_count() > 0 ?
+ "True" : "False",
+ "syntax", StringifySyntax(message_descriptor.file()->syntax()));
+ printer_->Print(",\n");
+
+ // Extension ranges
+ printer_->Print("extension_ranges=[");
+ for (int i = 0; i < message_descriptor.extension_range_count(); ++i) {
+ const Descriptor::ExtensionRange* range =
+ message_descriptor.extension_range(i);
+ printer_->Print("($start$, $end$), ",
+ "start", SimpleItoa(range->start),
+ "end", SimpleItoa(range->end));
+ }
+ printer_->Print("],\n");
+ printer_->Print("oneofs=[\n");
+ printer_->Indent();
+ for (int i = 0; i < message_descriptor.oneof_decl_count(); ++i) {
+ const OneofDescriptor* desc = message_descriptor.oneof_decl(i);
+ map<string, string> m;
+ m["name"] = desc->name();
+ m["full_name"] = desc->full_name();
+ m["index"] = SimpleItoa(desc->index());
+ string options_string =
+ OptionsValue("OneofOptions", desc->options().SerializeAsString());
+ if (options_string == "None") {
+ m["options"] = "";
+ } else {
+ m["options"] = ", options=" + options_string;
+ }
+ printer_->Print(
+ m,
+ "_descriptor.OneofDescriptor(\n"
+ " name='$name$', full_name='$full_name$',\n"
+ " index=$index$, containing_type=None, fields=[]$options$),\n");
+ }
+ printer_->Outdent();
+ printer_->Print("],\n");
+ // Serialization of proto
+ DescriptorProto edp;
+ PrintSerializedPbInterval(message_descriptor, edp);
+
+ printer_->Outdent();
+ printer_->Print(")\n");
+}
+
+// Prints Python Descriptor objects for all nested types contained in
+// message_descriptor.
+//
+// Mutually recursive with PrintDescriptor().
+void Generator::PrintNestedDescriptors(
+ const Descriptor& containing_descriptor) const {
+ for (int i = 0; i < containing_descriptor.nested_type_count(); ++i) {
+ PrintDescriptor(*containing_descriptor.nested_type(i));
+ }
+}
+
+// Prints all messages in |file|.
+void Generator::PrintMessages() const {
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ vector<string> to_register;
+ PrintMessage(*file_->message_type(i), "", &to_register);
+ for (int j = 0; j < to_register.size(); ++j) {
+ printer_->Print("_sym_db.RegisterMessage($name$)\n", "name",
+ to_register[j]);
+ }
+ printer_->Print("\n");
+ }
+}
+
+// Prints a Python class for the given message descriptor. We defer to the
+// metaclass to do almost all of the work of actually creating a useful class.
+// The purpose of this function and its many helper functions above is merely
+// to output a Python version of the descriptors, which the metaclass in
+// reflection.py will use to construct the meat of the class itself.
+//
+// Mutually recursive with PrintNestedMessages().
+// Collect nested message names to_register for the symbol_database.
+void Generator::PrintMessage(const Descriptor& message_descriptor,
+ const string& prefix,
+ vector<string>* to_register) const {
+ string qualified_name(prefix + message_descriptor.name());
+ to_register->push_back(qualified_name);
+ printer_->Print(
+ "$name$ = _reflection.GeneratedProtocolMessageType('$name$', "
+ "(_message.Message,), dict(\n",
+ "name", message_descriptor.name());
+ printer_->Indent();
+
+ PrintNestedMessages(message_descriptor, qualified_name + ".", to_register);
+ map<string, string> m;
+ m["descriptor_key"] = kDescriptorKey;
+ m["descriptor_name"] = ModuleLevelDescriptorName(message_descriptor);
+ printer_->Print(m, "$descriptor_key$ = $descriptor_name$,\n");
+ printer_->Print("__module__ = '$module_name$'\n",
+ "module_name", ModuleName(file_->name()));
+ printer_->Print("# @@protoc_insertion_point(class_scope:$full_name$)\n",
+ "full_name", message_descriptor.full_name());
+ printer_->Print("))\n");
+ printer_->Outdent();
+}
+
+// Prints all nested messages within |containing_descriptor|.
+// Mutually recursive with PrintMessage().
+void Generator::PrintNestedMessages(const Descriptor& containing_descriptor,
+ const string& prefix,
+ vector<string>* to_register) const {
+ for (int i = 0; i < containing_descriptor.nested_type_count(); ++i) {
+ printer_->Print("\n");
+ PrintMessage(*containing_descriptor.nested_type(i), prefix, to_register);
+ printer_->Print(",\n");
+ }
+}
+
+// Recursively fixes foreign fields in all nested types in |descriptor|, then
+// sets the message_type and enum_type of all message and enum fields to point
+// to their respective descriptors.
+// Args:
+// descriptor: descriptor to print fields for.
+// containing_descriptor: if descriptor is a nested type, this is its
+// containing type, or NULL if this is a root/top-level type.
+void Generator::FixForeignFieldsInDescriptor(
+ const Descriptor& descriptor,
+ const Descriptor* containing_descriptor) const {
+ for (int i = 0; i < descriptor.nested_type_count(); ++i) {
+ FixForeignFieldsInDescriptor(*descriptor.nested_type(i), &descriptor);
+ }
+
+ for (int i = 0; i < descriptor.field_count(); ++i) {
+ const FieldDescriptor& field_descriptor = *descriptor.field(i);
+ FixForeignFieldsInField(&descriptor, field_descriptor, "fields_by_name");
+ }
+
+ FixContainingTypeInDescriptor(descriptor, containing_descriptor);
+ for (int i = 0; i < descriptor.enum_type_count(); ++i) {
+ const EnumDescriptor& enum_descriptor = *descriptor.enum_type(i);
+ FixContainingTypeInDescriptor(enum_descriptor, &descriptor);
+ }
+ for (int i = 0; i < descriptor.oneof_decl_count(); ++i) {
+ map<string, string> m;
+ const OneofDescriptor* oneof = descriptor.oneof_decl(i);
+ m["descriptor_name"] = ModuleLevelDescriptorName(descriptor);
+ m["oneof_name"] = oneof->name();
+ for (int j = 0; j < oneof->field_count(); ++j) {
+ m["field_name"] = oneof->field(j)->name();
+ printer_->Print(
+ m,
+ "$descriptor_name$.oneofs_by_name['$oneof_name$'].fields.append(\n"
+ " $descriptor_name$.fields_by_name['$field_name$'])\n");
+ printer_->Print(
+ m,
+ "$descriptor_name$.fields_by_name['$field_name$'].containing_oneof = "
+ "$descriptor_name$.oneofs_by_name['$oneof_name$']\n");
+ }
+ }
+}
+
+void Generator::AddMessageToFileDescriptor(const Descriptor& descriptor) const {
+ map<string, string> m;
+ m["descriptor_name"] = kDescriptorKey;
+ m["message_name"] = descriptor.name();
+ m["message_descriptor_name"] = ModuleLevelDescriptorName(descriptor);
+ const char file_descriptor_template[] =
+ "$descriptor_name$.message_types_by_name['$message_name$'] = "
+ "$message_descriptor_name$\n";
+ printer_->Print(m, file_descriptor_template);
+}
+
+void Generator::AddEnumToFileDescriptor(
+ const EnumDescriptor& descriptor) const {
+ map<string, string> m;
+ m["descriptor_name"] = kDescriptorKey;
+ m["enum_name"] = descriptor.name();
+ m["enum_descriptor_name"] = ModuleLevelDescriptorName(descriptor);
+ const char file_descriptor_template[] =
+ "$descriptor_name$.enum_types_by_name['$enum_name$'] = "
+ "$enum_descriptor_name$\n";
+ printer_->Print(m, file_descriptor_template);
+}
+
+void Generator::AddExtensionToFileDescriptor(
+ const FieldDescriptor& descriptor) const {
+ map<string, string> m;
+ m["descriptor_name"] = kDescriptorKey;
+ m["field_name"] = descriptor.name();
+ const char file_descriptor_template[] =
+ "$descriptor_name$.extensions_by_name['$field_name$'] = "
+ "$field_name$\n";
+ printer_->Print(m, file_descriptor_template);
+}
+
+// Sets any necessary message_type and enum_type attributes
+// for the Python version of |field|.
+//
+// containing_type may be NULL, in which case this is a module-level field.
+//
+// python_dict_name is the name of the Python dict where we should
+// look the field up in the containing type. (e.g., fields_by_name
+// or extensions_by_name). We ignore python_dict_name if containing_type
+// is NULL.
+void Generator::FixForeignFieldsInField(const Descriptor* containing_type,
+ const FieldDescriptor& field,
+ const string& python_dict_name) const {
+ const string field_referencing_expression = FieldReferencingExpression(
+ containing_type, field, python_dict_name);
+ map<string, string> m;
+ m["field_ref"] = field_referencing_expression;
+ const Descriptor* foreign_message_type = field.message_type();
+ if (foreign_message_type) {
+ m["foreign_type"] = ModuleLevelDescriptorName(*foreign_message_type);
+ printer_->Print(m, "$field_ref$.message_type = $foreign_type$\n");
+ }
+ const EnumDescriptor* enum_type = field.enum_type();
+ if (enum_type) {
+ m["enum_type"] = ModuleLevelDescriptorName(*enum_type);
+ printer_->Print(m, "$field_ref$.enum_type = $enum_type$\n");
+ }
+}
+
+// Returns the module-level expression for the given FieldDescriptor.
+// Only works for fields in the .proto file this Generator is generating for.
+//
+// containing_type may be NULL, in which case this is a module-level field.
+//
+// python_dict_name is the name of the Python dict where we should
+// look the field up in the containing type. (e.g., fields_by_name
+// or extensions_by_name). We ignore python_dict_name if containing_type
+// is NULL.
+string Generator::FieldReferencingExpression(
+ const Descriptor* containing_type,
+ const FieldDescriptor& field,
+ const string& python_dict_name) const {
+ // We should only ever be looking up fields in the current file.
+ // The only things we refer to from other files are message descriptors.
+ GOOGLE_CHECK_EQ(field.file(), file_) << field.file()->name() << " vs. "
+ << file_->name();
+ if (!containing_type) {
+ return field.name();
+ }
+ return strings::Substitute(
+ "$0.$1['$2']",
+ ModuleLevelDescriptorName(*containing_type),
+ python_dict_name, field.name());
+}
+
+// Prints containing_type for nested descriptors or enum descriptors.
+template <typename DescriptorT>
+void Generator::FixContainingTypeInDescriptor(
+ const DescriptorT& descriptor,
+ const Descriptor* containing_descriptor) const {
+ if (containing_descriptor != NULL) {
+ const string nested_name = ModuleLevelDescriptorName(descriptor);
+ const string parent_name = ModuleLevelDescriptorName(
+ *containing_descriptor);
+ printer_->Print(
+ "$nested_name$.containing_type = $parent_name$\n",
+ "nested_name", nested_name,
+ "parent_name", parent_name);
+ }
+}
+
+// Prints statements setting the message_type and enum_type fields in the
+// Python descriptor objects we've already output in ths file. We must
+// do this in a separate step due to circular references (otherwise, we'd
+// just set everything in the initial assignment statements).
+void Generator::FixForeignFieldsInDescriptors() const {
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ FixForeignFieldsInDescriptor(*file_->message_type(i), NULL);
+ }
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ AddMessageToFileDescriptor(*file_->message_type(i));
+ }
+ for (int i = 0; i < file_->enum_type_count(); ++i) {
+ AddEnumToFileDescriptor(*file_->enum_type(i));
+ }
+ for (int i = 0; i < file_->extension_count(); ++i) {
+ AddExtensionToFileDescriptor(*file_->extension(i));
+ }
+ printer_->Print("\n");
+}
+
+// We need to not only set any necessary message_type fields, but
+// also need to call RegisterExtension() on each message we're
+// extending.
+void Generator::FixForeignFieldsInExtensions() const {
+ // Top-level extensions.
+ for (int i = 0; i < file_->extension_count(); ++i) {
+ FixForeignFieldsInExtension(*file_->extension(i));
+ }
+ // Nested extensions.
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ FixForeignFieldsInNestedExtensions(*file_->message_type(i));
+ }
+ printer_->Print("\n");
+}
+
+void Generator::FixForeignFieldsInExtension(
+ const FieldDescriptor& extension_field) const {
+ GOOGLE_CHECK(extension_field.is_extension());
+ // extension_scope() will be NULL for top-level extensions, which is
+ // exactly what FixForeignFieldsInField() wants.
+ FixForeignFieldsInField(extension_field.extension_scope(), extension_field,
+ "extensions_by_name");
+
+ map<string, string> m;
+ // Confusingly, for FieldDescriptors that happen to be extensions,
+ // containing_type() means "extended type."
+ // On the other hand, extension_scope() will give us what we normally
+ // mean by containing_type().
+ m["extended_message_class"] = ModuleLevelMessageName(
+ *extension_field.containing_type());
+ m["field"] = FieldReferencingExpression(extension_field.extension_scope(),
+ extension_field,
+ "extensions_by_name");
+ printer_->Print(m, "$extended_message_class$.RegisterExtension($field$)\n");
+}
+
+void Generator::FixForeignFieldsInNestedExtensions(
+ const Descriptor& descriptor) const {
+ // Recursively fix up extensions in all nested types.
+ for (int i = 0; i < descriptor.nested_type_count(); ++i) {
+ FixForeignFieldsInNestedExtensions(*descriptor.nested_type(i));
+ }
+ // Fix up extensions directly contained within this type.
+ for (int i = 0; i < descriptor.extension_count(); ++i) {
+ FixForeignFieldsInExtension(*descriptor.extension(i));
+ }
+}
+
+// Returns a Python expression that instantiates a Python EnumValueDescriptor
+// object for the given C++ descriptor.
+void Generator::PrintEnumValueDescriptor(
+ const EnumValueDescriptor& descriptor) const {
+ // TODO(robinson): Fix up EnumValueDescriptor "type" fields.
+ // More circular references. ::sigh::
+ string options_string;
+ descriptor.options().SerializeToString(&options_string);
+ map<string, string> m;
+ m["name"] = descriptor.name();
+ m["index"] = SimpleItoa(descriptor.index());
+ m["number"] = SimpleItoa(descriptor.number());
+ m["options"] = OptionsValue("EnumValueOptions", options_string);
+ printer_->Print(
+ m,
+ "_descriptor.EnumValueDescriptor(\n"
+ " name='$name$', index=$index$, number=$number$,\n"
+ " options=$options$,\n"
+ " type=None)");
+}
+
+// Returns a Python expression that calls descriptor._ParseOptions using
+// the given descriptor class name and serialized options protobuf string.
+string Generator::OptionsValue(
+ const string& class_name, const string& serialized_options) const {
+ if (serialized_options.length() == 0 || GeneratingDescriptorProto()) {
+ return "None";
+ } else {
+ string full_class_name = "descriptor_pb2." + class_name;
+//##!PY25 return "_descriptor._ParseOptions(" + full_class_name + "(), b'"
+//##!PY25 + CEscape(serialized_options)+ "')";
+ return "_descriptor._ParseOptions(" + full_class_name + "(), _b('" //##PY25
+ + CEscape(serialized_options)+ "'))"; //##PY25
+ }
+}
+
+// Prints an expression for a Python FieldDescriptor for |field|.
+void Generator::PrintFieldDescriptor(
+ const FieldDescriptor& field, bool is_extension) const {
+ string options_string;
+ field.options().SerializeToString(&options_string);
+ map<string, string> m;
+ m["name"] = field.name();
+ m["full_name"] = field.full_name();
+ m["index"] = SimpleItoa(field.index());
+ m["number"] = SimpleItoa(field.number());
+ m["type"] = SimpleItoa(field.type());
+ m["cpp_type"] = SimpleItoa(field.cpp_type());
+ m["label"] = SimpleItoa(field.label());
+ m["has_default_value"] = field.has_default_value() ? "True" : "False";
+ m["default_value"] = StringifyDefaultValue(field);
+ m["is_extension"] = is_extension ? "True" : "False";
+ m["options"] = OptionsValue("FieldOptions", options_string);
+ // We always set message_type and enum_type to None at this point, and then
+ // these fields in correctly after all referenced descriptors have been
+ // defined and/or imported (see FixForeignFieldsInDescriptors()).
+ const char field_descriptor_decl[] =
+ "_descriptor.FieldDescriptor(\n"
+ " name='$name$', full_name='$full_name$', index=$index$,\n"
+ " number=$number$, type=$type$, cpp_type=$cpp_type$, label=$label$,\n"
+ " has_default_value=$has_default_value$, default_value=$default_value$,\n"
+ " message_type=None, enum_type=None, containing_type=None,\n"
+ " is_extension=$is_extension$, extension_scope=None,\n"
+ " options=$options$)";
+ printer_->Print(m, field_descriptor_decl);
+}
+
+// Helper for Print{Fields,Extensions}InDescriptor().
+void Generator::PrintFieldDescriptorsInDescriptor(
+ const Descriptor& message_descriptor,
+ bool is_extension,
+ const string& list_variable_name,
+ int (Descriptor::*CountFn)() const,
+ const FieldDescriptor* (Descriptor::*GetterFn)(int) const) const {
+ printer_->Print("$list$=[\n", "list", list_variable_name);
+ printer_->Indent();
+ for (int i = 0; i < (message_descriptor.*CountFn)(); ++i) {
+ PrintFieldDescriptor(*(message_descriptor.*GetterFn)(i),
+ is_extension);
+ printer_->Print(",\n");
+ }
+ printer_->Outdent();
+ printer_->Print("],\n");
+}
+
+// Prints a statement assigning "fields" to a list of Python FieldDescriptors,
+// one for each field present in message_descriptor.
+void Generator::PrintFieldsInDescriptor(
+ const Descriptor& message_descriptor) const {
+ const bool is_extension = false;
+ PrintFieldDescriptorsInDescriptor(
+ message_descriptor, is_extension, "fields",
+ &Descriptor::field_count, &Descriptor::field);
+}
+
+// Prints a statement assigning "extensions" to a list of Python
+// FieldDescriptors, one for each extension present in message_descriptor.
+void Generator::PrintExtensionsInDescriptor(
+ const Descriptor& message_descriptor) const {
+ const bool is_extension = true;
+ PrintFieldDescriptorsInDescriptor(
+ message_descriptor, is_extension, "extensions",
+ &Descriptor::extension_count, &Descriptor::extension);
+}
+
+bool Generator::GeneratingDescriptorProto() const {
+ return file_->name() == "google/protobuf/descriptor.proto";
+}
+
+// Returns the unique Python module-level identifier given to a descriptor.
+// This name is module-qualified iff the given descriptor describes an
+// entity that doesn't come from the current file.
+template <typename DescriptorT>
+string Generator::ModuleLevelDescriptorName(
+ const DescriptorT& descriptor) const {
+ // FIXME(robinson):
+ // We currently don't worry about collisions with underscores in the type
+ // names, so these would collide in nasty ways if found in the same file:
+ // OuterProto.ProtoA.ProtoB
+ // OuterProto_ProtoA.ProtoB # Underscore instead of period.
+ // As would these:
+ // OuterProto.ProtoA_.ProtoB
+ // OuterProto.ProtoA._ProtoB # Leading vs. trailing underscore.
+ // (Contrived, but certainly possible).
+ //
+ // The C++ implementation doesn't guard against this either. Leaving
+ // it for now...
+ string name = NamePrefixedWithNestedTypes(descriptor, "_");
+ UpperString(&name);
+ // Module-private for now. Easy to make public later; almost impossible
+ // to make private later.
+ name = "_" + name;
+ // We now have the name relative to its own module. Also qualify with
+ // the module name iff this descriptor is from a different .proto file.
+ if (descriptor.file() != file_) {
+ name = ModuleAlias(descriptor.file()->name()) + "." + name;
+ }
+ return name;
+}
+
+// Returns the name of the message class itself, not the descriptor.
+// Like ModuleLevelDescriptorName(), module-qualifies the name iff
+// the given descriptor describes an entity that doesn't come from
+// the current file.
+string Generator::ModuleLevelMessageName(const Descriptor& descriptor) const {
+ string name = NamePrefixedWithNestedTypes(descriptor, ".");
+ if (descriptor.file() != file_) {
+ name = ModuleAlias(descriptor.file()->name()) + "." + name;
+ }
+ return name;
+}
+
+// Returns the unique Python module-level identifier given to a service
+// descriptor.
+string Generator::ModuleLevelServiceDescriptorName(
+ const ServiceDescriptor& descriptor) const {
+ string name = descriptor.name();
+ UpperString(&name);
+ name = "_" + name;
+ if (descriptor.file() != file_) {
+ name = ModuleAlias(descriptor.file()->name()) + "." + name;
+ }
+ return name;
+}
+
+// Prints standard constructor arguments serialized_start and serialized_end.
+// Args:
+// descriptor: The cpp descriptor to have a serialized reference.
+// proto: A proto
+// Example printer output:
+// serialized_start=41,
+// serialized_end=43,
+//
+template <typename DescriptorT, typename DescriptorProtoT>
+void Generator::PrintSerializedPbInterval(
+ const DescriptorT& descriptor, DescriptorProtoT& proto) const {
+ descriptor.CopyTo(&proto);
+ string sp;
+ proto.SerializeToString(&sp);
+ int offset = file_descriptor_serialized_.find(sp);
+ GOOGLE_CHECK_GE(offset, 0);
+
+ printer_->Print("serialized_start=$serialized_start$,\n"
+ "serialized_end=$serialized_end$,\n",
+ "serialized_start", SimpleItoa(offset),
+ "serialized_end", SimpleItoa(offset + sp.size()));
+}
+
+namespace {
+void PrintDescriptorOptionsFixingCode(const string& descriptor,
+ const string& options,
+ io::Printer* printer) {
+ // TODO(xiaofeng): I have added a method _SetOptions() to DescriptorBase
+ // in proto2 python runtime but it couldn't be used here because appengine
+ // uses a snapshot version of the library in which the new method is not
+ // yet present. After appengine has synced their runtime library, the code
+ // below should be cleaned up to use _SetOptions().
+ printer->Print(
+ "$descriptor$.has_options = True\n"
+ "$descriptor$._options = $options$\n",
+ "descriptor", descriptor, "options", options);
+}
+} // namespace
+
+// Prints expressions that set the options field of all descriptors.
+void Generator::FixAllDescriptorOptions() const {
+ // Prints an expression that sets the file descriptor's options.
+ string file_options = OptionsValue(
+ "FileOptions", file_->options().SerializeAsString());
+ if (file_options != "None") {
+ PrintDescriptorOptionsFixingCode(kDescriptorKey, file_options, printer_);
+ }
+ // Prints expressions that set the options for all top level enums.
+ for (int i = 0; i < file_->enum_type_count(); ++i) {
+ const EnumDescriptor& enum_descriptor = *file_->enum_type(i);
+ FixOptionsForEnum(enum_descriptor);
+ }
+ // Prints expressions that set the options for all top level extensions.
+ for (int i = 0; i < file_->extension_count(); ++i) {
+ const FieldDescriptor& field = *file_->extension(i);
+ FixOptionsForField(field);
+ }
+ // Prints expressions that set the options for all messages, nested enums,
+ // nested extensions and message fields.
+ for (int i = 0; i < file_->message_type_count(); ++i) {
+ FixOptionsForMessage(*file_->message_type(i));
+ }
+}
+
+void Generator::FixOptionsForOneof(const OneofDescriptor& oneof) const {
+ string oneof_options = OptionsValue(
+ "OneofOptions", oneof.options().SerializeAsString());
+ if (oneof_options != "None") {
+ string oneof_name = strings::Substitute(
+ "$0.$1['$2']",
+ ModuleLevelDescriptorName(*oneof.containing_type()),
+ "oneofs_by_name", oneof.name());
+ PrintDescriptorOptionsFixingCode(oneof_name, oneof_options, printer_);
+ }
+}
+
+// Prints expressions that set the options for an enum descriptor and its
+// value descriptors.
+void Generator::FixOptionsForEnum(const EnumDescriptor& enum_descriptor) const {
+ string descriptor_name = ModuleLevelDescriptorName(enum_descriptor);
+ string enum_options = OptionsValue(
+ "EnumOptions", enum_descriptor.options().SerializeAsString());
+ if (enum_options != "None") {
+ PrintDescriptorOptionsFixingCode(descriptor_name, enum_options, printer_);
+ }
+ for (int i = 0; i < enum_descriptor.value_count(); ++i) {
+ const EnumValueDescriptor& value_descriptor = *enum_descriptor.value(i);
+ string value_options = OptionsValue(
+ "EnumValueOptions", value_descriptor.options().SerializeAsString());
+ if (value_options != "None") {
+ PrintDescriptorOptionsFixingCode(
+ StringPrintf("%s.values_by_name[\"%s\"]", descriptor_name.c_str(),
+ value_descriptor.name().c_str()),
+ value_options, printer_);
+ }
+ }
+}
+
+// Prints expressions that set the options for field descriptors (including
+// extensions).
+void Generator::FixOptionsForField(
+ const FieldDescriptor& field) const {
+ string field_options = OptionsValue(
+ "FieldOptions", field.options().SerializeAsString());
+ if (field_options != "None") {
+ string field_name;
+ if (field.is_extension()) {
+ if (field.extension_scope() == NULL) {
+ // Top level extensions.
+ field_name = field.name();
+ } else {
+ field_name = FieldReferencingExpression(
+ field.extension_scope(), field, "extensions_by_name");
+ }
+ } else {
+ field_name = FieldReferencingExpression(
+ field.containing_type(), field, "fields_by_name");
+ }
+ PrintDescriptorOptionsFixingCode(field_name, field_options, printer_);
+ }
+}
+
+// Prints expressions that set the options for a message and all its inner
+// types (nested messages, nested enums, extensions, fields).
+void Generator::FixOptionsForMessage(const Descriptor& descriptor) const {
+ // Nested messages.
+ for (int i = 0; i < descriptor.nested_type_count(); ++i) {
+ FixOptionsForMessage(*descriptor.nested_type(i));
+ }
+ // Oneofs.
+ for (int i = 0; i < descriptor.oneof_decl_count(); ++i) {
+ FixOptionsForOneof(*descriptor.oneof_decl(i));
+ }
+ // Enums.
+ for (int i = 0; i < descriptor.enum_type_count(); ++i) {
+ FixOptionsForEnum(*descriptor.enum_type(i));
+ }
+ // Fields.
+ for (int i = 0; i < descriptor.field_count(); ++i) {
+ const FieldDescriptor& field = *descriptor.field(i);
+ FixOptionsForField(field);
+ }
+ // Extensions.
+ for (int i = 0; i < descriptor.extension_count(); ++i) {
+ const FieldDescriptor& field = *descriptor.extension(i);
+ FixOptionsForField(field);
+ }
+ // Message option for this message.
+ string message_options = OptionsValue(
+ "MessageOptions", descriptor.options().SerializeAsString());
+ if (message_options != "None") {
+ string descriptor_name = ModuleLevelDescriptorName(descriptor);
+ PrintDescriptorOptionsFixingCode(descriptor_name,
+ message_options,
+ printer_);
+ }
+}
+
+// If a dependency forwards other files through public dependencies, let's
+// copy over the corresponding module aliases.
+void Generator::CopyPublicDependenciesAliases(
+ const string& copy_from, const FileDescriptor* file) const {
+ for (int i = 0; i < file->public_dependency_count(); ++i) {
+ string module_alias = ModuleAlias(file->public_dependency(i)->name());
+ printer_->Print("$alias$ = $copy_from$.$alias$\n", "alias", module_alias,
+ "copy_from", copy_from);
+ CopyPublicDependenciesAliases(copy_from, file->public_dependency(i));
+ }
+}
+
+} // namespace python
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.h
new file mode 100644
index 0000000000..7583aa65bf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_generator.h
@@ -0,0 +1,174 @@
+// 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: robinson@google.com (Will Robinson)
+//
+// Generates Python code for a given .proto file.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_PYTHON_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_PYTHON_GENERATOR_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/stubs/mutex.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+class Descriptor;
+class EnumDescriptor;
+class EnumValueDescriptor;
+class FieldDescriptor;
+class OneofDescriptor;
+class ServiceDescriptor;
+
+namespace io { class Printer; }
+
+namespace compiler {
+namespace python {
+
+// CodeGenerator implementation for generated Python protocol buffer classes.
+// If you create your own protocol compiler binary and you want it to support
+// Python output, you can do so by registering an instance of this
+// CodeGenerator with the CommandLineInterface in your main() function.
+class LIBPROTOC_EXPORT Generator : public CodeGenerator {
+ public:
+ Generator();
+ virtual ~Generator();
+
+ // CodeGenerator methods.
+ virtual bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const;
+
+ private:
+ void PrintImports() const;
+ void PrintFileDescriptor() const;
+ void PrintTopLevelEnums() const;
+ void PrintAllNestedEnumsInFile() const;
+ void PrintNestedEnums(const Descriptor& descriptor) const;
+ void PrintEnum(const EnumDescriptor& enum_descriptor) const;
+
+ void PrintTopLevelExtensions() const;
+
+ void PrintFieldDescriptor(
+ const FieldDescriptor& field, bool is_extension) const;
+ void PrintFieldDescriptorsInDescriptor(
+ const Descriptor& message_descriptor,
+ bool is_extension,
+ const string& list_variable_name,
+ int (Descriptor::*CountFn)() const,
+ const FieldDescriptor* (Descriptor::*GetterFn)(int) const) const;
+ void PrintFieldsInDescriptor(const Descriptor& message_descriptor) const;
+ void PrintExtensionsInDescriptor(const Descriptor& message_descriptor) const;
+ void PrintMessageDescriptors() const;
+ void PrintDescriptor(const Descriptor& message_descriptor) const;
+ void PrintNestedDescriptors(const Descriptor& containing_descriptor) const;
+
+ void PrintMessages() const;
+ void PrintMessage(const Descriptor& message_descriptor, const string& prefix,
+ vector<string>* to_register) const;
+ void PrintNestedMessages(const Descriptor& containing_descriptor,
+ const string& prefix,
+ vector<string>* to_register) const;
+
+ void FixForeignFieldsInDescriptors() const;
+ void FixForeignFieldsInDescriptor(
+ const Descriptor& descriptor,
+ const Descriptor* containing_descriptor) const;
+ void FixForeignFieldsInField(const Descriptor* containing_type,
+ const FieldDescriptor& field,
+ const string& python_dict_name) const;
+ void AddMessageToFileDescriptor(const Descriptor& descriptor) const;
+ void AddEnumToFileDescriptor(const EnumDescriptor& descriptor) const;
+ void AddExtensionToFileDescriptor(const FieldDescriptor& descriptor) const;
+ string FieldReferencingExpression(const Descriptor* containing_type,
+ const FieldDescriptor& field,
+ const string& python_dict_name) const;
+ template <typename DescriptorT>
+ void FixContainingTypeInDescriptor(
+ const DescriptorT& descriptor,
+ const Descriptor* containing_descriptor) const;
+
+ void FixForeignFieldsInExtensions() const;
+ void FixForeignFieldsInExtension(
+ const FieldDescriptor& extension_field) const;
+ void FixForeignFieldsInNestedExtensions(const Descriptor& descriptor) const;
+
+ void PrintServices() const;
+ void PrintServiceDescriptor(const ServiceDescriptor& descriptor) const;
+ void PrintServiceClass(const ServiceDescriptor& descriptor) const;
+ void PrintServiceStub(const ServiceDescriptor& descriptor) const;
+ void PrintDescriptorKeyAndModuleName(
+ const ServiceDescriptor& descriptor) const ;
+
+ void PrintEnumValueDescriptor(const EnumValueDescriptor& descriptor) const;
+ string OptionsValue(const string& class_name,
+ const string& serialized_options) const;
+ bool GeneratingDescriptorProto() const;
+
+ template <typename DescriptorT>
+ string ModuleLevelDescriptorName(const DescriptorT& descriptor) const;
+ string ModuleLevelMessageName(const Descriptor& descriptor) const;
+ string ModuleLevelServiceDescriptorName(
+ const ServiceDescriptor& descriptor) const;
+
+ template <typename DescriptorT, typename DescriptorProtoT>
+ void PrintSerializedPbInterval(
+ const DescriptorT& descriptor, DescriptorProtoT& proto) const;
+
+ void FixAllDescriptorOptions() const;
+ void FixOptionsForField(const FieldDescriptor& field) const;
+ void FixOptionsForOneof(const OneofDescriptor& oneof) const;
+ void FixOptionsForEnum(const EnumDescriptor& descriptor) const;
+ void FixOptionsForMessage(const Descriptor& descriptor) const;
+
+ void CopyPublicDependenciesAliases(
+ const string& copy_from, const FileDescriptor* file) const;
+
+ // Very coarse-grained lock to ensure that Generate() is reentrant.
+ // Guards file_, printer_ and file_descriptor_serialized_.
+ mutable Mutex mutex_;
+ mutable const FileDescriptor* file_; // Set in Generate(). Under mutex_.
+ mutable string file_descriptor_serialized_;
+ mutable io::Printer* printer_; // Set in Generate(). Under mutex_.
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Generator);
+};
+
+} // namespace python
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_PYTHON_GENERATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_plugin_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_plugin_unittest.cc
new file mode 100644
index 0000000000..34f857fddb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/python/python_plugin_unittest.cc
@@ -0,0 +1,170 @@
+// 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)
+//
+// TODO(kenton): Share code with the versions of this test in other languages?
+// It seemed like parameterizing it would add more complexity than it is
+// worth.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/compiler/python/python_generator.h>
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/printer.h>
+
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace python {
+namespace {
+
+class TestGenerator : public CodeGenerator {
+ public:
+ TestGenerator() {}
+ ~TestGenerator() {}
+
+ virtual bool Generate(const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* context,
+ string* error) const {
+ TryInsert("test_pb2.py", "imports", context);
+ TryInsert("test_pb2.py", "module_scope", context);
+ TryInsert("test_pb2.py", "class_scope:foo.Bar", context);
+ TryInsert("test_pb2.py", "class_scope:foo.Bar.Baz", context);
+ return true;
+ }
+
+ void TryInsert(const string& filename, const string& insertion_point,
+ GeneratorContext* context) const {
+ google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(
+ context->OpenForInsert(filename, insertion_point));
+ io::Printer printer(output.get(), '$');
+ printer.Print("// inserted $name$\n", "name", insertion_point);
+ }
+};
+
+// This test verifies that all the expected insertion points exist. It does
+// not verify that they are correctly-placed; that would require actually
+// compiling the output which is a bit more than I care to do for this test.
+TEST(PythonPluginTest, PluginTest) {
+ GOOGLE_CHECK_OK(File::SetContents(TestTempDir() + "/test.proto",
+ "syntax = \"proto2\";\n"
+ "package foo;\n"
+ "message Bar {\n"
+ " message Baz {}\n"
+ "}\n",
+ true));
+
+ google::protobuf::compiler::CommandLineInterface cli;
+ cli.SetInputsAreProtoPathRelative(true);
+
+ python::Generator python_generator;
+ TestGenerator test_generator;
+ cli.RegisterGenerator("--python_out", &python_generator, "");
+ cli.RegisterGenerator("--test_out", &test_generator, "");
+
+ string proto_path = "-I" + TestTempDir();
+ string python_out = "--python_out=" + TestTempDir();
+ string test_out = "--test_out=" + TestTempDir();
+
+ const char* argv[] = {
+ "protoc",
+ proto_path.c_str(),
+ python_out.c_str(),
+ test_out.c_str(),
+ "test.proto"
+ };
+
+ EXPECT_EQ(0, cli.Run(5, argv));
+}
+
+// This test verifies that the generated Python output uses regular imports (as
+// opposed to importlib) in the usual case where the .proto file paths do not
+// not contain any Python keywords.
+TEST(PythonPluginTest, ImportTest) {
+ // Create files test1.proto and test2.proto with the former importing the
+ // latter.
+ GOOGLE_CHECK_OK(File::SetContents(TestTempDir() + "/test1.proto",
+ "syntax = \"proto3\";\n"
+ "package foo;\n"
+ "import \"test2.proto\";"
+ "message Message1 {\n"
+ " Message2 message_2 = 1;\n"
+ "}\n",
+ true));
+ GOOGLE_CHECK_OK(File::SetContents(TestTempDir() + "/test2.proto",
+ "syntax = \"proto3\";\n"
+ "package foo;\n"
+ "message Message2 {}\n",
+ true));
+
+ google::protobuf::compiler::CommandLineInterface cli;
+ cli.SetInputsAreProtoPathRelative(true);
+ python::Generator python_generator;
+ cli.RegisterGenerator("--python_out", &python_generator, "");
+ string proto_path = "-I" + TestTempDir();
+ string python_out = "--python_out=" + TestTempDir();
+ const char* argv[] = {"protoc", proto_path.c_str(), "-I.", python_out.c_str(),
+ "test1.proto"};
+ ASSERT_EQ(0, cli.Run(5, argv));
+
+ // Loop over the lines of the generated code and verify that we find an
+ // ordinary Python import but do not find the string "importlib".
+ string output;
+ GOOGLE_CHECK_OK(File::GetContents(TestTempDir() + "/test1_pb2.py", &output,
+ true));
+ std::vector<string> lines = Split(output, "\n");
+ string expected_import = "import test2_pb2";
+ bool found_expected_import = false;
+ for (int i = 0; i < lines.size(); ++i) {
+ if (lines[i].find(expected_import) != string::npos) {
+ found_expected_import = true;
+ }
+ EXPECT_EQ(string::npos, lines[i].find("importlib"));
+ }
+ EXPECT_TRUE(found_expected_import);
+}
+
+} // namespace
+} // namespace python
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code.proto b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code.proto
new file mode 100644
index 0000000000..42d82a6bac
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code.proto
@@ -0,0 +1,67 @@
+syntax = "proto3";
+
+package A.B.C;
+
+message TestMessage {
+ int32 optional_int32 = 1;
+ int64 optional_int64 = 2;
+ uint32 optional_uint32 = 3;
+ uint64 optional_uint64 = 4;
+ bool optional_bool = 5;
+ double optional_double = 6;
+ float optional_float = 7;
+ string optional_string = 8;
+ bytes optional_bytes = 9;
+ TestEnum optional_enum = 10;
+ TestMessage optional_msg = 11;
+
+ repeated int32 repeated_int32 = 21;
+ repeated int64 repeated_int64 = 22;
+ repeated uint32 repeated_uint32 = 23;
+ repeated uint64 repeated_uint64 = 24;
+ repeated bool repeated_bool = 25;
+ repeated double repeated_double = 26;
+ repeated float repeated_float = 27;
+ repeated string repeated_string = 28;
+ repeated bytes repeated_bytes = 29;
+ repeated TestEnum repeated_enum = 30;
+ repeated TestMessage repeated_msg = 31;
+
+ oneof my_oneof {
+ int32 oneof_int32 = 41;
+ int64 oneof_int64 = 42;
+ uint32 oneof_uint32 = 43;
+ uint64 oneof_uint64 = 44;
+ bool oneof_bool = 45;
+ double oneof_double = 46;
+ float oneof_float = 47;
+ string oneof_string = 48;
+ bytes oneof_bytes = 49;
+ TestEnum oneof_enum = 50;
+ TestMessage oneof_msg = 51;
+ }
+
+ map<int32, string> map_int32_string = 61;
+ map<int64, string> map_int64_string = 62;
+ map<uint32, string> map_uint32_string = 63;
+ map<uint64, string> map_uint64_string = 64;
+ map<bool, string> map_bool_string = 65;
+ map<string, string> map_string_string = 66;
+ map<string, TestMessage> map_string_msg = 67;
+ map<string, TestEnum> map_string_enum = 68;
+ map<string, int32> map_string_int32 = 69;
+ map<string, bool> map_string_bool = 70;
+
+ message NestedMessage {
+ int32 foo = 1;
+ }
+
+ NestedMessage nested_message = 80;
+}
+
+enum TestEnum {
+ Default = 0;
+ A = 1;
+ B = 2;
+ C = 3;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code_pb.rb b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code_pb.rb
new file mode 100644
index 0000000000..49b23fbe8d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generated_code_pb.rb
@@ -0,0 +1,74 @@
+# Generated by the protocol buffer compiler. DO NOT EDIT!
+# source: ruby_generated_code.proto
+
+require 'google/protobuf'
+
+Google::Protobuf::DescriptorPool.generated_pool.build do
+ add_message "A.B.C.TestMessage" do
+ optional :optional_int32, :int32, 1
+ optional :optional_int64, :int64, 2
+ optional :optional_uint32, :uint32, 3
+ optional :optional_uint64, :uint64, 4
+ optional :optional_bool, :bool, 5
+ optional :optional_double, :double, 6
+ optional :optional_float, :float, 7
+ optional :optional_string, :string, 8
+ optional :optional_bytes, :bytes, 9
+ optional :optional_enum, :enum, 10, "A.B.C.TestEnum"
+ optional :optional_msg, :message, 11, "A.B.C.TestMessage"
+ repeated :repeated_int32, :int32, 21
+ repeated :repeated_int64, :int64, 22
+ repeated :repeated_uint32, :uint32, 23
+ repeated :repeated_uint64, :uint64, 24
+ repeated :repeated_bool, :bool, 25
+ repeated :repeated_double, :double, 26
+ repeated :repeated_float, :float, 27
+ repeated :repeated_string, :string, 28
+ repeated :repeated_bytes, :bytes, 29
+ repeated :repeated_enum, :enum, 30, "A.B.C.TestEnum"
+ repeated :repeated_msg, :message, 31, "A.B.C.TestMessage"
+ map :map_int32_string, :int32, :string, 61
+ map :map_int64_string, :int64, :string, 62
+ map :map_uint32_string, :uint32, :string, 63
+ map :map_uint64_string, :uint64, :string, 64
+ map :map_bool_string, :bool, :string, 65
+ map :map_string_string, :string, :string, 66
+ map :map_string_msg, :string, :message, 67, "A.B.C.TestMessage"
+ map :map_string_enum, :string, :enum, 68, "A.B.C.TestEnum"
+ map :map_string_int32, :string, :int32, 69
+ map :map_string_bool, :string, :bool, 70
+ optional :nested_message, :message, 80, "A.B.C.TestMessage.NestedMessage"
+ oneof :my_oneof do
+ optional :oneof_int32, :int32, 41
+ optional :oneof_int64, :int64, 42
+ optional :oneof_uint32, :uint32, 43
+ optional :oneof_uint64, :uint64, 44
+ optional :oneof_bool, :bool, 45
+ optional :oneof_double, :double, 46
+ optional :oneof_float, :float, 47
+ optional :oneof_string, :string, 48
+ optional :oneof_bytes, :bytes, 49
+ optional :oneof_enum, :enum, 50, "A.B.C.TestEnum"
+ optional :oneof_msg, :message, 51, "A.B.C.TestMessage"
+ end
+ end
+ add_message "A.B.C.TestMessage.NestedMessage" do
+ optional :foo, :int32, 1
+ end
+ add_enum "A.B.C.TestEnum" do
+ value :Default, 0
+ value :A, 1
+ value :B, 2
+ value :C, 3
+ end
+end
+
+module A
+ module B
+ module C
+ TestMessage = Google::Protobuf::DescriptorPool.generated_pool.lookup("A.B.C.TestMessage").msgclass
+ TestMessage::NestedMessage = Google::Protobuf::DescriptorPool.generated_pool.lookup("A.B.C.TestMessage.NestedMessage").msgclass
+ TestEnum = Google::Protobuf::DescriptorPool.generated_pool.lookup("A.B.C.TestEnum").enummodule
+ end
+ end
+end
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.cc
new file mode 100644
index 0000000000..fbe3b4cb71
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.cc
@@ -0,0 +1,501 @@
+// 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.
+
+#include <sstream>
+
+#include <google/protobuf/compiler/code_generator.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+
+#include <google/protobuf/compiler/ruby/ruby_generator.h>
+
+using google::protobuf::internal::scoped_ptr;
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace ruby {
+
+// Forward decls.
+std::string IntToString(int32 value);
+std::string GetRequireName(const std::string& proto_file);
+std::string LabelForField(google::protobuf::FieldDescriptor* field);
+std::string TypeName(google::protobuf::FieldDescriptor* field);
+void GenerateMessage(const google::protobuf::Descriptor* message,
+ google::protobuf::io::Printer* printer);
+void GenerateEnum(const google::protobuf::EnumDescriptor* en,
+ google::protobuf::io::Printer* printer);
+void GenerateMessageAssignment(
+ const std::string& prefix,
+ const google::protobuf::Descriptor* message,
+ google::protobuf::io::Printer* printer);
+void GenerateEnumAssignment(
+ const std::string& prefix,
+ const google::protobuf::EnumDescriptor* en,
+ google::protobuf::io::Printer* printer);
+
+std::string IntToString(int32 value) {
+ std::ostringstream os;
+ os << value;
+ return os.str();
+}
+
+std::string GetRequireName(const std::string& proto_file) {
+ int lastindex = proto_file.find_last_of(".");
+ return proto_file.substr(0, lastindex) + "_pb";
+}
+
+std::string GetOutputFilename(const std::string& proto_file) {
+ return GetRequireName(proto_file) + ".rb";
+}
+
+std::string LabelForField(const google::protobuf::FieldDescriptor* field) {
+ switch (field->label()) {
+ case FieldDescriptor::LABEL_OPTIONAL: return "optional";
+ case FieldDescriptor::LABEL_REQUIRED: return "required";
+ case FieldDescriptor::LABEL_REPEATED: return "repeated";
+ default: assert(false); return "";
+ }
+}
+
+std::string TypeName(const google::protobuf::FieldDescriptor* field) {
+ switch (field->type()) {
+ case FieldDescriptor::TYPE_INT32: return "int32";
+ case FieldDescriptor::TYPE_INT64: return "int64";
+ case FieldDescriptor::TYPE_UINT32: return "uint32";
+ case FieldDescriptor::TYPE_UINT64: return "uint64";
+ case FieldDescriptor::TYPE_SINT32: return "sint32";
+ case FieldDescriptor::TYPE_SINT64: return "sint64";
+ case FieldDescriptor::TYPE_FIXED32: return "fixed32";
+ case FieldDescriptor::TYPE_FIXED64: return "fixed64";
+ case FieldDescriptor::TYPE_SFIXED32: return "sfixed32";
+ case FieldDescriptor::TYPE_SFIXED64: return "sfixed64";
+ case FieldDescriptor::TYPE_DOUBLE: return "double";
+ case FieldDescriptor::TYPE_FLOAT: return "float";
+ case FieldDescriptor::TYPE_BOOL: return "bool";
+ case FieldDescriptor::TYPE_ENUM: return "enum";
+ case FieldDescriptor::TYPE_STRING: return "string";
+ case FieldDescriptor::TYPE_BYTES: return "bytes";
+ case FieldDescriptor::TYPE_MESSAGE: return "message";
+ case FieldDescriptor::TYPE_GROUP: return "group";
+ default: assert(false); return "";
+ }
+}
+
+void GenerateField(const google::protobuf::FieldDescriptor* field,
+ google::protobuf::io::Printer* printer) {
+
+ if (field->is_map()) {
+ const FieldDescriptor* key_field =
+ field->message_type()->FindFieldByNumber(1);
+ const FieldDescriptor* value_field =
+ field->message_type()->FindFieldByNumber(2);
+
+ printer->Print(
+ "map :$name$, :$key_type$, :$value_type$, $number$",
+ "name", field->name(),
+ "key_type", TypeName(key_field),
+ "value_type", TypeName(value_field),
+ "number", IntToString(field->number()));
+
+ if (value_field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ printer->Print(
+ ", \"$subtype$\"\n",
+ "subtype", value_field->message_type()->full_name());
+ } else if (value_field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ printer->Print(
+ ", \"$subtype$\"\n",
+ "subtype", value_field->enum_type()->full_name());
+ } else {
+ printer->Print("\n");
+ }
+ } else {
+
+ printer->Print(
+ "$label$ :$name$, ",
+ "label", LabelForField(field),
+ "name", field->name());
+ printer->Print(
+ ":$type$, $number$",
+ "type", TypeName(field),
+ "number", IntToString(field->number()));
+
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ printer->Print(
+ ", \"$subtype$\"\n",
+ "subtype", field->message_type()->full_name());
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ printer->Print(
+ ", \"$subtype$\"\n",
+ "subtype", field->enum_type()->full_name());
+ } else {
+ printer->Print("\n");
+ }
+ }
+}
+
+void GenerateOneof(const google::protobuf::OneofDescriptor* oneof,
+ google::protobuf::io::Printer* printer) {
+ printer->Print(
+ "oneof :$name$ do\n",
+ "name", oneof->name());
+ printer->Indent();
+
+ for (int i = 0; i < oneof->field_count(); i++) {
+ const FieldDescriptor* field = oneof->field(i);
+ GenerateField(field, printer);
+ }
+
+ printer->Outdent();
+ printer->Print("end\n");
+}
+
+void GenerateMessage(const google::protobuf::Descriptor* message,
+ google::protobuf::io::Printer* printer) {
+
+ // Don't generate MapEntry messages -- we use the Ruby extension's native
+ // support for map fields instead.
+ if (message->options().map_entry()) {
+ return;
+ }
+
+ printer->Print(
+ "add_message \"$name$\" do\n",
+ "name", message->full_name());
+ printer->Indent();
+
+ for (int i = 0; i < message->field_count(); i++) {
+ const FieldDescriptor* field = message->field(i);
+ if (!field->containing_oneof()) {
+ GenerateField(field, printer);
+ }
+ }
+
+ for (int i = 0; i < message->oneof_decl_count(); i++) {
+ const OneofDescriptor* oneof = message->oneof_decl(i);
+ GenerateOneof(oneof, printer);
+ }
+
+ printer->Outdent();
+ printer->Print("end\n");
+
+ for (int i = 0; i < message->nested_type_count(); i++) {
+ GenerateMessage(message->nested_type(i), printer);
+ }
+ for (int i = 0; i < message->enum_type_count(); i++) {
+ GenerateEnum(message->enum_type(i), printer);
+ }
+}
+
+void GenerateEnum(const google::protobuf::EnumDescriptor* en,
+ google::protobuf::io::Printer* printer) {
+ printer->Print(
+ "add_enum \"$name$\" do\n",
+ "name", en->full_name());
+ printer->Indent();
+
+ for (int i = 0; i < en->value_count(); i++) {
+ const EnumValueDescriptor* value = en->value(i);
+ printer->Print(
+ "value :$name$, $number$\n",
+ "name", value->name(),
+ "number", IntToString(value->number()));
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "end\n");
+}
+
+// Locale-agnostic utility functions.
+bool IsLower(char ch) { return ch >= 'a' && ch <= 'z'; }
+
+bool IsUpper(char ch) { return ch >= 'A' && ch <= 'Z'; }
+
+bool IsAlpha(char ch) { return IsLower(ch) || IsUpper(ch); }
+
+char ToUpper(char ch) { return IsLower(ch) ? (ch - 'a' + 'A') : ch; }
+
+
+// Package names in protobuf are snake_case by convention, but Ruby module
+// names must be PascalCased.
+//
+// foo_bar_baz -> FooBarBaz
+std::string PackageToModule(const std::string& name) {
+ bool next_upper = true;
+ std::string result;
+ result.reserve(name.size());
+
+ for (int i = 0; i < name.size(); i++) {
+ if (name[i] == '_') {
+ next_upper = true;
+ } else {
+ if (next_upper) {
+ result.push_back(ToUpper(name[i]));
+ } else {
+ result.push_back(name[i]);
+ }
+ next_upper = false;
+ }
+ }
+
+ return result;
+}
+
+// Class and enum names in protobuf should be PascalCased by convention, but
+// since there is nothing enforcing this we need to ensure that they are valid
+// Ruby constants. That mainly means making sure that the first character is
+// an upper-case letter.
+std::string RubifyConstant(const std::string& name) {
+ std::string ret = name;
+ if (!ret.empty()) {
+ if (IsLower(ret[0])) {
+ // If it starts with a lowercase letter, capitalize it.
+ ret[0] = ToUpper(ret[0]);
+ } else if (!IsAlpha(ret[0])) {
+ // Otherwise (e.g. if it begins with an underscore), we need to come up
+ // with some prefix that starts with a capital letter. We could be smarter
+ // here, e.g. try to strip leading underscores, but this may cause other
+ // problems if the user really intended the name. So let's just prepend a
+ // well-known suffix.
+ ret = "PB_" + ret;
+ }
+ }
+
+ return ret;
+}
+
+void GenerateMessageAssignment(
+ const std::string& prefix,
+ const google::protobuf::Descriptor* message,
+ google::protobuf::io::Printer* printer) {
+
+ // Don't generate MapEntry messages -- we use the Ruby extension's native
+ // support for map fields instead.
+ if (message->options().map_entry()) {
+ return;
+ }
+
+ printer->Print(
+ "$prefix$$name$ = ",
+ "prefix", prefix,
+ "name", RubifyConstant(message->name()));
+ printer->Print(
+ "Google::Protobuf::DescriptorPool.generated_pool."
+ "lookup(\"$full_name$\").msgclass\n",
+ "full_name", message->full_name());
+
+ std::string nested_prefix = prefix + message->name() + "::";
+ for (int i = 0; i < message->nested_type_count(); i++) {
+ GenerateMessageAssignment(nested_prefix, message->nested_type(i), printer);
+ }
+ for (int i = 0; i < message->enum_type_count(); i++) {
+ GenerateEnumAssignment(nested_prefix, message->enum_type(i), printer);
+ }
+}
+
+void GenerateEnumAssignment(
+ const std::string& prefix,
+ const google::protobuf::EnumDescriptor* en,
+ google::protobuf::io::Printer* printer) {
+ printer->Print(
+ "$prefix$$name$ = ",
+ "prefix", prefix,
+ "name", RubifyConstant(en->name()));
+ printer->Print(
+ "Google::Protobuf::DescriptorPool.generated_pool."
+ "lookup(\"$full_name$\").enummodule\n",
+ "full_name", en->full_name());
+}
+
+int GeneratePackageModules(
+ std::string package_name,
+ google::protobuf::io::Printer* printer) {
+ int levels = 0;
+ while (!package_name.empty()) {
+ size_t dot_index = package_name.find(".");
+ string component;
+ if (dot_index == string::npos) {
+ component = package_name;
+ package_name = "";
+ } else {
+ component = package_name.substr(0, dot_index);
+ package_name = package_name.substr(dot_index + 1);
+ }
+ component = PackageToModule(component);
+ printer->Print(
+ "module $name$\n",
+ "name", component);
+ printer->Indent();
+ levels++;
+ }
+ return levels;
+}
+
+void EndPackageModules(
+ int levels,
+ google::protobuf::io::Printer* printer) {
+ while (levels > 0) {
+ levels--;
+ printer->Outdent();
+ printer->Print(
+ "end\n");
+ }
+}
+
+bool UsesTypeFromFile(const Descriptor* message, const FileDescriptor* file,
+ string* error) {
+ for (int i = 0; i < message->field_count(); i++) {
+ const FieldDescriptor* field = message->field(i);
+ if ((field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ field->message_type()->file() == file) ||
+ (field->type() == FieldDescriptor::TYPE_ENUM &&
+ field->enum_type()->file() == file)) {
+ *error = "proto3 message field " + field->full_name() + " in file " +
+ file->name() + " has a dependency on a type from proto2 file " +
+ file->name() +
+ ". Ruby doesn't support proto2 yet, so we must fail.";
+ return true;
+ }
+ }
+
+ for (int i = 0; i < message->nested_type_count(); i++) {
+ if (UsesTypeFromFile(message->nested_type(i), file, error)) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+// Ruby doesn't currently support proto2. This causes a failure even for proto3
+// files that import proto2. But in some cases, the proto2 file is only being
+// imported to extend another proto2 message. The prime example is declaring
+// custom options by extending FileOptions/FieldOptions/etc.
+//
+// If the proto3 messages don't have any proto2 submessages, it is safe to omit
+// the dependency completely. Users won't be able to use any proto2 extensions,
+// but they already couldn't because proto2 messages aren't supported.
+//
+// If/when we add proto2 support, we should remove this.
+bool MaybeEmitDependency(const FileDescriptor* import,
+ const FileDescriptor* from,
+ io::Printer* printer,
+ string* error) {
+ if (import->syntax() == FileDescriptor::SYNTAX_PROTO2) {
+ for (int i = 0; i < from->message_type_count(); i++) {
+ if (UsesTypeFromFile(from->message_type(i), import, error)) {
+ // Error text was already set by UsesTypeFromFile().
+ return false;
+ }
+ }
+
+ // Ok to omit this proto2 dependency -- so we won't print anything.
+ GOOGLE_LOG(WARNING) << "Omitting proto2 dependency '" << import->name()
+ << "' from proto3 output file '"
+ << GetOutputFilename(from->name())
+ << "' because we don't support proto2 and no proto2 "
+ "types from that file are being used.";
+ return true;
+ } else {
+ printer->Print(
+ "require '$name$'\n", "name", GetRequireName(import->name()));
+ return true;
+ }
+}
+
+bool GenerateFile(const FileDescriptor* file, io::Printer* printer,
+ string* error) {
+ printer->Print(
+ "# Generated by the protocol buffer compiler. DO NOT EDIT!\n"
+ "# source: $filename$\n"
+ "\n",
+ "filename", file->name());
+
+ printer->Print(
+ "require 'google/protobuf'\n\n");
+
+ for (int i = 0; i < file->dependency_count(); i++) {
+ if (!MaybeEmitDependency(file->dependency(i), file, printer, error)) {
+ return false;
+ }
+ }
+
+ printer->Print(
+ "Google::Protobuf::DescriptorPool.generated_pool.build do\n");
+ printer->Indent();
+ for (int i = 0; i < file->message_type_count(); i++) {
+ GenerateMessage(file->message_type(i), printer);
+ }
+ for (int i = 0; i < file->enum_type_count(); i++) {
+ GenerateEnum(file->enum_type(i), printer);
+ }
+ printer->Outdent();
+ printer->Print(
+ "end\n\n");
+
+ int levels = GeneratePackageModules(file->package(), printer);
+ for (int i = 0; i < file->message_type_count(); i++) {
+ GenerateMessageAssignment("", file->message_type(i), printer);
+ }
+ for (int i = 0; i < file->enum_type_count(); i++) {
+ GenerateEnumAssignment("", file->enum_type(i), printer);
+ }
+ EndPackageModules(levels, printer);
+ return true;
+}
+
+bool Generator::Generate(
+ const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const {
+
+ if (file->syntax() != FileDescriptor::SYNTAX_PROTO3) {
+ *error =
+ "Can only generate Ruby code for proto3 .proto files.\n"
+ "Please add 'syntax = \"proto3\";' to the top of your .proto file.\n";
+ return false;
+ }
+
+ scoped_ptr<io::ZeroCopyOutputStream> output(
+ generator_context->Open(GetOutputFilename(file->name())));
+ io::Printer printer(output.get(), '$');
+
+ return GenerateFile(file, &printer, error);
+}
+
+} // namespace ruby
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.h
new file mode 100644
index 0000000000..75555c31b5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator.h
@@ -0,0 +1,58 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_RUBY_GENERATOR_H__
+#define GOOGLE_PROTOBUF_COMPILER_RUBY_GENERATOR_H__
+
+#include <string>
+
+#include <google/protobuf/compiler/code_generator.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace ruby {
+
+class LIBPROTOC_EXPORT Generator
+ : public google::protobuf::compiler::CodeGenerator {
+ virtual bool Generate(
+ const FileDescriptor* file,
+ const string& parameter,
+ GeneratorContext* generator_context,
+ string* error) const;
+};
+
+} // namespace ruby
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMPILER_RUBY_GENERATOR_H__
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator_unittest.cc
new file mode 100644
index 0000000000..1aabe8aa98
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/ruby/ruby_generator_unittest.cc
@@ -0,0 +1,109 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+
+#include <memory>
+
+#include <google/protobuf/compiler/ruby/ruby_generator.h>
+#include <google/protobuf/compiler/command_line_interface.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/printer.h>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/testing/file.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+namespace ruby {
+namespace {
+
+string FindRubyTestDir() {
+ return TestSourceDir() + "/google/protobuf/compiler/ruby";
+}
+
+// This test is a simple golden-file test over the output of the Ruby code
+// generator. When we make changes to the Ruby extension and alter the Ruby code
+// generator to use those changes, we should (i) manually test the output of the
+// code generator with the extension, and (ii) update the golden output above.
+// Some day, we may integrate build systems between protoc and the language
+// extensions to the point where we can do this test in a more automated way.
+
+TEST(RubyGeneratorTest, GeneratorTest) {
+ string ruby_tests = FindRubyTestDir();
+
+ google::protobuf::compiler::CommandLineInterface cli;
+ cli.SetInputsAreProtoPathRelative(true);
+
+ ruby::Generator ruby_generator;
+ cli.RegisterGenerator("--ruby_out", &ruby_generator, "");
+
+ // Copy generated_code.proto to the temporary test directory.
+ string test_input;
+ GOOGLE_CHECK_OK(File::GetContents(
+ ruby_tests + "/ruby_generated_code.proto",
+ &test_input,
+ true));
+ GOOGLE_CHECK_OK(File::SetContents(
+ TestTempDir() + "/ruby_generated_code.proto",
+ test_input,
+ true));
+
+ // Invoke the proto compiler (we will be inside TestTempDir() at this point).
+ string ruby_out = "--ruby_out=" + TestTempDir();
+ string proto_path = "--proto_path=" + TestTempDir();
+ const char* argv[] = {
+ "protoc",
+ ruby_out.c_str(),
+ proto_path.c_str(),
+ "ruby_generated_code.proto",
+ };
+
+ EXPECT_EQ(0, cli.Run(4, argv));
+
+ // Load the generated output and compare to the expected result.
+ string output;
+ GOOGLE_CHECK_OK(File::GetContents(
+ TestTempDir() + "/ruby_generated_code_pb.rb",
+ &output,
+ true));
+ string expected_output;
+ GOOGLE_CHECK_OK(File::GetContents(
+ ruby_tests + "/ruby_generated_code_pb.rb",
+ &expected_output,
+ true));
+ EXPECT_EQ(expected_output, output);
+}
+
+} // namespace
+} // namespace ruby
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.cc
new file mode 100644
index 0000000000..6e25866412
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.cc
@@ -0,0 +1,465 @@
+// 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)
+
+#include <google/protobuf/compiler/subprocess.h>
+
+#include <algorithm>
+#include <iostream>
+
+#ifndef _WIN32
+#include <errno.h>
+#include <sys/select.h>
+#include <sys/wait.h>
+#include <signal.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/stubs/substitute.h>
+
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+#ifdef _WIN32
+
+static void CloseHandleOrDie(HANDLE handle) {
+ if (!CloseHandle(handle)) {
+ GOOGLE_LOG(FATAL) << "CloseHandle: "
+ << Subprocess::Win32ErrorMessage(GetLastError());
+ }
+}
+
+Subprocess::Subprocess()
+ : process_start_error_(ERROR_SUCCESS),
+ child_handle_(NULL), child_stdin_(NULL), child_stdout_(NULL) {}
+
+Subprocess::~Subprocess() {
+ if (child_stdin_ != NULL) {
+ CloseHandleOrDie(child_stdin_);
+ }
+ if (child_stdout_ != NULL) {
+ CloseHandleOrDie(child_stdout_);
+ }
+}
+
+void Subprocess::Start(const string& program, SearchMode search_mode) {
+ // Create the pipes.
+ HANDLE stdin_pipe_read;
+ HANDLE stdin_pipe_write;
+ HANDLE stdout_pipe_read;
+ HANDLE stdout_pipe_write;
+
+ if (!CreatePipe(&stdin_pipe_read, &stdin_pipe_write, NULL, 0)) {
+ GOOGLE_LOG(FATAL) << "CreatePipe: " << Win32ErrorMessage(GetLastError());
+ }
+ if (!CreatePipe(&stdout_pipe_read, &stdout_pipe_write, NULL, 0)) {
+ GOOGLE_LOG(FATAL) << "CreatePipe: " << Win32ErrorMessage(GetLastError());
+ }
+
+ // Make child side of the pipes inheritable.
+ if (!SetHandleInformation(stdin_pipe_read,
+ HANDLE_FLAG_INHERIT, HANDLE_FLAG_INHERIT)) {
+ GOOGLE_LOG(FATAL) << "SetHandleInformation: "
+ << Win32ErrorMessage(GetLastError());
+ }
+ if (!SetHandleInformation(stdout_pipe_write,
+ HANDLE_FLAG_INHERIT, HANDLE_FLAG_INHERIT)) {
+ GOOGLE_LOG(FATAL) << "SetHandleInformation: "
+ << Win32ErrorMessage(GetLastError());
+ }
+
+ // Setup STARTUPINFO to redirect handles.
+ STARTUPINFOA startup_info;
+ ZeroMemory(&startup_info, sizeof(startup_info));
+ startup_info.cb = sizeof(startup_info);
+ startup_info.dwFlags = STARTF_USESTDHANDLES;
+ startup_info.hStdInput = stdin_pipe_read;
+ startup_info.hStdOutput = stdout_pipe_write;
+ startup_info.hStdError = GetStdHandle(STD_ERROR_HANDLE);
+
+ if (startup_info.hStdError == INVALID_HANDLE_VALUE) {
+ GOOGLE_LOG(FATAL) << "GetStdHandle: "
+ << Win32ErrorMessage(GetLastError());
+ }
+
+ // CreateProcess() mutates its second parameter. WTF?
+ char* name_copy = strdup(program.c_str());
+
+ // Create the process.
+ PROCESS_INFORMATION process_info;
+
+ if (CreateProcessA((search_mode == SEARCH_PATH) ? NULL : program.c_str(),
+ (search_mode == SEARCH_PATH) ? name_copy : NULL,
+ NULL, // process security attributes
+ NULL, // thread security attributes
+ TRUE, // inherit handles?
+ 0, // obscure creation flags
+ NULL, // environment (inherit from parent)
+ NULL, // current directory (inherit from parent)
+ &startup_info,
+ &process_info)) {
+ child_handle_ = process_info.hProcess;
+ CloseHandleOrDie(process_info.hThread);
+ child_stdin_ = stdin_pipe_write;
+ child_stdout_ = stdout_pipe_read;
+ } else {
+ process_start_error_ = GetLastError();
+ CloseHandleOrDie(stdin_pipe_write);
+ CloseHandleOrDie(stdout_pipe_read);
+ }
+
+ CloseHandleOrDie(stdin_pipe_read);
+ CloseHandleOrDie(stdout_pipe_write);
+ free(name_copy);
+}
+
+bool Subprocess::Communicate(const Message& input, Message* output,
+ string* error) {
+ if (process_start_error_ != ERROR_SUCCESS) {
+ *error = Win32ErrorMessage(process_start_error_);
+ return false;
+ }
+
+ GOOGLE_CHECK(child_handle_ != NULL) << "Must call Start() first.";
+
+ string input_data = input.SerializeAsString();
+ string output_data;
+
+ int input_pos = 0;
+
+ while (child_stdout_ != NULL) {
+ HANDLE handles[2];
+ int handle_count = 0;
+
+ if (child_stdin_ != NULL) {
+ handles[handle_count++] = child_stdin_;
+ }
+ if (child_stdout_ != NULL) {
+ handles[handle_count++] = child_stdout_;
+ }
+
+ DWORD wait_result =
+ WaitForMultipleObjects(handle_count, handles, FALSE, INFINITE);
+
+ HANDLE signaled_handle = NULL;
+ if (wait_result >= WAIT_OBJECT_0 &&
+ wait_result < WAIT_OBJECT_0 + handle_count) {
+ signaled_handle = handles[wait_result - WAIT_OBJECT_0];
+ } else if (wait_result == WAIT_FAILED) {
+ GOOGLE_LOG(FATAL) << "WaitForMultipleObjects: "
+ << Win32ErrorMessage(GetLastError());
+ } else {
+ GOOGLE_LOG(FATAL) << "WaitForMultipleObjects: Unexpected return code: "
+ << wait_result;
+ }
+
+ if (signaled_handle == child_stdin_) {
+ DWORD n;
+ if (!WriteFile(child_stdin_,
+ input_data.data() + input_pos,
+ input_data.size() - input_pos,
+ &n, NULL)) {
+ // Child closed pipe. Presumably it will report an error later.
+ // Pretend we're done for now.
+ input_pos = input_data.size();
+ } else {
+ input_pos += n;
+ }
+
+ if (input_pos == input_data.size()) {
+ // We're done writing. Close.
+ CloseHandleOrDie(child_stdin_);
+ child_stdin_ = NULL;
+ }
+ } else if (signaled_handle == child_stdout_) {
+ char buffer[4096];
+ DWORD n;
+
+ if (!ReadFile(child_stdout_, buffer, sizeof(buffer), &n, NULL)) {
+ // We're done reading. Close.
+ CloseHandleOrDie(child_stdout_);
+ child_stdout_ = NULL;
+ } else {
+ output_data.append(buffer, n);
+ }
+ }
+ }
+
+ if (child_stdin_ != NULL) {
+ // Child did not finish reading input before it closed the output.
+ // Presumably it exited with an error.
+ CloseHandleOrDie(child_stdin_);
+ child_stdin_ = NULL;
+ }
+
+ DWORD wait_result = WaitForSingleObject(child_handle_, INFINITE);
+
+ if (wait_result == WAIT_FAILED) {
+ GOOGLE_LOG(FATAL) << "WaitForSingleObject: "
+ << Win32ErrorMessage(GetLastError());
+ } else if (wait_result != WAIT_OBJECT_0) {
+ GOOGLE_LOG(FATAL) << "WaitForSingleObject: Unexpected return code: "
+ << wait_result;
+ }
+
+ DWORD exit_code;
+ if (!GetExitCodeProcess(child_handle_, &exit_code)) {
+ GOOGLE_LOG(FATAL) << "GetExitCodeProcess: "
+ << Win32ErrorMessage(GetLastError());
+ }
+
+ CloseHandleOrDie(child_handle_);
+ child_handle_ = NULL;
+
+ if (exit_code != 0) {
+ *error = strings::Substitute(
+ "Plugin failed with status code $0.", exit_code);
+ return false;
+ }
+
+ if (!output->ParseFromString(output_data)) {
+ *error = "Plugin output is unparseable: " + CEscape(output_data);
+ return false;
+ }
+
+ return true;
+}
+
+string Subprocess::Win32ErrorMessage(DWORD error_code) {
+ char* message;
+
+ // WTF?
+ FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER |
+ FORMAT_MESSAGE_FROM_SYSTEM |
+ FORMAT_MESSAGE_IGNORE_INSERTS,
+ NULL, error_code, 0,
+ (LPTSTR)&message, // NOT A BUG!
+ 0, NULL);
+
+ string result = message;
+ LocalFree(message);
+ return result;
+}
+
+// ===================================================================
+
+#else // _WIN32
+
+Subprocess::Subprocess()
+ : child_pid_(-1), child_stdin_(-1), child_stdout_(-1) {}
+
+Subprocess::~Subprocess() {
+ if (child_stdin_ != -1) {
+ close(child_stdin_);
+ }
+ if (child_stdout_ != -1) {
+ close(child_stdout_);
+ }
+}
+
+void Subprocess::Start(const string& program, SearchMode search_mode) {
+ // Note that we assume that there are no other threads, thus we don't have to
+ // do crazy stuff like using socket pairs or avoiding libc locks.
+
+ // [0] is read end, [1] is write end.
+ int stdin_pipe[2];
+ int stdout_pipe[2];
+
+ GOOGLE_CHECK(pipe(stdin_pipe) != -1);
+ GOOGLE_CHECK(pipe(stdout_pipe) != -1);
+
+ char* argv[2] = { strdup(program.c_str()), NULL };
+
+ child_pid_ = fork();
+ if (child_pid_ == -1) {
+ GOOGLE_LOG(FATAL) << "fork: " << strerror(errno);
+ } else if (child_pid_ == 0) {
+ // We are the child.
+ dup2(stdin_pipe[0], STDIN_FILENO);
+ dup2(stdout_pipe[1], STDOUT_FILENO);
+
+ close(stdin_pipe[0]);
+ close(stdin_pipe[1]);
+ close(stdout_pipe[0]);
+ close(stdout_pipe[1]);
+
+ switch (search_mode) {
+ case SEARCH_PATH:
+ execvp(argv[0], argv);
+ break;
+ case EXACT_NAME:
+ execv(argv[0], argv);
+ break;
+ }
+
+ // Write directly to STDERR_FILENO to avoid stdio code paths that may do
+ // stuff that is unsafe here.
+ int ignored;
+ ignored = write(STDERR_FILENO, argv[0], strlen(argv[0]));
+ const char* message = ": program not found or is not executable\n";
+ ignored = write(STDERR_FILENO, message, strlen(message));
+ (void) ignored;
+
+ // Must use _exit() rather than exit() to avoid flushing output buffers
+ // that will also be flushed by the parent.
+ _exit(1);
+ } else {
+ free(argv[0]);
+
+ close(stdin_pipe[0]);
+ close(stdout_pipe[1]);
+
+ child_stdin_ = stdin_pipe[1];
+ child_stdout_ = stdout_pipe[0];
+ }
+}
+
+bool Subprocess::Communicate(const Message& input, Message* output,
+ string* error) {
+
+ GOOGLE_CHECK_NE(child_stdin_, -1) << "Must call Start() first.";
+
+ // The "sighandler_t" typedef is GNU-specific, so define our own.
+ typedef void SignalHandler(int);
+
+ // Make sure SIGPIPE is disabled so that if the child dies it doesn't kill us.
+ SignalHandler* old_pipe_handler = signal(SIGPIPE, SIG_IGN);
+
+ string input_data = input.SerializeAsString();
+ string output_data;
+
+ int input_pos = 0;
+ int max_fd = std::max(child_stdin_, child_stdout_);
+
+ while (child_stdout_ != -1) {
+ fd_set read_fds;
+ fd_set write_fds;
+ FD_ZERO(&read_fds);
+ FD_ZERO(&write_fds);
+ if (child_stdout_ != -1) {
+ FD_SET(child_stdout_, &read_fds);
+ }
+ if (child_stdin_ != -1) {
+ FD_SET(child_stdin_, &write_fds);
+ }
+
+ if (select(max_fd + 1, &read_fds, &write_fds, NULL, NULL) < 0) {
+ if (errno == EINTR) {
+ // Interrupted by signal. Try again.
+ continue;
+ } else {
+ GOOGLE_LOG(FATAL) << "select: " << strerror(errno);
+ }
+ }
+
+ if (child_stdin_ != -1 && FD_ISSET(child_stdin_, &write_fds)) {
+ int n = write(child_stdin_, input_data.data() + input_pos,
+ input_data.size() - input_pos);
+ if (n < 0) {
+ // Child closed pipe. Presumably it will report an error later.
+ // Pretend we're done for now.
+ input_pos = input_data.size();
+ } else {
+ input_pos += n;
+ }
+
+ if (input_pos == input_data.size()) {
+ // We're done writing. Close.
+ close(child_stdin_);
+ child_stdin_ = -1;
+ }
+ }
+
+ if (child_stdout_ != -1 && FD_ISSET(child_stdout_, &read_fds)) {
+ char buffer[4096];
+ int n = read(child_stdout_, buffer, sizeof(buffer));
+
+ if (n > 0) {
+ output_data.append(buffer, n);
+ } else {
+ // We're done reading. Close.
+ close(child_stdout_);
+ child_stdout_ = -1;
+ }
+ }
+ }
+
+ if (child_stdin_ != -1) {
+ // Child did not finish reading input before it closed the output.
+ // Presumably it exited with an error.
+ close(child_stdin_);
+ child_stdin_ = -1;
+ }
+
+ int status;
+ while (waitpid(child_pid_, &status, 0) == -1) {
+ if (errno != EINTR) {
+ GOOGLE_LOG(FATAL) << "waitpid: " << strerror(errno);
+ }
+ }
+
+ // Restore SIGPIPE handling.
+ signal(SIGPIPE, old_pipe_handler);
+
+ if (WIFEXITED(status)) {
+ if (WEXITSTATUS(status) != 0) {
+ int error_code = WEXITSTATUS(status);
+ *error = strings::Substitute(
+ "Plugin failed with status code $0.", error_code);
+ return false;
+ }
+ } else if (WIFSIGNALED(status)) {
+ int signal = WTERMSIG(status);
+ *error = strings::Substitute(
+ "Plugin killed by signal $0.", signal);
+ return false;
+ } else {
+ *error = "Neither WEXITSTATUS nor WTERMSIG is true?";
+ return false;
+ }
+
+ if (!output->ParseFromString(output_data)) {
+ *error = "Plugin output is unparseable: " + CEscape(output_data);
+ return false;
+ }
+
+ return true;
+}
+
+#endif // !_WIN32
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.h
new file mode 100644
index 0000000000..2513863144
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/subprocess.h
@@ -0,0 +1,108 @@
+// 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)
+
+#ifndef GOOGLE_PROTOBUF_COMPILER_SUBPROCESS_H__
+#define GOOGLE_PROTOBUF_COMPILER_SUBPROCESS_H__
+
+#ifdef _WIN32
+#define WIN32_LEAN_AND_MEAN // right...
+#include <windows.h>
+#else // _WIN32
+#include <sys/types.h>
+#include <unistd.h>
+#endif // !_WIN32
+#include <google/protobuf/stubs/common.h>
+
+#include <string>
+
+
+namespace google {
+namespace protobuf {
+
+class Message;
+
+namespace compiler {
+
+// Utility class for launching sub-processes.
+class LIBPROTOC_EXPORT Subprocess {
+ public:
+ Subprocess();
+ ~Subprocess();
+
+ enum SearchMode {
+ SEARCH_PATH, // Use PATH environment variable.
+ EXACT_NAME // Program is an exact file name; don't use the PATH.
+ };
+
+ // Start the subprocess. Currently we don't provide a way to specify
+ // arguments as protoc plugins don't have any.
+ void Start(const string& program, SearchMode search_mode);
+
+ // Serialize the input message and pipe it to the subprocess's stdin, then
+ // close the pipe. Meanwhile, read from the subprocess's stdout and parse
+ // the data into *output. All this is done carefully to avoid deadlocks.
+ // Returns true if successful. On any sort of error, returns false and sets
+ // *error to a description of the problem.
+ bool Communicate(const Message& input, Message* output, string* error);
+
+#ifdef _WIN32
+ // Given an error code, returns a human-readable error message. This is
+ // defined here so that CommandLineInterface can share it.
+ static string Win32ErrorMessage(DWORD error_code);
+#endif
+
+ private:
+#ifdef _WIN32
+ DWORD process_start_error_;
+ HANDLE child_handle_;
+
+ // The file handles for our end of the child's pipes. We close each and
+ // set it to NULL when no longer needed.
+ HANDLE child_stdin_;
+ HANDLE child_stdout_;
+
+#else // _WIN32
+ pid_t child_pid_;
+
+ // The file descriptors for our end of the child's pipes. We close each and
+ // set it to -1 when no longer needed.
+ int child_stdin_;
+ int child_stdout_;
+
+#endif // !_WIN32
+};
+
+} // namespace compiler
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_COMPILER_SUBPROCESS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/test_plugin.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/test_plugin.cc
new file mode 100644
index 0000000000..4830fd70a0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/test_plugin.cc
@@ -0,0 +1,51 @@
+// 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)
+//
+// This is a dummy code generator plugin used by
+// command_line_interface_unittest.
+
+#include <string>
+#include <stdlib.h>
+#include <google/protobuf/compiler/plugin.h>
+#include <google/protobuf/compiler/mock_code_generator.h>
+#include <google/protobuf/stubs/strutil.h>
+
+int main(int argc, char* argv[]) {
+#ifdef _MSC_VER
+ // Don't print a silly message or stick a modal dialog box in my face,
+ // please.
+ _set_abort_behavior(0, ~0);
+#endif // !_MSC_VER
+
+ google::protobuf::compiler::MockCodeGenerator generator("test_plugin");
+ return google::protobuf::compiler::PluginMain(argc, argv, &generator);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_output_unittest.sh b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_output_unittest.sh
new file mode 100755
index 0000000000..6fc7136dfa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_output_unittest.sh
@@ -0,0 +1,91 @@
+#!/bin/sh
+#
+# Protocol Buffers - Google's data interchange format
+# Copyright 2009 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)
+#
+# Test protoc's zip output mode.
+
+fail() {
+ echo "$@" >&2
+ exit 1
+}
+
+TEST_TMPDIR=.
+PROTOC=./protoc
+
+echo '
+ syntax = "proto2";
+ option java_multiple_files = true;
+ option java_package = "test.jar";
+ option java_outer_classname = "Outer";
+ message Foo {}
+ message Bar {}
+' > $TEST_TMPDIR/testzip.proto
+
+$PROTOC \
+ --cpp_out=$TEST_TMPDIR/testzip.zip --python_out=$TEST_TMPDIR/testzip.zip \
+ --java_out=$TEST_TMPDIR/testzip.jar -I$TEST_TMPDIR testzip.proto \
+ || fail 'protoc failed.'
+
+echo "Testing output to zip..."
+if unzip -h > /dev/null; then
+ unzip -t $TEST_TMPDIR/testzip.zip > $TEST_TMPDIR/testzip.list || fail 'unzip failed.'
+
+ grep 'testing: testzip\.pb\.cc *OK$' $TEST_TMPDIR/testzip.list > /dev/null \
+ || fail 'testzip.pb.cc not found in output zip.'
+ grep 'testing: testzip\.pb\.h *OK$' $TEST_TMPDIR/testzip.list > /dev/null \
+ || fail 'testzip.pb.h not found in output zip.'
+ grep 'testing: testzip_pb2\.py *OK$' $TEST_TMPDIR/testzip.list > /dev/null \
+ || fail 'testzip_pb2.py not found in output zip.'
+ grep -i 'manifest' $TEST_TMPDIR/testzip.list > /dev/null \
+ && fail 'Zip file contained manifest.'
+else
+ echo "Warning: 'unzip' command not available. Skipping test."
+fi
+
+echo "Testing output to jar..."
+if jar c $TEST_TMPDIR/testzip.proto > /dev/null; then
+ jar tf $TEST_TMPDIR/testzip.jar > $TEST_TMPDIR/testzip.list || fail 'jar failed.'
+
+ grep '^test/jar/Foo\.java$' $TEST_TMPDIR/testzip.list > /dev/null \
+ || fail 'Foo.java not found in output jar.'
+ grep '^test/jar/Bar\.java$' $TEST_TMPDIR/testzip.list > /dev/null \
+ || fail 'Bar.java not found in output jar.'
+ grep '^test/jar/Outer\.java$' $TEST_TMPDIR/testzip.list > /dev/null \
+ || fail 'Outer.java not found in output jar.'
+ grep '^META-INF/MANIFEST\.MF$' $TEST_TMPDIR/testzip.list > /dev/null \
+ || fail 'Manifest not found in output jar.'
+else
+ echo "Warning: 'jar' command not available. Skipping test."
+fi
+
+echo PASS
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.cc b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.cc
new file mode 100644
index 0000000000..458cced29d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.cc
@@ -0,0 +1,218 @@
+// 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.
+
+// 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: ambrose@google.com (Ambrose Feinstein),
+// kenton@google.com (Kenton Varda)
+//
+// Based on http://www.pkware.com/documents/casestudies/APPNOTE.TXT
+
+#include <google/protobuf/compiler/zip_writer.h>
+#include <google/protobuf/io/coded_stream.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+static const uint32 kCRC32Table[256] = {
+ 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, 0x706af48f,
+ 0xe963a535, 0x9e6495a3, 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988,
+ 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91, 0x1db71064, 0x6ab020f2,
+ 0xf3b97148, 0x84be41de, 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7,
+ 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9,
+ 0xfa0f3d63, 0x8d080df5, 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172,
+ 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b, 0x35b5a8fa, 0x42b2986c,
+ 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59,
+ 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423,
+ 0xcfba9599, 0xb8bda50f, 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924,
+ 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, 0x76dc4190, 0x01db7106,
+ 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433,
+ 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818, 0x7f6a0dbb, 0x086d3d2d,
+ 0x91646c97, 0xe6635c01, 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e,
+ 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457, 0x65b0d9c6, 0x12b7e950,
+ 0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65,
+ 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, 0x4adfa541, 0x3dd895d7,
+ 0xa4d1c46d, 0xd3d6f4fb, 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0,
+ 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9, 0x5005713c, 0x270241aa,
+ 0xbe0b1010, 0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
+ 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17, 0x2eb40d81,
+ 0xb7bd5c3b, 0xc0ba6cad, 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a,
+ 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683, 0xe3630b12, 0x94643b84,
+ 0x0d6d6a3e, 0x7a6a5aa8, 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1,
+ 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb,
+ 0x196c3671, 0x6e6b06e7, 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc,
+ 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5, 0xd6d6a3e8, 0xa1d1937e,
+ 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b,
+ 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55,
+ 0x316e8eef, 0x4669be79, 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236,
+ 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, 0xc5ba3bbe, 0xb2bd0b28,
+ 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d,
+ 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a, 0x9c0906a9, 0xeb0e363f,
+ 0x72076785, 0x05005713, 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38,
+ 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, 0x86d3d2d4, 0xf1d4e242,
+ 0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777,
+ 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, 0x8f659eff, 0xf862ae69,
+ 0x616bffd3, 0x166ccf45, 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2,
+ 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db, 0xaed16a4a, 0xd9d65adc,
+ 0x40df0b66, 0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
+ 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605, 0xcdd70693,
+ 0x54de5729, 0x23d967bf, 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94,
+ 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d
+};
+
+static uint32 ComputeCRC32(const string &buf) {
+ uint32 x = ~0U;
+ for (int i = 0; i < buf.size(); ++i) {
+ unsigned char c = buf[i];
+ x = kCRC32Table[(x ^ c) & 0xff] ^ (x >> 8);
+ }
+ return ~x;
+}
+
+static void WriteShort(io::CodedOutputStream *out, uint16 val) {
+ uint8 p[2];
+ p[0] = static_cast<uint8>(val);
+ p[1] = static_cast<uint8>(val >> 8);
+ out->WriteRaw(p, 2);
+}
+
+ZipWriter::ZipWriter(io::ZeroCopyOutputStream* raw_output)
+ : raw_output_(raw_output) {}
+ZipWriter::~ZipWriter() {}
+
+bool ZipWriter::Write(const string& filename, const string& contents) {
+ FileInfo info;
+
+ info.name = filename;
+ uint16 filename_size = filename.size();
+ info.offset = raw_output_->ByteCount();
+ info.size = contents.size();
+ info.crc32 = ComputeCRC32(contents);
+
+ files_.push_back(info);
+
+ // write file header
+ io::CodedOutputStream output(raw_output_);
+ output.WriteLittleEndian32(0x04034b50); // magic
+ WriteShort(&output, 10); // version needed to extract
+ WriteShort(&output, 0); // flags
+ WriteShort(&output, 0); // compression method: stored
+ WriteShort(&output, 0); // last modified time
+ WriteShort(&output, 0); // last modified date
+ output.WriteLittleEndian32(info.crc32); // crc-32
+ output.WriteLittleEndian32(info.size); // compressed size
+ output.WriteLittleEndian32(info.size); // uncompressed size
+ WriteShort(&output, filename_size); // file name length
+ WriteShort(&output, 0); // extra field length
+ output.WriteString(filename); // file name
+ output.WriteString(contents); // file data
+
+ return !output.HadError();
+}
+
+bool ZipWriter::WriteDirectory() {
+ uint16 num_entries = files_.size();
+ uint32 dir_ofs = raw_output_->ByteCount();
+
+ // write central directory
+ io::CodedOutputStream output(raw_output_);
+ for (int i = 0; i < num_entries; ++i) {
+ const string &filename = files_[i].name;
+ uint16 filename_size = filename.size();
+ uint32 crc32 = files_[i].crc32;
+ uint32 size = files_[i].size;
+ uint32 offset = files_[i].offset;
+
+ output.WriteLittleEndian32(0x02014b50); // magic
+ WriteShort(&output, 10); // version made by
+ WriteShort(&output, 10); // version needed to extract
+ WriteShort(&output, 0); // flags
+ WriteShort(&output, 0); // compression method: stored
+ WriteShort(&output, 0); // last modified time
+ WriteShort(&output, 0); // last modified date
+ output.WriteLittleEndian32(crc32); // crc-32
+ output.WriteLittleEndian32(size); // compressed size
+ output.WriteLittleEndian32(size); // uncompressed size
+ WriteShort(&output, filename_size); // file name length
+ WriteShort(&output, 0); // extra field length
+ WriteShort(&output, 0); // file comment length
+ WriteShort(&output, 0); // starting disk number
+ WriteShort(&output, 0); // internal file attributes
+ output.WriteLittleEndian32(0); // external file attributes
+ output.WriteLittleEndian32(offset); // local header offset
+ output.WriteString(filename); // file name
+ }
+ uint32 dir_len = output.ByteCount();
+
+ // write end of central directory marker
+ output.WriteLittleEndian32(0x06054b50); // magic
+ WriteShort(&output, 0); // disk number
+ WriteShort(&output, 0); // disk with start of central directory
+ WriteShort(&output, num_entries); // central directory entries (this disk)
+ WriteShort(&output, num_entries); // central directory entries (total)
+ output.WriteLittleEndian32(dir_len); // central directory byte size
+ output.WriteLittleEndian32(dir_ofs); // central directory offset
+ WriteShort(&output, 0); // comment length
+
+ return output.HadError();
+}
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.h b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.h
new file mode 100644
index 0000000000..602e508e2d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/compiler/zip_writer.h
@@ -0,0 +1,93 @@
+// 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.
+
+// 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)
+
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+
+namespace google {
+namespace protobuf {
+namespace compiler {
+
+class ZipWriter {
+ public:
+ ZipWriter(io::ZeroCopyOutputStream* raw_output);
+ ~ZipWriter();
+
+ bool Write(const string& filename, const string& contents);
+ bool WriteDirectory();
+
+ private:
+ struct FileInfo {
+ string name;
+ uint32 offset;
+ uint32 size;
+ uint32 crc32;
+ };
+
+ io::ZeroCopyOutputStream* raw_output_;
+ vector<FileInfo> files_;
+};
+
+} // namespace compiler
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.cc b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.cc
new file mode 100644
index 0000000000..9b20946c7f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.cc
@@ -0,0 +1,6295 @@
+// 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.
+
+#include <google/protobuf/stubs/hash.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <set>
+#include <string>
+#include <vector>
+#include <algorithm>
+#include <limits>
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor_database.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/io/strtod.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/mutex.h>
+#include <google/protobuf/stubs/once.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+#undef PACKAGE // autoheader #defines this. :(
+
+namespace google {
+namespace protobuf {
+
+const FieldDescriptor::CppType
+FieldDescriptor::kTypeToCppTypeMap[MAX_TYPE + 1] = {
+ static_cast<CppType>(0), // 0 is reserved for errors
+
+ CPPTYPE_DOUBLE, // TYPE_DOUBLE
+ CPPTYPE_FLOAT, // TYPE_FLOAT
+ CPPTYPE_INT64, // TYPE_INT64
+ CPPTYPE_UINT64, // TYPE_UINT64
+ CPPTYPE_INT32, // TYPE_INT32
+ CPPTYPE_UINT64, // TYPE_FIXED64
+ CPPTYPE_UINT32, // TYPE_FIXED32
+ CPPTYPE_BOOL, // TYPE_BOOL
+ CPPTYPE_STRING, // TYPE_STRING
+ CPPTYPE_MESSAGE, // TYPE_GROUP
+ CPPTYPE_MESSAGE, // TYPE_MESSAGE
+ CPPTYPE_STRING, // TYPE_BYTES
+ CPPTYPE_UINT32, // TYPE_UINT32
+ CPPTYPE_ENUM, // TYPE_ENUM
+ CPPTYPE_INT32, // TYPE_SFIXED32
+ CPPTYPE_INT64, // TYPE_SFIXED64
+ CPPTYPE_INT32, // TYPE_SINT32
+ CPPTYPE_INT64, // TYPE_SINT64
+};
+
+const char * const FieldDescriptor::kTypeToName[MAX_TYPE + 1] = {
+ "ERROR", // 0 is reserved for errors
+
+ "double", // TYPE_DOUBLE
+ "float", // TYPE_FLOAT
+ "int64", // TYPE_INT64
+ "uint64", // TYPE_UINT64
+ "int32", // TYPE_INT32
+ "fixed64", // TYPE_FIXED64
+ "fixed32", // TYPE_FIXED32
+ "bool", // TYPE_BOOL
+ "string", // TYPE_STRING
+ "group", // TYPE_GROUP
+ "message", // TYPE_MESSAGE
+ "bytes", // TYPE_BYTES
+ "uint32", // TYPE_UINT32
+ "enum", // TYPE_ENUM
+ "sfixed32", // TYPE_SFIXED32
+ "sfixed64", // TYPE_SFIXED64
+ "sint32", // TYPE_SINT32
+ "sint64", // TYPE_SINT64
+};
+
+const char * const FieldDescriptor::kCppTypeToName[MAX_CPPTYPE + 1] = {
+ "ERROR", // 0 is reserved for errors
+
+ "int32", // CPPTYPE_INT32
+ "int64", // CPPTYPE_INT64
+ "uint32", // CPPTYPE_UINT32
+ "uint64", // CPPTYPE_UINT64
+ "double", // CPPTYPE_DOUBLE
+ "float", // CPPTYPE_FLOAT
+ "bool", // CPPTYPE_BOOL
+ "enum", // CPPTYPE_ENUM
+ "string", // CPPTYPE_STRING
+ "message", // CPPTYPE_MESSAGE
+};
+
+const char * const FieldDescriptor::kLabelToName[MAX_LABEL + 1] = {
+ "ERROR", // 0 is reserved for errors
+
+ "optional", // LABEL_OPTIONAL
+ "required", // LABEL_REQUIRED
+ "repeated", // LABEL_REPEATED
+};
+
+const char* FileDescriptor::SyntaxName(FileDescriptor::Syntax syntax) {
+ switch (syntax) {
+ case SYNTAX_PROTO2:
+ return "proto2";
+ case SYNTAX_PROTO3:
+ return "proto3";
+ case SYNTAX_UNKNOWN:
+ return "unknown";
+ }
+ GOOGLE_LOG(FATAL) << "can't reach here.";
+ return NULL;
+}
+
+static const char * const kNonLinkedWeakMessageReplacementName = "google.protobuf.Empty";
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FieldDescriptor::kMaxNumber;
+const int FieldDescriptor::kFirstReservedNumber;
+const int FieldDescriptor::kLastReservedNumber;
+#endif
+
+namespace {
+
+string ToCamelCase(const string& input, bool lower_first) {
+ bool capitalize_next = !lower_first;
+ string result;
+ result.reserve(input.size());
+
+ for (int i = 0; i < input.size(); i++) {
+ if (input[i] == '_') {
+ capitalize_next = true;
+ } else if (capitalize_next) {
+ // Note: I distrust ctype.h due to locales.
+ if ('a' <= input[i] && input[i] <= 'z') {
+ result.push_back(input[i] - 'a' + 'A');
+ } else {
+ result.push_back(input[i]);
+ }
+ capitalize_next = false;
+ } else {
+ result.push_back(input[i]);
+ }
+ }
+
+ // Lower-case the first letter.
+ if (lower_first && !result.empty() && 'A' <= result[0] && result[0] <= 'Z') {
+ result[0] = result[0] - 'A' + 'a';
+ }
+
+ return result;
+}
+
+// A DescriptorPool contains a bunch of hash_maps to implement the
+// various Find*By*() methods. Since hashtable lookups are O(1), it's
+// most efficient to construct a fixed set of large hash_maps used by
+// all objects in the pool rather than construct one or more small
+// hash_maps for each object.
+//
+// The keys to these hash_maps are (parent, name) or (parent, number)
+// pairs. Unfortunately STL doesn't provide hash functions for pair<>,
+// so we must invent our own.
+//
+// TODO(kenton): Use StringPiece rather than const char* in keys? It would
+// be a lot cleaner but we'd just have to convert it back to const char*
+// for the open source release.
+
+typedef pair<const void*, const char*> PointerStringPair;
+
+struct PointerStringPairEqual {
+ inline bool operator()(const PointerStringPair& a,
+ const PointerStringPair& b) const {
+ return a.first == b.first && strcmp(a.second, b.second) == 0;
+ }
+};
+
+template<typename PairType>
+struct PointerIntegerPairHash {
+ size_t operator()(const PairType& p) const {
+ // FIXME(kenton): What is the best way to compute this hash? I have
+ // no idea! This seems a bit better than an XOR.
+ return reinterpret_cast<intptr_t>(p.first) * ((1 << 16) - 1) + p.second;
+ }
+
+#ifdef _MSC_VER
+ // Used only by MSVC and platforms where hash_map is not available.
+ static const size_t bucket_size = 4;
+ static const size_t min_buckets = 8;
+#endif
+ inline bool operator()(const PairType& a, const PairType& b) const {
+ return a.first < b.first ||
+ (a.first == b.first && a.second < b.second);
+ }
+};
+
+typedef pair<const Descriptor*, int> DescriptorIntPair;
+typedef pair<const EnumDescriptor*, int> EnumIntPair;
+
+struct PointerStringPairHash {
+ size_t operator()(const PointerStringPair& p) const {
+ // FIXME(kenton): What is the best way to compute this hash? I have
+ // no idea! This seems a bit better than an XOR.
+ hash<const char*> cstring_hash;
+ return reinterpret_cast<intptr_t>(p.first) * ((1 << 16) - 1) +
+ cstring_hash(p.second);
+ }
+
+#ifdef _MSC_VER
+ // Used only by MSVC and platforms where hash_map is not available.
+ static const size_t bucket_size = 4;
+ static const size_t min_buckets = 8;
+#endif
+ inline bool operator()(const PointerStringPair& a,
+ const PointerStringPair& b) const {
+ if (a.first < b.first) return true;
+ if (a.first > b.first) return false;
+ return strcmp(a.second, b.second) < 0;
+ }
+};
+
+
+struct Symbol {
+ enum Type {
+ NULL_SYMBOL, MESSAGE, FIELD, ONEOF, ENUM, ENUM_VALUE, SERVICE, METHOD,
+ PACKAGE
+ };
+ Type type;
+ union {
+ const Descriptor* descriptor;
+ const FieldDescriptor* field_descriptor;
+ const OneofDescriptor* oneof_descriptor;
+ const EnumDescriptor* enum_descriptor;
+ const EnumValueDescriptor* enum_value_descriptor;
+ const ServiceDescriptor* service_descriptor;
+ const MethodDescriptor* method_descriptor;
+ const FileDescriptor* package_file_descriptor;
+ };
+
+ inline Symbol() : type(NULL_SYMBOL) { descriptor = NULL; }
+ inline bool IsNull() const { return type == NULL_SYMBOL; }
+ inline bool IsType() const {
+ return type == MESSAGE || type == ENUM;
+ }
+ inline bool IsAggregate() const {
+ return type == MESSAGE || type == PACKAGE
+ || type == ENUM || type == SERVICE;
+ }
+
+#define CONSTRUCTOR(TYPE, TYPE_CONSTANT, FIELD) \
+ inline explicit Symbol(const TYPE* value) { \
+ type = TYPE_CONSTANT; \
+ this->FIELD = value; \
+ }
+
+ CONSTRUCTOR(Descriptor , MESSAGE , descriptor )
+ CONSTRUCTOR(FieldDescriptor , FIELD , field_descriptor )
+ CONSTRUCTOR(OneofDescriptor , ONEOF , oneof_descriptor )
+ CONSTRUCTOR(EnumDescriptor , ENUM , enum_descriptor )
+ CONSTRUCTOR(EnumValueDescriptor, ENUM_VALUE, enum_value_descriptor )
+ CONSTRUCTOR(ServiceDescriptor , SERVICE , service_descriptor )
+ CONSTRUCTOR(MethodDescriptor , METHOD , method_descriptor )
+ CONSTRUCTOR(FileDescriptor , PACKAGE , package_file_descriptor)
+#undef CONSTRUCTOR
+
+ const FileDescriptor* GetFile() const {
+ switch (type) {
+ case NULL_SYMBOL: return NULL;
+ case MESSAGE : return descriptor ->file();
+ case FIELD : return field_descriptor ->file();
+ case ONEOF : return oneof_descriptor ->containing_type()->file();
+ case ENUM : return enum_descriptor ->file();
+ case ENUM_VALUE : return enum_value_descriptor->type()->file();
+ case SERVICE : return service_descriptor ->file();
+ case METHOD : return method_descriptor ->service()->file();
+ case PACKAGE : return package_file_descriptor;
+ }
+ return NULL;
+ }
+};
+
+const Symbol kNullSymbol;
+
+typedef hash_map<const char*, Symbol,
+ hash<const char*>, streq>
+ SymbolsByNameMap;
+typedef hash_map<PointerStringPair, Symbol,
+ PointerStringPairHash, PointerStringPairEqual>
+ SymbolsByParentMap;
+typedef hash_map<const char*, const FileDescriptor*,
+ hash<const char*>, streq>
+ FilesByNameMap;
+typedef hash_map<PointerStringPair, const FieldDescriptor*,
+ PointerStringPairHash, PointerStringPairEqual>
+ FieldsByNameMap;
+typedef hash_map<DescriptorIntPair, const FieldDescriptor*,
+ PointerIntegerPairHash<DescriptorIntPair> >
+ FieldsByNumberMap;
+typedef hash_map<EnumIntPair, const EnumValueDescriptor*,
+ PointerIntegerPairHash<EnumIntPair> >
+ EnumValuesByNumberMap;
+// This is a map rather than a hash_map, since we use it to iterate
+// through all the extensions that extend a given Descriptor, and an
+// ordered data structure that implements lower_bound is convenient
+// for that.
+typedef map<DescriptorIntPair, const FieldDescriptor*>
+ ExtensionsGroupedByDescriptorMap;
+typedef hash_map<string, const SourceCodeInfo_Location*> LocationsByPathMap;
+
+set<string>* allowed_proto3_extendees_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(allowed_proto3_extendees_init_);
+
+void DeleteAllowedProto3Extendee() {
+ delete allowed_proto3_extendees_;
+}
+
+void InitAllowedProto3Extendee() {
+ allowed_proto3_extendees_ = new set<string>;
+ const char* kOptionNames[] = {
+ "FileOptions", "MessageOptions", "FieldOptions", "EnumOptions",
+ "EnumValueOptions", "ServiceOptions", "MethodOptions"};
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(kOptionNames); ++i) {
+ // descriptor.proto has a different package name in opensource. We allow
+ // both so the opensource protocol compiler can also compile internal
+ // proto3 files with custom options. See: b/27567912
+ allowed_proto3_extendees_->insert(string("google.protobuf.") +
+ kOptionNames[i]);
+ // Split the word to trick the opensource processing scripts so they
+ // will keep the origial package name.
+ allowed_proto3_extendees_->insert(string("proto") + "2." + kOptionNames[i]);
+ }
+
+ google::protobuf::internal::OnShutdown(&DeleteAllowedProto3Extendee);
+}
+
+// Checks whether the extendee type is allowed in proto3.
+// Only extensions to descriptor options are allowed. We use name comparison
+// instead of comparing the descriptor directly because the extensions may be
+// defined in a different pool.
+bool AllowedExtendeeInProto3(const string& name) {
+ ::google::protobuf::GoogleOnceInit(&allowed_proto3_extendees_init_, &InitAllowedProto3Extendee);
+ return allowed_proto3_extendees_->find(name) !=
+ allowed_proto3_extendees_->end();
+}
+
+} // anonymous namespace
+
+// ===================================================================
+// DescriptorPool::Tables
+
+class DescriptorPool::Tables {
+ public:
+ Tables();
+ ~Tables();
+
+ // Record the current state of the tables to the stack of checkpoints.
+ // Each call to AddCheckpoint() must be paired with exactly one call to either
+ // ClearLastCheckpoint() or RollbackToLastCheckpoint().
+ //
+ // This is used when building files, since some kinds of validation errors
+ // cannot be detected until the file's descriptors have already been added to
+ // the tables.
+ //
+ // This supports recursive checkpoints, since building a file may trigger
+ // recursive building of other files. Note that recursive checkpoints are not
+ // normally necessary; explicit dependencies are built prior to checkpointing.
+ // So although we recursively build transitive imports, there is at most one
+ // checkpoint in the stack during dependency building.
+ //
+ // Recursive checkpoints only arise during cross-linking of the descriptors.
+ // Symbol references must be resolved, via DescriptorBuilder::FindSymbol and
+ // friends. If the pending file references an unknown symbol
+ // (e.g., it is not defined in the pending file's explicit dependencies), and
+ // the pool is using a fallback database, and that database contains a file
+ // defining that symbol, and that file has not yet been built by the pool,
+ // the pool builds the file during cross-linking, leading to another
+ // checkpoint.
+ void AddCheckpoint();
+
+ // Mark the last checkpoint as having cleared successfully, removing it from
+ // the stack. If the stack is empty, all pending symbols will be committed.
+ //
+ // Note that this does not guarantee that the symbols added since the last
+ // checkpoint won't be rolled back: if a checkpoint gets rolled back,
+ // everything past that point gets rolled back, including symbols added after
+ // checkpoints that were pushed onto the stack after it and marked as cleared.
+ void ClearLastCheckpoint();
+
+ // Roll back the Tables to the state of the checkpoint at the top of the
+ // stack, removing everything that was added after that point.
+ void RollbackToLastCheckpoint();
+
+ // The stack of files which are currently being built. Used to detect
+ // cyclic dependencies when loading files from a DescriptorDatabase. Not
+ // used when fallback_database_ == NULL.
+ vector<string> pending_files_;
+
+ // A set of files which we have tried to load from the fallback database
+ // and encountered errors. We will not attempt to load them again during
+ // execution of the current public API call, but for compatibility with
+ // legacy clients, this is cleared at the beginning of each public API call.
+ // Not used when fallback_database_ == NULL.
+ hash_set<string> known_bad_files_;
+
+ // A set of symbols which we have tried to load from the fallback database
+ // and encountered errors. We will not attempt to load them again during
+ // execution of the current public API call, but for compatibility with
+ // legacy clients, this is cleared at the beginning of each public API call.
+ hash_set<string> known_bad_symbols_;
+
+ // The set of descriptors for which we've already loaded the full
+ // set of extensions numbers from fallback_database_.
+ hash_set<const Descriptor*> extensions_loaded_from_db_;
+
+ // -----------------------------------------------------------------
+ // Finding items.
+
+ // Find symbols. This returns a null Symbol (symbol.IsNull() is true)
+ // if not found.
+ inline Symbol FindSymbol(const string& key) const;
+
+ // This implements the body of DescriptorPool::Find*ByName(). It should
+ // really be a private method of DescriptorPool, but that would require
+ // declaring Symbol in descriptor.h, which would drag all kinds of other
+ // stuff into the header. Yay C++.
+ Symbol FindByNameHelper(
+ const DescriptorPool* pool, const string& name);
+
+ // These return NULL if not found.
+ inline const FileDescriptor* FindFile(const string& key) const;
+ inline const FieldDescriptor* FindExtension(const Descriptor* extendee,
+ int number);
+ inline void FindAllExtensions(const Descriptor* extendee,
+ vector<const FieldDescriptor*>* out) const;
+
+ // -----------------------------------------------------------------
+ // Adding items.
+
+ // These add items to the corresponding tables. They return false if
+ // the key already exists in the table. For AddSymbol(), the string passed
+ // in must be one that was constructed using AllocateString(), as it will
+ // be used as a key in the symbols_by_name_ map without copying.
+ bool AddSymbol(const string& full_name, Symbol symbol);
+ bool AddFile(const FileDescriptor* file);
+ bool AddExtension(const FieldDescriptor* field);
+
+ // -----------------------------------------------------------------
+ // Allocating memory.
+
+ // Allocate an object which will be reclaimed when the pool is
+ // destroyed. Note that the object's destructor will never be called,
+ // so its fields must be plain old data (primitive data types and
+ // pointers). All of the descriptor types are such objects.
+ template<typename Type> Type* Allocate();
+
+ // Allocate an array of objects which will be reclaimed when the
+ // pool in destroyed. Again, destructors are never called.
+ template<typename Type> Type* AllocateArray(int count);
+
+ // Allocate a string which will be destroyed when the pool is destroyed.
+ // The string is initialized to the given value for convenience.
+ string* AllocateString(const string& value);
+
+ // Allocate a protocol message object. Some older versions of GCC have
+ // trouble understanding explicit template instantiations in some cases, so
+ // in those cases we have to pass a dummy pointer of the right type as the
+ // parameter instead of specifying the type explicitly.
+ template<typename Type> Type* AllocateMessage(Type* dummy = NULL);
+
+ // Allocate a FileDescriptorTables object.
+ FileDescriptorTables* AllocateFileTables();
+
+ private:
+ vector<string*> strings_; // All strings in the pool.
+ vector<Message*> messages_; // All messages in the pool.
+ vector<FileDescriptorTables*> file_tables_; // All file tables in the pool.
+ vector<void*> allocations_; // All other memory allocated in the pool.
+
+ SymbolsByNameMap symbols_by_name_;
+ FilesByNameMap files_by_name_;
+ ExtensionsGroupedByDescriptorMap extensions_;
+
+ struct CheckPoint {
+ explicit CheckPoint(const Tables* tables)
+ : strings_before_checkpoint(tables->strings_.size()),
+ messages_before_checkpoint(tables->messages_.size()),
+ file_tables_before_checkpoint(tables->file_tables_.size()),
+ allocations_before_checkpoint(tables->allocations_.size()),
+ pending_symbols_before_checkpoint(
+ tables->symbols_after_checkpoint_.size()),
+ pending_files_before_checkpoint(
+ tables->files_after_checkpoint_.size()),
+ pending_extensions_before_checkpoint(
+ tables->extensions_after_checkpoint_.size()) {
+ }
+ int strings_before_checkpoint;
+ int messages_before_checkpoint;
+ int file_tables_before_checkpoint;
+ int allocations_before_checkpoint;
+ int pending_symbols_before_checkpoint;
+ int pending_files_before_checkpoint;
+ int pending_extensions_before_checkpoint;
+ };
+ vector<CheckPoint> checkpoints_;
+ vector<const char* > symbols_after_checkpoint_;
+ vector<const char* > files_after_checkpoint_;
+ vector<DescriptorIntPair> extensions_after_checkpoint_;
+
+ // Allocate some bytes which will be reclaimed when the pool is
+ // destroyed.
+ void* AllocateBytes(int size);
+};
+
+// Contains tables specific to a particular file. These tables are not
+// modified once the file has been constructed, so they need not be
+// protected by a mutex. This makes operations that depend only on the
+// contents of a single file -- e.g. Descriptor::FindFieldByName() --
+// lock-free.
+//
+// For historical reasons, the definitions of the methods of
+// FileDescriptorTables and DescriptorPool::Tables are interleaved below.
+// These used to be a single class.
+class FileDescriptorTables {
+ public:
+ FileDescriptorTables();
+ ~FileDescriptorTables();
+
+ // Empty table, used with placeholder files.
+ inline static const FileDescriptorTables& GetEmptyInstance();
+
+ // -----------------------------------------------------------------
+ // Finding items.
+
+ // Find symbols. These return a null Symbol (symbol.IsNull() is true)
+ // if not found.
+ inline Symbol FindNestedSymbol(const void* parent,
+ const string& name) const;
+ inline Symbol FindNestedSymbolOfType(const void* parent,
+ const string& name,
+ const Symbol::Type type) const;
+
+ // These return NULL if not found.
+ inline const FieldDescriptor* FindFieldByNumber(
+ const Descriptor* parent, int number) const;
+ inline const FieldDescriptor* FindFieldByLowercaseName(
+ const void* parent, const string& lowercase_name) const;
+ inline const FieldDescriptor* FindFieldByCamelcaseName(
+ const void* parent, const string& camelcase_name) const;
+ inline const EnumValueDescriptor* FindEnumValueByNumber(
+ const EnumDescriptor* parent, int number) const;
+ // This creates a new EnumValueDescriptor if not found, in a thread-safe way.
+ inline const EnumValueDescriptor* FindEnumValueByNumberCreatingIfUnknown(
+ const EnumDescriptor* parent, int number) const;
+
+ // -----------------------------------------------------------------
+ // Adding items.
+
+ // These add items to the corresponding tables. They return false if
+ // the key already exists in the table. For AddAliasUnderParent(), the
+ // string passed in must be one that was constructed using AllocateString(),
+ // as it will be used as a key in the symbols_by_parent_ map without copying.
+ bool AddAliasUnderParent(const void* parent, const string& name,
+ Symbol symbol);
+ bool AddFieldByNumber(const FieldDescriptor* field);
+ bool AddEnumValueByNumber(const EnumValueDescriptor* value);
+
+ // Adds the field to the lowercase_name and camelcase_name maps. Never
+ // fails because we allow duplicates; the first field by the name wins.
+ void AddFieldByStylizedNames(const FieldDescriptor* field);
+
+ // Populates p->first->locations_by_path_ from p->second.
+ // Unusual signature dictated by GoogleOnceDynamic.
+ static void BuildLocationsByPath(
+ pair<const FileDescriptorTables*, const SourceCodeInfo*>* p);
+
+ // Returns the location denoted by the specified path through info,
+ // or NULL if not found.
+ // The value of info must be that of the corresponding FileDescriptor.
+ // (Conceptually a pure function, but stateful as an optimisation.)
+ const SourceCodeInfo_Location* GetSourceLocation(
+ const vector<int>& path, const SourceCodeInfo* info) const;
+
+ private:
+ SymbolsByParentMap symbols_by_parent_;
+ FieldsByNameMap fields_by_lowercase_name_;
+ FieldsByNameMap fields_by_camelcase_name_;
+ FieldsByNumberMap fields_by_number_; // Not including extensions.
+ EnumValuesByNumberMap enum_values_by_number_;
+ mutable EnumValuesByNumberMap unknown_enum_values_by_number_
+ GOOGLE_GUARDED_BY(unknown_enum_values_mu_);
+
+ // Populated on first request to save space, hence constness games.
+ mutable GoogleOnceDynamic locations_by_path_once_;
+ mutable LocationsByPathMap locations_by_path_;
+
+ // Mutex to protect the unknown-enum-value map due to dynamic
+ // EnumValueDescriptor creation on unknown values.
+ mutable Mutex unknown_enum_values_mu_;
+};
+
+DescriptorPool::Tables::Tables()
+ // Start some hash_map and hash_set objects with a small # of buckets
+ : known_bad_files_(3),
+ known_bad_symbols_(3),
+ extensions_loaded_from_db_(3),
+ symbols_by_name_(3),
+ files_by_name_(3) {}
+
+
+DescriptorPool::Tables::~Tables() {
+ GOOGLE_DCHECK(checkpoints_.empty());
+ // Note that the deletion order is important, since the destructors of some
+ // messages may refer to objects in allocations_.
+ STLDeleteElements(&messages_);
+ for (int i = 0; i < allocations_.size(); i++) {
+ operator delete(allocations_[i]);
+ }
+ STLDeleteElements(&strings_);
+ STLDeleteElements(&file_tables_);
+}
+
+FileDescriptorTables::FileDescriptorTables()
+ // Initialize all the hash tables to start out with a small # of buckets
+ : symbols_by_parent_(3),
+ fields_by_lowercase_name_(3),
+ fields_by_camelcase_name_(3),
+ fields_by_number_(3),
+ enum_values_by_number_(3),
+ unknown_enum_values_by_number_(3) {
+}
+
+FileDescriptorTables::~FileDescriptorTables() {}
+
+namespace {
+
+FileDescriptorTables* file_descriptor_tables_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(file_descriptor_tables_once_init_);
+
+void DeleteFileDescriptorTables() {
+ delete file_descriptor_tables_;
+ file_descriptor_tables_ = NULL;
+}
+
+void InitFileDescriptorTables() {
+ file_descriptor_tables_ = new FileDescriptorTables();
+ internal::OnShutdown(&DeleteFileDescriptorTables);
+}
+
+inline void InitFileDescriptorTablesOnce() {
+ ::google::protobuf::GoogleOnceInit(
+ &file_descriptor_tables_once_init_, &InitFileDescriptorTables);
+}
+
+} // anonymous namespace
+
+inline const FileDescriptorTables& FileDescriptorTables::GetEmptyInstance() {
+ InitFileDescriptorTablesOnce();
+ return *file_descriptor_tables_;
+}
+
+void DescriptorPool::Tables::AddCheckpoint() {
+ checkpoints_.push_back(CheckPoint(this));
+}
+
+void DescriptorPool::Tables::ClearLastCheckpoint() {
+ GOOGLE_DCHECK(!checkpoints_.empty());
+ checkpoints_.pop_back();
+ if (checkpoints_.empty()) {
+ // All checkpoints have been cleared: we can now commit all of the pending
+ // data.
+ symbols_after_checkpoint_.clear();
+ files_after_checkpoint_.clear();
+ extensions_after_checkpoint_.clear();
+ }
+}
+
+void DescriptorPool::Tables::RollbackToLastCheckpoint() {
+ GOOGLE_DCHECK(!checkpoints_.empty());
+ const CheckPoint& checkpoint = checkpoints_.back();
+
+ for (int i = checkpoint.pending_symbols_before_checkpoint;
+ i < symbols_after_checkpoint_.size();
+ i++) {
+ symbols_by_name_.erase(symbols_after_checkpoint_[i]);
+ }
+ for (int i = checkpoint.pending_files_before_checkpoint;
+ i < files_after_checkpoint_.size();
+ i++) {
+ files_by_name_.erase(files_after_checkpoint_[i]);
+ }
+ for (int i = checkpoint.pending_extensions_before_checkpoint;
+ i < extensions_after_checkpoint_.size();
+ i++) {
+ extensions_.erase(extensions_after_checkpoint_[i]);
+ }
+
+ symbols_after_checkpoint_.resize(
+ checkpoint.pending_symbols_before_checkpoint);
+ files_after_checkpoint_.resize(checkpoint.pending_files_before_checkpoint);
+ extensions_after_checkpoint_.resize(
+ checkpoint.pending_extensions_before_checkpoint);
+
+ STLDeleteContainerPointers(
+ strings_.begin() + checkpoint.strings_before_checkpoint, strings_.end());
+ STLDeleteContainerPointers(
+ messages_.begin() + checkpoint.messages_before_checkpoint,
+ messages_.end());
+ STLDeleteContainerPointers(
+ file_tables_.begin() + checkpoint.file_tables_before_checkpoint,
+ file_tables_.end());
+ for (int i = checkpoint.allocations_before_checkpoint;
+ i < allocations_.size();
+ i++) {
+ operator delete(allocations_[i]);
+ }
+
+ strings_.resize(checkpoint.strings_before_checkpoint);
+ messages_.resize(checkpoint.messages_before_checkpoint);
+ file_tables_.resize(checkpoint.file_tables_before_checkpoint);
+ allocations_.resize(checkpoint.allocations_before_checkpoint);
+ checkpoints_.pop_back();
+}
+
+// -------------------------------------------------------------------
+
+inline Symbol DescriptorPool::Tables::FindSymbol(const string& key) const {
+ const Symbol* result = FindOrNull(symbols_by_name_, key.c_str());
+ if (result == NULL) {
+ return kNullSymbol;
+ } else {
+ return *result;
+ }
+}
+
+inline Symbol FileDescriptorTables::FindNestedSymbol(
+ const void* parent, const string& name) const {
+ const Symbol* result =
+ FindOrNull(symbols_by_parent_, PointerStringPair(parent, name.c_str()));
+ if (result == NULL) {
+ return kNullSymbol;
+ } else {
+ return *result;
+ }
+}
+
+inline Symbol FileDescriptorTables::FindNestedSymbolOfType(
+ const void* parent, const string& name, const Symbol::Type type) const {
+ Symbol result = FindNestedSymbol(parent, name);
+ if (result.type != type) return kNullSymbol;
+ return result;
+}
+
+Symbol DescriptorPool::Tables::FindByNameHelper(
+ const DescriptorPool* pool, const string& name) {
+ MutexLockMaybe lock(pool->mutex_);
+ known_bad_symbols_.clear();
+ known_bad_files_.clear();
+ Symbol result = FindSymbol(name);
+
+ if (result.IsNull() && pool->underlay_ != NULL) {
+ // Symbol not found; check the underlay.
+ result =
+ pool->underlay_->tables_->FindByNameHelper(pool->underlay_, name);
+ }
+
+ if (result.IsNull()) {
+ // Symbol still not found, so check fallback database.
+ if (pool->TryFindSymbolInFallbackDatabase(name)) {
+ result = FindSymbol(name);
+ }
+ }
+
+ return result;
+}
+
+inline const FileDescriptor* DescriptorPool::Tables::FindFile(
+ const string& key) const {
+ return FindPtrOrNull(files_by_name_, key.c_str());
+}
+
+inline const FieldDescriptor* FileDescriptorTables::FindFieldByNumber(
+ const Descriptor* parent, int number) const {
+ return FindPtrOrNull(fields_by_number_, std::make_pair(parent, number));
+}
+
+inline const FieldDescriptor* FileDescriptorTables::FindFieldByLowercaseName(
+ const void* parent, const string& lowercase_name) const {
+ return FindPtrOrNull(fields_by_lowercase_name_,
+ PointerStringPair(parent, lowercase_name.c_str()));
+}
+
+inline const FieldDescriptor* FileDescriptorTables::FindFieldByCamelcaseName(
+ const void* parent, const string& camelcase_name) const {
+ return FindPtrOrNull(fields_by_camelcase_name_,
+ PointerStringPair(parent, camelcase_name.c_str()));
+}
+
+inline const EnumValueDescriptor* FileDescriptorTables::FindEnumValueByNumber(
+ const EnumDescriptor* parent, int number) const {
+ return FindPtrOrNull(enum_values_by_number_, std::make_pair(parent, number));
+}
+
+inline const EnumValueDescriptor*
+FileDescriptorTables::FindEnumValueByNumberCreatingIfUnknown(
+ const EnumDescriptor* parent, int number) const {
+ // First try, with map of compiled-in values.
+ {
+ const EnumValueDescriptor* desc =
+ FindPtrOrNull(enum_values_by_number_, std::make_pair(parent, number));
+ if (desc != NULL) {
+ return desc;
+ }
+ }
+ // Second try, with reader lock held on unknown enum values: common case.
+ {
+ ReaderMutexLock l(&unknown_enum_values_mu_);
+ const EnumValueDescriptor* desc = FindPtrOrNull(
+ unknown_enum_values_by_number_, std::make_pair(parent, number));
+ if (desc != NULL) {
+ return desc;
+ }
+ }
+ // If not found, try again with writer lock held, and create new descriptor if
+ // necessary.
+ {
+ WriterMutexLock l(&unknown_enum_values_mu_);
+ const EnumValueDescriptor* desc = FindPtrOrNull(
+ unknown_enum_values_by_number_, std::make_pair(parent, number));
+ if (desc != NULL) {
+ return desc;
+ }
+
+ // Create an EnumValueDescriptor dynamically. We don't insert it into the
+ // EnumDescriptor (it's not a part of the enum as originally defined), but
+ // we do insert it into the table so that we can return the same pointer
+ // later.
+ string enum_value_name = StringPrintf(
+ "UNKNOWN_ENUM_VALUE_%s_%d", parent->name().c_str(), number);
+ DescriptorPool::Tables* tables =
+ const_cast<DescriptorPool::Tables*>(DescriptorPool::generated_pool()->
+ tables_.get());
+ EnumValueDescriptor* result = tables->Allocate<EnumValueDescriptor>();
+ result->name_ = tables->AllocateString(enum_value_name);
+ result->full_name_ = tables->AllocateString(parent->full_name() +
+ "." + enum_value_name);
+ result->number_ = number;
+ result->type_ = parent;
+ result->options_ = &EnumValueOptions::default_instance();
+ InsertIfNotPresent(&unknown_enum_values_by_number_,
+ std::make_pair(parent, number), result);
+ return result;
+ }
+}
+
+
+inline const FieldDescriptor* DescriptorPool::Tables::FindExtension(
+ const Descriptor* extendee, int number) {
+ return FindPtrOrNull(extensions_, std::make_pair(extendee, number));
+}
+
+inline void DescriptorPool::Tables::FindAllExtensions(
+ const Descriptor* extendee, vector<const FieldDescriptor*>* out) const {
+ ExtensionsGroupedByDescriptorMap::const_iterator it =
+ extensions_.lower_bound(std::make_pair(extendee, 0));
+ for (; it != extensions_.end() && it->first.first == extendee; ++it) {
+ out->push_back(it->second);
+ }
+}
+
+// -------------------------------------------------------------------
+
+bool DescriptorPool::Tables::AddSymbol(
+ const string& full_name, Symbol symbol) {
+ if (InsertIfNotPresent(&symbols_by_name_, full_name.c_str(), symbol)) {
+ symbols_after_checkpoint_.push_back(full_name.c_str());
+ return true;
+ } else {
+ return false;
+ }
+}
+
+bool FileDescriptorTables::AddAliasUnderParent(
+ const void* parent, const string& name, Symbol symbol) {
+ PointerStringPair by_parent_key(parent, name.c_str());
+ return InsertIfNotPresent(&symbols_by_parent_, by_parent_key, symbol);
+}
+
+bool DescriptorPool::Tables::AddFile(const FileDescriptor* file) {
+ if (InsertIfNotPresent(&files_by_name_, file->name().c_str(), file)) {
+ files_after_checkpoint_.push_back(file->name().c_str());
+ return true;
+ } else {
+ return false;
+ }
+}
+
+void FileDescriptorTables::AddFieldByStylizedNames(
+ const FieldDescriptor* field) {
+ const void* parent;
+ if (field->is_extension()) {
+ if (field->extension_scope() == NULL) {
+ parent = field->file();
+ } else {
+ parent = field->extension_scope();
+ }
+ } else {
+ parent = field->containing_type();
+ }
+
+ PointerStringPair lowercase_key(parent, field->lowercase_name().c_str());
+ InsertIfNotPresent(&fields_by_lowercase_name_, lowercase_key, field);
+
+ PointerStringPair camelcase_key(parent, field->camelcase_name().c_str());
+ InsertIfNotPresent(&fields_by_camelcase_name_, camelcase_key, field);
+}
+
+bool FileDescriptorTables::AddFieldByNumber(const FieldDescriptor* field) {
+ DescriptorIntPair key(field->containing_type(), field->number());
+ return InsertIfNotPresent(&fields_by_number_, key, field);
+}
+
+bool FileDescriptorTables::AddEnumValueByNumber(
+ const EnumValueDescriptor* value) {
+ EnumIntPair key(value->type(), value->number());
+ return InsertIfNotPresent(&enum_values_by_number_, key, value);
+}
+
+bool DescriptorPool::Tables::AddExtension(const FieldDescriptor* field) {
+ DescriptorIntPair key(field->containing_type(), field->number());
+ if (InsertIfNotPresent(&extensions_, key, field)) {
+ extensions_after_checkpoint_.push_back(key);
+ return true;
+ } else {
+ return false;
+ }
+}
+
+// -------------------------------------------------------------------
+
+template<typename Type>
+Type* DescriptorPool::Tables::Allocate() {
+ return reinterpret_cast<Type*>(AllocateBytes(sizeof(Type)));
+}
+
+template<typename Type>
+Type* DescriptorPool::Tables::AllocateArray(int count) {
+ return reinterpret_cast<Type*>(AllocateBytes(sizeof(Type) * count));
+}
+
+string* DescriptorPool::Tables::AllocateString(const string& value) {
+ string* result = new string(value);
+ strings_.push_back(result);
+ return result;
+}
+
+template<typename Type>
+Type* DescriptorPool::Tables::AllocateMessage(Type* /* dummy */) {
+ Type* result = new Type;
+ messages_.push_back(result);
+ return result;
+}
+
+FileDescriptorTables* DescriptorPool::Tables::AllocateFileTables() {
+ FileDescriptorTables* result = new FileDescriptorTables;
+ file_tables_.push_back(result);
+ return result;
+}
+
+void* DescriptorPool::Tables::AllocateBytes(int size) {
+ // TODO(kenton): Would it be worthwhile to implement this in some more
+ // sophisticated way? Probably not for the open source release, but for
+ // internal use we could easily plug in one of our existing memory pool
+ // allocators...
+ if (size == 0) return NULL;
+
+ void* result = operator new(size);
+ allocations_.push_back(result);
+ return result;
+}
+
+void FileDescriptorTables::BuildLocationsByPath(
+ pair<const FileDescriptorTables*, const SourceCodeInfo*>* p) {
+ for (int i = 0, len = p->second->location_size(); i < len; ++i) {
+ const SourceCodeInfo_Location* loc = &p->second->location().Get(i);
+ p->first->locations_by_path_[Join(loc->path(), ",")] = loc;
+ }
+}
+
+const SourceCodeInfo_Location* FileDescriptorTables::GetSourceLocation(
+ const vector<int>& path, const SourceCodeInfo* info) const {
+ pair<const FileDescriptorTables*, const SourceCodeInfo*> p(
+ std::make_pair(this, info));
+ locations_by_path_once_.Init(&FileDescriptorTables::BuildLocationsByPath, &p);
+ return FindPtrOrNull(locations_by_path_, Join(path, ","));
+}
+
+// ===================================================================
+// DescriptorPool
+
+DescriptorPool::ErrorCollector::~ErrorCollector() {}
+
+DescriptorPool::DescriptorPool()
+ : mutex_(NULL),
+ fallback_database_(NULL),
+ default_error_collector_(NULL),
+ underlay_(NULL),
+ tables_(new Tables),
+ enforce_dependencies_(true),
+ allow_unknown_(false),
+ enforce_weak_(false) {}
+
+DescriptorPool::DescriptorPool(DescriptorDatabase* fallback_database,
+ ErrorCollector* error_collector)
+ : mutex_(new Mutex),
+ fallback_database_(fallback_database),
+ default_error_collector_(error_collector),
+ underlay_(NULL),
+ tables_(new Tables),
+ enforce_dependencies_(true),
+ allow_unknown_(false),
+ enforce_weak_(false) {
+}
+
+DescriptorPool::DescriptorPool(const DescriptorPool* underlay)
+ : mutex_(NULL),
+ fallback_database_(NULL),
+ default_error_collector_(NULL),
+ underlay_(underlay),
+ tables_(new Tables),
+ enforce_dependencies_(true),
+ allow_unknown_(false),
+ enforce_weak_(false) {}
+
+DescriptorPool::~DescriptorPool() {
+ if (mutex_ != NULL) delete mutex_;
+}
+
+// DescriptorPool::BuildFile() defined later.
+// DescriptorPool::BuildFileCollectingErrors() defined later.
+
+void DescriptorPool::InternalDontEnforceDependencies() {
+ enforce_dependencies_ = false;
+}
+
+void DescriptorPool::AddUnusedImportTrackFile(const string& file_name) {
+ unused_import_track_files_.insert(file_name);
+}
+
+void DescriptorPool::ClearUnusedImportTrackFiles() {
+ unused_import_track_files_.clear();
+}
+
+bool DescriptorPool::InternalIsFileLoaded(const string& filename) const {
+ MutexLockMaybe lock(mutex_);
+ return tables_->FindFile(filename) != NULL;
+}
+
+// generated_pool ====================================================
+
+namespace {
+
+
+EncodedDescriptorDatabase* generated_database_ = NULL;
+DescriptorPool* generated_pool_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(generated_pool_init_);
+
+void DeleteGeneratedPool() {
+ delete generated_database_;
+ generated_database_ = NULL;
+ delete generated_pool_;
+ generated_pool_ = NULL;
+}
+
+static void InitGeneratedPool() {
+ generated_database_ = new EncodedDescriptorDatabase;
+ generated_pool_ = new DescriptorPool(generated_database_);
+
+ internal::OnShutdown(&DeleteGeneratedPool);
+}
+
+inline void InitGeneratedPoolOnce() {
+ ::google::protobuf::GoogleOnceInit(&generated_pool_init_, &InitGeneratedPool);
+}
+
+} // anonymous namespace
+
+const DescriptorPool* DescriptorPool::generated_pool() {
+ InitGeneratedPoolOnce();
+ return generated_pool_;
+}
+
+
+DescriptorPool* DescriptorPool::internal_generated_pool() {
+ InitGeneratedPoolOnce();
+ return generated_pool_;
+}
+
+void DescriptorPool::InternalAddGeneratedFile(
+ const void* encoded_file_descriptor, int size) {
+ // So, this function is called in the process of initializing the
+ // descriptors for generated proto classes. Each generated .pb.cc file
+ // has an internal procedure called AddDescriptors() which is called at
+ // process startup, and that function calls this one in order to register
+ // the raw bytes of the FileDescriptorProto representing the file.
+ //
+ // We do not actually construct the descriptor objects right away. We just
+ // hang on to the bytes until they are actually needed. We actually construct
+ // the descriptor the first time one of the following things happens:
+ // * Someone calls a method like descriptor(), GetDescriptor(), or
+ // GetReflection() on the generated types, which requires returning the
+ // descriptor or an object based on it.
+ // * Someone looks up the descriptor in DescriptorPool::generated_pool().
+ //
+ // Once one of these happens, the DescriptorPool actually parses the
+ // FileDescriptorProto and generates a FileDescriptor (and all its children)
+ // based on it.
+ //
+ // Note that FileDescriptorProto is itself a generated protocol message.
+ // Therefore, when we parse one, we have to be very careful to avoid using
+ // any descriptor-based operations, since this might cause infinite recursion
+ // or deadlock.
+ InitGeneratedPoolOnce();
+ GOOGLE_CHECK(generated_database_->Add(encoded_file_descriptor, size));
+}
+
+
+// Find*By* methods ==================================================
+
+// TODO(kenton): There's a lot of repeated code here, but I'm not sure if
+// there's any good way to factor it out. Think about this some time when
+// there's nothing more important to do (read: never).
+
+const FileDescriptor* DescriptorPool::FindFileByName(const string& name) const {
+ MutexLockMaybe lock(mutex_);
+ tables_->known_bad_symbols_.clear();
+ tables_->known_bad_files_.clear();
+ const FileDescriptor* result = tables_->FindFile(name);
+ if (result != NULL) return result;
+ if (underlay_ != NULL) {
+ result = underlay_->FindFileByName(name);
+ if (result != NULL) return result;
+ }
+ if (TryFindFileInFallbackDatabase(name)) {
+ result = tables_->FindFile(name);
+ if (result != NULL) return result;
+ }
+ return NULL;
+}
+
+const FileDescriptor* DescriptorPool::FindFileContainingSymbol(
+ const string& symbol_name) const {
+ MutexLockMaybe lock(mutex_);
+ tables_->known_bad_symbols_.clear();
+ tables_->known_bad_files_.clear();
+ Symbol result = tables_->FindSymbol(symbol_name);
+ if (!result.IsNull()) return result.GetFile();
+ if (underlay_ != NULL) {
+ const FileDescriptor* file_result =
+ underlay_->FindFileContainingSymbol(symbol_name);
+ if (file_result != NULL) return file_result;
+ }
+ if (TryFindSymbolInFallbackDatabase(symbol_name)) {
+ result = tables_->FindSymbol(symbol_name);
+ if (!result.IsNull()) return result.GetFile();
+ }
+ return NULL;
+}
+
+const Descriptor* DescriptorPool::FindMessageTypeByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ return (result.type == Symbol::MESSAGE) ? result.descriptor : NULL;
+}
+
+const FieldDescriptor* DescriptorPool::FindFieldByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ if (result.type == Symbol::FIELD &&
+ !result.field_descriptor->is_extension()) {
+ return result.field_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const FieldDescriptor* DescriptorPool::FindExtensionByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ if (result.type == Symbol::FIELD &&
+ result.field_descriptor->is_extension()) {
+ return result.field_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const OneofDescriptor* DescriptorPool::FindOneofByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ return (result.type == Symbol::ONEOF) ? result.oneof_descriptor : NULL;
+}
+
+const EnumDescriptor* DescriptorPool::FindEnumTypeByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ return (result.type == Symbol::ENUM) ? result.enum_descriptor : NULL;
+}
+
+const EnumValueDescriptor* DescriptorPool::FindEnumValueByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ return (result.type == Symbol::ENUM_VALUE) ?
+ result.enum_value_descriptor : NULL;
+}
+
+const ServiceDescriptor* DescriptorPool::FindServiceByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ return (result.type == Symbol::SERVICE) ? result.service_descriptor : NULL;
+}
+
+const MethodDescriptor* DescriptorPool::FindMethodByName(
+ const string& name) const {
+ Symbol result = tables_->FindByNameHelper(this, name);
+ return (result.type == Symbol::METHOD) ? result.method_descriptor : NULL;
+}
+
+const FieldDescriptor* DescriptorPool::FindExtensionByNumber(
+ const Descriptor* extendee, int number) const {
+ MutexLockMaybe lock(mutex_);
+ tables_->known_bad_symbols_.clear();
+ tables_->known_bad_files_.clear();
+ const FieldDescriptor* result = tables_->FindExtension(extendee, number);
+ if (result != NULL) {
+ return result;
+ }
+ if (underlay_ != NULL) {
+ result = underlay_->FindExtensionByNumber(extendee, number);
+ if (result != NULL) return result;
+ }
+ if (TryFindExtensionInFallbackDatabase(extendee, number)) {
+ result = tables_->FindExtension(extendee, number);
+ if (result != NULL) {
+ return result;
+ }
+ }
+ return NULL;
+}
+
+void DescriptorPool::FindAllExtensions(
+ const Descriptor* extendee, vector<const FieldDescriptor*>* out) const {
+ MutexLockMaybe lock(mutex_);
+ tables_->known_bad_symbols_.clear();
+ tables_->known_bad_files_.clear();
+
+ // Initialize tables_->extensions_ from the fallback database first
+ // (but do this only once per descriptor).
+ if (fallback_database_ != NULL &&
+ tables_->extensions_loaded_from_db_.count(extendee) == 0) {
+ vector<int> numbers;
+ if (fallback_database_->FindAllExtensionNumbers(extendee->full_name(),
+ &numbers)) {
+ for (int i = 0; i < numbers.size(); ++i) {
+ int number = numbers[i];
+ if (tables_->FindExtension(extendee, number) == NULL) {
+ TryFindExtensionInFallbackDatabase(extendee, number);
+ }
+ }
+ tables_->extensions_loaded_from_db_.insert(extendee);
+ }
+ }
+
+ tables_->FindAllExtensions(extendee, out);
+ if (underlay_ != NULL) {
+ underlay_->FindAllExtensions(extendee, out);
+ }
+}
+
+
+// -------------------------------------------------------------------
+
+const FieldDescriptor*
+Descriptor::FindFieldByNumber(int key) const {
+ const FieldDescriptor* result =
+ file()->tables_->FindFieldByNumber(this, key);
+ if (result == NULL || result->is_extension()) {
+ return NULL;
+ } else {
+ return result;
+ }
+}
+
+const FieldDescriptor*
+Descriptor::FindFieldByLowercaseName(const string& key) const {
+ const FieldDescriptor* result =
+ file()->tables_->FindFieldByLowercaseName(this, key);
+ if (result == NULL || result->is_extension()) {
+ return NULL;
+ } else {
+ return result;
+ }
+}
+
+const FieldDescriptor*
+Descriptor::FindFieldByCamelcaseName(const string& key) const {
+ const FieldDescriptor* result =
+ file()->tables_->FindFieldByCamelcaseName(this, key);
+ if (result == NULL || result->is_extension()) {
+ return NULL;
+ } else {
+ return result;
+ }
+}
+
+const FieldDescriptor*
+Descriptor::FindFieldByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::FIELD);
+ if (!result.IsNull() && !result.field_descriptor->is_extension()) {
+ return result.field_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const OneofDescriptor*
+Descriptor::FindOneofByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::ONEOF);
+ if (!result.IsNull()) {
+ return result.oneof_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const FieldDescriptor*
+Descriptor::FindExtensionByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::FIELD);
+ if (!result.IsNull() && result.field_descriptor->is_extension()) {
+ return result.field_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const FieldDescriptor*
+Descriptor::FindExtensionByLowercaseName(const string& key) const {
+ const FieldDescriptor* result =
+ file()->tables_->FindFieldByLowercaseName(this, key);
+ if (result == NULL || !result->is_extension()) {
+ return NULL;
+ } else {
+ return result;
+ }
+}
+
+const FieldDescriptor*
+Descriptor::FindExtensionByCamelcaseName(const string& key) const {
+ const FieldDescriptor* result =
+ file()->tables_->FindFieldByCamelcaseName(this, key);
+ if (result == NULL || !result->is_extension()) {
+ return NULL;
+ } else {
+ return result;
+ }
+}
+
+const Descriptor*
+Descriptor::FindNestedTypeByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::MESSAGE);
+ if (!result.IsNull()) {
+ return result.descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const EnumDescriptor*
+Descriptor::FindEnumTypeByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::ENUM);
+ if (!result.IsNull()) {
+ return result.enum_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const EnumValueDescriptor*
+Descriptor::FindEnumValueByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::ENUM_VALUE);
+ if (!result.IsNull()) {
+ return result.enum_value_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const EnumValueDescriptor*
+EnumDescriptor::FindValueByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::ENUM_VALUE);
+ if (!result.IsNull()) {
+ return result.enum_value_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const EnumValueDescriptor*
+EnumDescriptor::FindValueByNumber(int key) const {
+ return file()->tables_->FindEnumValueByNumber(this, key);
+}
+
+const EnumValueDescriptor*
+EnumDescriptor::FindValueByNumberCreatingIfUnknown(int key) const {
+ return file()->tables_->FindEnumValueByNumberCreatingIfUnknown(this, key);
+}
+
+const MethodDescriptor*
+ServiceDescriptor::FindMethodByName(const string& key) const {
+ Symbol result =
+ file()->tables_->FindNestedSymbolOfType(this, key, Symbol::METHOD);
+ if (!result.IsNull()) {
+ return result.method_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const Descriptor*
+FileDescriptor::FindMessageTypeByName(const string& key) const {
+ Symbol result = tables_->FindNestedSymbolOfType(this, key, Symbol::MESSAGE);
+ if (!result.IsNull()) {
+ return result.descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const EnumDescriptor*
+FileDescriptor::FindEnumTypeByName(const string& key) const {
+ Symbol result = tables_->FindNestedSymbolOfType(this, key, Symbol::ENUM);
+ if (!result.IsNull()) {
+ return result.enum_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const EnumValueDescriptor*
+FileDescriptor::FindEnumValueByName(const string& key) const {
+ Symbol result =
+ tables_->FindNestedSymbolOfType(this, key, Symbol::ENUM_VALUE);
+ if (!result.IsNull()) {
+ return result.enum_value_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const ServiceDescriptor*
+FileDescriptor::FindServiceByName(const string& key) const {
+ Symbol result = tables_->FindNestedSymbolOfType(this, key, Symbol::SERVICE);
+ if (!result.IsNull()) {
+ return result.service_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const FieldDescriptor*
+FileDescriptor::FindExtensionByName(const string& key) const {
+ Symbol result = tables_->FindNestedSymbolOfType(this, key, Symbol::FIELD);
+ if (!result.IsNull() && result.field_descriptor->is_extension()) {
+ return result.field_descriptor;
+ } else {
+ return NULL;
+ }
+}
+
+const FieldDescriptor*
+FileDescriptor::FindExtensionByLowercaseName(const string& key) const {
+ const FieldDescriptor* result = tables_->FindFieldByLowercaseName(this, key);
+ if (result == NULL || !result->is_extension()) {
+ return NULL;
+ } else {
+ return result;
+ }
+}
+
+const FieldDescriptor*
+FileDescriptor::FindExtensionByCamelcaseName(const string& key) const {
+ const FieldDescriptor* result = tables_->FindFieldByCamelcaseName(this, key);
+ if (result == NULL || !result->is_extension()) {
+ return NULL;
+ } else {
+ return result;
+ }
+}
+
+const Descriptor::ExtensionRange*
+Descriptor::FindExtensionRangeContainingNumber(int number) const {
+ // Linear search should be fine because we don't expect a message to have
+ // more than a couple extension ranges.
+ for (int i = 0; i < extension_range_count(); i++) {
+ if (number >= extension_range(i)->start &&
+ number < extension_range(i)->end) {
+ return extension_range(i);
+ }
+ }
+ return NULL;
+}
+
+const Descriptor::ReservedRange*
+Descriptor::FindReservedRangeContainingNumber(int number) const {
+ // TODO(chrisn): Consider a non-linear search.
+ for (int i = 0; i < reserved_range_count(); i++) {
+ if (number >= reserved_range(i)->start &&
+ number < reserved_range(i)->end) {
+ return reserved_range(i);
+ }
+ }
+ return NULL;
+}
+
+// -------------------------------------------------------------------
+
+bool DescriptorPool::TryFindFileInFallbackDatabase(const string& name) const {
+ if (fallback_database_ == NULL) return false;
+
+ if (tables_->known_bad_files_.count(name) > 0) return false;
+
+ FileDescriptorProto file_proto;
+ if (!fallback_database_->FindFileByName(name, &file_proto) ||
+ BuildFileFromDatabase(file_proto) == NULL) {
+ tables_->known_bad_files_.insert(name);
+ return false;
+ }
+ return true;
+}
+
+bool DescriptorPool::IsSubSymbolOfBuiltType(const string& name) const {
+ string prefix = name;
+ for (;;) {
+ string::size_type dot_pos = prefix.find_last_of('.');
+ if (dot_pos == string::npos) {
+ break;
+ }
+ prefix = prefix.substr(0, dot_pos);
+ Symbol symbol = tables_->FindSymbol(prefix);
+ // If the symbol type is anything other than PACKAGE, then its complete
+ // definition is already known.
+ if (!symbol.IsNull() && symbol.type != Symbol::PACKAGE) {
+ return true;
+ }
+ }
+ if (underlay_ != NULL) {
+ // Check to see if any prefix of this symbol exists in the underlay.
+ return underlay_->IsSubSymbolOfBuiltType(name);
+ }
+ return false;
+}
+
+bool DescriptorPool::TryFindSymbolInFallbackDatabase(const string& name) const {
+ if (fallback_database_ == NULL) return false;
+
+ if (tables_->known_bad_symbols_.count(name) > 0) return false;
+
+ FileDescriptorProto file_proto;
+ if (// We skip looking in the fallback database if the name is a sub-symbol
+ // of any descriptor that already exists in the descriptor pool (except
+ // for package descriptors). This is valid because all symbols except
+ // for packages are defined in a single file, so if the symbol exists
+ // then we should already have its definition.
+ //
+ // The other reason to do this is to support "overriding" type
+ // definitions by merging two databases that define the same type. (Yes,
+ // people do this.) The main difficulty with making this work is that
+ // FindFileContainingSymbol() is allowed to return both false positives
+ // (e.g., SimpleDescriptorDatabase, UpgradedDescriptorDatabase) and false
+ // negatives (e.g. ProtoFileParser, SourceTreeDescriptorDatabase).
+ // When two such databases are merged, looking up a non-existent
+ // sub-symbol of a type that already exists in the descriptor pool can
+ // result in an attempt to load multiple definitions of the same type.
+ // The check below avoids this.
+ IsSubSymbolOfBuiltType(name)
+
+ // Look up file containing this symbol in fallback database.
+ || !fallback_database_->FindFileContainingSymbol(name, &file_proto)
+
+ // Check if we've already built this file. If so, it apparently doesn't
+ // contain the symbol we're looking for. Some DescriptorDatabases
+ // return false positives.
+ || tables_->FindFile(file_proto.name()) != NULL
+
+ // Build the file.
+ || BuildFileFromDatabase(file_proto) == NULL) {
+ tables_->known_bad_symbols_.insert(name);
+ return false;
+ }
+
+ return true;
+}
+
+bool DescriptorPool::TryFindExtensionInFallbackDatabase(
+ const Descriptor* containing_type, int field_number) const {
+ if (fallback_database_ == NULL) return false;
+
+ FileDescriptorProto file_proto;
+ if (!fallback_database_->FindFileContainingExtension(
+ containing_type->full_name(), field_number, &file_proto)) {
+ return false;
+ }
+
+ if (tables_->FindFile(file_proto.name()) != NULL) {
+ // We've already loaded this file, and it apparently doesn't contain the
+ // extension we're looking for. Some DescriptorDatabases return false
+ // positives.
+ return false;
+ }
+
+ if (BuildFileFromDatabase(file_proto) == NULL) {
+ return false;
+ }
+
+ return true;
+}
+
+// ===================================================================
+
+bool FieldDescriptor::is_map() const {
+ return type() == TYPE_MESSAGE && message_type()->options().map_entry();
+}
+
+string FieldDescriptor::DefaultValueAsString(bool quote_string_type) const {
+ GOOGLE_CHECK(has_default_value()) << "No default value";
+ switch (cpp_type()) {
+ case CPPTYPE_INT32:
+ return SimpleItoa(default_value_int32());
+ break;
+ case CPPTYPE_INT64:
+ return SimpleItoa(default_value_int64());
+ break;
+ case CPPTYPE_UINT32:
+ return SimpleItoa(default_value_uint32());
+ break;
+ case CPPTYPE_UINT64:
+ return SimpleItoa(default_value_uint64());
+ break;
+ case CPPTYPE_FLOAT:
+ return SimpleFtoa(default_value_float());
+ break;
+ case CPPTYPE_DOUBLE:
+ return SimpleDtoa(default_value_double());
+ break;
+ case CPPTYPE_BOOL:
+ return default_value_bool() ? "true" : "false";
+ break;
+ case CPPTYPE_STRING:
+ if (quote_string_type) {
+ return "\"" + CEscape(default_value_string()) + "\"";
+ } else {
+ if (type() == TYPE_BYTES) {
+ return CEscape(default_value_string());
+ } else {
+ return default_value_string();
+ }
+ }
+ break;
+ case CPPTYPE_ENUM:
+ return default_value_enum()->name();
+ break;
+ case CPPTYPE_MESSAGE:
+ GOOGLE_LOG(DFATAL) << "Messages can't have default values!";
+ break;
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here: failed to get default value as string";
+ return "";
+}
+
+// CopyTo methods ====================================================
+
+void FileDescriptor::CopyTo(FileDescriptorProto* proto) const {
+ proto->set_name(name());
+ if (!package().empty()) proto->set_package(package());
+ // TODO(liujisi): Also populate when syntax="proto2".
+ if (syntax() == SYNTAX_PROTO3) proto->set_syntax(SyntaxName(syntax()));
+
+ for (int i = 0; i < dependency_count(); i++) {
+ proto->add_dependency(dependency(i)->name());
+ }
+
+ for (int i = 0; i < public_dependency_count(); i++) {
+ proto->add_public_dependency(public_dependencies_[i]);
+ }
+
+ for (int i = 0; i < weak_dependency_count(); i++) {
+ proto->add_weak_dependency(weak_dependencies_[i]);
+ }
+
+ for (int i = 0; i < message_type_count(); i++) {
+ message_type(i)->CopyTo(proto->add_message_type());
+ }
+ for (int i = 0; i < enum_type_count(); i++) {
+ enum_type(i)->CopyTo(proto->add_enum_type());
+ }
+ for (int i = 0; i < service_count(); i++) {
+ service(i)->CopyTo(proto->add_service());
+ }
+ for (int i = 0; i < extension_count(); i++) {
+ extension(i)->CopyTo(proto->add_extension());
+ }
+
+ if (&options() != &FileOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+}
+
+void FileDescriptor::CopyJsonNameTo(FileDescriptorProto* proto) const {
+ if (message_type_count() != proto->message_type_size() ||
+ extension_count() != proto->extension_size()) {
+ GOOGLE_LOG(ERROR) << "Cannot copy json_name to a proto of a different size.";
+ return;
+ }
+ for (int i = 0; i < message_type_count(); i++) {
+ message_type(i)->CopyJsonNameTo(proto->mutable_message_type(i));
+ }
+ for (int i = 0; i < extension_count(); i++) {
+ extension(i)->CopyJsonNameTo(proto->mutable_extension(i));
+ }
+}
+
+void FileDescriptor::CopySourceCodeInfoTo(FileDescriptorProto* proto) const {
+ if (source_code_info_ &&
+ source_code_info_ != &SourceCodeInfo::default_instance()) {
+ proto->mutable_source_code_info()->CopyFrom(*source_code_info_);
+ }
+}
+
+void Descriptor::CopyTo(DescriptorProto* proto) const {
+ proto->set_name(name());
+
+ for (int i = 0; i < field_count(); i++) {
+ field(i)->CopyTo(proto->add_field());
+ }
+ for (int i = 0; i < oneof_decl_count(); i++) {
+ oneof_decl(i)->CopyTo(proto->add_oneof_decl());
+ }
+ for (int i = 0; i < nested_type_count(); i++) {
+ nested_type(i)->CopyTo(proto->add_nested_type());
+ }
+ for (int i = 0; i < enum_type_count(); i++) {
+ enum_type(i)->CopyTo(proto->add_enum_type());
+ }
+ for (int i = 0; i < extension_range_count(); i++) {
+ DescriptorProto::ExtensionRange* range = proto->add_extension_range();
+ range->set_start(extension_range(i)->start);
+ range->set_end(extension_range(i)->end);
+ }
+ for (int i = 0; i < extension_count(); i++) {
+ extension(i)->CopyTo(proto->add_extension());
+ }
+ for (int i = 0; i < reserved_range_count(); i++) {
+ DescriptorProto::ReservedRange* range = proto->add_reserved_range();
+ range->set_start(reserved_range(i)->start);
+ range->set_end(reserved_range(i)->end);
+ }
+ for (int i = 0; i < reserved_name_count(); i++) {
+ proto->add_reserved_name(reserved_name(i));
+ }
+
+ if (&options() != &MessageOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+}
+
+void Descriptor::CopyJsonNameTo(DescriptorProto* proto) const {
+ if (field_count() != proto->field_size() ||
+ nested_type_count() != proto->nested_type_size() ||
+ extension_count() != proto->extension_size()) {
+ GOOGLE_LOG(ERROR) << "Cannot copy json_name to a proto of a different size.";
+ return;
+ }
+ for (int i = 0; i < field_count(); i++) {
+ field(i)->CopyJsonNameTo(proto->mutable_field(i));
+ }
+ for (int i = 0; i < nested_type_count(); i++) {
+ nested_type(i)->CopyJsonNameTo(proto->mutable_nested_type(i));
+ }
+ for (int i = 0; i < extension_count(); i++) {
+ extension(i)->CopyJsonNameTo(proto->mutable_extension(i));
+ }
+}
+
+void FieldDescriptor::CopyTo(FieldDescriptorProto* proto) const {
+ proto->set_name(name());
+ proto->set_number(number());
+ if (has_json_name_) {
+ proto->set_json_name(json_name());
+ }
+
+ // Some compilers do not allow static_cast directly between two enum types,
+ // so we must cast to int first.
+ proto->set_label(static_cast<FieldDescriptorProto::Label>(
+ implicit_cast<int>(label())));
+ proto->set_type(static_cast<FieldDescriptorProto::Type>(
+ implicit_cast<int>(type())));
+
+ if (is_extension()) {
+ if (!containing_type()->is_unqualified_placeholder_) {
+ proto->set_extendee(".");
+ }
+ proto->mutable_extendee()->append(containing_type()->full_name());
+ }
+
+ if (cpp_type() == CPPTYPE_MESSAGE) {
+ if (message_type()->is_placeholder_) {
+ // We don't actually know if the type is a message type. It could be
+ // an enum.
+ proto->clear_type();
+ }
+
+ if (!message_type()->is_unqualified_placeholder_) {
+ proto->set_type_name(".");
+ }
+ proto->mutable_type_name()->append(message_type()->full_name());
+ } else if (cpp_type() == CPPTYPE_ENUM) {
+ if (!enum_type()->is_unqualified_placeholder_) {
+ proto->set_type_name(".");
+ }
+ proto->mutable_type_name()->append(enum_type()->full_name());
+ }
+
+ if (has_default_value()) {
+ proto->set_default_value(DefaultValueAsString(false));
+ }
+
+ if (containing_oneof() != NULL && !is_extension()) {
+ proto->set_oneof_index(containing_oneof()->index());
+ }
+
+ if (&options() != &FieldOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+}
+
+void FieldDescriptor::CopyJsonNameTo(FieldDescriptorProto* proto) const {
+ proto->set_json_name(json_name());
+}
+
+void OneofDescriptor::CopyTo(OneofDescriptorProto* proto) const {
+ proto->set_name(name());
+ if (&options() != &OneofOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+}
+
+void EnumDescriptor::CopyTo(EnumDescriptorProto* proto) const {
+ proto->set_name(name());
+
+ for (int i = 0; i < value_count(); i++) {
+ value(i)->CopyTo(proto->add_value());
+ }
+
+ if (&options() != &EnumOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+}
+
+void EnumValueDescriptor::CopyTo(EnumValueDescriptorProto* proto) const {
+ proto->set_name(name());
+ proto->set_number(number());
+
+ if (&options() != &EnumValueOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+}
+
+void ServiceDescriptor::CopyTo(ServiceDescriptorProto* proto) const {
+ proto->set_name(name());
+
+ for (int i = 0; i < method_count(); i++) {
+ method(i)->CopyTo(proto->add_method());
+ }
+
+ if (&options() != &ServiceOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+}
+
+void MethodDescriptor::CopyTo(MethodDescriptorProto* proto) const {
+ proto->set_name(name());
+
+ if (!input_type()->is_unqualified_placeholder_) {
+ proto->set_input_type(".");
+ }
+ proto->mutable_input_type()->append(input_type()->full_name());
+
+ if (!output_type()->is_unqualified_placeholder_) {
+ proto->set_output_type(".");
+ }
+ proto->mutable_output_type()->append(output_type()->full_name());
+
+ if (&options() != &MethodOptions::default_instance()) {
+ proto->mutable_options()->CopyFrom(options());
+ }
+
+ if (client_streaming_) {
+ proto->set_client_streaming(true);
+ }
+ if (server_streaming_) {
+ proto->set_server_streaming(true);
+ }
+}
+
+// DebugString methods ===============================================
+
+namespace {
+
+// Used by each of the option formatters.
+bool RetrieveOptions(int depth,
+ const Message &options,
+ vector<string> *option_entries) {
+ option_entries->clear();
+ const Reflection* reflection = options.GetReflection();
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(options, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ int count = 1;
+ bool repeated = false;
+ if (fields[i]->is_repeated()) {
+ count = reflection->FieldSize(options, fields[i]);
+ repeated = true;
+ }
+ for (int j = 0; j < count; j++) {
+ string fieldval;
+ if (fields[i]->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ string tmp;
+ TextFormat::Printer printer;
+ printer.SetInitialIndentLevel(depth + 1);
+ printer.PrintFieldValueToString(options, fields[i],
+ repeated ? j : -1, &tmp);
+ fieldval.append("{\n");
+ fieldval.append(tmp);
+ fieldval.append(depth * 2, ' ');
+ fieldval.append("}");
+ } else {
+ TextFormat::PrintFieldValueToString(options, fields[i],
+ repeated ? j : -1, &fieldval);
+ }
+ string name;
+ if (fields[i]->is_extension()) {
+ name = "(." + fields[i]->full_name() + ")";
+ } else {
+ name = fields[i]->name();
+ }
+ option_entries->push_back(name + " = " + fieldval);
+ }
+ }
+ return !option_entries->empty();
+}
+
+// Formats options that all appear together in brackets. Does not include
+// brackets.
+bool FormatBracketedOptions(int depth, const Message &options, string *output) {
+ vector<string> all_options;
+ if (RetrieveOptions(depth, options, &all_options)) {
+ output->append(Join(all_options, ", "));
+ }
+ return !all_options.empty();
+}
+
+// Formats options one per line
+bool FormatLineOptions(int depth, const Message &options, string *output) {
+ string prefix(depth * 2, ' ');
+ vector<string> all_options;
+ if (RetrieveOptions(depth, options, &all_options)) {
+ for (int i = 0; i < all_options.size(); i++) {
+ strings::SubstituteAndAppend(output, "$0option $1;\n",
+ prefix, all_options[i]);
+ }
+ }
+ return !all_options.empty();
+}
+
+class SourceLocationCommentPrinter {
+ public:
+ template<typename DescType>
+ SourceLocationCommentPrinter(const DescType* desc,
+ const string& prefix,
+ const DebugStringOptions& options)
+ : options_(options), prefix_(prefix) {
+ // Perform the SourceLocation lookup only if we're including user comments,
+ // because the lookup is fairly expensive.
+ have_source_loc_ = options.include_comments &&
+ desc->GetSourceLocation(&source_loc_);
+ }
+ SourceLocationCommentPrinter(const FileDescriptor* file,
+ const vector<int>& path,
+ const string& prefix,
+ const DebugStringOptions& options)
+ : options_(options), prefix_(prefix) {
+ // Perform the SourceLocation lookup only if we're including user comments,
+ // because the lookup is fairly expensive.
+ have_source_loc_ = options.include_comments &&
+ file->GetSourceLocation(path, &source_loc_);
+ }
+ void AddPreComment(string* output) {
+ if (have_source_loc_) {
+ // Detached leading comments.
+ for (int i = 0 ; i < source_loc_.leading_detached_comments.size(); ++i) {
+ *output += FormatComment(source_loc_.leading_detached_comments[i]);
+ *output += "\n";
+ }
+ // Attached leading comments.
+ if (!source_loc_.leading_comments.empty()) {
+ *output += FormatComment(source_loc_.leading_comments);
+ }
+ }
+ }
+ void AddPostComment(string* output) {
+ if (have_source_loc_ && source_loc_.trailing_comments.size() > 0) {
+ *output += FormatComment(source_loc_.trailing_comments);
+ }
+ }
+
+ // Format comment such that each line becomes a full-line C++-style comment in
+ // the DebugString() output.
+ string FormatComment(const string& comment_text) {
+ string stripped_comment = comment_text;
+ StripWhitespace(&stripped_comment);
+ vector<string> lines = Split(stripped_comment, "\n");
+ string output;
+ for (int i = 0; i < lines.size(); ++i) {
+ const string& line = lines[i];
+ strings::SubstituteAndAppend(&output, "$0// $1\n", prefix_, line);
+ }
+ return output;
+ }
+
+ private:
+
+ bool have_source_loc_;
+ SourceLocation source_loc_;
+ DebugStringOptions options_;
+ string prefix_;
+};
+
+} // anonymous namespace
+
+string FileDescriptor::DebugString() const {
+ DebugStringOptions options; // default options
+ return DebugStringWithOptions(options);
+}
+
+string FileDescriptor::DebugStringWithOptions(
+ const DebugStringOptions& debug_string_options) const {
+ string contents;
+ {
+ vector<int> path;
+ path.push_back(FileDescriptorProto::kSyntaxFieldNumber);
+ SourceLocationCommentPrinter syntax_comment(
+ this, path, "", debug_string_options);
+ syntax_comment.AddPreComment(&contents);
+ strings::SubstituteAndAppend(&contents, "syntax = \"$0\";\n\n",
+ SyntaxName(syntax()));
+ syntax_comment.AddPostComment(&contents);
+ }
+
+ SourceLocationCommentPrinter
+ comment_printer(this, "", debug_string_options);
+ comment_printer.AddPreComment(&contents);
+
+ set<int> public_dependencies;
+ set<int> weak_dependencies;
+ public_dependencies.insert(public_dependencies_,
+ public_dependencies_ + public_dependency_count_);
+ weak_dependencies.insert(weak_dependencies_,
+ weak_dependencies_ + weak_dependency_count_);
+
+ for (int i = 0; i < dependency_count(); i++) {
+ if (public_dependencies.count(i) > 0) {
+ strings::SubstituteAndAppend(&contents, "import public \"$0\";\n",
+ dependency(i)->name());
+ } else if (weak_dependencies.count(i) > 0) {
+ strings::SubstituteAndAppend(&contents, "import weak \"$0\";\n",
+ dependency(i)->name());
+ } else {
+ strings::SubstituteAndAppend(&contents, "import \"$0\";\n",
+ dependency(i)->name());
+ }
+ }
+
+ if (!package().empty()) {
+ vector<int> path;
+ path.push_back(FileDescriptorProto::kPackageFieldNumber);
+ SourceLocationCommentPrinter package_comment(
+ this, path, "", debug_string_options);
+ package_comment.AddPreComment(&contents);
+ strings::SubstituteAndAppend(&contents, "package $0;\n\n", package());
+ package_comment.AddPostComment(&contents);
+ }
+
+ if (FormatLineOptions(0, options(), &contents)) {
+ contents.append("\n"); // add some space if we had options
+ }
+
+ for (int i = 0; i < enum_type_count(); i++) {
+ enum_type(i)->DebugString(0, &contents, debug_string_options);
+ contents.append("\n");
+ }
+
+ // Find all the 'group' type extensions; we will not output their nested
+ // definitions (those will be done with their group field descriptor).
+ set<const Descriptor*> groups;
+ for (int i = 0; i < extension_count(); i++) {
+ if (extension(i)->type() == FieldDescriptor::TYPE_GROUP) {
+ groups.insert(extension(i)->message_type());
+ }
+ }
+
+ for (int i = 0; i < message_type_count(); i++) {
+ if (groups.count(message_type(i)) == 0) {
+ message_type(i)->DebugString(0, &contents, debug_string_options,
+ /* include_opening_clause */ true);
+ contents.append("\n");
+ }
+ }
+
+ for (int i = 0; i < service_count(); i++) {
+ service(i)->DebugString(&contents, debug_string_options);
+ contents.append("\n");
+ }
+
+ const Descriptor* containing_type = NULL;
+ for (int i = 0; i < extension_count(); i++) {
+ if (extension(i)->containing_type() != containing_type) {
+ if (i > 0) contents.append("}\n\n");
+ containing_type = extension(i)->containing_type();
+ strings::SubstituteAndAppend(&contents, "extend .$0 {\n",
+ containing_type->full_name());
+ }
+ extension(i)->DebugString(1, FieldDescriptor::PRINT_LABEL, &contents,
+ debug_string_options);
+ }
+ if (extension_count() > 0) contents.append("}\n\n");
+
+ comment_printer.AddPostComment(&contents);
+
+ return contents;
+}
+
+string Descriptor::DebugString() const {
+ DebugStringOptions options; // default options
+ return DebugStringWithOptions(options);
+}
+
+string Descriptor::DebugStringWithOptions(
+ const DebugStringOptions& options) const {
+ string contents;
+ DebugString(0, &contents, options, /* include_opening_clause */ true);
+ return contents;
+}
+
+void Descriptor::DebugString(int depth, string *contents,
+ const DebugStringOptions&
+ debug_string_options,
+ bool include_opening_clause) const {
+ if (options().map_entry()) {
+ // Do not generate debug string for auto-generated map-entry type.
+ return;
+ }
+ string prefix(depth * 2, ' ');
+ ++depth;
+
+ SourceLocationCommentPrinter
+ comment_printer(this, prefix, debug_string_options);
+ comment_printer.AddPreComment(contents);
+
+ if (include_opening_clause) {
+ strings::SubstituteAndAppend(contents, "$0message $1", prefix, name());
+ }
+ contents->append(" {\n");
+
+ FormatLineOptions(depth, options(), contents);
+
+ // Find all the 'group' types for fields and extensions; we will not output
+ // their nested definitions (those will be done with their group field
+ // descriptor).
+ set<const Descriptor*> groups;
+ for (int i = 0; i < field_count(); i++) {
+ if (field(i)->type() == FieldDescriptor::TYPE_GROUP) {
+ groups.insert(field(i)->message_type());
+ }
+ }
+ for (int i = 0; i < extension_count(); i++) {
+ if (extension(i)->type() == FieldDescriptor::TYPE_GROUP) {
+ groups.insert(extension(i)->message_type());
+ }
+ }
+
+ for (int i = 0; i < nested_type_count(); i++) {
+ if (groups.count(nested_type(i)) == 0) {
+ nested_type(i)->DebugString(depth, contents, debug_string_options,
+ /* include_opening_clause */ true);
+ }
+ }
+ for (int i = 0; i < enum_type_count(); i++) {
+ enum_type(i)->DebugString(depth, contents, debug_string_options);
+ }
+ for (int i = 0; i < field_count(); i++) {
+ if (field(i)->containing_oneof() == NULL) {
+ field(i)->DebugString(depth, FieldDescriptor::PRINT_LABEL, contents,
+ debug_string_options);
+ } else if (field(i)->containing_oneof()->field(0) == field(i)) {
+ // This is the first field in this oneof, so print the whole oneof.
+ field(i)->containing_oneof()->DebugString(depth, contents,
+ debug_string_options);
+ }
+ }
+
+ for (int i = 0; i < extension_range_count(); i++) {
+ strings::SubstituteAndAppend(contents, "$0 extensions $1 to $2;\n",
+ prefix,
+ extension_range(i)->start,
+ extension_range(i)->end - 1);
+ }
+
+ // Group extensions by what they extend, so they can be printed out together.
+ const Descriptor* containing_type = NULL;
+ for (int i = 0; i < extension_count(); i++) {
+ if (extension(i)->containing_type() != containing_type) {
+ if (i > 0) strings::SubstituteAndAppend(contents, "$0 }\n", prefix);
+ containing_type = extension(i)->containing_type();
+ strings::SubstituteAndAppend(contents, "$0 extend .$1 {\n",
+ prefix, containing_type->full_name());
+ }
+ extension(i)->DebugString(
+ depth + 1, FieldDescriptor::PRINT_LABEL, contents,
+ debug_string_options);
+ }
+ if (extension_count() > 0)
+ strings::SubstituteAndAppend(contents, "$0 }\n", prefix);
+
+ if (reserved_range_count() > 0) {
+ strings::SubstituteAndAppend(contents, "$0 reserved ", prefix);
+ for (int i = 0; i < reserved_range_count(); i++) {
+ const Descriptor::ReservedRange* range = reserved_range(i);
+ if (range->end == range->start + 1) {
+ strings::SubstituteAndAppend(contents, "$0, ", range->start);
+ } else {
+ strings::SubstituteAndAppend(contents, "$0 to $1, ",
+ range->start, range->end - 1);
+ }
+ }
+ contents->replace(contents->size() - 2, 2, ";\n");
+ }
+
+ if (reserved_name_count() > 0) {
+ strings::SubstituteAndAppend(contents, "$0 reserved ", prefix);
+ for (int i = 0; i < reserved_name_count(); i++) {
+ strings::SubstituteAndAppend(contents, "\"$0\", ",
+ CEscape(reserved_name(i)));
+ }
+ contents->replace(contents->size() - 2, 2, ";\n");
+ }
+
+ strings::SubstituteAndAppend(contents, "$0}\n", prefix);
+ comment_printer.AddPostComment(contents);
+}
+
+string FieldDescriptor::DebugString() const {
+ DebugStringOptions options; // default options
+ return DebugStringWithOptions(options);
+}
+
+string FieldDescriptor::DebugStringWithOptions(
+ const DebugStringOptions& debug_string_options) const {
+ string contents;
+ int depth = 0;
+ if (is_extension()) {
+ strings::SubstituteAndAppend(&contents, "extend .$0 {\n",
+ containing_type()->full_name());
+ depth = 1;
+ }
+ DebugString(depth, PRINT_LABEL, &contents, debug_string_options);
+ if (is_extension()) {
+ contents.append("}\n");
+ }
+ return contents;
+}
+
+// The field type string used in FieldDescriptor::DebugString()
+string FieldDescriptor::FieldTypeNameDebugString() const {
+ switch(type()) {
+ case TYPE_MESSAGE:
+ return "." + message_type()->full_name();
+ case TYPE_ENUM:
+ return "." + enum_type()->full_name();
+ default:
+ return kTypeToName[type()];
+ }
+}
+
+void FieldDescriptor::DebugString(int depth,
+ PrintLabelFlag print_label_flag,
+ string *contents,
+ const DebugStringOptions&
+ debug_string_options) const {
+ string prefix(depth * 2, ' ');
+ string field_type;
+
+ // Special case map fields.
+ if (is_map()) {
+ strings::SubstituteAndAppend(
+ &field_type, "map<$0, $1>",
+ message_type()->field(0)->FieldTypeNameDebugString(),
+ message_type()->field(1)->FieldTypeNameDebugString());
+ } else {
+ field_type = FieldTypeNameDebugString();
+ }
+
+ string label;
+ if (print_label_flag == PRINT_LABEL && !is_map()) {
+ label = kLabelToName[this->label()];
+ label.push_back(' ');
+ }
+
+ SourceLocationCommentPrinter
+ comment_printer(this, prefix, debug_string_options);
+ comment_printer.AddPreComment(contents);
+
+ strings::SubstituteAndAppend(contents, "$0$1$2 $3 = $4",
+ prefix,
+ label,
+ field_type,
+ type() == TYPE_GROUP ? message_type()->name() :
+ name(),
+ number());
+
+ bool bracketed = false;
+ if (has_default_value()) {
+ bracketed = true;
+ strings::SubstituteAndAppend(contents, " [default = $0",
+ DefaultValueAsString(true));
+ }
+
+ string formatted_options;
+ if (FormatBracketedOptions(depth, options(), &formatted_options)) {
+ contents->append(bracketed ? ", " : " [");
+ bracketed = true;
+ contents->append(formatted_options);
+ }
+
+ if (bracketed) {
+ contents->append("]");
+ }
+
+ if (type() == TYPE_GROUP) {
+ if (debug_string_options.elide_group_body) {
+ contents->append(" { ... };\n");
+ } else {
+ message_type()->DebugString(depth, contents, debug_string_options,
+ /* include_opening_clause */ false);
+ }
+ } else {
+ contents->append(";\n");
+ }
+
+ comment_printer.AddPostComment(contents);
+}
+
+string OneofDescriptor::DebugString() const {
+ DebugStringOptions options; // default values
+ return DebugStringWithOptions(options);
+}
+
+string OneofDescriptor::DebugStringWithOptions(
+ const DebugStringOptions& options) const {
+ string contents;
+ DebugString(0, &contents, options);
+ return contents;
+}
+
+void OneofDescriptor::DebugString(int depth, string* contents,
+ const DebugStringOptions&
+ debug_string_options) const {
+ string prefix(depth * 2, ' ');
+ ++depth;
+ SourceLocationCommentPrinter
+ comment_printer(this, prefix, debug_string_options);
+ comment_printer.AddPreComment(contents);
+ strings::SubstituteAndAppend(
+ contents, "$0 oneof $1 {", prefix, name());
+
+ FormatLineOptions(depth, options(), contents);
+
+ if (debug_string_options.elide_oneof_body) {
+ contents->append(" ... }\n");
+ } else {
+ for (int i = 0; i < field_count(); i++) {
+ field(i)->DebugString(depth, FieldDescriptor::OMIT_LABEL, contents,
+ debug_string_options);
+ }
+ strings::SubstituteAndAppend(contents, "$0}\n", prefix);
+ }
+ comment_printer.AddPostComment(contents);
+}
+
+string EnumDescriptor::DebugString() const {
+ DebugStringOptions options; // default values
+ return DebugStringWithOptions(options);
+}
+
+string EnumDescriptor::DebugStringWithOptions(
+ const DebugStringOptions& options) const {
+ string contents;
+ DebugString(0, &contents, options);
+ return contents;
+}
+
+void EnumDescriptor::DebugString(int depth, string *contents,
+ const DebugStringOptions&
+ debug_string_options) const {
+ string prefix(depth * 2, ' ');
+ ++depth;
+
+ SourceLocationCommentPrinter
+ comment_printer(this, prefix, debug_string_options);
+ comment_printer.AddPreComment(contents);
+
+ strings::SubstituteAndAppend(contents, "$0enum $1 {\n",
+ prefix, name());
+
+ FormatLineOptions(depth, options(), contents);
+
+ for (int i = 0; i < value_count(); i++) {
+ value(i)->DebugString(depth, contents, debug_string_options);
+ }
+ strings::SubstituteAndAppend(contents, "$0}\n", prefix);
+
+ comment_printer.AddPostComment(contents);
+}
+
+string EnumValueDescriptor::DebugString() const {
+ DebugStringOptions options; // default values
+ return DebugStringWithOptions(options);
+}
+
+string EnumValueDescriptor::DebugStringWithOptions(
+ const DebugStringOptions& options) const {
+ string contents;
+ DebugString(0, &contents, options);
+ return contents;
+}
+
+void EnumValueDescriptor::DebugString(int depth, string *contents,
+ const DebugStringOptions&
+ debug_string_options) const {
+ string prefix(depth * 2, ' ');
+
+ SourceLocationCommentPrinter
+ comment_printer(this, prefix, debug_string_options);
+ comment_printer.AddPreComment(contents);
+
+ strings::SubstituteAndAppend(contents, "$0$1 = $2",
+ prefix, name(), number());
+
+ string formatted_options;
+ if (FormatBracketedOptions(depth, options(), &formatted_options)) {
+ strings::SubstituteAndAppend(contents, " [$0]", formatted_options);
+ }
+ contents->append(";\n");
+
+ comment_printer.AddPostComment(contents);
+}
+
+string ServiceDescriptor::DebugString() const {
+ DebugStringOptions options; // default values
+ return DebugStringWithOptions(options);
+}
+
+string ServiceDescriptor::DebugStringWithOptions(
+ const DebugStringOptions& options) const {
+ string contents;
+ DebugString(&contents, options);
+ return contents;
+}
+
+void ServiceDescriptor::DebugString(string *contents,
+ const DebugStringOptions&
+ debug_string_options) const {
+ SourceLocationCommentPrinter
+ comment_printer(this, /* prefix */ "", debug_string_options);
+ comment_printer.AddPreComment(contents);
+
+ strings::SubstituteAndAppend(contents, "service $0 {\n", name());
+
+ FormatLineOptions(1, options(), contents);
+
+ for (int i = 0; i < method_count(); i++) {
+ method(i)->DebugString(1, contents, debug_string_options);
+ }
+
+ contents->append("}\n");
+
+ comment_printer.AddPostComment(contents);
+}
+
+string MethodDescriptor::DebugString() const {
+ DebugStringOptions options; // default values
+ return DebugStringWithOptions(options);
+}
+
+string MethodDescriptor::DebugStringWithOptions(
+ const DebugStringOptions& options) const {
+ string contents;
+ DebugString(0, &contents, options);
+ return contents;
+}
+
+void MethodDescriptor::DebugString(int depth, string *contents,
+ const DebugStringOptions&
+ debug_string_options) const {
+ string prefix(depth * 2, ' ');
+ ++depth;
+
+ SourceLocationCommentPrinter
+ comment_printer(this, prefix, debug_string_options);
+ comment_printer.AddPreComment(contents);
+
+ strings::SubstituteAndAppend(contents, "$0rpc $1($4.$2) returns ($5.$3)",
+ prefix, name(),
+ input_type()->full_name(),
+ output_type()->full_name(),
+ client_streaming() ? "stream " : "",
+ server_streaming() ? "stream " : "");
+
+ string formatted_options;
+ if (FormatLineOptions(depth, options(), &formatted_options)) {
+ strings::SubstituteAndAppend(contents, " {\n$0$1}\n",
+ formatted_options, prefix);
+ } else {
+ contents->append(";\n");
+ }
+
+ comment_printer.AddPostComment(contents);
+}
+
+
+// Location methods ===============================================
+
+bool FileDescriptor::GetSourceLocation(const vector<int>& path,
+ SourceLocation* out_location) const {
+ GOOGLE_CHECK_NOTNULL(out_location);
+ if (source_code_info_) {
+ if (const SourceCodeInfo_Location* loc =
+ tables_->GetSourceLocation(path, source_code_info_)) {
+ const RepeatedField<int32>& span = loc->span();
+ if (span.size() == 3 || span.size() == 4) {
+ out_location->start_line = span.Get(0);
+ out_location->start_column = span.Get(1);
+ out_location->end_line = span.Get(span.size() == 3 ? 0 : 2);
+ out_location->end_column = span.Get(span.size() - 1);
+
+ out_location->leading_comments = loc->leading_comments();
+ out_location->trailing_comments = loc->trailing_comments();
+ out_location->leading_detached_comments.assign(
+ loc->leading_detached_comments().begin(),
+ loc->leading_detached_comments().end());
+ return true;
+ }
+ }
+ }
+ return false;
+}
+
+bool FileDescriptor::GetSourceLocation(SourceLocation* out_location) const {
+ vector<int> path; // empty path for root FileDescriptor
+ return GetSourceLocation(path, out_location);
+}
+
+bool FieldDescriptor::is_packed() const {
+ if (!is_packable()) return false;
+ if (file_->syntax() == FileDescriptor::SYNTAX_PROTO2) {
+ return (options_ != NULL) && options_->packed();
+ } else {
+ return options_ == NULL || !options_->has_packed() || options_->packed();
+ }
+}
+
+bool Descriptor::GetSourceLocation(SourceLocation* out_location) const {
+ vector<int> path;
+ GetLocationPath(&path);
+ return file()->GetSourceLocation(path, out_location);
+}
+
+bool FieldDescriptor::GetSourceLocation(SourceLocation* out_location) const {
+ vector<int> path;
+ GetLocationPath(&path);
+ return file()->GetSourceLocation(path, out_location);
+}
+
+bool OneofDescriptor::GetSourceLocation(SourceLocation* out_location) const {
+ vector<int> path;
+ GetLocationPath(&path);
+ return containing_type()->file()->GetSourceLocation(path, out_location);
+}
+
+bool EnumDescriptor::GetSourceLocation(SourceLocation* out_location) const {
+ vector<int> path;
+ GetLocationPath(&path);
+ return file()->GetSourceLocation(path, out_location);
+}
+
+bool MethodDescriptor::GetSourceLocation(SourceLocation* out_location) const {
+ vector<int> path;
+ GetLocationPath(&path);
+ return service()->file()->GetSourceLocation(path, out_location);
+}
+
+bool ServiceDescriptor::GetSourceLocation(SourceLocation* out_location) const {
+ vector<int> path;
+ GetLocationPath(&path);
+ return file()->GetSourceLocation(path, out_location);
+}
+
+bool EnumValueDescriptor::GetSourceLocation(
+ SourceLocation* out_location) const {
+ vector<int> path;
+ GetLocationPath(&path);
+ return type()->file()->GetSourceLocation(path, out_location);
+}
+
+void Descriptor::GetLocationPath(vector<int>* output) const {
+ if (containing_type()) {
+ containing_type()->GetLocationPath(output);
+ output->push_back(DescriptorProto::kNestedTypeFieldNumber);
+ output->push_back(index());
+ } else {
+ output->push_back(FileDescriptorProto::kMessageTypeFieldNumber);
+ output->push_back(index());
+ }
+}
+
+void FieldDescriptor::GetLocationPath(vector<int>* output) const {
+ if (is_extension()) {
+ if (extension_scope() == NULL) {
+ output->push_back(FileDescriptorProto::kExtensionFieldNumber);
+ output->push_back(index());
+ } else {
+ extension_scope()->GetLocationPath(output);
+ output->push_back(DescriptorProto::kExtensionFieldNumber);
+ output->push_back(index());
+ }
+ } else {
+ containing_type()->GetLocationPath(output);
+ output->push_back(DescriptorProto::kFieldFieldNumber);
+ output->push_back(index());
+ }
+}
+
+void OneofDescriptor::GetLocationPath(vector<int>* output) const {
+ containing_type()->GetLocationPath(output);
+ output->push_back(DescriptorProto::kOneofDeclFieldNumber);
+ output->push_back(index());
+}
+
+void EnumDescriptor::GetLocationPath(vector<int>* output) const {
+ if (containing_type()) {
+ containing_type()->GetLocationPath(output);
+ output->push_back(DescriptorProto::kEnumTypeFieldNumber);
+ output->push_back(index());
+ } else {
+ output->push_back(FileDescriptorProto::kEnumTypeFieldNumber);
+ output->push_back(index());
+ }
+}
+
+void EnumValueDescriptor::GetLocationPath(vector<int>* output) const {
+ type()->GetLocationPath(output);
+ output->push_back(EnumDescriptorProto::kValueFieldNumber);
+ output->push_back(index());
+}
+
+void ServiceDescriptor::GetLocationPath(vector<int>* output) const {
+ output->push_back(FileDescriptorProto::kServiceFieldNumber);
+ output->push_back(index());
+}
+
+void MethodDescriptor::GetLocationPath(vector<int>* output) const {
+ service()->GetLocationPath(output);
+ output->push_back(ServiceDescriptorProto::kMethodFieldNumber);
+ output->push_back(index());
+}
+
+// ===================================================================
+
+namespace {
+
+// Represents an options message to interpret. Extension names in the option
+// name are resolved relative to name_scope. element_name and orig_opt are
+// used only for error reporting (since the parser records locations against
+// pointers in the original options, not the mutable copy). The Message must be
+// one of the Options messages in descriptor.proto.
+struct OptionsToInterpret {
+ OptionsToInterpret(const string& ns,
+ const string& el,
+ const Message* orig_opt,
+ Message* opt)
+ : name_scope(ns),
+ element_name(el),
+ original_options(orig_opt),
+ options(opt) {
+ }
+ string name_scope;
+ string element_name;
+ const Message* original_options;
+ Message* options;
+};
+
+} // namespace
+
+class DescriptorBuilder {
+ public:
+ DescriptorBuilder(const DescriptorPool* pool,
+ DescriptorPool::Tables* tables,
+ DescriptorPool::ErrorCollector* error_collector);
+ ~DescriptorBuilder();
+
+ const FileDescriptor* BuildFile(const FileDescriptorProto& proto);
+
+ private:
+ friend class OptionInterpreter;
+
+ // Non-recursive part of BuildFile functionality.
+ const FileDescriptor* BuildFileImpl(const FileDescriptorProto& proto);
+
+ const DescriptorPool* pool_;
+ DescriptorPool::Tables* tables_; // for convenience
+ DescriptorPool::ErrorCollector* error_collector_;
+
+ // As we build descriptors we store copies of the options messages in
+ // them. We put pointers to those copies in this vector, as we build, so we
+ // can later (after cross-linking) interpret those options.
+ vector<OptionsToInterpret> options_to_interpret_;
+
+ bool had_errors_;
+ string filename_;
+ FileDescriptor* file_;
+ FileDescriptorTables* file_tables_;
+ set<const FileDescriptor*> dependencies_;
+
+ // unused_dependency_ is used to record the unused imported files.
+ // Note: public import is not considered.
+ set<const FileDescriptor*> unused_dependency_;
+
+ // If LookupSymbol() finds a symbol that is in a file which is not a declared
+ // dependency of this file, it will fail, but will set
+ // possible_undeclared_dependency_ to point at that file. This is only used
+ // by AddNotDefinedError() to report a more useful error message.
+ // possible_undeclared_dependency_name_ is the name of the symbol that was
+ // actually found in possible_undeclared_dependency_, which may be a parent
+ // of the symbol actually looked for.
+ const FileDescriptor* possible_undeclared_dependency_;
+ string possible_undeclared_dependency_name_;
+
+ // If LookupSymbol() could resolve a symbol which is not defined,
+ // record the resolved name. This is only used by AddNotDefinedError()
+ // to report a more useful error message.
+ string undefine_resolved_name_;
+
+ void AddError(const string& element_name,
+ const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const string& error);
+ void AddError(const string& element_name,
+ const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const char* error);
+ void AddRecursiveImportError(const FileDescriptorProto& proto, int from_here);
+ void AddTwiceListedError(const FileDescriptorProto& proto, int index);
+ void AddImportError(const FileDescriptorProto& proto, int index);
+
+ // Adds an error indicating that undefined_symbol was not defined. Must
+ // only be called after LookupSymbol() fails.
+ void AddNotDefinedError(
+ const string& element_name,
+ const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const string& undefined_symbol);
+
+ void AddWarning(const string& element_name, const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const string& error);
+
+ // Silly helper which determines if the given file is in the given package.
+ // I.e., either file->package() == package_name or file->package() is a
+ // nested package within package_name.
+ bool IsInPackage(const FileDescriptor* file, const string& package_name);
+
+ // Helper function which finds all public dependencies of the given file, and
+ // stores the them in the dependencies_ set in the builder.
+ void RecordPublicDependencies(const FileDescriptor* file);
+
+ // Like tables_->FindSymbol(), but additionally:
+ // - Search the pool's underlay if not found in tables_.
+ // - Insure that the resulting Symbol is from one of the file's declared
+ // dependencies.
+ Symbol FindSymbol(const string& name);
+
+ // Like FindSymbol() but does not require that the symbol is in one of the
+ // file's declared dependencies.
+ Symbol FindSymbolNotEnforcingDeps(const string& name);
+
+ // This implements the body of FindSymbolNotEnforcingDeps().
+ Symbol FindSymbolNotEnforcingDepsHelper(const DescriptorPool* pool,
+ const string& name);
+
+ // Like FindSymbol(), but looks up the name relative to some other symbol
+ // name. This first searches siblings of relative_to, then siblings of its
+ // parents, etc. For example, LookupSymbol("foo.bar", "baz.qux.corge") makes
+ // the following calls, returning the first non-null result:
+ // FindSymbol("baz.qux.foo.bar"), FindSymbol("baz.foo.bar"),
+ // FindSymbol("foo.bar"). If AllowUnknownDependencies() has been called
+ // on the DescriptorPool, this will generate a placeholder type if
+ // the name is not found (unless the name itself is malformed). The
+ // placeholder_type parameter indicates what kind of placeholder should be
+ // constructed in this case. The resolve_mode parameter determines whether
+ // any symbol is returned, or only symbols that are types. Note, however,
+ // that LookupSymbol may still return a non-type symbol in LOOKUP_TYPES mode,
+ // if it believes that's all it could refer to. The caller should always
+ // check that it receives the type of symbol it was expecting.
+ enum PlaceholderType {
+ PLACEHOLDER_MESSAGE,
+ PLACEHOLDER_ENUM,
+ PLACEHOLDER_EXTENDABLE_MESSAGE
+ };
+ enum ResolveMode {
+ LOOKUP_ALL, LOOKUP_TYPES
+ };
+ Symbol LookupSymbol(const string& name, const string& relative_to,
+ PlaceholderType placeholder_type = PLACEHOLDER_MESSAGE,
+ ResolveMode resolve_mode = LOOKUP_ALL);
+
+ // Like LookupSymbol() but will not return a placeholder even if
+ // AllowUnknownDependencies() has been used.
+ Symbol LookupSymbolNoPlaceholder(const string& name,
+ const string& relative_to,
+ ResolveMode resolve_mode = LOOKUP_ALL);
+
+ // Creates a placeholder type suitable for return from LookupSymbol(). May
+ // return kNullSymbol if the name is not a valid type name.
+ Symbol NewPlaceholder(const string& name, PlaceholderType placeholder_type);
+
+ // Creates a placeholder file. Never returns NULL. This is used when an
+ // import is not found and AllowUnknownDependencies() is enabled.
+ FileDescriptor* NewPlaceholderFile(const string& name);
+
+ // Calls tables_->AddSymbol() and records an error if it fails. Returns
+ // true if successful or false if failed, though most callers can ignore
+ // the return value since an error has already been recorded.
+ bool AddSymbol(const string& full_name,
+ const void* parent, const string& name,
+ const Message& proto, Symbol symbol);
+
+ // Like AddSymbol(), but succeeds if the symbol is already defined as long
+ // as the existing definition is also a package (because it's OK to define
+ // the same package in two different files). Also adds all parents of the
+ // packgae to the symbol table (e.g. AddPackage("foo.bar", ...) will add
+ // "foo.bar" and "foo" to the table).
+ void AddPackage(const string& name, const Message& proto,
+ const FileDescriptor* file);
+
+ // Checks that the symbol name contains only alphanumeric characters and
+ // underscores. Records an error otherwise.
+ void ValidateSymbolName(const string& name, const string& full_name,
+ const Message& proto);
+
+ // Like ValidateSymbolName(), but the name is allowed to contain periods and
+ // an error is indicated by returning false (not recording the error).
+ bool ValidateQualifiedName(const string& name);
+
+ // Used by BUILD_ARRAY macro (below) to avoid having to have the type
+ // specified as a macro parameter.
+ template <typename Type>
+ inline void AllocateArray(int size, Type** output) {
+ *output = tables_->AllocateArray<Type>(size);
+ }
+
+ // Allocates a copy of orig_options in tables_ and stores it in the
+ // descriptor. Remembers its uninterpreted options, to be interpreted
+ // later. DescriptorT must be one of the Descriptor messages from
+ // descriptor.proto.
+ template<class DescriptorT> void AllocateOptions(
+ const typename DescriptorT::OptionsType& orig_options,
+ DescriptorT* descriptor);
+ // Specialization for FileOptions.
+ void AllocateOptions(const FileOptions& orig_options,
+ FileDescriptor* descriptor);
+
+ // Implementation for AllocateOptions(). Don't call this directly.
+ template<class DescriptorT> void AllocateOptionsImpl(
+ const string& name_scope,
+ const string& element_name,
+ const typename DescriptorT::OptionsType& orig_options,
+ DescriptorT* descriptor);
+
+ // These methods all have the same signature for the sake of the BUILD_ARRAY
+ // macro, below.
+ void BuildMessage(const DescriptorProto& proto,
+ const Descriptor* parent,
+ Descriptor* result);
+ void BuildFieldOrExtension(const FieldDescriptorProto& proto,
+ const Descriptor* parent,
+ FieldDescriptor* result,
+ bool is_extension);
+ void BuildField(const FieldDescriptorProto& proto,
+ const Descriptor* parent,
+ FieldDescriptor* result) {
+ BuildFieldOrExtension(proto, parent, result, false);
+ }
+ void BuildExtension(const FieldDescriptorProto& proto,
+ const Descriptor* parent,
+ FieldDescriptor* result) {
+ BuildFieldOrExtension(proto, parent, result, true);
+ }
+ void BuildExtensionRange(const DescriptorProto::ExtensionRange& proto,
+ const Descriptor* parent,
+ Descriptor::ExtensionRange* result);
+ void BuildReservedRange(const DescriptorProto::ReservedRange& proto,
+ const Descriptor* parent,
+ Descriptor::ReservedRange* result);
+ void BuildOneof(const OneofDescriptorProto& proto,
+ Descriptor* parent,
+ OneofDescriptor* result);
+ void BuildEnum(const EnumDescriptorProto& proto,
+ const Descriptor* parent,
+ EnumDescriptor* result);
+ void BuildEnumValue(const EnumValueDescriptorProto& proto,
+ const EnumDescriptor* parent,
+ EnumValueDescriptor* result);
+ void BuildService(const ServiceDescriptorProto& proto,
+ const void* dummy,
+ ServiceDescriptor* result);
+ void BuildMethod(const MethodDescriptorProto& proto,
+ const ServiceDescriptor* parent,
+ MethodDescriptor* result);
+
+ void LogUnusedDependency(const FileDescriptorProto& proto,
+ const FileDescriptor* result);
+
+ // Must be run only after building.
+ //
+ // NOTE: Options will not be available during cross-linking, as they
+ // have not yet been interpreted. Defer any handling of options to the
+ // Validate*Options methods.
+ void CrossLinkFile(FileDescriptor* file, const FileDescriptorProto& proto);
+ void CrossLinkMessage(Descriptor* message, const DescriptorProto& proto);
+ void CrossLinkField(FieldDescriptor* field,
+ const FieldDescriptorProto& proto);
+ void CrossLinkEnum(EnumDescriptor* enum_type,
+ const EnumDescriptorProto& proto);
+ void CrossLinkEnumValue(EnumValueDescriptor* enum_value,
+ const EnumValueDescriptorProto& proto);
+ void CrossLinkService(ServiceDescriptor* service,
+ const ServiceDescriptorProto& proto);
+ void CrossLinkMethod(MethodDescriptor* method,
+ const MethodDescriptorProto& proto);
+
+ // Must be run only after cross-linking.
+ void InterpretOptions();
+
+ // A helper class for interpreting options.
+ class OptionInterpreter {
+ public:
+ // Creates an interpreter that operates in the context of the pool of the
+ // specified builder, which must not be NULL. We don't take ownership of the
+ // builder.
+ explicit OptionInterpreter(DescriptorBuilder* builder);
+
+ ~OptionInterpreter();
+
+ // Interprets the uninterpreted options in the specified Options message.
+ // On error, calls AddError() on the underlying builder and returns false.
+ // Otherwise returns true.
+ bool InterpretOptions(OptionsToInterpret* options_to_interpret);
+
+ class AggregateOptionFinder;
+
+ private:
+ // Interprets uninterpreted_option_ on the specified message, which
+ // must be the mutable copy of the original options message to which
+ // uninterpreted_option_ belongs.
+ bool InterpretSingleOption(Message* options);
+
+ // Adds the uninterpreted_option to the given options message verbatim.
+ // Used when AllowUnknownDependencies() is in effect and we can't find
+ // the option's definition.
+ void AddWithoutInterpreting(const UninterpretedOption& uninterpreted_option,
+ Message* options);
+
+ // A recursive helper function that drills into the intermediate fields
+ // in unknown_fields to check if field innermost_field is set on the
+ // innermost message. Returns false and sets an error if so.
+ bool ExamineIfOptionIsSet(
+ vector<const FieldDescriptor*>::const_iterator intermediate_fields_iter,
+ vector<const FieldDescriptor*>::const_iterator intermediate_fields_end,
+ const FieldDescriptor* innermost_field, const string& debug_msg_name,
+ const UnknownFieldSet& unknown_fields);
+
+ // Validates the value for the option field of the currently interpreted
+ // option and then sets it on the unknown_field.
+ bool SetOptionValue(const FieldDescriptor* option_field,
+ UnknownFieldSet* unknown_fields);
+
+ // Parses an aggregate value for a CPPTYPE_MESSAGE option and
+ // saves it into *unknown_fields.
+ bool SetAggregateOption(const FieldDescriptor* option_field,
+ UnknownFieldSet* unknown_fields);
+
+ // Convenience functions to set an int field the right way, depending on
+ // its wire type (a single int CppType can represent multiple wire types).
+ void SetInt32(int number, int32 value, FieldDescriptor::Type type,
+ UnknownFieldSet* unknown_fields);
+ void SetInt64(int number, int64 value, FieldDescriptor::Type type,
+ UnknownFieldSet* unknown_fields);
+ void SetUInt32(int number, uint32 value, FieldDescriptor::Type type,
+ UnknownFieldSet* unknown_fields);
+ void SetUInt64(int number, uint64 value, FieldDescriptor::Type type,
+ UnknownFieldSet* unknown_fields);
+
+ // A helper function that adds an error at the specified location of the
+ // option we're currently interpreting, and returns false.
+ bool AddOptionError(DescriptorPool::ErrorCollector::ErrorLocation location,
+ const string& msg) {
+ builder_->AddError(options_to_interpret_->element_name,
+ *uninterpreted_option_, location, msg);
+ return false;
+ }
+
+ // A helper function that adds an error at the location of the option name
+ // and returns false.
+ bool AddNameError(const string& msg) {
+ return AddOptionError(DescriptorPool::ErrorCollector::OPTION_NAME, msg);
+ }
+
+ // A helper function that adds an error at the location of the option name
+ // and returns false.
+ bool AddValueError(const string& msg) {
+ return AddOptionError(DescriptorPool::ErrorCollector::OPTION_VALUE, msg);
+ }
+
+ // We interpret against this builder's pool. Is never NULL. We don't own
+ // this pointer.
+ DescriptorBuilder* builder_;
+
+ // The options we're currently interpreting, or NULL if we're not in a call
+ // to InterpretOptions.
+ const OptionsToInterpret* options_to_interpret_;
+
+ // The option we're currently interpreting within options_to_interpret_, or
+ // NULL if we're not in a call to InterpretOptions(). This points to a
+ // submessage of the original option, not the mutable copy. Therefore we
+ // can use it to find locations recorded by the parser.
+ const UninterpretedOption* uninterpreted_option_;
+
+ // Factory used to create the dynamic messages we need to parse
+ // any aggregate option values we encounter.
+ DynamicMessageFactory dynamic_factory_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(OptionInterpreter);
+ };
+
+ // Work-around for broken compilers: According to the C++ standard,
+ // OptionInterpreter should have access to the private members of any class
+ // which has declared DescriptorBuilder as a friend. Unfortunately some old
+ // versions of GCC and other compilers do not implement this correctly. So,
+ // we have to have these intermediate methods to provide access. We also
+ // redundantly declare OptionInterpreter a friend just to make things extra
+ // clear for these bad compilers.
+ friend class OptionInterpreter;
+ friend class OptionInterpreter::AggregateOptionFinder;
+
+ static inline bool get_allow_unknown(const DescriptorPool* pool) {
+ return pool->allow_unknown_;
+ }
+ static inline bool get_enforce_weak(const DescriptorPool* pool) {
+ return pool->enforce_weak_;
+ }
+ static inline bool get_is_placeholder(const Descriptor* descriptor) {
+ return descriptor->is_placeholder_;
+ }
+ static inline void assert_mutex_held(const DescriptorPool* pool) {
+ if (pool->mutex_ != NULL) {
+ pool->mutex_->AssertHeld();
+ }
+ }
+
+ // Must be run only after options have been interpreted.
+ //
+ // NOTE: Validation code must only reference the options in the mutable
+ // descriptors, which are the ones that have been interpreted. The const
+ // proto references are passed in only so they can be provided to calls to
+ // AddError(). Do not look at their options, which have not been interpreted.
+ void ValidateFileOptions(FileDescriptor* file,
+ const FileDescriptorProto& proto);
+ void ValidateMessageOptions(Descriptor* message,
+ const DescriptorProto& proto);
+ void ValidateFieldOptions(FieldDescriptor* field,
+ const FieldDescriptorProto& proto);
+ void ValidateEnumOptions(EnumDescriptor* enm,
+ const EnumDescriptorProto& proto);
+ void ValidateEnumValueOptions(EnumValueDescriptor* enum_value,
+ const EnumValueDescriptorProto& proto);
+ void ValidateServiceOptions(ServiceDescriptor* service,
+ const ServiceDescriptorProto& proto);
+ void ValidateMethodOptions(MethodDescriptor* method,
+ const MethodDescriptorProto& proto);
+ void ValidateProto3(FileDescriptor* file,
+ const FileDescriptorProto& proto);
+ void ValidateProto3Message(Descriptor* message,
+ const DescriptorProto& proto);
+ void ValidateProto3Field(FieldDescriptor* field,
+ const FieldDescriptorProto& proto);
+ void ValidateProto3Enum(EnumDescriptor* enm,
+ const EnumDescriptorProto& proto);
+
+ // Returns true if the map entry message is compatible with the
+ // auto-generated entry message from map fields syntax.
+ bool ValidateMapEntry(FieldDescriptor* field,
+ const FieldDescriptorProto& proto);
+
+ // Recursively detects naming conflicts with map entry types for a
+ // better error message.
+ void DetectMapConflicts(const Descriptor* message,
+ const DescriptorProto& proto);
+
+};
+
+const FileDescriptor* DescriptorPool::BuildFile(
+ const FileDescriptorProto& proto) {
+ GOOGLE_CHECK(fallback_database_ == NULL)
+ << "Cannot call BuildFile on a DescriptorPool that uses a "
+ "DescriptorDatabase. You must instead find a way to get your file "
+ "into the underlying database.";
+ GOOGLE_CHECK(mutex_ == NULL); // Implied by the above GOOGLE_CHECK.
+ tables_->known_bad_symbols_.clear();
+ tables_->known_bad_files_.clear();
+ return DescriptorBuilder(this, tables_.get(), NULL).BuildFile(proto);
+}
+
+const FileDescriptor* DescriptorPool::BuildFileCollectingErrors(
+ const FileDescriptorProto& proto,
+ ErrorCollector* error_collector) {
+ GOOGLE_CHECK(fallback_database_ == NULL)
+ << "Cannot call BuildFile on a DescriptorPool that uses a "
+ "DescriptorDatabase. You must instead find a way to get your file "
+ "into the underlying database.";
+ GOOGLE_CHECK(mutex_ == NULL); // Implied by the above GOOGLE_CHECK.
+ tables_->known_bad_symbols_.clear();
+ tables_->known_bad_files_.clear();
+ return DescriptorBuilder(this, tables_.get(),
+ error_collector).BuildFile(proto);
+}
+
+const FileDescriptor* DescriptorPool::BuildFileFromDatabase(
+ const FileDescriptorProto& proto) const {
+ mutex_->AssertHeld();
+ if (tables_->known_bad_files_.count(proto.name()) > 0) {
+ return NULL;
+ }
+ const FileDescriptor* result =
+ DescriptorBuilder(this, tables_.get(),
+ default_error_collector_).BuildFile(proto);
+ if (result == NULL) {
+ tables_->known_bad_files_.insert(proto.name());
+ }
+ return result;
+}
+
+DescriptorBuilder::DescriptorBuilder(
+ const DescriptorPool* pool,
+ DescriptorPool::Tables* tables,
+ DescriptorPool::ErrorCollector* error_collector)
+ : pool_(pool),
+ tables_(tables),
+ error_collector_(error_collector),
+ had_errors_(false),
+ possible_undeclared_dependency_(NULL),
+ undefine_resolved_name_("") {}
+
+DescriptorBuilder::~DescriptorBuilder() {}
+
+void DescriptorBuilder::AddError(
+ const string& element_name,
+ const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const string& error) {
+ if (error_collector_ == NULL) {
+ if (!had_errors_) {
+ GOOGLE_LOG(ERROR) << "Invalid proto descriptor for file \"" << filename_
+ << "\":";
+ }
+ GOOGLE_LOG(ERROR) << " " << element_name << ": " << error;
+ } else {
+ error_collector_->AddError(filename_, element_name,
+ &descriptor, location, error);
+ }
+ had_errors_ = true;
+}
+
+void DescriptorBuilder::AddError(
+ const string& element_name,
+ const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const char* error) {
+ AddError(element_name, descriptor, location, string(error));
+}
+
+void DescriptorBuilder::AddNotDefinedError(
+ const string& element_name,
+ const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const string& undefined_symbol) {
+ if (possible_undeclared_dependency_ == NULL &&
+ undefine_resolved_name_.empty()) {
+ AddError(element_name, descriptor, location,
+ "\"" + undefined_symbol + "\" is not defined.");
+ } else {
+ if (possible_undeclared_dependency_ != NULL) {
+ AddError(element_name, descriptor, location,
+ "\"" + possible_undeclared_dependency_name_ +
+ "\" seems to be defined in \"" +
+ possible_undeclared_dependency_->name() + "\", which is not "
+ "imported by \"" + filename_ + "\". To use it here, please "
+ "add the necessary import.");
+ }
+ if (!undefine_resolved_name_.empty()) {
+ AddError(element_name, descriptor, location,
+ "\"" + undefined_symbol + "\" is resolved to \"" +
+ undefine_resolved_name_ + "\", which is not defined. "
+ "The innermost scope is searched first in name resolution. "
+ "Consider using a leading '.'(i.e., \"."
+ + undefined_symbol +
+ "\") to start from the outermost scope.");
+ }
+ }
+}
+
+void DescriptorBuilder::AddWarning(
+ const string& element_name, const Message& descriptor,
+ DescriptorPool::ErrorCollector::ErrorLocation location,
+ const string& error) {
+ if (error_collector_ == NULL) {
+ GOOGLE_LOG(WARNING) << filename_ << " " << element_name << ": " << error;
+ } else {
+ error_collector_->AddWarning(filename_, element_name, &descriptor, location,
+ error);
+ }
+}
+
+bool DescriptorBuilder::IsInPackage(const FileDescriptor* file,
+ const string& package_name) {
+ return HasPrefixString(file->package(), package_name) &&
+ (file->package().size() == package_name.size() ||
+ file->package()[package_name.size()] == '.');
+}
+
+void DescriptorBuilder::RecordPublicDependencies(const FileDescriptor* file) {
+ if (file == NULL || !dependencies_.insert(file).second) return;
+ for (int i = 0; file != NULL && i < file->public_dependency_count(); i++) {
+ RecordPublicDependencies(file->public_dependency(i));
+ }
+}
+
+Symbol DescriptorBuilder::FindSymbolNotEnforcingDepsHelper(
+ const DescriptorPool* pool, const string& name) {
+ // If we are looking at an underlay, we must lock its mutex_, since we are
+ // accessing the underlay's tables_ directly.
+ MutexLockMaybe lock((pool == pool_) ? NULL : pool->mutex_);
+
+ Symbol result = pool->tables_->FindSymbol(name);
+ if (result.IsNull() && pool->underlay_ != NULL) {
+ // Symbol not found; check the underlay.
+ result = FindSymbolNotEnforcingDepsHelper(pool->underlay_, name);
+ }
+
+ if (result.IsNull()) {
+ // In theory, we shouldn't need to check fallback_database_ because the
+ // symbol should be in one of its file's direct dependencies, and we have
+ // already loaded those by the time we get here. But we check anyway so
+ // that we can generate better error message when dependencies are missing
+ // (i.e., "missing dependency" rather than "type is not defined").
+ if (pool->TryFindSymbolInFallbackDatabase(name)) {
+ result = pool->tables_->FindSymbol(name);
+ }
+ }
+
+ return result;
+}
+
+Symbol DescriptorBuilder::FindSymbolNotEnforcingDeps(const string& name) {
+ return FindSymbolNotEnforcingDepsHelper(pool_, name);
+}
+
+Symbol DescriptorBuilder::FindSymbol(const string& name) {
+ Symbol result = FindSymbolNotEnforcingDeps(name);
+
+ if (result.IsNull()) return result;
+
+ if (!pool_->enforce_dependencies_) {
+ // Hack for CompilerUpgrader.
+ return result;
+ }
+
+ // Only find symbols which were defined in this file or one of its
+ // dependencies.
+ const FileDescriptor* file = result.GetFile();
+ if (file == file_ || dependencies_.count(file) > 0) {
+ unused_dependency_.erase(file);
+ return result;
+ }
+
+ if (result.type == Symbol::PACKAGE) {
+ // Arg, this is overcomplicated. The symbol is a package name. It could
+ // be that the package was defined in multiple files. result.GetFile()
+ // returns the first file we saw that used this package. We've determined
+ // that that file is not a direct dependency of the file we are currently
+ // building, but it could be that some other file which *is* a direct
+ // dependency also defines the same package. We can't really rule out this
+ // symbol unless none of the dependencies define it.
+ if (IsInPackage(file_, name)) return result;
+ for (set<const FileDescriptor*>::const_iterator it = dependencies_.begin();
+ it != dependencies_.end(); ++it) {
+ // Note: A dependency may be NULL if it was not found or had errors.
+ if (*it != NULL && IsInPackage(*it, name)) return result;
+ }
+ }
+
+ possible_undeclared_dependency_ = file;
+ possible_undeclared_dependency_name_ = name;
+ return kNullSymbol;
+}
+
+Symbol DescriptorBuilder::LookupSymbolNoPlaceholder(
+ const string& name, const string& relative_to, ResolveMode resolve_mode) {
+ possible_undeclared_dependency_ = NULL;
+ undefine_resolved_name_.clear();
+
+ if (name.size() > 0 && name[0] == '.') {
+ // Fully-qualified name.
+ return FindSymbol(name.substr(1));
+ }
+
+ // If name is something like "Foo.Bar.baz", and symbols named "Foo" are
+ // defined in multiple parent scopes, we only want to find "Bar.baz" in the
+ // innermost one. E.g., the following should produce an error:
+ // message Bar { message Baz {} }
+ // message Foo {
+ // message Bar {
+ // }
+ // optional Bar.Baz baz = 1;
+ // }
+ // So, we look for just "Foo" first, then look for "Bar.baz" within it if
+ // found.
+ string::size_type name_dot_pos = name.find_first_of('.');
+ string first_part_of_name;
+ if (name_dot_pos == string::npos) {
+ first_part_of_name = name;
+ } else {
+ first_part_of_name = name.substr(0, name_dot_pos);
+ }
+
+ string scope_to_try(relative_to);
+
+ while (true) {
+ // Chop off the last component of the scope.
+ string::size_type dot_pos = scope_to_try.find_last_of('.');
+ if (dot_pos == string::npos) {
+ return FindSymbol(name);
+ } else {
+ scope_to_try.erase(dot_pos);
+ }
+
+ // Append ".first_part_of_name" and try to find.
+ string::size_type old_size = scope_to_try.size();
+ scope_to_try.append(1, '.');
+ scope_to_try.append(first_part_of_name);
+ Symbol result = FindSymbol(scope_to_try);
+ if (!result.IsNull()) {
+ if (first_part_of_name.size() < name.size()) {
+ // name is a compound symbol, of which we only found the first part.
+ // Now try to look up the rest of it.
+ if (result.IsAggregate()) {
+ scope_to_try.append(name, first_part_of_name.size(),
+ name.size() - first_part_of_name.size());
+ result = FindSymbol(scope_to_try);
+ if (result.IsNull()) {
+ undefine_resolved_name_ = scope_to_try;
+ }
+ return result;
+ } else {
+ // We found a symbol but it's not an aggregate. Continue the loop.
+ }
+ } else {
+ if (resolve_mode == LOOKUP_TYPES && !result.IsType()) {
+ // We found a symbol but it's not a type. Continue the loop.
+ } else {
+ return result;
+ }
+ }
+ }
+
+ // Not found. Remove the name so we can try again.
+ scope_to_try.erase(old_size);
+ }
+}
+
+Symbol DescriptorBuilder::LookupSymbol(
+ const string& name, const string& relative_to,
+ PlaceholderType placeholder_type, ResolveMode resolve_mode) {
+ Symbol result = LookupSymbolNoPlaceholder(
+ name, relative_to, resolve_mode);
+ if (result.IsNull() && pool_->allow_unknown_) {
+ // Not found, but AllowUnknownDependencies() is enabled. Return a
+ // placeholder instead.
+ result = NewPlaceholder(name, placeholder_type);
+ }
+ return result;
+}
+
+Symbol DescriptorBuilder::NewPlaceholder(const string& name,
+ PlaceholderType placeholder_type) {
+ // Compute names.
+ const string* placeholder_full_name;
+ const string* placeholder_name;
+ const string* placeholder_package;
+
+ if (!ValidateQualifiedName(name)) return kNullSymbol;
+ if (name[0] == '.') {
+ // Fully-qualified.
+ placeholder_full_name = tables_->AllocateString(name.substr(1));
+ } else {
+ placeholder_full_name = tables_->AllocateString(name);
+ }
+
+ string::size_type dotpos = placeholder_full_name->find_last_of('.');
+ if (dotpos != string::npos) {
+ placeholder_package = tables_->AllocateString(
+ placeholder_full_name->substr(0, dotpos));
+ placeholder_name = tables_->AllocateString(
+ placeholder_full_name->substr(dotpos + 1));
+ } else {
+ placeholder_package = &internal::GetEmptyString();
+ placeholder_name = placeholder_full_name;
+ }
+
+ // Create the placeholders.
+ FileDescriptor* placeholder_file = NewPlaceholderFile(
+ *placeholder_full_name + ".placeholder.proto");
+ placeholder_file->package_ = placeholder_package;
+
+ if (placeholder_type == PLACEHOLDER_ENUM) {
+ placeholder_file->enum_type_count_ = 1;
+ placeholder_file->enum_types_ =
+ tables_->AllocateArray<EnumDescriptor>(1);
+
+ EnumDescriptor* placeholder_enum = &placeholder_file->enum_types_[0];
+ memset(placeholder_enum, 0, sizeof(*placeholder_enum));
+
+ placeholder_enum->full_name_ = placeholder_full_name;
+ placeholder_enum->name_ = placeholder_name;
+ placeholder_enum->file_ = placeholder_file;
+ placeholder_enum->options_ = &EnumOptions::default_instance();
+ placeholder_enum->is_placeholder_ = true;
+ placeholder_enum->is_unqualified_placeholder_ = (name[0] != '.');
+
+ // Enums must have at least one value.
+ placeholder_enum->value_count_ = 1;
+ placeholder_enum->values_ = tables_->AllocateArray<EnumValueDescriptor>(1);
+
+ EnumValueDescriptor* placeholder_value = &placeholder_enum->values_[0];
+ memset(placeholder_value, 0, sizeof(*placeholder_value));
+
+ placeholder_value->name_ = tables_->AllocateString("PLACEHOLDER_VALUE");
+ // Note that enum value names are siblings of their type, not children.
+ placeholder_value->full_name_ =
+ placeholder_package->empty() ? placeholder_value->name_ :
+ tables_->AllocateString(*placeholder_package + ".PLACEHOLDER_VALUE");
+
+ placeholder_value->number_ = 0;
+ placeholder_value->type_ = placeholder_enum;
+ placeholder_value->options_ = &EnumValueOptions::default_instance();
+
+ return Symbol(placeholder_enum);
+ } else {
+ placeholder_file->message_type_count_ = 1;
+ placeholder_file->message_types_ =
+ tables_->AllocateArray<Descriptor>(1);
+
+ Descriptor* placeholder_message = &placeholder_file->message_types_[0];
+ memset(placeholder_message, 0, sizeof(*placeholder_message));
+
+ placeholder_message->full_name_ = placeholder_full_name;
+ placeholder_message->name_ = placeholder_name;
+ placeholder_message->file_ = placeholder_file;
+ placeholder_message->options_ = &MessageOptions::default_instance();
+ placeholder_message->is_placeholder_ = true;
+ placeholder_message->is_unqualified_placeholder_ = (name[0] != '.');
+
+ if (placeholder_type == PLACEHOLDER_EXTENDABLE_MESSAGE) {
+ placeholder_message->extension_range_count_ = 1;
+ placeholder_message->extension_ranges_ =
+ tables_->AllocateArray<Descriptor::ExtensionRange>(1);
+ placeholder_message->extension_ranges_->start = 1;
+ // kMaxNumber + 1 because ExtensionRange::end is exclusive.
+ placeholder_message->extension_ranges_->end =
+ FieldDescriptor::kMaxNumber + 1;
+ }
+
+ return Symbol(placeholder_message);
+ }
+}
+
+FileDescriptor* DescriptorBuilder::NewPlaceholderFile(
+ const string& name) {
+ FileDescriptor* placeholder = tables_->Allocate<FileDescriptor>();
+ memset(placeholder, 0, sizeof(*placeholder));
+
+ placeholder->name_ = tables_->AllocateString(name);
+ placeholder->package_ = &internal::GetEmptyString();
+ placeholder->pool_ = pool_;
+ placeholder->options_ = &FileOptions::default_instance();
+ placeholder->tables_ = &FileDescriptorTables::GetEmptyInstance();
+ placeholder->source_code_info_ = &SourceCodeInfo::default_instance();
+ placeholder->is_placeholder_ = true;
+ placeholder->syntax_ = FileDescriptor::SYNTAX_PROTO2;
+ // All other fields are zero or NULL.
+
+ return placeholder;
+}
+
+bool DescriptorBuilder::AddSymbol(
+ const string& full_name, const void* parent, const string& name,
+ const Message& proto, Symbol symbol) {
+ // If the caller passed NULL for the parent, the symbol is at file scope.
+ // Use its file as the parent instead.
+ if (parent == NULL) parent = file_;
+
+ if (tables_->AddSymbol(full_name, symbol)) {
+ if (!file_tables_->AddAliasUnderParent(parent, name, symbol)) {
+ GOOGLE_LOG(DFATAL) << "\"" << full_name << "\" not previously defined in "
+ "symbols_by_name_, but was defined in symbols_by_parent_; "
+ "this shouldn't be possible.";
+ return false;
+ }
+ return true;
+ } else {
+ const FileDescriptor* other_file = tables_->FindSymbol(full_name).GetFile();
+ if (other_file == file_) {
+ string::size_type dot_pos = full_name.find_last_of('.');
+ if (dot_pos == string::npos) {
+ AddError(full_name, proto, DescriptorPool::ErrorCollector::NAME,
+ "\"" + full_name + "\" is already defined.");
+ } else {
+ AddError(full_name, proto, DescriptorPool::ErrorCollector::NAME,
+ "\"" + full_name.substr(dot_pos + 1) +
+ "\" is already defined in \"" +
+ full_name.substr(0, dot_pos) + "\".");
+ }
+ } else {
+ // Symbol seems to have been defined in a different file.
+ AddError(full_name, proto, DescriptorPool::ErrorCollector::NAME,
+ "\"" + full_name + "\" is already defined in file \"" +
+ other_file->name() + "\".");
+ }
+ return false;
+ }
+}
+
+void DescriptorBuilder::AddPackage(
+ const string& name, const Message& proto, const FileDescriptor* file) {
+ if (tables_->AddSymbol(name, Symbol(file))) {
+ // Success. Also add parent package, if any.
+ string::size_type dot_pos = name.find_last_of('.');
+ if (dot_pos == string::npos) {
+ // No parents.
+ ValidateSymbolName(name, name, proto);
+ } else {
+ // Has parent.
+ string* parent_name = tables_->AllocateString(name.substr(0, dot_pos));
+ AddPackage(*parent_name, proto, file);
+ ValidateSymbolName(name.substr(dot_pos + 1), name, proto);
+ }
+ } else {
+ Symbol existing_symbol = tables_->FindSymbol(name);
+ // It's OK to redefine a package.
+ if (existing_symbol.type != Symbol::PACKAGE) {
+ // Symbol seems to have been defined in a different file.
+ AddError(name, proto, DescriptorPool::ErrorCollector::NAME,
+ "\"" + name + "\" is already defined (as something other than "
+ "a package) in file \"" + existing_symbol.GetFile()->name() +
+ "\".");
+ }
+ }
+}
+
+void DescriptorBuilder::ValidateSymbolName(
+ const string& name, const string& full_name, const Message& proto) {
+ if (name.empty()) {
+ AddError(full_name, proto, DescriptorPool::ErrorCollector::NAME,
+ "Missing name.");
+ } else {
+ for (int i = 0; i < name.size(); i++) {
+ // I don't trust isalnum() due to locales. :(
+ if ((name[i] < 'a' || 'z' < name[i]) &&
+ (name[i] < 'A' || 'Z' < name[i]) &&
+ (name[i] < '0' || '9' < name[i]) &&
+ (name[i] != '_')) {
+ AddError(full_name, proto, DescriptorPool::ErrorCollector::NAME,
+ "\"" + name + "\" is not a valid identifier.");
+ }
+ }
+ }
+}
+
+bool DescriptorBuilder::ValidateQualifiedName(const string& name) {
+ bool last_was_period = false;
+
+ for (int i = 0; i < name.size(); i++) {
+ // I don't trust isalnum() due to locales. :(
+ if (('a' <= name[i] && name[i] <= 'z') ||
+ ('A' <= name[i] && name[i] <= 'Z') ||
+ ('0' <= name[i] && name[i] <= '9') ||
+ (name[i] == '_')) {
+ last_was_period = false;
+ } else if (name[i] == '.') {
+ if (last_was_period) return false;
+ last_was_period = true;
+ } else {
+ return false;
+ }
+ }
+
+ return !name.empty() && !last_was_period;
+}
+
+// -------------------------------------------------------------------
+
+// This generic implementation is good for all descriptors except
+// FileDescriptor.
+template<class DescriptorT> void DescriptorBuilder::AllocateOptions(
+ const typename DescriptorT::OptionsType& orig_options,
+ DescriptorT* descriptor) {
+ AllocateOptionsImpl(descriptor->full_name(), descriptor->full_name(),
+ orig_options, descriptor);
+}
+
+// We specialize for FileDescriptor.
+void DescriptorBuilder::AllocateOptions(const FileOptions& orig_options,
+ FileDescriptor* descriptor) {
+ // We add the dummy token so that LookupSymbol does the right thing.
+ AllocateOptionsImpl(descriptor->package() + ".dummy", descriptor->name(),
+ orig_options, descriptor);
+}
+
+template<class DescriptorT> void DescriptorBuilder::AllocateOptionsImpl(
+ const string& name_scope,
+ const string& element_name,
+ const typename DescriptorT::OptionsType& orig_options,
+ DescriptorT* descriptor) {
+ // We need to use a dummy pointer to work around a bug in older versions of
+ // GCC. Otherwise, the following two lines could be replaced with:
+ // typename DescriptorT::OptionsType* options =
+ // tables_->AllocateMessage<typename DescriptorT::OptionsType>();
+ typename DescriptorT::OptionsType* const dummy = NULL;
+ typename DescriptorT::OptionsType* options = tables_->AllocateMessage(dummy);
+ // Avoid using MergeFrom()/CopyFrom() in this class to make it -fno-rtti
+ // friendly. Without RTTI, MergeFrom() and CopyFrom() will fallback to the
+ // reflection based method, which requires the Descriptor. However, we are in
+ // the middle of building the descriptors, thus the deadlock.
+ options->ParseFromString(orig_options.SerializeAsString());
+ descriptor->options_ = options;
+
+ // Don't add to options_to_interpret_ unless there were uninterpreted
+ // options. This not only avoids unnecessary work, but prevents a
+ // bootstrapping problem when building descriptors for descriptor.proto.
+ // descriptor.proto does not contain any uninterpreted options, but
+ // attempting to interpret options anyway will cause
+ // OptionsType::GetDescriptor() to be called which may then deadlock since
+ // we're still trying to build it.
+ if (options->uninterpreted_option_size() > 0) {
+ options_to_interpret_.push_back(
+ OptionsToInterpret(name_scope, element_name, &orig_options, options));
+ }
+}
+
+
+// A common pattern: We want to convert a repeated field in the descriptor
+// to an array of values, calling some method to build each value.
+#define BUILD_ARRAY(INPUT, OUTPUT, NAME, METHOD, PARENT) \
+ OUTPUT->NAME##_count_ = INPUT.NAME##_size(); \
+ AllocateArray(INPUT.NAME##_size(), &OUTPUT->NAME##s_); \
+ for (int i = 0; i < INPUT.NAME##_size(); i++) { \
+ METHOD(INPUT.NAME(i), PARENT, OUTPUT->NAME##s_ + i); \
+ }
+
+void DescriptorBuilder::AddRecursiveImportError(
+ const FileDescriptorProto& proto, int from_here) {
+ string error_message("File recursively imports itself: ");
+ for (int i = from_here; i < tables_->pending_files_.size(); i++) {
+ error_message.append(tables_->pending_files_[i]);
+ error_message.append(" -> ");
+ }
+ error_message.append(proto.name());
+
+ AddError(proto.name(), proto, DescriptorPool::ErrorCollector::OTHER,
+ error_message);
+}
+
+void DescriptorBuilder::AddTwiceListedError(const FileDescriptorProto& proto,
+ int index) {
+ AddError(proto.name(), proto, DescriptorPool::ErrorCollector::OTHER,
+ "Import \"" + proto.dependency(index) + "\" was listed twice.");
+}
+
+void DescriptorBuilder::AddImportError(const FileDescriptorProto& proto,
+ int index) {
+ string message;
+ if (pool_->fallback_database_ == NULL) {
+ message = "Import \"" + proto.dependency(index) +
+ "\" has not been loaded.";
+ } else {
+ message = "Import \"" + proto.dependency(index) +
+ "\" was not found or had errors.";
+ }
+ AddError(proto.name(), proto, DescriptorPool::ErrorCollector::OTHER, message);
+}
+
+static bool ExistingFileMatchesProto(const FileDescriptor* existing_file,
+ const FileDescriptorProto& proto) {
+ FileDescriptorProto existing_proto;
+ existing_file->CopyTo(&existing_proto);
+ // TODO(liujisi): Remove it when CopyTo supports copying syntax params when
+ // syntax="proto2".
+ if (existing_file->syntax() == FileDescriptor::SYNTAX_PROTO2 &&
+ proto.has_syntax()) {
+ existing_proto.set_syntax(
+ existing_file->SyntaxName(existing_file->syntax()));
+ }
+
+ return existing_proto.SerializeAsString() == proto.SerializeAsString();
+}
+
+const FileDescriptor* DescriptorBuilder::BuildFile(
+ const FileDescriptorProto& proto) {
+ filename_ = proto.name();
+
+ // Check if the file already exists and is identical to the one being built.
+ // Note: This only works if the input is canonical -- that is, it
+ // fully-qualifies all type names, has no UninterpretedOptions, etc.
+ // This is fine, because this idempotency "feature" really only exists to
+ // accommodate one hack in the proto1->proto2 migration layer.
+ const FileDescriptor* existing_file = tables_->FindFile(filename_);
+ if (existing_file != NULL) {
+ // File already in pool. Compare the existing one to the input.
+ if (ExistingFileMatchesProto(existing_file, proto)) {
+ // They're identical. Return the existing descriptor.
+ return existing_file;
+ }
+
+ // Not a match. The error will be detected and handled later.
+ }
+
+ // Check to see if this file is already on the pending files list.
+ // TODO(kenton): Allow recursive imports? It may not work with some
+ // (most?) programming languages. E.g., in C++, a forward declaration
+ // of a type is not sufficient to allow it to be used even in a
+ // generated header file due to inlining. This could perhaps be
+ // worked around using tricks involving inserting #include statements
+ // mid-file, but that's pretty ugly, and I'm pretty sure there are
+ // some languages out there that do not allow recursive dependencies
+ // at all.
+ for (int i = 0; i < tables_->pending_files_.size(); i++) {
+ if (tables_->pending_files_[i] == proto.name()) {
+ AddRecursiveImportError(proto, i);
+ return NULL;
+ }
+ }
+
+ // If we have a fallback_database_, attempt to load all dependencies now,
+ // before checkpointing tables_. This avoids confusion with recursive
+ // checkpoints.
+ if (pool_->fallback_database_ != NULL) {
+ tables_->pending_files_.push_back(proto.name());
+ for (int i = 0; i < proto.dependency_size(); i++) {
+ if (tables_->FindFile(proto.dependency(i)) == NULL &&
+ (pool_->underlay_ == NULL ||
+ pool_->underlay_->FindFileByName(proto.dependency(i)) == NULL)) {
+ // We don't care what this returns since we'll find out below anyway.
+ pool_->TryFindFileInFallbackDatabase(proto.dependency(i));
+ }
+ }
+ tables_->pending_files_.pop_back();
+ }
+ return BuildFileImpl(proto);
+}
+
+const FileDescriptor* DescriptorBuilder::BuildFileImpl(
+ const FileDescriptorProto& proto) {
+ // Checkpoint the tables so that we can roll back if something goes wrong.
+ tables_->AddCheckpoint();
+
+ FileDescriptor* result = tables_->Allocate<FileDescriptor>();
+ file_ = result;
+
+ result->is_placeholder_ = false;
+ if (proto.has_source_code_info()) {
+ SourceCodeInfo *info = tables_->AllocateMessage<SourceCodeInfo>();
+ info->CopyFrom(proto.source_code_info());
+ result->source_code_info_ = info;
+ } else {
+ result->source_code_info_ = &SourceCodeInfo::default_instance();
+ }
+
+ file_tables_ = tables_->AllocateFileTables();
+ file_->tables_ = file_tables_;
+
+ if (!proto.has_name()) {
+ AddError("", proto, DescriptorPool::ErrorCollector::OTHER,
+ "Missing field: FileDescriptorProto.name.");
+ }
+
+ // TODO(liujisi): Report error when the syntax is empty after all the protos
+ // have added the syntax statement.
+ if (proto.syntax().empty() || proto.syntax() == "proto2") {
+ file_->syntax_ = FileDescriptor::SYNTAX_PROTO2;
+ } else if (proto.syntax() == "proto3") {
+ file_->syntax_ = FileDescriptor::SYNTAX_PROTO3;
+ } else {
+ file_->syntax_ = FileDescriptor::SYNTAX_UNKNOWN;
+ AddError(proto.name(), proto, DescriptorPool::ErrorCollector::OTHER,
+ "Unrecognized syntax: " + proto.syntax());
+ }
+
+ result->name_ = tables_->AllocateString(proto.name());
+ if (proto.has_package()) {
+ result->package_ = tables_->AllocateString(proto.package());
+ } else {
+ // We cannot rely on proto.package() returning a valid string if
+ // proto.has_package() is false, because we might be running at static
+ // initialization time, in which case default values have not yet been
+ // initialized.
+ result->package_ = tables_->AllocateString("");
+ }
+ result->pool_ = pool_;
+
+ // Add to tables.
+ if (!tables_->AddFile(result)) {
+ AddError(proto.name(), proto, DescriptorPool::ErrorCollector::OTHER,
+ "A file with this name is already in the pool.");
+ // Bail out early so that if this is actually the exact same file, we
+ // don't end up reporting that every single symbol is already defined.
+ tables_->RollbackToLastCheckpoint();
+ return NULL;
+ }
+ if (!result->package().empty()) {
+ AddPackage(result->package(), proto, result);
+ }
+
+ // Make sure all dependencies are loaded.
+ set<string> seen_dependencies;
+ result->dependency_count_ = proto.dependency_size();
+ result->dependencies_ =
+ tables_->AllocateArray<const FileDescriptor*>(proto.dependency_size());
+ unused_dependency_.clear();
+ set<int> weak_deps;
+ for (int i = 0; i < proto.weak_dependency_size(); ++i) {
+ weak_deps.insert(proto.weak_dependency(i));
+ }
+ for (int i = 0; i < proto.dependency_size(); i++) {
+ if (!seen_dependencies.insert(proto.dependency(i)).second) {
+ AddTwiceListedError(proto, i);
+ }
+
+ const FileDescriptor* dependency = tables_->FindFile(proto.dependency(i));
+ if (dependency == NULL && pool_->underlay_ != NULL) {
+ dependency = pool_->underlay_->FindFileByName(proto.dependency(i));
+ }
+
+ if (dependency == NULL) {
+ if (pool_->allow_unknown_ ||
+ (!pool_->enforce_weak_ && weak_deps.find(i) != weak_deps.end())) {
+ dependency = NewPlaceholderFile(proto.dependency(i));
+ } else {
+ AddImportError(proto, i);
+ }
+ } else {
+ // Add to unused_dependency_ to track unused imported files.
+ // Note: do not track unused imported files for public import.
+ if (pool_->enforce_dependencies_ &&
+ (pool_->unused_import_track_files_.find(proto.name()) !=
+ pool_->unused_import_track_files_.end()) &&
+ (dependency->public_dependency_count() == 0)) {
+ unused_dependency_.insert(dependency);
+ }
+ }
+
+ result->dependencies_[i] = dependency;
+ }
+
+ // Check public dependencies.
+ int public_dependency_count = 0;
+ result->public_dependencies_ = tables_->AllocateArray<int>(
+ proto.public_dependency_size());
+ for (int i = 0; i < proto.public_dependency_size(); i++) {
+ // Only put valid public dependency indexes.
+ int index = proto.public_dependency(i);
+ if (index >= 0 && index < proto.dependency_size()) {
+ result->public_dependencies_[public_dependency_count++] = index;
+ // Do not track unused imported files for public import.
+ unused_dependency_.erase(result->dependency(index));
+ } else {
+ AddError(proto.name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "Invalid public dependency index.");
+ }
+ }
+ result->public_dependency_count_ = public_dependency_count;
+
+ // Build dependency set
+ dependencies_.clear();
+ for (int i = 0; i < result->dependency_count(); i++) {
+ RecordPublicDependencies(result->dependency(i));
+ }
+
+ // Check weak dependencies.
+ int weak_dependency_count = 0;
+ result->weak_dependencies_ = tables_->AllocateArray<int>(
+ proto.weak_dependency_size());
+ for (int i = 0; i < proto.weak_dependency_size(); i++) {
+ int index = proto.weak_dependency(i);
+ if (index >= 0 && index < proto.dependency_size()) {
+ result->weak_dependencies_[weak_dependency_count++] = index;
+ } else {
+ AddError(proto.name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "Invalid weak dependency index.");
+ }
+ }
+ result->weak_dependency_count_ = weak_dependency_count;
+
+ // Convert children.
+ BUILD_ARRAY(proto, result, message_type, BuildMessage , NULL);
+ BUILD_ARRAY(proto, result, enum_type , BuildEnum , NULL);
+ BUILD_ARRAY(proto, result, service , BuildService , NULL);
+ BUILD_ARRAY(proto, result, extension , BuildExtension, NULL);
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+ // Note that the following steps must occur in exactly the specified order.
+
+ // Cross-link.
+ CrossLinkFile(result, proto);
+
+ // Interpret any remaining uninterpreted options gathered into
+ // options_to_interpret_ during descriptor building. Cross-linking has made
+ // extension options known, so all interpretations should now succeed.
+ if (!had_errors_) {
+ OptionInterpreter option_interpreter(this);
+ for (vector<OptionsToInterpret>::iterator iter =
+ options_to_interpret_.begin();
+ iter != options_to_interpret_.end(); ++iter) {
+ option_interpreter.InterpretOptions(&(*iter));
+ }
+ options_to_interpret_.clear();
+ }
+
+ // Validate options.
+ if (!had_errors_) {
+ ValidateFileOptions(result, proto);
+ }
+
+ // Additional naming conflict check for map entry types. Only need to check
+ // this if there are already errors.
+ if (had_errors_) {
+ for (int i = 0; i < proto.message_type_size(); ++i) {
+ DetectMapConflicts(result->message_type(i), proto.message_type(i));
+ }
+ }
+
+
+ if (!unused_dependency_.empty()) {
+ LogUnusedDependency(proto, result);
+ }
+
+ if (had_errors_) {
+ tables_->RollbackToLastCheckpoint();
+ return NULL;
+ } else {
+ tables_->ClearLastCheckpoint();
+ return result;
+ }
+}
+
+void DescriptorBuilder::BuildMessage(const DescriptorProto& proto,
+ const Descriptor* parent,
+ Descriptor* result) {
+ const string& scope = (parent == NULL) ?
+ file_->package() : parent->full_name();
+ string* full_name = tables_->AllocateString(scope);
+ if (!full_name->empty()) full_name->append(1, '.');
+ full_name->append(proto.name());
+
+ ValidateSymbolName(proto.name(), *full_name, proto);
+
+ result->name_ = tables_->AllocateString(proto.name());
+ result->full_name_ = full_name;
+ result->file_ = file_;
+ result->containing_type_ = parent;
+ result->is_placeholder_ = false;
+ result->is_unqualified_placeholder_ = false;
+
+ // Build oneofs first so that fields and extension ranges can refer to them.
+ BUILD_ARRAY(proto, result, oneof_decl , BuildOneof , result);
+ BUILD_ARRAY(proto, result, field , BuildField , result);
+ BUILD_ARRAY(proto, result, nested_type , BuildMessage , result);
+ BUILD_ARRAY(proto, result, enum_type , BuildEnum , result);
+ BUILD_ARRAY(proto, result, extension_range, BuildExtensionRange, result);
+ BUILD_ARRAY(proto, result, extension , BuildExtension , result);
+ BUILD_ARRAY(proto, result, reserved_range , BuildReservedRange , result);
+
+ // Copy reserved names.
+ int reserved_name_count = proto.reserved_name_size();
+ result->reserved_name_count_ = reserved_name_count;
+ result->reserved_names_ =
+ tables_->AllocateArray<const string*>(reserved_name_count);
+ for (int i = 0; i < reserved_name_count; ++i) {
+ result->reserved_names_[i] =
+ tables_->AllocateString(proto.reserved_name(i));
+ }
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+ AddSymbol(result->full_name(), parent, result->name(),
+ proto, Symbol(result));
+
+ for (int i = 0; i < proto.reserved_range_size(); i++) {
+ const DescriptorProto_ReservedRange& range1 = proto.reserved_range(i);
+ for (int j = i + 1; j < proto.reserved_range_size(); j++) {
+ const DescriptorProto_ReservedRange& range2 = proto.reserved_range(j);
+ if (range1.end() > range2.start() && range2.end() > range1.start()) {
+ AddError(result->full_name(), proto.reserved_range(i),
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("Reserved range $0 to $1 overlaps with "
+ "already-defined range $2 to $3.",
+ range2.start(), range2.end() - 1,
+ range1.start(), range1.end() - 1));
+ }
+ }
+ }
+
+ hash_set<string> reserved_name_set;
+ for (int i = 0; i < proto.reserved_name_size(); i++) {
+ const string& name = proto.reserved_name(i);
+ if (reserved_name_set.find(name) == reserved_name_set.end()) {
+ reserved_name_set.insert(name);
+ } else {
+ AddError(name, proto, DescriptorPool::ErrorCollector::NAME,
+ strings::Substitute(
+ "Field name \"$0\" is reserved multiple times.",
+ name));
+ }
+ }
+
+ for (int i = 0; i < result->field_count(); i++) {
+ const FieldDescriptor* field = result->field(i);
+ for (int j = 0; j < result->extension_range_count(); j++) {
+ const Descriptor::ExtensionRange* range = result->extension_range(j);
+ if (range->start <= field->number() && field->number() < range->end) {
+ AddError(field->full_name(), proto.extension_range(j),
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute(
+ "Extension range $0 to $1 includes field \"$2\" ($3).",
+ range->start, range->end - 1,
+ field->name(), field->number()));
+ }
+ }
+ for (int j = 0; j < result->reserved_range_count(); j++) {
+ const Descriptor::ReservedRange* range = result->reserved_range(j);
+ if (range->start <= field->number() && field->number() < range->end) {
+ AddError(field->full_name(), proto.reserved_range(j),
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute(
+ "Field \"$0\" uses reserved number $1.",
+ field->name(), field->number()));
+ }
+ }
+ if (reserved_name_set.find(field->name()) != reserved_name_set.end()) {
+ AddError(field->full_name(), proto.field(i),
+ DescriptorPool::ErrorCollector::NAME,
+ strings::Substitute(
+ "Field name \"$0\" is reserved.", field->name()));
+ }
+ }
+
+ // Check that extension ranges don't overlap and don't include
+ // reserved field numbers.
+ for (int i = 0; i < result->extension_range_count(); i++) {
+ const Descriptor::ExtensionRange* range1 = result->extension_range(i);
+ for (int j = 0; j < result->reserved_range_count(); j++) {
+ const Descriptor::ReservedRange* range2 = result->reserved_range(j);
+ if (range1->end > range2->start && range2->end > range1->start) {
+ AddError(result->full_name(), proto.extension_range(j),
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("Extension range $0 to $1 overlaps with "
+ "reserved range $2 to $3.",
+ range1->start, range1->end - 1,
+ range2->start, range2->end - 1));
+ }
+ }
+ for (int j = i + 1; j < result->extension_range_count(); j++) {
+ const Descriptor::ExtensionRange* range2 = result->extension_range(j);
+ if (range1->end > range2->start && range2->end > range1->start) {
+ AddError(result->full_name(), proto.extension_range(j),
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("Extension range $0 to $1 overlaps with "
+ "already-defined range $2 to $3.",
+ range2->start, range2->end - 1,
+ range1->start, range1->end - 1));
+ }
+ }
+ }
+}
+
+
+void DescriptorBuilder::BuildFieldOrExtension(const FieldDescriptorProto& proto,
+ const Descriptor* parent,
+ FieldDescriptor* result,
+ bool is_extension) {
+ const string& scope = (parent == NULL) ?
+ file_->package() : parent->full_name();
+ string* full_name = tables_->AllocateString(scope);
+ if (!full_name->empty()) full_name->append(1, '.');
+ full_name->append(proto.name());
+
+ ValidateSymbolName(proto.name(), *full_name, proto);
+
+ result->name_ = tables_->AllocateString(proto.name());
+ result->full_name_ = full_name;
+ result->file_ = file_;
+ result->number_ = proto.number();
+ result->is_extension_ = is_extension;
+
+ // If .proto files follow the style guide then the name should already be
+ // lower-cased. If that's the case we can just reuse the string we already
+ // allocated rather than allocate a new one.
+ string lowercase_name(proto.name());
+ LowerString(&lowercase_name);
+ if (lowercase_name == proto.name()) {
+ result->lowercase_name_ = result->name_;
+ } else {
+ result->lowercase_name_ = tables_->AllocateString(lowercase_name);
+ }
+
+ // Don't bother with the above optimization for camel-case names since
+ // .proto files that follow the guide shouldn't be using names in this
+ // format, so the optimization wouldn't help much.
+ result->camelcase_name_ =
+ tables_->AllocateString(ToCamelCase(proto.name(),
+ /* lower_first = */ true));
+
+ if (proto.has_json_name()) {
+ result->has_json_name_ = true;
+ result->json_name_ = tables_->AllocateString(proto.json_name());
+ } else {
+ result->has_json_name_ = false;
+ result->json_name_ = result->camelcase_name_;
+ }
+
+ // Some compilers do not allow static_cast directly between two enum types,
+ // so we must cast to int first.
+ result->type_ = static_cast<FieldDescriptor::Type>(
+ implicit_cast<int>(proto.type()));
+ result->label_ = static_cast<FieldDescriptor::Label>(
+ implicit_cast<int>(proto.label()));
+
+ // An extension cannot have a required field (b/13365836).
+ if (result->is_extension_ &&
+ result->label_ == FieldDescriptor::LABEL_REQUIRED) {
+ AddError(result->full_name(), proto,
+ // Error location `TYPE`: we would really like to indicate
+ // `LABEL`, but the `ErrorLocation` enum has no entry for this, and
+ // we don't necessarily know about all implementations of the
+ // `ErrorCollector` interface to extend them to handle the new
+ // error location type properly.
+ DescriptorPool::ErrorCollector::TYPE,
+ "Message extensions cannot have required fields.");
+ }
+
+ // Some of these may be filled in when cross-linking.
+ result->containing_type_ = NULL;
+ result->extension_scope_ = NULL;
+ result->message_type_ = NULL;
+ result->enum_type_ = NULL;
+
+ result->has_default_value_ = proto.has_default_value();
+ if (proto.has_default_value() && result->is_repeated()) {
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::DEFAULT_VALUE,
+ "Repeated fields can't have default values.");
+ }
+
+ if (proto.has_type()) {
+ if (proto.has_default_value()) {
+ char* end_pos = NULL;
+ switch (result->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ result->default_value_int32_ =
+ strtol(proto.default_value().c_str(), &end_pos, 0);
+ break;
+ case FieldDescriptor::CPPTYPE_INT64:
+ result->default_value_int64_ =
+ strto64(proto.default_value().c_str(), &end_pos, 0);
+ break;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ result->default_value_uint32_ =
+ strtoul(proto.default_value().c_str(), &end_pos, 0);
+ break;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ result->default_value_uint64_ =
+ strtou64(proto.default_value().c_str(), &end_pos, 0);
+ break;
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ if (proto.default_value() == "inf") {
+ result->default_value_float_ = numeric_limits<float>::infinity();
+ } else if (proto.default_value() == "-inf") {
+ result->default_value_float_ = -numeric_limits<float>::infinity();
+ } else if (proto.default_value() == "nan") {
+ result->default_value_float_ = numeric_limits<float>::quiet_NaN();
+ } else {
+ result->default_value_float_ = io::SafeDoubleToFloat(
+ io::NoLocaleStrtod(proto.default_value().c_str(), &end_pos));
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ if (proto.default_value() == "inf") {
+ result->default_value_double_ = numeric_limits<double>::infinity();
+ } else if (proto.default_value() == "-inf") {
+ result->default_value_double_ = -numeric_limits<double>::infinity();
+ } else if (proto.default_value() == "nan") {
+ result->default_value_double_ = numeric_limits<double>::quiet_NaN();
+ } else {
+ result->default_value_double_ =
+ io::NoLocaleStrtod(proto.default_value().c_str(), &end_pos);
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ if (proto.default_value() == "true") {
+ result->default_value_bool_ = true;
+ } else if (proto.default_value() == "false") {
+ result->default_value_bool_ = false;
+ } else {
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::DEFAULT_VALUE,
+ "Boolean default must be true or false.");
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_ENUM:
+ // This will be filled in when cross-linking.
+ result->default_value_enum_ = NULL;
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (result->type() == FieldDescriptor::TYPE_BYTES) {
+ result->default_value_string_ = tables_->AllocateString(
+ UnescapeCEscapeString(proto.default_value()));
+ } else {
+ result->default_value_string_ =
+ tables_->AllocateString(proto.default_value());
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::DEFAULT_VALUE,
+ "Messages can't have default values.");
+ result->has_default_value_ = false;
+ break;
+ }
+
+ if (end_pos != NULL) {
+ // end_pos is only set non-NULL by the parsers for numeric types, above.
+ // This checks that the default was non-empty and had no extra junk
+ // after the end of the number.
+ if (proto.default_value().empty() || *end_pos != '\0') {
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::DEFAULT_VALUE,
+ "Couldn't parse default value \"" + proto.default_value() +
+ "\".");
+ }
+ }
+ } else {
+ // No explicit default value
+ switch (result->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ result->default_value_int32_ = 0;
+ break;
+ case FieldDescriptor::CPPTYPE_INT64:
+ result->default_value_int64_ = 0;
+ break;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ result->default_value_uint32_ = 0;
+ break;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ result->default_value_uint64_ = 0;
+ break;
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ result->default_value_float_ = 0.0f;
+ break;
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ result->default_value_double_ = 0.0;
+ break;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ result->default_value_bool_ = false;
+ break;
+ case FieldDescriptor::CPPTYPE_ENUM:
+ // This will be filled in when cross-linking.
+ result->default_value_enum_ = NULL;
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ result->default_value_string_ = &internal::GetEmptyString();
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ break;
+ }
+ }
+ }
+
+ if (result->number() <= 0) {
+ AddError(result->full_name(), proto, DescriptorPool::ErrorCollector::NUMBER,
+ "Field numbers must be positive integers.");
+ } else if (!is_extension && result->number() > FieldDescriptor::kMaxNumber) {
+ // Only validate that the number is within the valid field range if it is
+ // not an extension. Since extension numbers are validated with the
+ // extendee's valid set of extension numbers, and those are in turn
+ // validated against the max allowed number, the check is unnecessary for
+ // extension fields.
+ // This avoids cross-linking issues that arise when attempting to check if
+ // the extendee is a message_set_wire_format message, which has a higher max
+ // on extension numbers.
+ AddError(result->full_name(), proto, DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("Field numbers cannot be greater than $0.",
+ FieldDescriptor::kMaxNumber));
+ } else if (result->number() >= FieldDescriptor::kFirstReservedNumber &&
+ result->number() <= FieldDescriptor::kLastReservedNumber) {
+ AddError(result->full_name(), proto, DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute(
+ "Field numbers $0 through $1 are reserved for the protocol "
+ "buffer library implementation.",
+ FieldDescriptor::kFirstReservedNumber,
+ FieldDescriptor::kLastReservedNumber));
+ }
+
+ if (is_extension) {
+ if (!proto.has_extendee()) {
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::EXTENDEE,
+ "FieldDescriptorProto.extendee not set for extension field.");
+ }
+
+ result->extension_scope_ = parent;
+
+ if (proto.has_oneof_index()) {
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "FieldDescriptorProto.oneof_index should not be set for "
+ "extensions.");
+ }
+
+ // Fill in later (maybe).
+ result->containing_oneof_ = NULL;
+ } else {
+ if (proto.has_extendee()) {
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::EXTENDEE,
+ "FieldDescriptorProto.extendee set for non-extension field.");
+ }
+
+ result->containing_type_ = parent;
+
+ if (proto.has_oneof_index()) {
+ if (proto.oneof_index() < 0 ||
+ proto.oneof_index() >= parent->oneof_decl_count()) {
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ strings::Substitute("FieldDescriptorProto.oneof_index $0 is "
+ "out of range for type \"$1\".",
+ proto.oneof_index(),
+ parent->name()));
+ result->containing_oneof_ = NULL;
+ } else {
+ result->containing_oneof_ = parent->oneof_decl(proto.oneof_index());
+ }
+ } else {
+ result->containing_oneof_ = NULL;
+ }
+ }
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+
+ AddSymbol(result->full_name(), parent, result->name(),
+ proto, Symbol(result));
+}
+
+void DescriptorBuilder::BuildExtensionRange(
+ const DescriptorProto::ExtensionRange& proto,
+ const Descriptor* parent,
+ Descriptor::ExtensionRange* result) {
+ result->start = proto.start();
+ result->end = proto.end();
+ if (result->start <= 0) {
+ AddError(parent->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER,
+ "Extension numbers must be positive integers.");
+ }
+
+ // Checking of the upper bound of the extension range is deferred until after
+ // options interpreting. This allows messages with message_set_wire_format to
+ // have extensions beyond FieldDescriptor::kMaxNumber, since the extension
+ // numbers are actually used as int32s in the message_set_wire_format.
+
+ if (result->start >= result->end) {
+ AddError(parent->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER,
+ "Extension range end number must be greater than start number.");
+ }
+}
+
+void DescriptorBuilder::BuildReservedRange(
+ const DescriptorProto::ReservedRange& proto,
+ const Descriptor* parent,
+ Descriptor::ReservedRange* result) {
+ result->start = proto.start();
+ result->end = proto.end();
+ if (result->start <= 0) {
+ AddError(parent->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER,
+ "Reserved numbers must be positive integers.");
+ }
+}
+
+void DescriptorBuilder::BuildOneof(const OneofDescriptorProto& proto,
+ Descriptor* parent,
+ OneofDescriptor* result) {
+ string* full_name = tables_->AllocateString(parent->full_name());
+ full_name->append(1, '.');
+ full_name->append(proto.name());
+
+ ValidateSymbolName(proto.name(), *full_name, proto);
+
+ result->name_ = tables_->AllocateString(proto.name());
+ result->full_name_ = full_name;
+
+ result->containing_type_ = parent;
+
+ // We need to fill these in later.
+ result->field_count_ = 0;
+ result->fields_ = NULL;
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+ AddSymbol(result->full_name(), parent, result->name(),
+ proto, Symbol(result));
+}
+
+void DescriptorBuilder::BuildEnum(const EnumDescriptorProto& proto,
+ const Descriptor* parent,
+ EnumDescriptor* result) {
+ const string& scope = (parent == NULL) ?
+ file_->package() : parent->full_name();
+ string* full_name = tables_->AllocateString(scope);
+ if (!full_name->empty()) full_name->append(1, '.');
+ full_name->append(proto.name());
+
+ ValidateSymbolName(proto.name(), *full_name, proto);
+
+ result->name_ = tables_->AllocateString(proto.name());
+ result->full_name_ = full_name;
+ result->file_ = file_;
+ result->containing_type_ = parent;
+ result->is_placeholder_ = false;
+ result->is_unqualified_placeholder_ = false;
+
+ if (proto.value_size() == 0) {
+ // We cannot allow enums with no values because this would mean there
+ // would be no valid default value for fields of this type.
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Enums must contain at least one value.");
+ }
+
+ BUILD_ARRAY(proto, result, value, BuildEnumValue, result);
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+ AddSymbol(result->full_name(), parent, result->name(),
+ proto, Symbol(result));
+}
+
+void DescriptorBuilder::BuildEnumValue(const EnumValueDescriptorProto& proto,
+ const EnumDescriptor* parent,
+ EnumValueDescriptor* result) {
+ result->name_ = tables_->AllocateString(proto.name());
+ result->number_ = proto.number();
+ result->type_ = parent;
+
+ // Note: full_name for enum values is a sibling to the parent's name, not a
+ // child of it.
+ string* full_name = tables_->AllocateString(*parent->full_name_);
+ full_name->resize(full_name->size() - parent->name_->size());
+ full_name->append(*result->name_);
+ result->full_name_ = full_name;
+
+ ValidateSymbolName(proto.name(), *full_name, proto);
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+ // Again, enum values are weird because we makes them appear as siblings
+ // of the enum type instead of children of it. So, we use
+ // parent->containing_type() as the value's parent.
+ bool added_to_outer_scope =
+ AddSymbol(result->full_name(), parent->containing_type(), result->name(),
+ proto, Symbol(result));
+
+ // However, we also want to be able to search for values within a single
+ // enum type, so we add it as a child of the enum type itself, too.
+ // Note: This could fail, but if it does, the error has already been
+ // reported by the above AddSymbol() call, so we ignore the return code.
+ bool added_to_inner_scope =
+ file_tables_->AddAliasUnderParent(parent, result->name(), Symbol(result));
+
+ if (added_to_inner_scope && !added_to_outer_scope) {
+ // This value did not conflict with any values defined in the same enum,
+ // but it did conflict with some other symbol defined in the enum type's
+ // scope. Let's print an additional error to explain this.
+ string outer_scope;
+ if (parent->containing_type() == NULL) {
+ outer_scope = file_->package();
+ } else {
+ outer_scope = parent->containing_type()->full_name();
+ }
+
+ if (outer_scope.empty()) {
+ outer_scope = "the global scope";
+ } else {
+ outer_scope = "\"" + outer_scope + "\"";
+ }
+
+ AddError(result->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Note that enum values use C++ scoping rules, meaning that "
+ "enum values are siblings of their type, not children of it. "
+ "Therefore, \"" + result->name() + "\" must be unique within "
+ + outer_scope + ", not just within \"" + parent->name() + "\".");
+ }
+
+ // An enum is allowed to define two numbers that refer to the same value.
+ // FindValueByNumber() should return the first such value, so we simply
+ // ignore AddEnumValueByNumber()'s return code.
+ file_tables_->AddEnumValueByNumber(result);
+}
+
+void DescriptorBuilder::BuildService(const ServiceDescriptorProto& proto,
+ const void* /* dummy */,
+ ServiceDescriptor* result) {
+ string* full_name = tables_->AllocateString(file_->package());
+ if (!full_name->empty()) full_name->append(1, '.');
+ full_name->append(proto.name());
+
+ ValidateSymbolName(proto.name(), *full_name, proto);
+
+ result->name_ = tables_->AllocateString(proto.name());
+ result->full_name_ = full_name;
+ result->file_ = file_;
+
+ BUILD_ARRAY(proto, result, method, BuildMethod, result);
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+ AddSymbol(result->full_name(), NULL, result->name(),
+ proto, Symbol(result));
+}
+
+void DescriptorBuilder::BuildMethod(const MethodDescriptorProto& proto,
+ const ServiceDescriptor* parent,
+ MethodDescriptor* result) {
+ result->name_ = tables_->AllocateString(proto.name());
+ result->service_ = parent;
+
+ string* full_name = tables_->AllocateString(parent->full_name());
+ full_name->append(1, '.');
+ full_name->append(*result->name_);
+ result->full_name_ = full_name;
+
+ ValidateSymbolName(proto.name(), *full_name, proto);
+
+ // These will be filled in when cross-linking.
+ result->input_type_ = NULL;
+ result->output_type_ = NULL;
+
+ // Copy options.
+ if (!proto.has_options()) {
+ result->options_ = NULL; // Will set to default_instance later.
+ } else {
+ AllocateOptions(proto.options(), result);
+ }
+
+ result->client_streaming_ = proto.client_streaming();
+ result->server_streaming_ = proto.server_streaming();
+
+ AddSymbol(result->full_name(), parent, result->name(),
+ proto, Symbol(result));
+}
+
+#undef BUILD_ARRAY
+
+// -------------------------------------------------------------------
+
+void DescriptorBuilder::CrossLinkFile(
+ FileDescriptor* file, const FileDescriptorProto& proto) {
+ if (file->options_ == NULL) {
+ file->options_ = &FileOptions::default_instance();
+ }
+
+ for (int i = 0; i < file->message_type_count(); i++) {
+ CrossLinkMessage(&file->message_types_[i], proto.message_type(i));
+ }
+
+ for (int i = 0; i < file->extension_count(); i++) {
+ CrossLinkField(&file->extensions_[i], proto.extension(i));
+ }
+
+ for (int i = 0; i < file->enum_type_count(); i++) {
+ CrossLinkEnum(&file->enum_types_[i], proto.enum_type(i));
+ }
+
+ for (int i = 0; i < file->service_count(); i++) {
+ CrossLinkService(&file->services_[i], proto.service(i));
+ }
+}
+
+void DescriptorBuilder::CrossLinkMessage(
+ Descriptor* message, const DescriptorProto& proto) {
+ if (message->options_ == NULL) {
+ message->options_ = &MessageOptions::default_instance();
+ }
+
+ for (int i = 0; i < message->nested_type_count(); i++) {
+ CrossLinkMessage(&message->nested_types_[i], proto.nested_type(i));
+ }
+
+ for (int i = 0; i < message->enum_type_count(); i++) {
+ CrossLinkEnum(&message->enum_types_[i], proto.enum_type(i));
+ }
+
+ for (int i = 0; i < message->field_count(); i++) {
+ CrossLinkField(&message->fields_[i], proto.field(i));
+ }
+
+ for (int i = 0; i < message->extension_count(); i++) {
+ CrossLinkField(&message->extensions_[i], proto.extension(i));
+ }
+
+ // Set up field array for each oneof.
+
+ // First count the number of fields per oneof.
+ for (int i = 0; i < message->field_count(); i++) {
+ const OneofDescriptor* oneof_decl = message->field(i)->containing_oneof();
+ if (oneof_decl != NULL) {
+ // Make sure fields belonging to the same oneof are defined consecutively.
+ // This enables optimizations in codegens and reflection libraries to
+ // skip fields in the oneof group, as only one of the field can be set.
+ // Note that field_count() returns how many fields in this oneof we have
+ // seen so far. field_count() > 0 guarantees that i > 0, so field(i-1) is
+ // safe.
+ if (oneof_decl->field_count() > 0 &&
+ message->field(i - 1)->containing_oneof() != oneof_decl) {
+ AddError(
+ message->full_name() + "." + message->field(i - 1)->name(),
+ proto.field(i - 1), DescriptorPool::ErrorCollector::OTHER,
+ strings::Substitute(
+ "Fields in the same oneof must be defined consecutively. "
+ "\"$0\" cannot be defined before the completion of the "
+ "\"$1\" oneof definition.",
+ message->field(i - 1)->name(), oneof_decl->name()));
+ }
+ // Must go through oneof_decls_ array to get a non-const version of the
+ // OneofDescriptor.
+ ++message->oneof_decls_[oneof_decl->index()].field_count_;
+ }
+ }
+
+ // Then allocate the arrays.
+ for (int i = 0; i < message->oneof_decl_count(); i++) {
+ OneofDescriptor* oneof_decl = &message->oneof_decls_[i];
+
+ if (oneof_decl->field_count() == 0) {
+ AddError(message->full_name() + "." + oneof_decl->name(),
+ proto.oneof_decl(i),
+ DescriptorPool::ErrorCollector::NAME,
+ "Oneof must have at least one field.");
+ }
+
+ oneof_decl->fields_ =
+ tables_->AllocateArray<const FieldDescriptor*>(oneof_decl->field_count_);
+ oneof_decl->field_count_ = 0;
+
+ if (oneof_decl->options_ == NULL) {
+ oneof_decl->options_ = &OneofOptions::default_instance();
+ }
+ }
+
+ // Then fill them in.
+ for (int i = 0; i < message->field_count(); i++) {
+ const OneofDescriptor* oneof_decl = message->field(i)->containing_oneof();
+ if (oneof_decl != NULL) {
+ OneofDescriptor* mutable_oneof_decl =
+ &message->oneof_decls_[oneof_decl->index()];
+ message->fields_[i].index_in_oneof_ = mutable_oneof_decl->field_count_;
+ mutable_oneof_decl->fields_[mutable_oneof_decl->field_count_++] =
+ message->field(i);
+ }
+ }
+}
+
+void DescriptorBuilder::CrossLinkField(
+ FieldDescriptor* field, const FieldDescriptorProto& proto) {
+ if (field->options_ == NULL) {
+ field->options_ = &FieldOptions::default_instance();
+ }
+
+ if (proto.has_extendee()) {
+ Symbol extendee = LookupSymbol(proto.extendee(), field->full_name(),
+ PLACEHOLDER_EXTENDABLE_MESSAGE);
+ if (extendee.IsNull()) {
+ AddNotDefinedError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::EXTENDEE,
+ proto.extendee());
+ return;
+ } else if (extendee.type != Symbol::MESSAGE) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::EXTENDEE,
+ "\"" + proto.extendee() + "\" is not a message type.");
+ return;
+ }
+ field->containing_type_ = extendee.descriptor;
+
+ const Descriptor::ExtensionRange* extension_range = field->containing_type()
+ ->FindExtensionRangeContainingNumber(field->number());
+
+ if (extension_range == NULL) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("\"$0\" does not declare $1 as an "
+ "extension number.",
+ field->containing_type()->full_name(),
+ field->number()));
+ }
+ }
+
+ if (field->containing_oneof() != NULL) {
+ if (field->label() != FieldDescriptor::LABEL_OPTIONAL) {
+ // Note that this error will never happen when parsing .proto files.
+ // It can only happen if you manually construct a FileDescriptorProto
+ // that is incorrect.
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Fields of oneofs must themselves have label LABEL_OPTIONAL.");
+ }
+ }
+
+ if (proto.has_type_name()) {
+ // Assume we are expecting a message type unless the proto contains some
+ // evidence that it expects an enum type. This only makes a difference if
+ // we end up creating a placeholder.
+ bool expecting_enum = (proto.type() == FieldDescriptorProto::TYPE_ENUM) ||
+ proto.has_default_value();
+
+ Symbol type =
+ LookupSymbol(proto.type_name(), field->full_name(),
+ expecting_enum ? PLACEHOLDER_ENUM : PLACEHOLDER_MESSAGE,
+ LOOKUP_TYPES);
+
+ // If the type is a weak type, we change the type to a google.protobuf.Empty field.
+ if (type.IsNull() && !pool_->enforce_weak_ && proto.options().weak()) {
+ type = FindSymbol(kNonLinkedWeakMessageReplacementName);
+ }
+
+ if (type.IsNull()) {
+ AddNotDefinedError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ proto.type_name());
+ return;
+ }
+
+ if (!proto.has_type()) {
+ // Choose field type based on symbol.
+ if (type.type == Symbol::MESSAGE) {
+ field->type_ = FieldDescriptor::TYPE_MESSAGE;
+ } else if (type.type == Symbol::ENUM) {
+ field->type_ = FieldDescriptor::TYPE_ENUM;
+ } else {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "\"" + proto.type_name() + "\" is not a type.");
+ return;
+ }
+ }
+
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (type.type != Symbol::MESSAGE) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "\"" + proto.type_name() + "\" is not a message type.");
+ return;
+ }
+ field->message_type_ = type.descriptor;
+
+ if (field->has_default_value()) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::DEFAULT_VALUE,
+ "Messages can't have default values.");
+ }
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ if (type.type != Symbol::ENUM) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "\"" + proto.type_name() + "\" is not an enum type.");
+ return;
+ }
+ field->enum_type_ = type.enum_descriptor;
+
+ if (field->enum_type()->is_placeholder_) {
+ // We can't look up default values for placeholder types. We'll have
+ // to just drop them.
+ field->has_default_value_ = false;
+ }
+
+ if (field->has_default_value()) {
+ // Ensure that the default value is an identifier. Parser cannot always
+ // verify this because it does not have complete type information.
+ // N.B. that this check yields better error messages but is not
+ // necessary for correctness (an enum symbol must be a valid identifier
+ // anyway), only for better errors.
+ if (!io::Tokenizer::IsIdentifier(proto.default_value())) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::DEFAULT_VALUE,
+ "Default value for an enum field must be an identifier.");
+ } else {
+ // We can't just use field->enum_type()->FindValueByName() here
+ // because that locks the pool's mutex, which we have already locked
+ // at this point.
+ Symbol default_value =
+ LookupSymbolNoPlaceholder(proto.default_value(),
+ field->enum_type()->full_name());
+
+ if (default_value.type == Symbol::ENUM_VALUE &&
+ default_value.enum_value_descriptor->type() ==
+ field->enum_type()) {
+ field->default_value_enum_ = default_value.enum_value_descriptor;
+ } else {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::DEFAULT_VALUE,
+ "Enum type \"" + field->enum_type()->full_name() +
+ "\" has no value named \"" + proto.default_value() +
+ "\".");
+ }
+ }
+ } else if (field->enum_type()->value_count() > 0) {
+ // All enums must have at least one value, or we would have reported
+ // an error elsewhere. We use the first defined value as the default
+ // if a default is not explicitly defined.
+ field->default_value_enum_ = field->enum_type()->value(0);
+ }
+ } else {
+ AddError(field->full_name(), proto, DescriptorPool::ErrorCollector::TYPE,
+ "Field with primitive type has type_name.");
+ }
+ } else {
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE ||
+ field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ AddError(field->full_name(), proto, DescriptorPool::ErrorCollector::TYPE,
+ "Field with message or enum type missing type_name.");
+ }
+ }
+
+ // Add the field to the fields-by-number table.
+ // Note: We have to do this *after* cross-linking because extensions do not
+ // know their containing type until now.
+ if (!file_tables_->AddFieldByNumber(field)) {
+ const FieldDescriptor* conflicting_field =
+ file_tables_->FindFieldByNumber(field->containing_type(),
+ field->number());
+ if (field->is_extension()) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("Extension number $0 has already been used "
+ "in \"$1\" by extension \"$2\".",
+ field->number(),
+ field->containing_type()->full_name(),
+ conflicting_field->full_name()));
+ } else {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("Field number $0 has already been used in "
+ "\"$1\" by field \"$2\".",
+ field->number(),
+ field->containing_type()->full_name(),
+ conflicting_field->name()));
+ }
+ } else {
+ if (field->is_extension()) {
+ if (!tables_->AddExtension(field)) {
+ const FieldDescriptor* conflicting_field =
+ tables_->FindExtension(field->containing_type(), field->number());
+ string error_msg = strings::Substitute(
+ "Extension number $0 has already been used in \"$1\" by extension "
+ "\"$2\" defined in $3.",
+ field->number(),
+ field->containing_type()->full_name(),
+ conflicting_field->full_name(),
+ conflicting_field->file()->name());
+ // Conflicting extension numbers should be an error. However, before
+ // turning this into an error we need to fix all existing broken
+ // protos first.
+ // TODO(xiaofeng): Change this to an error.
+ AddWarning(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER, error_msg);
+ }
+ }
+ }
+
+ // Add the field to the lowercase-name and camelcase-name tables.
+ file_tables_->AddFieldByStylizedNames(field);
+}
+
+void DescriptorBuilder::CrossLinkEnum(
+ EnumDescriptor* enum_type, const EnumDescriptorProto& proto) {
+ if (enum_type->options_ == NULL) {
+ enum_type->options_ = &EnumOptions::default_instance();
+ }
+
+ for (int i = 0; i < enum_type->value_count(); i++) {
+ CrossLinkEnumValue(&enum_type->values_[i], proto.value(i));
+ }
+}
+
+void DescriptorBuilder::CrossLinkEnumValue(
+ EnumValueDescriptor* enum_value,
+ const EnumValueDescriptorProto& /* proto */) {
+ if (enum_value->options_ == NULL) {
+ enum_value->options_ = &EnumValueOptions::default_instance();
+ }
+}
+
+void DescriptorBuilder::CrossLinkService(
+ ServiceDescriptor* service, const ServiceDescriptorProto& proto) {
+ if (service->options_ == NULL) {
+ service->options_ = &ServiceOptions::default_instance();
+ }
+
+ for (int i = 0; i < service->method_count(); i++) {
+ CrossLinkMethod(&service->methods_[i], proto.method(i));
+ }
+}
+
+void DescriptorBuilder::CrossLinkMethod(
+ MethodDescriptor* method, const MethodDescriptorProto& proto) {
+ if (method->options_ == NULL) {
+ method->options_ = &MethodOptions::default_instance();
+ }
+
+ Symbol input_type = LookupSymbol(proto.input_type(), method->full_name());
+ if (input_type.IsNull()) {
+ AddNotDefinedError(method->full_name(), proto,
+ DescriptorPool::ErrorCollector::INPUT_TYPE,
+ proto.input_type());
+ } else if (input_type.type != Symbol::MESSAGE) {
+ AddError(method->full_name(), proto,
+ DescriptorPool::ErrorCollector::INPUT_TYPE,
+ "\"" + proto.input_type() + "\" is not a message type.");
+ } else {
+ method->input_type_ = input_type.descriptor;
+ }
+
+ Symbol output_type = LookupSymbol(proto.output_type(), method->full_name());
+ if (output_type.IsNull()) {
+ AddNotDefinedError(method->full_name(), proto,
+ DescriptorPool::ErrorCollector::OUTPUT_TYPE,
+ proto.output_type());
+ } else if (output_type.type != Symbol::MESSAGE) {
+ AddError(method->full_name(), proto,
+ DescriptorPool::ErrorCollector::OUTPUT_TYPE,
+ "\"" + proto.output_type() + "\" is not a message type.");
+ } else {
+ method->output_type_ = output_type.descriptor;
+ }
+}
+
+// -------------------------------------------------------------------
+
+#define VALIDATE_OPTIONS_FROM_ARRAY(descriptor, array_name, type) \
+ for (int i = 0; i < descriptor->array_name##_count(); ++i) { \
+ Validate##type##Options(descriptor->array_name##s_ + i, \
+ proto.array_name(i)); \
+ }
+
+// Determine if the file uses optimize_for = LITE_RUNTIME, being careful to
+// avoid problems that exist at init time.
+static bool IsLite(const FileDescriptor* file) {
+ // TODO(kenton): I don't even remember how many of these conditions are
+ // actually possible. I'm just being super-safe.
+ return file != NULL &&
+ &file->options() != &FileOptions::default_instance() &&
+ file->options().optimize_for() == FileOptions::LITE_RUNTIME;
+}
+
+void DescriptorBuilder::ValidateFileOptions(FileDescriptor* file,
+ const FileDescriptorProto& proto) {
+ VALIDATE_OPTIONS_FROM_ARRAY(file, message_type, Message);
+ VALIDATE_OPTIONS_FROM_ARRAY(file, enum_type, Enum);
+ VALIDATE_OPTIONS_FROM_ARRAY(file, service, Service);
+ VALIDATE_OPTIONS_FROM_ARRAY(file, extension, Field);
+
+ // Lite files can only be imported by other Lite files.
+ if (!IsLite(file)) {
+ for (int i = 0; i < file->dependency_count(); i++) {
+ if (IsLite(file->dependency(i))) {
+ AddError(
+ file->name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "Files that do not use optimize_for = LITE_RUNTIME cannot import "
+ "files which do use this option. This file is not lite, but it "
+ "imports \"" + file->dependency(i)->name() + "\" which is.");
+ break;
+ }
+ }
+ }
+ if (file->syntax() == FileDescriptor::SYNTAX_PROTO3) {
+ ValidateProto3(file, proto);
+ }
+}
+
+void DescriptorBuilder::ValidateProto3(
+ FileDescriptor* file, const FileDescriptorProto& proto) {
+ for (int i = 0; i < file->extension_count(); ++i) {
+ ValidateProto3Field(file->extensions_ + i, proto.extension(i));
+ }
+ for (int i = 0; i < file->message_type_count(); ++i) {
+ ValidateProto3Message(file->message_types_ + i, proto.message_type(i));
+ }
+ for (int i = 0; i < file->enum_type_count(); ++i) {
+ ValidateProto3Enum(file->enum_types_ + i, proto.enum_type(i));
+ }
+}
+
+static string ToLowercaseWithoutUnderscores(const string& name) {
+ string result;
+ for (int i = 0; i < name.size(); ++i) {
+ if (name[i] != '_') {
+ if (name[i] >= 'A' && name[i] <= 'Z') {
+ result.push_back(name[i] - 'A' + 'a');
+ } else {
+ result.push_back(name[i]);
+ }
+ }
+ }
+ return result;
+}
+
+void DescriptorBuilder::ValidateProto3Message(
+ Descriptor* message, const DescriptorProto& proto) {
+ for (int i = 0; i < message->nested_type_count(); ++i) {
+ ValidateProto3Message(message->nested_types_ + i,
+ proto.nested_type(i));
+ }
+ for (int i = 0; i < message->enum_type_count(); ++i) {
+ ValidateProto3Enum(message->enum_types_ + i,
+ proto.enum_type(i));
+ }
+ for (int i = 0; i < message->field_count(); ++i) {
+ ValidateProto3Field(message->fields_ + i, proto.field(i));
+ }
+ for (int i = 0; i < message->extension_count(); ++i) {
+ ValidateProto3Field(message->extensions_ +i, proto.extension(i));
+ }
+ if (message->extension_range_count() > 0) {
+ AddError(message->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "Extension ranges are not allowed in proto3.");
+ }
+ if (message->options().message_set_wire_format()) {
+ // Using MessageSet doesn't make sense since we disallow extensions.
+ AddError(message->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "MessageSet is not supported in proto3.");
+ }
+
+ // In proto3, we reject field names if they conflict in camelCase.
+ // Note that we currently enforce a stricter rule: Field names must be
+ // unique after being converted to lowercase with underscores removed.
+ map<string, const FieldDescriptor*> name_to_field;
+ for (int i = 0; i < message->field_count(); ++i) {
+ string lowercase_name = ToLowercaseWithoutUnderscores(
+ message->field(i)->name());
+ if (name_to_field.find(lowercase_name) != name_to_field.end()) {
+ AddError(message->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "The JSON camel-case name of field \"" +
+ message->field(i)->name() + "\" conflicts with field \"" +
+ name_to_field[lowercase_name]->name() + "\". This is not " +
+ "allowed in proto3.");
+ } else {
+ name_to_field[lowercase_name] = message->field(i);
+ }
+ }
+}
+
+void DescriptorBuilder::ValidateProto3Field(
+ FieldDescriptor* field, const FieldDescriptorProto& proto) {
+ if (field->is_extension() &&
+ !AllowedExtendeeInProto3(field->containing_type()->full_name())) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "Extensions in proto3 are only allowed for defining options.");
+ }
+ if (field->is_required()) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "Required fields are not allowed in proto3.");
+ }
+ if (field->has_default_value()) {
+ AddError(
+ field->full_name(), proto, DescriptorPool::ErrorCollector::OTHER,
+ "Explicit default values are not allowed in proto3.");
+ }
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM &&
+ field->enum_type() &&
+ field->enum_type()->file()->syntax() != FileDescriptor::SYNTAX_PROTO3) {
+ // Proto3 messages can only use Proto3 enum types; otherwise we can't
+ // guarantee that the default value is zero.
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "Enum type \"" + field->enum_type()->full_name() +
+ "\" is not a proto3 enum, but is used in \"" +
+ field->containing_type()->full_name() +
+ "\" which is a proto3 message type.");
+ }
+ if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "Groups are not supported in proto3 syntax.");
+ }
+}
+
+void DescriptorBuilder::ValidateProto3Enum(
+ EnumDescriptor* enm, const EnumDescriptorProto& proto) {
+ if (enm->value_count() > 0 && enm->value(0)->number() != 0) {
+ AddError(
+ enm->full_name(), proto, DescriptorPool::ErrorCollector::OTHER,
+ "The first enum value must be zero in proto3.");
+ }
+}
+
+
+void DescriptorBuilder::ValidateMessageOptions(Descriptor* message,
+ const DescriptorProto& proto) {
+ VALIDATE_OPTIONS_FROM_ARRAY(message, field, Field);
+ VALIDATE_OPTIONS_FROM_ARRAY(message, nested_type, Message);
+ VALIDATE_OPTIONS_FROM_ARRAY(message, enum_type, Enum);
+ VALIDATE_OPTIONS_FROM_ARRAY(message, extension, Field);
+
+ const int64 max_extension_range =
+ static_cast<int64>(message->options().message_set_wire_format() ?
+ kint32max :
+ FieldDescriptor::kMaxNumber);
+ for (int i = 0; i < message->extension_range_count(); ++i) {
+ if (message->extension_range(i)->end > max_extension_range + 1) {
+ AddError(
+ message->full_name(), proto.extension_range(i),
+ DescriptorPool::ErrorCollector::NUMBER,
+ strings::Substitute("Extension numbers cannot be greater than $0.",
+ max_extension_range));
+ }
+ }
+
+}
+
+void DescriptorBuilder::ValidateFieldOptions(FieldDescriptor* field,
+ const FieldDescriptorProto& proto) {
+ // Only message type fields may be lazy.
+ if (field->options().lazy()) {
+ if (field->type() != FieldDescriptor::TYPE_MESSAGE) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "[lazy = true] can only be specified for submessage fields.");
+ }
+ }
+
+ // Only repeated primitive fields may be packed.
+ if (field->options().packed() && !field->is_packable()) {
+ AddError(
+ field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "[packed = true] can only be specified for repeated primitive fields.");
+ }
+
+ // Note: Default instance may not yet be initialized here, so we have to
+ // avoid reading from it.
+ if (field->containing_type_ != NULL &&
+ &field->containing_type()->options() !=
+ &MessageOptions::default_instance() &&
+ field->containing_type()->options().message_set_wire_format()) {
+ if (field->is_extension()) {
+ if (!field->is_optional() ||
+ field->type() != FieldDescriptor::TYPE_MESSAGE) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::TYPE,
+ "Extensions of MessageSets must be optional messages.");
+ }
+ } else {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "MessageSets cannot have fields, only extensions.");
+ }
+ }
+
+ // Lite extensions can only be of Lite types.
+ if (IsLite(field->file()) &&
+ field->containing_type_ != NULL &&
+ !IsLite(field->containing_type()->file())) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::EXTENDEE,
+ "Extensions to non-lite types can only be declared in non-lite "
+ "files. Note that you cannot extend a non-lite type to contain "
+ "a lite type, but the reverse is allowed.");
+ }
+
+ // Validate map types.
+ if (field->is_map()) {
+ if (!ValidateMapEntry(field, proto)) {
+ AddError(field->full_name(), proto,
+ DescriptorPool::ErrorCollector::OTHER,
+ "map_entry should not be set explicitly. Use map<KeyType, "
+ "ValueType> instead.");
+ }
+ }
+
+}
+
+void DescriptorBuilder::ValidateEnumOptions(EnumDescriptor* enm,
+ const EnumDescriptorProto& proto) {
+ VALIDATE_OPTIONS_FROM_ARRAY(enm, value, EnumValue);
+ if (!enm->options().has_allow_alias() || !enm->options().allow_alias()) {
+ map<int, string> used_values;
+ for (int i = 0; i < enm->value_count(); ++i) {
+ const EnumValueDescriptor* enum_value = enm->value(i);
+ if (used_values.find(enum_value->number()) != used_values.end()) {
+ string error =
+ "\"" + enum_value->full_name() +
+ "\" uses the same enum value as \"" +
+ used_values[enum_value->number()] + "\". If this is intended, set "
+ "'option allow_alias = true;' to the enum definition.";
+ if (!enm->options().allow_alias()) {
+ // Generate error if duplicated enum values are explicitly disallowed.
+ AddError(enm->full_name(), proto,
+ DescriptorPool::ErrorCollector::NUMBER,
+ error);
+ } else {
+ // Generate warning if duplicated values are found but the option
+ // isn't set.
+ GOOGLE_LOG(ERROR) << error;
+ }
+ } else {
+ used_values[enum_value->number()] = enum_value->full_name();
+ }
+ }
+ }
+}
+
+void DescriptorBuilder::ValidateEnumValueOptions(
+ EnumValueDescriptor* /* enum_value */,
+ const EnumValueDescriptorProto& /* proto */) {
+ // Nothing to do so far.
+}
+void DescriptorBuilder::ValidateServiceOptions(ServiceDescriptor* service,
+ const ServiceDescriptorProto& proto) {
+ if (IsLite(service->file()) &&
+ (service->file()->options().cc_generic_services() ||
+ service->file()->options().java_generic_services())) {
+ AddError(service->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Files with optimize_for = LITE_RUNTIME cannot define services "
+ "unless you set both options cc_generic_services and "
+ "java_generic_sevices to false.");
+ }
+
+ VALIDATE_OPTIONS_FROM_ARRAY(service, method, Method);
+}
+
+void DescriptorBuilder::ValidateMethodOptions(MethodDescriptor* /* method */,
+ const MethodDescriptorProto& /* proto */) {
+ // Nothing to do so far.
+}
+
+bool DescriptorBuilder::ValidateMapEntry(FieldDescriptor* field,
+ const FieldDescriptorProto& proto) {
+ const Descriptor* message = field->message_type();
+ if (// Must not contain extensions, extension range or nested message or
+ // enums
+ message->extension_count() != 0 ||
+ field->label() != FieldDescriptor::LABEL_REPEATED ||
+ message->extension_range_count() != 0 ||
+ message->nested_type_count() != 0 || message->enum_type_count() != 0 ||
+ // Must contain exactly two fields
+ message->field_count() != 2 ||
+ // Field name and message name must match
+ message->name() != ToCamelCase(field->name(), false) + "Entry" ||
+ // Entry message must be in the same containing type of the field.
+ field->containing_type() != message->containing_type()) {
+ return false;
+ }
+
+ const FieldDescriptor* key = message->field(0);
+ const FieldDescriptor* value = message->field(1);
+ if (key->label() != FieldDescriptor::LABEL_OPTIONAL || key->number() != 1 ||
+ key->name() != "key") {
+ return false;
+ }
+ if (value->label() != FieldDescriptor::LABEL_OPTIONAL ||
+ value->number() != 2 || value->name() != "value") {
+ return false;
+ }
+
+ // Check key types are legal.
+ switch (key->type()) {
+ case FieldDescriptor::TYPE_ENUM:
+ AddError(
+ field->full_name(), proto, DescriptorPool::ErrorCollector::TYPE,
+ "Key in map fields cannot be enum types.");
+ break;
+ case FieldDescriptor::TYPE_FLOAT:
+ case FieldDescriptor::TYPE_DOUBLE:
+ case FieldDescriptor::TYPE_MESSAGE:
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_BYTES:
+ AddError(
+ field->full_name(), proto, DescriptorPool::ErrorCollector::TYPE,
+ "Key in map fields cannot be float/double, bytes or message types.");
+ break;
+ case FieldDescriptor::TYPE_BOOL:
+ case FieldDescriptor::TYPE_INT32:
+ case FieldDescriptor::TYPE_INT64:
+ case FieldDescriptor::TYPE_SINT32:
+ case FieldDescriptor::TYPE_SINT64:
+ case FieldDescriptor::TYPE_STRING:
+ case FieldDescriptor::TYPE_UINT32:
+ case FieldDescriptor::TYPE_UINT64:
+ case FieldDescriptor::TYPE_FIXED32:
+ case FieldDescriptor::TYPE_FIXED64:
+ case FieldDescriptor::TYPE_SFIXED32:
+ case FieldDescriptor::TYPE_SFIXED64:
+ // Legal cases
+ break;
+ // Do not add a default, so that the compiler will complain when new types
+ // are added.
+ }
+
+ if (value->type() == FieldDescriptor::TYPE_ENUM) {
+ if (value->enum_type()->value(0)->number() != 0) {
+ AddError(
+ field->full_name(), proto, DescriptorPool::ErrorCollector::TYPE,
+ "Enum value in map must define 0 as the first value.");
+ }
+ }
+
+ return true;
+}
+
+void DescriptorBuilder::DetectMapConflicts(const Descriptor* message,
+ const DescriptorProto& proto) {
+ map<string, const Descriptor*> seen_types;
+ for (int i = 0; i < message->nested_type_count(); ++i) {
+ const Descriptor* nested = message->nested_type(i);
+ pair<map<string, const Descriptor*>::iterator, bool> result =
+ seen_types.insert(std::make_pair(nested->name(), nested));
+ if (!result.second) {
+ if (result.first->second->options().map_entry() ||
+ nested->options().map_entry()) {
+ AddError(message->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Expanded map entry type " + nested->name() +
+ " conflicts with an existing nested message type.");
+ }
+ }
+ // Recursively test on the nested types.
+ DetectMapConflicts(message->nested_type(i), proto.nested_type(i));
+ }
+ // Check for conflicted field names.
+ for (int i = 0; i < message->field_count(); ++i) {
+ const FieldDescriptor* field = message->field(i);
+ map<string, const Descriptor*>::iterator iter =
+ seen_types.find(field->name());
+ if (iter != seen_types.end() && iter->second->options().map_entry()) {
+ AddError(message->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Expanded map entry type " + iter->second->name() +
+ " conflicts with an existing field.");
+ }
+ }
+ // Check for conflicted enum names.
+ for (int i = 0; i < message->enum_type_count(); ++i) {
+ const EnumDescriptor* enum_desc = message->enum_type(i);
+ map<string, const Descriptor*>::iterator iter =
+ seen_types.find(enum_desc->name());
+ if (iter != seen_types.end() && iter->second->options().map_entry()) {
+ AddError(message->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Expanded map entry type " + iter->second->name() +
+ " conflicts with an existing enum type.");
+ }
+ }
+ // Check for conflicted oneof names.
+ for (int i = 0; i < message->oneof_decl_count(); ++i) {
+ const OneofDescriptor* oneof_desc = message->oneof_decl(i);
+ map<string, const Descriptor*>::iterator iter =
+ seen_types.find(oneof_desc->name());
+ if (iter != seen_types.end() && iter->second->options().map_entry()) {
+ AddError(message->full_name(), proto,
+ DescriptorPool::ErrorCollector::NAME,
+ "Expanded map entry type " + iter->second->name() +
+ " conflicts with an existing oneof type.");
+ }
+ }
+}
+
+
+#undef VALIDATE_OPTIONS_FROM_ARRAY
+
+// -------------------------------------------------------------------
+
+DescriptorBuilder::OptionInterpreter::OptionInterpreter(
+ DescriptorBuilder* builder) : builder_(builder) {
+ GOOGLE_CHECK(builder_);
+}
+
+DescriptorBuilder::OptionInterpreter::~OptionInterpreter() {
+}
+
+bool DescriptorBuilder::OptionInterpreter::InterpretOptions(
+ OptionsToInterpret* options_to_interpret) {
+ // Note that these may be in different pools, so we can't use the same
+ // descriptor and reflection objects on both.
+ Message* options = options_to_interpret->options;
+ const Message* original_options = options_to_interpret->original_options;
+
+ bool failed = false;
+ options_to_interpret_ = options_to_interpret;
+
+ // Find the uninterpreted_option field in the mutable copy of the options
+ // and clear them, since we're about to interpret them.
+ const FieldDescriptor* uninterpreted_options_field =
+ options->GetDescriptor()->FindFieldByName("uninterpreted_option");
+ GOOGLE_CHECK(uninterpreted_options_field != NULL)
+ << "No field named \"uninterpreted_option\" in the Options proto.";
+ options->GetReflection()->ClearField(options, uninterpreted_options_field);
+
+ // Find the uninterpreted_option field in the original options.
+ const FieldDescriptor* original_uninterpreted_options_field =
+ original_options->GetDescriptor()->
+ FindFieldByName("uninterpreted_option");
+ GOOGLE_CHECK(original_uninterpreted_options_field != NULL)
+ << "No field named \"uninterpreted_option\" in the Options proto.";
+
+ const int num_uninterpreted_options = original_options->GetReflection()->
+ FieldSize(*original_options, original_uninterpreted_options_field);
+ for (int i = 0; i < num_uninterpreted_options; ++i) {
+ uninterpreted_option_ = down_cast<const UninterpretedOption*>(
+ &original_options->GetReflection()->GetRepeatedMessage(
+ *original_options, original_uninterpreted_options_field, i));
+ if (!InterpretSingleOption(options)) {
+ // Error already added by InterpretSingleOption().
+ failed = true;
+ break;
+ }
+ }
+ // Reset these, so we don't have any dangling pointers.
+ uninterpreted_option_ = NULL;
+ options_to_interpret_ = NULL;
+
+ if (!failed) {
+ // InterpretSingleOption() added the interpreted options in the
+ // UnknownFieldSet, in case the option isn't yet known to us. Now we
+ // serialize the options message and deserialize it back. That way, any
+ // option fields that we do happen to know about will get moved from the
+ // UnknownFieldSet into the real fields, and thus be available right away.
+ // If they are not known, that's OK too. They will get reparsed into the
+ // UnknownFieldSet and wait there until the message is parsed by something
+ // that does know about the options.
+ string buf;
+ GOOGLE_CHECK(options->AppendPartialToString(&buf))
+ << "Protocol message could not be serialized.";
+ GOOGLE_CHECK(options->ParsePartialFromString(buf))
+ << "Protocol message serialized itself in invalid fashion.";
+ if (!options->IsInitialized()) {
+ builder_->AddWarning(
+ options_to_interpret->element_name, *original_options,
+ DescriptorPool::ErrorCollector::OTHER,
+ "Options could not be fully parsed using the proto descriptors "
+ "compiled into this binary. Missing required fields: " +
+ options->InitializationErrorString());
+ }
+ }
+ return !failed;
+}
+
+bool DescriptorBuilder::OptionInterpreter::InterpretSingleOption(
+ Message* options) {
+ // First do some basic validation.
+ if (uninterpreted_option_->name_size() == 0) {
+ // This should never happen unless the parser has gone seriously awry or
+ // someone has manually created the uninterpreted option badly.
+ return AddNameError("Option must have a name.");
+ }
+ if (uninterpreted_option_->name(0).name_part() == "uninterpreted_option") {
+ return AddNameError("Option must not use reserved name "
+ "\"uninterpreted_option\".");
+ }
+
+ const Descriptor* options_descriptor = NULL;
+ // Get the options message's descriptor from the builder's pool, so that we
+ // get the version that knows about any extension options declared in the
+ // file we're currently building. The descriptor should be there as long as
+ // the file we're building imported "google/protobuf/descriptors.proto".
+
+ // Note that we use DescriptorBuilder::FindSymbolNotEnforcingDeps(), not
+ // DescriptorPool::FindMessageTypeByName() because we're already holding the
+ // pool's mutex, and the latter method locks it again. We don't use
+ // FindSymbol() because files that use custom options only need to depend on
+ // the file that defines the option, not descriptor.proto itself.
+ Symbol symbol = builder_->FindSymbolNotEnforcingDeps(
+ options->GetDescriptor()->full_name());
+ if (!symbol.IsNull() && symbol.type == Symbol::MESSAGE) {
+ options_descriptor = symbol.descriptor;
+ } else {
+ // The options message's descriptor was not in the builder's pool, so use
+ // the standard version from the generated pool. We're not holding the
+ // generated pool's mutex, so we can search it the straightforward way.
+ options_descriptor = options->GetDescriptor();
+ }
+ GOOGLE_CHECK(options_descriptor);
+
+ // We iterate over the name parts to drill into the submessages until we find
+ // the leaf field for the option. As we drill down we remember the current
+ // submessage's descriptor in |descriptor| and the next field in that
+ // submessage in |field|. We also track the fields we're drilling down
+ // through in |intermediate_fields|. As we go, we reconstruct the full option
+ // name in |debug_msg_name|, for use in error messages.
+ const Descriptor* descriptor = options_descriptor;
+ const FieldDescriptor* field = NULL;
+ vector<const FieldDescriptor*> intermediate_fields;
+ string debug_msg_name = "";
+
+ for (int i = 0; i < uninterpreted_option_->name_size(); ++i) {
+ const string& name_part = uninterpreted_option_->name(i).name_part();
+ if (debug_msg_name.size() > 0) {
+ debug_msg_name += ".";
+ }
+ if (uninterpreted_option_->name(i).is_extension()) {
+ debug_msg_name += "(" + name_part + ")";
+ // Search for the extension's descriptor as an extension in the builder's
+ // pool. Note that we use DescriptorBuilder::LookupSymbol(), not
+ // DescriptorPool::FindExtensionByName(), for two reasons: 1) It allows
+ // relative lookups, and 2) because we're already holding the pool's
+ // mutex, and the latter method locks it again.
+ symbol = builder_->LookupSymbol(name_part,
+ options_to_interpret_->name_scope);
+ if (!symbol.IsNull() && symbol.type == Symbol::FIELD) {
+ field = symbol.field_descriptor;
+ }
+ // If we don't find the field then the field's descriptor was not in the
+ // builder's pool, but there's no point in looking in the generated
+ // pool. We require that you import the file that defines any extensions
+ // you use, so they must be present in the builder's pool.
+ } else {
+ debug_msg_name += name_part;
+ // Search for the field's descriptor as a regular field.
+ field = descriptor->FindFieldByName(name_part);
+ }
+
+ if (field == NULL) {
+ if (get_allow_unknown(builder_->pool_)) {
+ // We can't find the option, but AllowUnknownDependencies() is enabled,
+ // so we will just leave it as uninterpreted.
+ AddWithoutInterpreting(*uninterpreted_option_, options);
+ return true;
+ } else if (!(builder_->undefine_resolved_name_).empty()) {
+ // Option is resolved to a name which is not defined.
+ return AddNameError(
+ "Option \"" + debug_msg_name + "\" is resolved to \"(" +
+ builder_->undefine_resolved_name_ +
+ ")\", which is not defined. The innermost scope is searched first "
+ "in name resolution. Consider using a leading '.'(i.e., \"(." +
+ debug_msg_name.substr(1) +
+ "\") to start from the outermost scope.");
+ } else {
+ return AddNameError("Option \"" + debug_msg_name + "\" unknown.");
+ }
+ } else if (field->containing_type() != descriptor) {
+ if (get_is_placeholder(field->containing_type())) {
+ // The field is an extension of a placeholder type, so we can't
+ // reliably verify whether it is a valid extension to use here (e.g.
+ // we don't know if it is an extension of the correct *Options message,
+ // or if it has a valid field number, etc.). Just leave it as
+ // uninterpreted instead.
+ AddWithoutInterpreting(*uninterpreted_option_, options);
+ return true;
+ } else {
+ // This can only happen if, due to some insane misconfiguration of the
+ // pools, we find the options message in one pool but the field in
+ // another. This would probably imply a hefty bug somewhere.
+ return AddNameError("Option field \"" + debug_msg_name +
+ "\" is not a field or extension of message \"" +
+ descriptor->name() + "\".");
+ }
+ } else if (i < uninterpreted_option_->name_size() - 1) {
+ if (field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ return AddNameError("Option \"" + debug_msg_name +
+ "\" is an atomic type, not a message.");
+ } else if (field->is_repeated()) {
+ return AddNameError("Option field \"" + debug_msg_name +
+ "\" is a repeated message. Repeated message "
+ "options must be initialized using an "
+ "aggregate value.");
+ } else {
+ // Drill down into the submessage.
+ intermediate_fields.push_back(field);
+ descriptor = field->message_type();
+ }
+ }
+ }
+
+ // We've found the leaf field. Now we use UnknownFieldSets to set its value
+ // on the options message. We do so because the message may not yet know
+ // about its extension fields, so we may not be able to set the fields
+ // directly. But the UnknownFieldSets will serialize to the same wire-format
+ // message, so reading that message back in once the extension fields are
+ // known will populate them correctly.
+
+ // First see if the option is already set.
+ if (!field->is_repeated() && !ExamineIfOptionIsSet(
+ intermediate_fields.begin(),
+ intermediate_fields.end(),
+ field, debug_msg_name,
+ options->GetReflection()->GetUnknownFields(*options))) {
+ return false; // ExamineIfOptionIsSet() already added the error.
+ }
+
+
+ // First set the value on the UnknownFieldSet corresponding to the
+ // innermost message.
+ google::protobuf::scoped_ptr<UnknownFieldSet> unknown_fields(new UnknownFieldSet());
+ if (!SetOptionValue(field, unknown_fields.get())) {
+ return false; // SetOptionValue() already added the error.
+ }
+
+ // Now wrap the UnknownFieldSet with UnknownFieldSets corresponding to all
+ // the intermediate messages.
+ for (vector<const FieldDescriptor*>::reverse_iterator iter =
+ intermediate_fields.rbegin();
+ iter != intermediate_fields.rend(); ++iter) {
+ google::protobuf::scoped_ptr<UnknownFieldSet> parent_unknown_fields(
+ new UnknownFieldSet());
+ switch ((*iter)->type()) {
+ case FieldDescriptor::TYPE_MESSAGE: {
+ io::StringOutputStream outstr(
+ parent_unknown_fields->AddLengthDelimited((*iter)->number()));
+ io::CodedOutputStream out(&outstr);
+ internal::WireFormat::SerializeUnknownFields(*unknown_fields, &out);
+ GOOGLE_CHECK(!out.HadError())
+ << "Unexpected failure while serializing option submessage "
+ << debug_msg_name << "\".";
+ break;
+ }
+
+ case FieldDescriptor::TYPE_GROUP: {
+ parent_unknown_fields->AddGroup((*iter)->number())
+ ->MergeFrom(*unknown_fields);
+ break;
+ }
+
+ default:
+ GOOGLE_LOG(FATAL) << "Invalid wire type for CPPTYPE_MESSAGE: "
+ << (*iter)->type();
+ return false;
+ }
+ unknown_fields.reset(parent_unknown_fields.release());
+ }
+
+ // Now merge the UnknownFieldSet corresponding to the top-level message into
+ // the options message.
+ options->GetReflection()->MutableUnknownFields(options)->MergeFrom(
+ *unknown_fields);
+
+ return true;
+}
+
+void DescriptorBuilder::OptionInterpreter::AddWithoutInterpreting(
+ const UninterpretedOption& uninterpreted_option, Message* options) {
+ const FieldDescriptor* field =
+ options->GetDescriptor()->FindFieldByName("uninterpreted_option");
+ GOOGLE_CHECK(field != NULL);
+
+ options->GetReflection()->AddMessage(options, field)
+ ->CopyFrom(uninterpreted_option);
+}
+
+bool DescriptorBuilder::OptionInterpreter::ExamineIfOptionIsSet(
+ vector<const FieldDescriptor*>::const_iterator intermediate_fields_iter,
+ vector<const FieldDescriptor*>::const_iterator intermediate_fields_end,
+ const FieldDescriptor* innermost_field, const string& debug_msg_name,
+ const UnknownFieldSet& unknown_fields) {
+ // We do linear searches of the UnknownFieldSet and its sub-groups. This
+ // should be fine since it's unlikely that any one options structure will
+ // contain more than a handful of options.
+
+ if (intermediate_fields_iter == intermediate_fields_end) {
+ // We're at the innermost submessage.
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ if (unknown_fields.field(i).number() == innermost_field->number()) {
+ return AddNameError("Option \"" + debug_msg_name +
+ "\" was already set.");
+ }
+ }
+ return true;
+ }
+
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ if (unknown_fields.field(i).number() ==
+ (*intermediate_fields_iter)->number()) {
+ const UnknownField* unknown_field = &unknown_fields.field(i);
+ FieldDescriptor::Type type = (*intermediate_fields_iter)->type();
+ // Recurse into the next submessage.
+ switch (type) {
+ case FieldDescriptor::TYPE_MESSAGE:
+ if (unknown_field->type() == UnknownField::TYPE_LENGTH_DELIMITED) {
+ UnknownFieldSet intermediate_unknown_fields;
+ if (intermediate_unknown_fields.ParseFromString(
+ unknown_field->length_delimited()) &&
+ !ExamineIfOptionIsSet(intermediate_fields_iter + 1,
+ intermediate_fields_end,
+ innermost_field, debug_msg_name,
+ intermediate_unknown_fields)) {
+ return false; // Error already added.
+ }
+ }
+ break;
+
+ case FieldDescriptor::TYPE_GROUP:
+ if (unknown_field->type() == UnknownField::TYPE_GROUP) {
+ if (!ExamineIfOptionIsSet(intermediate_fields_iter + 1,
+ intermediate_fields_end,
+ innermost_field, debug_msg_name,
+ unknown_field->group())) {
+ return false; // Error already added.
+ }
+ }
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Invalid wire type for CPPTYPE_MESSAGE: " << type;
+ return false;
+ }
+ }
+ }
+ return true;
+}
+
+bool DescriptorBuilder::OptionInterpreter::SetOptionValue(
+ const FieldDescriptor* option_field,
+ UnknownFieldSet* unknown_fields) {
+ // We switch on the CppType to validate.
+ switch (option_field->cpp_type()) {
+
+ case FieldDescriptor::CPPTYPE_INT32:
+ if (uninterpreted_option_->has_positive_int_value()) {
+ if (uninterpreted_option_->positive_int_value() >
+ static_cast<uint64>(kint32max)) {
+ return AddValueError("Value out of range for int32 option \"" +
+ option_field->full_name() + "\".");
+ } else {
+ SetInt32(option_field->number(),
+ uninterpreted_option_->positive_int_value(),
+ option_field->type(), unknown_fields);
+ }
+ } else if (uninterpreted_option_->has_negative_int_value()) {
+ if (uninterpreted_option_->negative_int_value() <
+ static_cast<int64>(kint32min)) {
+ return AddValueError("Value out of range for int32 option \"" +
+ option_field->full_name() + "\".");
+ } else {
+ SetInt32(option_field->number(),
+ uninterpreted_option_->negative_int_value(),
+ option_field->type(), unknown_fields);
+ }
+ } else {
+ return AddValueError("Value must be integer for int32 option \"" +
+ option_field->full_name() + "\".");
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_INT64:
+ if (uninterpreted_option_->has_positive_int_value()) {
+ if (uninterpreted_option_->positive_int_value() >
+ static_cast<uint64>(kint64max)) {
+ return AddValueError("Value out of range for int64 option \"" +
+ option_field->full_name() + "\".");
+ } else {
+ SetInt64(option_field->number(),
+ uninterpreted_option_->positive_int_value(),
+ option_field->type(), unknown_fields);
+ }
+ } else if (uninterpreted_option_->has_negative_int_value()) {
+ SetInt64(option_field->number(),
+ uninterpreted_option_->negative_int_value(),
+ option_field->type(), unknown_fields);
+ } else {
+ return AddValueError("Value must be integer for int64 option \"" +
+ option_field->full_name() + "\".");
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_UINT32:
+ if (uninterpreted_option_->has_positive_int_value()) {
+ if (uninterpreted_option_->positive_int_value() > kuint32max) {
+ return AddValueError("Value out of range for uint32 option \"" +
+ option_field->name() + "\".");
+ } else {
+ SetUInt32(option_field->number(),
+ uninterpreted_option_->positive_int_value(),
+ option_field->type(), unknown_fields);
+ }
+ } else {
+ return AddValueError("Value must be non-negative integer for uint32 "
+ "option \"" + option_field->full_name() + "\".");
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_UINT64:
+ if (uninterpreted_option_->has_positive_int_value()) {
+ SetUInt64(option_field->number(),
+ uninterpreted_option_->positive_int_value(),
+ option_field->type(), unknown_fields);
+ } else {
+ return AddValueError("Value must be non-negative integer for uint64 "
+ "option \"" + option_field->full_name() + "\".");
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ float value;
+ if (uninterpreted_option_->has_double_value()) {
+ value = uninterpreted_option_->double_value();
+ } else if (uninterpreted_option_->has_positive_int_value()) {
+ value = uninterpreted_option_->positive_int_value();
+ } else if (uninterpreted_option_->has_negative_int_value()) {
+ value = uninterpreted_option_->negative_int_value();
+ } else {
+ return AddValueError("Value must be number for float option \"" +
+ option_field->full_name() + "\".");
+ }
+ unknown_fields->AddFixed32(option_field->number(),
+ google::protobuf::internal::WireFormatLite::EncodeFloat(value));
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value;
+ if (uninterpreted_option_->has_double_value()) {
+ value = uninterpreted_option_->double_value();
+ } else if (uninterpreted_option_->has_positive_int_value()) {
+ value = uninterpreted_option_->positive_int_value();
+ } else if (uninterpreted_option_->has_negative_int_value()) {
+ value = uninterpreted_option_->negative_int_value();
+ } else {
+ return AddValueError("Value must be number for double option \"" +
+ option_field->full_name() + "\".");
+ }
+ unknown_fields->AddFixed64(option_field->number(),
+ google::protobuf::internal::WireFormatLite::EncodeDouble(value));
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_BOOL:
+ uint64 value;
+ if (!uninterpreted_option_->has_identifier_value()) {
+ return AddValueError("Value must be identifier for boolean option "
+ "\"" + option_field->full_name() + "\".");
+ }
+ if (uninterpreted_option_->identifier_value() == "true") {
+ value = 1;
+ } else if (uninterpreted_option_->identifier_value() == "false") {
+ value = 0;
+ } else {
+ return AddValueError("Value must be \"true\" or \"false\" for boolean "
+ "option \"" + option_field->full_name() + "\".");
+ }
+ unknown_fields->AddVarint(option_field->number(), value);
+ break;
+
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ if (!uninterpreted_option_->has_identifier_value()) {
+ return AddValueError("Value must be identifier for enum-valued option "
+ "\"" + option_field->full_name() + "\".");
+ }
+ const EnumDescriptor* enum_type = option_field->enum_type();
+ const string& value_name = uninterpreted_option_->identifier_value();
+ const EnumValueDescriptor* enum_value = NULL;
+
+ if (enum_type->file()->pool() != DescriptorPool::generated_pool()) {
+ // Note that the enum value's fully-qualified name is a sibling of the
+ // enum's name, not a child of it.
+ string fully_qualified_name = enum_type->full_name();
+ fully_qualified_name.resize(fully_qualified_name.size() -
+ enum_type->name().size());
+ fully_qualified_name += value_name;
+
+ // Search for the enum value's descriptor in the builder's pool. Note
+ // that we use DescriptorBuilder::FindSymbolNotEnforcingDeps(), not
+ // DescriptorPool::FindEnumValueByName() because we're already holding
+ // the pool's mutex, and the latter method locks it again.
+ Symbol symbol =
+ builder_->FindSymbolNotEnforcingDeps(fully_qualified_name);
+ if (!symbol.IsNull() && symbol.type == Symbol::ENUM_VALUE) {
+ if (symbol.enum_value_descriptor->type() != enum_type) {
+ return AddValueError("Enum type \"" + enum_type->full_name() +
+ "\" has no value named \"" + value_name + "\" for option \"" +
+ option_field->full_name() +
+ "\". This appears to be a value from a sibling type.");
+ } else {
+ enum_value = symbol.enum_value_descriptor;
+ }
+ }
+ } else {
+ // The enum type is in the generated pool, so we can search for the
+ // value there.
+ enum_value = enum_type->FindValueByName(value_name);
+ }
+
+ if (enum_value == NULL) {
+ return AddValueError("Enum type \"" +
+ option_field->enum_type()->full_name() +
+ "\" has no value named \"" + value_name + "\" for "
+ "option \"" + option_field->full_name() + "\".");
+ } else {
+ // Sign-extension is not a problem, since we cast directly from int32 to
+ // uint64, without first going through uint32.
+ unknown_fields->AddVarint(option_field->number(),
+ static_cast<uint64>(static_cast<int64>(enum_value->number())));
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (!uninterpreted_option_->has_string_value()) {
+ return AddValueError("Value must be quoted string for string option "
+ "\"" + option_field->full_name() + "\".");
+ }
+ // The string has already been unquoted and unescaped by the parser.
+ unknown_fields->AddLengthDelimited(option_field->number(),
+ uninterpreted_option_->string_value());
+ break;
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (!SetAggregateOption(option_field, unknown_fields)) {
+ return false;
+ }
+ break;
+ }
+
+ return true;
+}
+
+class DescriptorBuilder::OptionInterpreter::AggregateOptionFinder
+ : public TextFormat::Finder {
+ public:
+ DescriptorBuilder* builder_;
+
+ virtual const FieldDescriptor* FindExtension(
+ Message* message, const string& name) const {
+ assert_mutex_held(builder_->pool_);
+ const Descriptor* descriptor = message->GetDescriptor();
+ Symbol result = builder_->LookupSymbolNoPlaceholder(
+ name, descriptor->full_name());
+ if (result.type == Symbol::FIELD &&
+ result.field_descriptor->is_extension()) {
+ return result.field_descriptor;
+ } else if (result.type == Symbol::MESSAGE &&
+ descriptor->options().message_set_wire_format()) {
+ const Descriptor* foreign_type = result.descriptor;
+ // The text format allows MessageSet items to be specified using
+ // the type name, rather than the extension identifier. If the symbol
+ // lookup returned a Message, and the enclosing Message has
+ // message_set_wire_format = true, then return the message set
+ // extension, if one exists.
+ for (int i = 0; i < foreign_type->extension_count(); i++) {
+ const FieldDescriptor* extension = foreign_type->extension(i);
+ if (extension->containing_type() == descriptor &&
+ extension->type() == FieldDescriptor::TYPE_MESSAGE &&
+ extension->is_optional() &&
+ extension->message_type() == foreign_type) {
+ // Found it.
+ return extension;
+ }
+ }
+ }
+ return NULL;
+ }
+};
+
+// A custom error collector to record any text-format parsing errors
+namespace {
+class AggregateErrorCollector : public io::ErrorCollector {
+ public:
+ string error_;
+
+ virtual void AddError(int /* line */, int /* column */,
+ const string& message) {
+ if (!error_.empty()) {
+ error_ += "; ";
+ }
+ error_ += message;
+ }
+
+ virtual void AddWarning(int /* line */, int /* column */,
+ const string& /* message */) {
+ // Ignore warnings
+ }
+};
+}
+
+// We construct a dynamic message of the type corresponding to
+// option_field, parse the supplied text-format string into this
+// message, and serialize the resulting message to produce the value.
+bool DescriptorBuilder::OptionInterpreter::SetAggregateOption(
+ const FieldDescriptor* option_field,
+ UnknownFieldSet* unknown_fields) {
+ if (!uninterpreted_option_->has_aggregate_value()) {
+ return AddValueError("Option \"" + option_field->full_name() +
+ "\" is a message. To set the entire message, use "
+ "syntax like \"" + option_field->name() +
+ " = { <proto text format> }\". "
+ "To set fields within it, use "
+ "syntax like \"" + option_field->name() +
+ ".foo = value\".");
+ }
+
+ const Descriptor* type = option_field->message_type();
+ google::protobuf::scoped_ptr<Message> dynamic(dynamic_factory_.GetPrototype(type)->New());
+ GOOGLE_CHECK(dynamic.get() != NULL)
+ << "Could not create an instance of " << option_field->DebugString();
+
+ AggregateErrorCollector collector;
+ AggregateOptionFinder finder;
+ finder.builder_ = builder_;
+ TextFormat::Parser parser;
+ parser.RecordErrorsTo(&collector);
+ parser.SetFinder(&finder);
+ if (!parser.ParseFromString(uninterpreted_option_->aggregate_value(),
+ dynamic.get())) {
+ AddValueError("Error while parsing option value for \"" +
+ option_field->name() + "\": " + collector.error_);
+ return false;
+ } else {
+ string serial;
+ dynamic->SerializeToString(&serial); // Never fails
+ if (option_field->type() == FieldDescriptor::TYPE_MESSAGE) {
+ unknown_fields->AddLengthDelimited(option_field->number(), serial);
+ } else {
+ GOOGLE_CHECK_EQ(option_field->type(), FieldDescriptor::TYPE_GROUP);
+ UnknownFieldSet* group = unknown_fields->AddGroup(option_field->number());
+ group->ParseFromString(serial);
+ }
+ return true;
+ }
+}
+
+void DescriptorBuilder::OptionInterpreter::SetInt32(int number, int32 value,
+ FieldDescriptor::Type type, UnknownFieldSet* unknown_fields) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT32:
+ unknown_fields->AddVarint(number,
+ static_cast<uint64>(static_cast<int64>(value)));
+ break;
+
+ case FieldDescriptor::TYPE_SFIXED32:
+ unknown_fields->AddFixed32(number, static_cast<uint32>(value));
+ break;
+
+ case FieldDescriptor::TYPE_SINT32:
+ unknown_fields->AddVarint(number,
+ google::protobuf::internal::WireFormatLite::ZigZagEncode32(value));
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Invalid wire type for CPPTYPE_INT32: " << type;
+ break;
+ }
+}
+
+void DescriptorBuilder::OptionInterpreter::SetInt64(int number, int64 value,
+ FieldDescriptor::Type type, UnknownFieldSet* unknown_fields) {
+ switch (type) {
+ case FieldDescriptor::TYPE_INT64:
+ unknown_fields->AddVarint(number, static_cast<uint64>(value));
+ break;
+
+ case FieldDescriptor::TYPE_SFIXED64:
+ unknown_fields->AddFixed64(number, static_cast<uint64>(value));
+ break;
+
+ case FieldDescriptor::TYPE_SINT64:
+ unknown_fields->AddVarint(number,
+ google::protobuf::internal::WireFormatLite::ZigZagEncode64(value));
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Invalid wire type for CPPTYPE_INT64: " << type;
+ break;
+ }
+}
+
+void DescriptorBuilder::OptionInterpreter::SetUInt32(int number, uint32 value,
+ FieldDescriptor::Type type, UnknownFieldSet* unknown_fields) {
+ switch (type) {
+ case FieldDescriptor::TYPE_UINT32:
+ unknown_fields->AddVarint(number, static_cast<uint64>(value));
+ break;
+
+ case FieldDescriptor::TYPE_FIXED32:
+ unknown_fields->AddFixed32(number, static_cast<uint32>(value));
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Invalid wire type for CPPTYPE_UINT32: " << type;
+ break;
+ }
+}
+
+void DescriptorBuilder::OptionInterpreter::SetUInt64(int number, uint64 value,
+ FieldDescriptor::Type type, UnknownFieldSet* unknown_fields) {
+ switch (type) {
+ case FieldDescriptor::TYPE_UINT64:
+ unknown_fields->AddVarint(number, value);
+ break;
+
+ case FieldDescriptor::TYPE_FIXED64:
+ unknown_fields->AddFixed64(number, value);
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Invalid wire type for CPPTYPE_UINT64: " << type;
+ break;
+ }
+}
+
+void DescriptorBuilder::LogUnusedDependency(const FileDescriptorProto& proto,
+ const FileDescriptor* result) {
+
+ if (!unused_dependency_.empty()) {
+ std::set<string> annotation_extensions;
+ annotation_extensions.insert("google.protobuf.MessageOptions");
+ annotation_extensions.insert("google.protobuf.FileOptions");
+ annotation_extensions.insert("google.protobuf.FieldOptions");
+ annotation_extensions.insert("google.protobuf.EnumOptions");
+ annotation_extensions.insert("google.protobuf.EnumValueOptions");
+ annotation_extensions.insert("google.protobuf.ServiceOptions");
+ annotation_extensions.insert("google.protobuf.MethodOptions");
+ annotation_extensions.insert("google.protobuf.StreamOptions");
+ for (set<const FileDescriptor*>::const_iterator
+ it = unused_dependency_.begin();
+ it != unused_dependency_.end(); ++it) {
+ // Do not log warnings for proto files which extend annotations.
+ int i;
+ for (i = 0 ; i < (*it)->extension_count(); ++i) {
+ if (annotation_extensions.find(
+ (*it)->extension(i)->containing_type()->full_name())
+ != annotation_extensions.end()) {
+ break;
+ }
+ }
+ // Log warnings for unused imported files.
+ if (i == (*it)->extension_count()) {
+ string error_message = "Import " + (*it)->name() + " but not used.";
+ AddWarning((*it)->name(), proto, DescriptorPool::ErrorCollector::OTHER,
+ error_message);
+ }
+ }
+ }
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.h b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.h
new file mode 100644
index 0000000000..b040b62c8b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.h
@@ -0,0 +1,1919 @@
+// 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 classes which describe a type of protocol message.
+// You can use a message's descriptor to learn at runtime what fields
+// it contains and what the types of those fields are. The Message
+// interface also allows you to dynamically access and modify individual
+// fields by passing the FieldDescriptor of the field you are interested
+// in.
+//
+// Most users will not care about descriptors, because they will write
+// code specific to certain protocol types and will simply use the classes
+// generated by the protocol compiler directly. Advanced users who want
+// to operate on arbitrary types (not known at compile time) may want to
+// read descriptors in order to learn about the contents of a message.
+// A very small number of users will want to construct their own
+// Descriptors, either because they are implementing Message manually or
+// because they are writing something like the protocol compiler.
+//
+// For an example of how you might use descriptors, see the code example
+// at the top of message.h.
+
+#ifndef GOOGLE_PROTOBUF_DESCRIPTOR_H__
+#define GOOGLE_PROTOBUF_DESCRIPTOR_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <set>
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+
+// TYPE_BOOL is defined in the MacOS's ConditionalMacros.h.
+#ifdef TYPE_BOOL
+#undef TYPE_BOOL
+#endif // TYPE_BOOL
+
+namespace google {
+namespace protobuf {
+
+// Defined in this file.
+class Descriptor;
+class FieldDescriptor;
+class OneofDescriptor;
+class EnumDescriptor;
+class EnumValueDescriptor;
+class ServiceDescriptor;
+class MethodDescriptor;
+class FileDescriptor;
+class DescriptorDatabase;
+class DescriptorPool;
+
+// Defined in descriptor.proto
+class DescriptorProto;
+class FieldDescriptorProto;
+class OneofDescriptorProto;
+class EnumDescriptorProto;
+class EnumValueDescriptorProto;
+class ServiceDescriptorProto;
+class MethodDescriptorProto;
+class FileDescriptorProto;
+class MessageOptions;
+class FieldOptions;
+class OneofOptions;
+class EnumOptions;
+class EnumValueOptions;
+class ServiceOptions;
+class MethodOptions;
+class FileOptions;
+class UninterpretedOption;
+class SourceCodeInfo;
+
+// Defined in message.h
+class Message;
+
+// Defined in descriptor.cc
+class DescriptorBuilder;
+class FileDescriptorTables;
+
+// Defined in unknown_field_set.h.
+class UnknownField;
+
+// Defined in generated_message_reflection.h.
+namespace internal {
+class GeneratedMessageReflection;
+} // namespace internal
+
+// Defined in command_line_interface.cc
+namespace compiler {
+class CommandLineInterface;
+} // namespace compiler
+
+namespace descriptor_unittest {
+class DescriptorTest;
+} // namespace descriptor_unittest
+
+// Defined in printer.h
+namespace io {
+class Printer;
+} // namespace io
+
+// NB, all indices are zero-based.
+struct SourceLocation {
+ int start_line;
+ int end_line;
+ int start_column;
+ int end_column;
+
+ // Doc comments found at the source location.
+ // See the comments in SourceCodeInfo.Location (descriptor.proto) for details.
+ string leading_comments;
+ string trailing_comments;
+ vector<string> leading_detached_comments;
+};
+
+// Options when generating machine-parsable output from a descriptor with
+// DebugString().
+struct DebugStringOptions {
+ // include original user comments as recorded in SourceLocation entries. N.B.
+ // that this must be |false| by default: several other pieces of code (for
+ // example, the C++ code generation for fields in the proto compiler) rely on
+ // DebugString() output being unobstructed by user comments.
+ bool include_comments;
+ // If true, elide the braced body in the debug string.
+ bool elide_group_body;
+ bool elide_oneof_body;
+
+ DebugStringOptions()
+ : include_comments(false),
+ elide_group_body(false),
+ elide_oneof_body(false) {}
+};
+
+// Describes a type of protocol message, or a particular group within a
+// message. To obtain the Descriptor for a given message object, call
+// Message::GetDescriptor(). Generated message classes also have a
+// static method called descriptor() which returns the type's descriptor.
+// Use DescriptorPool to construct your own descriptors.
+class LIBPROTOBUF_EXPORT Descriptor {
+ public:
+ // The name of the message type, not including its scope.
+ const string& name() const;
+
+ // The fully-qualified name of the message type, scope delimited by
+ // periods. For example, message type "Foo" which is declared in package
+ // "bar" has full name "bar.Foo". If a type "Baz" is nested within
+ // Foo, Baz's full_name is "bar.Foo.Baz". To get only the part that
+ // comes after the last '.', use name().
+ const string& full_name() const;
+
+ // Index of this descriptor within the file or containing type's message
+ // type array.
+ int index() const;
+
+ // The .proto file in which this message type was defined. Never NULL.
+ const FileDescriptor* file() const;
+
+ // If this Descriptor describes a nested type, this returns the type
+ // in which it is nested. Otherwise, returns NULL.
+ const Descriptor* containing_type() const;
+
+ // Get options for this message type. These are specified in the .proto file
+ // by placing lines like "option foo = 1234;" in the message definition.
+ // Allowed options are defined by MessageOptions in
+ // google/protobuf/descriptor.proto, and any available extensions of that
+ // message.
+ const MessageOptions& options() const;
+
+ // Write the contents of this Descriptor into the given DescriptorProto.
+ // The target DescriptorProto must be clear before calling this; if it
+ // isn't, the result may be garbage.
+ void CopyTo(DescriptorProto* proto) const;
+
+ // Write the contents of this decriptor in a human-readable form. Output
+ // will be suitable for re-parsing.
+ string DebugString() const;
+
+ // Similar to DebugString(), but additionally takes options (e.g.,
+ // include original user comments in output).
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+ // Returns true if this is a placeholder for an unknown type. This will
+ // only be the case if this descriptor comes from a DescriptorPool
+ // with AllowUnknownDependencies() set.
+ bool is_placeholder() const;
+
+ // Field stuff -----------------------------------------------------
+
+ // The number of fields in this message type.
+ int field_count() const;
+ // Gets a field by index, where 0 <= index < field_count().
+ // These are returned in the order they were defined in the .proto file.
+ const FieldDescriptor* field(int index) const;
+
+ // Looks up a field by declared tag number. Returns NULL if no such field
+ // exists.
+ const FieldDescriptor* FindFieldByNumber(int number) const;
+ // Looks up a field by name. Returns NULL if no such field exists.
+ const FieldDescriptor* FindFieldByName(const string& name) const;
+
+ // Looks up a field by lowercased name (as returned by lowercase_name()).
+ // This lookup may be ambiguous if multiple field names differ only by case,
+ // in which case the field returned is chosen arbitrarily from the matches.
+ const FieldDescriptor* FindFieldByLowercaseName(
+ const string& lowercase_name) const;
+
+ // Looks up a field by camel-case name (as returned by camelcase_name()).
+ // This lookup may be ambiguous if multiple field names differ in a way that
+ // leads them to have identical camel-case names, in which case the field
+ // returned is chosen arbitrarily from the matches.
+ const FieldDescriptor* FindFieldByCamelcaseName(
+ const string& camelcase_name) const;
+
+ // The number of oneofs in this message type.
+ int oneof_decl_count() const;
+ // Get a oneof by index, where 0 <= index < oneof_decl_count().
+ // These are returned in the order they were defined in the .proto file.
+ const OneofDescriptor* oneof_decl(int index) const;
+
+ // Looks up a oneof by name. Returns NULL if no such oneof exists.
+ const OneofDescriptor* FindOneofByName(const string& name) const;
+
+ // Nested type stuff -----------------------------------------------
+
+ // The number of nested types in this message type.
+ int nested_type_count() const;
+ // Gets a nested type by index, where 0 <= index < nested_type_count().
+ // These are returned in the order they were defined in the .proto file.
+ const Descriptor* nested_type(int index) const;
+
+ // Looks up a nested type by name. Returns NULL if no such nested type
+ // exists.
+ const Descriptor* FindNestedTypeByName(const string& name) const;
+
+ // Enum stuff ------------------------------------------------------
+
+ // The number of enum types in this message type.
+ int enum_type_count() const;
+ // Gets an enum type by index, where 0 <= index < enum_type_count().
+ // These are returned in the order they were defined in the .proto file.
+ const EnumDescriptor* enum_type(int index) const;
+
+ // Looks up an enum type by name. Returns NULL if no such enum type exists.
+ const EnumDescriptor* FindEnumTypeByName(const string& name) const;
+
+ // Looks up an enum value by name, among all enum types in this message.
+ // Returns NULL if no such value exists.
+ const EnumValueDescriptor* FindEnumValueByName(const string& name) const;
+
+ // Extensions ------------------------------------------------------
+
+ // A range of field numbers which are designated for third-party
+ // extensions.
+ struct ExtensionRange {
+ int start; // inclusive
+ int end; // exclusive
+ };
+
+ // The number of extension ranges in this message type.
+ int extension_range_count() const;
+ // Gets an extension range by index, where 0 <= index <
+ // extension_range_count(). These are returned in the order they were defined
+ // in the .proto file.
+ const ExtensionRange* extension_range(int index) const;
+
+ // Returns true if the number is in one of the extension ranges.
+ bool IsExtensionNumber(int number) const;
+
+ // Returns NULL if no extension range contains the given number.
+ const ExtensionRange* FindExtensionRangeContainingNumber(int number) const;
+
+ // The number of extensions -- extending *other* messages -- that were
+ // defined nested within this message type's scope.
+ int extension_count() const;
+ // Get an extension by index, where 0 <= index < extension_count().
+ // These are returned in the order they were defined in the .proto file.
+ const FieldDescriptor* extension(int index) const;
+
+ // Looks up a named extension (which extends some *other* message type)
+ // defined within this message type's scope.
+ const FieldDescriptor* FindExtensionByName(const string& name) const;
+
+ // Similar to FindFieldByLowercaseName(), but finds extensions defined within
+ // this message type's scope.
+ const FieldDescriptor* FindExtensionByLowercaseName(const string& name) const;
+
+ // Similar to FindFieldByCamelcaseName(), but finds extensions defined within
+ // this message type's scope.
+ const FieldDescriptor* FindExtensionByCamelcaseName(const string& name) const;
+
+ // Reserved fields -------------------------------------------------
+
+ // A range of reserved field numbers.
+ struct ReservedRange {
+ int start; // inclusive
+ int end; // exclusive
+ };
+
+ // The number of reserved ranges in this message type.
+ int reserved_range_count() const;
+ // Gets an reserved range by index, where 0 <= index <
+ // reserved_range_count(). These are returned in the order they were defined
+ // in the .proto file.
+ const ReservedRange* reserved_range(int index) const;
+
+ // Returns true if the number is in one of the reserved ranges.
+ bool IsReservedNumber(int number) const;
+
+ // Returns NULL if no reserved range contains the given number.
+ const ReservedRange* FindReservedRangeContainingNumber(int number) const;
+
+ // The number of reserved field names in this message type.
+ int reserved_name_count() const;
+
+ // Gets a reserved name by index, where 0 <= index < reserved_name_count().
+ const string& reserved_name(int index) const;
+
+ // Returns true if the field name is reserved.
+ bool IsReservedName(const string& name) const;
+
+ // Source Location ---------------------------------------------------
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of this message declaration. Returns false and leaves
+ // |*out_location| unchanged iff location information was not available.
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ private:
+ typedef MessageOptions OptionsType;
+
+ // Allows tests to test CopyTo(proto, true).
+ friend class ::google::protobuf::descriptor_unittest::DescriptorTest;
+
+ // Allows access to GetLocationPath for annotations.
+ friend class ::google::protobuf::io::Printer;
+
+ // Fill the json_name field of FieldDescriptorProto.
+ void CopyJsonNameTo(DescriptorProto* proto) const;
+
+ // Internal version of DebugString; controls the level of indenting for
+ // correct depth. Takes |options| to control debug-string options, and
+ // |include_opening_clause| to indicate whether the "message ... " part of the
+ // clause has already been generated (this varies depending on context).
+ void DebugString(int depth, string *contents,
+ const DebugStringOptions& options,
+ bool include_opening_clause) const;
+
+ // Walks up the descriptor tree to generate the source location path
+ // to this descriptor from the file root.
+ void GetLocationPath(std::vector<int>* output) const;
+
+ const string* name_;
+ const string* full_name_;
+ const FileDescriptor* file_;
+ const Descriptor* containing_type_;
+ const MessageOptions* options_;
+
+ // True if this is a placeholder for an unknown type.
+ bool is_placeholder_;
+ // True if this is a placeholder and the type name wasn't fully-qualified.
+ bool is_unqualified_placeholder_;
+
+ int field_count_;
+ FieldDescriptor* fields_;
+ int oneof_decl_count_;
+ OneofDescriptor* oneof_decls_;
+ int nested_type_count_;
+ Descriptor* nested_types_;
+ int enum_type_count_;
+ EnumDescriptor* enum_types_;
+ int extension_range_count_;
+ ExtensionRange* extension_ranges_;
+ int extension_count_;
+ FieldDescriptor* extensions_;
+ int reserved_range_count_;
+ ReservedRange* reserved_ranges_;
+ int reserved_name_count_;
+ const string** reserved_names_;
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<Descriptor>() and AllocateArray<Descriptor>() in descriptor.cc
+ // and update them to initialize the field.
+
+ // Must be constructed using DescriptorPool.
+ Descriptor() {}
+ friend class DescriptorBuilder;
+ friend class EnumDescriptor;
+ friend class FieldDescriptor;
+ friend class OneofDescriptor;
+ friend class MethodDescriptor;
+ friend class FileDescriptor;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Descriptor);
+};
+
+// Describes a single field of a message. To get the descriptor for a given
+// field, first get the Descriptor for the message in which it is defined,
+// then call Descriptor::FindFieldByName(). To get a FieldDescriptor for
+// an extension, do one of the following:
+// - Get the Descriptor or FileDescriptor for its containing scope, then
+// call Descriptor::FindExtensionByName() or
+// FileDescriptor::FindExtensionByName().
+// - Given a DescriptorPool, call DescriptorPool::FindExtensionByNumber().
+// - Given a Reflection for a message object, call
+// Reflection::FindKnownExtensionByName() or
+// Reflection::FindKnownExtensionByNumber().
+// Use DescriptorPool to construct your own descriptors.
+class LIBPROTOBUF_EXPORT FieldDescriptor {
+ public:
+ // Identifies a field type. 0 is reserved for errors. The order is weird
+ // for historical reasons. Types 12 and up are new in proto2.
+ enum Type {
+ TYPE_DOUBLE = 1, // double, exactly eight bytes on the wire.
+ TYPE_FLOAT = 2, // float, exactly four bytes on the wire.
+ TYPE_INT64 = 3, // int64, varint on the wire. Negative numbers
+ // take 10 bytes. Use TYPE_SINT64 if negative
+ // values are likely.
+ TYPE_UINT64 = 4, // uint64, varint on the wire.
+ TYPE_INT32 = 5, // int32, varint on the wire. Negative numbers
+ // take 10 bytes. Use TYPE_SINT32 if negative
+ // values are likely.
+ TYPE_FIXED64 = 6, // uint64, exactly eight bytes on the wire.
+ TYPE_FIXED32 = 7, // uint32, exactly four bytes on the wire.
+ TYPE_BOOL = 8, // bool, varint on the wire.
+ TYPE_STRING = 9, // UTF-8 text.
+ TYPE_GROUP = 10, // Tag-delimited message. Deprecated.
+ TYPE_MESSAGE = 11, // Length-delimited message.
+
+ TYPE_BYTES = 12, // Arbitrary byte array.
+ TYPE_UINT32 = 13, // uint32, varint on the wire
+ TYPE_ENUM = 14, // Enum, varint on the wire
+ TYPE_SFIXED32 = 15, // int32, exactly four bytes on the wire
+ TYPE_SFIXED64 = 16, // int64, exactly eight bytes on the wire
+ TYPE_SINT32 = 17, // int32, ZigZag-encoded varint on the wire
+ TYPE_SINT64 = 18, // int64, ZigZag-encoded varint on the wire
+
+ MAX_TYPE = 18, // Constant useful for defining lookup tables
+ // indexed by Type.
+ };
+
+ // Specifies the C++ data type used to represent the field. There is a
+ // fixed mapping from Type to CppType where each Type maps to exactly one
+ // CppType. 0 is reserved for errors.
+ enum CppType {
+ CPPTYPE_INT32 = 1, // TYPE_INT32, TYPE_SINT32, TYPE_SFIXED32
+ CPPTYPE_INT64 = 2, // TYPE_INT64, TYPE_SINT64, TYPE_SFIXED64
+ CPPTYPE_UINT32 = 3, // TYPE_UINT32, TYPE_FIXED32
+ CPPTYPE_UINT64 = 4, // TYPE_UINT64, TYPE_FIXED64
+ CPPTYPE_DOUBLE = 5, // TYPE_DOUBLE
+ CPPTYPE_FLOAT = 6, // TYPE_FLOAT
+ CPPTYPE_BOOL = 7, // TYPE_BOOL
+ CPPTYPE_ENUM = 8, // TYPE_ENUM
+ CPPTYPE_STRING = 9, // TYPE_STRING, TYPE_BYTES
+ CPPTYPE_MESSAGE = 10, // TYPE_MESSAGE, TYPE_GROUP
+
+ MAX_CPPTYPE = 10, // Constant useful for defining lookup tables
+ // indexed by CppType.
+ };
+
+ // Identifies whether the field is optional, required, or repeated. 0 is
+ // reserved for errors.
+ enum Label {
+ LABEL_OPTIONAL = 1, // optional
+ LABEL_REQUIRED = 2, // required
+ LABEL_REPEATED = 3, // repeated
+
+ MAX_LABEL = 3, // Constant useful for defining lookup tables
+ // indexed by Label.
+ };
+
+ // Valid field numbers are positive integers up to kMaxNumber.
+ static const int kMaxNumber = (1 << 29) - 1;
+
+ // First field number reserved for the protocol buffer library implementation.
+ // Users may not declare fields that use reserved numbers.
+ static const int kFirstReservedNumber = 19000;
+ // Last field number reserved for the protocol buffer library implementation.
+ // Users may not declare fields that use reserved numbers.
+ static const int kLastReservedNumber = 19999;
+
+ const string& name() const; // Name of this field within the message.
+ const string& full_name() const; // Fully-qualified name of the field.
+ const string& json_name() const; // JSON name of this field.
+ const FileDescriptor* file() const;// File in which this field was defined.
+ bool is_extension() const; // Is this an extension field?
+ int number() const; // Declared tag number.
+
+ // Same as name() except converted to lower-case. This (and especially the
+ // FindFieldByLowercaseName() method) can be useful when parsing formats
+ // which prefer to use lowercase naming style. (Although, technically
+ // field names should be lowercased anyway according to the protobuf style
+ // guide, so this only makes a difference when dealing with old .proto files
+ // which do not follow the guide.)
+ const string& lowercase_name() const;
+
+ // Same as name() except converted to camel-case. In this conversion, any
+ // time an underscore appears in the name, it is removed and the next
+ // letter is capitalized. Furthermore, the first letter of the name is
+ // lower-cased. Examples:
+ // FooBar -> fooBar
+ // foo_bar -> fooBar
+ // fooBar -> fooBar
+ // This (and especially the FindFieldByCamelcaseName() method) can be useful
+ // when parsing formats which prefer to use camel-case naming style.
+ const string& camelcase_name() const;
+
+ Type type() const; // Declared type of this field.
+ const char* type_name() const; // Name of the declared type.
+ CppType cpp_type() const; // C++ type of this field.
+ const char* cpp_type_name() const; // Name of the C++ type.
+ Label label() const; // optional/required/repeated
+
+ bool is_required() const; // shorthand for label() == LABEL_REQUIRED
+ bool is_optional() const; // shorthand for label() == LABEL_OPTIONAL
+ bool is_repeated() const; // shorthand for label() == LABEL_REPEATED
+ bool is_packable() const; // shorthand for is_repeated() &&
+ // IsTypePackable(type())
+ bool is_packed() const; // shorthand for is_packable() &&
+ // options().packed()
+ bool is_map() const; // shorthand for type() == TYPE_MESSAGE &&
+ // message_type()->options().map_entry()
+
+ // Index of this field within the message's field array, or the file or
+ // extension scope's extensions array.
+ int index() const;
+
+ // Does this field have an explicitly-declared default value?
+ bool has_default_value() const;
+
+ // Get the field default value if cpp_type() == CPPTYPE_INT32. If no
+ // explicit default was defined, the default is 0.
+ int32 default_value_int32() const;
+ // Get the field default value if cpp_type() == CPPTYPE_INT64. If no
+ // explicit default was defined, the default is 0.
+ int64 default_value_int64() const;
+ // Get the field default value if cpp_type() == CPPTYPE_UINT32. If no
+ // explicit default was defined, the default is 0.
+ uint32 default_value_uint32() const;
+ // Get the field default value if cpp_type() == CPPTYPE_UINT64. If no
+ // explicit default was defined, the default is 0.
+ uint64 default_value_uint64() const;
+ // Get the field default value if cpp_type() == CPPTYPE_FLOAT. If no
+ // explicit default was defined, the default is 0.0.
+ float default_value_float() const;
+ // Get the field default value if cpp_type() == CPPTYPE_DOUBLE. If no
+ // explicit default was defined, the default is 0.0.
+ double default_value_double() const;
+ // Get the field default value if cpp_type() == CPPTYPE_BOOL. If no
+ // explicit default was defined, the default is false.
+ bool default_value_bool() const;
+ // Get the field default value if cpp_type() == CPPTYPE_ENUM. If no
+ // explicit default was defined, the default is the first value defined
+ // in the enum type (all enum types are required to have at least one value).
+ // This never returns NULL.
+ const EnumValueDescriptor* default_value_enum() const;
+ // Get the field default value if cpp_type() == CPPTYPE_STRING. If no
+ // explicit default was defined, the default is the empty string.
+ const string& default_value_string() const;
+
+ // The Descriptor for the message of which this is a field. For extensions,
+ // this is the extended type. Never NULL.
+ const Descriptor* containing_type() const;
+
+ // If the field is a member of a oneof, this is the one, otherwise this is
+ // NULL.
+ const OneofDescriptor* containing_oneof() const;
+
+ // If the field is a member of a oneof, returns the index in that oneof.
+ int index_in_oneof() const;
+
+ // An extension may be declared within the scope of another message. If this
+ // field is an extension (is_extension() is true), then extension_scope()
+ // returns that message, or NULL if the extension was declared at global
+ // scope. If this is not an extension, extension_scope() is undefined (may
+ // assert-fail).
+ const Descriptor* extension_scope() const;
+
+ // If type is TYPE_MESSAGE or TYPE_GROUP, returns a descriptor for the
+ // message or the group type. Otherwise, returns null.
+ const Descriptor* message_type() const;
+ // If type is TYPE_ENUM, returns a descriptor for the enum. Otherwise,
+ // returns null.
+ const EnumDescriptor* enum_type() const;
+
+ // Get the FieldOptions for this field. This includes things listed in
+ // square brackets after the field definition. E.g., the field:
+ // optional string text = 1 [ctype=CORD];
+ // has the "ctype" option set. Allowed options are defined by FieldOptions
+ // in google/protobuf/descriptor.proto, and any available extensions of that
+ // message.
+ const FieldOptions& options() const;
+
+ // See Descriptor::CopyTo().
+ void CopyTo(FieldDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ string DebugString() const;
+
+ // See Descriptor::DebugStringWithOptions().
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+ // Helper method to get the CppType for a particular Type.
+ static CppType TypeToCppType(Type type);
+
+ // Helper method to get the name of a Type.
+ static const char* TypeName(Type type);
+
+ // Helper method to get the name of a CppType.
+ static const char* CppTypeName(CppType cpp_type);
+
+ // Return true iff [packed = true] is valid for fields of this type.
+ static inline bool IsTypePackable(Type field_type);
+
+ // Source Location ---------------------------------------------------
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of this field declaration. Returns false and leaves
+ // |*out_location| unchanged iff location information was not available.
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ private:
+ typedef FieldOptions OptionsType;
+
+ // Allows access to GetLocationPath for annotations.
+ friend class ::google::protobuf::io::Printer;
+
+ // Fill the json_name field of FieldDescriptorProto.
+ void CopyJsonNameTo(FieldDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ enum PrintLabelFlag { PRINT_LABEL, OMIT_LABEL };
+ void DebugString(int depth, PrintLabelFlag print_label_flag,
+ string* contents, const DebugStringOptions& options) const;
+
+ // formats the default value appropriately and returns it as a string.
+ // Must have a default value to call this. If quote_string_type is true, then
+ // types of CPPTYPE_STRING whill be surrounded by quotes and CEscaped.
+ string DefaultValueAsString(bool quote_string_type) const;
+
+ // Helper function that returns the field type name for DebugString.
+ string FieldTypeNameDebugString() const;
+
+ // Walks up the descriptor tree to generate the source location path
+ // to this descriptor from the file root.
+ void GetLocationPath(std::vector<int>* output) const;
+
+ const string* name_;
+ const string* full_name_;
+ const string* lowercase_name_;
+ const string* camelcase_name_;
+ // Whether the user has specified the json_name field option in the .proto
+ // file.
+ bool has_json_name_;
+ // If has_json_name_ is true, it's the value specified by the user.
+ // Otherwise, it has the same value as lowercase_name_.
+ const string* json_name_;
+ const FileDescriptor* file_;
+ int number_;
+ Type type_;
+ Label label_;
+ bool is_extension_;
+ int index_in_oneof_;
+ const Descriptor* containing_type_;
+ const OneofDescriptor* containing_oneof_;
+ const Descriptor* extension_scope_;
+ const Descriptor* message_type_;
+ const EnumDescriptor* enum_type_;
+ const FieldOptions* options_;
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<FieldDescriptor>() and AllocateArray<FieldDescriptor>() in
+ // descriptor.cc and update them to initialize the field.
+
+ bool has_default_value_;
+ union {
+ int32 default_value_int32_;
+ int64 default_value_int64_;
+ uint32 default_value_uint32_;
+ uint64 default_value_uint64_;
+ float default_value_float_;
+ double default_value_double_;
+ bool default_value_bool_;
+
+ const EnumValueDescriptor* default_value_enum_;
+ const string* default_value_string_;
+ };
+
+ static const CppType kTypeToCppTypeMap[MAX_TYPE + 1];
+
+ static const char * const kTypeToName[MAX_TYPE + 1];
+
+ static const char * const kCppTypeToName[MAX_CPPTYPE + 1];
+
+ static const char * const kLabelToName[MAX_LABEL + 1];
+
+ // Must be constructed using DescriptorPool.
+ FieldDescriptor() {}
+ friend class DescriptorBuilder;
+ friend class FileDescriptor;
+ friend class Descriptor;
+ friend class OneofDescriptor;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldDescriptor);
+};
+
+// Describes a oneof defined in a message type.
+class LIBPROTOBUF_EXPORT OneofDescriptor {
+ public:
+ const string& name() const; // Name of this oneof.
+ const string& full_name() const; // Fully-qualified name of the oneof.
+
+ // Index of this oneof within the message's oneof array.
+ int index() const;
+
+ // The Descriptor for the message containing this oneof.
+ const Descriptor* containing_type() const;
+
+ // The number of (non-extension) fields which are members of this oneof.
+ int field_count() const;
+ // Get a member of this oneof, in the order in which they were declared in the
+ // .proto file. Does not include extensions.
+ const FieldDescriptor* field(int index) const;
+
+ const OneofOptions& options() const;
+
+ // See Descriptor::CopyTo().
+ void CopyTo(OneofDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ string DebugString() const;
+
+ // See Descriptor::DebugStringWithOptions().
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+ // Source Location ---------------------------------------------------
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of this oneof declaration. Returns false and leaves
+ // |*out_location| unchanged iff location information was not available.
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ private:
+ typedef OneofOptions OptionsType;
+
+ // Allows access to GetLocationPath for annotations.
+ friend class ::google::protobuf::io::Printer;
+
+ // See Descriptor::DebugString().
+ void DebugString(int depth, string* contents,
+ const DebugStringOptions& options) const;
+
+ // Walks up the descriptor tree to generate the source location path
+ // to this descriptor from the file root.
+ void GetLocationPath(std::vector<int>* output) const;
+
+ const string* name_;
+ const string* full_name_;
+ const Descriptor* containing_type_;
+ bool is_extendable_;
+ int field_count_;
+ const FieldDescriptor** fields_;
+ const OneofOptions* options_;
+
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<OneofDescriptor>() and AllocateArray<OneofDescriptor>()
+ // in descriptor.cc and update them to initialize the field.
+
+ // Must be constructed using DescriptorPool.
+ OneofDescriptor() {}
+ friend class DescriptorBuilder;
+ friend class Descriptor;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(OneofDescriptor);
+};
+
+// Describes an enum type defined in a .proto file. To get the EnumDescriptor
+// for a generated enum type, call TypeName_descriptor(). Use DescriptorPool
+// to construct your own descriptors.
+class LIBPROTOBUF_EXPORT EnumDescriptor {
+ public:
+ // The name of this enum type in the containing scope.
+ const string& name() const;
+
+ // The fully-qualified name of the enum type, scope delimited by periods.
+ const string& full_name() const;
+
+ // Index of this enum within the file or containing message's enum array.
+ int index() const;
+
+ // The .proto file in which this enum type was defined. Never NULL.
+ const FileDescriptor* file() const;
+
+ // The number of values for this EnumDescriptor. Guaranteed to be greater
+ // than zero.
+ int value_count() const;
+ // Gets a value by index, where 0 <= index < value_count().
+ // These are returned in the order they were defined in the .proto file.
+ const EnumValueDescriptor* value(int index) const;
+
+ // Looks up a value by name. Returns NULL if no such value exists.
+ const EnumValueDescriptor* FindValueByName(const string& name) const;
+ // Looks up a value by number. Returns NULL if no such value exists. If
+ // multiple values have this number, the first one defined is returned.
+ const EnumValueDescriptor* FindValueByNumber(int number) const;
+
+ // If this enum type is nested in a message type, this is that message type.
+ // Otherwise, NULL.
+ const Descriptor* containing_type() const;
+
+ // Get options for this enum type. These are specified in the .proto file by
+ // placing lines like "option foo = 1234;" in the enum definition. Allowed
+ // options are defined by EnumOptions in google/protobuf/descriptor.proto,
+ // and any available extensions of that message.
+ const EnumOptions& options() const;
+
+ // See Descriptor::CopyTo().
+ void CopyTo(EnumDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ string DebugString() const;
+
+ // See Descriptor::DebugStringWithOptions().
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+
+ // Returns true if this is a placeholder for an unknown enum. This will
+ // only be the case if this descriptor comes from a DescriptorPool
+ // with AllowUnknownDependencies() set.
+ bool is_placeholder() const;
+
+ // Source Location ---------------------------------------------------
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of this enum declaration. Returns false and leaves
+ // |*out_location| unchanged iff location information was not available.
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ private:
+ typedef EnumOptions OptionsType;
+
+ // Allows access to GetLocationPath for annotations.
+ friend class ::google::protobuf::io::Printer;
+
+ // Looks up a value by number. If the value does not exist, dynamically
+ // creates a new EnumValueDescriptor for that value, assuming that it was
+ // unknown. If a new descriptor is created, this is done in a thread-safe way,
+ // and future calls will return the same value descriptor pointer.
+ //
+ // This is private but is used by GeneratedMessageReflection (which is
+ // friended below) to return a valid EnumValueDescriptor from GetEnum() when
+ // this feature is enabled.
+ const EnumValueDescriptor*
+ FindValueByNumberCreatingIfUnknown(int number) const;
+
+
+ // See Descriptor::DebugString().
+ void DebugString(int depth, string *contents,
+ const DebugStringOptions& options) const;
+
+ // Walks up the descriptor tree to generate the source location path
+ // to this descriptor from the file root.
+ void GetLocationPath(std::vector<int>* output) const;
+
+ const string* name_;
+ const string* full_name_;
+ const FileDescriptor* file_;
+ const Descriptor* containing_type_;
+ const EnumOptions* options_;
+
+ // True if this is a placeholder for an unknown type.
+ bool is_placeholder_;
+ // True if this is a placeholder and the type name wasn't fully-qualified.
+ bool is_unqualified_placeholder_;
+
+ int value_count_;
+ EnumValueDescriptor* values_;
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<EnumDescriptor>() and AllocateArray<EnumDescriptor>() in
+ // descriptor.cc and update them to initialize the field.
+
+ // Must be constructed using DescriptorPool.
+ EnumDescriptor() {}
+ friend class DescriptorBuilder;
+ friend class Descriptor;
+ friend class FieldDescriptor;
+ friend class EnumValueDescriptor;
+ friend class FileDescriptor;
+ friend class internal::GeneratedMessageReflection;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumDescriptor);
+};
+
+// Describes an individual enum constant of a particular type. To get the
+// EnumValueDescriptor for a given enum value, first get the EnumDescriptor
+// for its type, then use EnumDescriptor::FindValueByName() or
+// EnumDescriptor::FindValueByNumber(). Use DescriptorPool to construct
+// your own descriptors.
+class LIBPROTOBUF_EXPORT EnumValueDescriptor {
+ public:
+ const string& name() const; // Name of this enum constant.
+ int index() const; // Index within the enums's Descriptor.
+ int number() const; // Numeric value of this enum constant.
+
+ // The full_name of an enum value is a sibling symbol of the enum type.
+ // e.g. the full name of FieldDescriptorProto::TYPE_INT32 is actually
+ // "google.protobuf.FieldDescriptorProto.TYPE_INT32", NOT
+ // "google.protobuf.FieldDescriptorProto.Type.TYPE_INT32". This is to conform
+ // with C++ scoping rules for enums.
+ const string& full_name() const;
+
+ // The type of this value. Never NULL.
+ const EnumDescriptor* type() const;
+
+ // Get options for this enum value. These are specified in the .proto file
+ // by adding text like "[foo = 1234]" after an enum value definition.
+ // Allowed options are defined by EnumValueOptions in
+ // google/protobuf/descriptor.proto, and any available extensions of that
+ // message.
+ const EnumValueOptions& options() const;
+
+ // See Descriptor::CopyTo().
+ void CopyTo(EnumValueDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ string DebugString() const;
+
+ // See Descriptor::DebugStringWithOptions().
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+
+ // Source Location ---------------------------------------------------
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of this enum value declaration. Returns false and leaves
+ // |*out_location| unchanged iff location information was not available.
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ private:
+ typedef EnumValueOptions OptionsType;
+
+ // Allows access to GetLocationPath for annotations.
+ friend class ::google::protobuf::io::Printer;
+
+ // See Descriptor::DebugString().
+ void DebugString(int depth, string *contents,
+ const DebugStringOptions& options) const;
+
+ // Walks up the descriptor tree to generate the source location path
+ // to this descriptor from the file root.
+ void GetLocationPath(std::vector<int>* output) const;
+
+ const string* name_;
+ const string* full_name_;
+ int number_;
+ const EnumDescriptor* type_;
+ const EnumValueOptions* options_;
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<EnumValueDescriptor>() and AllocateArray<EnumValueDescriptor>()
+ // in descriptor.cc and update them to initialize the field.
+
+ // Must be constructed using DescriptorPool.
+ EnumValueDescriptor() {}
+ friend class DescriptorBuilder;
+ friend class EnumDescriptor;
+ friend class FileDescriptorTables;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumValueDescriptor);
+};
+
+// Describes an RPC service. To get the ServiceDescriptor for a service,
+// call Service::GetDescriptor(). Generated service classes also have a
+// static method called descriptor() which returns the type's
+// ServiceDescriptor. Use DescriptorPool to construct your own descriptors.
+class LIBPROTOBUF_EXPORT ServiceDescriptor {
+ public:
+ // The name of the service, not including its containing scope.
+ const string& name() const;
+ // The fully-qualified name of the service, scope delimited by periods.
+ const string& full_name() const;
+ // Index of this service within the file's services array.
+ int index() const;
+
+ // The .proto file in which this service was defined. Never NULL.
+ const FileDescriptor* file() const;
+
+ // Get options for this service type. These are specified in the .proto file
+ // by placing lines like "option foo = 1234;" in the service definition.
+ // Allowed options are defined by ServiceOptions in
+ // google/protobuf/descriptor.proto, and any available extensions of that
+ // message.
+ const ServiceOptions& options() const;
+
+ // The number of methods this service defines.
+ int method_count() const;
+ // Gets a MethodDescriptor by index, where 0 <= index < method_count().
+ // These are returned in the order they were defined in the .proto file.
+ const MethodDescriptor* method(int index) const;
+
+ // Look up a MethodDescriptor by name.
+ const MethodDescriptor* FindMethodByName(const string& name) const;
+ // See Descriptor::CopyTo().
+ void CopyTo(ServiceDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ string DebugString() const;
+
+ // See Descriptor::DebugStringWithOptions().
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+
+ // Source Location ---------------------------------------------------
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of this service declaration. Returns false and leaves
+ // |*out_location| unchanged iff location information was not available.
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ private:
+ typedef ServiceOptions OptionsType;
+
+ // Allows access to GetLocationPath for annotations.
+ friend class ::google::protobuf::io::Printer;
+
+ // See Descriptor::DebugString().
+ void DebugString(string *contents, const DebugStringOptions& options) const;
+
+ // Walks up the descriptor tree to generate the source location path
+ // to this descriptor from the file root.
+ void GetLocationPath(std::vector<int>* output) const;
+
+ const string* name_;
+ const string* full_name_;
+ const FileDescriptor* file_;
+ const ServiceOptions* options_;
+ int method_count_;
+ MethodDescriptor* methods_;
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<ServiceDescriptor>() and AllocateArray<ServiceDescriptor>() in
+ // descriptor.cc and update them to initialize the field.
+
+ // Must be constructed using DescriptorPool.
+ ServiceDescriptor() {}
+ friend class DescriptorBuilder;
+ friend class FileDescriptor;
+ friend class MethodDescriptor;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ServiceDescriptor);
+};
+
+// Describes an individual service method. To obtain a MethodDescriptor given
+// a service, first get its ServiceDescriptor, then call
+// ServiceDescriptor::FindMethodByName(). Use DescriptorPool to construct your
+// own descriptors.
+class LIBPROTOBUF_EXPORT MethodDescriptor {
+ public:
+ // Name of this method, not including containing scope.
+ const string& name() const;
+ // The fully-qualified name of the method, scope delimited by periods.
+ const string& full_name() const;
+ // Index within the service's Descriptor.
+ int index() const;
+
+ // Gets the service to which this method belongs. Never NULL.
+ const ServiceDescriptor* service() const;
+
+ // Gets the type of protocol message which this method accepts as input.
+ const Descriptor* input_type() const;
+ // Gets the type of protocol message which this message produces as output.
+ const Descriptor* output_type() const;
+
+ // Gets whether the client streams multiple requests.
+ bool client_streaming() const;
+ // Gets whether the server streams multiple responses.
+ bool server_streaming() const;
+
+ // Get options for this method. These are specified in the .proto file by
+ // placing lines like "option foo = 1234;" in curly-braces after a method
+ // declaration. Allowed options are defined by MethodOptions in
+ // google/protobuf/descriptor.proto, and any available extensions of that
+ // message.
+ const MethodOptions& options() const;
+
+ // See Descriptor::CopyTo().
+ void CopyTo(MethodDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ string DebugString() const;
+
+ // See Descriptor::DebugStringWithOptions().
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+
+ // Source Location ---------------------------------------------------
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of this method declaration. Returns false and leaves
+ // |*out_location| unchanged iff location information was not available.
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ private:
+ typedef MethodOptions OptionsType;
+
+ // Allows access to GetLocationPath for annotations.
+ friend class ::google::protobuf::io::Printer;
+
+ // See Descriptor::DebugString().
+ void DebugString(int depth, string *contents,
+ const DebugStringOptions& options) const;
+
+ // Walks up the descriptor tree to generate the source location path
+ // to this descriptor from the file root.
+ void GetLocationPath(std::vector<int>* output) const;
+
+ const string* name_;
+ const string* full_name_;
+ const ServiceDescriptor* service_;
+ const Descriptor* input_type_;
+ const Descriptor* output_type_;
+ const MethodOptions* options_;
+ bool client_streaming_;
+ bool server_streaming_;
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<MethodDescriptor>() and AllocateArray<MethodDescriptor>() in
+ // descriptor.cc and update them to initialize the field.
+
+ // Must be constructed using DescriptorPool.
+ MethodDescriptor() {}
+ friend class DescriptorBuilder;
+ friend class ServiceDescriptor;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MethodDescriptor);
+};
+
+
+// Describes a whole .proto file. To get the FileDescriptor for a compiled-in
+// file, get the descriptor for something defined in that file and call
+// descriptor->file(). Use DescriptorPool to construct your own descriptors.
+class LIBPROTOBUF_EXPORT FileDescriptor {
+ public:
+ // The filename, relative to the source tree.
+ // e.g. "google/protobuf/descriptor.proto"
+ const string& name() const;
+
+ // The package, e.g. "google.protobuf.compiler".
+ const string& package() const;
+
+ // The DescriptorPool in which this FileDescriptor and all its contents were
+ // allocated. Never NULL.
+ const DescriptorPool* pool() const;
+
+ // The number of files imported by this one.
+ int dependency_count() const;
+ // Gets an imported file by index, where 0 <= index < dependency_count().
+ // These are returned in the order they were defined in the .proto file.
+ const FileDescriptor* dependency(int index) const;
+
+ // The number of files public imported by this one.
+ // The public dependency list is a subset of the dependency list.
+ int public_dependency_count() const;
+ // Gets a public imported file by index, where 0 <= index <
+ // public_dependency_count().
+ // These are returned in the order they were defined in the .proto file.
+ const FileDescriptor* public_dependency(int index) const;
+
+ // The number of files that are imported for weak fields.
+ // The weak dependency list is a subset of the dependency list.
+ int weak_dependency_count() const;
+ // Gets a weak imported file by index, where 0 <= index <
+ // weak_dependency_count().
+ // These are returned in the order they were defined in the .proto file.
+ const FileDescriptor* weak_dependency(int index) const;
+
+ // Number of top-level message types defined in this file. (This does not
+ // include nested types.)
+ int message_type_count() const;
+ // Gets a top-level message type, where 0 <= index < message_type_count().
+ // These are returned in the order they were defined in the .proto file.
+ const Descriptor* message_type(int index) const;
+
+ // Number of top-level enum types defined in this file. (This does not
+ // include nested types.)
+ int enum_type_count() const;
+ // Gets a top-level enum type, where 0 <= index < enum_type_count().
+ // These are returned in the order they were defined in the .proto file.
+ const EnumDescriptor* enum_type(int index) const;
+
+ // Number of services defined in this file.
+ int service_count() const;
+ // Gets a service, where 0 <= index < service_count().
+ // These are returned in the order they were defined in the .proto file.
+ const ServiceDescriptor* service(int index) const;
+
+ // Number of extensions defined at file scope. (This does not include
+ // extensions nested within message types.)
+ int extension_count() const;
+ // Gets an extension's descriptor, where 0 <= index < extension_count().
+ // These are returned in the order they were defined in the .proto file.
+ const FieldDescriptor* extension(int index) const;
+
+ // Get options for this file. These are specified in the .proto file by
+ // placing lines like "option foo = 1234;" at the top level, outside of any
+ // other definitions. Allowed options are defined by FileOptions in
+ // google/protobuf/descriptor.proto, and any available extensions of that
+ // message.
+ const FileOptions& options() const;
+
+ // Syntax of this file.
+ enum Syntax {
+ SYNTAX_UNKNOWN = 0,
+ SYNTAX_PROTO2 = 2,
+ SYNTAX_PROTO3 = 3,
+ };
+ Syntax syntax() const;
+ static const char* SyntaxName(Syntax syntax);
+
+ // Find a top-level message type by name. Returns NULL if not found.
+ const Descriptor* FindMessageTypeByName(const string& name) const;
+ // Find a top-level enum type by name. Returns NULL if not found.
+ const EnumDescriptor* FindEnumTypeByName(const string& name) const;
+ // Find an enum value defined in any top-level enum by name. Returns NULL if
+ // not found.
+ const EnumValueDescriptor* FindEnumValueByName(const string& name) const;
+ // Find a service definition by name. Returns NULL if not found.
+ const ServiceDescriptor* FindServiceByName(const string& name) const;
+ // Find a top-level extension definition by name. Returns NULL if not found.
+ const FieldDescriptor* FindExtensionByName(const string& name) const;
+ // Similar to FindExtensionByName(), but searches by lowercased-name. See
+ // Descriptor::FindFieldByLowercaseName().
+ const FieldDescriptor* FindExtensionByLowercaseName(const string& name) const;
+ // Similar to FindExtensionByName(), but searches by camelcased-name. See
+ // Descriptor::FindFieldByCamelcaseName().
+ const FieldDescriptor* FindExtensionByCamelcaseName(const string& name) const;
+
+ // See Descriptor::CopyTo().
+ // Notes:
+ // - This method does NOT copy source code information since it is relatively
+ // large and rarely needed. See CopySourceCodeInfoTo() below.
+ void CopyTo(FileDescriptorProto* proto) const;
+ // Write the source code information of this FileDescriptor into the given
+ // FileDescriptorProto. See CopyTo() above.
+ void CopySourceCodeInfoTo(FileDescriptorProto* proto) const;
+ // Fill the json_name field of FieldDescriptorProto for all fields. Can only
+ // be called after CopyTo().
+ void CopyJsonNameTo(FileDescriptorProto* proto) const;
+
+ // See Descriptor::DebugString().
+ string DebugString() const;
+
+ // See Descriptor::DebugStringWithOptions().
+ string DebugStringWithOptions(const DebugStringOptions& options) const;
+
+ // Returns true if this is a placeholder for an unknown file. This will
+ // only be the case if this descriptor comes from a DescriptorPool
+ // with AllowUnknownDependencies() set.
+ bool is_placeholder() const;
+
+ // Updates |*out_location| to the source location of the complete extent of
+ // this file declaration (namely, the empty path).
+ bool GetSourceLocation(SourceLocation* out_location) const;
+
+ // Updates |*out_location| to the source location of the complete
+ // extent of the declaration or declaration-part denoted by |path|.
+ // Returns false and leaves |*out_location| unchanged iff location
+ // information was not available. (See SourceCodeInfo for
+ // description of path encoding.)
+ bool GetSourceLocation(const std::vector<int>& path,
+ SourceLocation* out_location) const;
+
+ private:
+ typedef FileOptions OptionsType;
+
+ const string* name_;
+ const string* package_;
+ const DescriptorPool* pool_;
+ int dependency_count_;
+ const FileDescriptor** dependencies_;
+ int public_dependency_count_;
+ int* public_dependencies_;
+ int weak_dependency_count_;
+ int* weak_dependencies_;
+ int message_type_count_;
+ Descriptor* message_types_;
+ int enum_type_count_;
+ EnumDescriptor* enum_types_;
+ int service_count_;
+ ServiceDescriptor* services_;
+ int extension_count_;
+ Syntax syntax_;
+ bool is_placeholder_;
+ FieldDescriptor* extensions_;
+ const FileOptions* options_;
+
+ const FileDescriptorTables* tables_;
+ const SourceCodeInfo* source_code_info_;
+ // IMPORTANT: If you add a new field, make sure to search for all instances
+ // of Allocate<FileDescriptor>() and AllocateArray<FileDescriptor>() in
+ // descriptor.cc and update them to initialize the field.
+
+ FileDescriptor() {}
+ friend class DescriptorBuilder;
+ friend class Descriptor;
+ friend class FieldDescriptor;
+ friend class OneofDescriptor;
+ friend class EnumDescriptor;
+ friend class EnumValueDescriptor;
+ friend class MethodDescriptor;
+ friend class ServiceDescriptor;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileDescriptor);
+};
+
+// ===================================================================
+
+// Used to construct descriptors.
+//
+// Normally you won't want to build your own descriptors. Message classes
+// constructed by the protocol compiler will provide them for you. However,
+// if you are implementing Message on your own, or if you are writing a
+// program which can operate on totally arbitrary types and needs to load
+// them from some sort of database, you might need to.
+//
+// Since Descriptors are composed of a whole lot of cross-linked bits of
+// data that would be a pain to put together manually, the
+// DescriptorPool class is provided to make the process easier. It can
+// take a FileDescriptorProto (defined in descriptor.proto), validate it,
+// and convert it to a set of nicely cross-linked Descriptors.
+//
+// DescriptorPool also helps with memory management. Descriptors are
+// composed of many objects containing static data and pointers to each
+// other. In all likelihood, when it comes time to delete this data,
+// you'll want to delete it all at once. In fact, it is not uncommon to
+// have a whole pool of descriptors all cross-linked with each other which
+// you wish to delete all at once. This class represents such a pool, and
+// handles the memory management for you.
+//
+// You can also search for descriptors within a DescriptorPool by name, and
+// extensions by number.
+class LIBPROTOBUF_EXPORT DescriptorPool {
+ public:
+ // Create a normal, empty DescriptorPool.
+ DescriptorPool();
+
+ // Constructs a DescriptorPool that, when it can't find something among the
+ // descriptors already in the pool, looks for it in the given
+ // DescriptorDatabase.
+ // Notes:
+ // - If a DescriptorPool is constructed this way, its BuildFile*() methods
+ // must not be called (they will assert-fail). The only way to populate
+ // the pool with descriptors is to call the Find*By*() methods.
+ // - The Find*By*() methods may block the calling thread if the
+ // DescriptorDatabase blocks. This in turn means that parsing messages
+ // may block if they need to look up extensions.
+ // - The Find*By*() methods will use mutexes for thread-safety, thus making
+ // them slower even when they don't have to fall back to the database.
+ // In fact, even the Find*By*() methods of descriptor objects owned by
+ // this pool will be slower, since they will have to obtain locks too.
+ // - An ErrorCollector may optionally be given to collect validation errors
+ // in files loaded from the database. If not given, errors will be printed
+ // to GOOGLE_LOG(ERROR). Remember that files are built on-demand, so this
+ // ErrorCollector may be called from any thread that calls one of the
+ // Find*By*() methods.
+ // - The DescriptorDatabase must not be mutated during the lifetime of
+ // the DescriptorPool. Even if the client takes care to avoid data races,
+ // changes to the content of the DescriptorDatabase may not be reflected
+ // in subsequent lookups in the DescriptorPool.
+ class ErrorCollector;
+ explicit DescriptorPool(DescriptorDatabase* fallback_database,
+ ErrorCollector* error_collector = NULL);
+
+ ~DescriptorPool();
+
+ // Get a pointer to the generated pool. Generated protocol message classes
+ // which are compiled into the binary will allocate their descriptors in
+ // this pool. Do not add your own descriptors to this pool.
+ static const DescriptorPool* generated_pool();
+
+
+ // Find a FileDescriptor in the pool by file name. Returns NULL if not
+ // found.
+ const FileDescriptor* FindFileByName(const string& name) const;
+
+ // Find the FileDescriptor in the pool which defines the given symbol.
+ // If any of the Find*ByName() methods below would succeed, then this is
+ // equivalent to calling that method and calling the result's file() method.
+ // Otherwise this returns NULL.
+ const FileDescriptor* FindFileContainingSymbol(
+ const string& symbol_name) const;
+
+ // Looking up descriptors ------------------------------------------
+ // These find descriptors by fully-qualified name. These will find both
+ // top-level descriptors and nested descriptors. They return NULL if not
+ // found.
+
+ const Descriptor* FindMessageTypeByName(const string& name) const;
+ const FieldDescriptor* FindFieldByName(const string& name) const;
+ const FieldDescriptor* FindExtensionByName(const string& name) const;
+ const OneofDescriptor* FindOneofByName(const string& name) const;
+ const EnumDescriptor* FindEnumTypeByName(const string& name) const;
+ const EnumValueDescriptor* FindEnumValueByName(const string& name) const;
+ const ServiceDescriptor* FindServiceByName(const string& name) const;
+ const MethodDescriptor* FindMethodByName(const string& name) const;
+
+ // Finds an extension of the given type by number. The extendee must be
+ // a member of this DescriptorPool or one of its underlays.
+ const FieldDescriptor* FindExtensionByNumber(const Descriptor* extendee,
+ int number) const;
+
+ // Finds extensions of extendee. The extensions will be appended to
+ // out in an undefined order. Only extensions defined directly in
+ // this DescriptorPool or one of its underlays are guaranteed to be
+ // found: extensions defined in the fallback database might not be found
+ // depending on the database implementation.
+ void FindAllExtensions(const Descriptor* extendee,
+ std::vector<const FieldDescriptor*>* out) const;
+
+ // Building descriptors --------------------------------------------
+
+ // When converting a FileDescriptorProto to a FileDescriptor, various
+ // errors might be detected in the input. The caller may handle these
+ // programmatically by implementing an ErrorCollector.
+ class LIBPROTOBUF_EXPORT ErrorCollector {
+ public:
+ inline ErrorCollector() {}
+ virtual ~ErrorCollector();
+
+ // These constants specify what exact part of the construct is broken.
+ // This is useful e.g. for mapping the error back to an exact location
+ // in a .proto file.
+ enum ErrorLocation {
+ NAME, // the symbol name, or the package name for files
+ NUMBER, // field or extension range number
+ TYPE, // field type
+ EXTENDEE, // field extendee
+ DEFAULT_VALUE, // field default value
+ INPUT_TYPE, // method input type
+ OUTPUT_TYPE, // method output type
+ OPTION_NAME, // name in assignment
+ OPTION_VALUE, // value in option assignment
+ OTHER // some other problem
+ };
+
+ // Reports an error in the FileDescriptorProto. Use this function if the
+ // problem occurred should interrupt building the FileDescriptorProto.
+ virtual void AddError(
+ const string& filename, // File name in which the error occurred.
+ const string& element_name, // Full name of the erroneous element.
+ const Message* descriptor, // Descriptor of the erroneous element.
+ ErrorLocation location, // One of the location constants, above.
+ const string& message // Human-readable error message.
+ ) = 0;
+
+ // Reports a warning in the FileDescriptorProto. Use this function if the
+ // problem occurred should NOT interrupt building the FileDescriptorProto.
+ virtual void AddWarning(
+ const string& /*filename*/, // File name in which the error occurred.
+ const string& /*element_name*/, // Full name of the erroneous element.
+ const Message* /*descriptor*/, // Descriptor of the erroneous element.
+ ErrorLocation /*location*/, // One of the location constants, above.
+ const string& /*message*/ // Human-readable error message.
+ ) {}
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ErrorCollector);
+ };
+
+ // Convert the FileDescriptorProto to real descriptors and place them in
+ // this DescriptorPool. All dependencies of the file must already be in
+ // the pool. Returns the resulting FileDescriptor, or NULL if there were
+ // problems with the input (e.g. the message was invalid, or dependencies
+ // were missing). Details about the errors are written to GOOGLE_LOG(ERROR).
+ const FileDescriptor* BuildFile(const FileDescriptorProto& proto);
+
+ // Same as BuildFile() except errors are sent to the given ErrorCollector.
+ const FileDescriptor* BuildFileCollectingErrors(
+ const FileDescriptorProto& proto,
+ ErrorCollector* error_collector);
+
+ // By default, it is an error if a FileDescriptorProto contains references
+ // to types or other files that are not found in the DescriptorPool (or its
+ // backing DescriptorDatabase, if any). If you call
+ // AllowUnknownDependencies(), however, then unknown types and files
+ // will be replaced by placeholder descriptors (which can be identified by
+ // the is_placeholder() method). This can allow you to
+ // perform some useful operations with a .proto file even if you do not
+ // have access to other .proto files on which it depends. However, some
+ // heuristics must be used to fill in the gaps in information, and these
+ // can lead to descriptors which are inaccurate. For example, the
+ // DescriptorPool may be forced to guess whether an unknown type is a message
+ // or an enum, as well as what package it resides in. Furthermore,
+ // placeholder types will not be discoverable via FindMessageTypeByName()
+ // and similar methods, which could confuse some descriptor-based algorithms.
+ // Generally, the results of this option should be handled with extreme care.
+ void AllowUnknownDependencies() { allow_unknown_ = true; }
+
+ // By default, weak imports are allowed to be missing, in which case we will
+ // use a placeholder for the dependency and convert the field to be an Empty
+ // message field. If you call EnforceWeakDependencies(true), however, the
+ // DescriptorPool will report a import not found error.
+ void EnforceWeakDependencies(bool enforce) { enforce_weak_ = enforce; }
+
+ // Internal stuff --------------------------------------------------
+ // These methods MUST NOT be called from outside the proto2 library.
+ // These methods may contain hidden pitfalls and may be removed in a
+ // future library version.
+
+ // Create a DescriptorPool which is overlaid on top of some other pool.
+ // If you search for a descriptor in the overlay and it is not found, the
+ // underlay will be searched as a backup. If the underlay has its own
+ // underlay, that will be searched next, and so on. This also means that
+ // files built in the overlay will be cross-linked with the underlay's
+ // descriptors if necessary. The underlay remains property of the caller;
+ // it must remain valid for the lifetime of the newly-constructed pool.
+ //
+ // Example: Say you want to parse a .proto file at runtime in order to use
+ // its type with a DynamicMessage. Say this .proto file has dependencies,
+ // but you know that all the dependencies will be things that are already
+ // compiled into the binary. For ease of use, you'd like to load the types
+ // right out of generated_pool() rather than have to parse redundant copies
+ // of all these .protos and runtime. But, you don't want to add the parsed
+ // types directly into generated_pool(): this is not allowed, and would be
+ // bad design anyway. So, instead, you could use generated_pool() as an
+ // underlay for a new DescriptorPool in which you add only the new file.
+ //
+ // WARNING: Use of underlays can lead to many subtle gotchas. Instead,
+ // try to formulate what you want to do in terms of DescriptorDatabases.
+ explicit DescriptorPool(const DescriptorPool* underlay);
+
+ // Called by generated classes at init time to add their descriptors to
+ // generated_pool. Do NOT call this in your own code! filename must be a
+ // permanent string (e.g. a string literal).
+ static void InternalAddGeneratedFile(
+ const void* encoded_file_descriptor, int size);
+
+
+ // For internal use only: Gets a non-const pointer to the generated pool.
+ // This is called at static-initialization time only, so thread-safety is
+ // not a concern. If both an underlay and a fallback database are present,
+ // the underlay takes precedence.
+ static DescriptorPool* internal_generated_pool();
+
+ // For internal use only: Changes the behavior of BuildFile() such that it
+ // allows the file to make reference to message types declared in other files
+ // which it did not officially declare as dependencies.
+ void InternalDontEnforceDependencies();
+
+ // For internal use only.
+ void internal_set_underlay(const DescriptorPool* underlay) {
+ underlay_ = underlay;
+ }
+
+ // For internal (unit test) use only: Returns true if a FileDescriptor has
+ // been constructed for the given file, false otherwise. Useful for testing
+ // lazy descriptor initialization behavior.
+ bool InternalIsFileLoaded(const string& filename) const;
+
+
+ // Add a file to unused_import_track_files_. DescriptorBuilder will log
+ // warnings for those files if there is any unused import.
+ void AddUnusedImportTrackFile(const string& file_name);
+ void ClearUnusedImportTrackFiles();
+
+ private:
+ friend class Descriptor;
+ friend class FieldDescriptor;
+ friend class EnumDescriptor;
+ friend class ServiceDescriptor;
+ friend class FileDescriptor;
+ friend class DescriptorBuilder;
+ friend class FileDescriptorTables;
+
+ // Return true if the given name is a sub-symbol of any non-package
+ // descriptor that already exists in the descriptor pool. (The full
+ // definition of such types is already known.)
+ bool IsSubSymbolOfBuiltType(const string& name) const;
+
+ // Tries to find something in the fallback database and link in the
+ // corresponding proto file. Returns true if successful, in which case
+ // the caller should search for the thing again. These are declared
+ // const because they are called by (semantically) const methods.
+ bool TryFindFileInFallbackDatabase(const string& name) const;
+ bool TryFindSymbolInFallbackDatabase(const string& name) const;
+ bool TryFindExtensionInFallbackDatabase(const Descriptor* containing_type,
+ int field_number) const;
+
+ // Like BuildFile() but called internally when the file has been loaded from
+ // fallback_database_. Declared const because it is called by (semantically)
+ // const methods.
+ const FileDescriptor* BuildFileFromDatabase(
+ const FileDescriptorProto& proto) const;
+
+ // If fallback_database_ is NULL, this is NULL. Otherwise, this is a mutex
+ // which must be locked while accessing tables_.
+ Mutex* mutex_;
+
+ // See constructor.
+ DescriptorDatabase* fallback_database_;
+ ErrorCollector* default_error_collector_;
+ const DescriptorPool* underlay_;
+
+ // This class contains a lot of hash maps with complicated types that
+ // we'd like to keep out of the header.
+ class Tables;
+ google::protobuf::scoped_ptr<Tables> tables_;
+
+ bool enforce_dependencies_;
+ bool allow_unknown_;
+ bool enforce_weak_;
+ std::set<string> unused_import_track_files_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DescriptorPool);
+};
+
+// inline methods ====================================================
+
+// These macros makes this repetitive code more readable.
+#define PROTOBUF_DEFINE_ACCESSOR(CLASS, FIELD, TYPE) \
+ inline TYPE CLASS::FIELD() const { return FIELD##_; }
+
+// Strings fields are stored as pointers but returned as const references.
+#define PROTOBUF_DEFINE_STRING_ACCESSOR(CLASS, FIELD) \
+ inline const string& CLASS::FIELD() const { return *FIELD##_; }
+
+// Arrays take an index parameter, obviously.
+#define PROTOBUF_DEFINE_ARRAY_ACCESSOR(CLASS, FIELD, TYPE) \
+ inline TYPE CLASS::FIELD(int index) const { return FIELD##s_ + index; }
+
+#define PROTOBUF_DEFINE_OPTIONS_ACCESSOR(CLASS, TYPE) \
+ inline const TYPE& CLASS::options() const { return *options_; }
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(Descriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(Descriptor, full_name)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, file, const FileDescriptor*)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, containing_type, const Descriptor*)
+
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, field_count, int)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, oneof_decl_count, int)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, nested_type_count, int)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, enum_type_count, int)
+
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(Descriptor, field, const FieldDescriptor*)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(Descriptor, oneof_decl, const OneofDescriptor*)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(Descriptor, nested_type, const Descriptor*)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(Descriptor, enum_type, const EnumDescriptor*)
+
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, extension_range_count, int)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, extension_count, int)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(Descriptor, extension_range,
+ const Descriptor::ExtensionRange*)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(Descriptor, extension,
+ const FieldDescriptor*)
+
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, reserved_range_count, int)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(Descriptor, reserved_range,
+ const Descriptor::ReservedRange*)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, reserved_name_count, int)
+
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(Descriptor, MessageOptions)
+PROTOBUF_DEFINE_ACCESSOR(Descriptor, is_placeholder, bool)
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(FieldDescriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(FieldDescriptor, full_name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(FieldDescriptor, json_name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(FieldDescriptor, lowercase_name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(FieldDescriptor, camelcase_name)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, file, const FileDescriptor*)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, number, int)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, is_extension, bool)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, type, FieldDescriptor::Type)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, label, FieldDescriptor::Label)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, containing_type, const Descriptor*)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, containing_oneof,
+ const OneofDescriptor*)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, index_in_oneof, int)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, extension_scope, const Descriptor*)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, message_type, const Descriptor*)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, enum_type, const EnumDescriptor*)
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(FieldDescriptor, FieldOptions)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, has_default_value, bool)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_int32 , int32 )
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_int64 , int64 )
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_uint32, uint32)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_uint64, uint64)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_float , float )
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_double, double)
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_bool , bool )
+PROTOBUF_DEFINE_ACCESSOR(FieldDescriptor, default_value_enum,
+ const EnumValueDescriptor*)
+PROTOBUF_DEFINE_STRING_ACCESSOR(FieldDescriptor, default_value_string)
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(OneofDescriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(OneofDescriptor, full_name)
+PROTOBUF_DEFINE_ACCESSOR(OneofDescriptor, containing_type, const Descriptor*)
+PROTOBUF_DEFINE_ACCESSOR(OneofDescriptor, field_count, int)
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(OneofDescriptor, OneofOptions)
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(EnumDescriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(EnumDescriptor, full_name)
+PROTOBUF_DEFINE_ACCESSOR(EnumDescriptor, file, const FileDescriptor*)
+PROTOBUF_DEFINE_ACCESSOR(EnumDescriptor, containing_type, const Descriptor*)
+PROTOBUF_DEFINE_ACCESSOR(EnumDescriptor, value_count, int)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(EnumDescriptor, value,
+ const EnumValueDescriptor*)
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(EnumDescriptor, EnumOptions)
+PROTOBUF_DEFINE_ACCESSOR(EnumDescriptor, is_placeholder, bool)
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(EnumValueDescriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(EnumValueDescriptor, full_name)
+PROTOBUF_DEFINE_ACCESSOR(EnumValueDescriptor, number, int)
+PROTOBUF_DEFINE_ACCESSOR(EnumValueDescriptor, type, const EnumDescriptor*)
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(EnumValueDescriptor, EnumValueOptions)
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(ServiceDescriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(ServiceDescriptor, full_name)
+PROTOBUF_DEFINE_ACCESSOR(ServiceDescriptor, file, const FileDescriptor*)
+PROTOBUF_DEFINE_ACCESSOR(ServiceDescriptor, method_count, int)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(ServiceDescriptor, method,
+ const MethodDescriptor*)
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(ServiceDescriptor, ServiceOptions)
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(MethodDescriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(MethodDescriptor, full_name)
+PROTOBUF_DEFINE_ACCESSOR(MethodDescriptor, service, const ServiceDescriptor*)
+PROTOBUF_DEFINE_ACCESSOR(MethodDescriptor, input_type, const Descriptor*)
+PROTOBUF_DEFINE_ACCESSOR(MethodDescriptor, output_type, const Descriptor*)
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(MethodDescriptor, MethodOptions)
+PROTOBUF_DEFINE_ACCESSOR(MethodDescriptor, client_streaming, bool)
+PROTOBUF_DEFINE_ACCESSOR(MethodDescriptor, server_streaming, bool)
+
+PROTOBUF_DEFINE_STRING_ACCESSOR(FileDescriptor, name)
+PROTOBUF_DEFINE_STRING_ACCESSOR(FileDescriptor, package)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, pool, const DescriptorPool*)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, dependency_count, int)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, public_dependency_count, int)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, weak_dependency_count, int)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, message_type_count, int)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, enum_type_count, int)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, service_count, int)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, extension_count, int)
+PROTOBUF_DEFINE_OPTIONS_ACCESSOR(FileDescriptor, FileOptions)
+PROTOBUF_DEFINE_ACCESSOR(FileDescriptor, is_placeholder, bool)
+
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(FileDescriptor, message_type, const Descriptor*)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(FileDescriptor, enum_type, const EnumDescriptor*)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(FileDescriptor, service,
+ const ServiceDescriptor*)
+PROTOBUF_DEFINE_ARRAY_ACCESSOR(FileDescriptor, extension,
+ const FieldDescriptor*)
+
+#undef PROTOBUF_DEFINE_ACCESSOR
+#undef PROTOBUF_DEFINE_STRING_ACCESSOR
+#undef PROTOBUF_DEFINE_ARRAY_ACCESSOR
+
+// A few accessors differ from the macros...
+
+inline bool Descriptor::IsExtensionNumber(int number) const {
+ return FindExtensionRangeContainingNumber(number) != NULL;
+}
+
+inline bool Descriptor::IsReservedNumber(int number) const {
+ return FindReservedRangeContainingNumber(number) != NULL;
+}
+
+inline bool Descriptor::IsReservedName(const string& name) const {
+ for (int i = 0; i < reserved_name_count(); i++) {
+ if (name == reserved_name(i)) {
+ return true;
+ }
+ }
+ return false;
+}
+
+// Can't use PROTOBUF_DEFINE_ARRAY_ACCESSOR because reserved_names_ is actually
+// an array of pointers rather than the usual array of objects.
+inline const string& Descriptor::reserved_name(int index) const {
+ return *reserved_names_[index];
+}
+
+inline bool FieldDescriptor::is_required() const {
+ return label() == LABEL_REQUIRED;
+}
+
+inline bool FieldDescriptor::is_optional() const {
+ return label() == LABEL_OPTIONAL;
+}
+
+inline bool FieldDescriptor::is_repeated() const {
+ return label() == LABEL_REPEATED;
+}
+
+inline bool FieldDescriptor::is_packable() const {
+ return is_repeated() && IsTypePackable(type());
+}
+
+// To save space, index() is computed by looking at the descriptor's position
+// in the parent's array of children.
+inline int FieldDescriptor::index() const {
+ if (!is_extension_) {
+ return static_cast<int>(this - containing_type_->fields_);
+ } else if (extension_scope_ != NULL) {
+ return static_cast<int>(this - extension_scope_->extensions_);
+ } else {
+ return static_cast<int>(this - file_->extensions_);
+ }
+}
+
+inline int Descriptor::index() const {
+ if (containing_type_ == NULL) {
+ return static_cast<int>(this - file_->message_types_);
+ } else {
+ return static_cast<int>(this - containing_type_->nested_types_);
+ }
+}
+
+inline int OneofDescriptor::index() const {
+ return static_cast<int>(this - containing_type_->oneof_decls_);
+}
+
+inline int EnumDescriptor::index() const {
+ if (containing_type_ == NULL) {
+ return static_cast<int>(this - file_->enum_types_);
+ } else {
+ return static_cast<int>(this - containing_type_->enum_types_);
+ }
+}
+
+inline int EnumValueDescriptor::index() const {
+ return static_cast<int>(this - type_->values_);
+}
+
+inline int ServiceDescriptor::index() const {
+ return static_cast<int>(this - file_->services_);
+}
+
+inline int MethodDescriptor::index() const {
+ return static_cast<int>(this - service_->methods_);
+}
+
+inline const char* FieldDescriptor::type_name() const {
+ return kTypeToName[type_];
+}
+
+inline FieldDescriptor::CppType FieldDescriptor::cpp_type() const {
+ return kTypeToCppTypeMap[type_];
+}
+
+inline const char* FieldDescriptor::cpp_type_name() const {
+ return kCppTypeToName[kTypeToCppTypeMap[type_]];
+}
+
+inline FieldDescriptor::CppType FieldDescriptor::TypeToCppType(Type type) {
+ return kTypeToCppTypeMap[type];
+}
+
+inline const char* FieldDescriptor::TypeName(Type type) {
+ return kTypeToName[type];
+}
+
+inline const char* FieldDescriptor::CppTypeName(CppType cpp_type) {
+ return kCppTypeToName[cpp_type];
+}
+
+inline bool FieldDescriptor::IsTypePackable(Type field_type) {
+ return (field_type != FieldDescriptor::TYPE_STRING &&
+ field_type != FieldDescriptor::TYPE_GROUP &&
+ field_type != FieldDescriptor::TYPE_MESSAGE &&
+ field_type != FieldDescriptor::TYPE_BYTES);
+}
+
+inline const FileDescriptor* FileDescriptor::dependency(int index) const {
+ return dependencies_[index];
+}
+
+inline const FileDescriptor* FileDescriptor::public_dependency(
+ int index) const {
+ return dependencies_[public_dependencies_[index]];
+}
+
+inline const FileDescriptor* FileDescriptor::weak_dependency(
+ int index) const {
+ return dependencies_[weak_dependencies_[index]];
+}
+
+inline FileDescriptor::Syntax FileDescriptor::syntax() const {
+ return syntax_;
+}
+
+// Can't use PROTOBUF_DEFINE_ARRAY_ACCESSOR because fields_ is actually an array
+// of pointers rather than the usual array of objects.
+inline const FieldDescriptor* OneofDescriptor::field(int index) const {
+ return fields_[index];
+}
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_DESCRIPTOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.cc
new file mode 100644
index 0000000000..0028c70862
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.cc
@@ -0,0 +1,15680 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/descriptor.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/descriptor.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* FileDescriptorSet_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ FileDescriptorSet_reflection_ = NULL;
+const ::google::protobuf::Descriptor* FileDescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ FileDescriptorProto_reflection_ = NULL;
+const ::google::protobuf::Descriptor* DescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ DescriptorProto_reflection_ = NULL;
+const ::google::protobuf::Descriptor* DescriptorProto_ExtensionRange_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ DescriptorProto_ExtensionRange_reflection_ = NULL;
+const ::google::protobuf::Descriptor* DescriptorProto_ReservedRange_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ DescriptorProto_ReservedRange_reflection_ = NULL;
+const ::google::protobuf::Descriptor* FieldDescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ FieldDescriptorProto_reflection_ = NULL;
+const ::google::protobuf::EnumDescriptor* FieldDescriptorProto_Type_descriptor_ = NULL;
+const ::google::protobuf::EnumDescriptor* FieldDescriptorProto_Label_descriptor_ = NULL;
+const ::google::protobuf::Descriptor* OneofDescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ OneofDescriptorProto_reflection_ = NULL;
+const ::google::protobuf::Descriptor* EnumDescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ EnumDescriptorProto_reflection_ = NULL;
+const ::google::protobuf::Descriptor* EnumValueDescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ EnumValueDescriptorProto_reflection_ = NULL;
+const ::google::protobuf::Descriptor* ServiceDescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ ServiceDescriptorProto_reflection_ = NULL;
+const ::google::protobuf::Descriptor* MethodDescriptorProto_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ MethodDescriptorProto_reflection_ = NULL;
+const ::google::protobuf::Descriptor* FileOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ FileOptions_reflection_ = NULL;
+const ::google::protobuf::EnumDescriptor* FileOptions_OptimizeMode_descriptor_ = NULL;
+const ::google::protobuf::Descriptor* MessageOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ MessageOptions_reflection_ = NULL;
+const ::google::protobuf::Descriptor* FieldOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ FieldOptions_reflection_ = NULL;
+const ::google::protobuf::EnumDescriptor* FieldOptions_CType_descriptor_ = NULL;
+const ::google::protobuf::EnumDescriptor* FieldOptions_JSType_descriptor_ = NULL;
+const ::google::protobuf::Descriptor* OneofOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ OneofOptions_reflection_ = NULL;
+const ::google::protobuf::Descriptor* EnumOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ EnumOptions_reflection_ = NULL;
+const ::google::protobuf::Descriptor* EnumValueOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ EnumValueOptions_reflection_ = NULL;
+const ::google::protobuf::Descriptor* ServiceOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ ServiceOptions_reflection_ = NULL;
+const ::google::protobuf::Descriptor* MethodOptions_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ MethodOptions_reflection_ = NULL;
+const ::google::protobuf::Descriptor* UninterpretedOption_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ UninterpretedOption_reflection_ = NULL;
+const ::google::protobuf::Descriptor* UninterpretedOption_NamePart_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ UninterpretedOption_NamePart_reflection_ = NULL;
+const ::google::protobuf::Descriptor* SourceCodeInfo_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ SourceCodeInfo_reflection_ = NULL;
+const ::google::protobuf::Descriptor* SourceCodeInfo_Location_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ SourceCodeInfo_Location_reflection_ = NULL;
+const ::google::protobuf::Descriptor* GeneratedCodeInfo_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ GeneratedCodeInfo_reflection_ = NULL;
+const ::google::protobuf::Descriptor* GeneratedCodeInfo_Annotation_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ GeneratedCodeInfo_Annotation_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/descriptor.proto");
+ GOOGLE_CHECK(file != NULL);
+ FileDescriptorSet_descriptor_ = file->message_type(0);
+ static const int FileDescriptorSet_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorSet, file_),
+ };
+ FileDescriptorSet_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ FileDescriptorSet_descriptor_,
+ FileDescriptorSet::default_instance_,
+ FileDescriptorSet_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorSet, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(FileDescriptorSet),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorSet, _internal_metadata_),
+ -1);
+ FileDescriptorProto_descriptor_ = file->message_type(1);
+ static const int FileDescriptorProto_offsets_[12] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, package_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, dependency_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, public_dependency_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, weak_dependency_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, message_type_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, enum_type_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, service_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, extension_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, source_code_info_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, syntax_),
+ };
+ FileDescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ FileDescriptorProto_descriptor_,
+ FileDescriptorProto::default_instance_,
+ FileDescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(FileDescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileDescriptorProto, _internal_metadata_),
+ -1);
+ DescriptorProto_descriptor_ = file->message_type(2);
+ static const int DescriptorProto_offsets_[10] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, field_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, extension_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, nested_type_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, enum_type_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, extension_range_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, oneof_decl_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, reserved_range_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, reserved_name_),
+ };
+ DescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ DescriptorProto_descriptor_,
+ DescriptorProto::default_instance_,
+ DescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(DescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto, _internal_metadata_),
+ -1);
+ DescriptorProto_ExtensionRange_descriptor_ = DescriptorProto_descriptor_->nested_type(0);
+ static const int DescriptorProto_ExtensionRange_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ExtensionRange, start_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ExtensionRange, end_),
+ };
+ DescriptorProto_ExtensionRange_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ DescriptorProto_ExtensionRange_descriptor_,
+ DescriptorProto_ExtensionRange::default_instance_,
+ DescriptorProto_ExtensionRange_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ExtensionRange, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(DescriptorProto_ExtensionRange),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ExtensionRange, _internal_metadata_),
+ -1);
+ DescriptorProto_ReservedRange_descriptor_ = DescriptorProto_descriptor_->nested_type(1);
+ static const int DescriptorProto_ReservedRange_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ReservedRange, start_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ReservedRange, end_),
+ };
+ DescriptorProto_ReservedRange_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ DescriptorProto_ReservedRange_descriptor_,
+ DescriptorProto_ReservedRange::default_instance_,
+ DescriptorProto_ReservedRange_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ReservedRange, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(DescriptorProto_ReservedRange),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DescriptorProto_ReservedRange, _internal_metadata_),
+ -1);
+ FieldDescriptorProto_descriptor_ = file->message_type(3);
+ static const int FieldDescriptorProto_offsets_[10] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, number_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, label_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, type_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, type_name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, extendee_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, default_value_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, oneof_index_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, json_name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, options_),
+ };
+ FieldDescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ FieldDescriptorProto_descriptor_,
+ FieldDescriptorProto::default_instance_,
+ FieldDescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(FieldDescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldDescriptorProto, _internal_metadata_),
+ -1);
+ FieldDescriptorProto_Type_descriptor_ = FieldDescriptorProto_descriptor_->enum_type(0);
+ FieldDescriptorProto_Label_descriptor_ = FieldDescriptorProto_descriptor_->enum_type(1);
+ OneofDescriptorProto_descriptor_ = file->message_type(4);
+ static const int OneofDescriptorProto_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofDescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofDescriptorProto, options_),
+ };
+ OneofDescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ OneofDescriptorProto_descriptor_,
+ OneofDescriptorProto::default_instance_,
+ OneofDescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofDescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(OneofDescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofDescriptorProto, _internal_metadata_),
+ -1);
+ EnumDescriptorProto_descriptor_ = file->message_type(5);
+ static const int EnumDescriptorProto_offsets_[3] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumDescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumDescriptorProto, value_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumDescriptorProto, options_),
+ };
+ EnumDescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ EnumDescriptorProto_descriptor_,
+ EnumDescriptorProto::default_instance_,
+ EnumDescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumDescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(EnumDescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumDescriptorProto, _internal_metadata_),
+ -1);
+ EnumValueDescriptorProto_descriptor_ = file->message_type(6);
+ static const int EnumValueDescriptorProto_offsets_[3] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueDescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueDescriptorProto, number_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueDescriptorProto, options_),
+ };
+ EnumValueDescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ EnumValueDescriptorProto_descriptor_,
+ EnumValueDescriptorProto::default_instance_,
+ EnumValueDescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueDescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(EnumValueDescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueDescriptorProto, _internal_metadata_),
+ -1);
+ ServiceDescriptorProto_descriptor_ = file->message_type(7);
+ static const int ServiceDescriptorProto_offsets_[3] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceDescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceDescriptorProto, method_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceDescriptorProto, options_),
+ };
+ ServiceDescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ ServiceDescriptorProto_descriptor_,
+ ServiceDescriptorProto::default_instance_,
+ ServiceDescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceDescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(ServiceDescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceDescriptorProto, _internal_metadata_),
+ -1);
+ MethodDescriptorProto_descriptor_ = file->message_type(8);
+ static const int MethodDescriptorProto_offsets_[6] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, input_type_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, output_type_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, client_streaming_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, server_streaming_),
+ };
+ MethodDescriptorProto_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ MethodDescriptorProto_descriptor_,
+ MethodDescriptorProto::default_instance_,
+ MethodDescriptorProto_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(MethodDescriptorProto),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodDescriptorProto, _internal_metadata_),
+ -1);
+ FileOptions_descriptor_ = file->message_type(9);
+ static const int FileOptions_offsets_[15] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, java_package_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, java_outer_classname_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, java_multiple_files_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, java_generate_equals_and_hash_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, java_string_check_utf8_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, optimize_for_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, go_package_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, cc_generic_services_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, java_generic_services_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, py_generic_services_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, deprecated_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, cc_enable_arenas_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, objc_class_prefix_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, csharp_namespace_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, uninterpreted_option_),
+ };
+ FileOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ FileOptions_descriptor_,
+ FileOptions::default_instance_,
+ FileOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, _extensions_),
+ sizeof(FileOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FileOptions, _internal_metadata_),
+ -1);
+ FileOptions_OptimizeMode_descriptor_ = FileOptions_descriptor_->enum_type(0);
+ MessageOptions_descriptor_ = file->message_type(10);
+ static const int MessageOptions_offsets_[5] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, message_set_wire_format_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, no_standard_descriptor_accessor_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, deprecated_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, map_entry_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, uninterpreted_option_),
+ };
+ MessageOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ MessageOptions_descriptor_,
+ MessageOptions::default_instance_,
+ MessageOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, _extensions_),
+ sizeof(MessageOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MessageOptions, _internal_metadata_),
+ -1);
+ FieldOptions_descriptor_ = file->message_type(11);
+ static const int FieldOptions_offsets_[7] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, ctype_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, packed_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, jstype_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, lazy_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, deprecated_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, weak_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, uninterpreted_option_),
+ };
+ FieldOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ FieldOptions_descriptor_,
+ FieldOptions::default_instance_,
+ FieldOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, _extensions_),
+ sizeof(FieldOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldOptions, _internal_metadata_),
+ -1);
+ FieldOptions_CType_descriptor_ = FieldOptions_descriptor_->enum_type(0);
+ FieldOptions_JSType_descriptor_ = FieldOptions_descriptor_->enum_type(1);
+ OneofOptions_descriptor_ = file->message_type(12);
+ static const int OneofOptions_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofOptions, uninterpreted_option_),
+ };
+ OneofOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ OneofOptions_descriptor_,
+ OneofOptions::default_instance_,
+ OneofOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofOptions, _extensions_),
+ sizeof(OneofOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(OneofOptions, _internal_metadata_),
+ -1);
+ EnumOptions_descriptor_ = file->message_type(13);
+ static const int EnumOptions_offsets_[3] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumOptions, allow_alias_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumOptions, deprecated_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumOptions, uninterpreted_option_),
+ };
+ EnumOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ EnumOptions_descriptor_,
+ EnumOptions::default_instance_,
+ EnumOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumOptions, _extensions_),
+ sizeof(EnumOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumOptions, _internal_metadata_),
+ -1);
+ EnumValueOptions_descriptor_ = file->message_type(14);
+ static const int EnumValueOptions_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueOptions, deprecated_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueOptions, uninterpreted_option_),
+ };
+ EnumValueOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ EnumValueOptions_descriptor_,
+ EnumValueOptions::default_instance_,
+ EnumValueOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueOptions, _extensions_),
+ sizeof(EnumValueOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValueOptions, _internal_metadata_),
+ -1);
+ ServiceOptions_descriptor_ = file->message_type(15);
+ static const int ServiceOptions_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceOptions, deprecated_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceOptions, uninterpreted_option_),
+ };
+ ServiceOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ ServiceOptions_descriptor_,
+ ServiceOptions::default_instance_,
+ ServiceOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceOptions, _extensions_),
+ sizeof(ServiceOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ServiceOptions, _internal_metadata_),
+ -1);
+ MethodOptions_descriptor_ = file->message_type(16);
+ static const int MethodOptions_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodOptions, deprecated_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodOptions, uninterpreted_option_),
+ };
+ MethodOptions_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ MethodOptions_descriptor_,
+ MethodOptions::default_instance_,
+ MethodOptions_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodOptions, _has_bits_[0]),
+ -1,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodOptions, _extensions_),
+ sizeof(MethodOptions),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MethodOptions, _internal_metadata_),
+ -1);
+ UninterpretedOption_descriptor_ = file->message_type(17);
+ static const int UninterpretedOption_offsets_[7] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, identifier_value_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, positive_int_value_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, negative_int_value_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, double_value_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, string_value_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, aggregate_value_),
+ };
+ UninterpretedOption_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ UninterpretedOption_descriptor_,
+ UninterpretedOption::default_instance_,
+ UninterpretedOption_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(UninterpretedOption),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption, _internal_metadata_),
+ -1);
+ UninterpretedOption_NamePart_descriptor_ = UninterpretedOption_descriptor_->nested_type(0);
+ static const int UninterpretedOption_NamePart_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption_NamePart, name_part_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption_NamePart, is_extension_),
+ };
+ UninterpretedOption_NamePart_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ UninterpretedOption_NamePart_descriptor_,
+ UninterpretedOption_NamePart::default_instance_,
+ UninterpretedOption_NamePart_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption_NamePart, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(UninterpretedOption_NamePart),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UninterpretedOption_NamePart, _internal_metadata_),
+ -1);
+ SourceCodeInfo_descriptor_ = file->message_type(18);
+ static const int SourceCodeInfo_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo, location_),
+ };
+ SourceCodeInfo_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ SourceCodeInfo_descriptor_,
+ SourceCodeInfo::default_instance_,
+ SourceCodeInfo_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(SourceCodeInfo),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo, _internal_metadata_),
+ -1);
+ SourceCodeInfo_Location_descriptor_ = SourceCodeInfo_descriptor_->nested_type(0);
+ static const int SourceCodeInfo_Location_offsets_[5] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo_Location, path_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo_Location, span_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo_Location, leading_comments_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo_Location, trailing_comments_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo_Location, leading_detached_comments_),
+ };
+ SourceCodeInfo_Location_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ SourceCodeInfo_Location_descriptor_,
+ SourceCodeInfo_Location::default_instance_,
+ SourceCodeInfo_Location_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo_Location, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(SourceCodeInfo_Location),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceCodeInfo_Location, _internal_metadata_),
+ -1);
+ GeneratedCodeInfo_descriptor_ = file->message_type(19);
+ static const int GeneratedCodeInfo_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo, annotation_),
+ };
+ GeneratedCodeInfo_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ GeneratedCodeInfo_descriptor_,
+ GeneratedCodeInfo::default_instance_,
+ GeneratedCodeInfo_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(GeneratedCodeInfo),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo, _internal_metadata_),
+ -1);
+ GeneratedCodeInfo_Annotation_descriptor_ = GeneratedCodeInfo_descriptor_->nested_type(0);
+ static const int GeneratedCodeInfo_Annotation_offsets_[4] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo_Annotation, path_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo_Annotation, source_file_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo_Annotation, begin_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo_Annotation, end_),
+ };
+ GeneratedCodeInfo_Annotation_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ GeneratedCodeInfo_Annotation_descriptor_,
+ GeneratedCodeInfo_Annotation::default_instance_,
+ GeneratedCodeInfo_Annotation_offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo_Annotation, _has_bits_[0]),
+ -1,
+ -1,
+ sizeof(GeneratedCodeInfo_Annotation),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(GeneratedCodeInfo_Annotation, _internal_metadata_),
+ -1);
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ FileDescriptorSet_descriptor_, &FileDescriptorSet::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ FileDescriptorProto_descriptor_, &FileDescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ DescriptorProto_descriptor_, &DescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ DescriptorProto_ExtensionRange_descriptor_, &DescriptorProto_ExtensionRange::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ DescriptorProto_ReservedRange_descriptor_, &DescriptorProto_ReservedRange::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ FieldDescriptorProto_descriptor_, &FieldDescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ OneofDescriptorProto_descriptor_, &OneofDescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ EnumDescriptorProto_descriptor_, &EnumDescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ EnumValueDescriptorProto_descriptor_, &EnumValueDescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ ServiceDescriptorProto_descriptor_, &ServiceDescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ MethodDescriptorProto_descriptor_, &MethodDescriptorProto::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ FileOptions_descriptor_, &FileOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ MessageOptions_descriptor_, &MessageOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ FieldOptions_descriptor_, &FieldOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ OneofOptions_descriptor_, &OneofOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ EnumOptions_descriptor_, &EnumOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ EnumValueOptions_descriptor_, &EnumValueOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ ServiceOptions_descriptor_, &ServiceOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ MethodOptions_descriptor_, &MethodOptions::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ UninterpretedOption_descriptor_, &UninterpretedOption::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ UninterpretedOption_NamePart_descriptor_, &UninterpretedOption_NamePart::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ SourceCodeInfo_descriptor_, &SourceCodeInfo::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ SourceCodeInfo_Location_descriptor_, &SourceCodeInfo_Location::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ GeneratedCodeInfo_descriptor_, &GeneratedCodeInfo::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ GeneratedCodeInfo_Annotation_descriptor_, &GeneratedCodeInfo_Annotation::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto() {
+ delete FileDescriptorSet::default_instance_;
+ delete FileDescriptorSet_reflection_;
+ delete FileDescriptorProto::default_instance_;
+ delete FileDescriptorProto_reflection_;
+ delete DescriptorProto::default_instance_;
+ delete DescriptorProto_reflection_;
+ delete DescriptorProto_ExtensionRange::default_instance_;
+ delete DescriptorProto_ExtensionRange_reflection_;
+ delete DescriptorProto_ReservedRange::default_instance_;
+ delete DescriptorProto_ReservedRange_reflection_;
+ delete FieldDescriptorProto::default_instance_;
+ delete FieldDescriptorProto_reflection_;
+ delete OneofDescriptorProto::default_instance_;
+ delete OneofDescriptorProto_reflection_;
+ delete EnumDescriptorProto::default_instance_;
+ delete EnumDescriptorProto_reflection_;
+ delete EnumValueDescriptorProto::default_instance_;
+ delete EnumValueDescriptorProto_reflection_;
+ delete ServiceDescriptorProto::default_instance_;
+ delete ServiceDescriptorProto_reflection_;
+ delete MethodDescriptorProto::default_instance_;
+ delete MethodDescriptorProto_reflection_;
+ delete FileOptions::default_instance_;
+ delete FileOptions_reflection_;
+ delete MessageOptions::default_instance_;
+ delete MessageOptions_reflection_;
+ delete FieldOptions::default_instance_;
+ delete FieldOptions_reflection_;
+ delete OneofOptions::default_instance_;
+ delete OneofOptions_reflection_;
+ delete EnumOptions::default_instance_;
+ delete EnumOptions_reflection_;
+ delete EnumValueOptions::default_instance_;
+ delete EnumValueOptions_reflection_;
+ delete ServiceOptions::default_instance_;
+ delete ServiceOptions_reflection_;
+ delete MethodOptions::default_instance_;
+ delete MethodOptions_reflection_;
+ delete UninterpretedOption::default_instance_;
+ delete UninterpretedOption_reflection_;
+ delete UninterpretedOption_NamePart::default_instance_;
+ delete UninterpretedOption_NamePart_reflection_;
+ delete SourceCodeInfo::default_instance_;
+ delete SourceCodeInfo_reflection_;
+ delete SourceCodeInfo_Location::default_instance_;
+ delete SourceCodeInfo_Location_reflection_;
+ delete GeneratedCodeInfo::default_instance_;
+ delete GeneratedCodeInfo_reflection_;
+ delete GeneratedCodeInfo_Annotation::default_instance_;
+ delete GeneratedCodeInfo_Annotation_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n google/protobuf/descriptor.proto\022\017goog"
+ "le.protobuf\"G\n\021FileDescriptorSet\0222\n\004file"
+ "\030\001 \003(\0132$.google.protobuf.FileDescriptorP"
+ "roto\"\333\003\n\023FileDescriptorProto\022\014\n\004name\030\001 \001"
+ "(\t\022\017\n\007package\030\002 \001(\t\022\022\n\ndependency\030\003 \003(\t\022"
+ "\031\n\021public_dependency\030\n \003(\005\022\027\n\017weak_depen"
+ "dency\030\013 \003(\005\0226\n\014message_type\030\004 \003(\0132 .goog"
+ "le.protobuf.DescriptorProto\0227\n\tenum_type"
+ "\030\005 \003(\0132$.google.protobuf.EnumDescriptorP"
+ "roto\0228\n\007service\030\006 \003(\0132\'.google.protobuf."
+ "ServiceDescriptorProto\0228\n\textension\030\007 \003("
+ "\0132%.google.protobuf.FieldDescriptorProto"
+ "\022-\n\007options\030\010 \001(\0132\034.google.protobuf.File"
+ "Options\0229\n\020source_code_info\030\t \001(\0132\037.goog"
+ "le.protobuf.SourceCodeInfo\022\016\n\006syntax\030\014 \001"
+ "(\t\"\360\004\n\017DescriptorProto\022\014\n\004name\030\001 \001(\t\0224\n\005"
+ "field\030\002 \003(\0132%.google.protobuf.FieldDescr"
+ "iptorProto\0228\n\textension\030\006 \003(\0132%.google.p"
+ "rotobuf.FieldDescriptorProto\0225\n\013nested_t"
+ "ype\030\003 \003(\0132 .google.protobuf.DescriptorPr"
+ "oto\0227\n\tenum_type\030\004 \003(\0132$.google.protobuf"
+ ".EnumDescriptorProto\022H\n\017extension_range\030"
+ "\005 \003(\0132/.google.protobuf.DescriptorProto."
+ "ExtensionRange\0229\n\noneof_decl\030\010 \003(\0132%.goo"
+ "gle.protobuf.OneofDescriptorProto\0220\n\007opt"
+ "ions\030\007 \001(\0132\037.google.protobuf.MessageOpti"
+ "ons\022F\n\016reserved_range\030\t \003(\0132..google.pro"
+ "tobuf.DescriptorProto.ReservedRange\022\025\n\rr"
+ "eserved_name\030\n \003(\t\032,\n\016ExtensionRange\022\r\n\005"
+ "start\030\001 \001(\005\022\013\n\003end\030\002 \001(\005\032+\n\rReservedRang"
+ "e\022\r\n\005start\030\001 \001(\005\022\013\n\003end\030\002 \001(\005\"\274\005\n\024FieldD"
+ "escriptorProto\022\014\n\004name\030\001 \001(\t\022\016\n\006number\030\003"
+ " \001(\005\022:\n\005label\030\004 \001(\0162+.google.protobuf.Fi"
+ "eldDescriptorProto.Label\0228\n\004type\030\005 \001(\0162*"
+ ".google.protobuf.FieldDescriptorProto.Ty"
+ "pe\022\021\n\ttype_name\030\006 \001(\t\022\020\n\010extendee\030\002 \001(\t\022"
+ "\025\n\rdefault_value\030\007 \001(\t\022\023\n\013oneof_index\030\t "
+ "\001(\005\022\021\n\tjson_name\030\n \001(\t\022.\n\007options\030\010 \001(\0132"
+ "\035.google.protobuf.FieldOptions\"\266\002\n\004Type\022"
+ "\017\n\013TYPE_DOUBLE\020\001\022\016\n\nTYPE_FLOAT\020\002\022\016\n\nTYPE"
+ "_INT64\020\003\022\017\n\013TYPE_UINT64\020\004\022\016\n\nTYPE_INT32\020"
+ "\005\022\020\n\014TYPE_FIXED64\020\006\022\020\n\014TYPE_FIXED32\020\007\022\r\n"
+ "\tTYPE_BOOL\020\010\022\017\n\013TYPE_STRING\020\t\022\016\n\nTYPE_GR"
+ "OUP\020\n\022\020\n\014TYPE_MESSAGE\020\013\022\016\n\nTYPE_BYTES\020\014\022"
+ "\017\n\013TYPE_UINT32\020\r\022\r\n\tTYPE_ENUM\020\016\022\021\n\rTYPE_"
+ "SFIXED32\020\017\022\021\n\rTYPE_SFIXED64\020\020\022\017\n\013TYPE_SI"
+ "NT32\020\021\022\017\n\013TYPE_SINT64\020\022\"C\n\005Label\022\022\n\016LABE"
+ "L_OPTIONAL\020\001\022\022\n\016LABEL_REQUIRED\020\002\022\022\n\016LABE"
+ "L_REPEATED\020\003\"T\n\024OneofDescriptorProto\022\014\n\004"
+ "name\030\001 \001(\t\022.\n\007options\030\002 \001(\0132\035.google.pro"
+ "tobuf.OneofOptions\"\214\001\n\023EnumDescriptorPro"
+ "to\022\014\n\004name\030\001 \001(\t\0228\n\005value\030\002 \003(\0132).google"
+ ".protobuf.EnumValueDescriptorProto\022-\n\007op"
+ "tions\030\003 \001(\0132\034.google.protobuf.EnumOption"
+ "s\"l\n\030EnumValueDescriptorProto\022\014\n\004name\030\001 "
+ "\001(\t\022\016\n\006number\030\002 \001(\005\0222\n\007options\030\003 \001(\0132!.g"
+ "oogle.protobuf.EnumValueOptions\"\220\001\n\026Serv"
+ "iceDescriptorProto\022\014\n\004name\030\001 \001(\t\0226\n\006meth"
+ "od\030\002 \003(\0132&.google.protobuf.MethodDescrip"
+ "torProto\0220\n\007options\030\003 \001(\0132\037.google.proto"
+ "buf.ServiceOptions\"\301\001\n\025MethodDescriptorP"
+ "roto\022\014\n\004name\030\001 \001(\t\022\022\n\ninput_type\030\002 \001(\t\022\023"
+ "\n\013output_type\030\003 \001(\t\022/\n\007options\030\004 \001(\0132\036.g"
+ "oogle.protobuf.MethodOptions\022\037\n\020client_s"
+ "treaming\030\005 \001(\010:\005false\022\037\n\020server_streamin"
+ "g\030\006 \001(\010:\005false\"\207\005\n\013FileOptions\022\024\n\014java_p"
+ "ackage\030\001 \001(\t\022\034\n\024java_outer_classname\030\010 \001"
+ "(\t\022\"\n\023java_multiple_files\030\n \001(\010:\005false\022,"
+ "\n\035java_generate_equals_and_hash\030\024 \001(\010:\005f"
+ "alse\022%\n\026java_string_check_utf8\030\033 \001(\010:\005fa"
+ "lse\022F\n\014optimize_for\030\t \001(\0162).google.proto"
+ "buf.FileOptions.OptimizeMode:\005SPEED\022\022\n\ng"
+ "o_package\030\013 \001(\t\022\"\n\023cc_generic_services\030\020"
+ " \001(\010:\005false\022$\n\025java_generic_services\030\021 \001"
+ "(\010:\005false\022\"\n\023py_generic_services\030\022 \001(\010:\005"
+ "false\022\031\n\ndeprecated\030\027 \001(\010:\005false\022\037\n\020cc_e"
+ "nable_arenas\030\037 \001(\010:\005false\022\031\n\021objc_class_"
+ "prefix\030$ \001(\t\022\030\n\020csharp_namespace\030% \001(\t\022C"
+ "\n\024uninterpreted_option\030\347\007 \003(\0132$.google.p"
+ "rotobuf.UninterpretedOption\":\n\014OptimizeM"
+ "ode\022\t\n\005SPEED\020\001\022\r\n\tCODE_SIZE\020\002\022\020\n\014LITE_RU"
+ "NTIME\020\003*\t\010\350\007\020\200\200\200\200\002J\004\010&\020\'\"\346\001\n\016MessageOpti"
+ "ons\022&\n\027message_set_wire_format\030\001 \001(\010:\005fa"
+ "lse\022.\n\037no_standard_descriptor_accessor\030\002"
+ " \001(\010:\005false\022\031\n\ndeprecated\030\003 \001(\010:\005false\022\021"
+ "\n\tmap_entry\030\007 \001(\010\022C\n\024uninterpreted_optio"
+ "n\030\347\007 \003(\0132$.google.protobuf.Uninterpreted"
+ "Option*\t\010\350\007\020\200\200\200\200\002\"\230\003\n\014FieldOptions\022:\n\005ct"
+ "ype\030\001 \001(\0162#.google.protobuf.FieldOptions"
+ ".CType:\006STRING\022\016\n\006packed\030\002 \001(\010\022\?\n\006jstype"
+ "\030\006 \001(\0162$.google.protobuf.FieldOptions.JS"
+ "Type:\tJS_NORMAL\022\023\n\004lazy\030\005 \001(\010:\005false\022\031\n\n"
+ "deprecated\030\003 \001(\010:\005false\022\023\n\004weak\030\n \001(\010:\005f"
+ "alse\022C\n\024uninterpreted_option\030\347\007 \003(\0132$.go"
+ "ogle.protobuf.UninterpretedOption\"/\n\005CTy"
+ "pe\022\n\n\006STRING\020\000\022\010\n\004CORD\020\001\022\020\n\014STRING_PIECE"
+ "\020\002\"5\n\006JSType\022\r\n\tJS_NORMAL\020\000\022\r\n\tJS_STRING"
+ "\020\001\022\r\n\tJS_NUMBER\020\002*\t\010\350\007\020\200\200\200\200\002\"^\n\014OneofOpt"
+ "ions\022C\n\024uninterpreted_option\030\347\007 \003(\0132$.go"
+ "ogle.protobuf.UninterpretedOption*\t\010\350\007\020\200"
+ "\200\200\200\002\"\215\001\n\013EnumOptions\022\023\n\013allow_alias\030\002 \001("
+ "\010\022\031\n\ndeprecated\030\003 \001(\010:\005false\022C\n\024uninterp"
+ "reted_option\030\347\007 \003(\0132$.google.protobuf.Un"
+ "interpretedOption*\t\010\350\007\020\200\200\200\200\002\"}\n\020EnumValu"
+ "eOptions\022\031\n\ndeprecated\030\001 \001(\010:\005false\022C\n\024u"
+ "ninterpreted_option\030\347\007 \003(\0132$.google.prot"
+ "obuf.UninterpretedOption*\t\010\350\007\020\200\200\200\200\002\"{\n\016S"
+ "erviceOptions\022\031\n\ndeprecated\030! \001(\010:\005false"
+ "\022C\n\024uninterpreted_option\030\347\007 \003(\0132$.google"
+ ".protobuf.UninterpretedOption*\t\010\350\007\020\200\200\200\200\002"
+ "\"z\n\rMethodOptions\022\031\n\ndeprecated\030! \001(\010:\005f"
+ "alse\022C\n\024uninterpreted_option\030\347\007 \003(\0132$.go"
+ "ogle.protobuf.UninterpretedOption*\t\010\350\007\020\200"
+ "\200\200\200\002\"\236\002\n\023UninterpretedOption\022;\n\004name\030\002 \003"
+ "(\0132-.google.protobuf.UninterpretedOption"
+ ".NamePart\022\030\n\020identifier_value\030\003 \001(\t\022\032\n\022p"
+ "ositive_int_value\030\004 \001(\004\022\032\n\022negative_int_"
+ "value\030\005 \001(\003\022\024\n\014double_value\030\006 \001(\001\022\024\n\014str"
+ "ing_value\030\007 \001(\014\022\027\n\017aggregate_value\030\010 \001(\t"
+ "\0323\n\010NamePart\022\021\n\tname_part\030\001 \002(\t\022\024\n\014is_ex"
+ "tension\030\002 \002(\010\"\325\001\n\016SourceCodeInfo\022:\n\010loca"
+ "tion\030\001 \003(\0132(.google.protobuf.SourceCodeI"
+ "nfo.Location\032\206\001\n\010Location\022\020\n\004path\030\001 \003(\005B"
+ "\002\020\001\022\020\n\004span\030\002 \003(\005B\002\020\001\022\030\n\020leading_comment"
+ "s\030\003 \001(\t\022\031\n\021trailing_comments\030\004 \001(\t\022!\n\031le"
+ "ading_detached_comments\030\006 \003(\t\"\247\001\n\021Genera"
+ "tedCodeInfo\022A\n\nannotation\030\001 \003(\0132-.google"
+ ".protobuf.GeneratedCodeInfo.Annotation\032O"
+ "\n\nAnnotation\022\020\n\004path\030\001 \003(\005B\002\020\001\022\023\n\013source"
+ "_file\030\002 \001(\t\022\r\n\005begin\030\003 \001(\005\022\013\n\003end\030\004 \001(\005B"
+ "[\n\023com.google.protobufB\020DescriptorProtos"
+ "H\001Z\ndescriptor\240\001\001\242\002\003GPB\252\002\032Google.Protobu"
+ "f.Reflection", 5292);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/descriptor.proto", &protobuf_RegisterTypes);
+ FileDescriptorSet::default_instance_ = new FileDescriptorSet();
+ FileDescriptorProto::default_instance_ = new FileDescriptorProto();
+ DescriptorProto::default_instance_ = new DescriptorProto();
+ DescriptorProto_ExtensionRange::default_instance_ = new DescriptorProto_ExtensionRange();
+ DescriptorProto_ReservedRange::default_instance_ = new DescriptorProto_ReservedRange();
+ FieldDescriptorProto::default_instance_ = new FieldDescriptorProto();
+ OneofDescriptorProto::default_instance_ = new OneofDescriptorProto();
+ EnumDescriptorProto::default_instance_ = new EnumDescriptorProto();
+ EnumValueDescriptorProto::default_instance_ = new EnumValueDescriptorProto();
+ ServiceDescriptorProto::default_instance_ = new ServiceDescriptorProto();
+ MethodDescriptorProto::default_instance_ = new MethodDescriptorProto();
+ FileOptions::default_instance_ = new FileOptions();
+ MessageOptions::default_instance_ = new MessageOptions();
+ FieldOptions::default_instance_ = new FieldOptions();
+ OneofOptions::default_instance_ = new OneofOptions();
+ EnumOptions::default_instance_ = new EnumOptions();
+ EnumValueOptions::default_instance_ = new EnumValueOptions();
+ ServiceOptions::default_instance_ = new ServiceOptions();
+ MethodOptions::default_instance_ = new MethodOptions();
+ UninterpretedOption::default_instance_ = new UninterpretedOption();
+ UninterpretedOption_NamePart::default_instance_ = new UninterpretedOption_NamePart();
+ SourceCodeInfo::default_instance_ = new SourceCodeInfo();
+ SourceCodeInfo_Location::default_instance_ = new SourceCodeInfo_Location();
+ GeneratedCodeInfo::default_instance_ = new GeneratedCodeInfo();
+ GeneratedCodeInfo_Annotation::default_instance_ = new GeneratedCodeInfo_Annotation();
+ FileDescriptorSet::default_instance_->InitAsDefaultInstance();
+ FileDescriptorProto::default_instance_->InitAsDefaultInstance();
+ DescriptorProto::default_instance_->InitAsDefaultInstance();
+ DescriptorProto_ExtensionRange::default_instance_->InitAsDefaultInstance();
+ DescriptorProto_ReservedRange::default_instance_->InitAsDefaultInstance();
+ FieldDescriptorProto::default_instance_->InitAsDefaultInstance();
+ OneofDescriptorProto::default_instance_->InitAsDefaultInstance();
+ EnumDescriptorProto::default_instance_->InitAsDefaultInstance();
+ EnumValueDescriptorProto::default_instance_->InitAsDefaultInstance();
+ ServiceDescriptorProto::default_instance_->InitAsDefaultInstance();
+ MethodDescriptorProto::default_instance_->InitAsDefaultInstance();
+ FileOptions::default_instance_->InitAsDefaultInstance();
+ MessageOptions::default_instance_->InitAsDefaultInstance();
+ FieldOptions::default_instance_->InitAsDefaultInstance();
+ OneofOptions::default_instance_->InitAsDefaultInstance();
+ EnumOptions::default_instance_->InitAsDefaultInstance();
+ EnumValueOptions::default_instance_->InitAsDefaultInstance();
+ ServiceOptions::default_instance_->InitAsDefaultInstance();
+ MethodOptions::default_instance_->InitAsDefaultInstance();
+ UninterpretedOption::default_instance_->InitAsDefaultInstance();
+ UninterpretedOption_NamePart::default_instance_->InitAsDefaultInstance();
+ SourceCodeInfo::default_instance_->InitAsDefaultInstance();
+ SourceCodeInfo_Location::default_instance_->InitAsDefaultInstance();
+ GeneratedCodeInfo::default_instance_->InitAsDefaultInstance();
+ GeneratedCodeInfo_Annotation::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fdescriptor_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fdescriptor_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fdescriptor_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FileDescriptorSet::kFileFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+FileDescriptorSet::FileDescriptorSet()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.FileDescriptorSet)
+}
+
+void FileDescriptorSet::InitAsDefaultInstance() {
+}
+
+FileDescriptorSet::FileDescriptorSet(const FileDescriptorSet& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.FileDescriptorSet)
+}
+
+void FileDescriptorSet::SharedCtor() {
+ _cached_size_ = 0;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+FileDescriptorSet::~FileDescriptorSet() {
+ // @@protoc_insertion_point(destructor:google.protobuf.FileDescriptorSet)
+ SharedDtor();
+}
+
+void FileDescriptorSet::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void FileDescriptorSet::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* FileDescriptorSet::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FileDescriptorSet_descriptor_;
+}
+
+const FileDescriptorSet& FileDescriptorSet::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+FileDescriptorSet* FileDescriptorSet::default_instance_ = NULL;
+
+FileDescriptorSet* FileDescriptorSet::New(::google::protobuf::Arena* arena) const {
+ FileDescriptorSet* n = new FileDescriptorSet;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void FileDescriptorSet::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.FileDescriptorSet)
+ file_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool FileDescriptorSet::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.FileDescriptorSet)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated .google.protobuf.FileDescriptorProto file = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_file:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_file()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(10)) goto parse_loop_file;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.FileDescriptorSet)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.FileDescriptorSet)
+ return false;
+#undef DO_
+}
+
+void FileDescriptorSet::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.FileDescriptorSet)
+ // repeated .google.protobuf.FileDescriptorProto file = 1;
+ for (unsigned int i = 0, n = this->file_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 1, this->file(i), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.FileDescriptorSet)
+}
+
+::google::protobuf::uint8* FileDescriptorSet::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.FileDescriptorSet)
+ // repeated .google.protobuf.FileDescriptorProto file = 1;
+ for (unsigned int i = 0, n = this->file_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 1, this->file(i), false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.FileDescriptorSet)
+ return target;
+}
+
+int FileDescriptorSet::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.FileDescriptorSet)
+ int total_size = 0;
+
+ // repeated .google.protobuf.FileDescriptorProto file = 1;
+ total_size += 1 * this->file_size();
+ for (int i = 0; i < this->file_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->file(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void FileDescriptorSet::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.FileDescriptorSet)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const FileDescriptorSet* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const FileDescriptorSet>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.FileDescriptorSet)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.FileDescriptorSet)
+ MergeFrom(*source);
+ }
+}
+
+void FileDescriptorSet::MergeFrom(const FileDescriptorSet& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.FileDescriptorSet)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ file_.MergeFrom(from.file_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void FileDescriptorSet::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.FileDescriptorSet)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void FileDescriptorSet::CopyFrom(const FileDescriptorSet& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.FileDescriptorSet)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool FileDescriptorSet::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->file())) return false;
+ return true;
+}
+
+void FileDescriptorSet::Swap(FileDescriptorSet* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void FileDescriptorSet::InternalSwap(FileDescriptorSet* other) {
+ file_.UnsafeArenaSwap(&other->file_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata FileDescriptorSet::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = FileDescriptorSet_descriptor_;
+ metadata.reflection = FileDescriptorSet_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// FileDescriptorSet
+
+// repeated .google.protobuf.FileDescriptorProto file = 1;
+int FileDescriptorSet::file_size() const {
+ return file_.size();
+}
+void FileDescriptorSet::clear_file() {
+ file_.Clear();
+}
+const ::google::protobuf::FileDescriptorProto& FileDescriptorSet::file(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorSet.file)
+ return file_.Get(index);
+}
+::google::protobuf::FileDescriptorProto* FileDescriptorSet::mutable_file(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorSet.file)
+ return file_.Mutable(index);
+}
+::google::protobuf::FileDescriptorProto* FileDescriptorSet::add_file() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorSet.file)
+ return file_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >*
+FileDescriptorSet::mutable_file() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorSet.file)
+ return &file_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >&
+FileDescriptorSet::file() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorSet.file)
+ return file_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FileDescriptorProto::kNameFieldNumber;
+const int FileDescriptorProto::kPackageFieldNumber;
+const int FileDescriptorProto::kDependencyFieldNumber;
+const int FileDescriptorProto::kPublicDependencyFieldNumber;
+const int FileDescriptorProto::kWeakDependencyFieldNumber;
+const int FileDescriptorProto::kMessageTypeFieldNumber;
+const int FileDescriptorProto::kEnumTypeFieldNumber;
+const int FileDescriptorProto::kServiceFieldNumber;
+const int FileDescriptorProto::kExtensionFieldNumber;
+const int FileDescriptorProto::kOptionsFieldNumber;
+const int FileDescriptorProto::kSourceCodeInfoFieldNumber;
+const int FileDescriptorProto::kSyntaxFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+FileDescriptorProto::FileDescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.FileDescriptorProto)
+}
+
+void FileDescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::FileOptions*>(&::google::protobuf::FileOptions::default_instance());
+ source_code_info_ = const_cast< ::google::protobuf::SourceCodeInfo*>(&::google::protobuf::SourceCodeInfo::default_instance());
+}
+
+FileDescriptorProto::FileDescriptorProto(const FileDescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.FileDescriptorProto)
+}
+
+void FileDescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ package_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ options_ = NULL;
+ source_code_info_ = NULL;
+ syntax_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+FileDescriptorProto::~FileDescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.FileDescriptorProto)
+ SharedDtor();
+}
+
+void FileDescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ package_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ syntax_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ delete source_code_info_;
+ }
+}
+
+void FileDescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* FileDescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FileDescriptorProto_descriptor_;
+}
+
+const FileDescriptorProto& FileDescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+FileDescriptorProto* FileDescriptorProto::default_instance_ = NULL;
+
+FileDescriptorProto* FileDescriptorProto::New(::google::protobuf::Arena* arena) const {
+ FileDescriptorProto* n = new FileDescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void FileDescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.FileDescriptorProto)
+ if (_has_bits_[0 / 32] & 3u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_package()) {
+ package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+ if (_has_bits_[8 / 32] & 3584u) {
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::FileOptions::Clear();
+ }
+ if (has_source_code_info()) {
+ if (source_code_info_ != NULL) source_code_info_->::google::protobuf::SourceCodeInfo::Clear();
+ }
+ if (has_syntax()) {
+ syntax_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+ dependency_.Clear();
+ public_dependency_.Clear();
+ weak_dependency_.Clear();
+ message_type_.Clear();
+ enum_type_.Clear();
+ service_.Clear();
+ extension_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool FileDescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.FileDescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileDescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_package;
+ break;
+ }
+
+ // optional string package = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_package:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_package()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->package().data(), this->package().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileDescriptorProto.package");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_dependency;
+ break;
+ }
+
+ // repeated string dependency = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_dependency:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->add_dependency()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->dependency(this->dependency_size() - 1).data(),
+ this->dependency(this->dependency_size() - 1).length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileDescriptorProto.dependency");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_dependency;
+ if (input->ExpectTag(34)) goto parse_message_type;
+ break;
+ }
+
+ // repeated .google.protobuf.DescriptorProto message_type = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_message_type:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_message_type:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_message_type()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(34)) goto parse_loop_message_type;
+ if (input->ExpectTag(42)) goto parse_loop_enum_type;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 5;
+ case 5: {
+ if (tag == 42) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_enum_type:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_enum_type()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(42)) goto parse_loop_enum_type;
+ if (input->ExpectTag(50)) goto parse_loop_service;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.ServiceDescriptorProto service = 6;
+ case 6: {
+ if (tag == 50) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_service:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_service()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_loop_service;
+ if (input->ExpectTag(58)) goto parse_loop_extension;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 7;
+ case 7: {
+ if (tag == 58) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_extension:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_extension()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(58)) goto parse_loop_extension;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(66)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.FileOptions options = 8;
+ case 8: {
+ if (tag == 66) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(74)) goto parse_source_code_info;
+ break;
+ }
+
+ // optional .google.protobuf.SourceCodeInfo source_code_info = 9;
+ case 9: {
+ if (tag == 74) {
+ parse_source_code_info:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_source_code_info()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(80)) goto parse_public_dependency;
+ break;
+ }
+
+ // repeated int32 public_dependency = 10;
+ case 10: {
+ if (tag == 80) {
+ parse_public_dependency:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadRepeatedPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ 1, 80, input, this->mutable_public_dependency())));
+ } else if (tag == 82) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPackedPrimitiveNoInline<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, this->mutable_public_dependency())));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(80)) goto parse_public_dependency;
+ if (input->ExpectTag(88)) goto parse_weak_dependency;
+ break;
+ }
+
+ // repeated int32 weak_dependency = 11;
+ case 11: {
+ if (tag == 88) {
+ parse_weak_dependency:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadRepeatedPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ 1, 88, input, this->mutable_weak_dependency())));
+ } else if (tag == 90) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPackedPrimitiveNoInline<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, this->mutable_weak_dependency())));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(88)) goto parse_weak_dependency;
+ if (input->ExpectTag(98)) goto parse_syntax;
+ break;
+ }
+
+ // optional string syntax = 12;
+ case 12: {
+ if (tag == 98) {
+ parse_syntax:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_syntax()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->syntax().data(), this->syntax().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileDescriptorProto.syntax");
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.FileDescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.FileDescriptorProto)
+ return false;
+#undef DO_
+}
+
+void FileDescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.FileDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional string package = 2;
+ if (has_package()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->package().data(), this->package().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.package");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->package(), output);
+ }
+
+ // repeated string dependency = 3;
+ for (int i = 0; i < this->dependency_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->dependency(i).data(), this->dependency(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.dependency");
+ ::google::protobuf::internal::WireFormatLite::WriteString(
+ 3, this->dependency(i), output);
+ }
+
+ // repeated .google.protobuf.DescriptorProto message_type = 4;
+ for (unsigned int i = 0, n = this->message_type_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 4, this->message_type(i), output);
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 5;
+ for (unsigned int i = 0, n = this->enum_type_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 5, this->enum_type(i), output);
+ }
+
+ // repeated .google.protobuf.ServiceDescriptorProto service = 6;
+ for (unsigned int i = 0, n = this->service_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 6, this->service(i), output);
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 7;
+ for (unsigned int i = 0, n = this->extension_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 7, this->extension(i), output);
+ }
+
+ // optional .google.protobuf.FileOptions options = 8;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 8, *this->options_, output);
+ }
+
+ // optional .google.protobuf.SourceCodeInfo source_code_info = 9;
+ if (has_source_code_info()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 9, *this->source_code_info_, output);
+ }
+
+ // repeated int32 public_dependency = 10;
+ for (int i = 0; i < this->public_dependency_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(
+ 10, this->public_dependency(i), output);
+ }
+
+ // repeated int32 weak_dependency = 11;
+ for (int i = 0; i < this->weak_dependency_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(
+ 11, this->weak_dependency(i), output);
+ }
+
+ // optional string syntax = 12;
+ if (has_syntax()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->syntax().data(), this->syntax().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.syntax");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 12, this->syntax(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.FileDescriptorProto)
+}
+
+::google::protobuf::uint8* FileDescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.FileDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional string package = 2;
+ if (has_package()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->package().data(), this->package().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.package");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->package(), target);
+ }
+
+ // repeated string dependency = 3;
+ for (int i = 0; i < this->dependency_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->dependency(i).data(), this->dependency(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.dependency");
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteStringToArray(3, this->dependency(i), target);
+ }
+
+ // repeated .google.protobuf.DescriptorProto message_type = 4;
+ for (unsigned int i = 0, n = this->message_type_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 4, this->message_type(i), false, target);
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 5;
+ for (unsigned int i = 0, n = this->enum_type_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 5, this->enum_type(i), false, target);
+ }
+
+ // repeated .google.protobuf.ServiceDescriptorProto service = 6;
+ for (unsigned int i = 0, n = this->service_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 6, this->service(i), false, target);
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 7;
+ for (unsigned int i = 0, n = this->extension_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 7, this->extension(i), false, target);
+ }
+
+ // optional .google.protobuf.FileOptions options = 8;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 8, *this->options_, false, target);
+ }
+
+ // optional .google.protobuf.SourceCodeInfo source_code_info = 9;
+ if (has_source_code_info()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 9, *this->source_code_info_, false, target);
+ }
+
+ // repeated int32 public_dependency = 10;
+ for (int i = 0; i < this->public_dependency_size(); i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteInt32ToArray(10, this->public_dependency(i), target);
+ }
+
+ // repeated int32 weak_dependency = 11;
+ for (int i = 0; i < this->weak_dependency_size(); i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteInt32ToArray(11, this->weak_dependency(i), target);
+ }
+
+ // optional string syntax = 12;
+ if (has_syntax()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->syntax().data(), this->syntax().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileDescriptorProto.syntax");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 12, this->syntax(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.FileDescriptorProto)
+ return target;
+}
+
+int FileDescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.FileDescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 3u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional string package = 2;
+ if (has_package()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->package());
+ }
+
+ }
+ if (_has_bits_[9 / 32] & 3584u) {
+ // optional .google.protobuf.FileOptions options = 8;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ // optional .google.protobuf.SourceCodeInfo source_code_info = 9;
+ if (has_source_code_info()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->source_code_info_);
+ }
+
+ // optional string syntax = 12;
+ if (has_syntax()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->syntax());
+ }
+
+ }
+ // repeated string dependency = 3;
+ total_size += 1 * this->dependency_size();
+ for (int i = 0; i < this->dependency_size(); i++) {
+ total_size += ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->dependency(i));
+ }
+
+ // repeated int32 public_dependency = 10;
+ {
+ int data_size = 0;
+ for (int i = 0; i < this->public_dependency_size(); i++) {
+ data_size += ::google::protobuf::internal::WireFormatLite::
+ Int32Size(this->public_dependency(i));
+ }
+ total_size += 1 * this->public_dependency_size() + data_size;
+ }
+
+ // repeated int32 weak_dependency = 11;
+ {
+ int data_size = 0;
+ for (int i = 0; i < this->weak_dependency_size(); i++) {
+ data_size += ::google::protobuf::internal::WireFormatLite::
+ Int32Size(this->weak_dependency(i));
+ }
+ total_size += 1 * this->weak_dependency_size() + data_size;
+ }
+
+ // repeated .google.protobuf.DescriptorProto message_type = 4;
+ total_size += 1 * this->message_type_size();
+ for (int i = 0; i < this->message_type_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->message_type(i));
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 5;
+ total_size += 1 * this->enum_type_size();
+ for (int i = 0; i < this->enum_type_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->enum_type(i));
+ }
+
+ // repeated .google.protobuf.ServiceDescriptorProto service = 6;
+ total_size += 1 * this->service_size();
+ for (int i = 0; i < this->service_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->service(i));
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 7;
+ total_size += 1 * this->extension_size();
+ for (int i = 0; i < this->extension_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->extension(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void FileDescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.FileDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const FileDescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const FileDescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.FileDescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.FileDescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void FileDescriptorProto::MergeFrom(const FileDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.FileDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ dependency_.MergeFrom(from.dependency_);
+ public_dependency_.MergeFrom(from.public_dependency_);
+ weak_dependency_.MergeFrom(from.weak_dependency_);
+ message_type_.MergeFrom(from.message_type_);
+ enum_type_.MergeFrom(from.enum_type_);
+ service_.MergeFrom(from.service_);
+ extension_.MergeFrom(from.extension_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_package()) {
+ set_has_package();
+ package_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.package_);
+ }
+ }
+ if (from._has_bits_[9 / 32] & (0xffu << (9 % 32))) {
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::FileOptions::MergeFrom(from.options());
+ }
+ if (from.has_source_code_info()) {
+ mutable_source_code_info()->::google::protobuf::SourceCodeInfo::MergeFrom(from.source_code_info());
+ }
+ if (from.has_syntax()) {
+ set_has_syntax();
+ syntax_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.syntax_);
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void FileDescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.FileDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void FileDescriptorProto::CopyFrom(const FileDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.FileDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool FileDescriptorProto::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->message_type())) return false;
+ if (!::google::protobuf::internal::AllAreInitialized(this->enum_type())) return false;
+ if (!::google::protobuf::internal::AllAreInitialized(this->service())) return false;
+ if (!::google::protobuf::internal::AllAreInitialized(this->extension())) return false;
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void FileDescriptorProto::Swap(FileDescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void FileDescriptorProto::InternalSwap(FileDescriptorProto* other) {
+ name_.Swap(&other->name_);
+ package_.Swap(&other->package_);
+ dependency_.UnsafeArenaSwap(&other->dependency_);
+ public_dependency_.UnsafeArenaSwap(&other->public_dependency_);
+ weak_dependency_.UnsafeArenaSwap(&other->weak_dependency_);
+ message_type_.UnsafeArenaSwap(&other->message_type_);
+ enum_type_.UnsafeArenaSwap(&other->enum_type_);
+ service_.UnsafeArenaSwap(&other->service_);
+ extension_.UnsafeArenaSwap(&other->extension_);
+ std::swap(options_, other->options_);
+ std::swap(source_code_info_, other->source_code_info_);
+ syntax_.Swap(&other->syntax_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata FileDescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = FileDescriptorProto_descriptor_;
+ metadata.reflection = FileDescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// FileDescriptorProto
+
+// optional string name = 1;
+bool FileDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void FileDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void FileDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void FileDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& FileDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.name)
+}
+ void FileDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.name)
+}
+ void FileDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.name)
+}
+ ::std::string* FileDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.name)
+}
+
+// optional string package = 2;
+bool FileDescriptorProto::has_package() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void FileDescriptorProto::set_has_package() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void FileDescriptorProto::clear_has_package() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void FileDescriptorProto::clear_package() {
+ package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_package();
+}
+ const ::std::string& FileDescriptorProto::package() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.package)
+ return package_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileDescriptorProto::set_package(const ::std::string& value) {
+ set_has_package();
+ package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.package)
+}
+ void FileDescriptorProto::set_package(const char* value) {
+ set_has_package();
+ package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.package)
+}
+ void FileDescriptorProto::set_package(const char* value, size_t size) {
+ set_has_package();
+ package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.package)
+}
+ ::std::string* FileDescriptorProto::mutable_package() {
+ set_has_package();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.package)
+ return package_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileDescriptorProto::release_package() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.package)
+ clear_has_package();
+ return package_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileDescriptorProto::set_allocated_package(::std::string* package) {
+ if (package != NULL) {
+ set_has_package();
+ } else {
+ clear_has_package();
+ }
+ package_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), package);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.package)
+}
+
+// repeated string dependency = 3;
+int FileDescriptorProto::dependency_size() const {
+ return dependency_.size();
+}
+void FileDescriptorProto::clear_dependency() {
+ dependency_.Clear();
+}
+ const ::std::string& FileDescriptorProto::dependency(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_.Get(index);
+}
+ ::std::string* FileDescriptorProto::mutable_dependency(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_.Mutable(index);
+}
+ void FileDescriptorProto::set_dependency(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.dependency)
+ dependency_.Mutable(index)->assign(value);
+}
+ void FileDescriptorProto::set_dependency(int index, const char* value) {
+ dependency_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.dependency)
+}
+ void FileDescriptorProto::set_dependency(int index, const char* value, size_t size) {
+ dependency_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.dependency)
+}
+ ::std::string* FileDescriptorProto::add_dependency() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_.Add();
+}
+ void FileDescriptorProto::add_dependency(const ::std::string& value) {
+ dependency_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.dependency)
+}
+ void FileDescriptorProto::add_dependency(const char* value) {
+ dependency_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.FileDescriptorProto.dependency)
+}
+ void FileDescriptorProto::add_dependency(const char* value, size_t size) {
+ dependency_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.FileDescriptorProto.dependency)
+}
+ const ::google::protobuf::RepeatedPtrField< ::std::string>&
+FileDescriptorProto::dependency() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_;
+}
+ ::google::protobuf::RepeatedPtrField< ::std::string>*
+FileDescriptorProto::mutable_dependency() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.dependency)
+ return &dependency_;
+}
+
+// repeated int32 public_dependency = 10;
+int FileDescriptorProto::public_dependency_size() const {
+ return public_dependency_.size();
+}
+void FileDescriptorProto::clear_public_dependency() {
+ public_dependency_.Clear();
+}
+ ::google::protobuf::int32 FileDescriptorProto::public_dependency(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.public_dependency)
+ return public_dependency_.Get(index);
+}
+ void FileDescriptorProto::set_public_dependency(int index, ::google::protobuf::int32 value) {
+ public_dependency_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.public_dependency)
+}
+ void FileDescriptorProto::add_public_dependency(::google::protobuf::int32 value) {
+ public_dependency_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.public_dependency)
+}
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+FileDescriptorProto::public_dependency() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.public_dependency)
+ return public_dependency_;
+}
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+FileDescriptorProto::mutable_public_dependency() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.public_dependency)
+ return &public_dependency_;
+}
+
+// repeated int32 weak_dependency = 11;
+int FileDescriptorProto::weak_dependency_size() const {
+ return weak_dependency_.size();
+}
+void FileDescriptorProto::clear_weak_dependency() {
+ weak_dependency_.Clear();
+}
+ ::google::protobuf::int32 FileDescriptorProto::weak_dependency(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.weak_dependency)
+ return weak_dependency_.Get(index);
+}
+ void FileDescriptorProto::set_weak_dependency(int index, ::google::protobuf::int32 value) {
+ weak_dependency_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.weak_dependency)
+}
+ void FileDescriptorProto::add_weak_dependency(::google::protobuf::int32 value) {
+ weak_dependency_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.weak_dependency)
+}
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+FileDescriptorProto::weak_dependency() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.weak_dependency)
+ return weak_dependency_;
+}
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+FileDescriptorProto::mutable_weak_dependency() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.weak_dependency)
+ return &weak_dependency_;
+}
+
+// repeated .google.protobuf.DescriptorProto message_type = 4;
+int FileDescriptorProto::message_type_size() const {
+ return message_type_.size();
+}
+void FileDescriptorProto::clear_message_type() {
+ message_type_.Clear();
+}
+const ::google::protobuf::DescriptorProto& FileDescriptorProto::message_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_.Get(index);
+}
+::google::protobuf::DescriptorProto* FileDescriptorProto::mutable_message_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_.Mutable(index);
+}
+::google::protobuf::DescriptorProto* FileDescriptorProto::add_message_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >*
+FileDescriptorProto::mutable_message_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.message_type)
+ return &message_type_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >&
+FileDescriptorProto::message_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_;
+}
+
+// repeated .google.protobuf.EnumDescriptorProto enum_type = 5;
+int FileDescriptorProto::enum_type_size() const {
+ return enum_type_.size();
+}
+void FileDescriptorProto::clear_enum_type() {
+ enum_type_.Clear();
+}
+const ::google::protobuf::EnumDescriptorProto& FileDescriptorProto::enum_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_.Get(index);
+}
+::google::protobuf::EnumDescriptorProto* FileDescriptorProto::mutable_enum_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_.Mutable(index);
+}
+::google::protobuf::EnumDescriptorProto* FileDescriptorProto::add_enum_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >*
+FileDescriptorProto::mutable_enum_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.enum_type)
+ return &enum_type_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >&
+FileDescriptorProto::enum_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_;
+}
+
+// repeated .google.protobuf.ServiceDescriptorProto service = 6;
+int FileDescriptorProto::service_size() const {
+ return service_.size();
+}
+void FileDescriptorProto::clear_service() {
+ service_.Clear();
+}
+const ::google::protobuf::ServiceDescriptorProto& FileDescriptorProto::service(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.service)
+ return service_.Get(index);
+}
+::google::protobuf::ServiceDescriptorProto* FileDescriptorProto::mutable_service(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.service)
+ return service_.Mutable(index);
+}
+::google::protobuf::ServiceDescriptorProto* FileDescriptorProto::add_service() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.service)
+ return service_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::ServiceDescriptorProto >*
+FileDescriptorProto::mutable_service() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.service)
+ return &service_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::ServiceDescriptorProto >&
+FileDescriptorProto::service() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.service)
+ return service_;
+}
+
+// repeated .google.protobuf.FieldDescriptorProto extension = 7;
+int FileDescriptorProto::extension_size() const {
+ return extension_.size();
+}
+void FileDescriptorProto::clear_extension() {
+ extension_.Clear();
+}
+const ::google::protobuf::FieldDescriptorProto& FileDescriptorProto::extension(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.extension)
+ return extension_.Get(index);
+}
+::google::protobuf::FieldDescriptorProto* FileDescriptorProto::mutable_extension(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.extension)
+ return extension_.Mutable(index);
+}
+::google::protobuf::FieldDescriptorProto* FileDescriptorProto::add_extension() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.extension)
+ return extension_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+FileDescriptorProto::mutable_extension() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.extension)
+ return &extension_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+FileDescriptorProto::extension() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.extension)
+ return extension_;
+}
+
+// optional .google.protobuf.FileOptions options = 8;
+bool FileDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000200u) != 0;
+}
+void FileDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000200u;
+}
+void FileDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000200u;
+}
+void FileDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::FileOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::FileOptions& FileDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::FileOptions* FileDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::FileOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.options)
+ return options_;
+}
+::google::protobuf::FileOptions* FileDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::FileOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void FileDescriptorProto::set_allocated_options(::google::protobuf::FileOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.options)
+}
+
+// optional .google.protobuf.SourceCodeInfo source_code_info = 9;
+bool FileDescriptorProto::has_source_code_info() const {
+ return (_has_bits_[0] & 0x00000400u) != 0;
+}
+void FileDescriptorProto::set_has_source_code_info() {
+ _has_bits_[0] |= 0x00000400u;
+}
+void FileDescriptorProto::clear_has_source_code_info() {
+ _has_bits_[0] &= ~0x00000400u;
+}
+void FileDescriptorProto::clear_source_code_info() {
+ if (source_code_info_ != NULL) source_code_info_->::google::protobuf::SourceCodeInfo::Clear();
+ clear_has_source_code_info();
+}
+const ::google::protobuf::SourceCodeInfo& FileDescriptorProto::source_code_info() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.source_code_info)
+ return source_code_info_ != NULL ? *source_code_info_ : *default_instance_->source_code_info_;
+}
+::google::protobuf::SourceCodeInfo* FileDescriptorProto::mutable_source_code_info() {
+ set_has_source_code_info();
+ if (source_code_info_ == NULL) {
+ source_code_info_ = new ::google::protobuf::SourceCodeInfo;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.source_code_info)
+ return source_code_info_;
+}
+::google::protobuf::SourceCodeInfo* FileDescriptorProto::release_source_code_info() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.source_code_info)
+ clear_has_source_code_info();
+ ::google::protobuf::SourceCodeInfo* temp = source_code_info_;
+ source_code_info_ = NULL;
+ return temp;
+}
+void FileDescriptorProto::set_allocated_source_code_info(::google::protobuf::SourceCodeInfo* source_code_info) {
+ delete source_code_info_;
+ source_code_info_ = source_code_info;
+ if (source_code_info) {
+ set_has_source_code_info();
+ } else {
+ clear_has_source_code_info();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.source_code_info)
+}
+
+// optional string syntax = 12;
+bool FileDescriptorProto::has_syntax() const {
+ return (_has_bits_[0] & 0x00000800u) != 0;
+}
+void FileDescriptorProto::set_has_syntax() {
+ _has_bits_[0] |= 0x00000800u;
+}
+void FileDescriptorProto::clear_has_syntax() {
+ _has_bits_[0] &= ~0x00000800u;
+}
+void FileDescriptorProto::clear_syntax() {
+ syntax_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_syntax();
+}
+ const ::std::string& FileDescriptorProto::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.syntax)
+ return syntax_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileDescriptorProto::set_syntax(const ::std::string& value) {
+ set_has_syntax();
+ syntax_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.syntax)
+}
+ void FileDescriptorProto::set_syntax(const char* value) {
+ set_has_syntax();
+ syntax_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.syntax)
+}
+ void FileDescriptorProto::set_syntax(const char* value, size_t size) {
+ set_has_syntax();
+ syntax_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.syntax)
+}
+ ::std::string* FileDescriptorProto::mutable_syntax() {
+ set_has_syntax();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.syntax)
+ return syntax_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileDescriptorProto::release_syntax() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.syntax)
+ clear_has_syntax();
+ return syntax_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileDescriptorProto::set_allocated_syntax(::std::string* syntax) {
+ if (syntax != NULL) {
+ set_has_syntax();
+ } else {
+ clear_has_syntax();
+ }
+ syntax_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), syntax);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.syntax)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int DescriptorProto_ExtensionRange::kStartFieldNumber;
+const int DescriptorProto_ExtensionRange::kEndFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+DescriptorProto_ExtensionRange::DescriptorProto_ExtensionRange()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.DescriptorProto.ExtensionRange)
+}
+
+void DescriptorProto_ExtensionRange::InitAsDefaultInstance() {
+}
+
+DescriptorProto_ExtensionRange::DescriptorProto_ExtensionRange(const DescriptorProto_ExtensionRange& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.DescriptorProto.ExtensionRange)
+}
+
+void DescriptorProto_ExtensionRange::SharedCtor() {
+ _cached_size_ = 0;
+ start_ = 0;
+ end_ = 0;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+DescriptorProto_ExtensionRange::~DescriptorProto_ExtensionRange() {
+ // @@protoc_insertion_point(destructor:google.protobuf.DescriptorProto.ExtensionRange)
+ SharedDtor();
+}
+
+void DescriptorProto_ExtensionRange::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void DescriptorProto_ExtensionRange::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* DescriptorProto_ExtensionRange::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return DescriptorProto_ExtensionRange_descriptor_;
+}
+
+const DescriptorProto_ExtensionRange& DescriptorProto_ExtensionRange::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+DescriptorProto_ExtensionRange* DescriptorProto_ExtensionRange::default_instance_ = NULL;
+
+DescriptorProto_ExtensionRange* DescriptorProto_ExtensionRange::New(::google::protobuf::Arena* arena) const {
+ DescriptorProto_ExtensionRange* n = new DescriptorProto_ExtensionRange;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void DescriptorProto_ExtensionRange::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.DescriptorProto.ExtensionRange)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(DescriptorProto_ExtensionRange, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<DescriptorProto_ExtensionRange*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(start_, end_);
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool DescriptorProto_ExtensionRange::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.DescriptorProto.ExtensionRange)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional int32 start = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &start_)));
+ set_has_start();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_end;
+ break;
+ }
+
+ // optional int32 end = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_end:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &end_)));
+ set_has_end();
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.DescriptorProto.ExtensionRange)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.DescriptorProto.ExtensionRange)
+ return false;
+#undef DO_
+}
+
+void DescriptorProto_ExtensionRange::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.DescriptorProto.ExtensionRange)
+ // optional int32 start = 1;
+ if (has_start()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(1, this->start(), output);
+ }
+
+ // optional int32 end = 2;
+ if (has_end()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(2, this->end(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.DescriptorProto.ExtensionRange)
+}
+
+::google::protobuf::uint8* DescriptorProto_ExtensionRange::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.DescriptorProto.ExtensionRange)
+ // optional int32 start = 1;
+ if (has_start()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(1, this->start(), target);
+ }
+
+ // optional int32 end = 2;
+ if (has_end()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(2, this->end(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.DescriptorProto.ExtensionRange)
+ return target;
+}
+
+int DescriptorProto_ExtensionRange::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.DescriptorProto.ExtensionRange)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 3u) {
+ // optional int32 start = 1;
+ if (has_start()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->start());
+ }
+
+ // optional int32 end = 2;
+ if (has_end()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->end());
+ }
+
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void DescriptorProto_ExtensionRange::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.DescriptorProto.ExtensionRange)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const DescriptorProto_ExtensionRange* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const DescriptorProto_ExtensionRange>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.DescriptorProto.ExtensionRange)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.DescriptorProto.ExtensionRange)
+ MergeFrom(*source);
+ }
+}
+
+void DescriptorProto_ExtensionRange::MergeFrom(const DescriptorProto_ExtensionRange& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.DescriptorProto.ExtensionRange)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_start()) {
+ set_start(from.start());
+ }
+ if (from.has_end()) {
+ set_end(from.end());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void DescriptorProto_ExtensionRange::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.DescriptorProto.ExtensionRange)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void DescriptorProto_ExtensionRange::CopyFrom(const DescriptorProto_ExtensionRange& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.DescriptorProto.ExtensionRange)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool DescriptorProto_ExtensionRange::IsInitialized() const {
+
+ return true;
+}
+
+void DescriptorProto_ExtensionRange::Swap(DescriptorProto_ExtensionRange* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void DescriptorProto_ExtensionRange::InternalSwap(DescriptorProto_ExtensionRange* other) {
+ std::swap(start_, other->start_);
+ std::swap(end_, other->end_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata DescriptorProto_ExtensionRange::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = DescriptorProto_ExtensionRange_descriptor_;
+ metadata.reflection = DescriptorProto_ExtensionRange_reflection_;
+ return metadata;
+}
+
+
+// -------------------------------------------------------------------
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int DescriptorProto_ReservedRange::kStartFieldNumber;
+const int DescriptorProto_ReservedRange::kEndFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+DescriptorProto_ReservedRange::DescriptorProto_ReservedRange()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.DescriptorProto.ReservedRange)
+}
+
+void DescriptorProto_ReservedRange::InitAsDefaultInstance() {
+}
+
+DescriptorProto_ReservedRange::DescriptorProto_ReservedRange(const DescriptorProto_ReservedRange& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.DescriptorProto.ReservedRange)
+}
+
+void DescriptorProto_ReservedRange::SharedCtor() {
+ _cached_size_ = 0;
+ start_ = 0;
+ end_ = 0;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+DescriptorProto_ReservedRange::~DescriptorProto_ReservedRange() {
+ // @@protoc_insertion_point(destructor:google.protobuf.DescriptorProto.ReservedRange)
+ SharedDtor();
+}
+
+void DescriptorProto_ReservedRange::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void DescriptorProto_ReservedRange::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* DescriptorProto_ReservedRange::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return DescriptorProto_ReservedRange_descriptor_;
+}
+
+const DescriptorProto_ReservedRange& DescriptorProto_ReservedRange::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+DescriptorProto_ReservedRange* DescriptorProto_ReservedRange::default_instance_ = NULL;
+
+DescriptorProto_ReservedRange* DescriptorProto_ReservedRange::New(::google::protobuf::Arena* arena) const {
+ DescriptorProto_ReservedRange* n = new DescriptorProto_ReservedRange;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void DescriptorProto_ReservedRange::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.DescriptorProto.ReservedRange)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(DescriptorProto_ReservedRange, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<DescriptorProto_ReservedRange*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(start_, end_);
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool DescriptorProto_ReservedRange::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.DescriptorProto.ReservedRange)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional int32 start = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &start_)));
+ set_has_start();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_end;
+ break;
+ }
+
+ // optional int32 end = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_end:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &end_)));
+ set_has_end();
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.DescriptorProto.ReservedRange)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.DescriptorProto.ReservedRange)
+ return false;
+#undef DO_
+}
+
+void DescriptorProto_ReservedRange::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.DescriptorProto.ReservedRange)
+ // optional int32 start = 1;
+ if (has_start()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(1, this->start(), output);
+ }
+
+ // optional int32 end = 2;
+ if (has_end()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(2, this->end(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.DescriptorProto.ReservedRange)
+}
+
+::google::protobuf::uint8* DescriptorProto_ReservedRange::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.DescriptorProto.ReservedRange)
+ // optional int32 start = 1;
+ if (has_start()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(1, this->start(), target);
+ }
+
+ // optional int32 end = 2;
+ if (has_end()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(2, this->end(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.DescriptorProto.ReservedRange)
+ return target;
+}
+
+int DescriptorProto_ReservedRange::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.DescriptorProto.ReservedRange)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 3u) {
+ // optional int32 start = 1;
+ if (has_start()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->start());
+ }
+
+ // optional int32 end = 2;
+ if (has_end()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->end());
+ }
+
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void DescriptorProto_ReservedRange::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.DescriptorProto.ReservedRange)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const DescriptorProto_ReservedRange* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const DescriptorProto_ReservedRange>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.DescriptorProto.ReservedRange)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.DescriptorProto.ReservedRange)
+ MergeFrom(*source);
+ }
+}
+
+void DescriptorProto_ReservedRange::MergeFrom(const DescriptorProto_ReservedRange& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.DescriptorProto.ReservedRange)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_start()) {
+ set_start(from.start());
+ }
+ if (from.has_end()) {
+ set_end(from.end());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void DescriptorProto_ReservedRange::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.DescriptorProto.ReservedRange)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void DescriptorProto_ReservedRange::CopyFrom(const DescriptorProto_ReservedRange& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.DescriptorProto.ReservedRange)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool DescriptorProto_ReservedRange::IsInitialized() const {
+
+ return true;
+}
+
+void DescriptorProto_ReservedRange::Swap(DescriptorProto_ReservedRange* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void DescriptorProto_ReservedRange::InternalSwap(DescriptorProto_ReservedRange* other) {
+ std::swap(start_, other->start_);
+ std::swap(end_, other->end_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata DescriptorProto_ReservedRange::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = DescriptorProto_ReservedRange_descriptor_;
+ metadata.reflection = DescriptorProto_ReservedRange_reflection_;
+ return metadata;
+}
+
+
+// -------------------------------------------------------------------
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int DescriptorProto::kNameFieldNumber;
+const int DescriptorProto::kFieldFieldNumber;
+const int DescriptorProto::kExtensionFieldNumber;
+const int DescriptorProto::kNestedTypeFieldNumber;
+const int DescriptorProto::kEnumTypeFieldNumber;
+const int DescriptorProto::kExtensionRangeFieldNumber;
+const int DescriptorProto::kOneofDeclFieldNumber;
+const int DescriptorProto::kOptionsFieldNumber;
+const int DescriptorProto::kReservedRangeFieldNumber;
+const int DescriptorProto::kReservedNameFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+DescriptorProto::DescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.DescriptorProto)
+}
+
+void DescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::MessageOptions*>(&::google::protobuf::MessageOptions::default_instance());
+}
+
+DescriptorProto::DescriptorProto(const DescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.DescriptorProto)
+}
+
+void DescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ options_ = NULL;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+DescriptorProto::~DescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.DescriptorProto)
+ SharedDtor();
+}
+
+void DescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ }
+}
+
+void DescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* DescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return DescriptorProto_descriptor_;
+}
+
+const DescriptorProto& DescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+DescriptorProto* DescriptorProto::default_instance_ = NULL;
+
+DescriptorProto* DescriptorProto::New(::google::protobuf::Arena* arena) const {
+ DescriptorProto* n = new DescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void DescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.DescriptorProto)
+ if (_has_bits_[0 / 32] & 129u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::MessageOptions::Clear();
+ }
+ }
+ field_.Clear();
+ extension_.Clear();
+ nested_type_.Clear();
+ enum_type_.Clear();
+ extension_range_.Clear();
+ oneof_decl_.Clear();
+ reserved_range_.Clear();
+ reserved_name_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool DescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.DescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.DescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_field;
+ break;
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto field = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_field:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_field:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_field()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_loop_field;
+ if (input->ExpectTag(26)) goto parse_loop_nested_type;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.DescriptorProto nested_type = 3;
+ case 3: {
+ if (tag == 26) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_nested_type:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_nested_type()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_loop_nested_type;
+ if (input->ExpectTag(34)) goto parse_loop_enum_type;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 4;
+ case 4: {
+ if (tag == 34) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_enum_type:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_enum_type()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(34)) goto parse_loop_enum_type;
+ if (input->ExpectTag(42)) goto parse_loop_extension_range;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ExtensionRange extension_range = 5;
+ case 5: {
+ if (tag == 42) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_extension_range:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_extension_range()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(42)) goto parse_loop_extension_range;
+ if (input->ExpectTag(50)) goto parse_loop_extension;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 6;
+ case 6: {
+ if (tag == 50) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_extension:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_extension()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_loop_extension;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(58)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.MessageOptions options = 7;
+ case 7: {
+ if (tag == 58) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(66)) goto parse_oneof_decl;
+ break;
+ }
+
+ // repeated .google.protobuf.OneofDescriptorProto oneof_decl = 8;
+ case 8: {
+ if (tag == 66) {
+ parse_oneof_decl:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_oneof_decl:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_oneof_decl()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(66)) goto parse_loop_oneof_decl;
+ if (input->ExpectTag(74)) goto parse_loop_reserved_range;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ReservedRange reserved_range = 9;
+ case 9: {
+ if (tag == 74) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_reserved_range:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_reserved_range()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(74)) goto parse_loop_reserved_range;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(82)) goto parse_reserved_name;
+ break;
+ }
+
+ // repeated string reserved_name = 10;
+ case 10: {
+ if (tag == 82) {
+ parse_reserved_name:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->add_reserved_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->reserved_name(this->reserved_name_size() - 1).data(),
+ this->reserved_name(this->reserved_name_size() - 1).length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.DescriptorProto.reserved_name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(82)) goto parse_reserved_name;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.DescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.DescriptorProto)
+ return false;
+#undef DO_
+}
+
+void DescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.DescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.DescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto field = 2;
+ for (unsigned int i = 0, n = this->field_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, this->field(i), output);
+ }
+
+ // repeated .google.protobuf.DescriptorProto nested_type = 3;
+ for (unsigned int i = 0, n = this->nested_type_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 3, this->nested_type(i), output);
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 4;
+ for (unsigned int i = 0, n = this->enum_type_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 4, this->enum_type(i), output);
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ExtensionRange extension_range = 5;
+ for (unsigned int i = 0, n = this->extension_range_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 5, this->extension_range(i), output);
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 6;
+ for (unsigned int i = 0, n = this->extension_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 6, this->extension(i), output);
+ }
+
+ // optional .google.protobuf.MessageOptions options = 7;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 7, *this->options_, output);
+ }
+
+ // repeated .google.protobuf.OneofDescriptorProto oneof_decl = 8;
+ for (unsigned int i = 0, n = this->oneof_decl_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 8, this->oneof_decl(i), output);
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ReservedRange reserved_range = 9;
+ for (unsigned int i = 0, n = this->reserved_range_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 9, this->reserved_range(i), output);
+ }
+
+ // repeated string reserved_name = 10;
+ for (int i = 0; i < this->reserved_name_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->reserved_name(i).data(), this->reserved_name(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.DescriptorProto.reserved_name");
+ ::google::protobuf::internal::WireFormatLite::WriteString(
+ 10, this->reserved_name(i), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.DescriptorProto)
+}
+
+::google::protobuf::uint8* DescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.DescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.DescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto field = 2;
+ for (unsigned int i = 0, n = this->field_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, this->field(i), false, target);
+ }
+
+ // repeated .google.protobuf.DescriptorProto nested_type = 3;
+ for (unsigned int i = 0, n = this->nested_type_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 3, this->nested_type(i), false, target);
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 4;
+ for (unsigned int i = 0, n = this->enum_type_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 4, this->enum_type(i), false, target);
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ExtensionRange extension_range = 5;
+ for (unsigned int i = 0, n = this->extension_range_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 5, this->extension_range(i), false, target);
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 6;
+ for (unsigned int i = 0, n = this->extension_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 6, this->extension(i), false, target);
+ }
+
+ // optional .google.protobuf.MessageOptions options = 7;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 7, *this->options_, false, target);
+ }
+
+ // repeated .google.protobuf.OneofDescriptorProto oneof_decl = 8;
+ for (unsigned int i = 0, n = this->oneof_decl_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 8, this->oneof_decl(i), false, target);
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ReservedRange reserved_range = 9;
+ for (unsigned int i = 0, n = this->reserved_range_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 9, this->reserved_range(i), false, target);
+ }
+
+ // repeated string reserved_name = 10;
+ for (int i = 0; i < this->reserved_name_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->reserved_name(i).data(), this->reserved_name(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.DescriptorProto.reserved_name");
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteStringToArray(10, this->reserved_name(i), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.DescriptorProto)
+ return target;
+}
+
+int DescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.DescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 129u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional .google.protobuf.MessageOptions options = 7;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ }
+ // repeated .google.protobuf.FieldDescriptorProto field = 2;
+ total_size += 1 * this->field_size();
+ for (int i = 0; i < this->field_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->field(i));
+ }
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 6;
+ total_size += 1 * this->extension_size();
+ for (int i = 0; i < this->extension_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->extension(i));
+ }
+
+ // repeated .google.protobuf.DescriptorProto nested_type = 3;
+ total_size += 1 * this->nested_type_size();
+ for (int i = 0; i < this->nested_type_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->nested_type(i));
+ }
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 4;
+ total_size += 1 * this->enum_type_size();
+ for (int i = 0; i < this->enum_type_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->enum_type(i));
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ExtensionRange extension_range = 5;
+ total_size += 1 * this->extension_range_size();
+ for (int i = 0; i < this->extension_range_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->extension_range(i));
+ }
+
+ // repeated .google.protobuf.OneofDescriptorProto oneof_decl = 8;
+ total_size += 1 * this->oneof_decl_size();
+ for (int i = 0; i < this->oneof_decl_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->oneof_decl(i));
+ }
+
+ // repeated .google.protobuf.DescriptorProto.ReservedRange reserved_range = 9;
+ total_size += 1 * this->reserved_range_size();
+ for (int i = 0; i < this->reserved_range_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->reserved_range(i));
+ }
+
+ // repeated string reserved_name = 10;
+ total_size += 1 * this->reserved_name_size();
+ for (int i = 0; i < this->reserved_name_size(); i++) {
+ total_size += ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->reserved_name(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void DescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.DescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const DescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const DescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.DescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.DescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void DescriptorProto::MergeFrom(const DescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.DescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ field_.MergeFrom(from.field_);
+ extension_.MergeFrom(from.extension_);
+ nested_type_.MergeFrom(from.nested_type_);
+ enum_type_.MergeFrom(from.enum_type_);
+ extension_range_.MergeFrom(from.extension_range_);
+ oneof_decl_.MergeFrom(from.oneof_decl_);
+ reserved_range_.MergeFrom(from.reserved_range_);
+ reserved_name_.MergeFrom(from.reserved_name_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::MessageOptions::MergeFrom(from.options());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void DescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.DescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void DescriptorProto::CopyFrom(const DescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.DescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool DescriptorProto::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->field())) return false;
+ if (!::google::protobuf::internal::AllAreInitialized(this->extension())) return false;
+ if (!::google::protobuf::internal::AllAreInitialized(this->nested_type())) return false;
+ if (!::google::protobuf::internal::AllAreInitialized(this->enum_type())) return false;
+ if (!::google::protobuf::internal::AllAreInitialized(this->oneof_decl())) return false;
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void DescriptorProto::Swap(DescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void DescriptorProto::InternalSwap(DescriptorProto* other) {
+ name_.Swap(&other->name_);
+ field_.UnsafeArenaSwap(&other->field_);
+ extension_.UnsafeArenaSwap(&other->extension_);
+ nested_type_.UnsafeArenaSwap(&other->nested_type_);
+ enum_type_.UnsafeArenaSwap(&other->enum_type_);
+ extension_range_.UnsafeArenaSwap(&other->extension_range_);
+ oneof_decl_.UnsafeArenaSwap(&other->oneof_decl_);
+ std::swap(options_, other->options_);
+ reserved_range_.UnsafeArenaSwap(&other->reserved_range_);
+ reserved_name_.UnsafeArenaSwap(&other->reserved_name_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata DescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = DescriptorProto_descriptor_;
+ metadata.reflection = DescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// DescriptorProto_ExtensionRange
+
+// optional int32 start = 1;
+bool DescriptorProto_ExtensionRange::has_start() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void DescriptorProto_ExtensionRange::set_has_start() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void DescriptorProto_ExtensionRange::clear_has_start() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void DescriptorProto_ExtensionRange::clear_start() {
+ start_ = 0;
+ clear_has_start();
+}
+ ::google::protobuf::int32 DescriptorProto_ExtensionRange::start() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ExtensionRange.start)
+ return start_;
+}
+ void DescriptorProto_ExtensionRange::set_start(::google::protobuf::int32 value) {
+ set_has_start();
+ start_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ExtensionRange.start)
+}
+
+// optional int32 end = 2;
+bool DescriptorProto_ExtensionRange::has_end() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void DescriptorProto_ExtensionRange::set_has_end() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void DescriptorProto_ExtensionRange::clear_has_end() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void DescriptorProto_ExtensionRange::clear_end() {
+ end_ = 0;
+ clear_has_end();
+}
+ ::google::protobuf::int32 DescriptorProto_ExtensionRange::end() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ExtensionRange.end)
+ return end_;
+}
+ void DescriptorProto_ExtensionRange::set_end(::google::protobuf::int32 value) {
+ set_has_end();
+ end_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ExtensionRange.end)
+}
+
+// -------------------------------------------------------------------
+
+// DescriptorProto_ReservedRange
+
+// optional int32 start = 1;
+bool DescriptorProto_ReservedRange::has_start() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void DescriptorProto_ReservedRange::set_has_start() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void DescriptorProto_ReservedRange::clear_has_start() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void DescriptorProto_ReservedRange::clear_start() {
+ start_ = 0;
+ clear_has_start();
+}
+ ::google::protobuf::int32 DescriptorProto_ReservedRange::start() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ReservedRange.start)
+ return start_;
+}
+ void DescriptorProto_ReservedRange::set_start(::google::protobuf::int32 value) {
+ set_has_start();
+ start_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ReservedRange.start)
+}
+
+// optional int32 end = 2;
+bool DescriptorProto_ReservedRange::has_end() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void DescriptorProto_ReservedRange::set_has_end() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void DescriptorProto_ReservedRange::clear_has_end() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void DescriptorProto_ReservedRange::clear_end() {
+ end_ = 0;
+ clear_has_end();
+}
+ ::google::protobuf::int32 DescriptorProto_ReservedRange::end() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ReservedRange.end)
+ return end_;
+}
+ void DescriptorProto_ReservedRange::set_end(::google::protobuf::int32 value) {
+ set_has_end();
+ end_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ReservedRange.end)
+}
+
+// -------------------------------------------------------------------
+
+// DescriptorProto
+
+// optional string name = 1;
+bool DescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void DescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void DescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void DescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& DescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void DescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.name)
+}
+ void DescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.DescriptorProto.name)
+}
+ void DescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.DescriptorProto.name)
+}
+ ::std::string* DescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* DescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.DescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void DescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.DescriptorProto.name)
+}
+
+// repeated .google.protobuf.FieldDescriptorProto field = 2;
+int DescriptorProto::field_size() const {
+ return field_.size();
+}
+void DescriptorProto::clear_field() {
+ field_.Clear();
+}
+const ::google::protobuf::FieldDescriptorProto& DescriptorProto::field(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.field)
+ return field_.Get(index);
+}
+::google::protobuf::FieldDescriptorProto* DescriptorProto::mutable_field(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.field)
+ return field_.Mutable(index);
+}
+::google::protobuf::FieldDescriptorProto* DescriptorProto::add_field() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.field)
+ return field_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+DescriptorProto::mutable_field() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.field)
+ return &field_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+DescriptorProto::field() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.field)
+ return field_;
+}
+
+// repeated .google.protobuf.FieldDescriptorProto extension = 6;
+int DescriptorProto::extension_size() const {
+ return extension_.size();
+}
+void DescriptorProto::clear_extension() {
+ extension_.Clear();
+}
+const ::google::protobuf::FieldDescriptorProto& DescriptorProto::extension(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.extension)
+ return extension_.Get(index);
+}
+::google::protobuf::FieldDescriptorProto* DescriptorProto::mutable_extension(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.extension)
+ return extension_.Mutable(index);
+}
+::google::protobuf::FieldDescriptorProto* DescriptorProto::add_extension() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.extension)
+ return extension_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+DescriptorProto::mutable_extension() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.extension)
+ return &extension_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+DescriptorProto::extension() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.extension)
+ return extension_;
+}
+
+// repeated .google.protobuf.DescriptorProto nested_type = 3;
+int DescriptorProto::nested_type_size() const {
+ return nested_type_.size();
+}
+void DescriptorProto::clear_nested_type() {
+ nested_type_.Clear();
+}
+const ::google::protobuf::DescriptorProto& DescriptorProto::nested_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_.Get(index);
+}
+::google::protobuf::DescriptorProto* DescriptorProto::mutable_nested_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_.Mutable(index);
+}
+::google::protobuf::DescriptorProto* DescriptorProto::add_nested_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >*
+DescriptorProto::mutable_nested_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.nested_type)
+ return &nested_type_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >&
+DescriptorProto::nested_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_;
+}
+
+// repeated .google.protobuf.EnumDescriptorProto enum_type = 4;
+int DescriptorProto::enum_type_size() const {
+ return enum_type_.size();
+}
+void DescriptorProto::clear_enum_type() {
+ enum_type_.Clear();
+}
+const ::google::protobuf::EnumDescriptorProto& DescriptorProto::enum_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_.Get(index);
+}
+::google::protobuf::EnumDescriptorProto* DescriptorProto::mutable_enum_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_.Mutable(index);
+}
+::google::protobuf::EnumDescriptorProto* DescriptorProto::add_enum_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >*
+DescriptorProto::mutable_enum_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.enum_type)
+ return &enum_type_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >&
+DescriptorProto::enum_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_;
+}
+
+// repeated .google.protobuf.DescriptorProto.ExtensionRange extension_range = 5;
+int DescriptorProto::extension_range_size() const {
+ return extension_range_.size();
+}
+void DescriptorProto::clear_extension_range() {
+ extension_range_.Clear();
+}
+const ::google::protobuf::DescriptorProto_ExtensionRange& DescriptorProto::extension_range(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_.Get(index);
+}
+::google::protobuf::DescriptorProto_ExtensionRange* DescriptorProto::mutable_extension_range(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_.Mutable(index);
+}
+::google::protobuf::DescriptorProto_ExtensionRange* DescriptorProto::add_extension_range() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ExtensionRange >*
+DescriptorProto::mutable_extension_range() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.extension_range)
+ return &extension_range_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ExtensionRange >&
+DescriptorProto::extension_range() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_;
+}
+
+// repeated .google.protobuf.OneofDescriptorProto oneof_decl = 8;
+int DescriptorProto::oneof_decl_size() const {
+ return oneof_decl_.size();
+}
+void DescriptorProto::clear_oneof_decl() {
+ oneof_decl_.Clear();
+}
+const ::google::protobuf::OneofDescriptorProto& DescriptorProto::oneof_decl(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_.Get(index);
+}
+::google::protobuf::OneofDescriptorProto* DescriptorProto::mutable_oneof_decl(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_.Mutable(index);
+}
+::google::protobuf::OneofDescriptorProto* DescriptorProto::add_oneof_decl() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::OneofDescriptorProto >*
+DescriptorProto::mutable_oneof_decl() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.oneof_decl)
+ return &oneof_decl_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::OneofDescriptorProto >&
+DescriptorProto::oneof_decl() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_;
+}
+
+// optional .google.protobuf.MessageOptions options = 7;
+bool DescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000080u) != 0;
+}
+void DescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000080u;
+}
+void DescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000080u;
+}
+void DescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::MessageOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::MessageOptions& DescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::MessageOptions* DescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::MessageOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.options)
+ return options_;
+}
+::google::protobuf::MessageOptions* DescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.DescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::MessageOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void DescriptorProto::set_allocated_options(::google::protobuf::MessageOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.DescriptorProto.options)
+}
+
+// repeated .google.protobuf.DescriptorProto.ReservedRange reserved_range = 9;
+int DescriptorProto::reserved_range_size() const {
+ return reserved_range_.size();
+}
+void DescriptorProto::clear_reserved_range() {
+ reserved_range_.Clear();
+}
+const ::google::protobuf::DescriptorProto_ReservedRange& DescriptorProto::reserved_range(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_.Get(index);
+}
+::google::protobuf::DescriptorProto_ReservedRange* DescriptorProto::mutable_reserved_range(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_.Mutable(index);
+}
+::google::protobuf::DescriptorProto_ReservedRange* DescriptorProto::add_reserved_range() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ReservedRange >*
+DescriptorProto::mutable_reserved_range() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.reserved_range)
+ return &reserved_range_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ReservedRange >&
+DescriptorProto::reserved_range() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_;
+}
+
+// repeated string reserved_name = 10;
+int DescriptorProto::reserved_name_size() const {
+ return reserved_name_.size();
+}
+void DescriptorProto::clear_reserved_name() {
+ reserved_name_.Clear();
+}
+ const ::std::string& DescriptorProto::reserved_name(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_.Get(index);
+}
+ ::std::string* DescriptorProto::mutable_reserved_name(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_.Mutable(index);
+}
+ void DescriptorProto::set_reserved_name(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.reserved_name)
+ reserved_name_.Mutable(index)->assign(value);
+}
+ void DescriptorProto::set_reserved_name(int index, const char* value) {
+ reserved_name_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.DescriptorProto.reserved_name)
+}
+ void DescriptorProto::set_reserved_name(int index, const char* value, size_t size) {
+ reserved_name_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.DescriptorProto.reserved_name)
+}
+ ::std::string* DescriptorProto::add_reserved_name() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_.Add();
+}
+ void DescriptorProto::add_reserved_name(const ::std::string& value) {
+ reserved_name_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.reserved_name)
+}
+ void DescriptorProto::add_reserved_name(const char* value) {
+ reserved_name_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.DescriptorProto.reserved_name)
+}
+ void DescriptorProto::add_reserved_name(const char* value, size_t size) {
+ reserved_name_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.DescriptorProto.reserved_name)
+}
+ const ::google::protobuf::RepeatedPtrField< ::std::string>&
+DescriptorProto::reserved_name() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_;
+}
+ ::google::protobuf::RepeatedPtrField< ::std::string>*
+DescriptorProto::mutable_reserved_name() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.reserved_name)
+ return &reserved_name_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+const ::google::protobuf::EnumDescriptor* FieldDescriptorProto_Type_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FieldDescriptorProto_Type_descriptor_;
+}
+bool FieldDescriptorProto_Type_IsValid(int value) {
+ switch(value) {
+ case 1:
+ case 2:
+ case 3:
+ case 4:
+ case 5:
+ case 6:
+ case 7:
+ case 8:
+ case 9:
+ case 10:
+ case 11:
+ case 12:
+ case 13:
+ case 14:
+ case 15:
+ case 16:
+ case 17:
+ case 18:
+ return true;
+ default:
+ return false;
+ }
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_DOUBLE;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_FLOAT;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_INT64;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_UINT64;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_INT32;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_FIXED64;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_FIXED32;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_BOOL;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_STRING;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_GROUP;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_MESSAGE;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_BYTES;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_UINT32;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_ENUM;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_SFIXED32;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_SFIXED64;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_SINT32;
+const FieldDescriptorProto_Type FieldDescriptorProto::TYPE_SINT64;
+const FieldDescriptorProto_Type FieldDescriptorProto::Type_MIN;
+const FieldDescriptorProto_Type FieldDescriptorProto::Type_MAX;
+const int FieldDescriptorProto::Type_ARRAYSIZE;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+const ::google::protobuf::EnumDescriptor* FieldDescriptorProto_Label_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FieldDescriptorProto_Label_descriptor_;
+}
+bool FieldDescriptorProto_Label_IsValid(int value) {
+ switch(value) {
+ case 1:
+ case 2:
+ case 3:
+ return true;
+ default:
+ return false;
+ }
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const FieldDescriptorProto_Label FieldDescriptorProto::LABEL_OPTIONAL;
+const FieldDescriptorProto_Label FieldDescriptorProto::LABEL_REQUIRED;
+const FieldDescriptorProto_Label FieldDescriptorProto::LABEL_REPEATED;
+const FieldDescriptorProto_Label FieldDescriptorProto::Label_MIN;
+const FieldDescriptorProto_Label FieldDescriptorProto::Label_MAX;
+const int FieldDescriptorProto::Label_ARRAYSIZE;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FieldDescriptorProto::kNameFieldNumber;
+const int FieldDescriptorProto::kNumberFieldNumber;
+const int FieldDescriptorProto::kLabelFieldNumber;
+const int FieldDescriptorProto::kTypeFieldNumber;
+const int FieldDescriptorProto::kTypeNameFieldNumber;
+const int FieldDescriptorProto::kExtendeeFieldNumber;
+const int FieldDescriptorProto::kDefaultValueFieldNumber;
+const int FieldDescriptorProto::kOneofIndexFieldNumber;
+const int FieldDescriptorProto::kJsonNameFieldNumber;
+const int FieldDescriptorProto::kOptionsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+FieldDescriptorProto::FieldDescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.FieldDescriptorProto)
+}
+
+void FieldDescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::FieldOptions*>(&::google::protobuf::FieldOptions::default_instance());
+}
+
+FieldDescriptorProto::FieldDescriptorProto(const FieldDescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.FieldDescriptorProto)
+}
+
+void FieldDescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ number_ = 0;
+ label_ = 1;
+ type_ = 1;
+ type_name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ extendee_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ default_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ oneof_index_ = 0;
+ json_name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ options_ = NULL;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+FieldDescriptorProto::~FieldDescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.FieldDescriptorProto)
+ SharedDtor();
+}
+
+void FieldDescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ type_name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ extendee_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ default_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ json_name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ }
+}
+
+void FieldDescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* FieldDescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FieldDescriptorProto_descriptor_;
+}
+
+const FieldDescriptorProto& FieldDescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+FieldDescriptorProto* FieldDescriptorProto::default_instance_ = NULL;
+
+FieldDescriptorProto* FieldDescriptorProto::New(::google::protobuf::Arena* arena) const {
+ FieldDescriptorProto* n = new FieldDescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void FieldDescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.FieldDescriptorProto)
+ if (_has_bits_[0 / 32] & 255u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ number_ = 0;
+ label_ = 1;
+ type_ = 1;
+ if (has_type_name()) {
+ type_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_extendee()) {
+ extendee_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_default_value()) {
+ default_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ oneof_index_ = 0;
+ }
+ if (_has_bits_[8 / 32] & 768u) {
+ if (has_json_name()) {
+ json_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::FieldOptions::Clear();
+ }
+ }
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool FieldDescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.FieldDescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FieldDescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_extendee;
+ break;
+ }
+
+ // optional string extendee = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_extendee:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_extendee()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->extendee().data(), this->extendee().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FieldDescriptorProto.extendee");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(24)) goto parse_number;
+ break;
+ }
+
+ // optional int32 number = 3;
+ case 3: {
+ if (tag == 24) {
+ parse_number:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &number_)));
+ set_has_number();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(32)) goto parse_label;
+ break;
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Label label = 4;
+ case 4: {
+ if (tag == 32) {
+ parse_label:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ if (::google::protobuf::FieldDescriptorProto_Label_IsValid(value)) {
+ set_label(static_cast< ::google::protobuf::FieldDescriptorProto_Label >(value));
+ } else {
+ mutable_unknown_fields()->AddVarint(4, value);
+ }
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(40)) goto parse_type;
+ break;
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Type type = 5;
+ case 5: {
+ if (tag == 40) {
+ parse_type:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ if (::google::protobuf::FieldDescriptorProto_Type_IsValid(value)) {
+ set_type(static_cast< ::google::protobuf::FieldDescriptorProto_Type >(value));
+ } else {
+ mutable_unknown_fields()->AddVarint(5, value);
+ }
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_type_name;
+ break;
+ }
+
+ // optional string type_name = 6;
+ case 6: {
+ if (tag == 50) {
+ parse_type_name:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_type_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->type_name().data(), this->type_name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FieldDescriptorProto.type_name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(58)) goto parse_default_value;
+ break;
+ }
+
+ // optional string default_value = 7;
+ case 7: {
+ if (tag == 58) {
+ parse_default_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_default_value()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->default_value().data(), this->default_value().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FieldDescriptorProto.default_value");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(66)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.FieldOptions options = 8;
+ case 8: {
+ if (tag == 66) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(72)) goto parse_oneof_index;
+ break;
+ }
+
+ // optional int32 oneof_index = 9;
+ case 9: {
+ if (tag == 72) {
+ parse_oneof_index:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &oneof_index_)));
+ set_has_oneof_index();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(82)) goto parse_json_name;
+ break;
+ }
+
+ // optional string json_name = 10;
+ case 10: {
+ if (tag == 82) {
+ parse_json_name:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_json_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->json_name().data(), this->json_name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FieldDescriptorProto.json_name");
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.FieldDescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.FieldDescriptorProto)
+ return false;
+#undef DO_
+}
+
+void FieldDescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.FieldDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional string extendee = 2;
+ if (has_extendee()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->extendee().data(), this->extendee().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.extendee");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->extendee(), output);
+ }
+
+ // optional int32 number = 3;
+ if (has_number()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(3, this->number(), output);
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Label label = 4;
+ if (has_label()) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 4, this->label(), output);
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Type type = 5;
+ if (has_type()) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 5, this->type(), output);
+ }
+
+ // optional string type_name = 6;
+ if (has_type_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->type_name().data(), this->type_name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.type_name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 6, this->type_name(), output);
+ }
+
+ // optional string default_value = 7;
+ if (has_default_value()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->default_value().data(), this->default_value().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.default_value");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 7, this->default_value(), output);
+ }
+
+ // optional .google.protobuf.FieldOptions options = 8;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 8, *this->options_, output);
+ }
+
+ // optional int32 oneof_index = 9;
+ if (has_oneof_index()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(9, this->oneof_index(), output);
+ }
+
+ // optional string json_name = 10;
+ if (has_json_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->json_name().data(), this->json_name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.json_name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 10, this->json_name(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.FieldDescriptorProto)
+}
+
+::google::protobuf::uint8* FieldDescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.FieldDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional string extendee = 2;
+ if (has_extendee()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->extendee().data(), this->extendee().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.extendee");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->extendee(), target);
+ }
+
+ // optional int32 number = 3;
+ if (has_number()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(3, this->number(), target);
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Label label = 4;
+ if (has_label()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 4, this->label(), target);
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Type type = 5;
+ if (has_type()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 5, this->type(), target);
+ }
+
+ // optional string type_name = 6;
+ if (has_type_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->type_name().data(), this->type_name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.type_name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 6, this->type_name(), target);
+ }
+
+ // optional string default_value = 7;
+ if (has_default_value()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->default_value().data(), this->default_value().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.default_value");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 7, this->default_value(), target);
+ }
+
+ // optional .google.protobuf.FieldOptions options = 8;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 8, *this->options_, false, target);
+ }
+
+ // optional int32 oneof_index = 9;
+ if (has_oneof_index()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(9, this->oneof_index(), target);
+ }
+
+ // optional string json_name = 10;
+ if (has_json_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->json_name().data(), this->json_name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FieldDescriptorProto.json_name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 10, this->json_name(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.FieldDescriptorProto)
+ return target;
+}
+
+int FieldDescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.FieldDescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 255u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional int32 number = 3;
+ if (has_number()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->number());
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Label label = 4;
+ if (has_label()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->label());
+ }
+
+ // optional .google.protobuf.FieldDescriptorProto.Type type = 5;
+ if (has_type()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->type());
+ }
+
+ // optional string type_name = 6;
+ if (has_type_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->type_name());
+ }
+
+ // optional string extendee = 2;
+ if (has_extendee()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->extendee());
+ }
+
+ // optional string default_value = 7;
+ if (has_default_value()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->default_value());
+ }
+
+ // optional int32 oneof_index = 9;
+ if (has_oneof_index()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->oneof_index());
+ }
+
+ }
+ if (_has_bits_[8 / 32] & 768u) {
+ // optional string json_name = 10;
+ if (has_json_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->json_name());
+ }
+
+ // optional .google.protobuf.FieldOptions options = 8;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void FieldDescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.FieldDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const FieldDescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const FieldDescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.FieldDescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.FieldDescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void FieldDescriptorProto::MergeFrom(const FieldDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.FieldDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_number()) {
+ set_number(from.number());
+ }
+ if (from.has_label()) {
+ set_label(from.label());
+ }
+ if (from.has_type()) {
+ set_type(from.type());
+ }
+ if (from.has_type_name()) {
+ set_has_type_name();
+ type_name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.type_name_);
+ }
+ if (from.has_extendee()) {
+ set_has_extendee();
+ extendee_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.extendee_);
+ }
+ if (from.has_default_value()) {
+ set_has_default_value();
+ default_value_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.default_value_);
+ }
+ if (from.has_oneof_index()) {
+ set_oneof_index(from.oneof_index());
+ }
+ }
+ if (from._has_bits_[8 / 32] & (0xffu << (8 % 32))) {
+ if (from.has_json_name()) {
+ set_has_json_name();
+ json_name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.json_name_);
+ }
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::FieldOptions::MergeFrom(from.options());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void FieldDescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.FieldDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void FieldDescriptorProto::CopyFrom(const FieldDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.FieldDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool FieldDescriptorProto::IsInitialized() const {
+
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void FieldDescriptorProto::Swap(FieldDescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void FieldDescriptorProto::InternalSwap(FieldDescriptorProto* other) {
+ name_.Swap(&other->name_);
+ std::swap(number_, other->number_);
+ std::swap(label_, other->label_);
+ std::swap(type_, other->type_);
+ type_name_.Swap(&other->type_name_);
+ extendee_.Swap(&other->extendee_);
+ default_value_.Swap(&other->default_value_);
+ std::swap(oneof_index_, other->oneof_index_);
+ json_name_.Swap(&other->json_name_);
+ std::swap(options_, other->options_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata FieldDescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = FieldDescriptorProto_descriptor_;
+ metadata.reflection = FieldDescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// FieldDescriptorProto
+
+// optional string name = 1;
+bool FieldDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void FieldDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void FieldDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void FieldDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& FieldDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.name)
+}
+ void FieldDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.name)
+}
+ void FieldDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.name)
+}
+ ::std::string* FieldDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FieldDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.name)
+}
+
+// optional int32 number = 3;
+bool FieldDescriptorProto::has_number() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void FieldDescriptorProto::set_has_number() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void FieldDescriptorProto::clear_has_number() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void FieldDescriptorProto::clear_number() {
+ number_ = 0;
+ clear_has_number();
+}
+ ::google::protobuf::int32 FieldDescriptorProto::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.number)
+ return number_;
+}
+ void FieldDescriptorProto::set_number(::google::protobuf::int32 value) {
+ set_has_number();
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.number)
+}
+
+// optional .google.protobuf.FieldDescriptorProto.Label label = 4;
+bool FieldDescriptorProto::has_label() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void FieldDescriptorProto::set_has_label() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void FieldDescriptorProto::clear_has_label() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void FieldDescriptorProto::clear_label() {
+ label_ = 1;
+ clear_has_label();
+}
+ ::google::protobuf::FieldDescriptorProto_Label FieldDescriptorProto::label() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.label)
+ return static_cast< ::google::protobuf::FieldDescriptorProto_Label >(label_);
+}
+ void FieldDescriptorProto::set_label(::google::protobuf::FieldDescriptorProto_Label value) {
+ assert(::google::protobuf::FieldDescriptorProto_Label_IsValid(value));
+ set_has_label();
+ label_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.label)
+}
+
+// optional .google.protobuf.FieldDescriptorProto.Type type = 5;
+bool FieldDescriptorProto::has_type() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void FieldDescriptorProto::set_has_type() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void FieldDescriptorProto::clear_has_type() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void FieldDescriptorProto::clear_type() {
+ type_ = 1;
+ clear_has_type();
+}
+ ::google::protobuf::FieldDescriptorProto_Type FieldDescriptorProto::type() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.type)
+ return static_cast< ::google::protobuf::FieldDescriptorProto_Type >(type_);
+}
+ void FieldDescriptorProto::set_type(::google::protobuf::FieldDescriptorProto_Type value) {
+ assert(::google::protobuf::FieldDescriptorProto_Type_IsValid(value));
+ set_has_type();
+ type_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.type)
+}
+
+// optional string type_name = 6;
+bool FieldDescriptorProto::has_type_name() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+void FieldDescriptorProto::set_has_type_name() {
+ _has_bits_[0] |= 0x00000010u;
+}
+void FieldDescriptorProto::clear_has_type_name() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+void FieldDescriptorProto::clear_type_name() {
+ type_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_type_name();
+}
+ const ::std::string& FieldDescriptorProto::type_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.type_name)
+ return type_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_type_name(const ::std::string& value) {
+ set_has_type_name();
+ type_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.type_name)
+}
+ void FieldDescriptorProto::set_type_name(const char* value) {
+ set_has_type_name();
+ type_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.type_name)
+}
+ void FieldDescriptorProto::set_type_name(const char* value, size_t size) {
+ set_has_type_name();
+ type_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.type_name)
+}
+ ::std::string* FieldDescriptorProto::mutable_type_name() {
+ set_has_type_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.type_name)
+ return type_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FieldDescriptorProto::release_type_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.type_name)
+ clear_has_type_name();
+ return type_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_allocated_type_name(::std::string* type_name) {
+ if (type_name != NULL) {
+ set_has_type_name();
+ } else {
+ clear_has_type_name();
+ }
+ type_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), type_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.type_name)
+}
+
+// optional string extendee = 2;
+bool FieldDescriptorProto::has_extendee() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+void FieldDescriptorProto::set_has_extendee() {
+ _has_bits_[0] |= 0x00000020u;
+}
+void FieldDescriptorProto::clear_has_extendee() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+void FieldDescriptorProto::clear_extendee() {
+ extendee_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_extendee();
+}
+ const ::std::string& FieldDescriptorProto::extendee() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.extendee)
+ return extendee_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_extendee(const ::std::string& value) {
+ set_has_extendee();
+ extendee_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.extendee)
+}
+ void FieldDescriptorProto::set_extendee(const char* value) {
+ set_has_extendee();
+ extendee_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.extendee)
+}
+ void FieldDescriptorProto::set_extendee(const char* value, size_t size) {
+ set_has_extendee();
+ extendee_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.extendee)
+}
+ ::std::string* FieldDescriptorProto::mutable_extendee() {
+ set_has_extendee();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.extendee)
+ return extendee_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FieldDescriptorProto::release_extendee() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.extendee)
+ clear_has_extendee();
+ return extendee_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_allocated_extendee(::std::string* extendee) {
+ if (extendee != NULL) {
+ set_has_extendee();
+ } else {
+ clear_has_extendee();
+ }
+ extendee_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), extendee);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.extendee)
+}
+
+// optional string default_value = 7;
+bool FieldDescriptorProto::has_default_value() const {
+ return (_has_bits_[0] & 0x00000040u) != 0;
+}
+void FieldDescriptorProto::set_has_default_value() {
+ _has_bits_[0] |= 0x00000040u;
+}
+void FieldDescriptorProto::clear_has_default_value() {
+ _has_bits_[0] &= ~0x00000040u;
+}
+void FieldDescriptorProto::clear_default_value() {
+ default_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_default_value();
+}
+ const ::std::string& FieldDescriptorProto::default_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.default_value)
+ return default_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_default_value(const ::std::string& value) {
+ set_has_default_value();
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.default_value)
+}
+ void FieldDescriptorProto::set_default_value(const char* value) {
+ set_has_default_value();
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.default_value)
+}
+ void FieldDescriptorProto::set_default_value(const char* value, size_t size) {
+ set_has_default_value();
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.default_value)
+}
+ ::std::string* FieldDescriptorProto::mutable_default_value() {
+ set_has_default_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.default_value)
+ return default_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FieldDescriptorProto::release_default_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.default_value)
+ clear_has_default_value();
+ return default_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_allocated_default_value(::std::string* default_value) {
+ if (default_value != NULL) {
+ set_has_default_value();
+ } else {
+ clear_has_default_value();
+ }
+ default_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), default_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.default_value)
+}
+
+// optional int32 oneof_index = 9;
+bool FieldDescriptorProto::has_oneof_index() const {
+ return (_has_bits_[0] & 0x00000080u) != 0;
+}
+void FieldDescriptorProto::set_has_oneof_index() {
+ _has_bits_[0] |= 0x00000080u;
+}
+void FieldDescriptorProto::clear_has_oneof_index() {
+ _has_bits_[0] &= ~0x00000080u;
+}
+void FieldDescriptorProto::clear_oneof_index() {
+ oneof_index_ = 0;
+ clear_has_oneof_index();
+}
+ ::google::protobuf::int32 FieldDescriptorProto::oneof_index() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.oneof_index)
+ return oneof_index_;
+}
+ void FieldDescriptorProto::set_oneof_index(::google::protobuf::int32 value) {
+ set_has_oneof_index();
+ oneof_index_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.oneof_index)
+}
+
+// optional string json_name = 10;
+bool FieldDescriptorProto::has_json_name() const {
+ return (_has_bits_[0] & 0x00000100u) != 0;
+}
+void FieldDescriptorProto::set_has_json_name() {
+ _has_bits_[0] |= 0x00000100u;
+}
+void FieldDescriptorProto::clear_has_json_name() {
+ _has_bits_[0] &= ~0x00000100u;
+}
+void FieldDescriptorProto::clear_json_name() {
+ json_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_json_name();
+}
+ const ::std::string& FieldDescriptorProto::json_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.json_name)
+ return json_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_json_name(const ::std::string& value) {
+ set_has_json_name();
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.json_name)
+}
+ void FieldDescriptorProto::set_json_name(const char* value) {
+ set_has_json_name();
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.json_name)
+}
+ void FieldDescriptorProto::set_json_name(const char* value, size_t size) {
+ set_has_json_name();
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.json_name)
+}
+ ::std::string* FieldDescriptorProto::mutable_json_name() {
+ set_has_json_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.json_name)
+ return json_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FieldDescriptorProto::release_json_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.json_name)
+ clear_has_json_name();
+ return json_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FieldDescriptorProto::set_allocated_json_name(::std::string* json_name) {
+ if (json_name != NULL) {
+ set_has_json_name();
+ } else {
+ clear_has_json_name();
+ }
+ json_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), json_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.json_name)
+}
+
+// optional .google.protobuf.FieldOptions options = 8;
+bool FieldDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000200u) != 0;
+}
+void FieldDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000200u;
+}
+void FieldDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000200u;
+}
+void FieldDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::FieldOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::FieldOptions& FieldDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::FieldOptions* FieldDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::FieldOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.options)
+ return options_;
+}
+::google::protobuf::FieldOptions* FieldDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::FieldOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void FieldDescriptorProto::set_allocated_options(::google::protobuf::FieldOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.options)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int OneofDescriptorProto::kNameFieldNumber;
+const int OneofDescriptorProto::kOptionsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+OneofDescriptorProto::OneofDescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.OneofDescriptorProto)
+}
+
+void OneofDescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::OneofOptions*>(&::google::protobuf::OneofOptions::default_instance());
+}
+
+OneofDescriptorProto::OneofDescriptorProto(const OneofDescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.OneofDescriptorProto)
+}
+
+void OneofDescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ options_ = NULL;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+OneofDescriptorProto::~OneofDescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.OneofDescriptorProto)
+ SharedDtor();
+}
+
+void OneofDescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ }
+}
+
+void OneofDescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* OneofDescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return OneofDescriptorProto_descriptor_;
+}
+
+const OneofDescriptorProto& OneofDescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+OneofDescriptorProto* OneofDescriptorProto::default_instance_ = NULL;
+
+OneofDescriptorProto* OneofDescriptorProto::New(::google::protobuf::Arena* arena) const {
+ OneofDescriptorProto* n = new OneofDescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void OneofDescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.OneofDescriptorProto)
+ if (_has_bits_[0 / 32] & 3u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::OneofOptions::Clear();
+ }
+ }
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool OneofDescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.OneofDescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.OneofDescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.OneofOptions options = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.OneofDescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.OneofDescriptorProto)
+ return false;
+#undef DO_
+}
+
+void OneofDescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.OneofDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.OneofDescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional .google.protobuf.OneofOptions options = 2;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, *this->options_, output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.OneofDescriptorProto)
+}
+
+::google::protobuf::uint8* OneofDescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.OneofDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.OneofDescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional .google.protobuf.OneofOptions options = 2;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, *this->options_, false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.OneofDescriptorProto)
+ return target;
+}
+
+int OneofDescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.OneofDescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 3u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional .google.protobuf.OneofOptions options = 2;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void OneofDescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.OneofDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const OneofDescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const OneofDescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.OneofDescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.OneofDescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void OneofDescriptorProto::MergeFrom(const OneofDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.OneofDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::OneofOptions::MergeFrom(from.options());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void OneofDescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.OneofDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void OneofDescriptorProto::CopyFrom(const OneofDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.OneofDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool OneofDescriptorProto::IsInitialized() const {
+
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void OneofDescriptorProto::Swap(OneofDescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void OneofDescriptorProto::InternalSwap(OneofDescriptorProto* other) {
+ name_.Swap(&other->name_);
+ std::swap(options_, other->options_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata OneofDescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = OneofDescriptorProto_descriptor_;
+ metadata.reflection = OneofDescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// OneofDescriptorProto
+
+// optional string name = 1;
+bool OneofDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void OneofDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void OneofDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void OneofDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& OneofDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.OneofDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void OneofDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.OneofDescriptorProto.name)
+}
+ void OneofDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.OneofDescriptorProto.name)
+}
+ void OneofDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.OneofDescriptorProto.name)
+}
+ ::std::string* OneofDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.OneofDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* OneofDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.OneofDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void OneofDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.OneofDescriptorProto.name)
+}
+
+// optional .google.protobuf.OneofOptions options = 2;
+bool OneofDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void OneofDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void OneofDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void OneofDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::OneofOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::OneofOptions& OneofDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.OneofDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::OneofOptions* OneofDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::OneofOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.OneofDescriptorProto.options)
+ return options_;
+}
+::google::protobuf::OneofOptions* OneofDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.OneofDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::OneofOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void OneofDescriptorProto::set_allocated_options(::google::protobuf::OneofOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.OneofDescriptorProto.options)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int EnumDescriptorProto::kNameFieldNumber;
+const int EnumDescriptorProto::kValueFieldNumber;
+const int EnumDescriptorProto::kOptionsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+EnumDescriptorProto::EnumDescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.EnumDescriptorProto)
+}
+
+void EnumDescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::EnumOptions*>(&::google::protobuf::EnumOptions::default_instance());
+}
+
+EnumDescriptorProto::EnumDescriptorProto(const EnumDescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.EnumDescriptorProto)
+}
+
+void EnumDescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ options_ = NULL;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+EnumDescriptorProto::~EnumDescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.EnumDescriptorProto)
+ SharedDtor();
+}
+
+void EnumDescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ }
+}
+
+void EnumDescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* EnumDescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return EnumDescriptorProto_descriptor_;
+}
+
+const EnumDescriptorProto& EnumDescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+EnumDescriptorProto* EnumDescriptorProto::default_instance_ = NULL;
+
+EnumDescriptorProto* EnumDescriptorProto::New(::google::protobuf::Arena* arena) const {
+ EnumDescriptorProto* n = new EnumDescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void EnumDescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.EnumDescriptorProto)
+ if (_has_bits_[0 / 32] & 5u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::EnumOptions::Clear();
+ }
+ }
+ value_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool EnumDescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.EnumDescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.EnumDescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_value;
+ break;
+ }
+
+ // repeated .google.protobuf.EnumValueDescriptorProto value = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_value:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_value()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_loop_value;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(26)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.EnumOptions options = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.EnumDescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.EnumDescriptorProto)
+ return false;
+#undef DO_
+}
+
+void EnumDescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.EnumDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.EnumDescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // repeated .google.protobuf.EnumValueDescriptorProto value = 2;
+ for (unsigned int i = 0, n = this->value_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, this->value(i), output);
+ }
+
+ // optional .google.protobuf.EnumOptions options = 3;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 3, *this->options_, output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.EnumDescriptorProto)
+}
+
+::google::protobuf::uint8* EnumDescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.EnumDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.EnumDescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // repeated .google.protobuf.EnumValueDescriptorProto value = 2;
+ for (unsigned int i = 0, n = this->value_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, this->value(i), false, target);
+ }
+
+ // optional .google.protobuf.EnumOptions options = 3;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 3, *this->options_, false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.EnumDescriptorProto)
+ return target;
+}
+
+int EnumDescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.EnumDescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 5u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional .google.protobuf.EnumOptions options = 3;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ }
+ // repeated .google.protobuf.EnumValueDescriptorProto value = 2;
+ total_size += 1 * this->value_size();
+ for (int i = 0; i < this->value_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->value(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void EnumDescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.EnumDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const EnumDescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const EnumDescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.EnumDescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.EnumDescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void EnumDescriptorProto::MergeFrom(const EnumDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.EnumDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ value_.MergeFrom(from.value_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::EnumOptions::MergeFrom(from.options());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void EnumDescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.EnumDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void EnumDescriptorProto::CopyFrom(const EnumDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.EnumDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool EnumDescriptorProto::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->value())) return false;
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void EnumDescriptorProto::Swap(EnumDescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void EnumDescriptorProto::InternalSwap(EnumDescriptorProto* other) {
+ name_.Swap(&other->name_);
+ value_.UnsafeArenaSwap(&other->value_);
+ std::swap(options_, other->options_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata EnumDescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = EnumDescriptorProto_descriptor_;
+ metadata.reflection = EnumDescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// EnumDescriptorProto
+
+// optional string name = 1;
+bool EnumDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void EnumDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void EnumDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void EnumDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& EnumDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void EnumDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumDescriptorProto.name)
+}
+ void EnumDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.EnumDescriptorProto.name)
+}
+ void EnumDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.EnumDescriptorProto.name)
+}
+ ::std::string* EnumDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* EnumDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void EnumDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumDescriptorProto.name)
+}
+
+// repeated .google.protobuf.EnumValueDescriptorProto value = 2;
+int EnumDescriptorProto::value_size() const {
+ return value_.size();
+}
+void EnumDescriptorProto::clear_value() {
+ value_.Clear();
+}
+const ::google::protobuf::EnumValueDescriptorProto& EnumDescriptorProto::value(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumDescriptorProto.value)
+ return value_.Get(index);
+}
+::google::protobuf::EnumValueDescriptorProto* EnumDescriptorProto::mutable_value(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumDescriptorProto.value)
+ return value_.Mutable(index);
+}
+::google::protobuf::EnumValueDescriptorProto* EnumDescriptorProto::add_value() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumDescriptorProto.value)
+ return value_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValueDescriptorProto >*
+EnumDescriptorProto::mutable_value() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumDescriptorProto.value)
+ return &value_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValueDescriptorProto >&
+EnumDescriptorProto::value() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumDescriptorProto.value)
+ return value_;
+}
+
+// optional .google.protobuf.EnumOptions options = 3;
+bool EnumDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void EnumDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void EnumDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void EnumDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::EnumOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::EnumOptions& EnumDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::EnumOptions* EnumDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::EnumOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumDescriptorProto.options)
+ return options_;
+}
+::google::protobuf::EnumOptions* EnumDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::EnumOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void EnumDescriptorProto::set_allocated_options(::google::protobuf::EnumOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumDescriptorProto.options)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int EnumValueDescriptorProto::kNameFieldNumber;
+const int EnumValueDescriptorProto::kNumberFieldNumber;
+const int EnumValueDescriptorProto::kOptionsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+EnumValueDescriptorProto::EnumValueDescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.EnumValueDescriptorProto)
+}
+
+void EnumValueDescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::EnumValueOptions*>(&::google::protobuf::EnumValueOptions::default_instance());
+}
+
+EnumValueDescriptorProto::EnumValueDescriptorProto(const EnumValueDescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.EnumValueDescriptorProto)
+}
+
+void EnumValueDescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ number_ = 0;
+ options_ = NULL;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+EnumValueDescriptorProto::~EnumValueDescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.EnumValueDescriptorProto)
+ SharedDtor();
+}
+
+void EnumValueDescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ }
+}
+
+void EnumValueDescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* EnumValueDescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return EnumValueDescriptorProto_descriptor_;
+}
+
+const EnumValueDescriptorProto& EnumValueDescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+EnumValueDescriptorProto* EnumValueDescriptorProto::default_instance_ = NULL;
+
+EnumValueDescriptorProto* EnumValueDescriptorProto::New(::google::protobuf::Arena* arena) const {
+ EnumValueDescriptorProto* n = new EnumValueDescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void EnumValueDescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.EnumValueDescriptorProto)
+ if (_has_bits_[0 / 32] & 7u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ number_ = 0;
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::EnumValueOptions::Clear();
+ }
+ }
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool EnumValueDescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.EnumValueDescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.EnumValueDescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_number;
+ break;
+ }
+
+ // optional int32 number = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_number:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &number_)));
+ set_has_number();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.EnumValueOptions options = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.EnumValueDescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.EnumValueDescriptorProto)
+ return false;
+#undef DO_
+}
+
+void EnumValueDescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.EnumValueDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.EnumValueDescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional int32 number = 2;
+ if (has_number()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(2, this->number(), output);
+ }
+
+ // optional .google.protobuf.EnumValueOptions options = 3;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 3, *this->options_, output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.EnumValueDescriptorProto)
+}
+
+::google::protobuf::uint8* EnumValueDescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.EnumValueDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.EnumValueDescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional int32 number = 2;
+ if (has_number()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(2, this->number(), target);
+ }
+
+ // optional .google.protobuf.EnumValueOptions options = 3;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 3, *this->options_, false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.EnumValueDescriptorProto)
+ return target;
+}
+
+int EnumValueDescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.EnumValueDescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 7u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional int32 number = 2;
+ if (has_number()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->number());
+ }
+
+ // optional .google.protobuf.EnumValueOptions options = 3;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void EnumValueDescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.EnumValueDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const EnumValueDescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const EnumValueDescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.EnumValueDescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.EnumValueDescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void EnumValueDescriptorProto::MergeFrom(const EnumValueDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.EnumValueDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_number()) {
+ set_number(from.number());
+ }
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::EnumValueOptions::MergeFrom(from.options());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void EnumValueDescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.EnumValueDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void EnumValueDescriptorProto::CopyFrom(const EnumValueDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.EnumValueDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool EnumValueDescriptorProto::IsInitialized() const {
+
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void EnumValueDescriptorProto::Swap(EnumValueDescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void EnumValueDescriptorProto::InternalSwap(EnumValueDescriptorProto* other) {
+ name_.Swap(&other->name_);
+ std::swap(number_, other->number_);
+ std::swap(options_, other->options_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata EnumValueDescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = EnumValueDescriptorProto_descriptor_;
+ metadata.reflection = EnumValueDescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// EnumValueDescriptorProto
+
+// optional string name = 1;
+bool EnumValueDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void EnumValueDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void EnumValueDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void EnumValueDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& EnumValueDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void EnumValueDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValueDescriptorProto.name)
+}
+ void EnumValueDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.EnumValueDescriptorProto.name)
+}
+ void EnumValueDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.EnumValueDescriptorProto.name)
+}
+ ::std::string* EnumValueDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValueDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* EnumValueDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumValueDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void EnumValueDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumValueDescriptorProto.name)
+}
+
+// optional int32 number = 2;
+bool EnumValueDescriptorProto::has_number() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void EnumValueDescriptorProto::set_has_number() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void EnumValueDescriptorProto::clear_has_number() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void EnumValueDescriptorProto::clear_number() {
+ number_ = 0;
+ clear_has_number();
+}
+ ::google::protobuf::int32 EnumValueDescriptorProto::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueDescriptorProto.number)
+ return number_;
+}
+ void EnumValueDescriptorProto::set_number(::google::protobuf::int32 value) {
+ set_has_number();
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValueDescriptorProto.number)
+}
+
+// optional .google.protobuf.EnumValueOptions options = 3;
+bool EnumValueDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void EnumValueDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void EnumValueDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void EnumValueDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::EnumValueOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::EnumValueOptions& EnumValueDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::EnumValueOptions* EnumValueDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::EnumValueOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValueDescriptorProto.options)
+ return options_;
+}
+::google::protobuf::EnumValueOptions* EnumValueDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumValueDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::EnumValueOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void EnumValueDescriptorProto::set_allocated_options(::google::protobuf::EnumValueOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumValueDescriptorProto.options)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int ServiceDescriptorProto::kNameFieldNumber;
+const int ServiceDescriptorProto::kMethodFieldNumber;
+const int ServiceDescriptorProto::kOptionsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+ServiceDescriptorProto::ServiceDescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.ServiceDescriptorProto)
+}
+
+void ServiceDescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::ServiceOptions*>(&::google::protobuf::ServiceOptions::default_instance());
+}
+
+ServiceDescriptorProto::ServiceDescriptorProto(const ServiceDescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.ServiceDescriptorProto)
+}
+
+void ServiceDescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ options_ = NULL;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+ServiceDescriptorProto::~ServiceDescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.ServiceDescriptorProto)
+ SharedDtor();
+}
+
+void ServiceDescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ }
+}
+
+void ServiceDescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* ServiceDescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return ServiceDescriptorProto_descriptor_;
+}
+
+const ServiceDescriptorProto& ServiceDescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+ServiceDescriptorProto* ServiceDescriptorProto::default_instance_ = NULL;
+
+ServiceDescriptorProto* ServiceDescriptorProto::New(::google::protobuf::Arena* arena) const {
+ ServiceDescriptorProto* n = new ServiceDescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void ServiceDescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.ServiceDescriptorProto)
+ if (_has_bits_[0 / 32] & 5u) {
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::ServiceOptions::Clear();
+ }
+ }
+ method_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool ServiceDescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.ServiceDescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.ServiceDescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_method;
+ break;
+ }
+
+ // repeated .google.protobuf.MethodDescriptorProto method = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_method:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_method:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_method()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_loop_method;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(26)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.ServiceOptions options = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.ServiceDescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.ServiceDescriptorProto)
+ return false;
+#undef DO_
+}
+
+void ServiceDescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.ServiceDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.ServiceDescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // repeated .google.protobuf.MethodDescriptorProto method = 2;
+ for (unsigned int i = 0, n = this->method_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, this->method(i), output);
+ }
+
+ // optional .google.protobuf.ServiceOptions options = 3;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 3, *this->options_, output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.ServiceDescriptorProto)
+}
+
+::google::protobuf::uint8* ServiceDescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.ServiceDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.ServiceDescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // repeated .google.protobuf.MethodDescriptorProto method = 2;
+ for (unsigned int i = 0, n = this->method_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, this->method(i), false, target);
+ }
+
+ // optional .google.protobuf.ServiceOptions options = 3;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 3, *this->options_, false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.ServiceDescriptorProto)
+ return target;
+}
+
+int ServiceDescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.ServiceDescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 5u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional .google.protobuf.ServiceOptions options = 3;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ }
+ // repeated .google.protobuf.MethodDescriptorProto method = 2;
+ total_size += 1 * this->method_size();
+ for (int i = 0; i < this->method_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->method(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void ServiceDescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.ServiceDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const ServiceDescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const ServiceDescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.ServiceDescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.ServiceDescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void ServiceDescriptorProto::MergeFrom(const ServiceDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.ServiceDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ method_.MergeFrom(from.method_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::ServiceOptions::MergeFrom(from.options());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void ServiceDescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.ServiceDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void ServiceDescriptorProto::CopyFrom(const ServiceDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.ServiceDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool ServiceDescriptorProto::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->method())) return false;
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void ServiceDescriptorProto::Swap(ServiceDescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void ServiceDescriptorProto::InternalSwap(ServiceDescriptorProto* other) {
+ name_.Swap(&other->name_);
+ method_.UnsafeArenaSwap(&other->method_);
+ std::swap(options_, other->options_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata ServiceDescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = ServiceDescriptorProto_descriptor_;
+ metadata.reflection = ServiceDescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// ServiceDescriptorProto
+
+// optional string name = 1;
+bool ServiceDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void ServiceDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void ServiceDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void ServiceDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& ServiceDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void ServiceDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.ServiceDescriptorProto.name)
+}
+ void ServiceDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.ServiceDescriptorProto.name)
+}
+ void ServiceDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.ServiceDescriptorProto.name)
+}
+ ::std::string* ServiceDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* ServiceDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.ServiceDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void ServiceDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.ServiceDescriptorProto.name)
+}
+
+// repeated .google.protobuf.MethodDescriptorProto method = 2;
+int ServiceDescriptorProto::method_size() const {
+ return method_.size();
+}
+void ServiceDescriptorProto::clear_method() {
+ method_.Clear();
+}
+const ::google::protobuf::MethodDescriptorProto& ServiceDescriptorProto::method(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceDescriptorProto.method)
+ return method_.Get(index);
+}
+::google::protobuf::MethodDescriptorProto* ServiceDescriptorProto::mutable_method(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceDescriptorProto.method)
+ return method_.Mutable(index);
+}
+::google::protobuf::MethodDescriptorProto* ServiceDescriptorProto::add_method() {
+ // @@protoc_insertion_point(field_add:google.protobuf.ServiceDescriptorProto.method)
+ return method_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::MethodDescriptorProto >*
+ServiceDescriptorProto::mutable_method() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.ServiceDescriptorProto.method)
+ return &method_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::MethodDescriptorProto >&
+ServiceDescriptorProto::method() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.ServiceDescriptorProto.method)
+ return method_;
+}
+
+// optional .google.protobuf.ServiceOptions options = 3;
+bool ServiceDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void ServiceDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void ServiceDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void ServiceDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::ServiceOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::ServiceOptions& ServiceDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::ServiceOptions* ServiceDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::ServiceOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceDescriptorProto.options)
+ return options_;
+}
+::google::protobuf::ServiceOptions* ServiceDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.ServiceDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::ServiceOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void ServiceDescriptorProto::set_allocated_options(::google::protobuf::ServiceOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.ServiceDescriptorProto.options)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int MethodDescriptorProto::kNameFieldNumber;
+const int MethodDescriptorProto::kInputTypeFieldNumber;
+const int MethodDescriptorProto::kOutputTypeFieldNumber;
+const int MethodDescriptorProto::kOptionsFieldNumber;
+const int MethodDescriptorProto::kClientStreamingFieldNumber;
+const int MethodDescriptorProto::kServerStreamingFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+MethodDescriptorProto::MethodDescriptorProto()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.MethodDescriptorProto)
+}
+
+void MethodDescriptorProto::InitAsDefaultInstance() {
+ options_ = const_cast< ::google::protobuf::MethodOptions*>(&::google::protobuf::MethodOptions::default_instance());
+}
+
+MethodDescriptorProto::MethodDescriptorProto(const MethodDescriptorProto& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.MethodDescriptorProto)
+}
+
+void MethodDescriptorProto::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ input_type_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ output_type_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ options_ = NULL;
+ client_streaming_ = false;
+ server_streaming_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+MethodDescriptorProto::~MethodDescriptorProto() {
+ // @@protoc_insertion_point(destructor:google.protobuf.MethodDescriptorProto)
+ SharedDtor();
+}
+
+void MethodDescriptorProto::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ input_type_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ output_type_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete options_;
+ }
+}
+
+void MethodDescriptorProto::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* MethodDescriptorProto::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return MethodDescriptorProto_descriptor_;
+}
+
+const MethodDescriptorProto& MethodDescriptorProto::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+MethodDescriptorProto* MethodDescriptorProto::default_instance_ = NULL;
+
+MethodDescriptorProto* MethodDescriptorProto::New(::google::protobuf::Arena* arena) const {
+ MethodDescriptorProto* n = new MethodDescriptorProto;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void MethodDescriptorProto::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.MethodDescriptorProto)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(MethodDescriptorProto, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<MethodDescriptorProto*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ if (_has_bits_[0 / 32] & 63u) {
+ ZR_(client_streaming_, server_streaming_);
+ if (has_name()) {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_input_type()) {
+ input_type_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_output_type()) {
+ output_type_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_options()) {
+ if (options_ != NULL) options_->::google::protobuf::MethodOptions::Clear();
+ }
+ }
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool MethodDescriptorProto::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.MethodDescriptorProto)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.MethodDescriptorProto.name");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_input_type;
+ break;
+ }
+
+ // optional string input_type = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_input_type:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_input_type()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->input_type().data(), this->input_type().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.MethodDescriptorProto.input_type");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_output_type;
+ break;
+ }
+
+ // optional string output_type = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_output_type:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_output_type()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->output_type().data(), this->output_type().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.MethodDescriptorProto.output_type");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(34)) goto parse_options;
+ break;
+ }
+
+ // optional .google.protobuf.MethodOptions options = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(40)) goto parse_client_streaming;
+ break;
+ }
+
+ // optional bool client_streaming = 5 [default = false];
+ case 5: {
+ if (tag == 40) {
+ parse_client_streaming:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &client_streaming_)));
+ set_has_client_streaming();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(48)) goto parse_server_streaming;
+ break;
+ }
+
+ // optional bool server_streaming = 6 [default = false];
+ case 6: {
+ if (tag == 48) {
+ parse_server_streaming:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &server_streaming_)));
+ set_has_server_streaming();
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.MethodDescriptorProto)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.MethodDescriptorProto)
+ return false;
+#undef DO_
+}
+
+void MethodDescriptorProto::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.MethodDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.MethodDescriptorProto.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional string input_type = 2;
+ if (has_input_type()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->input_type().data(), this->input_type().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.MethodDescriptorProto.input_type");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->input_type(), output);
+ }
+
+ // optional string output_type = 3;
+ if (has_output_type()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->output_type().data(), this->output_type().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.MethodDescriptorProto.output_type");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 3, this->output_type(), output);
+ }
+
+ // optional .google.protobuf.MethodOptions options = 4;
+ if (has_options()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 4, *this->options_, output);
+ }
+
+ // optional bool client_streaming = 5 [default = false];
+ if (has_client_streaming()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(5, this->client_streaming(), output);
+ }
+
+ // optional bool server_streaming = 6 [default = false];
+ if (has_server_streaming()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(6, this->server_streaming(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.MethodDescriptorProto)
+}
+
+::google::protobuf::uint8* MethodDescriptorProto::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.MethodDescriptorProto)
+ // optional string name = 1;
+ if (has_name()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.MethodDescriptorProto.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional string input_type = 2;
+ if (has_input_type()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->input_type().data(), this->input_type().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.MethodDescriptorProto.input_type");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->input_type(), target);
+ }
+
+ // optional string output_type = 3;
+ if (has_output_type()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->output_type().data(), this->output_type().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.MethodDescriptorProto.output_type");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 3, this->output_type(), target);
+ }
+
+ // optional .google.protobuf.MethodOptions options = 4;
+ if (has_options()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 4, *this->options_, false, target);
+ }
+
+ // optional bool client_streaming = 5 [default = false];
+ if (has_client_streaming()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(5, this->client_streaming(), target);
+ }
+
+ // optional bool server_streaming = 6 [default = false];
+ if (has_server_streaming()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(6, this->server_streaming(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.MethodDescriptorProto)
+ return target;
+}
+
+int MethodDescriptorProto::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.MethodDescriptorProto)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 63u) {
+ // optional string name = 1;
+ if (has_name()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional string input_type = 2;
+ if (has_input_type()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->input_type());
+ }
+
+ // optional string output_type = 3;
+ if (has_output_type()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->output_type());
+ }
+
+ // optional .google.protobuf.MethodOptions options = 4;
+ if (has_options()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->options_);
+ }
+
+ // optional bool client_streaming = 5 [default = false];
+ if (has_client_streaming()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool server_streaming = 6 [default = false];
+ if (has_server_streaming()) {
+ total_size += 1 + 1;
+ }
+
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void MethodDescriptorProto::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.MethodDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const MethodDescriptorProto* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const MethodDescriptorProto>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.MethodDescriptorProto)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.MethodDescriptorProto)
+ MergeFrom(*source);
+ }
+}
+
+void MethodDescriptorProto::MergeFrom(const MethodDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.MethodDescriptorProto)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name()) {
+ set_has_name();
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_input_type()) {
+ set_has_input_type();
+ input_type_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.input_type_);
+ }
+ if (from.has_output_type()) {
+ set_has_output_type();
+ output_type_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.output_type_);
+ }
+ if (from.has_options()) {
+ mutable_options()->::google::protobuf::MethodOptions::MergeFrom(from.options());
+ }
+ if (from.has_client_streaming()) {
+ set_client_streaming(from.client_streaming());
+ }
+ if (from.has_server_streaming()) {
+ set_server_streaming(from.server_streaming());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void MethodDescriptorProto::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.MethodDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void MethodDescriptorProto::CopyFrom(const MethodDescriptorProto& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.MethodDescriptorProto)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool MethodDescriptorProto::IsInitialized() const {
+
+ if (has_options()) {
+ if (!this->options_->IsInitialized()) return false;
+ }
+ return true;
+}
+
+void MethodDescriptorProto::Swap(MethodDescriptorProto* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void MethodDescriptorProto::InternalSwap(MethodDescriptorProto* other) {
+ name_.Swap(&other->name_);
+ input_type_.Swap(&other->input_type_);
+ output_type_.Swap(&other->output_type_);
+ std::swap(options_, other->options_);
+ std::swap(client_streaming_, other->client_streaming_);
+ std::swap(server_streaming_, other->server_streaming_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata MethodDescriptorProto::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = MethodDescriptorProto_descriptor_;
+ metadata.reflection = MethodDescriptorProto_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// MethodDescriptorProto
+
+// optional string name = 1;
+bool MethodDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void MethodDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void MethodDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void MethodDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+ const ::std::string& MethodDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void MethodDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.name)
+}
+ void MethodDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.MethodDescriptorProto.name)
+}
+ void MethodDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.MethodDescriptorProto.name)
+}
+ ::std::string* MethodDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* MethodDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void MethodDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.name)
+}
+
+// optional string input_type = 2;
+bool MethodDescriptorProto::has_input_type() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void MethodDescriptorProto::set_has_input_type() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void MethodDescriptorProto::clear_has_input_type() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void MethodDescriptorProto::clear_input_type() {
+ input_type_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_input_type();
+}
+ const ::std::string& MethodDescriptorProto::input_type() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.input_type)
+ return input_type_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void MethodDescriptorProto::set_input_type(const ::std::string& value) {
+ set_has_input_type();
+ input_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.input_type)
+}
+ void MethodDescriptorProto::set_input_type(const char* value) {
+ set_has_input_type();
+ input_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.MethodDescriptorProto.input_type)
+}
+ void MethodDescriptorProto::set_input_type(const char* value, size_t size) {
+ set_has_input_type();
+ input_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.MethodDescriptorProto.input_type)
+}
+ ::std::string* MethodDescriptorProto::mutable_input_type() {
+ set_has_input_type();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.input_type)
+ return input_type_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* MethodDescriptorProto::release_input_type() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.input_type)
+ clear_has_input_type();
+ return input_type_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void MethodDescriptorProto::set_allocated_input_type(::std::string* input_type) {
+ if (input_type != NULL) {
+ set_has_input_type();
+ } else {
+ clear_has_input_type();
+ }
+ input_type_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), input_type);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.input_type)
+}
+
+// optional string output_type = 3;
+bool MethodDescriptorProto::has_output_type() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void MethodDescriptorProto::set_has_output_type() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void MethodDescriptorProto::clear_has_output_type() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void MethodDescriptorProto::clear_output_type() {
+ output_type_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_output_type();
+}
+ const ::std::string& MethodDescriptorProto::output_type() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.output_type)
+ return output_type_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void MethodDescriptorProto::set_output_type(const ::std::string& value) {
+ set_has_output_type();
+ output_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.output_type)
+}
+ void MethodDescriptorProto::set_output_type(const char* value) {
+ set_has_output_type();
+ output_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.MethodDescriptorProto.output_type)
+}
+ void MethodDescriptorProto::set_output_type(const char* value, size_t size) {
+ set_has_output_type();
+ output_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.MethodDescriptorProto.output_type)
+}
+ ::std::string* MethodDescriptorProto::mutable_output_type() {
+ set_has_output_type();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.output_type)
+ return output_type_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* MethodDescriptorProto::release_output_type() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.output_type)
+ clear_has_output_type();
+ return output_type_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void MethodDescriptorProto::set_allocated_output_type(::std::string* output_type) {
+ if (output_type != NULL) {
+ set_has_output_type();
+ } else {
+ clear_has_output_type();
+ }
+ output_type_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), output_type);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.output_type)
+}
+
+// optional .google.protobuf.MethodOptions options = 4;
+bool MethodDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void MethodDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void MethodDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void MethodDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::MethodOptions::Clear();
+ clear_has_options();
+}
+const ::google::protobuf::MethodOptions& MethodDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+::google::protobuf::MethodOptions* MethodDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::MethodOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.options)
+ return options_;
+}
+::google::protobuf::MethodOptions* MethodDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::MethodOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+void MethodDescriptorProto::set_allocated_options(::google::protobuf::MethodOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.options)
+}
+
+// optional bool client_streaming = 5 [default = false];
+bool MethodDescriptorProto::has_client_streaming() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+void MethodDescriptorProto::set_has_client_streaming() {
+ _has_bits_[0] |= 0x00000010u;
+}
+void MethodDescriptorProto::clear_has_client_streaming() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+void MethodDescriptorProto::clear_client_streaming() {
+ client_streaming_ = false;
+ clear_has_client_streaming();
+}
+ bool MethodDescriptorProto::client_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.client_streaming)
+ return client_streaming_;
+}
+ void MethodDescriptorProto::set_client_streaming(bool value) {
+ set_has_client_streaming();
+ client_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.client_streaming)
+}
+
+// optional bool server_streaming = 6 [default = false];
+bool MethodDescriptorProto::has_server_streaming() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+void MethodDescriptorProto::set_has_server_streaming() {
+ _has_bits_[0] |= 0x00000020u;
+}
+void MethodDescriptorProto::clear_has_server_streaming() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+void MethodDescriptorProto::clear_server_streaming() {
+ server_streaming_ = false;
+ clear_has_server_streaming();
+}
+ bool MethodDescriptorProto::server_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.server_streaming)
+ return server_streaming_;
+}
+ void MethodDescriptorProto::set_server_streaming(bool value) {
+ set_has_server_streaming();
+ server_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.server_streaming)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+const ::google::protobuf::EnumDescriptor* FileOptions_OptimizeMode_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FileOptions_OptimizeMode_descriptor_;
+}
+bool FileOptions_OptimizeMode_IsValid(int value) {
+ switch(value) {
+ case 1:
+ case 2:
+ case 3:
+ return true;
+ default:
+ return false;
+ }
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const FileOptions_OptimizeMode FileOptions::SPEED;
+const FileOptions_OptimizeMode FileOptions::CODE_SIZE;
+const FileOptions_OptimizeMode FileOptions::LITE_RUNTIME;
+const FileOptions_OptimizeMode FileOptions::OptimizeMode_MIN;
+const FileOptions_OptimizeMode FileOptions::OptimizeMode_MAX;
+const int FileOptions::OptimizeMode_ARRAYSIZE;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FileOptions::kJavaPackageFieldNumber;
+const int FileOptions::kJavaOuterClassnameFieldNumber;
+const int FileOptions::kJavaMultipleFilesFieldNumber;
+const int FileOptions::kJavaGenerateEqualsAndHashFieldNumber;
+const int FileOptions::kJavaStringCheckUtf8FieldNumber;
+const int FileOptions::kOptimizeForFieldNumber;
+const int FileOptions::kGoPackageFieldNumber;
+const int FileOptions::kCcGenericServicesFieldNumber;
+const int FileOptions::kJavaGenericServicesFieldNumber;
+const int FileOptions::kPyGenericServicesFieldNumber;
+const int FileOptions::kDeprecatedFieldNumber;
+const int FileOptions::kCcEnableArenasFieldNumber;
+const int FileOptions::kObjcClassPrefixFieldNumber;
+const int FileOptions::kCsharpNamespaceFieldNumber;
+const int FileOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+FileOptions::FileOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.FileOptions)
+}
+
+void FileOptions::InitAsDefaultInstance() {
+}
+
+FileOptions::FileOptions(const FileOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.FileOptions)
+}
+
+void FileOptions::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ java_package_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ java_outer_classname_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ java_multiple_files_ = false;
+ java_generate_equals_and_hash_ = false;
+ java_string_check_utf8_ = false;
+ optimize_for_ = 1;
+ go_package_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ cc_generic_services_ = false;
+ java_generic_services_ = false;
+ py_generic_services_ = false;
+ deprecated_ = false;
+ cc_enable_arenas_ = false;
+ objc_class_prefix_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ csharp_namespace_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+FileOptions::~FileOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.FileOptions)
+ SharedDtor();
+}
+
+void FileOptions::SharedDtor() {
+ java_package_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ java_outer_classname_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ go_package_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ objc_class_prefix_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ csharp_namespace_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void FileOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* FileOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FileOptions_descriptor_;
+}
+
+const FileOptions& FileOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+FileOptions* FileOptions::default_instance_ = NULL;
+
+FileOptions* FileOptions::New(::google::protobuf::Arena* arena) const {
+ FileOptions* n = new FileOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void FileOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.FileOptions)
+ _extensions_.Clear();
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(FileOptions, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<FileOptions*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ if (_has_bits_[0 / 32] & 255u) {
+ ZR_(java_multiple_files_, cc_generic_services_);
+ if (has_java_package()) {
+ java_package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_java_outer_classname()) {
+ java_outer_classname_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ optimize_for_ = 1;
+ if (has_go_package()) {
+ go_package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+ if (_has_bits_[8 / 32] & 16128u) {
+ ZR_(java_generic_services_, cc_enable_arenas_);
+ if (has_objc_class_prefix()) {
+ objc_class_prefix_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_csharp_namespace()) {
+ csharp_namespace_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool FileOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.FileOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string java_package = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_java_package()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->java_package().data(), this->java_package().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileOptions.java_package");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(66)) goto parse_java_outer_classname;
+ break;
+ }
+
+ // optional string java_outer_classname = 8;
+ case 8: {
+ if (tag == 66) {
+ parse_java_outer_classname:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_java_outer_classname()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->java_outer_classname().data(), this->java_outer_classname().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileOptions.java_outer_classname");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(72)) goto parse_optimize_for;
+ break;
+ }
+
+ // optional .google.protobuf.FileOptions.OptimizeMode optimize_for = 9 [default = SPEED];
+ case 9: {
+ if (tag == 72) {
+ parse_optimize_for:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ if (::google::protobuf::FileOptions_OptimizeMode_IsValid(value)) {
+ set_optimize_for(static_cast< ::google::protobuf::FileOptions_OptimizeMode >(value));
+ } else {
+ mutable_unknown_fields()->AddVarint(9, value);
+ }
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(80)) goto parse_java_multiple_files;
+ break;
+ }
+
+ // optional bool java_multiple_files = 10 [default = false];
+ case 10: {
+ if (tag == 80) {
+ parse_java_multiple_files:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &java_multiple_files_)));
+ set_has_java_multiple_files();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(90)) goto parse_go_package;
+ break;
+ }
+
+ // optional string go_package = 11;
+ case 11: {
+ if (tag == 90) {
+ parse_go_package:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_go_package()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->go_package().data(), this->go_package().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileOptions.go_package");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(128)) goto parse_cc_generic_services;
+ break;
+ }
+
+ // optional bool cc_generic_services = 16 [default = false];
+ case 16: {
+ if (tag == 128) {
+ parse_cc_generic_services:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &cc_generic_services_)));
+ set_has_cc_generic_services();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(136)) goto parse_java_generic_services;
+ break;
+ }
+
+ // optional bool java_generic_services = 17 [default = false];
+ case 17: {
+ if (tag == 136) {
+ parse_java_generic_services:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &java_generic_services_)));
+ set_has_java_generic_services();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(144)) goto parse_py_generic_services;
+ break;
+ }
+
+ // optional bool py_generic_services = 18 [default = false];
+ case 18: {
+ if (tag == 144) {
+ parse_py_generic_services:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &py_generic_services_)));
+ set_has_py_generic_services();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(160)) goto parse_java_generate_equals_and_hash;
+ break;
+ }
+
+ // optional bool java_generate_equals_and_hash = 20 [default = false];
+ case 20: {
+ if (tag == 160) {
+ parse_java_generate_equals_and_hash:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &java_generate_equals_and_hash_)));
+ set_has_java_generate_equals_and_hash();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(184)) goto parse_deprecated;
+ break;
+ }
+
+ // optional bool deprecated = 23 [default = false];
+ case 23: {
+ if (tag == 184) {
+ parse_deprecated:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &deprecated_)));
+ set_has_deprecated();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(216)) goto parse_java_string_check_utf8;
+ break;
+ }
+
+ // optional bool java_string_check_utf8 = 27 [default = false];
+ case 27: {
+ if (tag == 216) {
+ parse_java_string_check_utf8:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &java_string_check_utf8_)));
+ set_has_java_string_check_utf8();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(248)) goto parse_cc_enable_arenas;
+ break;
+ }
+
+ // optional bool cc_enable_arenas = 31 [default = false];
+ case 31: {
+ if (tag == 248) {
+ parse_cc_enable_arenas:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &cc_enable_arenas_)));
+ set_has_cc_enable_arenas();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(290)) goto parse_objc_class_prefix;
+ break;
+ }
+
+ // optional string objc_class_prefix = 36;
+ case 36: {
+ if (tag == 290) {
+ parse_objc_class_prefix:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_objc_class_prefix()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->objc_class_prefix().data(), this->objc_class_prefix().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileOptions.objc_class_prefix");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(298)) goto parse_csharp_namespace;
+ break;
+ }
+
+ // optional string csharp_namespace = 37;
+ case 37: {
+ if (tag == 298) {
+ parse_csharp_namespace:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_csharp_namespace()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->csharp_namespace().data(), this->csharp_namespace().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.FileOptions.csharp_namespace");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_uninterpreted_option;
+ break;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ parse_uninterpreted_option:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.FileOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.FileOptions)
+ return false;
+#undef DO_
+}
+
+void FileOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.FileOptions)
+ // optional string java_package = 1;
+ if (has_java_package()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->java_package().data(), this->java_package().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.java_package");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->java_package(), output);
+ }
+
+ // optional string java_outer_classname = 8;
+ if (has_java_outer_classname()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->java_outer_classname().data(), this->java_outer_classname().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.java_outer_classname");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 8, this->java_outer_classname(), output);
+ }
+
+ // optional .google.protobuf.FileOptions.OptimizeMode optimize_for = 9 [default = SPEED];
+ if (has_optimize_for()) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 9, this->optimize_for(), output);
+ }
+
+ // optional bool java_multiple_files = 10 [default = false];
+ if (has_java_multiple_files()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(10, this->java_multiple_files(), output);
+ }
+
+ // optional string go_package = 11;
+ if (has_go_package()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->go_package().data(), this->go_package().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.go_package");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 11, this->go_package(), output);
+ }
+
+ // optional bool cc_generic_services = 16 [default = false];
+ if (has_cc_generic_services()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(16, this->cc_generic_services(), output);
+ }
+
+ // optional bool java_generic_services = 17 [default = false];
+ if (has_java_generic_services()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(17, this->java_generic_services(), output);
+ }
+
+ // optional bool py_generic_services = 18 [default = false];
+ if (has_py_generic_services()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(18, this->py_generic_services(), output);
+ }
+
+ // optional bool java_generate_equals_and_hash = 20 [default = false];
+ if (has_java_generate_equals_and_hash()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(20, this->java_generate_equals_and_hash(), output);
+ }
+
+ // optional bool deprecated = 23 [default = false];
+ if (has_deprecated()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(23, this->deprecated(), output);
+ }
+
+ // optional bool java_string_check_utf8 = 27 [default = false];
+ if (has_java_string_check_utf8()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(27, this->java_string_check_utf8(), output);
+ }
+
+ // optional bool cc_enable_arenas = 31 [default = false];
+ if (has_cc_enable_arenas()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(31, this->cc_enable_arenas(), output);
+ }
+
+ // optional string objc_class_prefix = 36;
+ if (has_objc_class_prefix()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->objc_class_prefix().data(), this->objc_class_prefix().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.objc_class_prefix");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 36, this->objc_class_prefix(), output);
+ }
+
+ // optional string csharp_namespace = 37;
+ if (has_csharp_namespace()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->csharp_namespace().data(), this->csharp_namespace().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.csharp_namespace");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 37, this->csharp_namespace(), output);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.FileOptions)
+}
+
+::google::protobuf::uint8* FileOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.FileOptions)
+ // optional string java_package = 1;
+ if (has_java_package()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->java_package().data(), this->java_package().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.java_package");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->java_package(), target);
+ }
+
+ // optional string java_outer_classname = 8;
+ if (has_java_outer_classname()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->java_outer_classname().data(), this->java_outer_classname().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.java_outer_classname");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 8, this->java_outer_classname(), target);
+ }
+
+ // optional .google.protobuf.FileOptions.OptimizeMode optimize_for = 9 [default = SPEED];
+ if (has_optimize_for()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 9, this->optimize_for(), target);
+ }
+
+ // optional bool java_multiple_files = 10 [default = false];
+ if (has_java_multiple_files()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(10, this->java_multiple_files(), target);
+ }
+
+ // optional string go_package = 11;
+ if (has_go_package()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->go_package().data(), this->go_package().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.go_package");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 11, this->go_package(), target);
+ }
+
+ // optional bool cc_generic_services = 16 [default = false];
+ if (has_cc_generic_services()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(16, this->cc_generic_services(), target);
+ }
+
+ // optional bool java_generic_services = 17 [default = false];
+ if (has_java_generic_services()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(17, this->java_generic_services(), target);
+ }
+
+ // optional bool py_generic_services = 18 [default = false];
+ if (has_py_generic_services()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(18, this->py_generic_services(), target);
+ }
+
+ // optional bool java_generate_equals_and_hash = 20 [default = false];
+ if (has_java_generate_equals_and_hash()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(20, this->java_generate_equals_and_hash(), target);
+ }
+
+ // optional bool deprecated = 23 [default = false];
+ if (has_deprecated()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(23, this->deprecated(), target);
+ }
+
+ // optional bool java_string_check_utf8 = 27 [default = false];
+ if (has_java_string_check_utf8()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(27, this->java_string_check_utf8(), target);
+ }
+
+ // optional bool cc_enable_arenas = 31 [default = false];
+ if (has_cc_enable_arenas()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(31, this->cc_enable_arenas(), target);
+ }
+
+ // optional string objc_class_prefix = 36;
+ if (has_objc_class_prefix()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->objc_class_prefix().data(), this->objc_class_prefix().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.objc_class_prefix");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 36, this->objc_class_prefix(), target);
+ }
+
+ // optional string csharp_namespace = 37;
+ if (has_csharp_namespace()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->csharp_namespace().data(), this->csharp_namespace().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.FileOptions.csharp_namespace");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 37, this->csharp_namespace(), target);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.FileOptions)
+ return target;
+}
+
+int FileOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.FileOptions)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 255u) {
+ // optional string java_package = 1;
+ if (has_java_package()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->java_package());
+ }
+
+ // optional string java_outer_classname = 8;
+ if (has_java_outer_classname()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->java_outer_classname());
+ }
+
+ // optional bool java_multiple_files = 10 [default = false];
+ if (has_java_multiple_files()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool java_generate_equals_and_hash = 20 [default = false];
+ if (has_java_generate_equals_and_hash()) {
+ total_size += 2 + 1;
+ }
+
+ // optional bool java_string_check_utf8 = 27 [default = false];
+ if (has_java_string_check_utf8()) {
+ total_size += 2 + 1;
+ }
+
+ // optional .google.protobuf.FileOptions.OptimizeMode optimize_for = 9 [default = SPEED];
+ if (has_optimize_for()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->optimize_for());
+ }
+
+ // optional string go_package = 11;
+ if (has_go_package()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->go_package());
+ }
+
+ // optional bool cc_generic_services = 16 [default = false];
+ if (has_cc_generic_services()) {
+ total_size += 2 + 1;
+ }
+
+ }
+ if (_has_bits_[8 / 32] & 16128u) {
+ // optional bool java_generic_services = 17 [default = false];
+ if (has_java_generic_services()) {
+ total_size += 2 + 1;
+ }
+
+ // optional bool py_generic_services = 18 [default = false];
+ if (has_py_generic_services()) {
+ total_size += 2 + 1;
+ }
+
+ // optional bool deprecated = 23 [default = false];
+ if (has_deprecated()) {
+ total_size += 2 + 1;
+ }
+
+ // optional bool cc_enable_arenas = 31 [default = false];
+ if (has_cc_enable_arenas()) {
+ total_size += 2 + 1;
+ }
+
+ // optional string objc_class_prefix = 36;
+ if (has_objc_class_prefix()) {
+ total_size += 2 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->objc_class_prefix());
+ }
+
+ // optional string csharp_namespace = 37;
+ if (has_csharp_namespace()) {
+ total_size += 2 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->csharp_namespace());
+ }
+
+ }
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void FileOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.FileOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const FileOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const FileOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.FileOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.FileOptions)
+ MergeFrom(*source);
+ }
+}
+
+void FileOptions::MergeFrom(const FileOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.FileOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_java_package()) {
+ set_has_java_package();
+ java_package_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.java_package_);
+ }
+ if (from.has_java_outer_classname()) {
+ set_has_java_outer_classname();
+ java_outer_classname_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.java_outer_classname_);
+ }
+ if (from.has_java_multiple_files()) {
+ set_java_multiple_files(from.java_multiple_files());
+ }
+ if (from.has_java_generate_equals_and_hash()) {
+ set_java_generate_equals_and_hash(from.java_generate_equals_and_hash());
+ }
+ if (from.has_java_string_check_utf8()) {
+ set_java_string_check_utf8(from.java_string_check_utf8());
+ }
+ if (from.has_optimize_for()) {
+ set_optimize_for(from.optimize_for());
+ }
+ if (from.has_go_package()) {
+ set_has_go_package();
+ go_package_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.go_package_);
+ }
+ if (from.has_cc_generic_services()) {
+ set_cc_generic_services(from.cc_generic_services());
+ }
+ }
+ if (from._has_bits_[8 / 32] & (0xffu << (8 % 32))) {
+ if (from.has_java_generic_services()) {
+ set_java_generic_services(from.java_generic_services());
+ }
+ if (from.has_py_generic_services()) {
+ set_py_generic_services(from.py_generic_services());
+ }
+ if (from.has_deprecated()) {
+ set_deprecated(from.deprecated());
+ }
+ if (from.has_cc_enable_arenas()) {
+ set_cc_enable_arenas(from.cc_enable_arenas());
+ }
+ if (from.has_objc_class_prefix()) {
+ set_has_objc_class_prefix();
+ objc_class_prefix_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.objc_class_prefix_);
+ }
+ if (from.has_csharp_namespace()) {
+ set_has_csharp_namespace();
+ csharp_namespace_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.csharp_namespace_);
+ }
+ }
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void FileOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.FileOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void FileOptions::CopyFrom(const FileOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.FileOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool FileOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void FileOptions::Swap(FileOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void FileOptions::InternalSwap(FileOptions* other) {
+ java_package_.Swap(&other->java_package_);
+ java_outer_classname_.Swap(&other->java_outer_classname_);
+ std::swap(java_multiple_files_, other->java_multiple_files_);
+ std::swap(java_generate_equals_and_hash_, other->java_generate_equals_and_hash_);
+ std::swap(java_string_check_utf8_, other->java_string_check_utf8_);
+ std::swap(optimize_for_, other->optimize_for_);
+ go_package_.Swap(&other->go_package_);
+ std::swap(cc_generic_services_, other->cc_generic_services_);
+ std::swap(java_generic_services_, other->java_generic_services_);
+ std::swap(py_generic_services_, other->py_generic_services_);
+ std::swap(deprecated_, other->deprecated_);
+ std::swap(cc_enable_arenas_, other->cc_enable_arenas_);
+ objc_class_prefix_.Swap(&other->objc_class_prefix_);
+ csharp_namespace_.Swap(&other->csharp_namespace_);
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata FileOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = FileOptions_descriptor_;
+ metadata.reflection = FileOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// FileOptions
+
+// optional string java_package = 1;
+bool FileOptions::has_java_package() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void FileOptions::set_has_java_package() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void FileOptions::clear_has_java_package() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void FileOptions::clear_java_package() {
+ java_package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_java_package();
+}
+ const ::std::string& FileOptions::java_package() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_package)
+ return java_package_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_java_package(const ::std::string& value) {
+ set_has_java_package();
+ java_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_package)
+}
+ void FileOptions::set_java_package(const char* value) {
+ set_has_java_package();
+ java_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.java_package)
+}
+ void FileOptions::set_java_package(const char* value, size_t size) {
+ set_has_java_package();
+ java_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.java_package)
+}
+ ::std::string* FileOptions::mutable_java_package() {
+ set_has_java_package();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.java_package)
+ return java_package_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileOptions::release_java_package() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.java_package)
+ clear_has_java_package();
+ return java_package_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_allocated_java_package(::std::string* java_package) {
+ if (java_package != NULL) {
+ set_has_java_package();
+ } else {
+ clear_has_java_package();
+ }
+ java_package_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), java_package);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.java_package)
+}
+
+// optional string java_outer_classname = 8;
+bool FileOptions::has_java_outer_classname() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void FileOptions::set_has_java_outer_classname() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void FileOptions::clear_has_java_outer_classname() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void FileOptions::clear_java_outer_classname() {
+ java_outer_classname_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_java_outer_classname();
+}
+ const ::std::string& FileOptions::java_outer_classname() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_outer_classname)
+ return java_outer_classname_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_java_outer_classname(const ::std::string& value) {
+ set_has_java_outer_classname();
+ java_outer_classname_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_outer_classname)
+}
+ void FileOptions::set_java_outer_classname(const char* value) {
+ set_has_java_outer_classname();
+ java_outer_classname_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.java_outer_classname)
+}
+ void FileOptions::set_java_outer_classname(const char* value, size_t size) {
+ set_has_java_outer_classname();
+ java_outer_classname_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.java_outer_classname)
+}
+ ::std::string* FileOptions::mutable_java_outer_classname() {
+ set_has_java_outer_classname();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.java_outer_classname)
+ return java_outer_classname_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileOptions::release_java_outer_classname() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.java_outer_classname)
+ clear_has_java_outer_classname();
+ return java_outer_classname_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_allocated_java_outer_classname(::std::string* java_outer_classname) {
+ if (java_outer_classname != NULL) {
+ set_has_java_outer_classname();
+ } else {
+ clear_has_java_outer_classname();
+ }
+ java_outer_classname_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), java_outer_classname);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.java_outer_classname)
+}
+
+// optional bool java_multiple_files = 10 [default = false];
+bool FileOptions::has_java_multiple_files() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void FileOptions::set_has_java_multiple_files() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void FileOptions::clear_has_java_multiple_files() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void FileOptions::clear_java_multiple_files() {
+ java_multiple_files_ = false;
+ clear_has_java_multiple_files();
+}
+ bool FileOptions::java_multiple_files() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_multiple_files)
+ return java_multiple_files_;
+}
+ void FileOptions::set_java_multiple_files(bool value) {
+ set_has_java_multiple_files();
+ java_multiple_files_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_multiple_files)
+}
+
+// optional bool java_generate_equals_and_hash = 20 [default = false];
+bool FileOptions::has_java_generate_equals_and_hash() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void FileOptions::set_has_java_generate_equals_and_hash() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void FileOptions::clear_has_java_generate_equals_and_hash() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void FileOptions::clear_java_generate_equals_and_hash() {
+ java_generate_equals_and_hash_ = false;
+ clear_has_java_generate_equals_and_hash();
+}
+ bool FileOptions::java_generate_equals_and_hash() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_generate_equals_and_hash)
+ return java_generate_equals_and_hash_;
+}
+ void FileOptions::set_java_generate_equals_and_hash(bool value) {
+ set_has_java_generate_equals_and_hash();
+ java_generate_equals_and_hash_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_generate_equals_and_hash)
+}
+
+// optional bool java_string_check_utf8 = 27 [default = false];
+bool FileOptions::has_java_string_check_utf8() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+void FileOptions::set_has_java_string_check_utf8() {
+ _has_bits_[0] |= 0x00000010u;
+}
+void FileOptions::clear_has_java_string_check_utf8() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+void FileOptions::clear_java_string_check_utf8() {
+ java_string_check_utf8_ = false;
+ clear_has_java_string_check_utf8();
+}
+ bool FileOptions::java_string_check_utf8() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_string_check_utf8)
+ return java_string_check_utf8_;
+}
+ void FileOptions::set_java_string_check_utf8(bool value) {
+ set_has_java_string_check_utf8();
+ java_string_check_utf8_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_string_check_utf8)
+}
+
+// optional .google.protobuf.FileOptions.OptimizeMode optimize_for = 9 [default = SPEED];
+bool FileOptions::has_optimize_for() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+void FileOptions::set_has_optimize_for() {
+ _has_bits_[0] |= 0x00000020u;
+}
+void FileOptions::clear_has_optimize_for() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+void FileOptions::clear_optimize_for() {
+ optimize_for_ = 1;
+ clear_has_optimize_for();
+}
+ ::google::protobuf::FileOptions_OptimizeMode FileOptions::optimize_for() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.optimize_for)
+ return static_cast< ::google::protobuf::FileOptions_OptimizeMode >(optimize_for_);
+}
+ void FileOptions::set_optimize_for(::google::protobuf::FileOptions_OptimizeMode value) {
+ assert(::google::protobuf::FileOptions_OptimizeMode_IsValid(value));
+ set_has_optimize_for();
+ optimize_for_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.optimize_for)
+}
+
+// optional string go_package = 11;
+bool FileOptions::has_go_package() const {
+ return (_has_bits_[0] & 0x00000040u) != 0;
+}
+void FileOptions::set_has_go_package() {
+ _has_bits_[0] |= 0x00000040u;
+}
+void FileOptions::clear_has_go_package() {
+ _has_bits_[0] &= ~0x00000040u;
+}
+void FileOptions::clear_go_package() {
+ go_package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_go_package();
+}
+ const ::std::string& FileOptions::go_package() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.go_package)
+ return go_package_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_go_package(const ::std::string& value) {
+ set_has_go_package();
+ go_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.go_package)
+}
+ void FileOptions::set_go_package(const char* value) {
+ set_has_go_package();
+ go_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.go_package)
+}
+ void FileOptions::set_go_package(const char* value, size_t size) {
+ set_has_go_package();
+ go_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.go_package)
+}
+ ::std::string* FileOptions::mutable_go_package() {
+ set_has_go_package();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.go_package)
+ return go_package_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileOptions::release_go_package() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.go_package)
+ clear_has_go_package();
+ return go_package_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_allocated_go_package(::std::string* go_package) {
+ if (go_package != NULL) {
+ set_has_go_package();
+ } else {
+ clear_has_go_package();
+ }
+ go_package_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), go_package);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.go_package)
+}
+
+// optional bool cc_generic_services = 16 [default = false];
+bool FileOptions::has_cc_generic_services() const {
+ return (_has_bits_[0] & 0x00000080u) != 0;
+}
+void FileOptions::set_has_cc_generic_services() {
+ _has_bits_[0] |= 0x00000080u;
+}
+void FileOptions::clear_has_cc_generic_services() {
+ _has_bits_[0] &= ~0x00000080u;
+}
+void FileOptions::clear_cc_generic_services() {
+ cc_generic_services_ = false;
+ clear_has_cc_generic_services();
+}
+ bool FileOptions::cc_generic_services() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.cc_generic_services)
+ return cc_generic_services_;
+}
+ void FileOptions::set_cc_generic_services(bool value) {
+ set_has_cc_generic_services();
+ cc_generic_services_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.cc_generic_services)
+}
+
+// optional bool java_generic_services = 17 [default = false];
+bool FileOptions::has_java_generic_services() const {
+ return (_has_bits_[0] & 0x00000100u) != 0;
+}
+void FileOptions::set_has_java_generic_services() {
+ _has_bits_[0] |= 0x00000100u;
+}
+void FileOptions::clear_has_java_generic_services() {
+ _has_bits_[0] &= ~0x00000100u;
+}
+void FileOptions::clear_java_generic_services() {
+ java_generic_services_ = false;
+ clear_has_java_generic_services();
+}
+ bool FileOptions::java_generic_services() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_generic_services)
+ return java_generic_services_;
+}
+ void FileOptions::set_java_generic_services(bool value) {
+ set_has_java_generic_services();
+ java_generic_services_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_generic_services)
+}
+
+// optional bool py_generic_services = 18 [default = false];
+bool FileOptions::has_py_generic_services() const {
+ return (_has_bits_[0] & 0x00000200u) != 0;
+}
+void FileOptions::set_has_py_generic_services() {
+ _has_bits_[0] |= 0x00000200u;
+}
+void FileOptions::clear_has_py_generic_services() {
+ _has_bits_[0] &= ~0x00000200u;
+}
+void FileOptions::clear_py_generic_services() {
+ py_generic_services_ = false;
+ clear_has_py_generic_services();
+}
+ bool FileOptions::py_generic_services() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.py_generic_services)
+ return py_generic_services_;
+}
+ void FileOptions::set_py_generic_services(bool value) {
+ set_has_py_generic_services();
+ py_generic_services_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.py_generic_services)
+}
+
+// optional bool deprecated = 23 [default = false];
+bool FileOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000400u) != 0;
+}
+void FileOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000400u;
+}
+void FileOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000400u;
+}
+void FileOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+ bool FileOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.deprecated)
+ return deprecated_;
+}
+ void FileOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.deprecated)
+}
+
+// optional bool cc_enable_arenas = 31 [default = false];
+bool FileOptions::has_cc_enable_arenas() const {
+ return (_has_bits_[0] & 0x00000800u) != 0;
+}
+void FileOptions::set_has_cc_enable_arenas() {
+ _has_bits_[0] |= 0x00000800u;
+}
+void FileOptions::clear_has_cc_enable_arenas() {
+ _has_bits_[0] &= ~0x00000800u;
+}
+void FileOptions::clear_cc_enable_arenas() {
+ cc_enable_arenas_ = false;
+ clear_has_cc_enable_arenas();
+}
+ bool FileOptions::cc_enable_arenas() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.cc_enable_arenas)
+ return cc_enable_arenas_;
+}
+ void FileOptions::set_cc_enable_arenas(bool value) {
+ set_has_cc_enable_arenas();
+ cc_enable_arenas_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.cc_enable_arenas)
+}
+
+// optional string objc_class_prefix = 36;
+bool FileOptions::has_objc_class_prefix() const {
+ return (_has_bits_[0] & 0x00001000u) != 0;
+}
+void FileOptions::set_has_objc_class_prefix() {
+ _has_bits_[0] |= 0x00001000u;
+}
+void FileOptions::clear_has_objc_class_prefix() {
+ _has_bits_[0] &= ~0x00001000u;
+}
+void FileOptions::clear_objc_class_prefix() {
+ objc_class_prefix_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_objc_class_prefix();
+}
+ const ::std::string& FileOptions::objc_class_prefix() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.objc_class_prefix)
+ return objc_class_prefix_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_objc_class_prefix(const ::std::string& value) {
+ set_has_objc_class_prefix();
+ objc_class_prefix_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.objc_class_prefix)
+}
+ void FileOptions::set_objc_class_prefix(const char* value) {
+ set_has_objc_class_prefix();
+ objc_class_prefix_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.objc_class_prefix)
+}
+ void FileOptions::set_objc_class_prefix(const char* value, size_t size) {
+ set_has_objc_class_prefix();
+ objc_class_prefix_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.objc_class_prefix)
+}
+ ::std::string* FileOptions::mutable_objc_class_prefix() {
+ set_has_objc_class_prefix();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.objc_class_prefix)
+ return objc_class_prefix_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileOptions::release_objc_class_prefix() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.objc_class_prefix)
+ clear_has_objc_class_prefix();
+ return objc_class_prefix_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_allocated_objc_class_prefix(::std::string* objc_class_prefix) {
+ if (objc_class_prefix != NULL) {
+ set_has_objc_class_prefix();
+ } else {
+ clear_has_objc_class_prefix();
+ }
+ objc_class_prefix_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), objc_class_prefix);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.objc_class_prefix)
+}
+
+// optional string csharp_namespace = 37;
+bool FileOptions::has_csharp_namespace() const {
+ return (_has_bits_[0] & 0x00002000u) != 0;
+}
+void FileOptions::set_has_csharp_namespace() {
+ _has_bits_[0] |= 0x00002000u;
+}
+void FileOptions::clear_has_csharp_namespace() {
+ _has_bits_[0] &= ~0x00002000u;
+}
+void FileOptions::clear_csharp_namespace() {
+ csharp_namespace_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_csharp_namespace();
+}
+ const ::std::string& FileOptions::csharp_namespace() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.csharp_namespace)
+ return csharp_namespace_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_csharp_namespace(const ::std::string& value) {
+ set_has_csharp_namespace();
+ csharp_namespace_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.csharp_namespace)
+}
+ void FileOptions::set_csharp_namespace(const char* value) {
+ set_has_csharp_namespace();
+ csharp_namespace_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.csharp_namespace)
+}
+ void FileOptions::set_csharp_namespace(const char* value, size_t size) {
+ set_has_csharp_namespace();
+ csharp_namespace_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.csharp_namespace)
+}
+ ::std::string* FileOptions::mutable_csharp_namespace() {
+ set_has_csharp_namespace();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.csharp_namespace)
+ return csharp_namespace_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* FileOptions::release_csharp_namespace() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.csharp_namespace)
+ clear_has_csharp_namespace();
+ return csharp_namespace_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void FileOptions::set_allocated_csharp_namespace(::std::string* csharp_namespace) {
+ if (csharp_namespace != NULL) {
+ set_has_csharp_namespace();
+ } else {
+ clear_has_csharp_namespace();
+ }
+ csharp_namespace_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), csharp_namespace);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.csharp_namespace)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int FileOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void FileOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& FileOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* FileOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* FileOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+FileOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+FileOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int MessageOptions::kMessageSetWireFormatFieldNumber;
+const int MessageOptions::kNoStandardDescriptorAccessorFieldNumber;
+const int MessageOptions::kDeprecatedFieldNumber;
+const int MessageOptions::kMapEntryFieldNumber;
+const int MessageOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+MessageOptions::MessageOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.MessageOptions)
+}
+
+void MessageOptions::InitAsDefaultInstance() {
+}
+
+MessageOptions::MessageOptions(const MessageOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.MessageOptions)
+}
+
+void MessageOptions::SharedCtor() {
+ _cached_size_ = 0;
+ message_set_wire_format_ = false;
+ no_standard_descriptor_accessor_ = false;
+ deprecated_ = false;
+ map_entry_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+MessageOptions::~MessageOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.MessageOptions)
+ SharedDtor();
+}
+
+void MessageOptions::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void MessageOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* MessageOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return MessageOptions_descriptor_;
+}
+
+const MessageOptions& MessageOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+MessageOptions* MessageOptions::default_instance_ = NULL;
+
+MessageOptions* MessageOptions::New(::google::protobuf::Arena* arena) const {
+ MessageOptions* n = new MessageOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void MessageOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.MessageOptions)
+ _extensions_.Clear();
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(MessageOptions, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<MessageOptions*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(message_set_wire_format_, map_entry_);
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool MessageOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.MessageOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional bool message_set_wire_format = 1 [default = false];
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &message_set_wire_format_)));
+ set_has_message_set_wire_format();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_no_standard_descriptor_accessor;
+ break;
+ }
+
+ // optional bool no_standard_descriptor_accessor = 2 [default = false];
+ case 2: {
+ if (tag == 16) {
+ parse_no_standard_descriptor_accessor:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &no_standard_descriptor_accessor_)));
+ set_has_no_standard_descriptor_accessor();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(24)) goto parse_deprecated;
+ break;
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ case 3: {
+ if (tag == 24) {
+ parse_deprecated:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &deprecated_)));
+ set_has_deprecated();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(56)) goto parse_map_entry;
+ break;
+ }
+
+ // optional bool map_entry = 7;
+ case 7: {
+ if (tag == 56) {
+ parse_map_entry:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &map_entry_)));
+ set_has_map_entry();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_uninterpreted_option;
+ break;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ parse_uninterpreted_option:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.MessageOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.MessageOptions)
+ return false;
+#undef DO_
+}
+
+void MessageOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.MessageOptions)
+ // optional bool message_set_wire_format = 1 [default = false];
+ if (has_message_set_wire_format()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(1, this->message_set_wire_format(), output);
+ }
+
+ // optional bool no_standard_descriptor_accessor = 2 [default = false];
+ if (has_no_standard_descriptor_accessor()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(2, this->no_standard_descriptor_accessor(), output);
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(3, this->deprecated(), output);
+ }
+
+ // optional bool map_entry = 7;
+ if (has_map_entry()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(7, this->map_entry(), output);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.MessageOptions)
+}
+
+::google::protobuf::uint8* MessageOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.MessageOptions)
+ // optional bool message_set_wire_format = 1 [default = false];
+ if (has_message_set_wire_format()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(1, this->message_set_wire_format(), target);
+ }
+
+ // optional bool no_standard_descriptor_accessor = 2 [default = false];
+ if (has_no_standard_descriptor_accessor()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(2, this->no_standard_descriptor_accessor(), target);
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(3, this->deprecated(), target);
+ }
+
+ // optional bool map_entry = 7;
+ if (has_map_entry()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(7, this->map_entry(), target);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.MessageOptions)
+ return target;
+}
+
+int MessageOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.MessageOptions)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 15u) {
+ // optional bool message_set_wire_format = 1 [default = false];
+ if (has_message_set_wire_format()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool no_standard_descriptor_accessor = 2 [default = false];
+ if (has_no_standard_descriptor_accessor()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool map_entry = 7;
+ if (has_map_entry()) {
+ total_size += 1 + 1;
+ }
+
+ }
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void MessageOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.MessageOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const MessageOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const MessageOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.MessageOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.MessageOptions)
+ MergeFrom(*source);
+ }
+}
+
+void MessageOptions::MergeFrom(const MessageOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.MessageOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_message_set_wire_format()) {
+ set_message_set_wire_format(from.message_set_wire_format());
+ }
+ if (from.has_no_standard_descriptor_accessor()) {
+ set_no_standard_descriptor_accessor(from.no_standard_descriptor_accessor());
+ }
+ if (from.has_deprecated()) {
+ set_deprecated(from.deprecated());
+ }
+ if (from.has_map_entry()) {
+ set_map_entry(from.map_entry());
+ }
+ }
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void MessageOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.MessageOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void MessageOptions::CopyFrom(const MessageOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.MessageOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool MessageOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void MessageOptions::Swap(MessageOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void MessageOptions::InternalSwap(MessageOptions* other) {
+ std::swap(message_set_wire_format_, other->message_set_wire_format_);
+ std::swap(no_standard_descriptor_accessor_, other->no_standard_descriptor_accessor_);
+ std::swap(deprecated_, other->deprecated_);
+ std::swap(map_entry_, other->map_entry_);
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata MessageOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = MessageOptions_descriptor_;
+ metadata.reflection = MessageOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// MessageOptions
+
+// optional bool message_set_wire_format = 1 [default = false];
+bool MessageOptions::has_message_set_wire_format() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void MessageOptions::set_has_message_set_wire_format() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void MessageOptions::clear_has_message_set_wire_format() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void MessageOptions::clear_message_set_wire_format() {
+ message_set_wire_format_ = false;
+ clear_has_message_set_wire_format();
+}
+ bool MessageOptions::message_set_wire_format() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.message_set_wire_format)
+ return message_set_wire_format_;
+}
+ void MessageOptions::set_message_set_wire_format(bool value) {
+ set_has_message_set_wire_format();
+ message_set_wire_format_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.message_set_wire_format)
+}
+
+// optional bool no_standard_descriptor_accessor = 2 [default = false];
+bool MessageOptions::has_no_standard_descriptor_accessor() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void MessageOptions::set_has_no_standard_descriptor_accessor() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void MessageOptions::clear_has_no_standard_descriptor_accessor() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void MessageOptions::clear_no_standard_descriptor_accessor() {
+ no_standard_descriptor_accessor_ = false;
+ clear_has_no_standard_descriptor_accessor();
+}
+ bool MessageOptions::no_standard_descriptor_accessor() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.no_standard_descriptor_accessor)
+ return no_standard_descriptor_accessor_;
+}
+ void MessageOptions::set_no_standard_descriptor_accessor(bool value) {
+ set_has_no_standard_descriptor_accessor();
+ no_standard_descriptor_accessor_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.no_standard_descriptor_accessor)
+}
+
+// optional bool deprecated = 3 [default = false];
+bool MessageOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void MessageOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void MessageOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void MessageOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+ bool MessageOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.deprecated)
+ return deprecated_;
+}
+ void MessageOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.deprecated)
+}
+
+// optional bool map_entry = 7;
+bool MessageOptions::has_map_entry() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void MessageOptions::set_has_map_entry() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void MessageOptions::clear_has_map_entry() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void MessageOptions::clear_map_entry() {
+ map_entry_ = false;
+ clear_has_map_entry();
+}
+ bool MessageOptions::map_entry() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.map_entry)
+ return map_entry_;
+}
+ void MessageOptions::set_map_entry(bool value) {
+ set_has_map_entry();
+ map_entry_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.map_entry)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int MessageOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void MessageOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& MessageOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* MessageOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* MessageOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+MessageOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.MessageOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+MessageOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+const ::google::protobuf::EnumDescriptor* FieldOptions_CType_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FieldOptions_CType_descriptor_;
+}
+bool FieldOptions_CType_IsValid(int value) {
+ switch(value) {
+ case 0:
+ case 1:
+ case 2:
+ return true;
+ default:
+ return false;
+ }
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const FieldOptions_CType FieldOptions::STRING;
+const FieldOptions_CType FieldOptions::CORD;
+const FieldOptions_CType FieldOptions::STRING_PIECE;
+const FieldOptions_CType FieldOptions::CType_MIN;
+const FieldOptions_CType FieldOptions::CType_MAX;
+const int FieldOptions::CType_ARRAYSIZE;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+const ::google::protobuf::EnumDescriptor* FieldOptions_JSType_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FieldOptions_JSType_descriptor_;
+}
+bool FieldOptions_JSType_IsValid(int value) {
+ switch(value) {
+ case 0:
+ case 1:
+ case 2:
+ return true;
+ default:
+ return false;
+ }
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const FieldOptions_JSType FieldOptions::JS_NORMAL;
+const FieldOptions_JSType FieldOptions::JS_STRING;
+const FieldOptions_JSType FieldOptions::JS_NUMBER;
+const FieldOptions_JSType FieldOptions::JSType_MIN;
+const FieldOptions_JSType FieldOptions::JSType_MAX;
+const int FieldOptions::JSType_ARRAYSIZE;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FieldOptions::kCtypeFieldNumber;
+const int FieldOptions::kPackedFieldNumber;
+const int FieldOptions::kJstypeFieldNumber;
+const int FieldOptions::kLazyFieldNumber;
+const int FieldOptions::kDeprecatedFieldNumber;
+const int FieldOptions::kWeakFieldNumber;
+const int FieldOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+FieldOptions::FieldOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.FieldOptions)
+}
+
+void FieldOptions::InitAsDefaultInstance() {
+}
+
+FieldOptions::FieldOptions(const FieldOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.FieldOptions)
+}
+
+void FieldOptions::SharedCtor() {
+ _cached_size_ = 0;
+ ctype_ = 0;
+ packed_ = false;
+ jstype_ = 0;
+ lazy_ = false;
+ deprecated_ = false;
+ weak_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+FieldOptions::~FieldOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.FieldOptions)
+ SharedDtor();
+}
+
+void FieldOptions::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void FieldOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* FieldOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FieldOptions_descriptor_;
+}
+
+const FieldOptions& FieldOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+FieldOptions* FieldOptions::default_instance_ = NULL;
+
+FieldOptions* FieldOptions::New(::google::protobuf::Arena* arena) const {
+ FieldOptions* n = new FieldOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void FieldOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.FieldOptions)
+ _extensions_.Clear();
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(FieldOptions, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<FieldOptions*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ if (_has_bits_[0 / 32] & 63u) {
+ ZR_(ctype_, jstype_);
+ ZR_(packed_, weak_);
+ }
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool FieldOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.FieldOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional .google.protobuf.FieldOptions.CType ctype = 1 [default = STRING];
+ case 1: {
+ if (tag == 8) {
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ if (::google::protobuf::FieldOptions_CType_IsValid(value)) {
+ set_ctype(static_cast< ::google::protobuf::FieldOptions_CType >(value));
+ } else {
+ mutable_unknown_fields()->AddVarint(1, value);
+ }
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_packed;
+ break;
+ }
+
+ // optional bool packed = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_packed:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &packed_)));
+ set_has_packed();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(24)) goto parse_deprecated;
+ break;
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ case 3: {
+ if (tag == 24) {
+ parse_deprecated:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &deprecated_)));
+ set_has_deprecated();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(40)) goto parse_lazy;
+ break;
+ }
+
+ // optional bool lazy = 5 [default = false];
+ case 5: {
+ if (tag == 40) {
+ parse_lazy:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &lazy_)));
+ set_has_lazy();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(48)) goto parse_jstype;
+ break;
+ }
+
+ // optional .google.protobuf.FieldOptions.JSType jstype = 6 [default = JS_NORMAL];
+ case 6: {
+ if (tag == 48) {
+ parse_jstype:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ if (::google::protobuf::FieldOptions_JSType_IsValid(value)) {
+ set_jstype(static_cast< ::google::protobuf::FieldOptions_JSType >(value));
+ } else {
+ mutable_unknown_fields()->AddVarint(6, value);
+ }
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(80)) goto parse_weak;
+ break;
+ }
+
+ // optional bool weak = 10 [default = false];
+ case 10: {
+ if (tag == 80) {
+ parse_weak:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &weak_)));
+ set_has_weak();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_uninterpreted_option;
+ break;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ parse_uninterpreted_option:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.FieldOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.FieldOptions)
+ return false;
+#undef DO_
+}
+
+void FieldOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.FieldOptions)
+ // optional .google.protobuf.FieldOptions.CType ctype = 1 [default = STRING];
+ if (has_ctype()) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 1, this->ctype(), output);
+ }
+
+ // optional bool packed = 2;
+ if (has_packed()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(2, this->packed(), output);
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(3, this->deprecated(), output);
+ }
+
+ // optional bool lazy = 5 [default = false];
+ if (has_lazy()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(5, this->lazy(), output);
+ }
+
+ // optional .google.protobuf.FieldOptions.JSType jstype = 6 [default = JS_NORMAL];
+ if (has_jstype()) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 6, this->jstype(), output);
+ }
+
+ // optional bool weak = 10 [default = false];
+ if (has_weak()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(10, this->weak(), output);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.FieldOptions)
+}
+
+::google::protobuf::uint8* FieldOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.FieldOptions)
+ // optional .google.protobuf.FieldOptions.CType ctype = 1 [default = STRING];
+ if (has_ctype()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 1, this->ctype(), target);
+ }
+
+ // optional bool packed = 2;
+ if (has_packed()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(2, this->packed(), target);
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(3, this->deprecated(), target);
+ }
+
+ // optional bool lazy = 5 [default = false];
+ if (has_lazy()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(5, this->lazy(), target);
+ }
+
+ // optional .google.protobuf.FieldOptions.JSType jstype = 6 [default = JS_NORMAL];
+ if (has_jstype()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 6, this->jstype(), target);
+ }
+
+ // optional bool weak = 10 [default = false];
+ if (has_weak()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(10, this->weak(), target);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.FieldOptions)
+ return target;
+}
+
+int FieldOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.FieldOptions)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 63u) {
+ // optional .google.protobuf.FieldOptions.CType ctype = 1 [default = STRING];
+ if (has_ctype()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->ctype());
+ }
+
+ // optional bool packed = 2;
+ if (has_packed()) {
+ total_size += 1 + 1;
+ }
+
+ // optional .google.protobuf.FieldOptions.JSType jstype = 6 [default = JS_NORMAL];
+ if (has_jstype()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->jstype());
+ }
+
+ // optional bool lazy = 5 [default = false];
+ if (has_lazy()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool weak = 10 [default = false];
+ if (has_weak()) {
+ total_size += 1 + 1;
+ }
+
+ }
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void FieldOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.FieldOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const FieldOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const FieldOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.FieldOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.FieldOptions)
+ MergeFrom(*source);
+ }
+}
+
+void FieldOptions::MergeFrom(const FieldOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.FieldOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_ctype()) {
+ set_ctype(from.ctype());
+ }
+ if (from.has_packed()) {
+ set_packed(from.packed());
+ }
+ if (from.has_jstype()) {
+ set_jstype(from.jstype());
+ }
+ if (from.has_lazy()) {
+ set_lazy(from.lazy());
+ }
+ if (from.has_deprecated()) {
+ set_deprecated(from.deprecated());
+ }
+ if (from.has_weak()) {
+ set_weak(from.weak());
+ }
+ }
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void FieldOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.FieldOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void FieldOptions::CopyFrom(const FieldOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.FieldOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool FieldOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void FieldOptions::Swap(FieldOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void FieldOptions::InternalSwap(FieldOptions* other) {
+ std::swap(ctype_, other->ctype_);
+ std::swap(packed_, other->packed_);
+ std::swap(jstype_, other->jstype_);
+ std::swap(lazy_, other->lazy_);
+ std::swap(deprecated_, other->deprecated_);
+ std::swap(weak_, other->weak_);
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata FieldOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = FieldOptions_descriptor_;
+ metadata.reflection = FieldOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// FieldOptions
+
+// optional .google.protobuf.FieldOptions.CType ctype = 1 [default = STRING];
+bool FieldOptions::has_ctype() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void FieldOptions::set_has_ctype() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void FieldOptions::clear_has_ctype() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void FieldOptions::clear_ctype() {
+ ctype_ = 0;
+ clear_has_ctype();
+}
+ ::google::protobuf::FieldOptions_CType FieldOptions::ctype() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.ctype)
+ return static_cast< ::google::protobuf::FieldOptions_CType >(ctype_);
+}
+ void FieldOptions::set_ctype(::google::protobuf::FieldOptions_CType value) {
+ assert(::google::protobuf::FieldOptions_CType_IsValid(value));
+ set_has_ctype();
+ ctype_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.ctype)
+}
+
+// optional bool packed = 2;
+bool FieldOptions::has_packed() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void FieldOptions::set_has_packed() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void FieldOptions::clear_has_packed() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void FieldOptions::clear_packed() {
+ packed_ = false;
+ clear_has_packed();
+}
+ bool FieldOptions::packed() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.packed)
+ return packed_;
+}
+ void FieldOptions::set_packed(bool value) {
+ set_has_packed();
+ packed_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.packed)
+}
+
+// optional .google.protobuf.FieldOptions.JSType jstype = 6 [default = JS_NORMAL];
+bool FieldOptions::has_jstype() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void FieldOptions::set_has_jstype() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void FieldOptions::clear_has_jstype() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void FieldOptions::clear_jstype() {
+ jstype_ = 0;
+ clear_has_jstype();
+}
+ ::google::protobuf::FieldOptions_JSType FieldOptions::jstype() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.jstype)
+ return static_cast< ::google::protobuf::FieldOptions_JSType >(jstype_);
+}
+ void FieldOptions::set_jstype(::google::protobuf::FieldOptions_JSType value) {
+ assert(::google::protobuf::FieldOptions_JSType_IsValid(value));
+ set_has_jstype();
+ jstype_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.jstype)
+}
+
+// optional bool lazy = 5 [default = false];
+bool FieldOptions::has_lazy() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void FieldOptions::set_has_lazy() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void FieldOptions::clear_has_lazy() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void FieldOptions::clear_lazy() {
+ lazy_ = false;
+ clear_has_lazy();
+}
+ bool FieldOptions::lazy() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.lazy)
+ return lazy_;
+}
+ void FieldOptions::set_lazy(bool value) {
+ set_has_lazy();
+ lazy_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.lazy)
+}
+
+// optional bool deprecated = 3 [default = false];
+bool FieldOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+void FieldOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000010u;
+}
+void FieldOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+void FieldOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+ bool FieldOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.deprecated)
+ return deprecated_;
+}
+ void FieldOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.deprecated)
+}
+
+// optional bool weak = 10 [default = false];
+bool FieldOptions::has_weak() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+void FieldOptions::set_has_weak() {
+ _has_bits_[0] |= 0x00000020u;
+}
+void FieldOptions::clear_has_weak() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+void FieldOptions::clear_weak() {
+ weak_ = false;
+ clear_has_weak();
+}
+ bool FieldOptions::weak() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.weak)
+ return weak_;
+}
+ void FieldOptions::set_weak(bool value) {
+ set_has_weak();
+ weak_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.weak)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int FieldOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void FieldOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& FieldOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* FieldOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* FieldOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+FieldOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FieldOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+FieldOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int OneofOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+OneofOptions::OneofOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.OneofOptions)
+}
+
+void OneofOptions::InitAsDefaultInstance() {
+}
+
+OneofOptions::OneofOptions(const OneofOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.OneofOptions)
+}
+
+void OneofOptions::SharedCtor() {
+ _cached_size_ = 0;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+OneofOptions::~OneofOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.OneofOptions)
+ SharedDtor();
+}
+
+void OneofOptions::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void OneofOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* OneofOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return OneofOptions_descriptor_;
+}
+
+const OneofOptions& OneofOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+OneofOptions* OneofOptions::default_instance_ = NULL;
+
+OneofOptions* OneofOptions::New(::google::protobuf::Arena* arena) const {
+ OneofOptions* n = new OneofOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void OneofOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.OneofOptions)
+ _extensions_.Clear();
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool OneofOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.OneofOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.OneofOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.OneofOptions)
+ return false;
+#undef DO_
+}
+
+void OneofOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.OneofOptions)
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.OneofOptions)
+}
+
+::google::protobuf::uint8* OneofOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.OneofOptions)
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.OneofOptions)
+ return target;
+}
+
+int OneofOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.OneofOptions)
+ int total_size = 0;
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void OneofOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.OneofOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const OneofOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const OneofOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.OneofOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.OneofOptions)
+ MergeFrom(*source);
+ }
+}
+
+void OneofOptions::MergeFrom(const OneofOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.OneofOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void OneofOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.OneofOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void OneofOptions::CopyFrom(const OneofOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.OneofOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool OneofOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void OneofOptions::Swap(OneofOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void OneofOptions::InternalSwap(OneofOptions* other) {
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata OneofOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = OneofOptions_descriptor_;
+ metadata.reflection = OneofOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// OneofOptions
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int OneofOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void OneofOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& OneofOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* OneofOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* OneofOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+OneofOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.OneofOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+OneofOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int EnumOptions::kAllowAliasFieldNumber;
+const int EnumOptions::kDeprecatedFieldNumber;
+const int EnumOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+EnumOptions::EnumOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.EnumOptions)
+}
+
+void EnumOptions::InitAsDefaultInstance() {
+}
+
+EnumOptions::EnumOptions(const EnumOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.EnumOptions)
+}
+
+void EnumOptions::SharedCtor() {
+ _cached_size_ = 0;
+ allow_alias_ = false;
+ deprecated_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+EnumOptions::~EnumOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.EnumOptions)
+ SharedDtor();
+}
+
+void EnumOptions::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void EnumOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* EnumOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return EnumOptions_descriptor_;
+}
+
+const EnumOptions& EnumOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+EnumOptions* EnumOptions::default_instance_ = NULL;
+
+EnumOptions* EnumOptions::New(::google::protobuf::Arena* arena) const {
+ EnumOptions* n = new EnumOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void EnumOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.EnumOptions)
+ _extensions_.Clear();
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(EnumOptions, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<EnumOptions*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(allow_alias_, deprecated_);
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool EnumOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.EnumOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional bool allow_alias = 2;
+ case 2: {
+ if (tag == 16) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &allow_alias_)));
+ set_has_allow_alias();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(24)) goto parse_deprecated;
+ break;
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ case 3: {
+ if (tag == 24) {
+ parse_deprecated:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &deprecated_)));
+ set_has_deprecated();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_uninterpreted_option;
+ break;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ parse_uninterpreted_option:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.EnumOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.EnumOptions)
+ return false;
+#undef DO_
+}
+
+void EnumOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.EnumOptions)
+ // optional bool allow_alias = 2;
+ if (has_allow_alias()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(2, this->allow_alias(), output);
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(3, this->deprecated(), output);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.EnumOptions)
+}
+
+::google::protobuf::uint8* EnumOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.EnumOptions)
+ // optional bool allow_alias = 2;
+ if (has_allow_alias()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(2, this->allow_alias(), target);
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(3, this->deprecated(), target);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.EnumOptions)
+ return target;
+}
+
+int EnumOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.EnumOptions)
+ int total_size = 0;
+
+ if (_has_bits_[0 / 32] & 3u) {
+ // optional bool allow_alias = 2;
+ if (has_allow_alias()) {
+ total_size += 1 + 1;
+ }
+
+ // optional bool deprecated = 3 [default = false];
+ if (has_deprecated()) {
+ total_size += 1 + 1;
+ }
+
+ }
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void EnumOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.EnumOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const EnumOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const EnumOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.EnumOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.EnumOptions)
+ MergeFrom(*source);
+ }
+}
+
+void EnumOptions::MergeFrom(const EnumOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.EnumOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_allow_alias()) {
+ set_allow_alias(from.allow_alias());
+ }
+ if (from.has_deprecated()) {
+ set_deprecated(from.deprecated());
+ }
+ }
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void EnumOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.EnumOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void EnumOptions::CopyFrom(const EnumOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.EnumOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool EnumOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void EnumOptions::Swap(EnumOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void EnumOptions::InternalSwap(EnumOptions* other) {
+ std::swap(allow_alias_, other->allow_alias_);
+ std::swap(deprecated_, other->deprecated_);
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata EnumOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = EnumOptions_descriptor_;
+ metadata.reflection = EnumOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// EnumOptions
+
+// optional bool allow_alias = 2;
+bool EnumOptions::has_allow_alias() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void EnumOptions::set_has_allow_alias() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void EnumOptions::clear_has_allow_alias() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void EnumOptions::clear_allow_alias() {
+ allow_alias_ = false;
+ clear_has_allow_alias();
+}
+ bool EnumOptions::allow_alias() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumOptions.allow_alias)
+ return allow_alias_;
+}
+ void EnumOptions::set_allow_alias(bool value) {
+ set_has_allow_alias();
+ allow_alias_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumOptions.allow_alias)
+}
+
+// optional bool deprecated = 3 [default = false];
+bool EnumOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void EnumOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void EnumOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void EnumOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+ bool EnumOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumOptions.deprecated)
+ return deprecated_;
+}
+ void EnumOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int EnumOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void EnumOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& EnumOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* EnumOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* EnumOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+EnumOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+EnumOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int EnumValueOptions::kDeprecatedFieldNumber;
+const int EnumValueOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+EnumValueOptions::EnumValueOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.EnumValueOptions)
+}
+
+void EnumValueOptions::InitAsDefaultInstance() {
+}
+
+EnumValueOptions::EnumValueOptions(const EnumValueOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.EnumValueOptions)
+}
+
+void EnumValueOptions::SharedCtor() {
+ _cached_size_ = 0;
+ deprecated_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+EnumValueOptions::~EnumValueOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.EnumValueOptions)
+ SharedDtor();
+}
+
+void EnumValueOptions::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void EnumValueOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* EnumValueOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return EnumValueOptions_descriptor_;
+}
+
+const EnumValueOptions& EnumValueOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+EnumValueOptions* EnumValueOptions::default_instance_ = NULL;
+
+EnumValueOptions* EnumValueOptions::New(::google::protobuf::Arena* arena) const {
+ EnumValueOptions* n = new EnumValueOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void EnumValueOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.EnumValueOptions)
+ _extensions_.Clear();
+ deprecated_ = false;
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool EnumValueOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.EnumValueOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional bool deprecated = 1 [default = false];
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &deprecated_)));
+ set_has_deprecated();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_uninterpreted_option;
+ break;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ parse_uninterpreted_option:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.EnumValueOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.EnumValueOptions)
+ return false;
+#undef DO_
+}
+
+void EnumValueOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.EnumValueOptions)
+ // optional bool deprecated = 1 [default = false];
+ if (has_deprecated()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(1, this->deprecated(), output);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.EnumValueOptions)
+}
+
+::google::protobuf::uint8* EnumValueOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.EnumValueOptions)
+ // optional bool deprecated = 1 [default = false];
+ if (has_deprecated()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(1, this->deprecated(), target);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.EnumValueOptions)
+ return target;
+}
+
+int EnumValueOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.EnumValueOptions)
+ int total_size = 0;
+
+ // optional bool deprecated = 1 [default = false];
+ if (has_deprecated()) {
+ total_size += 1 + 1;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void EnumValueOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.EnumValueOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const EnumValueOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const EnumValueOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.EnumValueOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.EnumValueOptions)
+ MergeFrom(*source);
+ }
+}
+
+void EnumValueOptions::MergeFrom(const EnumValueOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.EnumValueOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_deprecated()) {
+ set_deprecated(from.deprecated());
+ }
+ }
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void EnumValueOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.EnumValueOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void EnumValueOptions::CopyFrom(const EnumValueOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.EnumValueOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool EnumValueOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void EnumValueOptions::Swap(EnumValueOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void EnumValueOptions::InternalSwap(EnumValueOptions* other) {
+ std::swap(deprecated_, other->deprecated_);
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata EnumValueOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = EnumValueOptions_descriptor_;
+ metadata.reflection = EnumValueOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// EnumValueOptions
+
+// optional bool deprecated = 1 [default = false];
+bool EnumValueOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void EnumValueOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void EnumValueOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void EnumValueOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+ bool EnumValueOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueOptions.deprecated)
+ return deprecated_;
+}
+ void EnumValueOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValueOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int EnumValueOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void EnumValueOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& EnumValueOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* EnumValueOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* EnumValueOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+EnumValueOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+EnumValueOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int ServiceOptions::kDeprecatedFieldNumber;
+const int ServiceOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+ServiceOptions::ServiceOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.ServiceOptions)
+}
+
+void ServiceOptions::InitAsDefaultInstance() {
+}
+
+ServiceOptions::ServiceOptions(const ServiceOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.ServiceOptions)
+}
+
+void ServiceOptions::SharedCtor() {
+ _cached_size_ = 0;
+ deprecated_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+ServiceOptions::~ServiceOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.ServiceOptions)
+ SharedDtor();
+}
+
+void ServiceOptions::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void ServiceOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* ServiceOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return ServiceOptions_descriptor_;
+}
+
+const ServiceOptions& ServiceOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+ServiceOptions* ServiceOptions::default_instance_ = NULL;
+
+ServiceOptions* ServiceOptions::New(::google::protobuf::Arena* arena) const {
+ ServiceOptions* n = new ServiceOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void ServiceOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.ServiceOptions)
+ _extensions_.Clear();
+ deprecated_ = false;
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool ServiceOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.ServiceOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional bool deprecated = 33 [default = false];
+ case 33: {
+ if (tag == 264) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &deprecated_)));
+ set_has_deprecated();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_uninterpreted_option;
+ break;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ parse_uninterpreted_option:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.ServiceOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.ServiceOptions)
+ return false;
+#undef DO_
+}
+
+void ServiceOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.ServiceOptions)
+ // optional bool deprecated = 33 [default = false];
+ if (has_deprecated()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(33, this->deprecated(), output);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.ServiceOptions)
+}
+
+::google::protobuf::uint8* ServiceOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.ServiceOptions)
+ // optional bool deprecated = 33 [default = false];
+ if (has_deprecated()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(33, this->deprecated(), target);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.ServiceOptions)
+ return target;
+}
+
+int ServiceOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.ServiceOptions)
+ int total_size = 0;
+
+ // optional bool deprecated = 33 [default = false];
+ if (has_deprecated()) {
+ total_size += 2 + 1;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void ServiceOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.ServiceOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const ServiceOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const ServiceOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.ServiceOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.ServiceOptions)
+ MergeFrom(*source);
+ }
+}
+
+void ServiceOptions::MergeFrom(const ServiceOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.ServiceOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_deprecated()) {
+ set_deprecated(from.deprecated());
+ }
+ }
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void ServiceOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.ServiceOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void ServiceOptions::CopyFrom(const ServiceOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.ServiceOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool ServiceOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void ServiceOptions::Swap(ServiceOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void ServiceOptions::InternalSwap(ServiceOptions* other) {
+ std::swap(deprecated_, other->deprecated_);
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata ServiceOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = ServiceOptions_descriptor_;
+ metadata.reflection = ServiceOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// ServiceOptions
+
+// optional bool deprecated = 33 [default = false];
+bool ServiceOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void ServiceOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void ServiceOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void ServiceOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+ bool ServiceOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceOptions.deprecated)
+ return deprecated_;
+}
+ void ServiceOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.ServiceOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int ServiceOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void ServiceOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& ServiceOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* ServiceOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* ServiceOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ServiceOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.ServiceOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ServiceOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int MethodOptions::kDeprecatedFieldNumber;
+const int MethodOptions::kUninterpretedOptionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+MethodOptions::MethodOptions()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.MethodOptions)
+}
+
+void MethodOptions::InitAsDefaultInstance() {
+}
+
+MethodOptions::MethodOptions(const MethodOptions& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.MethodOptions)
+}
+
+void MethodOptions::SharedCtor() {
+ _cached_size_ = 0;
+ deprecated_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+MethodOptions::~MethodOptions() {
+ // @@protoc_insertion_point(destructor:google.protobuf.MethodOptions)
+ SharedDtor();
+}
+
+void MethodOptions::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void MethodOptions::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* MethodOptions::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return MethodOptions_descriptor_;
+}
+
+const MethodOptions& MethodOptions::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+MethodOptions* MethodOptions::default_instance_ = NULL;
+
+MethodOptions* MethodOptions::New(::google::protobuf::Arena* arena) const {
+ MethodOptions* n = new MethodOptions;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void MethodOptions::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.MethodOptions)
+ _extensions_.Clear();
+ deprecated_ = false;
+ uninterpreted_option_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool MethodOptions::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.MethodOptions)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(16383);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional bool deprecated = 33 [default = false];
+ case 33: {
+ if (tag == 264) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &deprecated_)));
+ set_has_deprecated();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_uninterpreted_option;
+ break;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ case 999: {
+ if (tag == 7994) {
+ parse_uninterpreted_option:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_uninterpreted_option:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_uninterpreted_option()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(7994)) goto parse_loop_uninterpreted_option;
+ 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) {
+ goto success;
+ }
+ if ((8000u <= tag)) {
+ DO_(_extensions_.ParseField(tag, input, default_instance_,
+ mutable_unknown_fields()));
+ continue;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.MethodOptions)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.MethodOptions)
+ return false;
+#undef DO_
+}
+
+void MethodOptions::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.MethodOptions)
+ // optional bool deprecated = 33 [default = false];
+ if (has_deprecated()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(33, this->deprecated(), output);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 999, this->uninterpreted_option(i), output);
+ }
+
+ // Extension range [1000, 536870912)
+ _extensions_.SerializeWithCachedSizes(
+ 1000, 536870912, output);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.MethodOptions)
+}
+
+::google::protobuf::uint8* MethodOptions::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.MethodOptions)
+ // optional bool deprecated = 33 [default = false];
+ if (has_deprecated()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(33, this->deprecated(), target);
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ for (unsigned int i = 0, n = this->uninterpreted_option_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 999, this->uninterpreted_option(i), false, target);
+ }
+
+ // Extension range [1000, 536870912)
+ target = _extensions_.InternalSerializeWithCachedSizesToArray(
+ 1000, 536870912, false, target);
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.MethodOptions)
+ return target;
+}
+
+int MethodOptions::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.MethodOptions)
+ int total_size = 0;
+
+ // optional bool deprecated = 33 [default = false];
+ if (has_deprecated()) {
+ total_size += 2 + 1;
+ }
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ total_size += 2 * this->uninterpreted_option_size();
+ for (int i = 0; i < this->uninterpreted_option_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->uninterpreted_option(i));
+ }
+
+ total_size += _extensions_.ByteSize();
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void MethodOptions::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.MethodOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const MethodOptions* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const MethodOptions>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.MethodOptions)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.MethodOptions)
+ MergeFrom(*source);
+ }
+}
+
+void MethodOptions::MergeFrom(const MethodOptions& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.MethodOptions)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ uninterpreted_option_.MergeFrom(from.uninterpreted_option_);
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_deprecated()) {
+ set_deprecated(from.deprecated());
+ }
+ }
+ _extensions_.MergeFrom(from._extensions_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void MethodOptions::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.MethodOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void MethodOptions::CopyFrom(const MethodOptions& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.MethodOptions)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool MethodOptions::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->uninterpreted_option())) return false;
+
+ if (!_extensions_.IsInitialized()) return false; return true;
+}
+
+void MethodOptions::Swap(MethodOptions* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void MethodOptions::InternalSwap(MethodOptions* other) {
+ std::swap(deprecated_, other->deprecated_);
+ uninterpreted_option_.UnsafeArenaSwap(&other->uninterpreted_option_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+ _extensions_.Swap(&other->_extensions_);
+}
+
+::google::protobuf::Metadata MethodOptions::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = MethodOptions_descriptor_;
+ metadata.reflection = MethodOptions_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// MethodOptions
+
+// optional bool deprecated = 33 [default = false];
+bool MethodOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void MethodOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void MethodOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void MethodOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+ bool MethodOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodOptions.deprecated)
+ return deprecated_;
+}
+ void MethodOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+int MethodOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+void MethodOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+const ::google::protobuf::UninterpretedOption& MethodOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+::google::protobuf::UninterpretedOption* MethodOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption* MethodOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+MethodOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.MethodOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+MethodOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int UninterpretedOption_NamePart::kNamePartFieldNumber;
+const int UninterpretedOption_NamePart::kIsExtensionFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+UninterpretedOption_NamePart::UninterpretedOption_NamePart()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.UninterpretedOption.NamePart)
+}
+
+void UninterpretedOption_NamePart::InitAsDefaultInstance() {
+}
+
+UninterpretedOption_NamePart::UninterpretedOption_NamePart(const UninterpretedOption_NamePart& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.UninterpretedOption.NamePart)
+}
+
+void UninterpretedOption_NamePart::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_part_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ is_extension_ = false;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+UninterpretedOption_NamePart::~UninterpretedOption_NamePart() {
+ // @@protoc_insertion_point(destructor:google.protobuf.UninterpretedOption.NamePart)
+ SharedDtor();
+}
+
+void UninterpretedOption_NamePart::SharedDtor() {
+ name_part_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void UninterpretedOption_NamePart::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* UninterpretedOption_NamePart::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return UninterpretedOption_NamePart_descriptor_;
+}
+
+const UninterpretedOption_NamePart& UninterpretedOption_NamePart::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+UninterpretedOption_NamePart* UninterpretedOption_NamePart::default_instance_ = NULL;
+
+UninterpretedOption_NamePart* UninterpretedOption_NamePart::New(::google::protobuf::Arena* arena) const {
+ UninterpretedOption_NamePart* n = new UninterpretedOption_NamePart;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void UninterpretedOption_NamePart::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.UninterpretedOption.NamePart)
+ if (_has_bits_[0 / 32] & 3u) {
+ if (has_name_part()) {
+ name_part_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ is_extension_ = false;
+ }
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool UninterpretedOption_NamePart::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.UninterpretedOption.NamePart)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // required string name_part = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name_part()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name_part().data(), this->name_part().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.UninterpretedOption.NamePart.name_part");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_is_extension;
+ break;
+ }
+
+ // required bool is_extension = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_is_extension:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &is_extension_)));
+ set_has_is_extension();
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.UninterpretedOption.NamePart)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.UninterpretedOption.NamePart)
+ return false;
+#undef DO_
+}
+
+void UninterpretedOption_NamePart::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.UninterpretedOption.NamePart)
+ // required string name_part = 1;
+ if (has_name_part()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name_part().data(), this->name_part().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.UninterpretedOption.NamePart.name_part");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name_part(), output);
+ }
+
+ // required bool is_extension = 2;
+ if (has_is_extension()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(2, this->is_extension(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.UninterpretedOption.NamePart)
+}
+
+::google::protobuf::uint8* UninterpretedOption_NamePart::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.UninterpretedOption.NamePart)
+ // required string name_part = 1;
+ if (has_name_part()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->name_part().data(), this->name_part().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.UninterpretedOption.NamePart.name_part");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name_part(), target);
+ }
+
+ // required bool is_extension = 2;
+ if (has_is_extension()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(2, this->is_extension(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.UninterpretedOption.NamePart)
+ return target;
+}
+
+int UninterpretedOption_NamePart::RequiredFieldsByteSizeFallback() const {
+// @@protoc_insertion_point(required_fields_byte_size_fallback_start:google.protobuf.UninterpretedOption.NamePart)
+ int total_size = 0;
+
+ if (has_name_part()) {
+ // required string name_part = 1;
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name_part());
+ }
+
+ if (has_is_extension()) {
+ // required bool is_extension = 2;
+ total_size += 1 + 1;
+ }
+
+ return total_size;
+}
+int UninterpretedOption_NamePart::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.UninterpretedOption.NamePart)
+ int total_size = 0;
+
+ if (((_has_bits_[0] & 0x00000003) ^ 0x00000003) == 0) { // All required fields are present.
+ // required string name_part = 1;
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name_part());
+
+ // required bool is_extension = 2;
+ total_size += 1 + 1;
+
+ } else {
+ total_size += RequiredFieldsByteSizeFallback();
+ }
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void UninterpretedOption_NamePart::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.UninterpretedOption.NamePart)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const UninterpretedOption_NamePart* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const UninterpretedOption_NamePart>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.UninterpretedOption.NamePart)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.UninterpretedOption.NamePart)
+ MergeFrom(*source);
+ }
+}
+
+void UninterpretedOption_NamePart::MergeFrom(const UninterpretedOption_NamePart& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.UninterpretedOption.NamePart)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from._has_bits_[0 / 32] & (0xffu << (0 % 32))) {
+ if (from.has_name_part()) {
+ set_has_name_part();
+ name_part_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_part_);
+ }
+ if (from.has_is_extension()) {
+ set_is_extension(from.is_extension());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void UninterpretedOption_NamePart::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.UninterpretedOption.NamePart)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void UninterpretedOption_NamePart::CopyFrom(const UninterpretedOption_NamePart& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.UninterpretedOption.NamePart)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool UninterpretedOption_NamePart::IsInitialized() const {
+ if ((_has_bits_[0] & 0x00000003) != 0x00000003) return false;
+
+ return true;
+}
+
+void UninterpretedOption_NamePart::Swap(UninterpretedOption_NamePart* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void UninterpretedOption_NamePart::InternalSwap(UninterpretedOption_NamePart* other) {
+ name_part_.Swap(&other->name_part_);
+ std::swap(is_extension_, other->is_extension_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata UninterpretedOption_NamePart::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = UninterpretedOption_NamePart_descriptor_;
+ metadata.reflection = UninterpretedOption_NamePart_reflection_;
+ return metadata;
+}
+
+
+// -------------------------------------------------------------------
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int UninterpretedOption::kNameFieldNumber;
+const int UninterpretedOption::kIdentifierValueFieldNumber;
+const int UninterpretedOption::kPositiveIntValueFieldNumber;
+const int UninterpretedOption::kNegativeIntValueFieldNumber;
+const int UninterpretedOption::kDoubleValueFieldNumber;
+const int UninterpretedOption::kStringValueFieldNumber;
+const int UninterpretedOption::kAggregateValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+UninterpretedOption::UninterpretedOption()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.UninterpretedOption)
+}
+
+void UninterpretedOption::InitAsDefaultInstance() {
+}
+
+UninterpretedOption::UninterpretedOption(const UninterpretedOption& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.UninterpretedOption)
+}
+
+void UninterpretedOption::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ identifier_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ positive_int_value_ = GOOGLE_ULONGLONG(0);
+ negative_int_value_ = GOOGLE_LONGLONG(0);
+ double_value_ = 0;
+ string_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ aggregate_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+UninterpretedOption::~UninterpretedOption() {
+ // @@protoc_insertion_point(destructor:google.protobuf.UninterpretedOption)
+ SharedDtor();
+}
+
+void UninterpretedOption::SharedDtor() {
+ identifier_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ string_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ aggregate_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void UninterpretedOption::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* UninterpretedOption::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return UninterpretedOption_descriptor_;
+}
+
+const UninterpretedOption& UninterpretedOption::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+UninterpretedOption* UninterpretedOption::default_instance_ = NULL;
+
+UninterpretedOption* UninterpretedOption::New(::google::protobuf::Arena* arena) const {
+ UninterpretedOption* n = new UninterpretedOption;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void UninterpretedOption::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.UninterpretedOption)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(UninterpretedOption, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<UninterpretedOption*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ if (_has_bits_[0 / 32] & 126u) {
+ ZR_(positive_int_value_, double_value_);
+ if (has_identifier_value()) {
+ identifier_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_string_value()) {
+ string_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_aggregate_value()) {
+ aggregate_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ name_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool UninterpretedOption::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.UninterpretedOption)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated .google.protobuf.UninterpretedOption.NamePart name = 2;
+ case 2: {
+ if (tag == 18) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_name:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_name()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_loop_name;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(26)) goto parse_identifier_value;
+ break;
+ }
+
+ // optional string identifier_value = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_identifier_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_identifier_value()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->identifier_value().data(), this->identifier_value().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.UninterpretedOption.identifier_value");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(32)) goto parse_positive_int_value;
+ break;
+ }
+
+ // optional uint64 positive_int_value = 4;
+ case 4: {
+ if (tag == 32) {
+ parse_positive_int_value:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::uint64, ::google::protobuf::internal::WireFormatLite::TYPE_UINT64>(
+ input, &positive_int_value_)));
+ set_has_positive_int_value();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(40)) goto parse_negative_int_value;
+ break;
+ }
+
+ // optional int64 negative_int_value = 5;
+ case 5: {
+ if (tag == 40) {
+ parse_negative_int_value:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int64, ::google::protobuf::internal::WireFormatLite::TYPE_INT64>(
+ input, &negative_int_value_)));
+ set_has_negative_int_value();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(49)) goto parse_double_value;
+ break;
+ }
+
+ // optional double double_value = 6;
+ case 6: {
+ if (tag == 49) {
+ parse_double_value:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ double, ::google::protobuf::internal::WireFormatLite::TYPE_DOUBLE>(
+ input, &double_value_)));
+ set_has_double_value();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(58)) goto parse_string_value;
+ break;
+ }
+
+ // optional bytes string_value = 7;
+ case 7: {
+ if (tag == 58) {
+ parse_string_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadBytes(
+ input, this->mutable_string_value()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(66)) goto parse_aggregate_value;
+ break;
+ }
+
+ // optional string aggregate_value = 8;
+ case 8: {
+ if (tag == 66) {
+ parse_aggregate_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_aggregate_value()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->aggregate_value().data(), this->aggregate_value().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.UninterpretedOption.aggregate_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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.UninterpretedOption)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.UninterpretedOption)
+ return false;
+#undef DO_
+}
+
+void UninterpretedOption::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.UninterpretedOption)
+ // repeated .google.protobuf.UninterpretedOption.NamePart name = 2;
+ for (unsigned int i = 0, n = this->name_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, this->name(i), output);
+ }
+
+ // optional string identifier_value = 3;
+ if (has_identifier_value()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->identifier_value().data(), this->identifier_value().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.UninterpretedOption.identifier_value");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 3, this->identifier_value(), output);
+ }
+
+ // optional uint64 positive_int_value = 4;
+ if (has_positive_int_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteUInt64(4, this->positive_int_value(), output);
+ }
+
+ // optional int64 negative_int_value = 5;
+ if (has_negative_int_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt64(5, this->negative_int_value(), output);
+ }
+
+ // optional double double_value = 6;
+ if (has_double_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteDouble(6, this->double_value(), output);
+ }
+
+ // optional bytes string_value = 7;
+ if (has_string_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBytesMaybeAliased(
+ 7, this->string_value(), output);
+ }
+
+ // optional string aggregate_value = 8;
+ if (has_aggregate_value()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->aggregate_value().data(), this->aggregate_value().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.UninterpretedOption.aggregate_value");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 8, this->aggregate_value(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.UninterpretedOption)
+}
+
+::google::protobuf::uint8* UninterpretedOption::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.UninterpretedOption)
+ // repeated .google.protobuf.UninterpretedOption.NamePart name = 2;
+ for (unsigned int i = 0, n = this->name_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, this->name(i), false, target);
+ }
+
+ // optional string identifier_value = 3;
+ if (has_identifier_value()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->identifier_value().data(), this->identifier_value().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.UninterpretedOption.identifier_value");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 3, this->identifier_value(), target);
+ }
+
+ // optional uint64 positive_int_value = 4;
+ if (has_positive_int_value()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteUInt64ToArray(4, this->positive_int_value(), target);
+ }
+
+ // optional int64 negative_int_value = 5;
+ if (has_negative_int_value()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt64ToArray(5, this->negative_int_value(), target);
+ }
+
+ // optional double double_value = 6;
+ if (has_double_value()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteDoubleToArray(6, this->double_value(), target);
+ }
+
+ // optional bytes string_value = 7;
+ if (has_string_value()) {
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteBytesToArray(
+ 7, this->string_value(), target);
+ }
+
+ // optional string aggregate_value = 8;
+ if (has_aggregate_value()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->aggregate_value().data(), this->aggregate_value().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.UninterpretedOption.aggregate_value");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 8, this->aggregate_value(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.UninterpretedOption)
+ return target;
+}
+
+int UninterpretedOption::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.UninterpretedOption)
+ int total_size = 0;
+
+ if (_has_bits_[1 / 32] & 126u) {
+ // optional string identifier_value = 3;
+ if (has_identifier_value()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->identifier_value());
+ }
+
+ // optional uint64 positive_int_value = 4;
+ if (has_positive_int_value()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::UInt64Size(
+ this->positive_int_value());
+ }
+
+ // optional int64 negative_int_value = 5;
+ if (has_negative_int_value()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int64Size(
+ this->negative_int_value());
+ }
+
+ // optional double double_value = 6;
+ if (has_double_value()) {
+ total_size += 1 + 8;
+ }
+
+ // optional bytes string_value = 7;
+ if (has_string_value()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::BytesSize(
+ this->string_value());
+ }
+
+ // optional string aggregate_value = 8;
+ if (has_aggregate_value()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->aggregate_value());
+ }
+
+ }
+ // repeated .google.protobuf.UninterpretedOption.NamePart name = 2;
+ total_size += 1 * this->name_size();
+ for (int i = 0; i < this->name_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->name(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void UninterpretedOption::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.UninterpretedOption)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const UninterpretedOption* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const UninterpretedOption>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.UninterpretedOption)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.UninterpretedOption)
+ MergeFrom(*source);
+ }
+}
+
+void UninterpretedOption::MergeFrom(const UninterpretedOption& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.UninterpretedOption)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ name_.MergeFrom(from.name_);
+ if (from._has_bits_[1 / 32] & (0xffu << (1 % 32))) {
+ if (from.has_identifier_value()) {
+ set_has_identifier_value();
+ identifier_value_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.identifier_value_);
+ }
+ if (from.has_positive_int_value()) {
+ set_positive_int_value(from.positive_int_value());
+ }
+ if (from.has_negative_int_value()) {
+ set_negative_int_value(from.negative_int_value());
+ }
+ if (from.has_double_value()) {
+ set_double_value(from.double_value());
+ }
+ if (from.has_string_value()) {
+ set_has_string_value();
+ string_value_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.string_value_);
+ }
+ if (from.has_aggregate_value()) {
+ set_has_aggregate_value();
+ aggregate_value_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.aggregate_value_);
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void UninterpretedOption::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.UninterpretedOption)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void UninterpretedOption::CopyFrom(const UninterpretedOption& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.UninterpretedOption)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool UninterpretedOption::IsInitialized() const {
+
+ if (!::google::protobuf::internal::AllAreInitialized(this->name())) return false;
+ return true;
+}
+
+void UninterpretedOption::Swap(UninterpretedOption* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void UninterpretedOption::InternalSwap(UninterpretedOption* other) {
+ name_.UnsafeArenaSwap(&other->name_);
+ identifier_value_.Swap(&other->identifier_value_);
+ std::swap(positive_int_value_, other->positive_int_value_);
+ std::swap(negative_int_value_, other->negative_int_value_);
+ std::swap(double_value_, other->double_value_);
+ string_value_.Swap(&other->string_value_);
+ aggregate_value_.Swap(&other->aggregate_value_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata UninterpretedOption::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = UninterpretedOption_descriptor_;
+ metadata.reflection = UninterpretedOption_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// UninterpretedOption_NamePart
+
+// required string name_part = 1;
+bool UninterpretedOption_NamePart::has_name_part() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+void UninterpretedOption_NamePart::set_has_name_part() {
+ _has_bits_[0] |= 0x00000001u;
+}
+void UninterpretedOption_NamePart::clear_has_name_part() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+void UninterpretedOption_NamePart::clear_name_part() {
+ name_part_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name_part();
+}
+ const ::std::string& UninterpretedOption_NamePart::name_part() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.NamePart.name_part)
+ return name_part_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption_NamePart::set_name_part(const ::std::string& value) {
+ set_has_name_part();
+ name_part_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+ void UninterpretedOption_NamePart::set_name_part(const char* value) {
+ set_has_name_part();
+ name_part_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+ void UninterpretedOption_NamePart::set_name_part(const char* value, size_t size) {
+ set_has_name_part();
+ name_part_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+ ::std::string* UninterpretedOption_NamePart::mutable_name_part() {
+ set_has_name_part();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.NamePart.name_part)
+ return name_part_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* UninterpretedOption_NamePart::release_name_part() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.NamePart.name_part)
+ clear_has_name_part();
+ return name_part_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption_NamePart::set_allocated_name_part(::std::string* name_part) {
+ if (name_part != NULL) {
+ set_has_name_part();
+ } else {
+ clear_has_name_part();
+ }
+ name_part_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name_part);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+
+// required bool is_extension = 2;
+bool UninterpretedOption_NamePart::has_is_extension() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void UninterpretedOption_NamePart::set_has_is_extension() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void UninterpretedOption_NamePart::clear_has_is_extension() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void UninterpretedOption_NamePart::clear_is_extension() {
+ is_extension_ = false;
+ clear_has_is_extension();
+}
+ bool UninterpretedOption_NamePart::is_extension() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.NamePart.is_extension)
+ return is_extension_;
+}
+ void UninterpretedOption_NamePart::set_is_extension(bool value) {
+ set_has_is_extension();
+ is_extension_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.NamePart.is_extension)
+}
+
+// -------------------------------------------------------------------
+
+// UninterpretedOption
+
+// repeated .google.protobuf.UninterpretedOption.NamePart name = 2;
+int UninterpretedOption::name_size() const {
+ return name_.size();
+}
+void UninterpretedOption::clear_name() {
+ name_.Clear();
+}
+const ::google::protobuf::UninterpretedOption_NamePart& UninterpretedOption::name(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.name)
+ return name_.Get(index);
+}
+::google::protobuf::UninterpretedOption_NamePart* UninterpretedOption::mutable_name(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.name)
+ return name_.Mutable(index);
+}
+::google::protobuf::UninterpretedOption_NamePart* UninterpretedOption::add_name() {
+ // @@protoc_insertion_point(field_add:google.protobuf.UninterpretedOption.name)
+ return name_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption_NamePart >*
+UninterpretedOption::mutable_name() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.UninterpretedOption.name)
+ return &name_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption_NamePart >&
+UninterpretedOption::name() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.UninterpretedOption.name)
+ return name_;
+}
+
+// optional string identifier_value = 3;
+bool UninterpretedOption::has_identifier_value() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void UninterpretedOption::set_has_identifier_value() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void UninterpretedOption::clear_has_identifier_value() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void UninterpretedOption::clear_identifier_value() {
+ identifier_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_identifier_value();
+}
+ const ::std::string& UninterpretedOption::identifier_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.identifier_value)
+ return identifier_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption::set_identifier_value(const ::std::string& value) {
+ set_has_identifier_value();
+ identifier_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.identifier_value)
+}
+ void UninterpretedOption::set_identifier_value(const char* value) {
+ set_has_identifier_value();
+ identifier_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.identifier_value)
+}
+ void UninterpretedOption::set_identifier_value(const char* value, size_t size) {
+ set_has_identifier_value();
+ identifier_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.identifier_value)
+}
+ ::std::string* UninterpretedOption::mutable_identifier_value() {
+ set_has_identifier_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.identifier_value)
+ return identifier_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* UninterpretedOption::release_identifier_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.identifier_value)
+ clear_has_identifier_value();
+ return identifier_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption::set_allocated_identifier_value(::std::string* identifier_value) {
+ if (identifier_value != NULL) {
+ set_has_identifier_value();
+ } else {
+ clear_has_identifier_value();
+ }
+ identifier_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), identifier_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.identifier_value)
+}
+
+// optional uint64 positive_int_value = 4;
+bool UninterpretedOption::has_positive_int_value() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void UninterpretedOption::set_has_positive_int_value() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void UninterpretedOption::clear_has_positive_int_value() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void UninterpretedOption::clear_positive_int_value() {
+ positive_int_value_ = GOOGLE_ULONGLONG(0);
+ clear_has_positive_int_value();
+}
+ ::google::protobuf::uint64 UninterpretedOption::positive_int_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.positive_int_value)
+ return positive_int_value_;
+}
+ void UninterpretedOption::set_positive_int_value(::google::protobuf::uint64 value) {
+ set_has_positive_int_value();
+ positive_int_value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.positive_int_value)
+}
+
+// optional int64 negative_int_value = 5;
+bool UninterpretedOption::has_negative_int_value() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void UninterpretedOption::set_has_negative_int_value() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void UninterpretedOption::clear_has_negative_int_value() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void UninterpretedOption::clear_negative_int_value() {
+ negative_int_value_ = GOOGLE_LONGLONG(0);
+ clear_has_negative_int_value();
+}
+ ::google::protobuf::int64 UninterpretedOption::negative_int_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.negative_int_value)
+ return negative_int_value_;
+}
+ void UninterpretedOption::set_negative_int_value(::google::protobuf::int64 value) {
+ set_has_negative_int_value();
+ negative_int_value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.negative_int_value)
+}
+
+// optional double double_value = 6;
+bool UninterpretedOption::has_double_value() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+void UninterpretedOption::set_has_double_value() {
+ _has_bits_[0] |= 0x00000010u;
+}
+void UninterpretedOption::clear_has_double_value() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+void UninterpretedOption::clear_double_value() {
+ double_value_ = 0;
+ clear_has_double_value();
+}
+ double UninterpretedOption::double_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.double_value)
+ return double_value_;
+}
+ void UninterpretedOption::set_double_value(double value) {
+ set_has_double_value();
+ double_value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.double_value)
+}
+
+// optional bytes string_value = 7;
+bool UninterpretedOption::has_string_value() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+void UninterpretedOption::set_has_string_value() {
+ _has_bits_[0] |= 0x00000020u;
+}
+void UninterpretedOption::clear_has_string_value() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+void UninterpretedOption::clear_string_value() {
+ string_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_string_value();
+}
+ const ::std::string& UninterpretedOption::string_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.string_value)
+ return string_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption::set_string_value(const ::std::string& value) {
+ set_has_string_value();
+ string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.string_value)
+}
+ void UninterpretedOption::set_string_value(const char* value) {
+ set_has_string_value();
+ string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.string_value)
+}
+ void UninterpretedOption::set_string_value(const void* value, size_t size) {
+ set_has_string_value();
+ string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.string_value)
+}
+ ::std::string* UninterpretedOption::mutable_string_value() {
+ set_has_string_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.string_value)
+ return string_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* UninterpretedOption::release_string_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.string_value)
+ clear_has_string_value();
+ return string_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption::set_allocated_string_value(::std::string* string_value) {
+ if (string_value != NULL) {
+ set_has_string_value();
+ } else {
+ clear_has_string_value();
+ }
+ string_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), string_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.string_value)
+}
+
+// optional string aggregate_value = 8;
+bool UninterpretedOption::has_aggregate_value() const {
+ return (_has_bits_[0] & 0x00000040u) != 0;
+}
+void UninterpretedOption::set_has_aggregate_value() {
+ _has_bits_[0] |= 0x00000040u;
+}
+void UninterpretedOption::clear_has_aggregate_value() {
+ _has_bits_[0] &= ~0x00000040u;
+}
+void UninterpretedOption::clear_aggregate_value() {
+ aggregate_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_aggregate_value();
+}
+ const ::std::string& UninterpretedOption::aggregate_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.aggregate_value)
+ return aggregate_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption::set_aggregate_value(const ::std::string& value) {
+ set_has_aggregate_value();
+ aggregate_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.aggregate_value)
+}
+ void UninterpretedOption::set_aggregate_value(const char* value) {
+ set_has_aggregate_value();
+ aggregate_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.aggregate_value)
+}
+ void UninterpretedOption::set_aggregate_value(const char* value, size_t size) {
+ set_has_aggregate_value();
+ aggregate_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.aggregate_value)
+}
+ ::std::string* UninterpretedOption::mutable_aggregate_value() {
+ set_has_aggregate_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.aggregate_value)
+ return aggregate_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* UninterpretedOption::release_aggregate_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.aggregate_value)
+ clear_has_aggregate_value();
+ return aggregate_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void UninterpretedOption::set_allocated_aggregate_value(::std::string* aggregate_value) {
+ if (aggregate_value != NULL) {
+ set_has_aggregate_value();
+ } else {
+ clear_has_aggregate_value();
+ }
+ aggregate_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), aggregate_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.aggregate_value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int SourceCodeInfo_Location::kPathFieldNumber;
+const int SourceCodeInfo_Location::kSpanFieldNumber;
+const int SourceCodeInfo_Location::kLeadingCommentsFieldNumber;
+const int SourceCodeInfo_Location::kTrailingCommentsFieldNumber;
+const int SourceCodeInfo_Location::kLeadingDetachedCommentsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+SourceCodeInfo_Location::SourceCodeInfo_Location()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.SourceCodeInfo.Location)
+}
+
+void SourceCodeInfo_Location::InitAsDefaultInstance() {
+}
+
+SourceCodeInfo_Location::SourceCodeInfo_Location(const SourceCodeInfo_Location& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.SourceCodeInfo.Location)
+}
+
+void SourceCodeInfo_Location::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ leading_comments_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ trailing_comments_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+SourceCodeInfo_Location::~SourceCodeInfo_Location() {
+ // @@protoc_insertion_point(destructor:google.protobuf.SourceCodeInfo.Location)
+ SharedDtor();
+}
+
+void SourceCodeInfo_Location::SharedDtor() {
+ leading_comments_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ trailing_comments_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void SourceCodeInfo_Location::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* SourceCodeInfo_Location::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return SourceCodeInfo_Location_descriptor_;
+}
+
+const SourceCodeInfo_Location& SourceCodeInfo_Location::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+SourceCodeInfo_Location* SourceCodeInfo_Location::default_instance_ = NULL;
+
+SourceCodeInfo_Location* SourceCodeInfo_Location::New(::google::protobuf::Arena* arena) const {
+ SourceCodeInfo_Location* n = new SourceCodeInfo_Location;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void SourceCodeInfo_Location::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.SourceCodeInfo.Location)
+ if (_has_bits_[0 / 32] & 12u) {
+ if (has_leading_comments()) {
+ leading_comments_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ if (has_trailing_comments()) {
+ trailing_comments_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+ path_.Clear();
+ span_.Clear();
+ leading_detached_comments_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool SourceCodeInfo_Location::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.SourceCodeInfo.Location)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated int32 path = 1 [packed = true];
+ case 1: {
+ if (tag == 10) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPackedPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, this->mutable_path())));
+ } else if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadRepeatedPrimitiveNoInline<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ 1, 10, input, this->mutable_path())));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_span;
+ break;
+ }
+
+ // repeated int32 span = 2 [packed = true];
+ case 2: {
+ if (tag == 18) {
+ parse_span:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPackedPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, this->mutable_span())));
+ } else if (tag == 16) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadRepeatedPrimitiveNoInline<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ 1, 18, input, this->mutable_span())));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_leading_comments;
+ break;
+ }
+
+ // optional string leading_comments = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_leading_comments:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_leading_comments()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->leading_comments().data(), this->leading_comments().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.SourceCodeInfo.Location.leading_comments");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(34)) goto parse_trailing_comments;
+ break;
+ }
+
+ // optional string trailing_comments = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_trailing_comments:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_trailing_comments()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->trailing_comments().data(), this->trailing_comments().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.SourceCodeInfo.Location.trailing_comments");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_leading_detached_comments;
+ break;
+ }
+
+ // repeated string leading_detached_comments = 6;
+ case 6: {
+ if (tag == 50) {
+ parse_leading_detached_comments:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->add_leading_detached_comments()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->leading_detached_comments(this->leading_detached_comments_size() - 1).data(),
+ this->leading_detached_comments(this->leading_detached_comments_size() - 1).length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.SourceCodeInfo.Location.leading_detached_comments");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_leading_detached_comments;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.SourceCodeInfo.Location)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.SourceCodeInfo.Location)
+ return false;
+#undef DO_
+}
+
+void SourceCodeInfo_Location::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.SourceCodeInfo.Location)
+ // repeated int32 path = 1 [packed = true];
+ if (this->path_size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteTag(1, ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED, output);
+ output->WriteVarint32(_path_cached_byte_size_);
+ }
+ for (int i = 0; i < this->path_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32NoTag(
+ this->path(i), output);
+ }
+
+ // repeated int32 span = 2 [packed = true];
+ if (this->span_size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteTag(2, ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED, output);
+ output->WriteVarint32(_span_cached_byte_size_);
+ }
+ for (int i = 0; i < this->span_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32NoTag(
+ this->span(i), output);
+ }
+
+ // optional string leading_comments = 3;
+ if (has_leading_comments()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->leading_comments().data(), this->leading_comments().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.SourceCodeInfo.Location.leading_comments");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 3, this->leading_comments(), output);
+ }
+
+ // optional string trailing_comments = 4;
+ if (has_trailing_comments()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->trailing_comments().data(), this->trailing_comments().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.SourceCodeInfo.Location.trailing_comments");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 4, this->trailing_comments(), output);
+ }
+
+ // repeated string leading_detached_comments = 6;
+ for (int i = 0; i < this->leading_detached_comments_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->leading_detached_comments(i).data(), this->leading_detached_comments(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.SourceCodeInfo.Location.leading_detached_comments");
+ ::google::protobuf::internal::WireFormatLite::WriteString(
+ 6, this->leading_detached_comments(i), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.SourceCodeInfo.Location)
+}
+
+::google::protobuf::uint8* SourceCodeInfo_Location::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.SourceCodeInfo.Location)
+ // repeated int32 path = 1 [packed = true];
+ if (this->path_size() > 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteTagToArray(
+ 1,
+ ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ target);
+ target = ::google::protobuf::io::CodedOutputStream::WriteVarint32ToArray(
+ _path_cached_byte_size_, target);
+ }
+ for (int i = 0; i < this->path_size(); i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteInt32NoTagToArray(this->path(i), target);
+ }
+
+ // repeated int32 span = 2 [packed = true];
+ if (this->span_size() > 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteTagToArray(
+ 2,
+ ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ target);
+ target = ::google::protobuf::io::CodedOutputStream::WriteVarint32ToArray(
+ _span_cached_byte_size_, target);
+ }
+ for (int i = 0; i < this->span_size(); i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteInt32NoTagToArray(this->span(i), target);
+ }
+
+ // optional string leading_comments = 3;
+ if (has_leading_comments()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->leading_comments().data(), this->leading_comments().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.SourceCodeInfo.Location.leading_comments");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 3, this->leading_comments(), target);
+ }
+
+ // optional string trailing_comments = 4;
+ if (has_trailing_comments()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->trailing_comments().data(), this->trailing_comments().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.SourceCodeInfo.Location.trailing_comments");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 4, this->trailing_comments(), target);
+ }
+
+ // repeated string leading_detached_comments = 6;
+ for (int i = 0; i < this->leading_detached_comments_size(); i++) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->leading_detached_comments(i).data(), this->leading_detached_comments(i).length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.SourceCodeInfo.Location.leading_detached_comments");
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteStringToArray(6, this->leading_detached_comments(i), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.SourceCodeInfo.Location)
+ return target;
+}
+
+int SourceCodeInfo_Location::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.SourceCodeInfo.Location)
+ int total_size = 0;
+
+ if (_has_bits_[2 / 32] & 12u) {
+ // optional string leading_comments = 3;
+ if (has_leading_comments()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->leading_comments());
+ }
+
+ // optional string trailing_comments = 4;
+ if (has_trailing_comments()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->trailing_comments());
+ }
+
+ }
+ // repeated int32 path = 1 [packed = true];
+ {
+ int data_size = 0;
+ for (int i = 0; i < this->path_size(); i++) {
+ data_size += ::google::protobuf::internal::WireFormatLite::
+ Int32Size(this->path(i));
+ }
+ if (data_size > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(data_size);
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _path_cached_byte_size_ = data_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ total_size += data_size;
+ }
+
+ // repeated int32 span = 2 [packed = true];
+ {
+ int data_size = 0;
+ for (int i = 0; i < this->span_size(); i++) {
+ data_size += ::google::protobuf::internal::WireFormatLite::
+ Int32Size(this->span(i));
+ }
+ if (data_size > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(data_size);
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _span_cached_byte_size_ = data_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ total_size += data_size;
+ }
+
+ // repeated string leading_detached_comments = 6;
+ total_size += 1 * this->leading_detached_comments_size();
+ for (int i = 0; i < this->leading_detached_comments_size(); i++) {
+ total_size += ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->leading_detached_comments(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void SourceCodeInfo_Location::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.SourceCodeInfo.Location)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const SourceCodeInfo_Location* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const SourceCodeInfo_Location>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.SourceCodeInfo.Location)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.SourceCodeInfo.Location)
+ MergeFrom(*source);
+ }
+}
+
+void SourceCodeInfo_Location::MergeFrom(const SourceCodeInfo_Location& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.SourceCodeInfo.Location)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ path_.MergeFrom(from.path_);
+ span_.MergeFrom(from.span_);
+ leading_detached_comments_.MergeFrom(from.leading_detached_comments_);
+ if (from._has_bits_[2 / 32] & (0xffu << (2 % 32))) {
+ if (from.has_leading_comments()) {
+ set_has_leading_comments();
+ leading_comments_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.leading_comments_);
+ }
+ if (from.has_trailing_comments()) {
+ set_has_trailing_comments();
+ trailing_comments_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.trailing_comments_);
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void SourceCodeInfo_Location::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.SourceCodeInfo.Location)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void SourceCodeInfo_Location::CopyFrom(const SourceCodeInfo_Location& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.SourceCodeInfo.Location)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool SourceCodeInfo_Location::IsInitialized() const {
+
+ return true;
+}
+
+void SourceCodeInfo_Location::Swap(SourceCodeInfo_Location* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void SourceCodeInfo_Location::InternalSwap(SourceCodeInfo_Location* other) {
+ path_.UnsafeArenaSwap(&other->path_);
+ span_.UnsafeArenaSwap(&other->span_);
+ leading_comments_.Swap(&other->leading_comments_);
+ trailing_comments_.Swap(&other->trailing_comments_);
+ leading_detached_comments_.UnsafeArenaSwap(&other->leading_detached_comments_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata SourceCodeInfo_Location::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = SourceCodeInfo_Location_descriptor_;
+ metadata.reflection = SourceCodeInfo_Location_reflection_;
+ return metadata;
+}
+
+
+// -------------------------------------------------------------------
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int SourceCodeInfo::kLocationFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+SourceCodeInfo::SourceCodeInfo()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.SourceCodeInfo)
+}
+
+void SourceCodeInfo::InitAsDefaultInstance() {
+}
+
+SourceCodeInfo::SourceCodeInfo(const SourceCodeInfo& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.SourceCodeInfo)
+}
+
+void SourceCodeInfo::SharedCtor() {
+ _cached_size_ = 0;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+SourceCodeInfo::~SourceCodeInfo() {
+ // @@protoc_insertion_point(destructor:google.protobuf.SourceCodeInfo)
+ SharedDtor();
+}
+
+void SourceCodeInfo::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void SourceCodeInfo::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* SourceCodeInfo::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return SourceCodeInfo_descriptor_;
+}
+
+const SourceCodeInfo& SourceCodeInfo::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+SourceCodeInfo* SourceCodeInfo::default_instance_ = NULL;
+
+SourceCodeInfo* SourceCodeInfo::New(::google::protobuf::Arena* arena) const {
+ SourceCodeInfo* n = new SourceCodeInfo;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void SourceCodeInfo::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.SourceCodeInfo)
+ location_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool SourceCodeInfo::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.SourceCodeInfo)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated .google.protobuf.SourceCodeInfo.Location location = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_location:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_location()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(10)) goto parse_loop_location;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.SourceCodeInfo)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.SourceCodeInfo)
+ return false;
+#undef DO_
+}
+
+void SourceCodeInfo::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.SourceCodeInfo)
+ // repeated .google.protobuf.SourceCodeInfo.Location location = 1;
+ for (unsigned int i = 0, n = this->location_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 1, this->location(i), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.SourceCodeInfo)
+}
+
+::google::protobuf::uint8* SourceCodeInfo::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.SourceCodeInfo)
+ // repeated .google.protobuf.SourceCodeInfo.Location location = 1;
+ for (unsigned int i = 0, n = this->location_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 1, this->location(i), false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.SourceCodeInfo)
+ return target;
+}
+
+int SourceCodeInfo::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.SourceCodeInfo)
+ int total_size = 0;
+
+ // repeated .google.protobuf.SourceCodeInfo.Location location = 1;
+ total_size += 1 * this->location_size();
+ for (int i = 0; i < this->location_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->location(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void SourceCodeInfo::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.SourceCodeInfo)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const SourceCodeInfo* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const SourceCodeInfo>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.SourceCodeInfo)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.SourceCodeInfo)
+ MergeFrom(*source);
+ }
+}
+
+void SourceCodeInfo::MergeFrom(const SourceCodeInfo& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.SourceCodeInfo)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ location_.MergeFrom(from.location_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void SourceCodeInfo::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.SourceCodeInfo)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void SourceCodeInfo::CopyFrom(const SourceCodeInfo& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.SourceCodeInfo)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool SourceCodeInfo::IsInitialized() const {
+
+ return true;
+}
+
+void SourceCodeInfo::Swap(SourceCodeInfo* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void SourceCodeInfo::InternalSwap(SourceCodeInfo* other) {
+ location_.UnsafeArenaSwap(&other->location_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata SourceCodeInfo::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = SourceCodeInfo_descriptor_;
+ metadata.reflection = SourceCodeInfo_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// SourceCodeInfo_Location
+
+// repeated int32 path = 1 [packed = true];
+int SourceCodeInfo_Location::path_size() const {
+ return path_.size();
+}
+void SourceCodeInfo_Location::clear_path() {
+ path_.Clear();
+}
+ ::google::protobuf::int32 SourceCodeInfo_Location::path(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.path)
+ return path_.Get(index);
+}
+ void SourceCodeInfo_Location::set_path(int index, ::google::protobuf::int32 value) {
+ path_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.path)
+}
+ void SourceCodeInfo_Location::add_path(::google::protobuf::int32 value) {
+ path_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.Location.path)
+}
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+SourceCodeInfo_Location::path() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.Location.path)
+ return path_;
+}
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+SourceCodeInfo_Location::mutable_path() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.Location.path)
+ return &path_;
+}
+
+// repeated int32 span = 2 [packed = true];
+int SourceCodeInfo_Location::span_size() const {
+ return span_.size();
+}
+void SourceCodeInfo_Location::clear_span() {
+ span_.Clear();
+}
+ ::google::protobuf::int32 SourceCodeInfo_Location::span(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.span)
+ return span_.Get(index);
+}
+ void SourceCodeInfo_Location::set_span(int index, ::google::protobuf::int32 value) {
+ span_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.span)
+}
+ void SourceCodeInfo_Location::add_span(::google::protobuf::int32 value) {
+ span_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.Location.span)
+}
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+SourceCodeInfo_Location::span() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.Location.span)
+ return span_;
+}
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+SourceCodeInfo_Location::mutable_span() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.Location.span)
+ return &span_;
+}
+
+// optional string leading_comments = 3;
+bool SourceCodeInfo_Location::has_leading_comments() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void SourceCodeInfo_Location::set_has_leading_comments() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void SourceCodeInfo_Location::clear_has_leading_comments() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void SourceCodeInfo_Location::clear_leading_comments() {
+ leading_comments_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_leading_comments();
+}
+ const ::std::string& SourceCodeInfo_Location::leading_comments() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.leading_comments)
+ return leading_comments_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void SourceCodeInfo_Location::set_leading_comments(const ::std::string& value) {
+ set_has_leading_comments();
+ leading_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+ void SourceCodeInfo_Location::set_leading_comments(const char* value) {
+ set_has_leading_comments();
+ leading_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+ void SourceCodeInfo_Location::set_leading_comments(const char* value, size_t size) {
+ set_has_leading_comments();
+ leading_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+ ::std::string* SourceCodeInfo_Location::mutable_leading_comments() {
+ set_has_leading_comments();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.Location.leading_comments)
+ return leading_comments_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* SourceCodeInfo_Location::release_leading_comments() {
+ // @@protoc_insertion_point(field_release:google.protobuf.SourceCodeInfo.Location.leading_comments)
+ clear_has_leading_comments();
+ return leading_comments_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void SourceCodeInfo_Location::set_allocated_leading_comments(::std::string* leading_comments) {
+ if (leading_comments != NULL) {
+ set_has_leading_comments();
+ } else {
+ clear_has_leading_comments();
+ }
+ leading_comments_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), leading_comments);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+
+// optional string trailing_comments = 4;
+bool SourceCodeInfo_Location::has_trailing_comments() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void SourceCodeInfo_Location::set_has_trailing_comments() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void SourceCodeInfo_Location::clear_has_trailing_comments() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void SourceCodeInfo_Location::clear_trailing_comments() {
+ trailing_comments_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_trailing_comments();
+}
+ const ::std::string& SourceCodeInfo_Location::trailing_comments() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+ return trailing_comments_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void SourceCodeInfo_Location::set_trailing_comments(const ::std::string& value) {
+ set_has_trailing_comments();
+ trailing_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+ void SourceCodeInfo_Location::set_trailing_comments(const char* value) {
+ set_has_trailing_comments();
+ trailing_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+ void SourceCodeInfo_Location::set_trailing_comments(const char* value, size_t size) {
+ set_has_trailing_comments();
+ trailing_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+ ::std::string* SourceCodeInfo_Location::mutable_trailing_comments() {
+ set_has_trailing_comments();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+ return trailing_comments_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* SourceCodeInfo_Location::release_trailing_comments() {
+ // @@protoc_insertion_point(field_release:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+ clear_has_trailing_comments();
+ return trailing_comments_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void SourceCodeInfo_Location::set_allocated_trailing_comments(::std::string* trailing_comments) {
+ if (trailing_comments != NULL) {
+ set_has_trailing_comments();
+ } else {
+ clear_has_trailing_comments();
+ }
+ trailing_comments_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), trailing_comments);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+
+// repeated string leading_detached_comments = 6;
+int SourceCodeInfo_Location::leading_detached_comments_size() const {
+ return leading_detached_comments_.size();
+}
+void SourceCodeInfo_Location::clear_leading_detached_comments() {
+ leading_detached_comments_.Clear();
+}
+ const ::std::string& SourceCodeInfo_Location::leading_detached_comments(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_.Get(index);
+}
+ ::std::string* SourceCodeInfo_Location::mutable_leading_detached_comments(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_.Mutable(index);
+}
+ void SourceCodeInfo_Location::set_leading_detached_comments(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ leading_detached_comments_.Mutable(index)->assign(value);
+}
+ void SourceCodeInfo_Location::set_leading_detached_comments(int index, const char* value) {
+ leading_detached_comments_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+ void SourceCodeInfo_Location::set_leading_detached_comments(int index, const char* value, size_t size) {
+ leading_detached_comments_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+ ::std::string* SourceCodeInfo_Location::add_leading_detached_comments() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_.Add();
+}
+ void SourceCodeInfo_Location::add_leading_detached_comments(const ::std::string& value) {
+ leading_detached_comments_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+ void SourceCodeInfo_Location::add_leading_detached_comments(const char* value) {
+ leading_detached_comments_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+ void SourceCodeInfo_Location::add_leading_detached_comments(const char* value, size_t size) {
+ leading_detached_comments_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+ const ::google::protobuf::RepeatedPtrField< ::std::string>&
+SourceCodeInfo_Location::leading_detached_comments() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_;
+}
+ ::google::protobuf::RepeatedPtrField< ::std::string>*
+SourceCodeInfo_Location::mutable_leading_detached_comments() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return &leading_detached_comments_;
+}
+
+// -------------------------------------------------------------------
+
+// SourceCodeInfo
+
+// repeated .google.protobuf.SourceCodeInfo.Location location = 1;
+int SourceCodeInfo::location_size() const {
+ return location_.size();
+}
+void SourceCodeInfo::clear_location() {
+ location_.Clear();
+}
+const ::google::protobuf::SourceCodeInfo_Location& SourceCodeInfo::location(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.location)
+ return location_.Get(index);
+}
+::google::protobuf::SourceCodeInfo_Location* SourceCodeInfo::mutable_location(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.location)
+ return location_.Mutable(index);
+}
+::google::protobuf::SourceCodeInfo_Location* SourceCodeInfo::add_location() {
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.location)
+ return location_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::SourceCodeInfo_Location >*
+SourceCodeInfo::mutable_location() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.location)
+ return &location_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::SourceCodeInfo_Location >&
+SourceCodeInfo::location() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.location)
+ return location_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int GeneratedCodeInfo_Annotation::kPathFieldNumber;
+const int GeneratedCodeInfo_Annotation::kSourceFileFieldNumber;
+const int GeneratedCodeInfo_Annotation::kBeginFieldNumber;
+const int GeneratedCodeInfo_Annotation::kEndFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+GeneratedCodeInfo_Annotation::GeneratedCodeInfo_Annotation()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.GeneratedCodeInfo.Annotation)
+}
+
+void GeneratedCodeInfo_Annotation::InitAsDefaultInstance() {
+}
+
+GeneratedCodeInfo_Annotation::GeneratedCodeInfo_Annotation(const GeneratedCodeInfo_Annotation& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.GeneratedCodeInfo.Annotation)
+}
+
+void GeneratedCodeInfo_Annotation::SharedCtor() {
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ source_file_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ begin_ = 0;
+ end_ = 0;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+GeneratedCodeInfo_Annotation::~GeneratedCodeInfo_Annotation() {
+ // @@protoc_insertion_point(destructor:google.protobuf.GeneratedCodeInfo.Annotation)
+ SharedDtor();
+}
+
+void GeneratedCodeInfo_Annotation::SharedDtor() {
+ source_file_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void GeneratedCodeInfo_Annotation::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* GeneratedCodeInfo_Annotation::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return GeneratedCodeInfo_Annotation_descriptor_;
+}
+
+const GeneratedCodeInfo_Annotation& GeneratedCodeInfo_Annotation::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+GeneratedCodeInfo_Annotation* GeneratedCodeInfo_Annotation::default_instance_ = NULL;
+
+GeneratedCodeInfo_Annotation* GeneratedCodeInfo_Annotation::New(::google::protobuf::Arena* arena) const {
+ GeneratedCodeInfo_Annotation* n = new GeneratedCodeInfo_Annotation;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void GeneratedCodeInfo_Annotation::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.GeneratedCodeInfo.Annotation)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(GeneratedCodeInfo_Annotation, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<GeneratedCodeInfo_Annotation*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ if (_has_bits_[0 / 32] & 14u) {
+ ZR_(begin_, end_);
+ if (has_source_file()) {
+ source_file_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ }
+ }
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ path_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool GeneratedCodeInfo_Annotation::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated int32 path = 1 [packed = true];
+ case 1: {
+ if (tag == 10) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPackedPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, this->mutable_path())));
+ } else if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadRepeatedPrimitiveNoInline<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ 1, 10, input, this->mutable_path())));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_source_file;
+ break;
+ }
+
+ // optional string source_file = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_source_file:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_source_file()));
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->source_file().data(), this->source_file().length(),
+ ::google::protobuf::internal::WireFormat::PARSE,
+ "google.protobuf.GeneratedCodeInfo.Annotation.source_file");
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(24)) goto parse_begin;
+ break;
+ }
+
+ // optional int32 begin = 3;
+ case 3: {
+ if (tag == 24) {
+ parse_begin:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &begin_)));
+ set_has_begin();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(32)) goto parse_end;
+ break;
+ }
+
+ // optional int32 end = 4;
+ case 4: {
+ if (tag == 32) {
+ parse_end:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &end_)));
+ set_has_end();
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.GeneratedCodeInfo.Annotation)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.GeneratedCodeInfo.Annotation)
+ return false;
+#undef DO_
+}
+
+void GeneratedCodeInfo_Annotation::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ // repeated int32 path = 1 [packed = true];
+ if (this->path_size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteTag(1, ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED, output);
+ output->WriteVarint32(_path_cached_byte_size_);
+ }
+ for (int i = 0; i < this->path_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32NoTag(
+ this->path(i), output);
+ }
+
+ // optional string source_file = 2;
+ if (has_source_file()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->source_file().data(), this->source_file().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.GeneratedCodeInfo.Annotation.source_file");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 2, this->source_file(), output);
+ }
+
+ // optional int32 begin = 3;
+ if (has_begin()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(3, this->begin(), output);
+ }
+
+ // optional int32 end = 4;
+ if (has_end()) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(4, this->end(), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.GeneratedCodeInfo.Annotation)
+}
+
+::google::protobuf::uint8* GeneratedCodeInfo_Annotation::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ // repeated int32 path = 1 [packed = true];
+ if (this->path_size() > 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteTagToArray(
+ 1,
+ ::google::protobuf::internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ target);
+ target = ::google::protobuf::io::CodedOutputStream::WriteVarint32ToArray(
+ _path_cached_byte_size_, target);
+ }
+ for (int i = 0; i < this->path_size(); i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteInt32NoTagToArray(this->path(i), target);
+ }
+
+ // optional string source_file = 2;
+ if (has_source_file()) {
+ ::google::protobuf::internal::WireFormat::VerifyUTF8StringNamedField(
+ this->source_file().data(), this->source_file().length(),
+ ::google::protobuf::internal::WireFormat::SERIALIZE,
+ "google.protobuf.GeneratedCodeInfo.Annotation.source_file");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 2, this->source_file(), target);
+ }
+
+ // optional int32 begin = 3;
+ if (has_begin()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(3, this->begin(), target);
+ }
+
+ // optional int32 end = 4;
+ if (has_end()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(4, this->end(), target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.GeneratedCodeInfo.Annotation)
+ return target;
+}
+
+int GeneratedCodeInfo_Annotation::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ int total_size = 0;
+
+ if (_has_bits_[1 / 32] & 14u) {
+ // optional string source_file = 2;
+ if (has_source_file()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->source_file());
+ }
+
+ // optional int32 begin = 3;
+ if (has_begin()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->begin());
+ }
+
+ // optional int32 end = 4;
+ if (has_end()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->end());
+ }
+
+ }
+ // repeated int32 path = 1 [packed = true];
+ {
+ int data_size = 0;
+ for (int i = 0; i < this->path_size(); i++) {
+ data_size += ::google::protobuf::internal::WireFormatLite::
+ Int32Size(this->path(i));
+ }
+ if (data_size > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(data_size);
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _path_cached_byte_size_ = data_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ total_size += data_size;
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void GeneratedCodeInfo_Annotation::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const GeneratedCodeInfo_Annotation* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const GeneratedCodeInfo_Annotation>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.GeneratedCodeInfo.Annotation)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.GeneratedCodeInfo.Annotation)
+ MergeFrom(*source);
+ }
+}
+
+void GeneratedCodeInfo_Annotation::MergeFrom(const GeneratedCodeInfo_Annotation& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ path_.MergeFrom(from.path_);
+ if (from._has_bits_[1 / 32] & (0xffu << (1 % 32))) {
+ if (from.has_source_file()) {
+ set_has_source_file();
+ source_file_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.source_file_);
+ }
+ if (from.has_begin()) {
+ set_begin(from.begin());
+ }
+ if (from.has_end()) {
+ set_end(from.end());
+ }
+ }
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void GeneratedCodeInfo_Annotation::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void GeneratedCodeInfo_Annotation::CopyFrom(const GeneratedCodeInfo_Annotation& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.GeneratedCodeInfo.Annotation)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool GeneratedCodeInfo_Annotation::IsInitialized() const {
+
+ return true;
+}
+
+void GeneratedCodeInfo_Annotation::Swap(GeneratedCodeInfo_Annotation* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void GeneratedCodeInfo_Annotation::InternalSwap(GeneratedCodeInfo_Annotation* other) {
+ path_.UnsafeArenaSwap(&other->path_);
+ source_file_.Swap(&other->source_file_);
+ std::swap(begin_, other->begin_);
+ std::swap(end_, other->end_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata GeneratedCodeInfo_Annotation::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = GeneratedCodeInfo_Annotation_descriptor_;
+ metadata.reflection = GeneratedCodeInfo_Annotation_reflection_;
+ return metadata;
+}
+
+
+// -------------------------------------------------------------------
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int GeneratedCodeInfo::kAnnotationFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+GeneratedCodeInfo::GeneratedCodeInfo()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.GeneratedCodeInfo)
+}
+
+void GeneratedCodeInfo::InitAsDefaultInstance() {
+}
+
+GeneratedCodeInfo::GeneratedCodeInfo(const GeneratedCodeInfo& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.GeneratedCodeInfo)
+}
+
+void GeneratedCodeInfo::SharedCtor() {
+ _cached_size_ = 0;
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+}
+
+GeneratedCodeInfo::~GeneratedCodeInfo() {
+ // @@protoc_insertion_point(destructor:google.protobuf.GeneratedCodeInfo)
+ SharedDtor();
+}
+
+void GeneratedCodeInfo::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void GeneratedCodeInfo::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* GeneratedCodeInfo::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return GeneratedCodeInfo_descriptor_;
+}
+
+const GeneratedCodeInfo& GeneratedCodeInfo::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ return *default_instance_;
+}
+
+GeneratedCodeInfo* GeneratedCodeInfo::default_instance_ = NULL;
+
+GeneratedCodeInfo* GeneratedCodeInfo::New(::google::protobuf::Arena* arena) const {
+ GeneratedCodeInfo* n = new GeneratedCodeInfo;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void GeneratedCodeInfo::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.GeneratedCodeInfo)
+ annotation_.Clear();
+ ::memset(_has_bits_, 0, sizeof(_has_bits_));
+ if (_internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->Clear();
+ }
+}
+
+bool GeneratedCodeInfo::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.GeneratedCodeInfo)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated .google.protobuf.GeneratedCodeInfo.Annotation annotation = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_annotation:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_annotation()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(10)) goto parse_loop_annotation;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormat::SkipField(
+ input, tag, mutable_unknown_fields()));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.GeneratedCodeInfo)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.GeneratedCodeInfo)
+ return false;
+#undef DO_
+}
+
+void GeneratedCodeInfo::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.GeneratedCodeInfo)
+ // repeated .google.protobuf.GeneratedCodeInfo.Annotation annotation = 1;
+ for (unsigned int i = 0, n = this->annotation_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 1, this->annotation(i), output);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+ unknown_fields(), output);
+ }
+ // @@protoc_insertion_point(serialize_end:google.protobuf.GeneratedCodeInfo)
+}
+
+::google::protobuf::uint8* GeneratedCodeInfo::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.GeneratedCodeInfo)
+ // repeated .google.protobuf.GeneratedCodeInfo.Annotation annotation = 1;
+ for (unsigned int i = 0, n = this->annotation_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 1, this->annotation(i), false, target);
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+ unknown_fields(), target);
+ }
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.GeneratedCodeInfo)
+ return target;
+}
+
+int GeneratedCodeInfo::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.GeneratedCodeInfo)
+ int total_size = 0;
+
+ // repeated .google.protobuf.GeneratedCodeInfo.Annotation annotation = 1;
+ total_size += 1 * this->annotation_size();
+ for (int i = 0; i < this->annotation_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->annotation(i));
+ }
+
+ if (_internal_metadata_.have_unknown_fields()) {
+ total_size +=
+ ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+ unknown_fields());
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void GeneratedCodeInfo::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.GeneratedCodeInfo)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const GeneratedCodeInfo* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const GeneratedCodeInfo>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.GeneratedCodeInfo)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.GeneratedCodeInfo)
+ MergeFrom(*source);
+ }
+}
+
+void GeneratedCodeInfo::MergeFrom(const GeneratedCodeInfo& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.GeneratedCodeInfo)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ annotation_.MergeFrom(from.annotation_);
+ if (from._internal_metadata_.have_unknown_fields()) {
+ mutable_unknown_fields()->MergeFrom(from.unknown_fields());
+ }
+}
+
+void GeneratedCodeInfo::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.GeneratedCodeInfo)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void GeneratedCodeInfo::CopyFrom(const GeneratedCodeInfo& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.GeneratedCodeInfo)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool GeneratedCodeInfo::IsInitialized() const {
+
+ return true;
+}
+
+void GeneratedCodeInfo::Swap(GeneratedCodeInfo* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void GeneratedCodeInfo::InternalSwap(GeneratedCodeInfo* other) {
+ annotation_.UnsafeArenaSwap(&other->annotation_);
+ std::swap(_has_bits_[0], other->_has_bits_[0]);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata GeneratedCodeInfo::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = GeneratedCodeInfo_descriptor_;
+ metadata.reflection = GeneratedCodeInfo_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// GeneratedCodeInfo_Annotation
+
+// repeated int32 path = 1 [packed = true];
+int GeneratedCodeInfo_Annotation::path_size() const {
+ return path_.size();
+}
+void GeneratedCodeInfo_Annotation::clear_path() {
+ path_.Clear();
+}
+ ::google::protobuf::int32 GeneratedCodeInfo_Annotation::path(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.path)
+ return path_.Get(index);
+}
+ void GeneratedCodeInfo_Annotation::set_path(int index, ::google::protobuf::int32 value) {
+ path_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.path)
+}
+ void GeneratedCodeInfo_Annotation::add_path(::google::protobuf::int32 value) {
+ path_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.GeneratedCodeInfo.Annotation.path)
+}
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+GeneratedCodeInfo_Annotation::path() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.GeneratedCodeInfo.Annotation.path)
+ return path_;
+}
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+GeneratedCodeInfo_Annotation::mutable_path() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.GeneratedCodeInfo.Annotation.path)
+ return &path_;
+}
+
+// optional string source_file = 2;
+bool GeneratedCodeInfo_Annotation::has_source_file() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+void GeneratedCodeInfo_Annotation::set_has_source_file() {
+ _has_bits_[0] |= 0x00000002u;
+}
+void GeneratedCodeInfo_Annotation::clear_has_source_file() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+void GeneratedCodeInfo_Annotation::clear_source_file() {
+ source_file_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_source_file();
+}
+ const ::std::string& GeneratedCodeInfo_Annotation::source_file() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+ return source_file_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void GeneratedCodeInfo_Annotation::set_source_file(const ::std::string& value) {
+ set_has_source_file();
+ source_file_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+ void GeneratedCodeInfo_Annotation::set_source_file(const char* value) {
+ set_has_source_file();
+ source_file_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+ void GeneratedCodeInfo_Annotation::set_source_file(const char* value, size_t size) {
+ set_has_source_file();
+ source_file_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+ ::std::string* GeneratedCodeInfo_Annotation::mutable_source_file() {
+ set_has_source_file();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+ return source_file_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* GeneratedCodeInfo_Annotation::release_source_file() {
+ // @@protoc_insertion_point(field_release:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+ clear_has_source_file();
+ return source_file_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void GeneratedCodeInfo_Annotation::set_allocated_source_file(::std::string* source_file) {
+ if (source_file != NULL) {
+ set_has_source_file();
+ } else {
+ clear_has_source_file();
+ }
+ source_file_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), source_file);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+
+// optional int32 begin = 3;
+bool GeneratedCodeInfo_Annotation::has_begin() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+void GeneratedCodeInfo_Annotation::set_has_begin() {
+ _has_bits_[0] |= 0x00000004u;
+}
+void GeneratedCodeInfo_Annotation::clear_has_begin() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+void GeneratedCodeInfo_Annotation::clear_begin() {
+ begin_ = 0;
+ clear_has_begin();
+}
+ ::google::protobuf::int32 GeneratedCodeInfo_Annotation::begin() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.begin)
+ return begin_;
+}
+ void GeneratedCodeInfo_Annotation::set_begin(::google::protobuf::int32 value) {
+ set_has_begin();
+ begin_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.begin)
+}
+
+// optional int32 end = 4;
+bool GeneratedCodeInfo_Annotation::has_end() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+void GeneratedCodeInfo_Annotation::set_has_end() {
+ _has_bits_[0] |= 0x00000008u;
+}
+void GeneratedCodeInfo_Annotation::clear_has_end() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+void GeneratedCodeInfo_Annotation::clear_end() {
+ end_ = 0;
+ clear_has_end();
+}
+ ::google::protobuf::int32 GeneratedCodeInfo_Annotation::end() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.end)
+ return end_;
+}
+ void GeneratedCodeInfo_Annotation::set_end(::google::protobuf::int32 value) {
+ set_has_end();
+ end_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.end)
+}
+
+// -------------------------------------------------------------------
+
+// GeneratedCodeInfo
+
+// repeated .google.protobuf.GeneratedCodeInfo.Annotation annotation = 1;
+int GeneratedCodeInfo::annotation_size() const {
+ return annotation_.size();
+}
+void GeneratedCodeInfo::clear_annotation() {
+ annotation_.Clear();
+}
+const ::google::protobuf::GeneratedCodeInfo_Annotation& GeneratedCodeInfo::annotation(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_.Get(index);
+}
+::google::protobuf::GeneratedCodeInfo_Annotation* GeneratedCodeInfo::mutable_annotation(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_.Mutable(index);
+}
+::google::protobuf::GeneratedCodeInfo_Annotation* GeneratedCodeInfo::add_annotation() {
+ // @@protoc_insertion_point(field_add:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::GeneratedCodeInfo_Annotation >*
+GeneratedCodeInfo::mutable_annotation() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.GeneratedCodeInfo.annotation)
+ return &annotation_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::GeneratedCodeInfo_Annotation >&
+GeneratedCodeInfo::annotation() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.h
new file mode 100644
index 0000000000..5a9e12bcaf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.pb.h
@@ -0,0 +1,8002 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/descriptor.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fdescriptor_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fdescriptor_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/generated_enum_reflection.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+class DescriptorProto;
+class DescriptorProto_ExtensionRange;
+class DescriptorProto_ReservedRange;
+class EnumDescriptorProto;
+class EnumOptions;
+class EnumValueDescriptorProto;
+class EnumValueOptions;
+class FieldDescriptorProto;
+class FieldOptions;
+class FileDescriptorProto;
+class FileDescriptorSet;
+class FileOptions;
+class GeneratedCodeInfo;
+class GeneratedCodeInfo_Annotation;
+class MessageOptions;
+class MethodDescriptorProto;
+class MethodOptions;
+class OneofDescriptorProto;
+class OneofOptions;
+class ServiceDescriptorProto;
+class ServiceOptions;
+class SourceCodeInfo;
+class SourceCodeInfo_Location;
+class UninterpretedOption;
+class UninterpretedOption_NamePart;
+
+enum FieldDescriptorProto_Type {
+ FieldDescriptorProto_Type_TYPE_DOUBLE = 1,
+ FieldDescriptorProto_Type_TYPE_FLOAT = 2,
+ FieldDescriptorProto_Type_TYPE_INT64 = 3,
+ FieldDescriptorProto_Type_TYPE_UINT64 = 4,
+ FieldDescriptorProto_Type_TYPE_INT32 = 5,
+ FieldDescriptorProto_Type_TYPE_FIXED64 = 6,
+ FieldDescriptorProto_Type_TYPE_FIXED32 = 7,
+ FieldDescriptorProto_Type_TYPE_BOOL = 8,
+ FieldDescriptorProto_Type_TYPE_STRING = 9,
+ FieldDescriptorProto_Type_TYPE_GROUP = 10,
+ FieldDescriptorProto_Type_TYPE_MESSAGE = 11,
+ FieldDescriptorProto_Type_TYPE_BYTES = 12,
+ FieldDescriptorProto_Type_TYPE_UINT32 = 13,
+ FieldDescriptorProto_Type_TYPE_ENUM = 14,
+ FieldDescriptorProto_Type_TYPE_SFIXED32 = 15,
+ FieldDescriptorProto_Type_TYPE_SFIXED64 = 16,
+ FieldDescriptorProto_Type_TYPE_SINT32 = 17,
+ FieldDescriptorProto_Type_TYPE_SINT64 = 18
+};
+LIBPROTOBUF_EXPORT bool FieldDescriptorProto_Type_IsValid(int value);
+const FieldDescriptorProto_Type FieldDescriptorProto_Type_Type_MIN = FieldDescriptorProto_Type_TYPE_DOUBLE;
+const FieldDescriptorProto_Type FieldDescriptorProto_Type_Type_MAX = FieldDescriptorProto_Type_TYPE_SINT64;
+const int FieldDescriptorProto_Type_Type_ARRAYSIZE = FieldDescriptorProto_Type_Type_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* FieldDescriptorProto_Type_descriptor();
+inline const ::std::string& FieldDescriptorProto_Type_Name(FieldDescriptorProto_Type value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ FieldDescriptorProto_Type_descriptor(), value);
+}
+inline bool FieldDescriptorProto_Type_Parse(
+ const ::std::string& name, FieldDescriptorProto_Type* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<FieldDescriptorProto_Type>(
+ FieldDescriptorProto_Type_descriptor(), name, value);
+}
+enum FieldDescriptorProto_Label {
+ FieldDescriptorProto_Label_LABEL_OPTIONAL = 1,
+ FieldDescriptorProto_Label_LABEL_REQUIRED = 2,
+ FieldDescriptorProto_Label_LABEL_REPEATED = 3
+};
+LIBPROTOBUF_EXPORT bool FieldDescriptorProto_Label_IsValid(int value);
+const FieldDescriptorProto_Label FieldDescriptorProto_Label_Label_MIN = FieldDescriptorProto_Label_LABEL_OPTIONAL;
+const FieldDescriptorProto_Label FieldDescriptorProto_Label_Label_MAX = FieldDescriptorProto_Label_LABEL_REPEATED;
+const int FieldDescriptorProto_Label_Label_ARRAYSIZE = FieldDescriptorProto_Label_Label_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* FieldDescriptorProto_Label_descriptor();
+inline const ::std::string& FieldDescriptorProto_Label_Name(FieldDescriptorProto_Label value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ FieldDescriptorProto_Label_descriptor(), value);
+}
+inline bool FieldDescriptorProto_Label_Parse(
+ const ::std::string& name, FieldDescriptorProto_Label* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<FieldDescriptorProto_Label>(
+ FieldDescriptorProto_Label_descriptor(), name, value);
+}
+enum FileOptions_OptimizeMode {
+ FileOptions_OptimizeMode_SPEED = 1,
+ FileOptions_OptimizeMode_CODE_SIZE = 2,
+ FileOptions_OptimizeMode_LITE_RUNTIME = 3
+};
+LIBPROTOBUF_EXPORT bool FileOptions_OptimizeMode_IsValid(int value);
+const FileOptions_OptimizeMode FileOptions_OptimizeMode_OptimizeMode_MIN = FileOptions_OptimizeMode_SPEED;
+const FileOptions_OptimizeMode FileOptions_OptimizeMode_OptimizeMode_MAX = FileOptions_OptimizeMode_LITE_RUNTIME;
+const int FileOptions_OptimizeMode_OptimizeMode_ARRAYSIZE = FileOptions_OptimizeMode_OptimizeMode_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* FileOptions_OptimizeMode_descriptor();
+inline const ::std::string& FileOptions_OptimizeMode_Name(FileOptions_OptimizeMode value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ FileOptions_OptimizeMode_descriptor(), value);
+}
+inline bool FileOptions_OptimizeMode_Parse(
+ const ::std::string& name, FileOptions_OptimizeMode* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<FileOptions_OptimizeMode>(
+ FileOptions_OptimizeMode_descriptor(), name, value);
+}
+enum FieldOptions_CType {
+ FieldOptions_CType_STRING = 0,
+ FieldOptions_CType_CORD = 1,
+ FieldOptions_CType_STRING_PIECE = 2
+};
+LIBPROTOBUF_EXPORT bool FieldOptions_CType_IsValid(int value);
+const FieldOptions_CType FieldOptions_CType_CType_MIN = FieldOptions_CType_STRING;
+const FieldOptions_CType FieldOptions_CType_CType_MAX = FieldOptions_CType_STRING_PIECE;
+const int FieldOptions_CType_CType_ARRAYSIZE = FieldOptions_CType_CType_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* FieldOptions_CType_descriptor();
+inline const ::std::string& FieldOptions_CType_Name(FieldOptions_CType value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ FieldOptions_CType_descriptor(), value);
+}
+inline bool FieldOptions_CType_Parse(
+ const ::std::string& name, FieldOptions_CType* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<FieldOptions_CType>(
+ FieldOptions_CType_descriptor(), name, value);
+}
+enum FieldOptions_JSType {
+ FieldOptions_JSType_JS_NORMAL = 0,
+ FieldOptions_JSType_JS_STRING = 1,
+ FieldOptions_JSType_JS_NUMBER = 2
+};
+LIBPROTOBUF_EXPORT bool FieldOptions_JSType_IsValid(int value);
+const FieldOptions_JSType FieldOptions_JSType_JSType_MIN = FieldOptions_JSType_JS_NORMAL;
+const FieldOptions_JSType FieldOptions_JSType_JSType_MAX = FieldOptions_JSType_JS_NUMBER;
+const int FieldOptions_JSType_JSType_ARRAYSIZE = FieldOptions_JSType_JSType_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* FieldOptions_JSType_descriptor();
+inline const ::std::string& FieldOptions_JSType_Name(FieldOptions_JSType value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ FieldOptions_JSType_descriptor(), value);
+}
+inline bool FieldOptions_JSType_Parse(
+ const ::std::string& name, FieldOptions_JSType* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<FieldOptions_JSType>(
+ FieldOptions_JSType_descriptor(), name, value);
+}
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT FileDescriptorSet : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.FileDescriptorSet) */ {
+ public:
+ FileDescriptorSet();
+ virtual ~FileDescriptorSet();
+
+ FileDescriptorSet(const FileDescriptorSet& from);
+
+ inline FileDescriptorSet& operator=(const FileDescriptorSet& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const FileDescriptorSet& default_instance();
+
+ void Swap(FileDescriptorSet* other);
+
+ // implements Message ----------------------------------------------
+
+ inline FileDescriptorSet* New() const { return New(NULL); }
+
+ FileDescriptorSet* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const FileDescriptorSet& from);
+ void MergeFrom(const FileDescriptorSet& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(FileDescriptorSet* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // repeated .google.protobuf.FileDescriptorProto file = 1;
+ int file_size() const;
+ void clear_file();
+ static const int kFileFieldNumber = 1;
+ const ::google::protobuf::FileDescriptorProto& file(int index) const;
+ ::google::protobuf::FileDescriptorProto* mutable_file(int index);
+ ::google::protobuf::FileDescriptorProto* add_file();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >*
+ mutable_file();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >&
+ file() const;
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.FileDescriptorSet)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto > file_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static FileDescriptorSet* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT FileDescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.FileDescriptorProto) */ {
+ public:
+ FileDescriptorProto();
+ virtual ~FileDescriptorProto();
+
+ FileDescriptorProto(const FileDescriptorProto& from);
+
+ inline FileDescriptorProto& operator=(const FileDescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const FileDescriptorProto& default_instance();
+
+ void Swap(FileDescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline FileDescriptorProto* New() const { return New(NULL); }
+
+ FileDescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const FileDescriptorProto& from);
+ void MergeFrom(const FileDescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(FileDescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional string package = 2;
+ bool has_package() const;
+ void clear_package();
+ static const int kPackageFieldNumber = 2;
+ const ::std::string& package() const;
+ void set_package(const ::std::string& value);
+ void set_package(const char* value);
+ void set_package(const char* value, size_t size);
+ ::std::string* mutable_package();
+ ::std::string* release_package();
+ void set_allocated_package(::std::string* package);
+
+ // repeated string dependency = 3;
+ int dependency_size() const;
+ void clear_dependency();
+ static const int kDependencyFieldNumber = 3;
+ const ::std::string& dependency(int index) const;
+ ::std::string* mutable_dependency(int index);
+ void set_dependency(int index, const ::std::string& value);
+ void set_dependency(int index, const char* value);
+ void set_dependency(int index, const char* value, size_t size);
+ ::std::string* add_dependency();
+ void add_dependency(const ::std::string& value);
+ void add_dependency(const char* value);
+ void add_dependency(const char* value, size_t size);
+ const ::google::protobuf::RepeatedPtrField< ::std::string>& dependency() const;
+ ::google::protobuf::RepeatedPtrField< ::std::string>* mutable_dependency();
+
+ // repeated int32 public_dependency = 10;
+ int public_dependency_size() const;
+ void clear_public_dependency();
+ static const int kPublicDependencyFieldNumber = 10;
+ ::google::protobuf::int32 public_dependency(int index) const;
+ void set_public_dependency(int index, ::google::protobuf::int32 value);
+ void add_public_dependency(::google::protobuf::int32 value);
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+ public_dependency() const;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+ mutable_public_dependency();
+
+ // repeated int32 weak_dependency = 11;
+ int weak_dependency_size() const;
+ void clear_weak_dependency();
+ static const int kWeakDependencyFieldNumber = 11;
+ ::google::protobuf::int32 weak_dependency(int index) const;
+ void set_weak_dependency(int index, ::google::protobuf::int32 value);
+ void add_weak_dependency(::google::protobuf::int32 value);
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+ weak_dependency() const;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+ mutable_weak_dependency();
+
+ // repeated .google.protobuf.DescriptorProto message_type = 4;
+ int message_type_size() const;
+ void clear_message_type();
+ static const int kMessageTypeFieldNumber = 4;
+ const ::google::protobuf::DescriptorProto& message_type(int index) const;
+ ::google::protobuf::DescriptorProto* mutable_message_type(int index);
+ ::google::protobuf::DescriptorProto* add_message_type();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >*
+ mutable_message_type();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >&
+ message_type() const;
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 5;
+ int enum_type_size() const;
+ void clear_enum_type();
+ static const int kEnumTypeFieldNumber = 5;
+ const ::google::protobuf::EnumDescriptorProto& enum_type(int index) const;
+ ::google::protobuf::EnumDescriptorProto* mutable_enum_type(int index);
+ ::google::protobuf::EnumDescriptorProto* add_enum_type();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >*
+ mutable_enum_type();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >&
+ enum_type() const;
+
+ // repeated .google.protobuf.ServiceDescriptorProto service = 6;
+ int service_size() const;
+ void clear_service();
+ static const int kServiceFieldNumber = 6;
+ const ::google::protobuf::ServiceDescriptorProto& service(int index) const;
+ ::google::protobuf::ServiceDescriptorProto* mutable_service(int index);
+ ::google::protobuf::ServiceDescriptorProto* add_service();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::ServiceDescriptorProto >*
+ mutable_service();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::ServiceDescriptorProto >&
+ service() const;
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 7;
+ int extension_size() const;
+ void clear_extension();
+ static const int kExtensionFieldNumber = 7;
+ const ::google::protobuf::FieldDescriptorProto& extension(int index) const;
+ ::google::protobuf::FieldDescriptorProto* mutable_extension(int index);
+ ::google::protobuf::FieldDescriptorProto* add_extension();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+ mutable_extension();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+ extension() const;
+
+ // optional .google.protobuf.FileOptions options = 8;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 8;
+ const ::google::protobuf::FileOptions& options() const;
+ ::google::protobuf::FileOptions* mutable_options();
+ ::google::protobuf::FileOptions* release_options();
+ void set_allocated_options(::google::protobuf::FileOptions* options);
+
+ // optional .google.protobuf.SourceCodeInfo source_code_info = 9;
+ bool has_source_code_info() const;
+ void clear_source_code_info();
+ static const int kSourceCodeInfoFieldNumber = 9;
+ const ::google::protobuf::SourceCodeInfo& source_code_info() const;
+ ::google::protobuf::SourceCodeInfo* mutable_source_code_info();
+ ::google::protobuf::SourceCodeInfo* release_source_code_info();
+ void set_allocated_source_code_info(::google::protobuf::SourceCodeInfo* source_code_info);
+
+ // optional string syntax = 12;
+ bool has_syntax() const;
+ void clear_syntax();
+ static const int kSyntaxFieldNumber = 12;
+ const ::std::string& syntax() const;
+ void set_syntax(const ::std::string& value);
+ void set_syntax(const char* value);
+ void set_syntax(const char* value, size_t size);
+ ::std::string* mutable_syntax();
+ ::std::string* release_syntax();
+ void set_allocated_syntax(::std::string* syntax);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.FileDescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_package();
+ inline void clear_has_package();
+ inline void set_has_options();
+ inline void clear_has_options();
+ inline void set_has_source_code_info();
+ inline void clear_has_source_code_info();
+ inline void set_has_syntax();
+ inline void clear_has_syntax();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::internal::ArenaStringPtr package_;
+ ::google::protobuf::RepeatedPtrField< ::std::string> dependency_;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 > public_dependency_;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 > weak_dependency_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto > message_type_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto > enum_type_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::ServiceDescriptorProto > service_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto > extension_;
+ ::google::protobuf::FileOptions* options_;
+ ::google::protobuf::SourceCodeInfo* source_code_info_;
+ ::google::protobuf::internal::ArenaStringPtr syntax_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static FileDescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT DescriptorProto_ExtensionRange : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.DescriptorProto.ExtensionRange) */ {
+ public:
+ DescriptorProto_ExtensionRange();
+ virtual ~DescriptorProto_ExtensionRange();
+
+ DescriptorProto_ExtensionRange(const DescriptorProto_ExtensionRange& from);
+
+ inline DescriptorProto_ExtensionRange& operator=(const DescriptorProto_ExtensionRange& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const DescriptorProto_ExtensionRange& default_instance();
+
+ void Swap(DescriptorProto_ExtensionRange* other);
+
+ // implements Message ----------------------------------------------
+
+ inline DescriptorProto_ExtensionRange* New() const { return New(NULL); }
+
+ DescriptorProto_ExtensionRange* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const DescriptorProto_ExtensionRange& from);
+ void MergeFrom(const DescriptorProto_ExtensionRange& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(DescriptorProto_ExtensionRange* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional int32 start = 1;
+ bool has_start() const;
+ void clear_start();
+ static const int kStartFieldNumber = 1;
+ ::google::protobuf::int32 start() const;
+ void set_start(::google::protobuf::int32 value);
+
+ // optional int32 end = 2;
+ bool has_end() const;
+ void clear_end();
+ static const int kEndFieldNumber = 2;
+ ::google::protobuf::int32 end() const;
+ void set_end(::google::protobuf::int32 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.DescriptorProto.ExtensionRange)
+ private:
+ inline void set_has_start();
+ inline void clear_has_start();
+ inline void set_has_end();
+ inline void clear_has_end();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::int32 start_;
+ ::google::protobuf::int32 end_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static DescriptorProto_ExtensionRange* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT DescriptorProto_ReservedRange : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.DescriptorProto.ReservedRange) */ {
+ public:
+ DescriptorProto_ReservedRange();
+ virtual ~DescriptorProto_ReservedRange();
+
+ DescriptorProto_ReservedRange(const DescriptorProto_ReservedRange& from);
+
+ inline DescriptorProto_ReservedRange& operator=(const DescriptorProto_ReservedRange& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const DescriptorProto_ReservedRange& default_instance();
+
+ void Swap(DescriptorProto_ReservedRange* other);
+
+ // implements Message ----------------------------------------------
+
+ inline DescriptorProto_ReservedRange* New() const { return New(NULL); }
+
+ DescriptorProto_ReservedRange* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const DescriptorProto_ReservedRange& from);
+ void MergeFrom(const DescriptorProto_ReservedRange& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(DescriptorProto_ReservedRange* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional int32 start = 1;
+ bool has_start() const;
+ void clear_start();
+ static const int kStartFieldNumber = 1;
+ ::google::protobuf::int32 start() const;
+ void set_start(::google::protobuf::int32 value);
+
+ // optional int32 end = 2;
+ bool has_end() const;
+ void clear_end();
+ static const int kEndFieldNumber = 2;
+ ::google::protobuf::int32 end() const;
+ void set_end(::google::protobuf::int32 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.DescriptorProto.ReservedRange)
+ private:
+ inline void set_has_start();
+ inline void clear_has_start();
+ inline void set_has_end();
+ inline void clear_has_end();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::int32 start_;
+ ::google::protobuf::int32 end_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static DescriptorProto_ReservedRange* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT DescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.DescriptorProto) */ {
+ public:
+ DescriptorProto();
+ virtual ~DescriptorProto();
+
+ DescriptorProto(const DescriptorProto& from);
+
+ inline DescriptorProto& operator=(const DescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const DescriptorProto& default_instance();
+
+ void Swap(DescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline DescriptorProto* New() const { return New(NULL); }
+
+ DescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const DescriptorProto& from);
+ void MergeFrom(const DescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(DescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef DescriptorProto_ExtensionRange ExtensionRange;
+ typedef DescriptorProto_ReservedRange ReservedRange;
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // repeated .google.protobuf.FieldDescriptorProto field = 2;
+ int field_size() const;
+ void clear_field();
+ static const int kFieldFieldNumber = 2;
+ const ::google::protobuf::FieldDescriptorProto& field(int index) const;
+ ::google::protobuf::FieldDescriptorProto* mutable_field(int index);
+ ::google::protobuf::FieldDescriptorProto* add_field();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+ mutable_field();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+ field() const;
+
+ // repeated .google.protobuf.FieldDescriptorProto extension = 6;
+ int extension_size() const;
+ void clear_extension();
+ static const int kExtensionFieldNumber = 6;
+ const ::google::protobuf::FieldDescriptorProto& extension(int index) const;
+ ::google::protobuf::FieldDescriptorProto* mutable_extension(int index);
+ ::google::protobuf::FieldDescriptorProto* add_extension();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+ mutable_extension();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+ extension() const;
+
+ // repeated .google.protobuf.DescriptorProto nested_type = 3;
+ int nested_type_size() const;
+ void clear_nested_type();
+ static const int kNestedTypeFieldNumber = 3;
+ const ::google::protobuf::DescriptorProto& nested_type(int index) const;
+ ::google::protobuf::DescriptorProto* mutable_nested_type(int index);
+ ::google::protobuf::DescriptorProto* add_nested_type();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >*
+ mutable_nested_type();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >&
+ nested_type() const;
+
+ // repeated .google.protobuf.EnumDescriptorProto enum_type = 4;
+ int enum_type_size() const;
+ void clear_enum_type();
+ static const int kEnumTypeFieldNumber = 4;
+ const ::google::protobuf::EnumDescriptorProto& enum_type(int index) const;
+ ::google::protobuf::EnumDescriptorProto* mutable_enum_type(int index);
+ ::google::protobuf::EnumDescriptorProto* add_enum_type();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >*
+ mutable_enum_type();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >&
+ enum_type() const;
+
+ // repeated .google.protobuf.DescriptorProto.ExtensionRange extension_range = 5;
+ int extension_range_size() const;
+ void clear_extension_range();
+ static const int kExtensionRangeFieldNumber = 5;
+ const ::google::protobuf::DescriptorProto_ExtensionRange& extension_range(int index) const;
+ ::google::protobuf::DescriptorProto_ExtensionRange* mutable_extension_range(int index);
+ ::google::protobuf::DescriptorProto_ExtensionRange* add_extension_range();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ExtensionRange >*
+ mutable_extension_range();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ExtensionRange >&
+ extension_range() const;
+
+ // repeated .google.protobuf.OneofDescriptorProto oneof_decl = 8;
+ int oneof_decl_size() const;
+ void clear_oneof_decl();
+ static const int kOneofDeclFieldNumber = 8;
+ const ::google::protobuf::OneofDescriptorProto& oneof_decl(int index) const;
+ ::google::protobuf::OneofDescriptorProto* mutable_oneof_decl(int index);
+ ::google::protobuf::OneofDescriptorProto* add_oneof_decl();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::OneofDescriptorProto >*
+ mutable_oneof_decl();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::OneofDescriptorProto >&
+ oneof_decl() const;
+
+ // optional .google.protobuf.MessageOptions options = 7;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 7;
+ const ::google::protobuf::MessageOptions& options() const;
+ ::google::protobuf::MessageOptions* mutable_options();
+ ::google::protobuf::MessageOptions* release_options();
+ void set_allocated_options(::google::protobuf::MessageOptions* options);
+
+ // repeated .google.protobuf.DescriptorProto.ReservedRange reserved_range = 9;
+ int reserved_range_size() const;
+ void clear_reserved_range();
+ static const int kReservedRangeFieldNumber = 9;
+ const ::google::protobuf::DescriptorProto_ReservedRange& reserved_range(int index) const;
+ ::google::protobuf::DescriptorProto_ReservedRange* mutable_reserved_range(int index);
+ ::google::protobuf::DescriptorProto_ReservedRange* add_reserved_range();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ReservedRange >*
+ mutable_reserved_range();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ReservedRange >&
+ reserved_range() const;
+
+ // repeated string reserved_name = 10;
+ int reserved_name_size() const;
+ void clear_reserved_name();
+ static const int kReservedNameFieldNumber = 10;
+ const ::std::string& reserved_name(int index) const;
+ ::std::string* mutable_reserved_name(int index);
+ void set_reserved_name(int index, const ::std::string& value);
+ void set_reserved_name(int index, const char* value);
+ void set_reserved_name(int index, const char* value, size_t size);
+ ::std::string* add_reserved_name();
+ void add_reserved_name(const ::std::string& value);
+ void add_reserved_name(const char* value);
+ void add_reserved_name(const char* value, size_t size);
+ const ::google::protobuf::RepeatedPtrField< ::std::string>& reserved_name() const;
+ ::google::protobuf::RepeatedPtrField< ::std::string>* mutable_reserved_name();
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.DescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_options();
+ inline void clear_has_options();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto > field_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto > extension_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto > nested_type_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto > enum_type_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ExtensionRange > extension_range_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::OneofDescriptorProto > oneof_decl_;
+ ::google::protobuf::MessageOptions* options_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ReservedRange > reserved_range_;
+ ::google::protobuf::RepeatedPtrField< ::std::string> reserved_name_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static DescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT FieldDescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.FieldDescriptorProto) */ {
+ public:
+ FieldDescriptorProto();
+ virtual ~FieldDescriptorProto();
+
+ FieldDescriptorProto(const FieldDescriptorProto& from);
+
+ inline FieldDescriptorProto& operator=(const FieldDescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const FieldDescriptorProto& default_instance();
+
+ void Swap(FieldDescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline FieldDescriptorProto* New() const { return New(NULL); }
+
+ FieldDescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const FieldDescriptorProto& from);
+ void MergeFrom(const FieldDescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(FieldDescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef FieldDescriptorProto_Type Type;
+ static const Type TYPE_DOUBLE =
+ FieldDescriptorProto_Type_TYPE_DOUBLE;
+ static const Type TYPE_FLOAT =
+ FieldDescriptorProto_Type_TYPE_FLOAT;
+ static const Type TYPE_INT64 =
+ FieldDescriptorProto_Type_TYPE_INT64;
+ static const Type TYPE_UINT64 =
+ FieldDescriptorProto_Type_TYPE_UINT64;
+ static const Type TYPE_INT32 =
+ FieldDescriptorProto_Type_TYPE_INT32;
+ static const Type TYPE_FIXED64 =
+ FieldDescriptorProto_Type_TYPE_FIXED64;
+ static const Type TYPE_FIXED32 =
+ FieldDescriptorProto_Type_TYPE_FIXED32;
+ static const Type TYPE_BOOL =
+ FieldDescriptorProto_Type_TYPE_BOOL;
+ static const Type TYPE_STRING =
+ FieldDescriptorProto_Type_TYPE_STRING;
+ static const Type TYPE_GROUP =
+ FieldDescriptorProto_Type_TYPE_GROUP;
+ static const Type TYPE_MESSAGE =
+ FieldDescriptorProto_Type_TYPE_MESSAGE;
+ static const Type TYPE_BYTES =
+ FieldDescriptorProto_Type_TYPE_BYTES;
+ static const Type TYPE_UINT32 =
+ FieldDescriptorProto_Type_TYPE_UINT32;
+ static const Type TYPE_ENUM =
+ FieldDescriptorProto_Type_TYPE_ENUM;
+ static const Type TYPE_SFIXED32 =
+ FieldDescriptorProto_Type_TYPE_SFIXED32;
+ static const Type TYPE_SFIXED64 =
+ FieldDescriptorProto_Type_TYPE_SFIXED64;
+ static const Type TYPE_SINT32 =
+ FieldDescriptorProto_Type_TYPE_SINT32;
+ static const Type TYPE_SINT64 =
+ FieldDescriptorProto_Type_TYPE_SINT64;
+ static inline bool Type_IsValid(int value) {
+ return FieldDescriptorProto_Type_IsValid(value);
+ }
+ static const Type Type_MIN =
+ FieldDescriptorProto_Type_Type_MIN;
+ static const Type Type_MAX =
+ FieldDescriptorProto_Type_Type_MAX;
+ static const int Type_ARRAYSIZE =
+ FieldDescriptorProto_Type_Type_ARRAYSIZE;
+ static inline const ::google::protobuf::EnumDescriptor*
+ Type_descriptor() {
+ return FieldDescriptorProto_Type_descriptor();
+ }
+ static inline const ::std::string& Type_Name(Type value) {
+ return FieldDescriptorProto_Type_Name(value);
+ }
+ static inline bool Type_Parse(const ::std::string& name,
+ Type* value) {
+ return FieldDescriptorProto_Type_Parse(name, value);
+ }
+
+ typedef FieldDescriptorProto_Label Label;
+ static const Label LABEL_OPTIONAL =
+ FieldDescriptorProto_Label_LABEL_OPTIONAL;
+ static const Label LABEL_REQUIRED =
+ FieldDescriptorProto_Label_LABEL_REQUIRED;
+ static const Label LABEL_REPEATED =
+ FieldDescriptorProto_Label_LABEL_REPEATED;
+ static inline bool Label_IsValid(int value) {
+ return FieldDescriptorProto_Label_IsValid(value);
+ }
+ static const Label Label_MIN =
+ FieldDescriptorProto_Label_Label_MIN;
+ static const Label Label_MAX =
+ FieldDescriptorProto_Label_Label_MAX;
+ static const int Label_ARRAYSIZE =
+ FieldDescriptorProto_Label_Label_ARRAYSIZE;
+ static inline const ::google::protobuf::EnumDescriptor*
+ Label_descriptor() {
+ return FieldDescriptorProto_Label_descriptor();
+ }
+ static inline const ::std::string& Label_Name(Label value) {
+ return FieldDescriptorProto_Label_Name(value);
+ }
+ static inline bool Label_Parse(const ::std::string& name,
+ Label* value) {
+ return FieldDescriptorProto_Label_Parse(name, value);
+ }
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional int32 number = 3;
+ bool has_number() const;
+ void clear_number();
+ static const int kNumberFieldNumber = 3;
+ ::google::protobuf::int32 number() const;
+ void set_number(::google::protobuf::int32 value);
+
+ // optional .google.protobuf.FieldDescriptorProto.Label label = 4;
+ bool has_label() const;
+ void clear_label();
+ static const int kLabelFieldNumber = 4;
+ ::google::protobuf::FieldDescriptorProto_Label label() const;
+ void set_label(::google::protobuf::FieldDescriptorProto_Label value);
+
+ // optional .google.protobuf.FieldDescriptorProto.Type type = 5;
+ bool has_type() const;
+ void clear_type();
+ static const int kTypeFieldNumber = 5;
+ ::google::protobuf::FieldDescriptorProto_Type type() const;
+ void set_type(::google::protobuf::FieldDescriptorProto_Type value);
+
+ // optional string type_name = 6;
+ bool has_type_name() const;
+ void clear_type_name();
+ static const int kTypeNameFieldNumber = 6;
+ const ::std::string& type_name() const;
+ void set_type_name(const ::std::string& value);
+ void set_type_name(const char* value);
+ void set_type_name(const char* value, size_t size);
+ ::std::string* mutable_type_name();
+ ::std::string* release_type_name();
+ void set_allocated_type_name(::std::string* type_name);
+
+ // optional string extendee = 2;
+ bool has_extendee() const;
+ void clear_extendee();
+ static const int kExtendeeFieldNumber = 2;
+ const ::std::string& extendee() const;
+ void set_extendee(const ::std::string& value);
+ void set_extendee(const char* value);
+ void set_extendee(const char* value, size_t size);
+ ::std::string* mutable_extendee();
+ ::std::string* release_extendee();
+ void set_allocated_extendee(::std::string* extendee);
+
+ // optional string default_value = 7;
+ bool has_default_value() const;
+ void clear_default_value();
+ static const int kDefaultValueFieldNumber = 7;
+ const ::std::string& default_value() const;
+ void set_default_value(const ::std::string& value);
+ void set_default_value(const char* value);
+ void set_default_value(const char* value, size_t size);
+ ::std::string* mutable_default_value();
+ ::std::string* release_default_value();
+ void set_allocated_default_value(::std::string* default_value);
+
+ // optional int32 oneof_index = 9;
+ bool has_oneof_index() const;
+ void clear_oneof_index();
+ static const int kOneofIndexFieldNumber = 9;
+ ::google::protobuf::int32 oneof_index() const;
+ void set_oneof_index(::google::protobuf::int32 value);
+
+ // optional string json_name = 10;
+ bool has_json_name() const;
+ void clear_json_name();
+ static const int kJsonNameFieldNumber = 10;
+ const ::std::string& json_name() const;
+ void set_json_name(const ::std::string& value);
+ void set_json_name(const char* value);
+ void set_json_name(const char* value, size_t size);
+ ::std::string* mutable_json_name();
+ ::std::string* release_json_name();
+ void set_allocated_json_name(::std::string* json_name);
+
+ // optional .google.protobuf.FieldOptions options = 8;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 8;
+ const ::google::protobuf::FieldOptions& options() const;
+ ::google::protobuf::FieldOptions* mutable_options();
+ ::google::protobuf::FieldOptions* release_options();
+ void set_allocated_options(::google::protobuf::FieldOptions* options);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.FieldDescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_number();
+ inline void clear_has_number();
+ inline void set_has_label();
+ inline void clear_has_label();
+ inline void set_has_type();
+ inline void clear_has_type();
+ inline void set_has_type_name();
+ inline void clear_has_type_name();
+ inline void set_has_extendee();
+ inline void clear_has_extendee();
+ inline void set_has_default_value();
+ inline void clear_has_default_value();
+ inline void set_has_oneof_index();
+ inline void clear_has_oneof_index();
+ inline void set_has_json_name();
+ inline void clear_has_json_name();
+ inline void set_has_options();
+ inline void clear_has_options();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::int32 number_;
+ int label_;
+ ::google::protobuf::internal::ArenaStringPtr type_name_;
+ ::google::protobuf::internal::ArenaStringPtr extendee_;
+ int type_;
+ ::google::protobuf::int32 oneof_index_;
+ ::google::protobuf::internal::ArenaStringPtr default_value_;
+ ::google::protobuf::internal::ArenaStringPtr json_name_;
+ ::google::protobuf::FieldOptions* options_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static FieldDescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT OneofDescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.OneofDescriptorProto) */ {
+ public:
+ OneofDescriptorProto();
+ virtual ~OneofDescriptorProto();
+
+ OneofDescriptorProto(const OneofDescriptorProto& from);
+
+ inline OneofDescriptorProto& operator=(const OneofDescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const OneofDescriptorProto& default_instance();
+
+ void Swap(OneofDescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline OneofDescriptorProto* New() const { return New(NULL); }
+
+ OneofDescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const OneofDescriptorProto& from);
+ void MergeFrom(const OneofDescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(OneofDescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional .google.protobuf.OneofOptions options = 2;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 2;
+ const ::google::protobuf::OneofOptions& options() const;
+ ::google::protobuf::OneofOptions* mutable_options();
+ ::google::protobuf::OneofOptions* release_options();
+ void set_allocated_options(::google::protobuf::OneofOptions* options);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.OneofDescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_options();
+ inline void clear_has_options();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::OneofOptions* options_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static OneofDescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT EnumDescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.EnumDescriptorProto) */ {
+ public:
+ EnumDescriptorProto();
+ virtual ~EnumDescriptorProto();
+
+ EnumDescriptorProto(const EnumDescriptorProto& from);
+
+ inline EnumDescriptorProto& operator=(const EnumDescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const EnumDescriptorProto& default_instance();
+
+ void Swap(EnumDescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline EnumDescriptorProto* New() const { return New(NULL); }
+
+ EnumDescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const EnumDescriptorProto& from);
+ void MergeFrom(const EnumDescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(EnumDescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // repeated .google.protobuf.EnumValueDescriptorProto value = 2;
+ int value_size() const;
+ void clear_value();
+ static const int kValueFieldNumber = 2;
+ const ::google::protobuf::EnumValueDescriptorProto& value(int index) const;
+ ::google::protobuf::EnumValueDescriptorProto* mutable_value(int index);
+ ::google::protobuf::EnumValueDescriptorProto* add_value();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValueDescriptorProto >*
+ mutable_value();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValueDescriptorProto >&
+ value() const;
+
+ // optional .google.protobuf.EnumOptions options = 3;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 3;
+ const ::google::protobuf::EnumOptions& options() const;
+ ::google::protobuf::EnumOptions* mutable_options();
+ ::google::protobuf::EnumOptions* release_options();
+ void set_allocated_options(::google::protobuf::EnumOptions* options);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.EnumDescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_options();
+ inline void clear_has_options();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValueDescriptorProto > value_;
+ ::google::protobuf::EnumOptions* options_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static EnumDescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT EnumValueDescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.EnumValueDescriptorProto) */ {
+ public:
+ EnumValueDescriptorProto();
+ virtual ~EnumValueDescriptorProto();
+
+ EnumValueDescriptorProto(const EnumValueDescriptorProto& from);
+
+ inline EnumValueDescriptorProto& operator=(const EnumValueDescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const EnumValueDescriptorProto& default_instance();
+
+ void Swap(EnumValueDescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline EnumValueDescriptorProto* New() const { return New(NULL); }
+
+ EnumValueDescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const EnumValueDescriptorProto& from);
+ void MergeFrom(const EnumValueDescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(EnumValueDescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional int32 number = 2;
+ bool has_number() const;
+ void clear_number();
+ static const int kNumberFieldNumber = 2;
+ ::google::protobuf::int32 number() const;
+ void set_number(::google::protobuf::int32 value);
+
+ // optional .google.protobuf.EnumValueOptions options = 3;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 3;
+ const ::google::protobuf::EnumValueOptions& options() const;
+ ::google::protobuf::EnumValueOptions* mutable_options();
+ ::google::protobuf::EnumValueOptions* release_options();
+ void set_allocated_options(::google::protobuf::EnumValueOptions* options);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.EnumValueDescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_number();
+ inline void clear_has_number();
+ inline void set_has_options();
+ inline void clear_has_options();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::EnumValueOptions* options_;
+ ::google::protobuf::int32 number_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static EnumValueDescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT ServiceDescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.ServiceDescriptorProto) */ {
+ public:
+ ServiceDescriptorProto();
+ virtual ~ServiceDescriptorProto();
+
+ ServiceDescriptorProto(const ServiceDescriptorProto& from);
+
+ inline ServiceDescriptorProto& operator=(const ServiceDescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const ServiceDescriptorProto& default_instance();
+
+ void Swap(ServiceDescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline ServiceDescriptorProto* New() const { return New(NULL); }
+
+ ServiceDescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const ServiceDescriptorProto& from);
+ void MergeFrom(const ServiceDescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(ServiceDescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // repeated .google.protobuf.MethodDescriptorProto method = 2;
+ int method_size() const;
+ void clear_method();
+ static const int kMethodFieldNumber = 2;
+ const ::google::protobuf::MethodDescriptorProto& method(int index) const;
+ ::google::protobuf::MethodDescriptorProto* mutable_method(int index);
+ ::google::protobuf::MethodDescriptorProto* add_method();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::MethodDescriptorProto >*
+ mutable_method();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::MethodDescriptorProto >&
+ method() const;
+
+ // optional .google.protobuf.ServiceOptions options = 3;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 3;
+ const ::google::protobuf::ServiceOptions& options() const;
+ ::google::protobuf::ServiceOptions* mutable_options();
+ ::google::protobuf::ServiceOptions* release_options();
+ void set_allocated_options(::google::protobuf::ServiceOptions* options);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.ServiceDescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_options();
+ inline void clear_has_options();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::MethodDescriptorProto > method_;
+ ::google::protobuf::ServiceOptions* options_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static ServiceDescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT MethodDescriptorProto : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.MethodDescriptorProto) */ {
+ public:
+ MethodDescriptorProto();
+ virtual ~MethodDescriptorProto();
+
+ MethodDescriptorProto(const MethodDescriptorProto& from);
+
+ inline MethodDescriptorProto& operator=(const MethodDescriptorProto& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const MethodDescriptorProto& default_instance();
+
+ void Swap(MethodDescriptorProto* other);
+
+ // implements Message ----------------------------------------------
+
+ inline MethodDescriptorProto* New() const { return New(NULL); }
+
+ MethodDescriptorProto* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const MethodDescriptorProto& from);
+ void MergeFrom(const MethodDescriptorProto& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(MethodDescriptorProto* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ bool has_name() const;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional string input_type = 2;
+ bool has_input_type() const;
+ void clear_input_type();
+ static const int kInputTypeFieldNumber = 2;
+ const ::std::string& input_type() const;
+ void set_input_type(const ::std::string& value);
+ void set_input_type(const char* value);
+ void set_input_type(const char* value, size_t size);
+ ::std::string* mutable_input_type();
+ ::std::string* release_input_type();
+ void set_allocated_input_type(::std::string* input_type);
+
+ // optional string output_type = 3;
+ bool has_output_type() const;
+ void clear_output_type();
+ static const int kOutputTypeFieldNumber = 3;
+ const ::std::string& output_type() const;
+ void set_output_type(const ::std::string& value);
+ void set_output_type(const char* value);
+ void set_output_type(const char* value, size_t size);
+ ::std::string* mutable_output_type();
+ ::std::string* release_output_type();
+ void set_allocated_output_type(::std::string* output_type);
+
+ // optional .google.protobuf.MethodOptions options = 4;
+ bool has_options() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 4;
+ const ::google::protobuf::MethodOptions& options() const;
+ ::google::protobuf::MethodOptions* mutable_options();
+ ::google::protobuf::MethodOptions* release_options();
+ void set_allocated_options(::google::protobuf::MethodOptions* options);
+
+ // optional bool client_streaming = 5 [default = false];
+ bool has_client_streaming() const;
+ void clear_client_streaming();
+ static const int kClientStreamingFieldNumber = 5;
+ bool client_streaming() const;
+ void set_client_streaming(bool value);
+
+ // optional bool server_streaming = 6 [default = false];
+ bool has_server_streaming() const;
+ void clear_server_streaming();
+ static const int kServerStreamingFieldNumber = 6;
+ bool server_streaming() const;
+ void set_server_streaming(bool value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.MethodDescriptorProto)
+ private:
+ inline void set_has_name();
+ inline void clear_has_name();
+ inline void set_has_input_type();
+ inline void clear_has_input_type();
+ inline void set_has_output_type();
+ inline void clear_has_output_type();
+ inline void set_has_options();
+ inline void clear_has_options();
+ inline void set_has_client_streaming();
+ inline void clear_has_client_streaming();
+ inline void set_has_server_streaming();
+ inline void clear_has_server_streaming();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::internal::ArenaStringPtr input_type_;
+ ::google::protobuf::internal::ArenaStringPtr output_type_;
+ ::google::protobuf::MethodOptions* options_;
+ bool client_streaming_;
+ bool server_streaming_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static MethodDescriptorProto* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT FileOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.FileOptions) */ {
+ public:
+ FileOptions();
+ virtual ~FileOptions();
+
+ FileOptions(const FileOptions& from);
+
+ inline FileOptions& operator=(const FileOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const FileOptions& default_instance();
+
+ void Swap(FileOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline FileOptions* New() const { return New(NULL); }
+
+ FileOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const FileOptions& from);
+ void MergeFrom(const FileOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(FileOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef FileOptions_OptimizeMode OptimizeMode;
+ static const OptimizeMode SPEED =
+ FileOptions_OptimizeMode_SPEED;
+ static const OptimizeMode CODE_SIZE =
+ FileOptions_OptimizeMode_CODE_SIZE;
+ static const OptimizeMode LITE_RUNTIME =
+ FileOptions_OptimizeMode_LITE_RUNTIME;
+ static inline bool OptimizeMode_IsValid(int value) {
+ return FileOptions_OptimizeMode_IsValid(value);
+ }
+ static const OptimizeMode OptimizeMode_MIN =
+ FileOptions_OptimizeMode_OptimizeMode_MIN;
+ static const OptimizeMode OptimizeMode_MAX =
+ FileOptions_OptimizeMode_OptimizeMode_MAX;
+ static const int OptimizeMode_ARRAYSIZE =
+ FileOptions_OptimizeMode_OptimizeMode_ARRAYSIZE;
+ static inline const ::google::protobuf::EnumDescriptor*
+ OptimizeMode_descriptor() {
+ return FileOptions_OptimizeMode_descriptor();
+ }
+ static inline const ::std::string& OptimizeMode_Name(OptimizeMode value) {
+ return FileOptions_OptimizeMode_Name(value);
+ }
+ static inline bool OptimizeMode_Parse(const ::std::string& name,
+ OptimizeMode* value) {
+ return FileOptions_OptimizeMode_Parse(name, value);
+ }
+
+ // accessors -------------------------------------------------------
+
+ // optional string java_package = 1;
+ bool has_java_package() const;
+ void clear_java_package();
+ static const int kJavaPackageFieldNumber = 1;
+ const ::std::string& java_package() const;
+ void set_java_package(const ::std::string& value);
+ void set_java_package(const char* value);
+ void set_java_package(const char* value, size_t size);
+ ::std::string* mutable_java_package();
+ ::std::string* release_java_package();
+ void set_allocated_java_package(::std::string* java_package);
+
+ // optional string java_outer_classname = 8;
+ bool has_java_outer_classname() const;
+ void clear_java_outer_classname();
+ static const int kJavaOuterClassnameFieldNumber = 8;
+ const ::std::string& java_outer_classname() const;
+ void set_java_outer_classname(const ::std::string& value);
+ void set_java_outer_classname(const char* value);
+ void set_java_outer_classname(const char* value, size_t size);
+ ::std::string* mutable_java_outer_classname();
+ ::std::string* release_java_outer_classname();
+ void set_allocated_java_outer_classname(::std::string* java_outer_classname);
+
+ // optional bool java_multiple_files = 10 [default = false];
+ bool has_java_multiple_files() const;
+ void clear_java_multiple_files();
+ static const int kJavaMultipleFilesFieldNumber = 10;
+ bool java_multiple_files() const;
+ void set_java_multiple_files(bool value);
+
+ // optional bool java_generate_equals_and_hash = 20 [default = false];
+ bool has_java_generate_equals_and_hash() const;
+ void clear_java_generate_equals_and_hash();
+ static const int kJavaGenerateEqualsAndHashFieldNumber = 20;
+ bool java_generate_equals_and_hash() const;
+ void set_java_generate_equals_and_hash(bool value);
+
+ // optional bool java_string_check_utf8 = 27 [default = false];
+ bool has_java_string_check_utf8() const;
+ void clear_java_string_check_utf8();
+ static const int kJavaStringCheckUtf8FieldNumber = 27;
+ bool java_string_check_utf8() const;
+ void set_java_string_check_utf8(bool value);
+
+ // optional .google.protobuf.FileOptions.OptimizeMode optimize_for = 9 [default = SPEED];
+ bool has_optimize_for() const;
+ void clear_optimize_for();
+ static const int kOptimizeForFieldNumber = 9;
+ ::google::protobuf::FileOptions_OptimizeMode optimize_for() const;
+ void set_optimize_for(::google::protobuf::FileOptions_OptimizeMode value);
+
+ // optional string go_package = 11;
+ bool has_go_package() const;
+ void clear_go_package();
+ static const int kGoPackageFieldNumber = 11;
+ const ::std::string& go_package() const;
+ void set_go_package(const ::std::string& value);
+ void set_go_package(const char* value);
+ void set_go_package(const char* value, size_t size);
+ ::std::string* mutable_go_package();
+ ::std::string* release_go_package();
+ void set_allocated_go_package(::std::string* go_package);
+
+ // optional bool cc_generic_services = 16 [default = false];
+ bool has_cc_generic_services() const;
+ void clear_cc_generic_services();
+ static const int kCcGenericServicesFieldNumber = 16;
+ bool cc_generic_services() const;
+ void set_cc_generic_services(bool value);
+
+ // optional bool java_generic_services = 17 [default = false];
+ bool has_java_generic_services() const;
+ void clear_java_generic_services();
+ static const int kJavaGenericServicesFieldNumber = 17;
+ bool java_generic_services() const;
+ void set_java_generic_services(bool value);
+
+ // optional bool py_generic_services = 18 [default = false];
+ bool has_py_generic_services() const;
+ void clear_py_generic_services();
+ static const int kPyGenericServicesFieldNumber = 18;
+ bool py_generic_services() const;
+ void set_py_generic_services(bool value);
+
+ // optional bool deprecated = 23 [default = false];
+ bool has_deprecated() const;
+ void clear_deprecated();
+ static const int kDeprecatedFieldNumber = 23;
+ bool deprecated() const;
+ void set_deprecated(bool value);
+
+ // optional bool cc_enable_arenas = 31 [default = false];
+ bool has_cc_enable_arenas() const;
+ void clear_cc_enable_arenas();
+ static const int kCcEnableArenasFieldNumber = 31;
+ bool cc_enable_arenas() const;
+ void set_cc_enable_arenas(bool value);
+
+ // optional string objc_class_prefix = 36;
+ bool has_objc_class_prefix() const;
+ void clear_objc_class_prefix();
+ static const int kObjcClassPrefixFieldNumber = 36;
+ const ::std::string& objc_class_prefix() const;
+ void set_objc_class_prefix(const ::std::string& value);
+ void set_objc_class_prefix(const char* value);
+ void set_objc_class_prefix(const char* value, size_t size);
+ ::std::string* mutable_objc_class_prefix();
+ ::std::string* release_objc_class_prefix();
+ void set_allocated_objc_class_prefix(::std::string* objc_class_prefix);
+
+ // optional string csharp_namespace = 37;
+ bool has_csharp_namespace() const;
+ void clear_csharp_namespace();
+ static const int kCsharpNamespaceFieldNumber = 37;
+ const ::std::string& csharp_namespace() const;
+ void set_csharp_namespace(const ::std::string& value);
+ void set_csharp_namespace(const char* value);
+ void set_csharp_namespace(const char* value, size_t size);
+ ::std::string* mutable_csharp_namespace();
+ ::std::string* release_csharp_namespace();
+ void set_allocated_csharp_namespace(::std::string* csharp_namespace);
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(FileOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.FileOptions)
+ private:
+ inline void set_has_java_package();
+ inline void clear_has_java_package();
+ inline void set_has_java_outer_classname();
+ inline void clear_has_java_outer_classname();
+ inline void set_has_java_multiple_files();
+ inline void clear_has_java_multiple_files();
+ inline void set_has_java_generate_equals_and_hash();
+ inline void clear_has_java_generate_equals_and_hash();
+ inline void set_has_java_string_check_utf8();
+ inline void clear_has_java_string_check_utf8();
+ inline void set_has_optimize_for();
+ inline void clear_has_optimize_for();
+ inline void set_has_go_package();
+ inline void clear_has_go_package();
+ inline void set_has_cc_generic_services();
+ inline void clear_has_cc_generic_services();
+ inline void set_has_java_generic_services();
+ inline void clear_has_java_generic_services();
+ inline void set_has_py_generic_services();
+ inline void clear_has_py_generic_services();
+ inline void set_has_deprecated();
+ inline void clear_has_deprecated();
+ inline void set_has_cc_enable_arenas();
+ inline void clear_has_cc_enable_arenas();
+ inline void set_has_objc_class_prefix();
+ inline void clear_has_objc_class_prefix();
+ inline void set_has_csharp_namespace();
+ inline void clear_has_csharp_namespace();
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr java_package_;
+ ::google::protobuf::internal::ArenaStringPtr java_outer_classname_;
+ bool java_multiple_files_;
+ bool java_generate_equals_and_hash_;
+ bool java_string_check_utf8_;
+ bool cc_generic_services_;
+ int optimize_for_;
+ ::google::protobuf::internal::ArenaStringPtr go_package_;
+ ::google::protobuf::internal::ArenaStringPtr objc_class_prefix_;
+ ::google::protobuf::internal::ArenaStringPtr csharp_namespace_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ bool java_generic_services_;
+ bool py_generic_services_;
+ bool deprecated_;
+ bool cc_enable_arenas_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static FileOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT MessageOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.MessageOptions) */ {
+ public:
+ MessageOptions();
+ virtual ~MessageOptions();
+
+ MessageOptions(const MessageOptions& from);
+
+ inline MessageOptions& operator=(const MessageOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const MessageOptions& default_instance();
+
+ void Swap(MessageOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline MessageOptions* New() const { return New(NULL); }
+
+ MessageOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const MessageOptions& from);
+ void MergeFrom(const MessageOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(MessageOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional bool message_set_wire_format = 1 [default = false];
+ bool has_message_set_wire_format() const;
+ void clear_message_set_wire_format();
+ static const int kMessageSetWireFormatFieldNumber = 1;
+ bool message_set_wire_format() const;
+ void set_message_set_wire_format(bool value);
+
+ // optional bool no_standard_descriptor_accessor = 2 [default = false];
+ bool has_no_standard_descriptor_accessor() const;
+ void clear_no_standard_descriptor_accessor();
+ static const int kNoStandardDescriptorAccessorFieldNumber = 2;
+ bool no_standard_descriptor_accessor() const;
+ void set_no_standard_descriptor_accessor(bool value);
+
+ // optional bool deprecated = 3 [default = false];
+ bool has_deprecated() const;
+ void clear_deprecated();
+ static const int kDeprecatedFieldNumber = 3;
+ bool deprecated() const;
+ void set_deprecated(bool value);
+
+ // optional bool map_entry = 7;
+ bool has_map_entry() const;
+ void clear_map_entry();
+ static const int kMapEntryFieldNumber = 7;
+ bool map_entry() const;
+ void set_map_entry(bool value);
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(MessageOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.MessageOptions)
+ private:
+ inline void set_has_message_set_wire_format();
+ inline void clear_has_message_set_wire_format();
+ inline void set_has_no_standard_descriptor_accessor();
+ inline void clear_has_no_standard_descriptor_accessor();
+ inline void set_has_deprecated();
+ inline void clear_has_deprecated();
+ inline void set_has_map_entry();
+ inline void clear_has_map_entry();
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ bool message_set_wire_format_;
+ bool no_standard_descriptor_accessor_;
+ bool deprecated_;
+ bool map_entry_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static MessageOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT FieldOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.FieldOptions) */ {
+ public:
+ FieldOptions();
+ virtual ~FieldOptions();
+
+ FieldOptions(const FieldOptions& from);
+
+ inline FieldOptions& operator=(const FieldOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const FieldOptions& default_instance();
+
+ void Swap(FieldOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline FieldOptions* New() const { return New(NULL); }
+
+ FieldOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const FieldOptions& from);
+ void MergeFrom(const FieldOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(FieldOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef FieldOptions_CType CType;
+ static const CType STRING =
+ FieldOptions_CType_STRING;
+ static const CType CORD =
+ FieldOptions_CType_CORD;
+ static const CType STRING_PIECE =
+ FieldOptions_CType_STRING_PIECE;
+ static inline bool CType_IsValid(int value) {
+ return FieldOptions_CType_IsValid(value);
+ }
+ static const CType CType_MIN =
+ FieldOptions_CType_CType_MIN;
+ static const CType CType_MAX =
+ FieldOptions_CType_CType_MAX;
+ static const int CType_ARRAYSIZE =
+ FieldOptions_CType_CType_ARRAYSIZE;
+ static inline const ::google::protobuf::EnumDescriptor*
+ CType_descriptor() {
+ return FieldOptions_CType_descriptor();
+ }
+ static inline const ::std::string& CType_Name(CType value) {
+ return FieldOptions_CType_Name(value);
+ }
+ static inline bool CType_Parse(const ::std::string& name,
+ CType* value) {
+ return FieldOptions_CType_Parse(name, value);
+ }
+
+ typedef FieldOptions_JSType JSType;
+ static const JSType JS_NORMAL =
+ FieldOptions_JSType_JS_NORMAL;
+ static const JSType JS_STRING =
+ FieldOptions_JSType_JS_STRING;
+ static const JSType JS_NUMBER =
+ FieldOptions_JSType_JS_NUMBER;
+ static inline bool JSType_IsValid(int value) {
+ return FieldOptions_JSType_IsValid(value);
+ }
+ static const JSType JSType_MIN =
+ FieldOptions_JSType_JSType_MIN;
+ static const JSType JSType_MAX =
+ FieldOptions_JSType_JSType_MAX;
+ static const int JSType_ARRAYSIZE =
+ FieldOptions_JSType_JSType_ARRAYSIZE;
+ static inline const ::google::protobuf::EnumDescriptor*
+ JSType_descriptor() {
+ return FieldOptions_JSType_descriptor();
+ }
+ static inline const ::std::string& JSType_Name(JSType value) {
+ return FieldOptions_JSType_Name(value);
+ }
+ static inline bool JSType_Parse(const ::std::string& name,
+ JSType* value) {
+ return FieldOptions_JSType_Parse(name, value);
+ }
+
+ // accessors -------------------------------------------------------
+
+ // optional .google.protobuf.FieldOptions.CType ctype = 1 [default = STRING];
+ bool has_ctype() const;
+ void clear_ctype();
+ static const int kCtypeFieldNumber = 1;
+ ::google::protobuf::FieldOptions_CType ctype() const;
+ void set_ctype(::google::protobuf::FieldOptions_CType value);
+
+ // optional bool packed = 2;
+ bool has_packed() const;
+ void clear_packed();
+ static const int kPackedFieldNumber = 2;
+ bool packed() const;
+ void set_packed(bool value);
+
+ // optional .google.protobuf.FieldOptions.JSType jstype = 6 [default = JS_NORMAL];
+ bool has_jstype() const;
+ void clear_jstype();
+ static const int kJstypeFieldNumber = 6;
+ ::google::protobuf::FieldOptions_JSType jstype() const;
+ void set_jstype(::google::protobuf::FieldOptions_JSType value);
+
+ // optional bool lazy = 5 [default = false];
+ bool has_lazy() const;
+ void clear_lazy();
+ static const int kLazyFieldNumber = 5;
+ bool lazy() const;
+ void set_lazy(bool value);
+
+ // optional bool deprecated = 3 [default = false];
+ bool has_deprecated() const;
+ void clear_deprecated();
+ static const int kDeprecatedFieldNumber = 3;
+ bool deprecated() const;
+ void set_deprecated(bool value);
+
+ // optional bool weak = 10 [default = false];
+ bool has_weak() const;
+ void clear_weak();
+ static const int kWeakFieldNumber = 10;
+ bool weak() const;
+ void set_weak(bool value);
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(FieldOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.FieldOptions)
+ private:
+ inline void set_has_ctype();
+ inline void clear_has_ctype();
+ inline void set_has_packed();
+ inline void clear_has_packed();
+ inline void set_has_jstype();
+ inline void clear_has_jstype();
+ inline void set_has_lazy();
+ inline void clear_has_lazy();
+ inline void set_has_deprecated();
+ inline void clear_has_deprecated();
+ inline void set_has_weak();
+ inline void clear_has_weak();
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ int ctype_;
+ int jstype_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ bool packed_;
+ bool lazy_;
+ bool deprecated_;
+ bool weak_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static FieldOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT OneofOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.OneofOptions) */ {
+ public:
+ OneofOptions();
+ virtual ~OneofOptions();
+
+ OneofOptions(const OneofOptions& from);
+
+ inline OneofOptions& operator=(const OneofOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const OneofOptions& default_instance();
+
+ void Swap(OneofOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline OneofOptions* New() const { return New(NULL); }
+
+ OneofOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const OneofOptions& from);
+ void MergeFrom(const OneofOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(OneofOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(OneofOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.OneofOptions)
+ private:
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static OneofOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT EnumOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.EnumOptions) */ {
+ public:
+ EnumOptions();
+ virtual ~EnumOptions();
+
+ EnumOptions(const EnumOptions& from);
+
+ inline EnumOptions& operator=(const EnumOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const EnumOptions& default_instance();
+
+ void Swap(EnumOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline EnumOptions* New() const { return New(NULL); }
+
+ EnumOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const EnumOptions& from);
+ void MergeFrom(const EnumOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(EnumOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional bool allow_alias = 2;
+ bool has_allow_alias() const;
+ void clear_allow_alias();
+ static const int kAllowAliasFieldNumber = 2;
+ bool allow_alias() const;
+ void set_allow_alias(bool value);
+
+ // optional bool deprecated = 3 [default = false];
+ bool has_deprecated() const;
+ void clear_deprecated();
+ static const int kDeprecatedFieldNumber = 3;
+ bool deprecated() const;
+ void set_deprecated(bool value);
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(EnumOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.EnumOptions)
+ private:
+ inline void set_has_allow_alias();
+ inline void clear_has_allow_alias();
+ inline void set_has_deprecated();
+ inline void clear_has_deprecated();
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ bool allow_alias_;
+ bool deprecated_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static EnumOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT EnumValueOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.EnumValueOptions) */ {
+ public:
+ EnumValueOptions();
+ virtual ~EnumValueOptions();
+
+ EnumValueOptions(const EnumValueOptions& from);
+
+ inline EnumValueOptions& operator=(const EnumValueOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const EnumValueOptions& default_instance();
+
+ void Swap(EnumValueOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline EnumValueOptions* New() const { return New(NULL); }
+
+ EnumValueOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const EnumValueOptions& from);
+ void MergeFrom(const EnumValueOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(EnumValueOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional bool deprecated = 1 [default = false];
+ bool has_deprecated() const;
+ void clear_deprecated();
+ static const int kDeprecatedFieldNumber = 1;
+ bool deprecated() const;
+ void set_deprecated(bool value);
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(EnumValueOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.EnumValueOptions)
+ private:
+ inline void set_has_deprecated();
+ inline void clear_has_deprecated();
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ bool deprecated_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static EnumValueOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT ServiceOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.ServiceOptions) */ {
+ public:
+ ServiceOptions();
+ virtual ~ServiceOptions();
+
+ ServiceOptions(const ServiceOptions& from);
+
+ inline ServiceOptions& operator=(const ServiceOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const ServiceOptions& default_instance();
+
+ void Swap(ServiceOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline ServiceOptions* New() const { return New(NULL); }
+
+ ServiceOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const ServiceOptions& from);
+ void MergeFrom(const ServiceOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(ServiceOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional bool deprecated = 33 [default = false];
+ bool has_deprecated() const;
+ void clear_deprecated();
+ static const int kDeprecatedFieldNumber = 33;
+ bool deprecated() const;
+ void set_deprecated(bool value);
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(ServiceOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.ServiceOptions)
+ private:
+ inline void set_has_deprecated();
+ inline void clear_has_deprecated();
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ bool deprecated_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static ServiceOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT MethodOptions : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.MethodOptions) */ {
+ public:
+ MethodOptions();
+ virtual ~MethodOptions();
+
+ MethodOptions(const MethodOptions& from);
+
+ inline MethodOptions& operator=(const MethodOptions& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const MethodOptions& default_instance();
+
+ void Swap(MethodOptions* other);
+
+ // implements Message ----------------------------------------------
+
+ inline MethodOptions* New() const { return New(NULL); }
+
+ MethodOptions* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const MethodOptions& from);
+ void MergeFrom(const MethodOptions& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(MethodOptions* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional bool deprecated = 33 [default = false];
+ bool has_deprecated() const;
+ void clear_deprecated();
+ static const int kDeprecatedFieldNumber = 33;
+ bool deprecated() const;
+ void set_deprecated(bool value);
+
+ // repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+ int uninterpreted_option_size() const;
+ void clear_uninterpreted_option();
+ static const int kUninterpretedOptionFieldNumber = 999;
+ const ::google::protobuf::UninterpretedOption& uninterpreted_option(int index) const;
+ ::google::protobuf::UninterpretedOption* mutable_uninterpreted_option(int index);
+ ::google::protobuf::UninterpretedOption* add_uninterpreted_option();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ mutable_uninterpreted_option();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ uninterpreted_option() const;
+
+ GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(MethodOptions)
+ // @@protoc_insertion_point(class_scope:google.protobuf.MethodOptions)
+ private:
+ inline void set_has_deprecated();
+ inline void clear_has_deprecated();
+
+ ::google::protobuf::internal::ExtensionSet _extensions_;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption > uninterpreted_option_;
+ bool deprecated_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static MethodOptions* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT UninterpretedOption_NamePart : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.UninterpretedOption.NamePart) */ {
+ public:
+ UninterpretedOption_NamePart();
+ virtual ~UninterpretedOption_NamePart();
+
+ UninterpretedOption_NamePart(const UninterpretedOption_NamePart& from);
+
+ inline UninterpretedOption_NamePart& operator=(const UninterpretedOption_NamePart& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const UninterpretedOption_NamePart& default_instance();
+
+ void Swap(UninterpretedOption_NamePart* other);
+
+ // implements Message ----------------------------------------------
+
+ inline UninterpretedOption_NamePart* New() const { return New(NULL); }
+
+ UninterpretedOption_NamePart* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const UninterpretedOption_NamePart& from);
+ void MergeFrom(const UninterpretedOption_NamePart& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(UninterpretedOption_NamePart* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // required string name_part = 1;
+ bool has_name_part() const;
+ void clear_name_part();
+ static const int kNamePartFieldNumber = 1;
+ const ::std::string& name_part() const;
+ void set_name_part(const ::std::string& value);
+ void set_name_part(const char* value);
+ void set_name_part(const char* value, size_t size);
+ ::std::string* mutable_name_part();
+ ::std::string* release_name_part();
+ void set_allocated_name_part(::std::string* name_part);
+
+ // required bool is_extension = 2;
+ bool has_is_extension() const;
+ void clear_is_extension();
+ static const int kIsExtensionFieldNumber = 2;
+ bool is_extension() const;
+ void set_is_extension(bool value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.UninterpretedOption.NamePart)
+ private:
+ inline void set_has_name_part();
+ inline void clear_has_name_part();
+ inline void set_has_is_extension();
+ inline void clear_has_is_extension();
+
+ // helper for ByteSize()
+ int RequiredFieldsByteSizeFallback() const;
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::internal::ArenaStringPtr name_part_;
+ bool is_extension_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static UninterpretedOption_NamePart* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT UninterpretedOption : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.UninterpretedOption) */ {
+ public:
+ UninterpretedOption();
+ virtual ~UninterpretedOption();
+
+ UninterpretedOption(const UninterpretedOption& from);
+
+ inline UninterpretedOption& operator=(const UninterpretedOption& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const UninterpretedOption& default_instance();
+
+ void Swap(UninterpretedOption* other);
+
+ // implements Message ----------------------------------------------
+
+ inline UninterpretedOption* New() const { return New(NULL); }
+
+ UninterpretedOption* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const UninterpretedOption& from);
+ void MergeFrom(const UninterpretedOption& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(UninterpretedOption* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef UninterpretedOption_NamePart NamePart;
+
+ // accessors -------------------------------------------------------
+
+ // repeated .google.protobuf.UninterpretedOption.NamePart name = 2;
+ int name_size() const;
+ void clear_name();
+ static const int kNameFieldNumber = 2;
+ const ::google::protobuf::UninterpretedOption_NamePart& name(int index) const;
+ ::google::protobuf::UninterpretedOption_NamePart* mutable_name(int index);
+ ::google::protobuf::UninterpretedOption_NamePart* add_name();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption_NamePart >*
+ mutable_name();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption_NamePart >&
+ name() const;
+
+ // optional string identifier_value = 3;
+ bool has_identifier_value() const;
+ void clear_identifier_value();
+ static const int kIdentifierValueFieldNumber = 3;
+ const ::std::string& identifier_value() const;
+ void set_identifier_value(const ::std::string& value);
+ void set_identifier_value(const char* value);
+ void set_identifier_value(const char* value, size_t size);
+ ::std::string* mutable_identifier_value();
+ ::std::string* release_identifier_value();
+ void set_allocated_identifier_value(::std::string* identifier_value);
+
+ // optional uint64 positive_int_value = 4;
+ bool has_positive_int_value() const;
+ void clear_positive_int_value();
+ static const int kPositiveIntValueFieldNumber = 4;
+ ::google::protobuf::uint64 positive_int_value() const;
+ void set_positive_int_value(::google::protobuf::uint64 value);
+
+ // optional int64 negative_int_value = 5;
+ bool has_negative_int_value() const;
+ void clear_negative_int_value();
+ static const int kNegativeIntValueFieldNumber = 5;
+ ::google::protobuf::int64 negative_int_value() const;
+ void set_negative_int_value(::google::protobuf::int64 value);
+
+ // optional double double_value = 6;
+ bool has_double_value() const;
+ void clear_double_value();
+ static const int kDoubleValueFieldNumber = 6;
+ double double_value() const;
+ void set_double_value(double value);
+
+ // optional bytes string_value = 7;
+ bool has_string_value() const;
+ void clear_string_value();
+ static const int kStringValueFieldNumber = 7;
+ const ::std::string& string_value() const;
+ void set_string_value(const ::std::string& value);
+ void set_string_value(const char* value);
+ void set_string_value(const void* value, size_t size);
+ ::std::string* mutable_string_value();
+ ::std::string* release_string_value();
+ void set_allocated_string_value(::std::string* string_value);
+
+ // optional string aggregate_value = 8;
+ bool has_aggregate_value() const;
+ void clear_aggregate_value();
+ static const int kAggregateValueFieldNumber = 8;
+ const ::std::string& aggregate_value() const;
+ void set_aggregate_value(const ::std::string& value);
+ void set_aggregate_value(const char* value);
+ void set_aggregate_value(const char* value, size_t size);
+ ::std::string* mutable_aggregate_value();
+ ::std::string* release_aggregate_value();
+ void set_allocated_aggregate_value(::std::string* aggregate_value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.UninterpretedOption)
+ private:
+ inline void set_has_identifier_value();
+ inline void clear_has_identifier_value();
+ inline void set_has_positive_int_value();
+ inline void clear_has_positive_int_value();
+ inline void set_has_negative_int_value();
+ inline void clear_has_negative_int_value();
+ inline void set_has_double_value();
+ inline void clear_has_double_value();
+ inline void set_has_string_value();
+ inline void clear_has_string_value();
+ inline void set_has_aggregate_value();
+ inline void clear_has_aggregate_value();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption_NamePart > name_;
+ ::google::protobuf::internal::ArenaStringPtr identifier_value_;
+ ::google::protobuf::uint64 positive_int_value_;
+ ::google::protobuf::int64 negative_int_value_;
+ double double_value_;
+ ::google::protobuf::internal::ArenaStringPtr string_value_;
+ ::google::protobuf::internal::ArenaStringPtr aggregate_value_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static UninterpretedOption* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT SourceCodeInfo_Location : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.SourceCodeInfo.Location) */ {
+ public:
+ SourceCodeInfo_Location();
+ virtual ~SourceCodeInfo_Location();
+
+ SourceCodeInfo_Location(const SourceCodeInfo_Location& from);
+
+ inline SourceCodeInfo_Location& operator=(const SourceCodeInfo_Location& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const SourceCodeInfo_Location& default_instance();
+
+ void Swap(SourceCodeInfo_Location* other);
+
+ // implements Message ----------------------------------------------
+
+ inline SourceCodeInfo_Location* New() const { return New(NULL); }
+
+ SourceCodeInfo_Location* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const SourceCodeInfo_Location& from);
+ void MergeFrom(const SourceCodeInfo_Location& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(SourceCodeInfo_Location* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // repeated int32 path = 1 [packed = true];
+ int path_size() const;
+ void clear_path();
+ static const int kPathFieldNumber = 1;
+ ::google::protobuf::int32 path(int index) const;
+ void set_path(int index, ::google::protobuf::int32 value);
+ void add_path(::google::protobuf::int32 value);
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+ path() const;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+ mutable_path();
+
+ // repeated int32 span = 2 [packed = true];
+ int span_size() const;
+ void clear_span();
+ static const int kSpanFieldNumber = 2;
+ ::google::protobuf::int32 span(int index) const;
+ void set_span(int index, ::google::protobuf::int32 value);
+ void add_span(::google::protobuf::int32 value);
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+ span() const;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+ mutable_span();
+
+ // optional string leading_comments = 3;
+ bool has_leading_comments() const;
+ void clear_leading_comments();
+ static const int kLeadingCommentsFieldNumber = 3;
+ const ::std::string& leading_comments() const;
+ void set_leading_comments(const ::std::string& value);
+ void set_leading_comments(const char* value);
+ void set_leading_comments(const char* value, size_t size);
+ ::std::string* mutable_leading_comments();
+ ::std::string* release_leading_comments();
+ void set_allocated_leading_comments(::std::string* leading_comments);
+
+ // optional string trailing_comments = 4;
+ bool has_trailing_comments() const;
+ void clear_trailing_comments();
+ static const int kTrailingCommentsFieldNumber = 4;
+ const ::std::string& trailing_comments() const;
+ void set_trailing_comments(const ::std::string& value);
+ void set_trailing_comments(const char* value);
+ void set_trailing_comments(const char* value, size_t size);
+ ::std::string* mutable_trailing_comments();
+ ::std::string* release_trailing_comments();
+ void set_allocated_trailing_comments(::std::string* trailing_comments);
+
+ // repeated string leading_detached_comments = 6;
+ int leading_detached_comments_size() const;
+ void clear_leading_detached_comments();
+ static const int kLeadingDetachedCommentsFieldNumber = 6;
+ const ::std::string& leading_detached_comments(int index) const;
+ ::std::string* mutable_leading_detached_comments(int index);
+ void set_leading_detached_comments(int index, const ::std::string& value);
+ void set_leading_detached_comments(int index, const char* value);
+ void set_leading_detached_comments(int index, const char* value, size_t size);
+ ::std::string* add_leading_detached_comments();
+ void add_leading_detached_comments(const ::std::string& value);
+ void add_leading_detached_comments(const char* value);
+ void add_leading_detached_comments(const char* value, size_t size);
+ const ::google::protobuf::RepeatedPtrField< ::std::string>& leading_detached_comments() const;
+ ::google::protobuf::RepeatedPtrField< ::std::string>* mutable_leading_detached_comments();
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.SourceCodeInfo.Location)
+ private:
+ inline void set_has_leading_comments();
+ inline void clear_has_leading_comments();
+ inline void set_has_trailing_comments();
+ inline void clear_has_trailing_comments();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 > path_;
+ mutable int _path_cached_byte_size_;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 > span_;
+ mutable int _span_cached_byte_size_;
+ ::google::protobuf::internal::ArenaStringPtr leading_comments_;
+ ::google::protobuf::internal::ArenaStringPtr trailing_comments_;
+ ::google::protobuf::RepeatedPtrField< ::std::string> leading_detached_comments_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static SourceCodeInfo_Location* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT SourceCodeInfo : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.SourceCodeInfo) */ {
+ public:
+ SourceCodeInfo();
+ virtual ~SourceCodeInfo();
+
+ SourceCodeInfo(const SourceCodeInfo& from);
+
+ inline SourceCodeInfo& operator=(const SourceCodeInfo& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const SourceCodeInfo& default_instance();
+
+ void Swap(SourceCodeInfo* other);
+
+ // implements Message ----------------------------------------------
+
+ inline SourceCodeInfo* New() const { return New(NULL); }
+
+ SourceCodeInfo* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const SourceCodeInfo& from);
+ void MergeFrom(const SourceCodeInfo& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(SourceCodeInfo* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef SourceCodeInfo_Location Location;
+
+ // accessors -------------------------------------------------------
+
+ // repeated .google.protobuf.SourceCodeInfo.Location location = 1;
+ int location_size() const;
+ void clear_location();
+ static const int kLocationFieldNumber = 1;
+ const ::google::protobuf::SourceCodeInfo_Location& location(int index) const;
+ ::google::protobuf::SourceCodeInfo_Location* mutable_location(int index);
+ ::google::protobuf::SourceCodeInfo_Location* add_location();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::SourceCodeInfo_Location >*
+ mutable_location();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::SourceCodeInfo_Location >&
+ location() const;
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.SourceCodeInfo)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::SourceCodeInfo_Location > location_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static SourceCodeInfo* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT GeneratedCodeInfo_Annotation : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.GeneratedCodeInfo.Annotation) */ {
+ public:
+ GeneratedCodeInfo_Annotation();
+ virtual ~GeneratedCodeInfo_Annotation();
+
+ GeneratedCodeInfo_Annotation(const GeneratedCodeInfo_Annotation& from);
+
+ inline GeneratedCodeInfo_Annotation& operator=(const GeneratedCodeInfo_Annotation& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const GeneratedCodeInfo_Annotation& default_instance();
+
+ void Swap(GeneratedCodeInfo_Annotation* other);
+
+ // implements Message ----------------------------------------------
+
+ inline GeneratedCodeInfo_Annotation* New() const { return New(NULL); }
+
+ GeneratedCodeInfo_Annotation* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const GeneratedCodeInfo_Annotation& from);
+ void MergeFrom(const GeneratedCodeInfo_Annotation& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(GeneratedCodeInfo_Annotation* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // repeated int32 path = 1 [packed = true];
+ int path_size() const;
+ void clear_path();
+ static const int kPathFieldNumber = 1;
+ ::google::protobuf::int32 path(int index) const;
+ void set_path(int index, ::google::protobuf::int32 value);
+ void add_path(::google::protobuf::int32 value);
+ const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+ path() const;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+ mutable_path();
+
+ // optional string source_file = 2;
+ bool has_source_file() const;
+ void clear_source_file();
+ static const int kSourceFileFieldNumber = 2;
+ const ::std::string& source_file() const;
+ void set_source_file(const ::std::string& value);
+ void set_source_file(const char* value);
+ void set_source_file(const char* value, size_t size);
+ ::std::string* mutable_source_file();
+ ::std::string* release_source_file();
+ void set_allocated_source_file(::std::string* source_file);
+
+ // optional int32 begin = 3;
+ bool has_begin() const;
+ void clear_begin();
+ static const int kBeginFieldNumber = 3;
+ ::google::protobuf::int32 begin() const;
+ void set_begin(::google::protobuf::int32 value);
+
+ // optional int32 end = 4;
+ bool has_end() const;
+ void clear_end();
+ static const int kEndFieldNumber = 4;
+ ::google::protobuf::int32 end() const;
+ void set_end(::google::protobuf::int32 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.GeneratedCodeInfo.Annotation)
+ private:
+ inline void set_has_source_file();
+ inline void clear_has_source_file();
+ inline void set_has_begin();
+ inline void clear_has_begin();
+ inline void set_has_end();
+ inline void clear_has_end();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedField< ::google::protobuf::int32 > path_;
+ mutable int _path_cached_byte_size_;
+ ::google::protobuf::internal::ArenaStringPtr source_file_;
+ ::google::protobuf::int32 begin_;
+ ::google::protobuf::int32 end_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static GeneratedCodeInfo_Annotation* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT GeneratedCodeInfo : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.GeneratedCodeInfo) */ {
+ public:
+ GeneratedCodeInfo();
+ virtual ~GeneratedCodeInfo();
+
+ GeneratedCodeInfo(const GeneratedCodeInfo& from);
+
+ inline GeneratedCodeInfo& operator=(const GeneratedCodeInfo& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline const ::google::protobuf::UnknownFieldSet& unknown_fields() const {
+ return _internal_metadata_.unknown_fields();
+ }
+
+ inline ::google::protobuf::UnknownFieldSet* mutable_unknown_fields() {
+ return _internal_metadata_.mutable_unknown_fields();
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const GeneratedCodeInfo& default_instance();
+
+ void Swap(GeneratedCodeInfo* other);
+
+ // implements Message ----------------------------------------------
+
+ inline GeneratedCodeInfo* New() const { return New(NULL); }
+
+ GeneratedCodeInfo* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const GeneratedCodeInfo& from);
+ void MergeFrom(const GeneratedCodeInfo& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(GeneratedCodeInfo* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef GeneratedCodeInfo_Annotation Annotation;
+
+ // accessors -------------------------------------------------------
+
+ // repeated .google.protobuf.GeneratedCodeInfo.Annotation annotation = 1;
+ int annotation_size() const;
+ void clear_annotation();
+ static const int kAnnotationFieldNumber = 1;
+ const ::google::protobuf::GeneratedCodeInfo_Annotation& annotation(int index) const;
+ ::google::protobuf::GeneratedCodeInfo_Annotation* mutable_annotation(int index);
+ ::google::protobuf::GeneratedCodeInfo_Annotation* add_annotation();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::GeneratedCodeInfo_Annotation >*
+ mutable_annotation();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::GeneratedCodeInfo_Annotation >&
+ annotation() const;
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.GeneratedCodeInfo)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ ::google::protobuf::uint32 _has_bits_[1];
+ mutable int _cached_size_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::GeneratedCodeInfo_Annotation > annotation_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fdescriptor_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fdescriptor_2eproto();
+
+ void InitAsDefaultInstance();
+ static GeneratedCodeInfo* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// FileDescriptorSet
+
+// repeated .google.protobuf.FileDescriptorProto file = 1;
+inline int FileDescriptorSet::file_size() const {
+ return file_.size();
+}
+inline void FileDescriptorSet::clear_file() {
+ file_.Clear();
+}
+inline const ::google::protobuf::FileDescriptorProto& FileDescriptorSet::file(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorSet.file)
+ return file_.Get(index);
+}
+inline ::google::protobuf::FileDescriptorProto* FileDescriptorSet::mutable_file(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorSet.file)
+ return file_.Mutable(index);
+}
+inline ::google::protobuf::FileDescriptorProto* FileDescriptorSet::add_file() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorSet.file)
+ return file_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >*
+FileDescriptorSet::mutable_file() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorSet.file)
+ return &file_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FileDescriptorProto >&
+FileDescriptorSet::file() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorSet.file)
+ return file_;
+}
+
+// -------------------------------------------------------------------
+
+// FileDescriptorProto
+
+// optional string name = 1;
+inline bool FileDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void FileDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void FileDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void FileDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& FileDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.name)
+}
+inline void FileDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.name)
+}
+inline void FileDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.name)
+}
+inline ::std::string* FileDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.name)
+}
+
+// optional string package = 2;
+inline bool FileDescriptorProto::has_package() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void FileDescriptorProto::set_has_package() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void FileDescriptorProto::clear_has_package() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void FileDescriptorProto::clear_package() {
+ package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_package();
+}
+inline const ::std::string& FileDescriptorProto::package() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.package)
+ return package_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileDescriptorProto::set_package(const ::std::string& value) {
+ set_has_package();
+ package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.package)
+}
+inline void FileDescriptorProto::set_package(const char* value) {
+ set_has_package();
+ package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.package)
+}
+inline void FileDescriptorProto::set_package(const char* value, size_t size) {
+ set_has_package();
+ package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.package)
+}
+inline ::std::string* FileDescriptorProto::mutable_package() {
+ set_has_package();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.package)
+ return package_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileDescriptorProto::release_package() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.package)
+ clear_has_package();
+ return package_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileDescriptorProto::set_allocated_package(::std::string* package) {
+ if (package != NULL) {
+ set_has_package();
+ } else {
+ clear_has_package();
+ }
+ package_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), package);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.package)
+}
+
+// repeated string dependency = 3;
+inline int FileDescriptorProto::dependency_size() const {
+ return dependency_.size();
+}
+inline void FileDescriptorProto::clear_dependency() {
+ dependency_.Clear();
+}
+inline const ::std::string& FileDescriptorProto::dependency(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_.Get(index);
+}
+inline ::std::string* FileDescriptorProto::mutable_dependency(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_.Mutable(index);
+}
+inline void FileDescriptorProto::set_dependency(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.dependency)
+ dependency_.Mutable(index)->assign(value);
+}
+inline void FileDescriptorProto::set_dependency(int index, const char* value) {
+ dependency_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.dependency)
+}
+inline void FileDescriptorProto::set_dependency(int index, const char* value, size_t size) {
+ dependency_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.dependency)
+}
+inline ::std::string* FileDescriptorProto::add_dependency() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_.Add();
+}
+inline void FileDescriptorProto::add_dependency(const ::std::string& value) {
+ dependency_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.dependency)
+}
+inline void FileDescriptorProto::add_dependency(const char* value) {
+ dependency_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.FileDescriptorProto.dependency)
+}
+inline void FileDescriptorProto::add_dependency(const char* value, size_t size) {
+ dependency_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.FileDescriptorProto.dependency)
+}
+inline const ::google::protobuf::RepeatedPtrField< ::std::string>&
+FileDescriptorProto::dependency() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.dependency)
+ return dependency_;
+}
+inline ::google::protobuf::RepeatedPtrField< ::std::string>*
+FileDescriptorProto::mutable_dependency() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.dependency)
+ return &dependency_;
+}
+
+// repeated int32 public_dependency = 10;
+inline int FileDescriptorProto::public_dependency_size() const {
+ return public_dependency_.size();
+}
+inline void FileDescriptorProto::clear_public_dependency() {
+ public_dependency_.Clear();
+}
+inline ::google::protobuf::int32 FileDescriptorProto::public_dependency(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.public_dependency)
+ return public_dependency_.Get(index);
+}
+inline void FileDescriptorProto::set_public_dependency(int index, ::google::protobuf::int32 value) {
+ public_dependency_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.public_dependency)
+}
+inline void FileDescriptorProto::add_public_dependency(::google::protobuf::int32 value) {
+ public_dependency_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.public_dependency)
+}
+inline const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+FileDescriptorProto::public_dependency() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.public_dependency)
+ return public_dependency_;
+}
+inline ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+FileDescriptorProto::mutable_public_dependency() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.public_dependency)
+ return &public_dependency_;
+}
+
+// repeated int32 weak_dependency = 11;
+inline int FileDescriptorProto::weak_dependency_size() const {
+ return weak_dependency_.size();
+}
+inline void FileDescriptorProto::clear_weak_dependency() {
+ weak_dependency_.Clear();
+}
+inline ::google::protobuf::int32 FileDescriptorProto::weak_dependency(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.weak_dependency)
+ return weak_dependency_.Get(index);
+}
+inline void FileDescriptorProto::set_weak_dependency(int index, ::google::protobuf::int32 value) {
+ weak_dependency_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.weak_dependency)
+}
+inline void FileDescriptorProto::add_weak_dependency(::google::protobuf::int32 value) {
+ weak_dependency_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.weak_dependency)
+}
+inline const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+FileDescriptorProto::weak_dependency() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.weak_dependency)
+ return weak_dependency_;
+}
+inline ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+FileDescriptorProto::mutable_weak_dependency() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.weak_dependency)
+ return &weak_dependency_;
+}
+
+// repeated .google.protobuf.DescriptorProto message_type = 4;
+inline int FileDescriptorProto::message_type_size() const {
+ return message_type_.size();
+}
+inline void FileDescriptorProto::clear_message_type() {
+ message_type_.Clear();
+}
+inline const ::google::protobuf::DescriptorProto& FileDescriptorProto::message_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_.Get(index);
+}
+inline ::google::protobuf::DescriptorProto* FileDescriptorProto::mutable_message_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_.Mutable(index);
+}
+inline ::google::protobuf::DescriptorProto* FileDescriptorProto::add_message_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >*
+FileDescriptorProto::mutable_message_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.message_type)
+ return &message_type_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >&
+FileDescriptorProto::message_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.message_type)
+ return message_type_;
+}
+
+// repeated .google.protobuf.EnumDescriptorProto enum_type = 5;
+inline int FileDescriptorProto::enum_type_size() const {
+ return enum_type_.size();
+}
+inline void FileDescriptorProto::clear_enum_type() {
+ enum_type_.Clear();
+}
+inline const ::google::protobuf::EnumDescriptorProto& FileDescriptorProto::enum_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_.Get(index);
+}
+inline ::google::protobuf::EnumDescriptorProto* FileDescriptorProto::mutable_enum_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_.Mutable(index);
+}
+inline ::google::protobuf::EnumDescriptorProto* FileDescriptorProto::add_enum_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >*
+FileDescriptorProto::mutable_enum_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.enum_type)
+ return &enum_type_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >&
+FileDescriptorProto::enum_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.enum_type)
+ return enum_type_;
+}
+
+// repeated .google.protobuf.ServiceDescriptorProto service = 6;
+inline int FileDescriptorProto::service_size() const {
+ return service_.size();
+}
+inline void FileDescriptorProto::clear_service() {
+ service_.Clear();
+}
+inline const ::google::protobuf::ServiceDescriptorProto& FileDescriptorProto::service(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.service)
+ return service_.Get(index);
+}
+inline ::google::protobuf::ServiceDescriptorProto* FileDescriptorProto::mutable_service(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.service)
+ return service_.Mutable(index);
+}
+inline ::google::protobuf::ServiceDescriptorProto* FileDescriptorProto::add_service() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.service)
+ return service_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::ServiceDescriptorProto >*
+FileDescriptorProto::mutable_service() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.service)
+ return &service_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::ServiceDescriptorProto >&
+FileDescriptorProto::service() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.service)
+ return service_;
+}
+
+// repeated .google.protobuf.FieldDescriptorProto extension = 7;
+inline int FileDescriptorProto::extension_size() const {
+ return extension_.size();
+}
+inline void FileDescriptorProto::clear_extension() {
+ extension_.Clear();
+}
+inline const ::google::protobuf::FieldDescriptorProto& FileDescriptorProto::extension(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.extension)
+ return extension_.Get(index);
+}
+inline ::google::protobuf::FieldDescriptorProto* FileDescriptorProto::mutable_extension(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.extension)
+ return extension_.Mutable(index);
+}
+inline ::google::protobuf::FieldDescriptorProto* FileDescriptorProto::add_extension() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileDescriptorProto.extension)
+ return extension_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+FileDescriptorProto::mutable_extension() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileDescriptorProto.extension)
+ return &extension_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+FileDescriptorProto::extension() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileDescriptorProto.extension)
+ return extension_;
+}
+
+// optional .google.protobuf.FileOptions options = 8;
+inline bool FileDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000200u) != 0;
+}
+inline void FileDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000200u;
+}
+inline void FileDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000200u;
+}
+inline void FileDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::FileOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::FileOptions& FileDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::FileOptions* FileDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::FileOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::FileOptions* FileDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::FileOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void FileDescriptorProto::set_allocated_options(::google::protobuf::FileOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.options)
+}
+
+// optional .google.protobuf.SourceCodeInfo source_code_info = 9;
+inline bool FileDescriptorProto::has_source_code_info() const {
+ return (_has_bits_[0] & 0x00000400u) != 0;
+}
+inline void FileDescriptorProto::set_has_source_code_info() {
+ _has_bits_[0] |= 0x00000400u;
+}
+inline void FileDescriptorProto::clear_has_source_code_info() {
+ _has_bits_[0] &= ~0x00000400u;
+}
+inline void FileDescriptorProto::clear_source_code_info() {
+ if (source_code_info_ != NULL) source_code_info_->::google::protobuf::SourceCodeInfo::Clear();
+ clear_has_source_code_info();
+}
+inline const ::google::protobuf::SourceCodeInfo& FileDescriptorProto::source_code_info() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.source_code_info)
+ return source_code_info_ != NULL ? *source_code_info_ : *default_instance_->source_code_info_;
+}
+inline ::google::protobuf::SourceCodeInfo* FileDescriptorProto::mutable_source_code_info() {
+ set_has_source_code_info();
+ if (source_code_info_ == NULL) {
+ source_code_info_ = new ::google::protobuf::SourceCodeInfo;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.source_code_info)
+ return source_code_info_;
+}
+inline ::google::protobuf::SourceCodeInfo* FileDescriptorProto::release_source_code_info() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.source_code_info)
+ clear_has_source_code_info();
+ ::google::protobuf::SourceCodeInfo* temp = source_code_info_;
+ source_code_info_ = NULL;
+ return temp;
+}
+inline void FileDescriptorProto::set_allocated_source_code_info(::google::protobuf::SourceCodeInfo* source_code_info) {
+ delete source_code_info_;
+ source_code_info_ = source_code_info;
+ if (source_code_info) {
+ set_has_source_code_info();
+ } else {
+ clear_has_source_code_info();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.source_code_info)
+}
+
+// optional string syntax = 12;
+inline bool FileDescriptorProto::has_syntax() const {
+ return (_has_bits_[0] & 0x00000800u) != 0;
+}
+inline void FileDescriptorProto::set_has_syntax() {
+ _has_bits_[0] |= 0x00000800u;
+}
+inline void FileDescriptorProto::clear_has_syntax() {
+ _has_bits_[0] &= ~0x00000800u;
+}
+inline void FileDescriptorProto::clear_syntax() {
+ syntax_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_syntax();
+}
+inline const ::std::string& FileDescriptorProto::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileDescriptorProto.syntax)
+ return syntax_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileDescriptorProto::set_syntax(const ::std::string& value) {
+ set_has_syntax();
+ syntax_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileDescriptorProto.syntax)
+}
+inline void FileDescriptorProto::set_syntax(const char* value) {
+ set_has_syntax();
+ syntax_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileDescriptorProto.syntax)
+}
+inline void FileDescriptorProto::set_syntax(const char* value, size_t size) {
+ set_has_syntax();
+ syntax_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileDescriptorProto.syntax)
+}
+inline ::std::string* FileDescriptorProto::mutable_syntax() {
+ set_has_syntax();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileDescriptorProto.syntax)
+ return syntax_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileDescriptorProto::release_syntax() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileDescriptorProto.syntax)
+ clear_has_syntax();
+ return syntax_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileDescriptorProto::set_allocated_syntax(::std::string* syntax) {
+ if (syntax != NULL) {
+ set_has_syntax();
+ } else {
+ clear_has_syntax();
+ }
+ syntax_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), syntax);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileDescriptorProto.syntax)
+}
+
+// -------------------------------------------------------------------
+
+// DescriptorProto_ExtensionRange
+
+// optional int32 start = 1;
+inline bool DescriptorProto_ExtensionRange::has_start() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void DescriptorProto_ExtensionRange::set_has_start() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void DescriptorProto_ExtensionRange::clear_has_start() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void DescriptorProto_ExtensionRange::clear_start() {
+ start_ = 0;
+ clear_has_start();
+}
+inline ::google::protobuf::int32 DescriptorProto_ExtensionRange::start() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ExtensionRange.start)
+ return start_;
+}
+inline void DescriptorProto_ExtensionRange::set_start(::google::protobuf::int32 value) {
+ set_has_start();
+ start_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ExtensionRange.start)
+}
+
+// optional int32 end = 2;
+inline bool DescriptorProto_ExtensionRange::has_end() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void DescriptorProto_ExtensionRange::set_has_end() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void DescriptorProto_ExtensionRange::clear_has_end() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void DescriptorProto_ExtensionRange::clear_end() {
+ end_ = 0;
+ clear_has_end();
+}
+inline ::google::protobuf::int32 DescriptorProto_ExtensionRange::end() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ExtensionRange.end)
+ return end_;
+}
+inline void DescriptorProto_ExtensionRange::set_end(::google::protobuf::int32 value) {
+ set_has_end();
+ end_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ExtensionRange.end)
+}
+
+// -------------------------------------------------------------------
+
+// DescriptorProto_ReservedRange
+
+// optional int32 start = 1;
+inline bool DescriptorProto_ReservedRange::has_start() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void DescriptorProto_ReservedRange::set_has_start() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void DescriptorProto_ReservedRange::clear_has_start() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void DescriptorProto_ReservedRange::clear_start() {
+ start_ = 0;
+ clear_has_start();
+}
+inline ::google::protobuf::int32 DescriptorProto_ReservedRange::start() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ReservedRange.start)
+ return start_;
+}
+inline void DescriptorProto_ReservedRange::set_start(::google::protobuf::int32 value) {
+ set_has_start();
+ start_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ReservedRange.start)
+}
+
+// optional int32 end = 2;
+inline bool DescriptorProto_ReservedRange::has_end() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void DescriptorProto_ReservedRange::set_has_end() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void DescriptorProto_ReservedRange::clear_has_end() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void DescriptorProto_ReservedRange::clear_end() {
+ end_ = 0;
+ clear_has_end();
+}
+inline ::google::protobuf::int32 DescriptorProto_ReservedRange::end() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.ReservedRange.end)
+ return end_;
+}
+inline void DescriptorProto_ReservedRange::set_end(::google::protobuf::int32 value) {
+ set_has_end();
+ end_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.ReservedRange.end)
+}
+
+// -------------------------------------------------------------------
+
+// DescriptorProto
+
+// optional string name = 1;
+inline bool DescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void DescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void DescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void DescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& DescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void DescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.name)
+}
+inline void DescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.DescriptorProto.name)
+}
+inline void DescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.DescriptorProto.name)
+}
+inline ::std::string* DescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* DescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.DescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void DescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.DescriptorProto.name)
+}
+
+// repeated .google.protobuf.FieldDescriptorProto field = 2;
+inline int DescriptorProto::field_size() const {
+ return field_.size();
+}
+inline void DescriptorProto::clear_field() {
+ field_.Clear();
+}
+inline const ::google::protobuf::FieldDescriptorProto& DescriptorProto::field(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.field)
+ return field_.Get(index);
+}
+inline ::google::protobuf::FieldDescriptorProto* DescriptorProto::mutable_field(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.field)
+ return field_.Mutable(index);
+}
+inline ::google::protobuf::FieldDescriptorProto* DescriptorProto::add_field() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.field)
+ return field_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+DescriptorProto::mutable_field() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.field)
+ return &field_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+DescriptorProto::field() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.field)
+ return field_;
+}
+
+// repeated .google.protobuf.FieldDescriptorProto extension = 6;
+inline int DescriptorProto::extension_size() const {
+ return extension_.size();
+}
+inline void DescriptorProto::clear_extension() {
+ extension_.Clear();
+}
+inline const ::google::protobuf::FieldDescriptorProto& DescriptorProto::extension(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.extension)
+ return extension_.Get(index);
+}
+inline ::google::protobuf::FieldDescriptorProto* DescriptorProto::mutable_extension(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.extension)
+ return extension_.Mutable(index);
+}
+inline ::google::protobuf::FieldDescriptorProto* DescriptorProto::add_extension() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.extension)
+ return extension_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >*
+DescriptorProto::mutable_extension() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.extension)
+ return &extension_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::FieldDescriptorProto >&
+DescriptorProto::extension() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.extension)
+ return extension_;
+}
+
+// repeated .google.protobuf.DescriptorProto nested_type = 3;
+inline int DescriptorProto::nested_type_size() const {
+ return nested_type_.size();
+}
+inline void DescriptorProto::clear_nested_type() {
+ nested_type_.Clear();
+}
+inline const ::google::protobuf::DescriptorProto& DescriptorProto::nested_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_.Get(index);
+}
+inline ::google::protobuf::DescriptorProto* DescriptorProto::mutable_nested_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_.Mutable(index);
+}
+inline ::google::protobuf::DescriptorProto* DescriptorProto::add_nested_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >*
+DescriptorProto::mutable_nested_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.nested_type)
+ return &nested_type_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto >&
+DescriptorProto::nested_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.nested_type)
+ return nested_type_;
+}
+
+// repeated .google.protobuf.EnumDescriptorProto enum_type = 4;
+inline int DescriptorProto::enum_type_size() const {
+ return enum_type_.size();
+}
+inline void DescriptorProto::clear_enum_type() {
+ enum_type_.Clear();
+}
+inline const ::google::protobuf::EnumDescriptorProto& DescriptorProto::enum_type(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_.Get(index);
+}
+inline ::google::protobuf::EnumDescriptorProto* DescriptorProto::mutable_enum_type(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_.Mutable(index);
+}
+inline ::google::protobuf::EnumDescriptorProto* DescriptorProto::add_enum_type() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >*
+DescriptorProto::mutable_enum_type() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.enum_type)
+ return &enum_type_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumDescriptorProto >&
+DescriptorProto::enum_type() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.enum_type)
+ return enum_type_;
+}
+
+// repeated .google.protobuf.DescriptorProto.ExtensionRange extension_range = 5;
+inline int DescriptorProto::extension_range_size() const {
+ return extension_range_.size();
+}
+inline void DescriptorProto::clear_extension_range() {
+ extension_range_.Clear();
+}
+inline const ::google::protobuf::DescriptorProto_ExtensionRange& DescriptorProto::extension_range(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_.Get(index);
+}
+inline ::google::protobuf::DescriptorProto_ExtensionRange* DescriptorProto::mutable_extension_range(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_.Mutable(index);
+}
+inline ::google::protobuf::DescriptorProto_ExtensionRange* DescriptorProto::add_extension_range() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ExtensionRange >*
+DescriptorProto::mutable_extension_range() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.extension_range)
+ return &extension_range_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ExtensionRange >&
+DescriptorProto::extension_range() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.extension_range)
+ return extension_range_;
+}
+
+// repeated .google.protobuf.OneofDescriptorProto oneof_decl = 8;
+inline int DescriptorProto::oneof_decl_size() const {
+ return oneof_decl_.size();
+}
+inline void DescriptorProto::clear_oneof_decl() {
+ oneof_decl_.Clear();
+}
+inline const ::google::protobuf::OneofDescriptorProto& DescriptorProto::oneof_decl(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_.Get(index);
+}
+inline ::google::protobuf::OneofDescriptorProto* DescriptorProto::mutable_oneof_decl(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_.Mutable(index);
+}
+inline ::google::protobuf::OneofDescriptorProto* DescriptorProto::add_oneof_decl() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::OneofDescriptorProto >*
+DescriptorProto::mutable_oneof_decl() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.oneof_decl)
+ return &oneof_decl_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::OneofDescriptorProto >&
+DescriptorProto::oneof_decl() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.oneof_decl)
+ return oneof_decl_;
+}
+
+// optional .google.protobuf.MessageOptions options = 7;
+inline bool DescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000080u) != 0;
+}
+inline void DescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000080u;
+}
+inline void DescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000080u;
+}
+inline void DescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::MessageOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::MessageOptions& DescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::MessageOptions* DescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::MessageOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::MessageOptions* DescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.DescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::MessageOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void DescriptorProto::set_allocated_options(::google::protobuf::MessageOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.DescriptorProto.options)
+}
+
+// repeated .google.protobuf.DescriptorProto.ReservedRange reserved_range = 9;
+inline int DescriptorProto::reserved_range_size() const {
+ return reserved_range_.size();
+}
+inline void DescriptorProto::clear_reserved_range() {
+ reserved_range_.Clear();
+}
+inline const ::google::protobuf::DescriptorProto_ReservedRange& DescriptorProto::reserved_range(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_.Get(index);
+}
+inline ::google::protobuf::DescriptorProto_ReservedRange* DescriptorProto::mutable_reserved_range(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_.Mutable(index);
+}
+inline ::google::protobuf::DescriptorProto_ReservedRange* DescriptorProto::add_reserved_range() {
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ReservedRange >*
+DescriptorProto::mutable_reserved_range() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.reserved_range)
+ return &reserved_range_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::DescriptorProto_ReservedRange >&
+DescriptorProto::reserved_range() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.reserved_range)
+ return reserved_range_;
+}
+
+// repeated string reserved_name = 10;
+inline int DescriptorProto::reserved_name_size() const {
+ return reserved_name_.size();
+}
+inline void DescriptorProto::clear_reserved_name() {
+ reserved_name_.Clear();
+}
+inline const ::std::string& DescriptorProto::reserved_name(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_.Get(index);
+}
+inline ::std::string* DescriptorProto::mutable_reserved_name(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_.Mutable(index);
+}
+inline void DescriptorProto::set_reserved_name(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.DescriptorProto.reserved_name)
+ reserved_name_.Mutable(index)->assign(value);
+}
+inline void DescriptorProto::set_reserved_name(int index, const char* value) {
+ reserved_name_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.DescriptorProto.reserved_name)
+}
+inline void DescriptorProto::set_reserved_name(int index, const char* value, size_t size) {
+ reserved_name_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.DescriptorProto.reserved_name)
+}
+inline ::std::string* DescriptorProto::add_reserved_name() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_.Add();
+}
+inline void DescriptorProto::add_reserved_name(const ::std::string& value) {
+ reserved_name_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.DescriptorProto.reserved_name)
+}
+inline void DescriptorProto::add_reserved_name(const char* value) {
+ reserved_name_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.DescriptorProto.reserved_name)
+}
+inline void DescriptorProto::add_reserved_name(const char* value, size_t size) {
+ reserved_name_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.DescriptorProto.reserved_name)
+}
+inline const ::google::protobuf::RepeatedPtrField< ::std::string>&
+DescriptorProto::reserved_name() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.DescriptorProto.reserved_name)
+ return reserved_name_;
+}
+inline ::google::protobuf::RepeatedPtrField< ::std::string>*
+DescriptorProto::mutable_reserved_name() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.DescriptorProto.reserved_name)
+ return &reserved_name_;
+}
+
+// -------------------------------------------------------------------
+
+// FieldDescriptorProto
+
+// optional string name = 1;
+inline bool FieldDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void FieldDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void FieldDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void FieldDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& FieldDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.name)
+}
+inline void FieldDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.name)
+}
+inline void FieldDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.name)
+}
+inline ::std::string* FieldDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FieldDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.name)
+}
+
+// optional int32 number = 3;
+inline bool FieldDescriptorProto::has_number() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void FieldDescriptorProto::set_has_number() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void FieldDescriptorProto::clear_has_number() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void FieldDescriptorProto::clear_number() {
+ number_ = 0;
+ clear_has_number();
+}
+inline ::google::protobuf::int32 FieldDescriptorProto::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.number)
+ return number_;
+}
+inline void FieldDescriptorProto::set_number(::google::protobuf::int32 value) {
+ set_has_number();
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.number)
+}
+
+// optional .google.protobuf.FieldDescriptorProto.Label label = 4;
+inline bool FieldDescriptorProto::has_label() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void FieldDescriptorProto::set_has_label() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void FieldDescriptorProto::clear_has_label() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void FieldDescriptorProto::clear_label() {
+ label_ = 1;
+ clear_has_label();
+}
+inline ::google::protobuf::FieldDescriptorProto_Label FieldDescriptorProto::label() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.label)
+ return static_cast< ::google::protobuf::FieldDescriptorProto_Label >(label_);
+}
+inline void FieldDescriptorProto::set_label(::google::protobuf::FieldDescriptorProto_Label value) {
+ assert(::google::protobuf::FieldDescriptorProto_Label_IsValid(value));
+ set_has_label();
+ label_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.label)
+}
+
+// optional .google.protobuf.FieldDescriptorProto.Type type = 5;
+inline bool FieldDescriptorProto::has_type() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void FieldDescriptorProto::set_has_type() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void FieldDescriptorProto::clear_has_type() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void FieldDescriptorProto::clear_type() {
+ type_ = 1;
+ clear_has_type();
+}
+inline ::google::protobuf::FieldDescriptorProto_Type FieldDescriptorProto::type() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.type)
+ return static_cast< ::google::protobuf::FieldDescriptorProto_Type >(type_);
+}
+inline void FieldDescriptorProto::set_type(::google::protobuf::FieldDescriptorProto_Type value) {
+ assert(::google::protobuf::FieldDescriptorProto_Type_IsValid(value));
+ set_has_type();
+ type_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.type)
+}
+
+// optional string type_name = 6;
+inline bool FieldDescriptorProto::has_type_name() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+inline void FieldDescriptorProto::set_has_type_name() {
+ _has_bits_[0] |= 0x00000010u;
+}
+inline void FieldDescriptorProto::clear_has_type_name() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+inline void FieldDescriptorProto::clear_type_name() {
+ type_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_type_name();
+}
+inline const ::std::string& FieldDescriptorProto::type_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.type_name)
+ return type_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_type_name(const ::std::string& value) {
+ set_has_type_name();
+ type_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.type_name)
+}
+inline void FieldDescriptorProto::set_type_name(const char* value) {
+ set_has_type_name();
+ type_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.type_name)
+}
+inline void FieldDescriptorProto::set_type_name(const char* value, size_t size) {
+ set_has_type_name();
+ type_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.type_name)
+}
+inline ::std::string* FieldDescriptorProto::mutable_type_name() {
+ set_has_type_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.type_name)
+ return type_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FieldDescriptorProto::release_type_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.type_name)
+ clear_has_type_name();
+ return type_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_allocated_type_name(::std::string* type_name) {
+ if (type_name != NULL) {
+ set_has_type_name();
+ } else {
+ clear_has_type_name();
+ }
+ type_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), type_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.type_name)
+}
+
+// optional string extendee = 2;
+inline bool FieldDescriptorProto::has_extendee() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+inline void FieldDescriptorProto::set_has_extendee() {
+ _has_bits_[0] |= 0x00000020u;
+}
+inline void FieldDescriptorProto::clear_has_extendee() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+inline void FieldDescriptorProto::clear_extendee() {
+ extendee_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_extendee();
+}
+inline const ::std::string& FieldDescriptorProto::extendee() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.extendee)
+ return extendee_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_extendee(const ::std::string& value) {
+ set_has_extendee();
+ extendee_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.extendee)
+}
+inline void FieldDescriptorProto::set_extendee(const char* value) {
+ set_has_extendee();
+ extendee_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.extendee)
+}
+inline void FieldDescriptorProto::set_extendee(const char* value, size_t size) {
+ set_has_extendee();
+ extendee_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.extendee)
+}
+inline ::std::string* FieldDescriptorProto::mutable_extendee() {
+ set_has_extendee();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.extendee)
+ return extendee_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FieldDescriptorProto::release_extendee() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.extendee)
+ clear_has_extendee();
+ return extendee_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_allocated_extendee(::std::string* extendee) {
+ if (extendee != NULL) {
+ set_has_extendee();
+ } else {
+ clear_has_extendee();
+ }
+ extendee_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), extendee);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.extendee)
+}
+
+// optional string default_value = 7;
+inline bool FieldDescriptorProto::has_default_value() const {
+ return (_has_bits_[0] & 0x00000040u) != 0;
+}
+inline void FieldDescriptorProto::set_has_default_value() {
+ _has_bits_[0] |= 0x00000040u;
+}
+inline void FieldDescriptorProto::clear_has_default_value() {
+ _has_bits_[0] &= ~0x00000040u;
+}
+inline void FieldDescriptorProto::clear_default_value() {
+ default_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_default_value();
+}
+inline const ::std::string& FieldDescriptorProto::default_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.default_value)
+ return default_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_default_value(const ::std::string& value) {
+ set_has_default_value();
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.default_value)
+}
+inline void FieldDescriptorProto::set_default_value(const char* value) {
+ set_has_default_value();
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.default_value)
+}
+inline void FieldDescriptorProto::set_default_value(const char* value, size_t size) {
+ set_has_default_value();
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.default_value)
+}
+inline ::std::string* FieldDescriptorProto::mutable_default_value() {
+ set_has_default_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.default_value)
+ return default_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FieldDescriptorProto::release_default_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.default_value)
+ clear_has_default_value();
+ return default_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_allocated_default_value(::std::string* default_value) {
+ if (default_value != NULL) {
+ set_has_default_value();
+ } else {
+ clear_has_default_value();
+ }
+ default_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), default_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.default_value)
+}
+
+// optional int32 oneof_index = 9;
+inline bool FieldDescriptorProto::has_oneof_index() const {
+ return (_has_bits_[0] & 0x00000080u) != 0;
+}
+inline void FieldDescriptorProto::set_has_oneof_index() {
+ _has_bits_[0] |= 0x00000080u;
+}
+inline void FieldDescriptorProto::clear_has_oneof_index() {
+ _has_bits_[0] &= ~0x00000080u;
+}
+inline void FieldDescriptorProto::clear_oneof_index() {
+ oneof_index_ = 0;
+ clear_has_oneof_index();
+}
+inline ::google::protobuf::int32 FieldDescriptorProto::oneof_index() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.oneof_index)
+ return oneof_index_;
+}
+inline void FieldDescriptorProto::set_oneof_index(::google::protobuf::int32 value) {
+ set_has_oneof_index();
+ oneof_index_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.oneof_index)
+}
+
+// optional string json_name = 10;
+inline bool FieldDescriptorProto::has_json_name() const {
+ return (_has_bits_[0] & 0x00000100u) != 0;
+}
+inline void FieldDescriptorProto::set_has_json_name() {
+ _has_bits_[0] |= 0x00000100u;
+}
+inline void FieldDescriptorProto::clear_has_json_name() {
+ _has_bits_[0] &= ~0x00000100u;
+}
+inline void FieldDescriptorProto::clear_json_name() {
+ json_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_json_name();
+}
+inline const ::std::string& FieldDescriptorProto::json_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.json_name)
+ return json_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_json_name(const ::std::string& value) {
+ set_has_json_name();
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldDescriptorProto.json_name)
+}
+inline void FieldDescriptorProto::set_json_name(const char* value) {
+ set_has_json_name();
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldDescriptorProto.json_name)
+}
+inline void FieldDescriptorProto::set_json_name(const char* value, size_t size) {
+ set_has_json_name();
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldDescriptorProto.json_name)
+}
+inline ::std::string* FieldDescriptorProto::mutable_json_name() {
+ set_has_json_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.json_name)
+ return json_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FieldDescriptorProto::release_json_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.json_name)
+ clear_has_json_name();
+ return json_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FieldDescriptorProto::set_allocated_json_name(::std::string* json_name) {
+ if (json_name != NULL) {
+ set_has_json_name();
+ } else {
+ clear_has_json_name();
+ }
+ json_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), json_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.json_name)
+}
+
+// optional .google.protobuf.FieldOptions options = 8;
+inline bool FieldDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000200u) != 0;
+}
+inline void FieldDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000200u;
+}
+inline void FieldDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000200u;
+}
+inline void FieldDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::FieldOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::FieldOptions& FieldDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::FieldOptions* FieldDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::FieldOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldDescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::FieldOptions* FieldDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FieldDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::FieldOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void FieldDescriptorProto::set_allocated_options(::google::protobuf::FieldOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FieldDescriptorProto.options)
+}
+
+// -------------------------------------------------------------------
+
+// OneofDescriptorProto
+
+// optional string name = 1;
+inline bool OneofDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void OneofDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void OneofDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void OneofDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& OneofDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.OneofDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void OneofDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.OneofDescriptorProto.name)
+}
+inline void OneofDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.OneofDescriptorProto.name)
+}
+inline void OneofDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.OneofDescriptorProto.name)
+}
+inline ::std::string* OneofDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.OneofDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* OneofDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.OneofDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void OneofDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.OneofDescriptorProto.name)
+}
+
+// optional .google.protobuf.OneofOptions options = 2;
+inline bool OneofDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void OneofDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void OneofDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void OneofDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::OneofOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::OneofOptions& OneofDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.OneofDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::OneofOptions* OneofDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::OneofOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.OneofDescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::OneofOptions* OneofDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.OneofDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::OneofOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void OneofDescriptorProto::set_allocated_options(::google::protobuf::OneofOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.OneofDescriptorProto.options)
+}
+
+// -------------------------------------------------------------------
+
+// EnumDescriptorProto
+
+// optional string name = 1;
+inline bool EnumDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void EnumDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void EnumDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void EnumDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& EnumDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void EnumDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumDescriptorProto.name)
+}
+inline void EnumDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.EnumDescriptorProto.name)
+}
+inline void EnumDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.EnumDescriptorProto.name)
+}
+inline ::std::string* EnumDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* EnumDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void EnumDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumDescriptorProto.name)
+}
+
+// repeated .google.protobuf.EnumValueDescriptorProto value = 2;
+inline int EnumDescriptorProto::value_size() const {
+ return value_.size();
+}
+inline void EnumDescriptorProto::clear_value() {
+ value_.Clear();
+}
+inline const ::google::protobuf::EnumValueDescriptorProto& EnumDescriptorProto::value(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumDescriptorProto.value)
+ return value_.Get(index);
+}
+inline ::google::protobuf::EnumValueDescriptorProto* EnumDescriptorProto::mutable_value(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumDescriptorProto.value)
+ return value_.Mutable(index);
+}
+inline ::google::protobuf::EnumValueDescriptorProto* EnumDescriptorProto::add_value() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumDescriptorProto.value)
+ return value_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValueDescriptorProto >*
+EnumDescriptorProto::mutable_value() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumDescriptorProto.value)
+ return &value_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValueDescriptorProto >&
+EnumDescriptorProto::value() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumDescriptorProto.value)
+ return value_;
+}
+
+// optional .google.protobuf.EnumOptions options = 3;
+inline bool EnumDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void EnumDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void EnumDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void EnumDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::EnumOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::EnumOptions& EnumDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::EnumOptions* EnumDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::EnumOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumDescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::EnumOptions* EnumDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::EnumOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void EnumDescriptorProto::set_allocated_options(::google::protobuf::EnumOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumDescriptorProto.options)
+}
+
+// -------------------------------------------------------------------
+
+// EnumValueDescriptorProto
+
+// optional string name = 1;
+inline bool EnumValueDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void EnumValueDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void EnumValueDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void EnumValueDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& EnumValueDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void EnumValueDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValueDescriptorProto.name)
+}
+inline void EnumValueDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.EnumValueDescriptorProto.name)
+}
+inline void EnumValueDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.EnumValueDescriptorProto.name)
+}
+inline ::std::string* EnumValueDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValueDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* EnumValueDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumValueDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void EnumValueDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumValueDescriptorProto.name)
+}
+
+// optional int32 number = 2;
+inline bool EnumValueDescriptorProto::has_number() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void EnumValueDescriptorProto::set_has_number() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void EnumValueDescriptorProto::clear_has_number() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void EnumValueDescriptorProto::clear_number() {
+ number_ = 0;
+ clear_has_number();
+}
+inline ::google::protobuf::int32 EnumValueDescriptorProto::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueDescriptorProto.number)
+ return number_;
+}
+inline void EnumValueDescriptorProto::set_number(::google::protobuf::int32 value) {
+ set_has_number();
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValueDescriptorProto.number)
+}
+
+// optional .google.protobuf.EnumValueOptions options = 3;
+inline bool EnumValueDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void EnumValueDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void EnumValueDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void EnumValueDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::EnumValueOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::EnumValueOptions& EnumValueDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::EnumValueOptions* EnumValueDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::EnumValueOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValueDescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::EnumValueOptions* EnumValueDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumValueDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::EnumValueOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void EnumValueDescriptorProto::set_allocated_options(::google::protobuf::EnumValueOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumValueDescriptorProto.options)
+}
+
+// -------------------------------------------------------------------
+
+// ServiceDescriptorProto
+
+// optional string name = 1;
+inline bool ServiceDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void ServiceDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void ServiceDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void ServiceDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& ServiceDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void ServiceDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.ServiceDescriptorProto.name)
+}
+inline void ServiceDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.ServiceDescriptorProto.name)
+}
+inline void ServiceDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.ServiceDescriptorProto.name)
+}
+inline ::std::string* ServiceDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* ServiceDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.ServiceDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void ServiceDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.ServiceDescriptorProto.name)
+}
+
+// repeated .google.protobuf.MethodDescriptorProto method = 2;
+inline int ServiceDescriptorProto::method_size() const {
+ return method_.size();
+}
+inline void ServiceDescriptorProto::clear_method() {
+ method_.Clear();
+}
+inline const ::google::protobuf::MethodDescriptorProto& ServiceDescriptorProto::method(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceDescriptorProto.method)
+ return method_.Get(index);
+}
+inline ::google::protobuf::MethodDescriptorProto* ServiceDescriptorProto::mutable_method(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceDescriptorProto.method)
+ return method_.Mutable(index);
+}
+inline ::google::protobuf::MethodDescriptorProto* ServiceDescriptorProto::add_method() {
+ // @@protoc_insertion_point(field_add:google.protobuf.ServiceDescriptorProto.method)
+ return method_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::MethodDescriptorProto >*
+ServiceDescriptorProto::mutable_method() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.ServiceDescriptorProto.method)
+ return &method_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::MethodDescriptorProto >&
+ServiceDescriptorProto::method() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.ServiceDescriptorProto.method)
+ return method_;
+}
+
+// optional .google.protobuf.ServiceOptions options = 3;
+inline bool ServiceDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void ServiceDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void ServiceDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void ServiceDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::ServiceOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::ServiceOptions& ServiceDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::ServiceOptions* ServiceDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::ServiceOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceDescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::ServiceOptions* ServiceDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.ServiceDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::ServiceOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void ServiceDescriptorProto::set_allocated_options(::google::protobuf::ServiceOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.ServiceDescriptorProto.options)
+}
+
+// -------------------------------------------------------------------
+
+// MethodDescriptorProto
+
+// optional string name = 1;
+inline bool MethodDescriptorProto::has_name() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void MethodDescriptorProto::set_has_name() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void MethodDescriptorProto::clear_has_name() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void MethodDescriptorProto::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name();
+}
+inline const ::std::string& MethodDescriptorProto::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void MethodDescriptorProto::set_name(const ::std::string& value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.name)
+}
+inline void MethodDescriptorProto::set_name(const char* value) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.MethodDescriptorProto.name)
+}
+inline void MethodDescriptorProto::set_name(const char* value, size_t size) {
+ set_has_name();
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.MethodDescriptorProto.name)
+}
+inline ::std::string* MethodDescriptorProto::mutable_name() {
+ set_has_name();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* MethodDescriptorProto::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.name)
+ clear_has_name();
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void MethodDescriptorProto::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+ set_has_name();
+ } else {
+ clear_has_name();
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.name)
+}
+
+// optional string input_type = 2;
+inline bool MethodDescriptorProto::has_input_type() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void MethodDescriptorProto::set_has_input_type() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void MethodDescriptorProto::clear_has_input_type() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void MethodDescriptorProto::clear_input_type() {
+ input_type_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_input_type();
+}
+inline const ::std::string& MethodDescriptorProto::input_type() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.input_type)
+ return input_type_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void MethodDescriptorProto::set_input_type(const ::std::string& value) {
+ set_has_input_type();
+ input_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.input_type)
+}
+inline void MethodDescriptorProto::set_input_type(const char* value) {
+ set_has_input_type();
+ input_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.MethodDescriptorProto.input_type)
+}
+inline void MethodDescriptorProto::set_input_type(const char* value, size_t size) {
+ set_has_input_type();
+ input_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.MethodDescriptorProto.input_type)
+}
+inline ::std::string* MethodDescriptorProto::mutable_input_type() {
+ set_has_input_type();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.input_type)
+ return input_type_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* MethodDescriptorProto::release_input_type() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.input_type)
+ clear_has_input_type();
+ return input_type_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void MethodDescriptorProto::set_allocated_input_type(::std::string* input_type) {
+ if (input_type != NULL) {
+ set_has_input_type();
+ } else {
+ clear_has_input_type();
+ }
+ input_type_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), input_type);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.input_type)
+}
+
+// optional string output_type = 3;
+inline bool MethodDescriptorProto::has_output_type() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void MethodDescriptorProto::set_has_output_type() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void MethodDescriptorProto::clear_has_output_type() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void MethodDescriptorProto::clear_output_type() {
+ output_type_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_output_type();
+}
+inline const ::std::string& MethodDescriptorProto::output_type() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.output_type)
+ return output_type_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void MethodDescriptorProto::set_output_type(const ::std::string& value) {
+ set_has_output_type();
+ output_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.output_type)
+}
+inline void MethodDescriptorProto::set_output_type(const char* value) {
+ set_has_output_type();
+ output_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.MethodDescriptorProto.output_type)
+}
+inline void MethodDescriptorProto::set_output_type(const char* value, size_t size) {
+ set_has_output_type();
+ output_type_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.MethodDescriptorProto.output_type)
+}
+inline ::std::string* MethodDescriptorProto::mutable_output_type() {
+ set_has_output_type();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.output_type)
+ return output_type_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* MethodDescriptorProto::release_output_type() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.output_type)
+ clear_has_output_type();
+ return output_type_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void MethodDescriptorProto::set_allocated_output_type(::std::string* output_type) {
+ if (output_type != NULL) {
+ set_has_output_type();
+ } else {
+ clear_has_output_type();
+ }
+ output_type_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), output_type);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.output_type)
+}
+
+// optional .google.protobuf.MethodOptions options = 4;
+inline bool MethodDescriptorProto::has_options() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void MethodDescriptorProto::set_has_options() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void MethodDescriptorProto::clear_has_options() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void MethodDescriptorProto::clear_options() {
+ if (options_ != NULL) options_->::google::protobuf::MethodOptions::Clear();
+ clear_has_options();
+}
+inline const ::google::protobuf::MethodOptions& MethodDescriptorProto::options() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.options)
+ return options_ != NULL ? *options_ : *default_instance_->options_;
+}
+inline ::google::protobuf::MethodOptions* MethodDescriptorProto::mutable_options() {
+ set_has_options();
+ if (options_ == NULL) {
+ options_ = new ::google::protobuf::MethodOptions;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodDescriptorProto.options)
+ return options_;
+}
+inline ::google::protobuf::MethodOptions* MethodDescriptorProto::release_options() {
+ // @@protoc_insertion_point(field_release:google.protobuf.MethodDescriptorProto.options)
+ clear_has_options();
+ ::google::protobuf::MethodOptions* temp = options_;
+ options_ = NULL;
+ return temp;
+}
+inline void MethodDescriptorProto::set_allocated_options(::google::protobuf::MethodOptions* options) {
+ delete options_;
+ options_ = options;
+ if (options) {
+ set_has_options();
+ } else {
+ clear_has_options();
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.MethodDescriptorProto.options)
+}
+
+// optional bool client_streaming = 5 [default = false];
+inline bool MethodDescriptorProto::has_client_streaming() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+inline void MethodDescriptorProto::set_has_client_streaming() {
+ _has_bits_[0] |= 0x00000010u;
+}
+inline void MethodDescriptorProto::clear_has_client_streaming() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+inline void MethodDescriptorProto::clear_client_streaming() {
+ client_streaming_ = false;
+ clear_has_client_streaming();
+}
+inline bool MethodDescriptorProto::client_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.client_streaming)
+ return client_streaming_;
+}
+inline void MethodDescriptorProto::set_client_streaming(bool value) {
+ set_has_client_streaming();
+ client_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.client_streaming)
+}
+
+// optional bool server_streaming = 6 [default = false];
+inline bool MethodDescriptorProto::has_server_streaming() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+inline void MethodDescriptorProto::set_has_server_streaming() {
+ _has_bits_[0] |= 0x00000020u;
+}
+inline void MethodDescriptorProto::clear_has_server_streaming() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+inline void MethodDescriptorProto::clear_server_streaming() {
+ server_streaming_ = false;
+ clear_has_server_streaming();
+}
+inline bool MethodDescriptorProto::server_streaming() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodDescriptorProto.server_streaming)
+ return server_streaming_;
+}
+inline void MethodDescriptorProto::set_server_streaming(bool value) {
+ set_has_server_streaming();
+ server_streaming_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodDescriptorProto.server_streaming)
+}
+
+// -------------------------------------------------------------------
+
+// FileOptions
+
+// optional string java_package = 1;
+inline bool FileOptions::has_java_package() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void FileOptions::set_has_java_package() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void FileOptions::clear_has_java_package() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void FileOptions::clear_java_package() {
+ java_package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_java_package();
+}
+inline const ::std::string& FileOptions::java_package() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_package)
+ return java_package_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_java_package(const ::std::string& value) {
+ set_has_java_package();
+ java_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_package)
+}
+inline void FileOptions::set_java_package(const char* value) {
+ set_has_java_package();
+ java_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.java_package)
+}
+inline void FileOptions::set_java_package(const char* value, size_t size) {
+ set_has_java_package();
+ java_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.java_package)
+}
+inline ::std::string* FileOptions::mutable_java_package() {
+ set_has_java_package();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.java_package)
+ return java_package_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileOptions::release_java_package() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.java_package)
+ clear_has_java_package();
+ return java_package_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_allocated_java_package(::std::string* java_package) {
+ if (java_package != NULL) {
+ set_has_java_package();
+ } else {
+ clear_has_java_package();
+ }
+ java_package_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), java_package);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.java_package)
+}
+
+// optional string java_outer_classname = 8;
+inline bool FileOptions::has_java_outer_classname() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void FileOptions::set_has_java_outer_classname() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void FileOptions::clear_has_java_outer_classname() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void FileOptions::clear_java_outer_classname() {
+ java_outer_classname_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_java_outer_classname();
+}
+inline const ::std::string& FileOptions::java_outer_classname() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_outer_classname)
+ return java_outer_classname_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_java_outer_classname(const ::std::string& value) {
+ set_has_java_outer_classname();
+ java_outer_classname_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_outer_classname)
+}
+inline void FileOptions::set_java_outer_classname(const char* value) {
+ set_has_java_outer_classname();
+ java_outer_classname_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.java_outer_classname)
+}
+inline void FileOptions::set_java_outer_classname(const char* value, size_t size) {
+ set_has_java_outer_classname();
+ java_outer_classname_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.java_outer_classname)
+}
+inline ::std::string* FileOptions::mutable_java_outer_classname() {
+ set_has_java_outer_classname();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.java_outer_classname)
+ return java_outer_classname_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileOptions::release_java_outer_classname() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.java_outer_classname)
+ clear_has_java_outer_classname();
+ return java_outer_classname_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_allocated_java_outer_classname(::std::string* java_outer_classname) {
+ if (java_outer_classname != NULL) {
+ set_has_java_outer_classname();
+ } else {
+ clear_has_java_outer_classname();
+ }
+ java_outer_classname_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), java_outer_classname);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.java_outer_classname)
+}
+
+// optional bool java_multiple_files = 10 [default = false];
+inline bool FileOptions::has_java_multiple_files() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void FileOptions::set_has_java_multiple_files() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void FileOptions::clear_has_java_multiple_files() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void FileOptions::clear_java_multiple_files() {
+ java_multiple_files_ = false;
+ clear_has_java_multiple_files();
+}
+inline bool FileOptions::java_multiple_files() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_multiple_files)
+ return java_multiple_files_;
+}
+inline void FileOptions::set_java_multiple_files(bool value) {
+ set_has_java_multiple_files();
+ java_multiple_files_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_multiple_files)
+}
+
+// optional bool java_generate_equals_and_hash = 20 [default = false];
+inline bool FileOptions::has_java_generate_equals_and_hash() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void FileOptions::set_has_java_generate_equals_and_hash() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void FileOptions::clear_has_java_generate_equals_and_hash() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void FileOptions::clear_java_generate_equals_and_hash() {
+ java_generate_equals_and_hash_ = false;
+ clear_has_java_generate_equals_and_hash();
+}
+inline bool FileOptions::java_generate_equals_and_hash() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_generate_equals_and_hash)
+ return java_generate_equals_and_hash_;
+}
+inline void FileOptions::set_java_generate_equals_and_hash(bool value) {
+ set_has_java_generate_equals_and_hash();
+ java_generate_equals_and_hash_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_generate_equals_and_hash)
+}
+
+// optional bool java_string_check_utf8 = 27 [default = false];
+inline bool FileOptions::has_java_string_check_utf8() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+inline void FileOptions::set_has_java_string_check_utf8() {
+ _has_bits_[0] |= 0x00000010u;
+}
+inline void FileOptions::clear_has_java_string_check_utf8() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+inline void FileOptions::clear_java_string_check_utf8() {
+ java_string_check_utf8_ = false;
+ clear_has_java_string_check_utf8();
+}
+inline bool FileOptions::java_string_check_utf8() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_string_check_utf8)
+ return java_string_check_utf8_;
+}
+inline void FileOptions::set_java_string_check_utf8(bool value) {
+ set_has_java_string_check_utf8();
+ java_string_check_utf8_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_string_check_utf8)
+}
+
+// optional .google.protobuf.FileOptions.OptimizeMode optimize_for = 9 [default = SPEED];
+inline bool FileOptions::has_optimize_for() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+inline void FileOptions::set_has_optimize_for() {
+ _has_bits_[0] |= 0x00000020u;
+}
+inline void FileOptions::clear_has_optimize_for() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+inline void FileOptions::clear_optimize_for() {
+ optimize_for_ = 1;
+ clear_has_optimize_for();
+}
+inline ::google::protobuf::FileOptions_OptimizeMode FileOptions::optimize_for() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.optimize_for)
+ return static_cast< ::google::protobuf::FileOptions_OptimizeMode >(optimize_for_);
+}
+inline void FileOptions::set_optimize_for(::google::protobuf::FileOptions_OptimizeMode value) {
+ assert(::google::protobuf::FileOptions_OptimizeMode_IsValid(value));
+ set_has_optimize_for();
+ optimize_for_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.optimize_for)
+}
+
+// optional string go_package = 11;
+inline bool FileOptions::has_go_package() const {
+ return (_has_bits_[0] & 0x00000040u) != 0;
+}
+inline void FileOptions::set_has_go_package() {
+ _has_bits_[0] |= 0x00000040u;
+}
+inline void FileOptions::clear_has_go_package() {
+ _has_bits_[0] &= ~0x00000040u;
+}
+inline void FileOptions::clear_go_package() {
+ go_package_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_go_package();
+}
+inline const ::std::string& FileOptions::go_package() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.go_package)
+ return go_package_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_go_package(const ::std::string& value) {
+ set_has_go_package();
+ go_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.go_package)
+}
+inline void FileOptions::set_go_package(const char* value) {
+ set_has_go_package();
+ go_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.go_package)
+}
+inline void FileOptions::set_go_package(const char* value, size_t size) {
+ set_has_go_package();
+ go_package_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.go_package)
+}
+inline ::std::string* FileOptions::mutable_go_package() {
+ set_has_go_package();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.go_package)
+ return go_package_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileOptions::release_go_package() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.go_package)
+ clear_has_go_package();
+ return go_package_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_allocated_go_package(::std::string* go_package) {
+ if (go_package != NULL) {
+ set_has_go_package();
+ } else {
+ clear_has_go_package();
+ }
+ go_package_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), go_package);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.go_package)
+}
+
+// optional bool cc_generic_services = 16 [default = false];
+inline bool FileOptions::has_cc_generic_services() const {
+ return (_has_bits_[0] & 0x00000080u) != 0;
+}
+inline void FileOptions::set_has_cc_generic_services() {
+ _has_bits_[0] |= 0x00000080u;
+}
+inline void FileOptions::clear_has_cc_generic_services() {
+ _has_bits_[0] &= ~0x00000080u;
+}
+inline void FileOptions::clear_cc_generic_services() {
+ cc_generic_services_ = false;
+ clear_has_cc_generic_services();
+}
+inline bool FileOptions::cc_generic_services() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.cc_generic_services)
+ return cc_generic_services_;
+}
+inline void FileOptions::set_cc_generic_services(bool value) {
+ set_has_cc_generic_services();
+ cc_generic_services_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.cc_generic_services)
+}
+
+// optional bool java_generic_services = 17 [default = false];
+inline bool FileOptions::has_java_generic_services() const {
+ return (_has_bits_[0] & 0x00000100u) != 0;
+}
+inline void FileOptions::set_has_java_generic_services() {
+ _has_bits_[0] |= 0x00000100u;
+}
+inline void FileOptions::clear_has_java_generic_services() {
+ _has_bits_[0] &= ~0x00000100u;
+}
+inline void FileOptions::clear_java_generic_services() {
+ java_generic_services_ = false;
+ clear_has_java_generic_services();
+}
+inline bool FileOptions::java_generic_services() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.java_generic_services)
+ return java_generic_services_;
+}
+inline void FileOptions::set_java_generic_services(bool value) {
+ set_has_java_generic_services();
+ java_generic_services_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.java_generic_services)
+}
+
+// optional bool py_generic_services = 18 [default = false];
+inline bool FileOptions::has_py_generic_services() const {
+ return (_has_bits_[0] & 0x00000200u) != 0;
+}
+inline void FileOptions::set_has_py_generic_services() {
+ _has_bits_[0] |= 0x00000200u;
+}
+inline void FileOptions::clear_has_py_generic_services() {
+ _has_bits_[0] &= ~0x00000200u;
+}
+inline void FileOptions::clear_py_generic_services() {
+ py_generic_services_ = false;
+ clear_has_py_generic_services();
+}
+inline bool FileOptions::py_generic_services() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.py_generic_services)
+ return py_generic_services_;
+}
+inline void FileOptions::set_py_generic_services(bool value) {
+ set_has_py_generic_services();
+ py_generic_services_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.py_generic_services)
+}
+
+// optional bool deprecated = 23 [default = false];
+inline bool FileOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000400u) != 0;
+}
+inline void FileOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000400u;
+}
+inline void FileOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000400u;
+}
+inline void FileOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+inline bool FileOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.deprecated)
+ return deprecated_;
+}
+inline void FileOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.deprecated)
+}
+
+// optional bool cc_enable_arenas = 31 [default = false];
+inline bool FileOptions::has_cc_enable_arenas() const {
+ return (_has_bits_[0] & 0x00000800u) != 0;
+}
+inline void FileOptions::set_has_cc_enable_arenas() {
+ _has_bits_[0] |= 0x00000800u;
+}
+inline void FileOptions::clear_has_cc_enable_arenas() {
+ _has_bits_[0] &= ~0x00000800u;
+}
+inline void FileOptions::clear_cc_enable_arenas() {
+ cc_enable_arenas_ = false;
+ clear_has_cc_enable_arenas();
+}
+inline bool FileOptions::cc_enable_arenas() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.cc_enable_arenas)
+ return cc_enable_arenas_;
+}
+inline void FileOptions::set_cc_enable_arenas(bool value) {
+ set_has_cc_enable_arenas();
+ cc_enable_arenas_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.cc_enable_arenas)
+}
+
+// optional string objc_class_prefix = 36;
+inline bool FileOptions::has_objc_class_prefix() const {
+ return (_has_bits_[0] & 0x00001000u) != 0;
+}
+inline void FileOptions::set_has_objc_class_prefix() {
+ _has_bits_[0] |= 0x00001000u;
+}
+inline void FileOptions::clear_has_objc_class_prefix() {
+ _has_bits_[0] &= ~0x00001000u;
+}
+inline void FileOptions::clear_objc_class_prefix() {
+ objc_class_prefix_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_objc_class_prefix();
+}
+inline const ::std::string& FileOptions::objc_class_prefix() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.objc_class_prefix)
+ return objc_class_prefix_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_objc_class_prefix(const ::std::string& value) {
+ set_has_objc_class_prefix();
+ objc_class_prefix_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.objc_class_prefix)
+}
+inline void FileOptions::set_objc_class_prefix(const char* value) {
+ set_has_objc_class_prefix();
+ objc_class_prefix_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.objc_class_prefix)
+}
+inline void FileOptions::set_objc_class_prefix(const char* value, size_t size) {
+ set_has_objc_class_prefix();
+ objc_class_prefix_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.objc_class_prefix)
+}
+inline ::std::string* FileOptions::mutable_objc_class_prefix() {
+ set_has_objc_class_prefix();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.objc_class_prefix)
+ return objc_class_prefix_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileOptions::release_objc_class_prefix() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.objc_class_prefix)
+ clear_has_objc_class_prefix();
+ return objc_class_prefix_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_allocated_objc_class_prefix(::std::string* objc_class_prefix) {
+ if (objc_class_prefix != NULL) {
+ set_has_objc_class_prefix();
+ } else {
+ clear_has_objc_class_prefix();
+ }
+ objc_class_prefix_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), objc_class_prefix);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.objc_class_prefix)
+}
+
+// optional string csharp_namespace = 37;
+inline bool FileOptions::has_csharp_namespace() const {
+ return (_has_bits_[0] & 0x00002000u) != 0;
+}
+inline void FileOptions::set_has_csharp_namespace() {
+ _has_bits_[0] |= 0x00002000u;
+}
+inline void FileOptions::clear_has_csharp_namespace() {
+ _has_bits_[0] &= ~0x00002000u;
+}
+inline void FileOptions::clear_csharp_namespace() {
+ csharp_namespace_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_csharp_namespace();
+}
+inline const ::std::string& FileOptions::csharp_namespace() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.csharp_namespace)
+ return csharp_namespace_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_csharp_namespace(const ::std::string& value) {
+ set_has_csharp_namespace();
+ csharp_namespace_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.FileOptions.csharp_namespace)
+}
+inline void FileOptions::set_csharp_namespace(const char* value) {
+ set_has_csharp_namespace();
+ csharp_namespace_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FileOptions.csharp_namespace)
+}
+inline void FileOptions::set_csharp_namespace(const char* value, size_t size) {
+ set_has_csharp_namespace();
+ csharp_namespace_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FileOptions.csharp_namespace)
+}
+inline ::std::string* FileOptions::mutable_csharp_namespace() {
+ set_has_csharp_namespace();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.csharp_namespace)
+ return csharp_namespace_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* FileOptions::release_csharp_namespace() {
+ // @@protoc_insertion_point(field_release:google.protobuf.FileOptions.csharp_namespace)
+ clear_has_csharp_namespace();
+ return csharp_namespace_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void FileOptions::set_allocated_csharp_namespace(::std::string* csharp_namespace) {
+ if (csharp_namespace != NULL) {
+ set_has_csharp_namespace();
+ } else {
+ clear_has_csharp_namespace();
+ }
+ csharp_namespace_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), csharp_namespace);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.FileOptions.csharp_namespace)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int FileOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void FileOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& FileOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* FileOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* FileOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+FileOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FileOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+FileOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FileOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// MessageOptions
+
+// optional bool message_set_wire_format = 1 [default = false];
+inline bool MessageOptions::has_message_set_wire_format() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void MessageOptions::set_has_message_set_wire_format() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void MessageOptions::clear_has_message_set_wire_format() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void MessageOptions::clear_message_set_wire_format() {
+ message_set_wire_format_ = false;
+ clear_has_message_set_wire_format();
+}
+inline bool MessageOptions::message_set_wire_format() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.message_set_wire_format)
+ return message_set_wire_format_;
+}
+inline void MessageOptions::set_message_set_wire_format(bool value) {
+ set_has_message_set_wire_format();
+ message_set_wire_format_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.message_set_wire_format)
+}
+
+// optional bool no_standard_descriptor_accessor = 2 [default = false];
+inline bool MessageOptions::has_no_standard_descriptor_accessor() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void MessageOptions::set_has_no_standard_descriptor_accessor() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void MessageOptions::clear_has_no_standard_descriptor_accessor() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void MessageOptions::clear_no_standard_descriptor_accessor() {
+ no_standard_descriptor_accessor_ = false;
+ clear_has_no_standard_descriptor_accessor();
+}
+inline bool MessageOptions::no_standard_descriptor_accessor() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.no_standard_descriptor_accessor)
+ return no_standard_descriptor_accessor_;
+}
+inline void MessageOptions::set_no_standard_descriptor_accessor(bool value) {
+ set_has_no_standard_descriptor_accessor();
+ no_standard_descriptor_accessor_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.no_standard_descriptor_accessor)
+}
+
+// optional bool deprecated = 3 [default = false];
+inline bool MessageOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void MessageOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void MessageOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void MessageOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+inline bool MessageOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.deprecated)
+ return deprecated_;
+}
+inline void MessageOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.deprecated)
+}
+
+// optional bool map_entry = 7;
+inline bool MessageOptions::has_map_entry() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void MessageOptions::set_has_map_entry() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void MessageOptions::clear_has_map_entry() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void MessageOptions::clear_map_entry() {
+ map_entry_ = false;
+ clear_has_map_entry();
+}
+inline bool MessageOptions::map_entry() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.map_entry)
+ return map_entry_;
+}
+inline void MessageOptions::set_map_entry(bool value) {
+ set_has_map_entry();
+ map_entry_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MessageOptions.map_entry)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int MessageOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void MessageOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& MessageOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* MessageOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* MessageOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+MessageOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.MessageOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+MessageOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.MessageOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// FieldOptions
+
+// optional .google.protobuf.FieldOptions.CType ctype = 1 [default = STRING];
+inline bool FieldOptions::has_ctype() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void FieldOptions::set_has_ctype() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void FieldOptions::clear_has_ctype() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void FieldOptions::clear_ctype() {
+ ctype_ = 0;
+ clear_has_ctype();
+}
+inline ::google::protobuf::FieldOptions_CType FieldOptions::ctype() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.ctype)
+ return static_cast< ::google::protobuf::FieldOptions_CType >(ctype_);
+}
+inline void FieldOptions::set_ctype(::google::protobuf::FieldOptions_CType value) {
+ assert(::google::protobuf::FieldOptions_CType_IsValid(value));
+ set_has_ctype();
+ ctype_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.ctype)
+}
+
+// optional bool packed = 2;
+inline bool FieldOptions::has_packed() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void FieldOptions::set_has_packed() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void FieldOptions::clear_has_packed() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void FieldOptions::clear_packed() {
+ packed_ = false;
+ clear_has_packed();
+}
+inline bool FieldOptions::packed() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.packed)
+ return packed_;
+}
+inline void FieldOptions::set_packed(bool value) {
+ set_has_packed();
+ packed_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.packed)
+}
+
+// optional .google.protobuf.FieldOptions.JSType jstype = 6 [default = JS_NORMAL];
+inline bool FieldOptions::has_jstype() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void FieldOptions::set_has_jstype() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void FieldOptions::clear_has_jstype() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void FieldOptions::clear_jstype() {
+ jstype_ = 0;
+ clear_has_jstype();
+}
+inline ::google::protobuf::FieldOptions_JSType FieldOptions::jstype() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.jstype)
+ return static_cast< ::google::protobuf::FieldOptions_JSType >(jstype_);
+}
+inline void FieldOptions::set_jstype(::google::protobuf::FieldOptions_JSType value) {
+ assert(::google::protobuf::FieldOptions_JSType_IsValid(value));
+ set_has_jstype();
+ jstype_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.jstype)
+}
+
+// optional bool lazy = 5 [default = false];
+inline bool FieldOptions::has_lazy() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void FieldOptions::set_has_lazy() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void FieldOptions::clear_has_lazy() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void FieldOptions::clear_lazy() {
+ lazy_ = false;
+ clear_has_lazy();
+}
+inline bool FieldOptions::lazy() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.lazy)
+ return lazy_;
+}
+inline void FieldOptions::set_lazy(bool value) {
+ set_has_lazy();
+ lazy_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.lazy)
+}
+
+// optional bool deprecated = 3 [default = false];
+inline bool FieldOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+inline void FieldOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000010u;
+}
+inline void FieldOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+inline void FieldOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+inline bool FieldOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.deprecated)
+ return deprecated_;
+}
+inline void FieldOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.deprecated)
+}
+
+// optional bool weak = 10 [default = false];
+inline bool FieldOptions::has_weak() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+inline void FieldOptions::set_has_weak() {
+ _has_bits_[0] |= 0x00000020u;
+}
+inline void FieldOptions::clear_has_weak() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+inline void FieldOptions::clear_weak() {
+ weak_ = false;
+ clear_has_weak();
+}
+inline bool FieldOptions::weak() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.weak)
+ return weak_;
+}
+inline void FieldOptions::set_weak(bool value) {
+ set_has_weak();
+ weak_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldOptions.weak)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int FieldOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void FieldOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& FieldOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* FieldOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* FieldOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+FieldOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FieldOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+FieldOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FieldOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// OneofOptions
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int OneofOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void OneofOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& OneofOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* OneofOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* OneofOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+OneofOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.OneofOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+OneofOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.OneofOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// EnumOptions
+
+// optional bool allow_alias = 2;
+inline bool EnumOptions::has_allow_alias() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void EnumOptions::set_has_allow_alias() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void EnumOptions::clear_has_allow_alias() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void EnumOptions::clear_allow_alias() {
+ allow_alias_ = false;
+ clear_has_allow_alias();
+}
+inline bool EnumOptions::allow_alias() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumOptions.allow_alias)
+ return allow_alias_;
+}
+inline void EnumOptions::set_allow_alias(bool value) {
+ set_has_allow_alias();
+ allow_alias_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumOptions.allow_alias)
+}
+
+// optional bool deprecated = 3 [default = false];
+inline bool EnumOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void EnumOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void EnumOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void EnumOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+inline bool EnumOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumOptions.deprecated)
+ return deprecated_;
+}
+inline void EnumOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int EnumOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void EnumOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& EnumOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* EnumOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* EnumOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+EnumOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+EnumOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// EnumValueOptions
+
+// optional bool deprecated = 1 [default = false];
+inline bool EnumValueOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void EnumValueOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void EnumValueOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void EnumValueOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+inline bool EnumValueOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueOptions.deprecated)
+ return deprecated_;
+}
+inline void EnumValueOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValueOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int EnumValueOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void EnumValueOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& EnumValueOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* EnumValueOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* EnumValueOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+EnumValueOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+EnumValueOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumValueOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// ServiceOptions
+
+// optional bool deprecated = 33 [default = false];
+inline bool ServiceOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void ServiceOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void ServiceOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void ServiceOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+inline bool ServiceOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceOptions.deprecated)
+ return deprecated_;
+}
+inline void ServiceOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.ServiceOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int ServiceOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void ServiceOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& ServiceOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* ServiceOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* ServiceOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+ServiceOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.ServiceOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+ServiceOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.ServiceOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// MethodOptions
+
+// optional bool deprecated = 33 [default = false];
+inline bool MethodOptions::has_deprecated() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void MethodOptions::set_has_deprecated() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void MethodOptions::clear_has_deprecated() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void MethodOptions::clear_deprecated() {
+ deprecated_ = false;
+ clear_has_deprecated();
+}
+inline bool MethodOptions::deprecated() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodOptions.deprecated)
+ return deprecated_;
+}
+inline void MethodOptions::set_deprecated(bool value) {
+ set_has_deprecated();
+ deprecated_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.MethodOptions.deprecated)
+}
+
+// repeated .google.protobuf.UninterpretedOption uninterpreted_option = 999;
+inline int MethodOptions::uninterpreted_option_size() const {
+ return uninterpreted_option_.size();
+}
+inline void MethodOptions::clear_uninterpreted_option() {
+ uninterpreted_option_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption& MethodOptions::uninterpreted_option(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption* MethodOptions::mutable_uninterpreted_option(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption* MethodOptions::add_uninterpreted_option() {
+ // @@protoc_insertion_point(field_add:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >*
+MethodOptions::mutable_uninterpreted_option() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.MethodOptions.uninterpreted_option)
+ return &uninterpreted_option_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption >&
+MethodOptions::uninterpreted_option() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.MethodOptions.uninterpreted_option)
+ return uninterpreted_option_;
+}
+
+// -------------------------------------------------------------------
+
+// UninterpretedOption_NamePart
+
+// required string name_part = 1;
+inline bool UninterpretedOption_NamePart::has_name_part() const {
+ return (_has_bits_[0] & 0x00000001u) != 0;
+}
+inline void UninterpretedOption_NamePart::set_has_name_part() {
+ _has_bits_[0] |= 0x00000001u;
+}
+inline void UninterpretedOption_NamePart::clear_has_name_part() {
+ _has_bits_[0] &= ~0x00000001u;
+}
+inline void UninterpretedOption_NamePart::clear_name_part() {
+ name_part_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_name_part();
+}
+inline const ::std::string& UninterpretedOption_NamePart::name_part() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.NamePart.name_part)
+ return name_part_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption_NamePart::set_name_part(const ::std::string& value) {
+ set_has_name_part();
+ name_part_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+inline void UninterpretedOption_NamePart::set_name_part(const char* value) {
+ set_has_name_part();
+ name_part_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+inline void UninterpretedOption_NamePart::set_name_part(const char* value, size_t size) {
+ set_has_name_part();
+ name_part_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+inline ::std::string* UninterpretedOption_NamePart::mutable_name_part() {
+ set_has_name_part();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.NamePart.name_part)
+ return name_part_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* UninterpretedOption_NamePart::release_name_part() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.NamePart.name_part)
+ clear_has_name_part();
+ return name_part_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption_NamePart::set_allocated_name_part(::std::string* name_part) {
+ if (name_part != NULL) {
+ set_has_name_part();
+ } else {
+ clear_has_name_part();
+ }
+ name_part_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name_part);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.NamePart.name_part)
+}
+
+// required bool is_extension = 2;
+inline bool UninterpretedOption_NamePart::has_is_extension() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void UninterpretedOption_NamePart::set_has_is_extension() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void UninterpretedOption_NamePart::clear_has_is_extension() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void UninterpretedOption_NamePart::clear_is_extension() {
+ is_extension_ = false;
+ clear_has_is_extension();
+}
+inline bool UninterpretedOption_NamePart::is_extension() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.NamePart.is_extension)
+ return is_extension_;
+}
+inline void UninterpretedOption_NamePart::set_is_extension(bool value) {
+ set_has_is_extension();
+ is_extension_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.NamePart.is_extension)
+}
+
+// -------------------------------------------------------------------
+
+// UninterpretedOption
+
+// repeated .google.protobuf.UninterpretedOption.NamePart name = 2;
+inline int UninterpretedOption::name_size() const {
+ return name_.size();
+}
+inline void UninterpretedOption::clear_name() {
+ name_.Clear();
+}
+inline const ::google::protobuf::UninterpretedOption_NamePart& UninterpretedOption::name(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.name)
+ return name_.Get(index);
+}
+inline ::google::protobuf::UninterpretedOption_NamePart* UninterpretedOption::mutable_name(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.name)
+ return name_.Mutable(index);
+}
+inline ::google::protobuf::UninterpretedOption_NamePart* UninterpretedOption::add_name() {
+ // @@protoc_insertion_point(field_add:google.protobuf.UninterpretedOption.name)
+ return name_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption_NamePart >*
+UninterpretedOption::mutable_name() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.UninterpretedOption.name)
+ return &name_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::UninterpretedOption_NamePart >&
+UninterpretedOption::name() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.UninterpretedOption.name)
+ return name_;
+}
+
+// optional string identifier_value = 3;
+inline bool UninterpretedOption::has_identifier_value() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void UninterpretedOption::set_has_identifier_value() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void UninterpretedOption::clear_has_identifier_value() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void UninterpretedOption::clear_identifier_value() {
+ identifier_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_identifier_value();
+}
+inline const ::std::string& UninterpretedOption::identifier_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.identifier_value)
+ return identifier_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption::set_identifier_value(const ::std::string& value) {
+ set_has_identifier_value();
+ identifier_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.identifier_value)
+}
+inline void UninterpretedOption::set_identifier_value(const char* value) {
+ set_has_identifier_value();
+ identifier_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.identifier_value)
+}
+inline void UninterpretedOption::set_identifier_value(const char* value, size_t size) {
+ set_has_identifier_value();
+ identifier_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.identifier_value)
+}
+inline ::std::string* UninterpretedOption::mutable_identifier_value() {
+ set_has_identifier_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.identifier_value)
+ return identifier_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* UninterpretedOption::release_identifier_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.identifier_value)
+ clear_has_identifier_value();
+ return identifier_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption::set_allocated_identifier_value(::std::string* identifier_value) {
+ if (identifier_value != NULL) {
+ set_has_identifier_value();
+ } else {
+ clear_has_identifier_value();
+ }
+ identifier_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), identifier_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.identifier_value)
+}
+
+// optional uint64 positive_int_value = 4;
+inline bool UninterpretedOption::has_positive_int_value() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void UninterpretedOption::set_has_positive_int_value() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void UninterpretedOption::clear_has_positive_int_value() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void UninterpretedOption::clear_positive_int_value() {
+ positive_int_value_ = GOOGLE_ULONGLONG(0);
+ clear_has_positive_int_value();
+}
+inline ::google::protobuf::uint64 UninterpretedOption::positive_int_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.positive_int_value)
+ return positive_int_value_;
+}
+inline void UninterpretedOption::set_positive_int_value(::google::protobuf::uint64 value) {
+ set_has_positive_int_value();
+ positive_int_value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.positive_int_value)
+}
+
+// optional int64 negative_int_value = 5;
+inline bool UninterpretedOption::has_negative_int_value() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void UninterpretedOption::set_has_negative_int_value() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void UninterpretedOption::clear_has_negative_int_value() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void UninterpretedOption::clear_negative_int_value() {
+ negative_int_value_ = GOOGLE_LONGLONG(0);
+ clear_has_negative_int_value();
+}
+inline ::google::protobuf::int64 UninterpretedOption::negative_int_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.negative_int_value)
+ return negative_int_value_;
+}
+inline void UninterpretedOption::set_negative_int_value(::google::protobuf::int64 value) {
+ set_has_negative_int_value();
+ negative_int_value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.negative_int_value)
+}
+
+// optional double double_value = 6;
+inline bool UninterpretedOption::has_double_value() const {
+ return (_has_bits_[0] & 0x00000010u) != 0;
+}
+inline void UninterpretedOption::set_has_double_value() {
+ _has_bits_[0] |= 0x00000010u;
+}
+inline void UninterpretedOption::clear_has_double_value() {
+ _has_bits_[0] &= ~0x00000010u;
+}
+inline void UninterpretedOption::clear_double_value() {
+ double_value_ = 0;
+ clear_has_double_value();
+}
+inline double UninterpretedOption::double_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.double_value)
+ return double_value_;
+}
+inline void UninterpretedOption::set_double_value(double value) {
+ set_has_double_value();
+ double_value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.double_value)
+}
+
+// optional bytes string_value = 7;
+inline bool UninterpretedOption::has_string_value() const {
+ return (_has_bits_[0] & 0x00000020u) != 0;
+}
+inline void UninterpretedOption::set_has_string_value() {
+ _has_bits_[0] |= 0x00000020u;
+}
+inline void UninterpretedOption::clear_has_string_value() {
+ _has_bits_[0] &= ~0x00000020u;
+}
+inline void UninterpretedOption::clear_string_value() {
+ string_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_string_value();
+}
+inline const ::std::string& UninterpretedOption::string_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.string_value)
+ return string_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption::set_string_value(const ::std::string& value) {
+ set_has_string_value();
+ string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.string_value)
+}
+inline void UninterpretedOption::set_string_value(const char* value) {
+ set_has_string_value();
+ string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.string_value)
+}
+inline void UninterpretedOption::set_string_value(const void* value, size_t size) {
+ set_has_string_value();
+ string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.string_value)
+}
+inline ::std::string* UninterpretedOption::mutable_string_value() {
+ set_has_string_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.string_value)
+ return string_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* UninterpretedOption::release_string_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.string_value)
+ clear_has_string_value();
+ return string_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption::set_allocated_string_value(::std::string* string_value) {
+ if (string_value != NULL) {
+ set_has_string_value();
+ } else {
+ clear_has_string_value();
+ }
+ string_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), string_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.string_value)
+}
+
+// optional string aggregate_value = 8;
+inline bool UninterpretedOption::has_aggregate_value() const {
+ return (_has_bits_[0] & 0x00000040u) != 0;
+}
+inline void UninterpretedOption::set_has_aggregate_value() {
+ _has_bits_[0] |= 0x00000040u;
+}
+inline void UninterpretedOption::clear_has_aggregate_value() {
+ _has_bits_[0] &= ~0x00000040u;
+}
+inline void UninterpretedOption::clear_aggregate_value() {
+ aggregate_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_aggregate_value();
+}
+inline const ::std::string& UninterpretedOption::aggregate_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UninterpretedOption.aggregate_value)
+ return aggregate_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption::set_aggregate_value(const ::std::string& value) {
+ set_has_aggregate_value();
+ aggregate_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.UninterpretedOption.aggregate_value)
+}
+inline void UninterpretedOption::set_aggregate_value(const char* value) {
+ set_has_aggregate_value();
+ aggregate_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.UninterpretedOption.aggregate_value)
+}
+inline void UninterpretedOption::set_aggregate_value(const char* value, size_t size) {
+ set_has_aggregate_value();
+ aggregate_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.UninterpretedOption.aggregate_value)
+}
+inline ::std::string* UninterpretedOption::mutable_aggregate_value() {
+ set_has_aggregate_value();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.UninterpretedOption.aggregate_value)
+ return aggregate_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* UninterpretedOption::release_aggregate_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.UninterpretedOption.aggregate_value)
+ clear_has_aggregate_value();
+ return aggregate_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void UninterpretedOption::set_allocated_aggregate_value(::std::string* aggregate_value) {
+ if (aggregate_value != NULL) {
+ set_has_aggregate_value();
+ } else {
+ clear_has_aggregate_value();
+ }
+ aggregate_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), aggregate_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.UninterpretedOption.aggregate_value)
+}
+
+// -------------------------------------------------------------------
+
+// SourceCodeInfo_Location
+
+// repeated int32 path = 1 [packed = true];
+inline int SourceCodeInfo_Location::path_size() const {
+ return path_.size();
+}
+inline void SourceCodeInfo_Location::clear_path() {
+ path_.Clear();
+}
+inline ::google::protobuf::int32 SourceCodeInfo_Location::path(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.path)
+ return path_.Get(index);
+}
+inline void SourceCodeInfo_Location::set_path(int index, ::google::protobuf::int32 value) {
+ path_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.path)
+}
+inline void SourceCodeInfo_Location::add_path(::google::protobuf::int32 value) {
+ path_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.Location.path)
+}
+inline const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+SourceCodeInfo_Location::path() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.Location.path)
+ return path_;
+}
+inline ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+SourceCodeInfo_Location::mutable_path() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.Location.path)
+ return &path_;
+}
+
+// repeated int32 span = 2 [packed = true];
+inline int SourceCodeInfo_Location::span_size() const {
+ return span_.size();
+}
+inline void SourceCodeInfo_Location::clear_span() {
+ span_.Clear();
+}
+inline ::google::protobuf::int32 SourceCodeInfo_Location::span(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.span)
+ return span_.Get(index);
+}
+inline void SourceCodeInfo_Location::set_span(int index, ::google::protobuf::int32 value) {
+ span_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.span)
+}
+inline void SourceCodeInfo_Location::add_span(::google::protobuf::int32 value) {
+ span_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.Location.span)
+}
+inline const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+SourceCodeInfo_Location::span() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.Location.span)
+ return span_;
+}
+inline ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+SourceCodeInfo_Location::mutable_span() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.Location.span)
+ return &span_;
+}
+
+// optional string leading_comments = 3;
+inline bool SourceCodeInfo_Location::has_leading_comments() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void SourceCodeInfo_Location::set_has_leading_comments() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void SourceCodeInfo_Location::clear_has_leading_comments() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void SourceCodeInfo_Location::clear_leading_comments() {
+ leading_comments_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_leading_comments();
+}
+inline const ::std::string& SourceCodeInfo_Location::leading_comments() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.leading_comments)
+ return leading_comments_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void SourceCodeInfo_Location::set_leading_comments(const ::std::string& value) {
+ set_has_leading_comments();
+ leading_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+inline void SourceCodeInfo_Location::set_leading_comments(const char* value) {
+ set_has_leading_comments();
+ leading_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+inline void SourceCodeInfo_Location::set_leading_comments(const char* value, size_t size) {
+ set_has_leading_comments();
+ leading_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+inline ::std::string* SourceCodeInfo_Location::mutable_leading_comments() {
+ set_has_leading_comments();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.Location.leading_comments)
+ return leading_comments_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* SourceCodeInfo_Location::release_leading_comments() {
+ // @@protoc_insertion_point(field_release:google.protobuf.SourceCodeInfo.Location.leading_comments)
+ clear_has_leading_comments();
+ return leading_comments_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void SourceCodeInfo_Location::set_allocated_leading_comments(::std::string* leading_comments) {
+ if (leading_comments != NULL) {
+ set_has_leading_comments();
+ } else {
+ clear_has_leading_comments();
+ }
+ leading_comments_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), leading_comments);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.SourceCodeInfo.Location.leading_comments)
+}
+
+// optional string trailing_comments = 4;
+inline bool SourceCodeInfo_Location::has_trailing_comments() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void SourceCodeInfo_Location::set_has_trailing_comments() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void SourceCodeInfo_Location::clear_has_trailing_comments() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void SourceCodeInfo_Location::clear_trailing_comments() {
+ trailing_comments_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_trailing_comments();
+}
+inline const ::std::string& SourceCodeInfo_Location::trailing_comments() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+ return trailing_comments_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void SourceCodeInfo_Location::set_trailing_comments(const ::std::string& value) {
+ set_has_trailing_comments();
+ trailing_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+inline void SourceCodeInfo_Location::set_trailing_comments(const char* value) {
+ set_has_trailing_comments();
+ trailing_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+inline void SourceCodeInfo_Location::set_trailing_comments(const char* value, size_t size) {
+ set_has_trailing_comments();
+ trailing_comments_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+inline ::std::string* SourceCodeInfo_Location::mutable_trailing_comments() {
+ set_has_trailing_comments();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+ return trailing_comments_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* SourceCodeInfo_Location::release_trailing_comments() {
+ // @@protoc_insertion_point(field_release:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+ clear_has_trailing_comments();
+ return trailing_comments_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void SourceCodeInfo_Location::set_allocated_trailing_comments(::std::string* trailing_comments) {
+ if (trailing_comments != NULL) {
+ set_has_trailing_comments();
+ } else {
+ clear_has_trailing_comments();
+ }
+ trailing_comments_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), trailing_comments);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.SourceCodeInfo.Location.trailing_comments)
+}
+
+// repeated string leading_detached_comments = 6;
+inline int SourceCodeInfo_Location::leading_detached_comments_size() const {
+ return leading_detached_comments_.size();
+}
+inline void SourceCodeInfo_Location::clear_leading_detached_comments() {
+ leading_detached_comments_.Clear();
+}
+inline const ::std::string& SourceCodeInfo_Location::leading_detached_comments(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_.Get(index);
+}
+inline ::std::string* SourceCodeInfo_Location::mutable_leading_detached_comments(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_.Mutable(index);
+}
+inline void SourceCodeInfo_Location::set_leading_detached_comments(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ leading_detached_comments_.Mutable(index)->assign(value);
+}
+inline void SourceCodeInfo_Location::set_leading_detached_comments(int index, const char* value) {
+ leading_detached_comments_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+inline void SourceCodeInfo_Location::set_leading_detached_comments(int index, const char* value, size_t size) {
+ leading_detached_comments_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+inline ::std::string* SourceCodeInfo_Location::add_leading_detached_comments() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_.Add();
+}
+inline void SourceCodeInfo_Location::add_leading_detached_comments(const ::std::string& value) {
+ leading_detached_comments_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+inline void SourceCodeInfo_Location::add_leading_detached_comments(const char* value) {
+ leading_detached_comments_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+inline void SourceCodeInfo_Location::add_leading_detached_comments(const char* value, size_t size) {
+ leading_detached_comments_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+}
+inline const ::google::protobuf::RepeatedPtrField< ::std::string>&
+SourceCodeInfo_Location::leading_detached_comments() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return leading_detached_comments_;
+}
+inline ::google::protobuf::RepeatedPtrField< ::std::string>*
+SourceCodeInfo_Location::mutable_leading_detached_comments() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.Location.leading_detached_comments)
+ return &leading_detached_comments_;
+}
+
+// -------------------------------------------------------------------
+
+// SourceCodeInfo
+
+// repeated .google.protobuf.SourceCodeInfo.Location location = 1;
+inline int SourceCodeInfo::location_size() const {
+ return location_.size();
+}
+inline void SourceCodeInfo::clear_location() {
+ location_.Clear();
+}
+inline const ::google::protobuf::SourceCodeInfo_Location& SourceCodeInfo::location(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceCodeInfo.location)
+ return location_.Get(index);
+}
+inline ::google::protobuf::SourceCodeInfo_Location* SourceCodeInfo::mutable_location(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceCodeInfo.location)
+ return location_.Mutable(index);
+}
+inline ::google::protobuf::SourceCodeInfo_Location* SourceCodeInfo::add_location() {
+ // @@protoc_insertion_point(field_add:google.protobuf.SourceCodeInfo.location)
+ return location_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::SourceCodeInfo_Location >*
+SourceCodeInfo::mutable_location() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.SourceCodeInfo.location)
+ return &location_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::SourceCodeInfo_Location >&
+SourceCodeInfo::location() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.SourceCodeInfo.location)
+ return location_;
+}
+
+// -------------------------------------------------------------------
+
+// GeneratedCodeInfo_Annotation
+
+// repeated int32 path = 1 [packed = true];
+inline int GeneratedCodeInfo_Annotation::path_size() const {
+ return path_.size();
+}
+inline void GeneratedCodeInfo_Annotation::clear_path() {
+ path_.Clear();
+}
+inline ::google::protobuf::int32 GeneratedCodeInfo_Annotation::path(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.path)
+ return path_.Get(index);
+}
+inline void GeneratedCodeInfo_Annotation::set_path(int index, ::google::protobuf::int32 value) {
+ path_.Set(index, value);
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.path)
+}
+inline void GeneratedCodeInfo_Annotation::add_path(::google::protobuf::int32 value) {
+ path_.Add(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.GeneratedCodeInfo.Annotation.path)
+}
+inline const ::google::protobuf::RepeatedField< ::google::protobuf::int32 >&
+GeneratedCodeInfo_Annotation::path() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.GeneratedCodeInfo.Annotation.path)
+ return path_;
+}
+inline ::google::protobuf::RepeatedField< ::google::protobuf::int32 >*
+GeneratedCodeInfo_Annotation::mutable_path() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.GeneratedCodeInfo.Annotation.path)
+ return &path_;
+}
+
+// optional string source_file = 2;
+inline bool GeneratedCodeInfo_Annotation::has_source_file() const {
+ return (_has_bits_[0] & 0x00000002u) != 0;
+}
+inline void GeneratedCodeInfo_Annotation::set_has_source_file() {
+ _has_bits_[0] |= 0x00000002u;
+}
+inline void GeneratedCodeInfo_Annotation::clear_has_source_file() {
+ _has_bits_[0] &= ~0x00000002u;
+}
+inline void GeneratedCodeInfo_Annotation::clear_source_file() {
+ source_file_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_source_file();
+}
+inline const ::std::string& GeneratedCodeInfo_Annotation::source_file() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+ return source_file_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void GeneratedCodeInfo_Annotation::set_source_file(const ::std::string& value) {
+ set_has_source_file();
+ source_file_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+inline void GeneratedCodeInfo_Annotation::set_source_file(const char* value) {
+ set_has_source_file();
+ source_file_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+inline void GeneratedCodeInfo_Annotation::set_source_file(const char* value, size_t size) {
+ set_has_source_file();
+ source_file_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+inline ::std::string* GeneratedCodeInfo_Annotation::mutable_source_file() {
+ set_has_source_file();
+ // @@protoc_insertion_point(field_mutable:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+ return source_file_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* GeneratedCodeInfo_Annotation::release_source_file() {
+ // @@protoc_insertion_point(field_release:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+ clear_has_source_file();
+ return source_file_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void GeneratedCodeInfo_Annotation::set_allocated_source_file(::std::string* source_file) {
+ if (source_file != NULL) {
+ set_has_source_file();
+ } else {
+ clear_has_source_file();
+ }
+ source_file_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), source_file);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.GeneratedCodeInfo.Annotation.source_file)
+}
+
+// optional int32 begin = 3;
+inline bool GeneratedCodeInfo_Annotation::has_begin() const {
+ return (_has_bits_[0] & 0x00000004u) != 0;
+}
+inline void GeneratedCodeInfo_Annotation::set_has_begin() {
+ _has_bits_[0] |= 0x00000004u;
+}
+inline void GeneratedCodeInfo_Annotation::clear_has_begin() {
+ _has_bits_[0] &= ~0x00000004u;
+}
+inline void GeneratedCodeInfo_Annotation::clear_begin() {
+ begin_ = 0;
+ clear_has_begin();
+}
+inline ::google::protobuf::int32 GeneratedCodeInfo_Annotation::begin() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.begin)
+ return begin_;
+}
+inline void GeneratedCodeInfo_Annotation::set_begin(::google::protobuf::int32 value) {
+ set_has_begin();
+ begin_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.begin)
+}
+
+// optional int32 end = 4;
+inline bool GeneratedCodeInfo_Annotation::has_end() const {
+ return (_has_bits_[0] & 0x00000008u) != 0;
+}
+inline void GeneratedCodeInfo_Annotation::set_has_end() {
+ _has_bits_[0] |= 0x00000008u;
+}
+inline void GeneratedCodeInfo_Annotation::clear_has_end() {
+ _has_bits_[0] &= ~0x00000008u;
+}
+inline void GeneratedCodeInfo_Annotation::clear_end() {
+ end_ = 0;
+ clear_has_end();
+}
+inline ::google::protobuf::int32 GeneratedCodeInfo_Annotation::end() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.Annotation.end)
+ return end_;
+}
+inline void GeneratedCodeInfo_Annotation::set_end(::google::protobuf::int32 value) {
+ set_has_end();
+ end_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.GeneratedCodeInfo.Annotation.end)
+}
+
+// -------------------------------------------------------------------
+
+// GeneratedCodeInfo
+
+// repeated .google.protobuf.GeneratedCodeInfo.Annotation annotation = 1;
+inline int GeneratedCodeInfo::annotation_size() const {
+ return annotation_.size();
+}
+inline void GeneratedCodeInfo::clear_annotation() {
+ annotation_.Clear();
+}
+inline const ::google::protobuf::GeneratedCodeInfo_Annotation& GeneratedCodeInfo::annotation(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_.Get(index);
+}
+inline ::google::protobuf::GeneratedCodeInfo_Annotation* GeneratedCodeInfo::mutable_annotation(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_.Mutable(index);
+}
+inline ::google::protobuf::GeneratedCodeInfo_Annotation* GeneratedCodeInfo::add_annotation() {
+ // @@protoc_insertion_point(field_add:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::GeneratedCodeInfo_Annotation >*
+GeneratedCodeInfo::mutable_annotation() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.GeneratedCodeInfo.annotation)
+ return &annotation_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::GeneratedCodeInfo_Annotation >&
+GeneratedCodeInfo::annotation() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.GeneratedCodeInfo.annotation)
+ return annotation_;
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+#ifndef SWIG
+namespace google {
+namespace protobuf {
+
+template <> struct is_proto_enum< ::google::protobuf::FieldDescriptorProto_Type> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::FieldDescriptorProto_Type>() {
+ return ::google::protobuf::FieldDescriptorProto_Type_descriptor();
+}
+template <> struct is_proto_enum< ::google::protobuf::FieldDescriptorProto_Label> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::FieldDescriptorProto_Label>() {
+ return ::google::protobuf::FieldDescriptorProto_Label_descriptor();
+}
+template <> struct is_proto_enum< ::google::protobuf::FileOptions_OptimizeMode> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::FileOptions_OptimizeMode>() {
+ return ::google::protobuf::FileOptions_OptimizeMode_descriptor();
+}
+template <> struct is_proto_enum< ::google::protobuf::FieldOptions_CType> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::FieldOptions_CType>() {
+ return ::google::protobuf::FieldOptions_CType_descriptor();
+}
+template <> struct is_proto_enum< ::google::protobuf::FieldOptions_JSType> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::FieldOptions_JSType>() {
+ return ::google::protobuf::FieldOptions_JSType_descriptor();
+}
+
+} // namespace protobuf
+} // namespace google
+#endif // SWIG
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fdescriptor_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.proto b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.proto
new file mode 100644
index 0000000000..28410d4a9a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor.proto
@@ -0,0 +1,813 @@
+// 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.
+//
+// The messages in this file describe the definitions found in .proto files.
+// A valid .proto file can be translated directly to a FileDescriptorProto
+// without any other information (e.g. without reading its imports).
+
+
+syntax = "proto2";
+
+package google.protobuf;
+option go_package = "descriptor";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "DescriptorProtos";
+option csharp_namespace = "Google.Protobuf.Reflection";
+option objc_class_prefix = "GPB";
+option java_generate_equals_and_hash = true;
+
+// descriptor.proto must be optimized for speed because reflection-based
+// algorithms don't work during bootstrapping.
+option optimize_for = SPEED;
+
+// The protocol compiler can output a FileDescriptorSet containing the .proto
+// files it parses.
+message FileDescriptorSet {
+ repeated FileDescriptorProto file = 1;
+}
+
+// Describes a complete .proto file.
+message FileDescriptorProto {
+ optional string name = 1; // file name, relative to root of source tree
+ optional string package = 2; // e.g. "foo", "foo.bar", etc.
+
+ // Names of files imported by this file.
+ repeated string dependency = 3;
+ // Indexes of the public imported files in the dependency list above.
+ repeated int32 public_dependency = 10;
+ // Indexes of the weak imported files in the dependency list.
+ // For Google-internal migration only. Do not use.
+ repeated int32 weak_dependency = 11;
+
+ // All top-level definitions in this file.
+ repeated DescriptorProto message_type = 4;
+ repeated EnumDescriptorProto enum_type = 5;
+ repeated ServiceDescriptorProto service = 6;
+ repeated FieldDescriptorProto extension = 7;
+
+ optional FileOptions options = 8;
+
+ // This field contains optional information about the original source code.
+ // You may safely remove this entire field without harming runtime
+ // functionality of the descriptors -- the information is needed only by
+ // development tools.
+ optional SourceCodeInfo source_code_info = 9;
+
+ // The syntax of the proto file.
+ // The supported values are "proto2" and "proto3".
+ optional string syntax = 12;
+}
+
+// Describes a message type.
+message DescriptorProto {
+ optional string name = 1;
+
+ repeated FieldDescriptorProto field = 2;
+ repeated FieldDescriptorProto extension = 6;
+
+ repeated DescriptorProto nested_type = 3;
+ repeated EnumDescriptorProto enum_type = 4;
+
+ message ExtensionRange {
+ optional int32 start = 1;
+ optional int32 end = 2;
+ }
+ repeated ExtensionRange extension_range = 5;
+
+ repeated OneofDescriptorProto oneof_decl = 8;
+
+ optional MessageOptions options = 7;
+
+ // Range of reserved tag numbers. Reserved tag numbers may not be used by
+ // fields or extension ranges in the same message. Reserved ranges may
+ // not overlap.
+ message ReservedRange {
+ optional int32 start = 1; // Inclusive.
+ optional int32 end = 2; // Exclusive.
+ }
+ repeated ReservedRange reserved_range = 9;
+ // Reserved field names, which may not be used by fields in the same message.
+ // A given name may only be reserved once.
+ repeated string reserved_name = 10;
+}
+
+// Describes a field within a message.
+message FieldDescriptorProto {
+ enum Type {
+ // 0 is reserved for errors.
+ // Order is weird for historical reasons.
+ TYPE_DOUBLE = 1;
+ TYPE_FLOAT = 2;
+ // Not ZigZag encoded. Negative numbers take 10 bytes. Use TYPE_SINT64 if
+ // negative values are likely.
+ TYPE_INT64 = 3;
+ TYPE_UINT64 = 4;
+ // Not ZigZag encoded. Negative numbers take 10 bytes. Use TYPE_SINT32 if
+ // negative values are likely.
+ TYPE_INT32 = 5;
+ TYPE_FIXED64 = 6;
+ TYPE_FIXED32 = 7;
+ TYPE_BOOL = 8;
+ TYPE_STRING = 9;
+ TYPE_GROUP = 10; // Tag-delimited aggregate.
+ TYPE_MESSAGE = 11; // Length-delimited aggregate.
+
+ // New in version 2.
+ TYPE_BYTES = 12;
+ TYPE_UINT32 = 13;
+ TYPE_ENUM = 14;
+ TYPE_SFIXED32 = 15;
+ TYPE_SFIXED64 = 16;
+ TYPE_SINT32 = 17; // Uses ZigZag encoding.
+ TYPE_SINT64 = 18; // Uses ZigZag encoding.
+ };
+
+ enum Label {
+ // 0 is reserved for errors
+ LABEL_OPTIONAL = 1;
+ LABEL_REQUIRED = 2;
+ LABEL_REPEATED = 3;
+ // TODO(sanjay): Should we add LABEL_MAP?
+ };
+
+ optional string name = 1;
+ optional int32 number = 3;
+ optional Label label = 4;
+
+ // If type_name is set, this need not be set. If both this and type_name
+ // are set, this must be one of TYPE_ENUM, TYPE_MESSAGE or TYPE_GROUP.
+ optional Type type = 5;
+
+ // For message and enum types, this is the name of the type. If the name
+ // starts with a '.', it is fully-qualified. Otherwise, C++-like scoping
+ // rules are used to find the type (i.e. first the nested types within this
+ // message are searched, then within the parent, on up to the root
+ // namespace).
+ optional string type_name = 6;
+
+ // For extensions, this is the name of the type being extended. It is
+ // resolved in the same manner as type_name.
+ optional string extendee = 2;
+
+ // For numeric types, contains the original text representation of the value.
+ // For booleans, "true" or "false".
+ // For strings, contains the default text contents (not escaped in any way).
+ // For bytes, contains the C escaped value. All bytes >= 128 are escaped.
+ // TODO(kenton): Base-64 encode?
+ optional string default_value = 7;
+
+ // If set, gives the index of a oneof in the containing type's oneof_decl
+ // list. This field is a member of that oneof.
+ optional int32 oneof_index = 9;
+
+ // JSON name of this field. The value is set by protocol compiler. If the
+ // user has set a "json_name" option on this field, that option's value
+ // will be used. Otherwise, it's deduced from the field's name by converting
+ // it to camelCase.
+ optional string json_name = 10;
+
+ optional FieldOptions options = 8;
+}
+
+// Describes a oneof.
+message OneofDescriptorProto {
+ optional string name = 1;
+ optional OneofOptions options = 2;
+}
+
+// Describes an enum type.
+message EnumDescriptorProto {
+ optional string name = 1;
+
+ repeated EnumValueDescriptorProto value = 2;
+
+ optional EnumOptions options = 3;
+}
+
+// Describes a value within an enum.
+message EnumValueDescriptorProto {
+ optional string name = 1;
+ optional int32 number = 2;
+
+ optional EnumValueOptions options = 3;
+}
+
+// Describes a service.
+message ServiceDescriptorProto {
+ optional string name = 1;
+ repeated MethodDescriptorProto method = 2;
+
+ optional ServiceOptions options = 3;
+}
+
+// Describes a method of a service.
+message MethodDescriptorProto {
+ optional string name = 1;
+
+ // Input and output type names. These are resolved in the same way as
+ // FieldDescriptorProto.type_name, but must refer to a message type.
+ optional string input_type = 2;
+ optional string output_type = 3;
+
+ optional MethodOptions options = 4;
+
+ // Identifies if client streams multiple client messages
+ optional bool client_streaming = 5 [default=false];
+ // Identifies if server streams multiple server messages
+ optional bool server_streaming = 6 [default=false];
+}
+
+
+// ===================================================================
+// Options
+
+// Each of the definitions above may have "options" attached. These are
+// just annotations which may cause code to be generated slightly differently
+// or may contain hints for code that manipulates protocol messages.
+//
+// Clients may define custom options as extensions of the *Options messages.
+// These extensions may not yet be known at parsing time, so the parser cannot
+// store the values in them. Instead it stores them in a field in the *Options
+// message called uninterpreted_option. This field must have the same name
+// across all *Options messages. We then use this field to populate the
+// extensions when we build a descriptor, at which point all protos have been
+// parsed and so all extensions are known.
+//
+// Extension numbers for custom options may be chosen as follows:
+// * For options which will only be used within a single application or
+// organization, or for experimental options, use field numbers 50000
+// through 99999. It is up to you to ensure that you do not use the
+// same number for multiple options.
+// * For options which will be published and used publicly by multiple
+// independent entities, e-mail protobuf-global-extension-registry@google.com
+// to reserve extension numbers. Simply provide your project name (e.g.
+// Objective-C plugin) and your project website (if available) -- there's no
+// need to explain how you intend to use them. Usually you only need one
+// extension number. You can declare multiple options with only one extension
+// number by putting them in a sub-message. See the Custom Options section of
+// the docs for examples:
+// https://developers.google.com/protocol-buffers/docs/proto#options
+// If this turns out to be popular, a web service will be set up
+// to automatically assign option numbers.
+
+
+message FileOptions {
+
+ // Sets the Java package where classes generated from this .proto will be
+ // placed. By default, the proto package is used, but this is often
+ // inappropriate because proto packages do not normally start with backwards
+ // domain names.
+ optional string java_package = 1;
+
+
+ // If set, all the classes from the .proto file are wrapped in a single
+ // outer class with the given name. This applies to both Proto1
+ // (equivalent to the old "--one_java_file" option) and Proto2 (where
+ // a .proto always translates to a single class, but you may want to
+ // explicitly choose the class name).
+ optional string java_outer_classname = 8;
+
+ // If set true, then the Java code generator will generate a separate .java
+ // file for each top-level message, enum, and service defined in the .proto
+ // file. Thus, these types will *not* be nested inside the outer class
+ // named by java_outer_classname. However, the outer class will still be
+ // generated to contain the file's getDescriptor() method as well as any
+ // top-level extensions defined in the file.
+ optional bool java_multiple_files = 10 [default=false];
+
+ // If set true, then the Java code generator will generate equals() and
+ // hashCode() methods for all messages defined in the .proto file.
+ // This increases generated code size, potentially substantially for large
+ // protos, which may harm a memory-constrained application.
+ // - In the full runtime this is a speed optimization, as the
+ // AbstractMessage base class includes reflection-based implementations of
+ // these methods.
+ // - In the lite runtime, setting this option changes the semantics of
+ // equals() and hashCode() to more closely match those of the full runtime;
+ // the generated methods compute their results based on field values rather
+ // than object identity. (Implementations should not assume that hashcodes
+ // will be consistent across runtimes or versions of the protocol compiler.)
+ optional bool java_generate_equals_and_hash = 20 [default=false];
+
+ // If set true, then the Java2 code generator will generate code that
+ // throws an exception whenever an attempt is made to assign a non-UTF-8
+ // byte sequence to a string field.
+ // Message reflection will do the same.
+ // However, an extension field still accepts non-UTF-8 byte sequences.
+ // This option has no effect on when used with the lite runtime.
+ optional bool java_string_check_utf8 = 27 [default=false];
+
+
+ // Generated classes can be optimized for speed or code size.
+ enum OptimizeMode {
+ SPEED = 1; // Generate complete code for parsing, serialization,
+ // etc.
+ CODE_SIZE = 2; // Use ReflectionOps to implement these methods.
+ LITE_RUNTIME = 3; // Generate code using MessageLite and the lite runtime.
+ }
+ optional OptimizeMode optimize_for = 9 [default=SPEED];
+
+ // Sets the Go package where structs generated from this .proto will be
+ // placed. If omitted, the Go package will be derived from the following:
+ // - The basename of the package import path, if provided.
+ // - Otherwise, the package statement in the .proto file, if present.
+ // - Otherwise, the basename of the .proto file, without extension.
+ optional string go_package = 11;
+
+
+
+ // Should generic services be generated in each language? "Generic" services
+ // are not specific to any particular RPC system. They are generated by the
+ // main code generators in each language (without additional plugins).
+ // Generic services were the only kind of service generation supported by
+ // early versions of google.protobuf.
+ //
+ // Generic services are now considered deprecated in favor of using plugins
+ // that generate code specific to your particular RPC system. Therefore,
+ // these default to false. Old code which depends on generic services should
+ // explicitly set them to true.
+ optional bool cc_generic_services = 16 [default=false];
+ optional bool java_generic_services = 17 [default=false];
+ optional bool py_generic_services = 18 [default=false];
+
+ // Is this file deprecated?
+ // Depending on the target platform, this can emit Deprecated annotations
+ // for everything in the file, or it will be completely ignored; in the very
+ // least, this is a formalization for deprecating files.
+ optional bool deprecated = 23 [default=false];
+
+ // Enables the use of arenas for the proto messages in this file. This applies
+ // only to generated classes for C++.
+ optional bool cc_enable_arenas = 31 [default=false];
+
+
+ // Sets the objective c class prefix which is prepended to all objective c
+ // generated classes from this .proto. There is no default.
+ optional string objc_class_prefix = 36;
+
+ // Namespace for generated classes; defaults to the package.
+ optional string csharp_namespace = 37;
+
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+
+ reserved 38;
+}
+
+message MessageOptions {
+ // Set true to use the old proto1 MessageSet wire format for extensions.
+ // This is provided for backwards-compatibility with the MessageSet wire
+ // format. You should not use this for any other reason: It's less
+ // efficient, has fewer features, and is more complicated.
+ //
+ // The message must be defined exactly as follows:
+ // message Foo {
+ // option message_set_wire_format = true;
+ // extensions 4 to max;
+ // }
+ // Note that the message cannot have any defined fields; MessageSets only
+ // have extensions.
+ //
+ // All extensions of your type must be singular messages; e.g. they cannot
+ // be int32s, enums, or repeated messages.
+ //
+ // Because this is an option, the above two restrictions are not enforced by
+ // the protocol compiler.
+ optional bool message_set_wire_format = 1 [default=false];
+
+ // Disables the generation of the standard "descriptor()" accessor, which can
+ // conflict with a field of the same name. This is meant to make migration
+ // from proto1 easier; new code should avoid fields named "descriptor".
+ optional bool no_standard_descriptor_accessor = 2 [default=false];
+
+ // Is this message deprecated?
+ // Depending on the target platform, this can emit Deprecated annotations
+ // for the message, or it will be completely ignored; in the very least,
+ // this is a formalization for deprecating messages.
+ optional bool deprecated = 3 [default=false];
+
+ // Whether the message is an automatically generated map entry type for the
+ // maps field.
+ //
+ // For maps fields:
+ // map<KeyType, ValueType> map_field = 1;
+ // The parsed descriptor looks like:
+ // message MapFieldEntry {
+ // option map_entry = true;
+ // optional KeyType key = 1;
+ // optional ValueType value = 2;
+ // }
+ // repeated MapFieldEntry map_field = 1;
+ //
+ // Implementations may choose not to generate the map_entry=true message, but
+ // use a native map in the target language to hold the keys and values.
+ // The reflection APIs in such implementions still need to work as
+ // if the field is a repeated message field.
+ //
+ // NOTE: Do not set the option in .proto files. Always use the maps syntax
+ // instead. The option should only be implicitly set by the proto compiler
+ // parser.
+ optional bool map_entry = 7;
+
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+}
+
+message FieldOptions {
+ // The ctype option instructs the C++ code generator to use a different
+ // representation of the field than it normally would. See the specific
+ // options below. This option is not yet implemented in the open source
+ // release -- sorry, we'll try to include it in a future version!
+ optional CType ctype = 1 [default = STRING];
+ enum CType {
+ // Default mode.
+ STRING = 0;
+
+ CORD = 1;
+
+ STRING_PIECE = 2;
+ }
+ // The packed option can be enabled for repeated primitive fields to enable
+ // a more efficient representation on the wire. Rather than repeatedly
+ // writing the tag and type for each element, the entire array is encoded as
+ // a single length-delimited blob. In proto3, only explicit setting it to
+ // false will avoid using packed encoding.
+ optional bool packed = 2;
+
+
+ // The jstype option determines the JavaScript type used for values of the
+ // field. The option is permitted only for 64 bit integral and fixed types
+ // (int64, uint64, sint64, fixed64, sfixed64). By default these types are
+ // represented as JavaScript strings. This avoids loss of precision that can
+ // happen when a large value is converted to a floating point JavaScript
+ // numbers. Specifying JS_NUMBER for the jstype causes the generated
+ // JavaScript code to use the JavaScript "number" type instead of strings.
+ // This option is an enum to permit additional types to be added,
+ // e.g. goog.math.Integer.
+ optional JSType jstype = 6 [default = JS_NORMAL];
+ enum JSType {
+ // Use the default type.
+ JS_NORMAL = 0;
+
+ // Use JavaScript strings.
+ JS_STRING = 1;
+
+ // Use JavaScript numbers.
+ JS_NUMBER = 2;
+ }
+
+ // Should this field be parsed lazily? Lazy applies only to message-type
+ // fields. It means that when the outer message is initially parsed, the
+ // inner message's contents will not be parsed but instead stored in encoded
+ // form. The inner message will actually be parsed when it is first accessed.
+ //
+ // This is only a hint. Implementations are free to choose whether to use
+ // eager or lazy parsing regardless of the value of this option. However,
+ // setting this option true suggests that the protocol author believes that
+ // using lazy parsing on this field is worth the additional bookkeeping
+ // overhead typically needed to implement it.
+ //
+ // This option does not affect the public interface of any generated code;
+ // all method signatures remain the same. Furthermore, thread-safety of the
+ // interface is not affected by this option; const methods remain safe to
+ // call from multiple threads concurrently, while non-const methods continue
+ // to require exclusive access.
+ //
+ //
+ // Note that implementations may choose not to check required fields within
+ // a lazy sub-message. That is, calling IsInitialized() on the outher message
+ // may return true even if the inner message has missing required fields.
+ // This is necessary because otherwise the inner message would have to be
+ // parsed in order to perform the check, defeating the purpose of lazy
+ // parsing. An implementation which chooses not to check required fields
+ // must be consistent about it. That is, for any particular sub-message, the
+ // implementation must either *always* check its required fields, or *never*
+ // check its required fields, regardless of whether or not the message has
+ // been parsed.
+ optional bool lazy = 5 [default=false];
+
+ // Is this field deprecated?
+ // Depending on the target platform, this can emit Deprecated annotations
+ // for accessors, or it will be completely ignored; in the very least, this
+ // is a formalization for deprecating fields.
+ optional bool deprecated = 3 [default=false];
+
+ // For Google-internal migration only. Do not use.
+ optional bool weak = 10 [default=false];
+
+
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+}
+
+message OneofOptions {
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+}
+
+message EnumOptions {
+
+ // Set this option to true to allow mapping different tag names to the same
+ // value.
+ optional bool allow_alias = 2;
+
+ // Is this enum deprecated?
+ // Depending on the target platform, this can emit Deprecated annotations
+ // for the enum, or it will be completely ignored; in the very least, this
+ // is a formalization for deprecating enums.
+ optional bool deprecated = 3 [default=false];
+
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+}
+
+message EnumValueOptions {
+ // Is this enum value deprecated?
+ // Depending on the target platform, this can emit Deprecated annotations
+ // for the enum value, or it will be completely ignored; in the very least,
+ // this is a formalization for deprecating enum values.
+ optional bool deprecated = 1 [default=false];
+
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+}
+
+message ServiceOptions {
+
+ // Note: Field numbers 1 through 32 are reserved for Google's internal RPC
+ // framework. We apologize for hoarding these numbers to ourselves, but
+ // we were already using them long before we decided to release Protocol
+ // Buffers.
+
+ // Is this service deprecated?
+ // Depending on the target platform, this can emit Deprecated annotations
+ // for the service, or it will be completely ignored; in the very least,
+ // this is a formalization for deprecating services.
+ optional bool deprecated = 33 [default=false];
+
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+}
+
+message MethodOptions {
+
+ // Note: Field numbers 1 through 32 are reserved for Google's internal RPC
+ // framework. We apologize for hoarding these numbers to ourselves, but
+ // we were already using them long before we decided to release Protocol
+ // Buffers.
+
+ // Is this method deprecated?
+ // Depending on the target platform, this can emit Deprecated annotations
+ // for the method, or it will be completely ignored; in the very least,
+ // this is a formalization for deprecating methods.
+ optional bool deprecated = 33 [default=false];
+
+ // The parser stores options it doesn't recognize here. See above.
+ repeated UninterpretedOption uninterpreted_option = 999;
+
+ // Clients can define custom options in extensions of this message. See above.
+ extensions 1000 to max;
+}
+
+
+// A message representing a option the parser does not recognize. This only
+// appears in options protos created by the compiler::Parser class.
+// DescriptorPool resolves these when building Descriptor objects. Therefore,
+// options protos in descriptor objects (e.g. returned by Descriptor::options(),
+// or produced by Descriptor::CopyTo()) will never have UninterpretedOptions
+// in them.
+message UninterpretedOption {
+ // The name of the uninterpreted option. Each string represents a segment in
+ // a dot-separated name. is_extension is true iff a segment represents an
+ // extension (denoted with parentheses in options specs in .proto files).
+ // E.g.,{ ["foo", false], ["bar.baz", true], ["qux", false] } represents
+ // "foo.(bar.baz).qux".
+ message NamePart {
+ required string name_part = 1;
+ required bool is_extension = 2;
+ }
+ repeated NamePart name = 2;
+
+ // The value of the uninterpreted option, in whatever type the tokenizer
+ // identified it as during parsing. Exactly one of these should be set.
+ optional string identifier_value = 3;
+ optional uint64 positive_int_value = 4;
+ optional int64 negative_int_value = 5;
+ optional double double_value = 6;
+ optional bytes string_value = 7;
+ optional string aggregate_value = 8;
+}
+
+// ===================================================================
+// Optional source code info
+
+// Encapsulates information about the original source file from which a
+// FileDescriptorProto was generated.
+message SourceCodeInfo {
+ // A Location identifies a piece of source code in a .proto file which
+ // corresponds to a particular definition. This information is intended
+ // to be useful to IDEs, code indexers, documentation generators, and similar
+ // tools.
+ //
+ // For example, say we have a file like:
+ // message Foo {
+ // optional string foo = 1;
+ // }
+ // Let's look at just the field definition:
+ // optional string foo = 1;
+ // ^ ^^ ^^ ^ ^^^
+ // a bc de f ghi
+ // We have the following locations:
+ // span path represents
+ // [a,i) [ 4, 0, 2, 0 ] The whole field definition.
+ // [a,b) [ 4, 0, 2, 0, 4 ] The label (optional).
+ // [c,d) [ 4, 0, 2, 0, 5 ] The type (string).
+ // [e,f) [ 4, 0, 2, 0, 1 ] The name (foo).
+ // [g,h) [ 4, 0, 2, 0, 3 ] The number (1).
+ //
+ // Notes:
+ // - A location may refer to a repeated field itself (i.e. not to any
+ // particular index within it). This is used whenever a set of elements are
+ // logically enclosed in a single code segment. For example, an entire
+ // extend block (possibly containing multiple extension definitions) will
+ // have an outer location whose path refers to the "extensions" repeated
+ // field without an index.
+ // - Multiple locations may have the same path. This happens when a single
+ // logical declaration is spread out across multiple places. The most
+ // obvious example is the "extend" block again -- there may be multiple
+ // extend blocks in the same scope, each of which will have the same path.
+ // - A location's span is not always a subset of its parent's span. For
+ // example, the "extendee" of an extension declaration appears at the
+ // beginning of the "extend" block and is shared by all extensions within
+ // the block.
+ // - Just because a location's span is a subset of some other location's span
+ // does not mean that it is a descendent. For example, a "group" defines
+ // both a type and a field in a single declaration. Thus, the locations
+ // corresponding to the type and field and their components will overlap.
+ // - Code which tries to interpret locations should probably be designed to
+ // ignore those that it doesn't understand, as more types of locations could
+ // be recorded in the future.
+ repeated Location location = 1;
+ message Location {
+ // Identifies which part of the FileDescriptorProto was defined at this
+ // location.
+ //
+ // Each element is a field number or an index. They form a path from
+ // the root FileDescriptorProto to the place where the definition. For
+ // example, this path:
+ // [ 4, 3, 2, 7, 1 ]
+ // refers to:
+ // file.message_type(3) // 4, 3
+ // .field(7) // 2, 7
+ // .name() // 1
+ // This is because FileDescriptorProto.message_type has field number 4:
+ // repeated DescriptorProto message_type = 4;
+ // and DescriptorProto.field has field number 2:
+ // repeated FieldDescriptorProto field = 2;
+ // and FieldDescriptorProto.name has field number 1:
+ // optional string name = 1;
+ //
+ // Thus, the above path gives the location of a field name. If we removed
+ // the last element:
+ // [ 4, 3, 2, 7 ]
+ // this path refers to the whole field declaration (from the beginning
+ // of the label to the terminating semicolon).
+ repeated int32 path = 1 [packed=true];
+
+ // Always has exactly three or four elements: start line, start column,
+ // end line (optional, otherwise assumed same as start line), end column.
+ // These are packed into a single field for efficiency. Note that line
+ // and column numbers are zero-based -- typically you will want to add
+ // 1 to each before displaying to a user.
+ repeated int32 span = 2 [packed=true];
+
+ // If this SourceCodeInfo represents a complete declaration, these are any
+ // comments appearing before and after the declaration which appear to be
+ // attached to the declaration.
+ //
+ // A series of line comments appearing on consecutive lines, with no other
+ // tokens appearing on those lines, will be treated as a single comment.
+ //
+ // leading_detached_comments will keep paragraphs of comments that appear
+ // before (but not connected to) the current element. Each paragraph,
+ // separated by empty lines, will be one comment element in the repeated
+ // field.
+ //
+ // Only the comment content is provided; comment markers (e.g. //) are
+ // stripped out. For block comments, leading whitespace and an asterisk
+ // will be stripped from the beginning of each line other than the first.
+ // Newlines are included in the output.
+ //
+ // Examples:
+ //
+ // optional int32 foo = 1; // Comment attached to foo.
+ // // Comment attached to bar.
+ // optional int32 bar = 2;
+ //
+ // optional string baz = 3;
+ // // Comment attached to baz.
+ // // Another line attached to baz.
+ //
+ // // Comment attached to qux.
+ // //
+ // // Another line attached to qux.
+ // optional double qux = 4;
+ //
+ // // Detached comment for corge. This is not leading or trailing comments
+ // // to qux or corge because there are blank lines separating it from
+ // // both.
+ //
+ // // Detached comment for corge paragraph 2.
+ //
+ // optional string corge = 5;
+ // /* Block comment attached
+ // * to corge. Leading asterisks
+ // * will be removed. */
+ // /* Block comment attached to
+ // * grault. */
+ // optional int32 grault = 6;
+ //
+ // // ignored detached comments.
+ optional string leading_comments = 3;
+ optional string trailing_comments = 4;
+ repeated string leading_detached_comments = 6;
+ }
+}
+
+// Describes the relationship between generated code and its original source
+// file. A GeneratedCodeInfo message is associated with only one generated
+// source file, but may contain references to different source .proto files.
+message GeneratedCodeInfo {
+ // An Annotation connects some span of text in generated code to an element
+ // of its generating .proto file.
+ repeated Annotation annotation = 1;
+ message Annotation {
+ // Identifies the element in the original source .proto file. This field
+ // is formatted the same as SourceCodeInfo.Location.path.
+ repeated int32 path = 1 [packed=true];
+
+ // Identifies the filesystem path to the original source .proto.
+ optional string source_file = 2;
+
+ // Identifies the starting offset in bytes in the generated code
+ // that relates to the identified object.
+ optional int32 begin = 3;
+
+ // Identifies the ending offset in bytes in the generated code that
+ // relates to the identified offset. The end offset should be one past
+ // the last relevant byte (so the length of the text = end - begin).
+ optional int32 end = 4;
+ }
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.cc b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.cc
new file mode 100644
index 0000000000..2117c020f5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.cc
@@ -0,0 +1,543 @@
+// 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.
+
+#include <google/protobuf/descriptor_database.h>
+
+#include <set>
+
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/stl_util.h>
+#include <google/protobuf/stubs/map_util.h>
+
+namespace google {
+namespace protobuf {
+
+DescriptorDatabase::~DescriptorDatabase() {}
+
+// ===================================================================
+
+template <typename Value>
+bool SimpleDescriptorDatabase::DescriptorIndex<Value>::AddFile(
+ const FileDescriptorProto& file,
+ Value value) {
+ if (!InsertIfNotPresent(&by_name_, file.name(), value)) {
+ GOOGLE_LOG(ERROR) << "File already exists in database: " << file.name();
+ return false;
+ }
+
+ // We must be careful here -- calling file.package() if file.has_package() is
+ // false could access an uninitialized static-storage variable if we are being
+ // run at startup time.
+ string path = file.has_package() ? file.package() : string();
+ if (!path.empty()) path += '.';
+
+ for (int i = 0; i < file.message_type_size(); i++) {
+ if (!AddSymbol(path + file.message_type(i).name(), value)) return false;
+ if (!AddNestedExtensions(file.message_type(i), value)) return false;
+ }
+ for (int i = 0; i < file.enum_type_size(); i++) {
+ if (!AddSymbol(path + file.enum_type(i).name(), value)) return false;
+ }
+ for (int i = 0; i < file.extension_size(); i++) {
+ if (!AddSymbol(path + file.extension(i).name(), value)) return false;
+ if (!AddExtension(file.extension(i), value)) return false;
+ }
+ for (int i = 0; i < file.service_size(); i++) {
+ if (!AddSymbol(path + file.service(i).name(), value)) return false;
+ }
+
+ return true;
+}
+
+template <typename Value>
+bool SimpleDescriptorDatabase::DescriptorIndex<Value>::AddSymbol(
+ const string& name, Value value) {
+ // We need to make sure not to violate our map invariant.
+
+ // If the symbol name is invalid it could break our lookup algorithm (which
+ // relies on the fact that '.' sorts before all other characters that are
+ // valid in symbol names).
+ if (!ValidateSymbolName(name)) {
+ GOOGLE_LOG(ERROR) << "Invalid symbol name: " << name;
+ return false;
+ }
+
+ // Try to look up the symbol to make sure a super-symbol doesn't already
+ // exist.
+ typename map<string, Value>::iterator iter = FindLastLessOrEqual(name);
+
+ if (iter == by_symbol_.end()) {
+ // Apparently the map is currently empty. Just insert and be done with it.
+ by_symbol_.insert(typename map<string, Value>::value_type(name, value));
+ return true;
+ }
+
+ if (IsSubSymbol(iter->first, name)) {
+ GOOGLE_LOG(ERROR) << "Symbol name \"" << name << "\" conflicts with the existing "
+ "symbol \"" << iter->first << "\".";
+ return false;
+ }
+
+ // OK, that worked. Now we have to make sure that no symbol in the map is
+ // a sub-symbol of the one we are inserting. The only symbol which could
+ // be so is the first symbol that is greater than the new symbol. Since
+ // |iter| points at the last symbol that is less than or equal, we just have
+ // to increment it.
+ ++iter;
+
+ if (iter != by_symbol_.end() && IsSubSymbol(name, iter->first)) {
+ GOOGLE_LOG(ERROR) << "Symbol name \"" << name << "\" conflicts with the existing "
+ "symbol \"" << iter->first << "\".";
+ return false;
+ }
+
+ // OK, no conflicts.
+
+ // Insert the new symbol using the iterator as a hint, the new entry will
+ // appear immediately before the one the iterator is pointing at.
+ by_symbol_.insert(iter, typename map<string, Value>::value_type(name, value));
+
+ return true;
+}
+
+template <typename Value>
+bool SimpleDescriptorDatabase::DescriptorIndex<Value>::AddNestedExtensions(
+ const DescriptorProto& message_type,
+ Value value) {
+ for (int i = 0; i < message_type.nested_type_size(); i++) {
+ if (!AddNestedExtensions(message_type.nested_type(i), value)) return false;
+ }
+ for (int i = 0; i < message_type.extension_size(); i++) {
+ if (!AddExtension(message_type.extension(i), value)) return false;
+ }
+ return true;
+}
+
+template <typename Value>
+bool SimpleDescriptorDatabase::DescriptorIndex<Value>::AddExtension(
+ const FieldDescriptorProto& field,
+ Value value) {
+ if (!field.extendee().empty() && field.extendee()[0] == '.') {
+ // The extension is fully-qualified. We can use it as a lookup key in
+ // the by_symbol_ table.
+ if (!InsertIfNotPresent(
+ &by_extension_,
+ std::make_pair(field.extendee().substr(1), field.number()),
+ value)) {
+ GOOGLE_LOG(ERROR) << "Extension conflicts with extension already in database: "
+ "extend " << field.extendee() << " { "
+ << field.name() << " = " << field.number() << " }";
+ return false;
+ }
+ } else {
+ // Not fully-qualified. We can't really do anything here, unfortunately.
+ // We don't consider this an error, though, because the descriptor is
+ // valid.
+ }
+ return true;
+}
+
+template <typename Value>
+Value SimpleDescriptorDatabase::DescriptorIndex<Value>::FindFile(
+ const string& filename) {
+ return FindWithDefault(by_name_, filename, Value());
+}
+
+template <typename Value>
+Value SimpleDescriptorDatabase::DescriptorIndex<Value>::FindSymbol(
+ const string& name) {
+ typename map<string, Value>::iterator iter = FindLastLessOrEqual(name);
+
+ return (iter != by_symbol_.end() && IsSubSymbol(iter->first, name)) ?
+ iter->second : Value();
+}
+
+template <typename Value>
+Value SimpleDescriptorDatabase::DescriptorIndex<Value>::FindExtension(
+ const string& containing_type,
+ int field_number) {
+ return FindWithDefault(
+ by_extension_, std::make_pair(containing_type, field_number), Value());
+}
+
+template <typename Value>
+bool SimpleDescriptorDatabase::DescriptorIndex<Value>::FindAllExtensionNumbers(
+ const string& containing_type,
+ vector<int>* output) {
+ typename map<pair<string, int>, Value>::const_iterator it =
+ by_extension_.lower_bound(std::make_pair(containing_type, 0));
+ bool success = false;
+
+ for (; it != by_extension_.end() && it->first.first == containing_type;
+ ++it) {
+ output->push_back(it->first.second);
+ success = true;
+ }
+
+ return success;
+}
+
+template <typename Value>
+typename map<string, Value>::iterator
+SimpleDescriptorDatabase::DescriptorIndex<Value>::FindLastLessOrEqual(
+ const string& name) {
+ // Find the last key in the map which sorts less than or equal to the
+ // symbol name. Since upper_bound() returns the *first* key that sorts
+ // *greater* than the input, we want the element immediately before that.
+ typename map<string, Value>::iterator iter = by_symbol_.upper_bound(name);
+ if (iter != by_symbol_.begin()) --iter;
+ return iter;
+}
+
+template <typename Value>
+bool SimpleDescriptorDatabase::DescriptorIndex<Value>::IsSubSymbol(
+ const string& sub_symbol, const string& super_symbol) {
+ return sub_symbol == super_symbol ||
+ (HasPrefixString(super_symbol, sub_symbol) &&
+ super_symbol[sub_symbol.size()] == '.');
+}
+
+template <typename Value>
+bool SimpleDescriptorDatabase::DescriptorIndex<Value>::ValidateSymbolName(
+ const string& name) {
+ for (int i = 0; i < name.size(); i++) {
+ // I don't trust ctype.h due to locales. :(
+ if (name[i] != '.' && name[i] != '_' &&
+ (name[i] < '0' || name[i] > '9') &&
+ (name[i] < 'A' || name[i] > 'Z') &&
+ (name[i] < 'a' || name[i] > 'z')) {
+ return false;
+ }
+ }
+ return true;
+}
+
+// -------------------------------------------------------------------
+
+SimpleDescriptorDatabase::SimpleDescriptorDatabase() {}
+SimpleDescriptorDatabase::~SimpleDescriptorDatabase() {
+ STLDeleteElements(&files_to_delete_);
+}
+
+bool SimpleDescriptorDatabase::Add(const FileDescriptorProto& file) {
+ FileDescriptorProto* new_file = new FileDescriptorProto;
+ new_file->CopyFrom(file);
+ return AddAndOwn(new_file);
+}
+
+bool SimpleDescriptorDatabase::AddAndOwn(const FileDescriptorProto* file) {
+ files_to_delete_.push_back(file);
+ return index_.AddFile(*file, file);
+}
+
+bool SimpleDescriptorDatabase::FindFileByName(
+ const string& filename,
+ FileDescriptorProto* output) {
+ return MaybeCopy(index_.FindFile(filename), output);
+}
+
+bool SimpleDescriptorDatabase::FindFileContainingSymbol(
+ const string& symbol_name,
+ FileDescriptorProto* output) {
+ return MaybeCopy(index_.FindSymbol(symbol_name), output);
+}
+
+bool SimpleDescriptorDatabase::FindFileContainingExtension(
+ const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ return MaybeCopy(index_.FindExtension(containing_type, field_number), output);
+}
+
+bool SimpleDescriptorDatabase::FindAllExtensionNumbers(
+ const string& extendee_type,
+ vector<int>* output) {
+ return index_.FindAllExtensionNumbers(extendee_type, output);
+}
+
+
+bool SimpleDescriptorDatabase::MaybeCopy(const FileDescriptorProto* file,
+ FileDescriptorProto* output) {
+ if (file == NULL) return false;
+ output->CopyFrom(*file);
+ return true;
+}
+
+// -------------------------------------------------------------------
+
+EncodedDescriptorDatabase::EncodedDescriptorDatabase() {}
+EncodedDescriptorDatabase::~EncodedDescriptorDatabase() {
+ for (int i = 0; i < files_to_delete_.size(); i++) {
+ operator delete(files_to_delete_[i]);
+ }
+}
+
+bool EncodedDescriptorDatabase::Add(
+ const void* encoded_file_descriptor, int size) {
+ FileDescriptorProto file;
+ if (file.ParseFromArray(encoded_file_descriptor, size)) {
+ return index_.AddFile(file, std::make_pair(encoded_file_descriptor, size));
+ } else {
+ GOOGLE_LOG(ERROR) << "Invalid file descriptor data passed to "
+ "EncodedDescriptorDatabase::Add().";
+ return false;
+ }
+}
+
+bool EncodedDescriptorDatabase::AddCopy(
+ const void* encoded_file_descriptor, int size) {
+ void* copy = operator new(size);
+ memcpy(copy, encoded_file_descriptor, size);
+ files_to_delete_.push_back(copy);
+ return Add(copy, size);
+}
+
+bool EncodedDescriptorDatabase::FindFileByName(
+ const string& filename,
+ FileDescriptorProto* output) {
+ return MaybeParse(index_.FindFile(filename), output);
+}
+
+bool EncodedDescriptorDatabase::FindFileContainingSymbol(
+ const string& symbol_name,
+ FileDescriptorProto* output) {
+ return MaybeParse(index_.FindSymbol(symbol_name), output);
+}
+
+bool EncodedDescriptorDatabase::FindNameOfFileContainingSymbol(
+ const string& symbol_name,
+ string* output) {
+ pair<const void*, int> encoded_file = index_.FindSymbol(symbol_name);
+ if (encoded_file.first == NULL) return false;
+
+ // Optimization: The name should be the first field in the encoded message.
+ // Try to just read it directly.
+ io::CodedInputStream input(reinterpret_cast<const uint8*>(encoded_file.first),
+ encoded_file.second);
+
+ const uint32 kNameTag = internal::WireFormatLite::MakeTag(
+ FileDescriptorProto::kNameFieldNumber,
+ internal::WireFormatLite::WIRETYPE_LENGTH_DELIMITED);
+
+ if (input.ReadTag() == kNameTag) {
+ // Success!
+ return internal::WireFormatLite::ReadString(&input, output);
+ } else {
+ // Slow path. Parse whole message.
+ FileDescriptorProto file_proto;
+ if (!file_proto.ParseFromArray(encoded_file.first, encoded_file.second)) {
+ return false;
+ }
+ *output = file_proto.name();
+ return true;
+ }
+}
+
+bool EncodedDescriptorDatabase::FindFileContainingExtension(
+ const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ return MaybeParse(index_.FindExtension(containing_type, field_number),
+ output);
+}
+
+bool EncodedDescriptorDatabase::FindAllExtensionNumbers(
+ const string& extendee_type,
+ vector<int>* output) {
+ return index_.FindAllExtensionNumbers(extendee_type, output);
+}
+
+bool EncodedDescriptorDatabase::MaybeParse(
+ pair<const void*, int> encoded_file,
+ FileDescriptorProto* output) {
+ if (encoded_file.first == NULL) return false;
+ return output->ParseFromArray(encoded_file.first, encoded_file.second);
+}
+
+// ===================================================================
+
+DescriptorPoolDatabase::DescriptorPoolDatabase(const DescriptorPool& pool)
+ : pool_(pool) {}
+DescriptorPoolDatabase::~DescriptorPoolDatabase() {}
+
+bool DescriptorPoolDatabase::FindFileByName(
+ const string& filename,
+ FileDescriptorProto* output) {
+ const FileDescriptor* file = pool_.FindFileByName(filename);
+ if (file == NULL) return false;
+ output->Clear();
+ file->CopyTo(output);
+ return true;
+}
+
+bool DescriptorPoolDatabase::FindFileContainingSymbol(
+ const string& symbol_name,
+ FileDescriptorProto* output) {
+ const FileDescriptor* file = pool_.FindFileContainingSymbol(symbol_name);
+ if (file == NULL) return false;
+ output->Clear();
+ file->CopyTo(output);
+ return true;
+}
+
+bool DescriptorPoolDatabase::FindFileContainingExtension(
+ const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ const Descriptor* extendee = pool_.FindMessageTypeByName(containing_type);
+ if (extendee == NULL) return false;
+
+ const FieldDescriptor* extension =
+ pool_.FindExtensionByNumber(extendee, field_number);
+ if (extension == NULL) return false;
+
+ output->Clear();
+ extension->file()->CopyTo(output);
+ return true;
+}
+
+bool DescriptorPoolDatabase::FindAllExtensionNumbers(
+ const string& extendee_type,
+ vector<int>* output) {
+ const Descriptor* extendee = pool_.FindMessageTypeByName(extendee_type);
+ if (extendee == NULL) return false;
+
+ vector<const FieldDescriptor*> extensions;
+ pool_.FindAllExtensions(extendee, &extensions);
+
+ for (int i = 0; i < extensions.size(); ++i) {
+ output->push_back(extensions[i]->number());
+ }
+
+ return true;
+}
+
+// ===================================================================
+
+MergedDescriptorDatabase::MergedDescriptorDatabase(
+ DescriptorDatabase* source1,
+ DescriptorDatabase* source2) {
+ sources_.push_back(source1);
+ sources_.push_back(source2);
+}
+MergedDescriptorDatabase::MergedDescriptorDatabase(
+ const vector<DescriptorDatabase*>& sources)
+ : sources_(sources) {}
+MergedDescriptorDatabase::~MergedDescriptorDatabase() {}
+
+bool MergedDescriptorDatabase::FindFileByName(
+ const string& filename,
+ FileDescriptorProto* output) {
+ for (int i = 0; i < sources_.size(); i++) {
+ if (sources_[i]->FindFileByName(filename, output)) {
+ return true;
+ }
+ }
+ return false;
+}
+
+bool MergedDescriptorDatabase::FindFileContainingSymbol(
+ const string& symbol_name,
+ FileDescriptorProto* output) {
+ for (int i = 0; i < sources_.size(); i++) {
+ if (sources_[i]->FindFileContainingSymbol(symbol_name, output)) {
+ // The symbol was found in source i. However, if one of the previous
+ // sources defines a file with the same name (which presumably doesn't
+ // contain the symbol, since it wasn't found in that source), then we
+ // must hide it from the caller.
+ FileDescriptorProto temp;
+ for (int j = 0; j < i; j++) {
+ if (sources_[j]->FindFileByName(output->name(), &temp)) {
+ // Found conflicting file in a previous source.
+ return false;
+ }
+ }
+ return true;
+ }
+ }
+ return false;
+}
+
+bool MergedDescriptorDatabase::FindFileContainingExtension(
+ const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ for (int i = 0; i < sources_.size(); i++) {
+ if (sources_[i]->FindFileContainingExtension(
+ containing_type, field_number, output)) {
+ // The symbol was found in source i. However, if one of the previous
+ // sources defines a file with the same name (which presumably doesn't
+ // contain the symbol, since it wasn't found in that source), then we
+ // must hide it from the caller.
+ FileDescriptorProto temp;
+ for (int j = 0; j < i; j++) {
+ if (sources_[j]->FindFileByName(output->name(), &temp)) {
+ // Found conflicting file in a previous source.
+ return false;
+ }
+ }
+ return true;
+ }
+ }
+ return false;
+}
+
+bool MergedDescriptorDatabase::FindAllExtensionNumbers(
+ const string& extendee_type,
+ vector<int>* output) {
+ set<int> merged_results;
+ vector<int> results;
+ bool success = false;
+
+ for (int i = 0; i < sources_.size(); i++) {
+ if (sources_[i]->FindAllExtensionNumbers(extendee_type, &results)) {
+ std::copy(
+ results.begin(), results.end(),
+ insert_iterator<set<int> >(merged_results, merged_results.begin()));
+ success = true;
+ }
+ results.clear();
+ }
+
+ std::copy(merged_results.begin(), merged_results.end(),
+ insert_iterator<vector<int> >(*output, output->end()));
+
+ return success;
+}
+
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.h b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.h
new file mode 100644
index 0000000000..86002d56f6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database.h
@@ -0,0 +1,369 @@
+// 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.
+//
+// Interface for manipulating databases of descriptors.
+
+#ifndef GOOGLE_PROTOBUF_DESCRIPTOR_DATABASE_H__
+#define GOOGLE_PROTOBUF_DESCRIPTOR_DATABASE_H__
+
+#include <map>
+#include <string>
+#include <utility>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+
+namespace google {
+namespace protobuf {
+
+// Defined in this file.
+class DescriptorDatabase;
+class SimpleDescriptorDatabase;
+class EncodedDescriptorDatabase;
+class DescriptorPoolDatabase;
+class MergedDescriptorDatabase;
+
+// Abstract interface for a database of descriptors.
+//
+// This is useful if you want to create a DescriptorPool which loads
+// descriptors on-demand from some sort of large database. If the database
+// is large, it may be inefficient to enumerate every .proto file inside it
+// calling DescriptorPool::BuildFile() for each one. Instead, a DescriptorPool
+// can be created which wraps a DescriptorDatabase and only builds particular
+// descriptors when they are needed.
+class LIBPROTOBUF_EXPORT DescriptorDatabase {
+ public:
+ inline DescriptorDatabase() {}
+ virtual ~DescriptorDatabase();
+
+ // Find a file by file name. Fills in in *output and returns true if found.
+ // Otherwise, returns false, leaving the contents of *output undefined.
+ virtual bool FindFileByName(const string& filename,
+ FileDescriptorProto* output) = 0;
+
+ // Find the file that declares the given fully-qualified symbol name.
+ // If found, fills in *output and returns true, otherwise returns false
+ // and leaves *output undefined.
+ virtual bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output) = 0;
+
+ // Find the file which defines an extension extending the given message type
+ // with the given field number. If found, fills in *output and returns true,
+ // otherwise returns false and leaves *output undefined. containing_type
+ // must be a fully-qualified type name.
+ virtual bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) = 0;
+
+ // Finds the tag numbers used by all known extensions of
+ // extendee_type, and appends them to output in an undefined
+ // order. This method is best-effort: it's not guaranteed that the
+ // database will find all extensions, and it's not guaranteed that
+ // FindFileContainingExtension will return true on all of the found
+ // numbers. Returns true if the search was successful, otherwise
+ // returns false and leaves output unchanged.
+ //
+ // This method has a default implementation that always returns
+ // false.
+ virtual bool FindAllExtensionNumbers(const string& /* extendee_type */,
+ vector<int>* /* output */) {
+ return false;
+ }
+
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DescriptorDatabase);
+};
+
+// A DescriptorDatabase into which you can insert files manually.
+//
+// FindFileContainingSymbol() is fully-implemented. When you add a file, its
+// symbols will be indexed for this purpose. Note that the implementation
+// may return false positives, but only if it isn't possible for the symbol
+// to be defined in any other file. In particular, if a file defines a symbol
+// "Foo", then searching for "Foo.[anything]" will match that file. This way,
+// the database does not need to aggressively index all children of a symbol.
+//
+// FindFileContainingExtension() is mostly-implemented. It works if and only
+// if the original FieldDescriptorProto defining the extension has a
+// fully-qualified type name in its "extendee" field (i.e. starts with a '.').
+// If the extendee is a relative name, SimpleDescriptorDatabase will not
+// attempt to resolve the type, so it will not know what type the extension is
+// extending. Therefore, calling FindFileContainingExtension() with the
+// extension's containing type will never actually find that extension. Note
+// that this is an unlikely problem, as all FileDescriptorProtos created by the
+// protocol compiler (as well as ones created by calling
+// FileDescriptor::CopyTo()) will always use fully-qualified names for all
+// types. You only need to worry if you are constructing FileDescriptorProtos
+// yourself, or are calling compiler::Parser directly.
+class LIBPROTOBUF_EXPORT SimpleDescriptorDatabase : public DescriptorDatabase {
+ public:
+ SimpleDescriptorDatabase();
+ ~SimpleDescriptorDatabase();
+
+ // Adds the FileDescriptorProto to the database, making a copy. The object
+ // can be deleted after Add() returns. Returns false if the file conflicted
+ // with a file already in the database, in which case an error will have
+ // been written to GOOGLE_LOG(ERROR).
+ bool Add(const FileDescriptorProto& file);
+
+ // Adds the FileDescriptorProto to the database and takes ownership of it.
+ bool AddAndOwn(const FileDescriptorProto* file);
+
+ // implements DescriptorDatabase -----------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output);
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output);
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output);
+ bool FindAllExtensionNumbers(const string& extendee_type,
+ vector<int>* output);
+
+ private:
+ // So that it can use DescriptorIndex.
+ friend class EncodedDescriptorDatabase;
+
+ // An index mapping file names, symbol names, and extension numbers to
+ // some sort of values.
+ template <typename Value>
+ class DescriptorIndex {
+ public:
+ // Helpers to recursively add particular descriptors and all their contents
+ // to the index.
+ bool AddFile(const FileDescriptorProto& file,
+ Value value);
+ bool AddSymbol(const string& name, Value value);
+ bool AddNestedExtensions(const DescriptorProto& message_type,
+ Value value);
+ bool AddExtension(const FieldDescriptorProto& field,
+ Value value);
+
+ Value FindFile(const string& filename);
+ Value FindSymbol(const string& name);
+ Value FindExtension(const string& containing_type, int field_number);
+ bool FindAllExtensionNumbers(const string& containing_type,
+ vector<int>* output);
+
+ private:
+ map<string, Value> by_name_;
+ map<string, Value> by_symbol_;
+ map<pair<string, int>, Value> by_extension_;
+
+ // Invariant: The by_symbol_ map does not contain any symbols which are
+ // prefixes of other symbols in the map. For example, "foo.bar" is a
+ // prefix of "foo.bar.baz" (but is not a prefix of "foo.barbaz").
+ //
+ // This invariant is important because it means that given a symbol name,
+ // we can find a key in the map which is a prefix of the symbol in O(lg n)
+ // time, and we know that there is at most one such key.
+ //
+ // The prefix lookup algorithm works like so:
+ // 1) Find the last key in the map which is less than or equal to the
+ // search key.
+ // 2) If the found key is a prefix of the search key, then return it.
+ // Otherwise, there is no match.
+ //
+ // I am sure this algorithm has been described elsewhere, but since I
+ // wasn't able to find it quickly I will instead prove that it works
+ // myself. The key to the algorithm is that if a match exists, step (1)
+ // will find it. Proof:
+ // 1) Define the "search key" to be the key we are looking for, the "found
+ // key" to be the key found in step (1), and the "match key" to be the
+ // key which actually matches the serach key (i.e. the key we're trying
+ // to find).
+ // 2) The found key must be less than or equal to the search key by
+ // definition.
+ // 3) The match key must also be less than or equal to the search key
+ // (because it is a prefix).
+ // 4) The match key cannot be greater than the found key, because if it
+ // were, then step (1) of the algorithm would have returned the match
+ // key instead (since it finds the *greatest* key which is less than or
+ // equal to the search key).
+ // 5) Therefore, the found key must be between the match key and the search
+ // key, inclusive.
+ // 6) Since the search key must be a sub-symbol of the match key, if it is
+ // not equal to the match key, then search_key[match_key.size()] must
+ // be '.'.
+ // 7) Since '.' sorts before any other character that is valid in a symbol
+ // name, then if the found key is not equal to the match key, then
+ // found_key[match_key.size()] must also be '.', because any other value
+ // would make it sort after the search key.
+ // 8) Therefore, if the found key is not equal to the match key, then the
+ // found key must be a sub-symbol of the match key. However, this would
+ // contradict our map invariant which says that no symbol in the map is
+ // a sub-symbol of any other.
+ // 9) Therefore, the found key must match the match key.
+ //
+ // The above proof assumes the match key exists. In the case that the
+ // match key does not exist, then step (1) will return some other symbol.
+ // That symbol cannot be a super-symbol of the search key since if it were,
+ // then it would be a match, and we're assuming the match key doesn't exist.
+ // Therefore, step 2 will correctly return no match.
+
+ // Find the last entry in the by_symbol_ map whose key is less than or
+ // equal to the given name.
+ typename map<string, Value>::iterator FindLastLessOrEqual(
+ const string& name);
+
+ // True if either the arguments are equal or super_symbol identifies a
+ // parent symbol of sub_symbol (e.g. "foo.bar" is a parent of
+ // "foo.bar.baz", but not a parent of "foo.barbaz").
+ bool IsSubSymbol(const string& sub_symbol, const string& super_symbol);
+
+ // Returns true if and only if all characters in the name are alphanumerics,
+ // underscores, or periods.
+ bool ValidateSymbolName(const string& name);
+ };
+
+
+ DescriptorIndex<const FileDescriptorProto*> index_;
+ vector<const FileDescriptorProto*> files_to_delete_;
+
+ // If file is non-NULL, copy it into *output and return true, otherwise
+ // return false.
+ bool MaybeCopy(const FileDescriptorProto* file,
+ FileDescriptorProto* output);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(SimpleDescriptorDatabase);
+};
+
+// Very similar to SimpleDescriptorDatabase, but stores all the descriptors
+// as raw bytes and generally tries to use as little memory as possible.
+//
+// The same caveats regarding FindFileContainingExtension() apply as with
+// SimpleDescriptorDatabase.
+class LIBPROTOBUF_EXPORT EncodedDescriptorDatabase : public DescriptorDatabase {
+ public:
+ EncodedDescriptorDatabase();
+ ~EncodedDescriptorDatabase();
+
+ // Adds the FileDescriptorProto to the database. The descriptor is provided
+ // in encoded form. The database does not make a copy of the bytes, nor
+ // does it take ownership; it's up to the caller to make sure the bytes
+ // remain valid for the life of the database. Returns false and logs an error
+ // if the bytes are not a valid FileDescriptorProto or if the file conflicted
+ // with a file already in the database.
+ bool Add(const void* encoded_file_descriptor, int size);
+
+ // Like Add(), but makes a copy of the data, so that the caller does not
+ // need to keep it around.
+ bool AddCopy(const void* encoded_file_descriptor, int size);
+
+ // Like FindFileContainingSymbol but returns only the name of the file.
+ bool FindNameOfFileContainingSymbol(const string& symbol_name,
+ string* output);
+
+ // implements DescriptorDatabase -----------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output);
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output);
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output);
+ bool FindAllExtensionNumbers(const string& extendee_type,
+ vector<int>* output);
+
+ private:
+ SimpleDescriptorDatabase::DescriptorIndex<pair<const void*, int> > index_;
+ vector<void*> files_to_delete_;
+
+ // If encoded_file.first is non-NULL, parse the data into *output and return
+ // true, otherwise return false.
+ bool MaybeParse(pair<const void*, int> encoded_file,
+ FileDescriptorProto* output);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EncodedDescriptorDatabase);
+};
+
+// A DescriptorDatabase that fetches files from a given pool.
+class LIBPROTOBUF_EXPORT DescriptorPoolDatabase : public DescriptorDatabase {
+ public:
+ explicit DescriptorPoolDatabase(const DescriptorPool& pool);
+ ~DescriptorPoolDatabase();
+
+ // implements DescriptorDatabase -----------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output);
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output);
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output);
+ bool FindAllExtensionNumbers(const string& extendee_type,
+ vector<int>* output);
+
+ private:
+ const DescriptorPool& pool_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DescriptorPoolDatabase);
+};
+
+// A DescriptorDatabase that wraps two or more others. It first searches the
+// first database and, if that fails, tries the second, and so on.
+class LIBPROTOBUF_EXPORT MergedDescriptorDatabase : public DescriptorDatabase {
+ public:
+ // Merge just two databases. The sources remain property of the caller.
+ MergedDescriptorDatabase(DescriptorDatabase* source1,
+ DescriptorDatabase* source2);
+ // Merge more than two databases. The sources remain property of the caller.
+ // The vector may be deleted after the constructor returns but the
+ // DescriptorDatabases need to stick around.
+ explicit MergedDescriptorDatabase(const vector<DescriptorDatabase*>& sources);
+ ~MergedDescriptorDatabase();
+
+ // implements DescriptorDatabase -----------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output);
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output);
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output);
+ // Merges the results of calling all databases. Returns true iff any
+ // of the databases returned true.
+ bool FindAllExtensionNumbers(const string& extendee_type,
+ vector<int>* output);
+
+
+ private:
+ vector<DescriptorDatabase*> sources_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MergedDescriptorDatabase);
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_DESCRIPTOR_DATABASE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database_unittest.cc
new file mode 100644
index 0000000000..4f568f7de1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_database_unittest.cc
@@ -0,0 +1,753 @@
+// 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 makes extensive use of RFC 3092. :)
+
+#include <algorithm>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/descriptor_database.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+
+static void AddToDatabase(SimpleDescriptorDatabase* database,
+ const char* file_text) {
+ FileDescriptorProto file_proto;
+ EXPECT_TRUE(TextFormat::ParseFromString(file_text, &file_proto));
+ database->Add(file_proto);
+}
+
+static void ExpectContainsType(const FileDescriptorProto& proto,
+ const string& type_name) {
+ for (int i = 0; i < proto.message_type_size(); i++) {
+ if (proto.message_type(i).name() == type_name) return;
+ }
+ ADD_FAILURE() << "\"" << proto.name()
+ << "\" did not contain expected type \""
+ << type_name << "\".";
+}
+
+// ===================================================================
+
+#if GTEST_HAS_PARAM_TEST
+
+// SimpleDescriptorDatabase, EncodedDescriptorDatabase, and
+// DescriptorPoolDatabase call for very similar tests. Instead of writing
+// three nearly-identical sets of tests, we use parameterized tests to apply
+// the same code to all three.
+
+// The parameterized test runs against a DescriptarDatabaseTestCase. We have
+// implementations for each of the three classes we want to test.
+class DescriptorDatabaseTestCase {
+ public:
+ virtual ~DescriptorDatabaseTestCase() {}
+
+ virtual DescriptorDatabase* GetDatabase() = 0;
+ virtual bool AddToDatabase(const FileDescriptorProto& file) = 0;
+};
+
+// Factory function type.
+typedef DescriptorDatabaseTestCase* DescriptorDatabaseTestCaseFactory();
+
+// Specialization for SimpleDescriptorDatabase.
+class SimpleDescriptorDatabaseTestCase : public DescriptorDatabaseTestCase {
+ public:
+ static DescriptorDatabaseTestCase* New() {
+ return new SimpleDescriptorDatabaseTestCase;
+ }
+
+ virtual ~SimpleDescriptorDatabaseTestCase() {}
+
+ virtual DescriptorDatabase* GetDatabase() {
+ return &database_;
+ }
+ virtual bool AddToDatabase(const FileDescriptorProto& file) {
+ return database_.Add(file);
+ }
+
+ private:
+ SimpleDescriptorDatabase database_;
+};
+
+// Specialization for EncodedDescriptorDatabase.
+class EncodedDescriptorDatabaseTestCase : public DescriptorDatabaseTestCase {
+ public:
+ static DescriptorDatabaseTestCase* New() {
+ return new EncodedDescriptorDatabaseTestCase;
+ }
+
+ virtual ~EncodedDescriptorDatabaseTestCase() {}
+
+ virtual DescriptorDatabase* GetDatabase() {
+ return &database_;
+ }
+ virtual bool AddToDatabase(const FileDescriptorProto& file) {
+ string data;
+ file.SerializeToString(&data);
+ return database_.AddCopy(data.data(), data.size());
+ }
+
+ private:
+ EncodedDescriptorDatabase database_;
+};
+
+// Specialization for DescriptorPoolDatabase.
+class DescriptorPoolDatabaseTestCase : public DescriptorDatabaseTestCase {
+ public:
+ static DescriptorDatabaseTestCase* New() {
+ return new EncodedDescriptorDatabaseTestCase;
+ }
+
+ DescriptorPoolDatabaseTestCase() : database_(pool_) {}
+ virtual ~DescriptorPoolDatabaseTestCase() {}
+
+ virtual DescriptorDatabase* GetDatabase() {
+ return &database_;
+ }
+ virtual bool AddToDatabase(const FileDescriptorProto& file) {
+ return pool_.BuildFile(file);
+ }
+
+ private:
+ DescriptorPool pool_;
+ DescriptorPoolDatabase database_;
+};
+
+// -------------------------------------------------------------------
+
+class DescriptorDatabaseTest
+ : public testing::TestWithParam<DescriptorDatabaseTestCaseFactory*> {
+ protected:
+ virtual void SetUp() {
+ test_case_.reset(GetParam()());
+ database_ = test_case_->GetDatabase();
+ }
+
+ void AddToDatabase(const char* file_descriptor_text) {
+ FileDescriptorProto file_proto;
+ EXPECT_TRUE(TextFormat::ParseFromString(file_descriptor_text, &file_proto));
+ EXPECT_TRUE(test_case_->AddToDatabase(file_proto));
+ }
+
+ void AddToDatabaseWithError(const char* file_descriptor_text) {
+ FileDescriptorProto file_proto;
+ EXPECT_TRUE(TextFormat::ParseFromString(file_descriptor_text, &file_proto));
+ EXPECT_FALSE(test_case_->AddToDatabase(file_proto));
+ }
+
+ google::protobuf::scoped_ptr<DescriptorDatabaseTestCase> test_case_;
+ DescriptorDatabase* database_;
+};
+
+TEST_P(DescriptorDatabaseTest, FindFileByName) {
+ AddToDatabase(
+ "name: \"foo.proto\" "
+ "message_type { name:\"Foo\" }");
+ AddToDatabase(
+ "name: \"bar.proto\" "
+ "message_type { name:\"Bar\" }");
+
+ {
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileByName("foo.proto", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ ExpectContainsType(file, "Foo");
+ }
+
+ {
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileByName("bar.proto", &file));
+ EXPECT_EQ("bar.proto", file.name());
+ ExpectContainsType(file, "Bar");
+ }
+
+ {
+ // Fails to find undefined files.
+ FileDescriptorProto file;
+ EXPECT_FALSE(database_->FindFileByName("baz.proto", &file));
+ }
+}
+
+TEST_P(DescriptorDatabaseTest, FindFileContainingSymbol) {
+ AddToDatabase(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ " field { name:\"qux\" }"
+ " nested_type { name: \"Grault\" } "
+ " enum_type { name: \"Garply\" } "
+ "} "
+ "enum_type { "
+ " name: \"Waldo\" "
+ " value { name:\"FRED\" } "
+ "} "
+ "extension { name: \"plugh\" } "
+ "service { "
+ " name: \"Xyzzy\" "
+ " method { name: \"Thud\" } "
+ "}"
+ );
+ AddToDatabase(
+ "name: \"bar.proto\" "
+ "package: \"corge\" "
+ "message_type { name: \"Bar\" }");
+
+ {
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Foo", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find fields.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Foo.qux", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find nested types.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Foo.Grault", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find nested enums.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Foo.Garply", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find enum types.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Waldo", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find enum values.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Waldo.FRED", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find extensions.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("plugh", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find services.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Xyzzy", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find methods.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("Xyzzy.Thud", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ // Can find things in packages.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingSymbol("corge.Bar", &file));
+ EXPECT_EQ("bar.proto", file.name());
+ }
+
+ {
+ // Fails to find undefined symbols.
+ FileDescriptorProto file;
+ EXPECT_FALSE(database_->FindFileContainingSymbol("Baz", &file));
+ }
+
+ {
+ // Names must be fully-qualified.
+ FileDescriptorProto file;
+ EXPECT_FALSE(database_->FindFileContainingSymbol("Bar", &file));
+ }
+}
+
+TEST_P(DescriptorDatabaseTest, FindFileContainingExtension) {
+ AddToDatabase(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ " extension_range { start: 1 end: 1000 } "
+ " extension { name:\"qux\" label:LABEL_OPTIONAL type:TYPE_INT32 number:5 "
+ " extendee: \".Foo\" }"
+ "}");
+ AddToDatabase(
+ "name: \"bar.proto\" "
+ "package: \"corge\" "
+ "dependency: \"foo.proto\" "
+ "message_type { "
+ " name: \"Bar\" "
+ " extension_range { start: 1 end: 1000 } "
+ "} "
+ "extension { name:\"grault\" extendee: \".Foo\" number:32 } "
+ "extension { name:\"garply\" extendee: \".corge.Bar\" number:70 } "
+ "extension { name:\"waldo\" extendee: \"Bar\" number:56 } ");
+
+ {
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingExtension("Foo", 5, &file));
+ EXPECT_EQ("foo.proto", file.name());
+ }
+
+ {
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingExtension("Foo", 32, &file));
+ EXPECT_EQ("bar.proto", file.name());
+ }
+
+ {
+ // Can find extensions for qualified type names.
+ FileDescriptorProto file;
+ EXPECT_TRUE(database_->FindFileContainingExtension("corge.Bar", 70, &file));
+ EXPECT_EQ("bar.proto", file.name());
+ }
+
+ {
+ // Can't find extensions whose extendee was not fully-qualified in the
+ // FileDescriptorProto.
+ FileDescriptorProto file;
+ EXPECT_FALSE(database_->FindFileContainingExtension("Bar", 56, &file));
+ EXPECT_FALSE(
+ database_->FindFileContainingExtension("corge.Bar", 56, &file));
+ }
+
+ {
+ // Can't find non-existent extension numbers.
+ FileDescriptorProto file;
+ EXPECT_FALSE(database_->FindFileContainingExtension("Foo", 12, &file));
+ }
+
+ {
+ // Can't find extensions for non-existent types.
+ FileDescriptorProto file;
+ EXPECT_FALSE(
+ database_->FindFileContainingExtension("NoSuchType", 5, &file));
+ }
+
+ {
+ // Can't find extensions for unqualified type names.
+ FileDescriptorProto file;
+ EXPECT_FALSE(database_->FindFileContainingExtension("Bar", 70, &file));
+ }
+}
+
+TEST_P(DescriptorDatabaseTest, FindAllExtensionNumbers) {
+ AddToDatabase(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ " extension_range { start: 1 end: 1000 } "
+ " extension { name:\"qux\" label:LABEL_OPTIONAL type:TYPE_INT32 number:5 "
+ " extendee: \".Foo\" }"
+ "}");
+ AddToDatabase(
+ "name: \"bar.proto\" "
+ "package: \"corge\" "
+ "dependency: \"foo.proto\" "
+ "message_type { "
+ " name: \"Bar\" "
+ " extension_range { start: 1 end: 1000 } "
+ "} "
+ "extension { name:\"grault\" extendee: \".Foo\" number:32 } "
+ "extension { name:\"garply\" extendee: \".corge.Bar\" number:70 } "
+ "extension { name:\"waldo\" extendee: \"Bar\" number:56 } ");
+
+ {
+ vector<int> numbers;
+ EXPECT_TRUE(database_->FindAllExtensionNumbers("Foo", &numbers));
+ ASSERT_EQ(2, numbers.size());
+ std::sort(numbers.begin(), numbers.end());
+ EXPECT_EQ(5, numbers[0]);
+ EXPECT_EQ(32, numbers[1]);
+ }
+
+ {
+ vector<int> numbers;
+ EXPECT_TRUE(database_->FindAllExtensionNumbers("corge.Bar", &numbers));
+ // Note: won't find extension 56 due to the name not being fully qualified.
+ ASSERT_EQ(1, numbers.size());
+ EXPECT_EQ(70, numbers[0]);
+ }
+
+ {
+ // Can't find extensions for non-existent types.
+ vector<int> numbers;
+ EXPECT_FALSE(database_->FindAllExtensionNumbers("NoSuchType", &numbers));
+ }
+
+ {
+ // Can't find extensions for unqualified types.
+ vector<int> numbers;
+ EXPECT_FALSE(database_->FindAllExtensionNumbers("Bar", &numbers));
+ }
+}
+
+TEST_P(DescriptorDatabaseTest, ConflictingFileError) {
+ AddToDatabase(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ "}");
+ AddToDatabaseWithError(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"Bar\" "
+ "}");
+}
+
+TEST_P(DescriptorDatabaseTest, ConflictingTypeError) {
+ AddToDatabase(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ "}");
+ AddToDatabaseWithError(
+ "name: \"bar.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ "}");
+}
+
+TEST_P(DescriptorDatabaseTest, ConflictingExtensionError) {
+ AddToDatabase(
+ "name: \"foo.proto\" "
+ "extension { name:\"foo\" label:LABEL_OPTIONAL type:TYPE_INT32 number:5 "
+ " extendee: \".Foo\" }");
+ AddToDatabaseWithError(
+ "name: \"bar.proto\" "
+ "extension { name:\"bar\" label:LABEL_OPTIONAL type:TYPE_INT32 number:5 "
+ " extendee: \".Foo\" }");
+}
+
+INSTANTIATE_TEST_CASE_P(Simple, DescriptorDatabaseTest,
+ testing::Values(&SimpleDescriptorDatabaseTestCase::New));
+INSTANTIATE_TEST_CASE_P(MemoryConserving, DescriptorDatabaseTest,
+ testing::Values(&EncodedDescriptorDatabaseTestCase::New));
+INSTANTIATE_TEST_CASE_P(Pool, DescriptorDatabaseTest,
+ testing::Values(&DescriptorPoolDatabaseTestCase::New));
+
+#endif // GTEST_HAS_PARAM_TEST
+
+TEST(EncodedDescriptorDatabaseExtraTest, FindNameOfFileContainingSymbol) {
+ // Create two files, one of which is in two parts.
+ FileDescriptorProto file1, file2a, file2b;
+ file1.set_name("foo.proto");
+ file1.set_package("foo");
+ file1.add_message_type()->set_name("Foo");
+ file2a.set_name("bar.proto");
+ file2b.set_package("bar");
+ file2b.add_message_type()->set_name("Bar");
+
+ // Normal serialization allows our optimization to kick in.
+ string data1 = file1.SerializeAsString();
+
+ // Force out-of-order serialization to test slow path.
+ string data2 = file2b.SerializeAsString() + file2a.SerializeAsString();
+
+ // Create EncodedDescriptorDatabase containing both files.
+ EncodedDescriptorDatabase db;
+ db.Add(data1.data(), data1.size());
+ db.Add(data2.data(), data2.size());
+
+ // Test!
+ string filename;
+ EXPECT_TRUE(db.FindNameOfFileContainingSymbol("foo.Foo", &filename));
+ EXPECT_EQ("foo.proto", filename);
+ EXPECT_TRUE(db.FindNameOfFileContainingSymbol("foo.Foo.Blah", &filename));
+ EXPECT_EQ("foo.proto", filename);
+ EXPECT_TRUE(db.FindNameOfFileContainingSymbol("bar.Bar", &filename));
+ EXPECT_EQ("bar.proto", filename);
+ EXPECT_FALSE(db.FindNameOfFileContainingSymbol("foo", &filename));
+ EXPECT_FALSE(db.FindNameOfFileContainingSymbol("bar", &filename));
+ EXPECT_FALSE(db.FindNameOfFileContainingSymbol("baz.Baz", &filename));
+}
+
+// ===================================================================
+
+class MergedDescriptorDatabaseTest : public testing::Test {
+ protected:
+ MergedDescriptorDatabaseTest()
+ : forward_merged_(&database1_, &database2_),
+ reverse_merged_(&database2_, &database1_) {}
+
+ virtual void SetUp() {
+ AddToDatabase(&database1_,
+ "name: \"foo.proto\" "
+ "message_type { name:\"Foo\" extension_range { start: 1 end: 100 } } "
+ "extension { name:\"foo_ext\" extendee: \".Foo\" number:3 "
+ " label:LABEL_OPTIONAL type:TYPE_INT32 } ");
+ AddToDatabase(&database2_,
+ "name: \"bar.proto\" "
+ "message_type { name:\"Bar\" extension_range { start: 1 end: 100 } } "
+ "extension { name:\"bar_ext\" extendee: \".Bar\" number:5 "
+ " label:LABEL_OPTIONAL type:TYPE_INT32 } ");
+
+ // baz.proto exists in both pools, with different definitions.
+ AddToDatabase(&database1_,
+ "name: \"baz.proto\" "
+ "message_type { name:\"Baz\" extension_range { start: 1 end: 100 } } "
+ "message_type { name:\"FromPool1\" } "
+ "extension { name:\"baz_ext\" extendee: \".Baz\" number:12 "
+ " label:LABEL_OPTIONAL type:TYPE_INT32 } "
+ "extension { name:\"database1_only_ext\" extendee: \".Baz\" number:13 "
+ " label:LABEL_OPTIONAL type:TYPE_INT32 } ");
+ AddToDatabase(&database2_,
+ "name: \"baz.proto\" "
+ "message_type { name:\"Baz\" extension_range { start: 1 end: 100 } } "
+ "message_type { name:\"FromPool2\" } "
+ "extension { name:\"baz_ext\" extendee: \".Baz\" number:12 "
+ " label:LABEL_OPTIONAL type:TYPE_INT32 } ");
+ }
+
+ SimpleDescriptorDatabase database1_;
+ SimpleDescriptorDatabase database2_;
+
+ MergedDescriptorDatabase forward_merged_;
+ MergedDescriptorDatabase reverse_merged_;
+};
+
+TEST_F(MergedDescriptorDatabaseTest, FindFileByName) {
+ {
+ // Can find file that is only in database1_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileByName("foo.proto", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ ExpectContainsType(file, "Foo");
+ }
+
+ {
+ // Can find file that is only in database2_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileByName("bar.proto", &file));
+ EXPECT_EQ("bar.proto", file.name());
+ ExpectContainsType(file, "Bar");
+ }
+
+ {
+ // In forward_merged_, database1_'s baz.proto takes precedence.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileByName("baz.proto", &file));
+ EXPECT_EQ("baz.proto", file.name());
+ ExpectContainsType(file, "FromPool1");
+ }
+
+ {
+ // In reverse_merged_, database2_'s baz.proto takes precedence.
+ FileDescriptorProto file;
+ EXPECT_TRUE(reverse_merged_.FindFileByName("baz.proto", &file));
+ EXPECT_EQ("baz.proto", file.name());
+ ExpectContainsType(file, "FromPool2");
+ }
+
+ {
+ // Can't find non-existent file.
+ FileDescriptorProto file;
+ EXPECT_FALSE(forward_merged_.FindFileByName("no_such.proto", &file));
+ }
+}
+
+TEST_F(MergedDescriptorDatabaseTest, FindFileContainingSymbol) {
+ {
+ // Can find file that is only in database1_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileContainingSymbol("Foo", &file));
+ EXPECT_EQ("foo.proto", file.name());
+ ExpectContainsType(file, "Foo");
+ }
+
+ {
+ // Can find file that is only in database2_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileContainingSymbol("Bar", &file));
+ EXPECT_EQ("bar.proto", file.name());
+ ExpectContainsType(file, "Bar");
+ }
+
+ {
+ // In forward_merged_, database1_'s baz.proto takes precedence.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileContainingSymbol("Baz", &file));
+ EXPECT_EQ("baz.proto", file.name());
+ ExpectContainsType(file, "FromPool1");
+ }
+
+ {
+ // In reverse_merged_, database2_'s baz.proto takes precedence.
+ FileDescriptorProto file;
+ EXPECT_TRUE(reverse_merged_.FindFileContainingSymbol("Baz", &file));
+ EXPECT_EQ("baz.proto", file.name());
+ ExpectContainsType(file, "FromPool2");
+ }
+
+ {
+ // FromPool1 only shows up in forward_merged_ because it is masked by
+ // database2_'s baz.proto in reverse_merged_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileContainingSymbol("FromPool1", &file));
+ EXPECT_FALSE(reverse_merged_.FindFileContainingSymbol("FromPool1", &file));
+ }
+
+ {
+ // Can't find non-existent symbol.
+ FileDescriptorProto file;
+ EXPECT_FALSE(
+ forward_merged_.FindFileContainingSymbol("NoSuchType", &file));
+ }
+}
+
+TEST_F(MergedDescriptorDatabaseTest, FindFileContainingExtension) {
+ {
+ // Can find file that is only in database1_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(
+ forward_merged_.FindFileContainingExtension("Foo", 3, &file));
+ EXPECT_EQ("foo.proto", file.name());
+ ExpectContainsType(file, "Foo");
+ }
+
+ {
+ // Can find file that is only in database2_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(
+ forward_merged_.FindFileContainingExtension("Bar", 5, &file));
+ EXPECT_EQ("bar.proto", file.name());
+ ExpectContainsType(file, "Bar");
+ }
+
+ {
+ // In forward_merged_, database1_'s baz.proto takes precedence.
+ FileDescriptorProto file;
+ EXPECT_TRUE(
+ forward_merged_.FindFileContainingExtension("Baz", 12, &file));
+ EXPECT_EQ("baz.proto", file.name());
+ ExpectContainsType(file, "FromPool1");
+ }
+
+ {
+ // In reverse_merged_, database2_'s baz.proto takes precedence.
+ FileDescriptorProto file;
+ EXPECT_TRUE(
+ reverse_merged_.FindFileContainingExtension("Baz", 12, &file));
+ EXPECT_EQ("baz.proto", file.name());
+ ExpectContainsType(file, "FromPool2");
+ }
+
+ {
+ // Baz's extension 13 only shows up in forward_merged_ because it is
+ // masked by database2_'s baz.proto in reverse_merged_.
+ FileDescriptorProto file;
+ EXPECT_TRUE(forward_merged_.FindFileContainingExtension("Baz", 13, &file));
+ EXPECT_FALSE(reverse_merged_.FindFileContainingExtension("Baz", 13, &file));
+ }
+
+ {
+ // Can't find non-existent extension.
+ FileDescriptorProto file;
+ EXPECT_FALSE(
+ forward_merged_.FindFileContainingExtension("Foo", 6, &file));
+ }
+}
+
+TEST_F(MergedDescriptorDatabaseTest, FindAllExtensionNumbers) {
+ {
+ // Message only has extension in database1_
+ vector<int> numbers;
+ EXPECT_TRUE(forward_merged_.FindAllExtensionNumbers("Foo", &numbers));
+ ASSERT_EQ(1, numbers.size());
+ EXPECT_EQ(3, numbers[0]);
+ }
+
+ {
+ // Message only has extension in database2_
+ vector<int> numbers;
+ EXPECT_TRUE(forward_merged_.FindAllExtensionNumbers("Bar", &numbers));
+ ASSERT_EQ(1, numbers.size());
+ EXPECT_EQ(5, numbers[0]);
+ }
+
+ {
+ // Merge results from the two databases.
+ vector<int> numbers;
+ EXPECT_TRUE(forward_merged_.FindAllExtensionNumbers("Baz", &numbers));
+ ASSERT_EQ(2, numbers.size());
+ std::sort(numbers.begin(), numbers.end());
+ EXPECT_EQ(12, numbers[0]);
+ EXPECT_EQ(13, numbers[1]);
+ }
+
+ {
+ vector<int> numbers;
+ EXPECT_TRUE(reverse_merged_.FindAllExtensionNumbers("Baz", &numbers));
+ ASSERT_EQ(2, numbers.size());
+ std::sort(numbers.begin(), numbers.end());
+ EXPECT_EQ(12, numbers[0]);
+ EXPECT_EQ(13, numbers[1]);
+ }
+
+ {
+ // Can't find extensions for a non-existent message.
+ vector<int> numbers;
+ EXPECT_FALSE(reverse_merged_.FindAllExtensionNumbers("Blah", &numbers));
+ }
+}
+
+} // anonymous namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_unittest.cc
new file mode 100644
index 0000000000..4183138f72
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/descriptor_unittest.cc
@@ -0,0 +1,6615 @@
+// 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 makes extensive use of RFC 3092. :)
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/compiler/importer.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_custom_options.pb.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor_database.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+// Can't use an anonymous namespace here due to brokenness of Tru64 compiler.
+namespace descriptor_unittest {
+
+// Some helpers to make assembling descriptors faster.
+DescriptorProto* AddMessage(FileDescriptorProto* file, const string& name) {
+ DescriptorProto* result = file->add_message_type();
+ result->set_name(name);
+ return result;
+}
+
+DescriptorProto* AddNestedMessage(DescriptorProto* parent, const string& name) {
+ DescriptorProto* result = parent->add_nested_type();
+ result->set_name(name);
+ return result;
+}
+
+EnumDescriptorProto* AddEnum(FileDescriptorProto* file, const string& name) {
+ EnumDescriptorProto* result = file->add_enum_type();
+ result->set_name(name);
+ return result;
+}
+
+EnumDescriptorProto* AddNestedEnum(DescriptorProto* parent,
+ const string& name) {
+ EnumDescriptorProto* result = parent->add_enum_type();
+ result->set_name(name);
+ return result;
+}
+
+ServiceDescriptorProto* AddService(FileDescriptorProto* file,
+ const string& name) {
+ ServiceDescriptorProto* result = file->add_service();
+ result->set_name(name);
+ return result;
+}
+
+FieldDescriptorProto* AddField(DescriptorProto* parent,
+ const string& name, int number,
+ FieldDescriptorProto::Label label,
+ FieldDescriptorProto::Type type) {
+ FieldDescriptorProto* result = parent->add_field();
+ result->set_name(name);
+ result->set_number(number);
+ result->set_label(label);
+ result->set_type(type);
+ return result;
+}
+
+FieldDescriptorProto* AddExtension(FileDescriptorProto* file,
+ const string& extendee,
+ const string& name, int number,
+ FieldDescriptorProto::Label label,
+ FieldDescriptorProto::Type type) {
+ FieldDescriptorProto* result = file->add_extension();
+ result->set_name(name);
+ result->set_number(number);
+ result->set_label(label);
+ result->set_type(type);
+ result->set_extendee(extendee);
+ return result;
+}
+
+FieldDescriptorProto* AddNestedExtension(DescriptorProto* parent,
+ const string& extendee,
+ const string& name, int number,
+ FieldDescriptorProto::Label label,
+ FieldDescriptorProto::Type type) {
+ FieldDescriptorProto* result = parent->add_extension();
+ result->set_name(name);
+ result->set_number(number);
+ result->set_label(label);
+ result->set_type(type);
+ result->set_extendee(extendee);
+ return result;
+}
+
+DescriptorProto::ExtensionRange* AddExtensionRange(DescriptorProto* parent,
+ int start, int end) {
+ DescriptorProto::ExtensionRange* result = parent->add_extension_range();
+ result->set_start(start);
+ result->set_end(end);
+ return result;
+}
+
+DescriptorProto::ReservedRange* AddReservedRange(DescriptorProto* parent,
+ int start, int end) {
+ DescriptorProto::ReservedRange* result = parent->add_reserved_range();
+ result->set_start(start);
+ result->set_end(end);
+ return result;
+}
+
+EnumValueDescriptorProto* AddEnumValue(EnumDescriptorProto* enum_proto,
+ const string& name, int number) {
+ EnumValueDescriptorProto* result = enum_proto->add_value();
+ result->set_name(name);
+ result->set_number(number);
+ return result;
+}
+
+MethodDescriptorProto* AddMethod(ServiceDescriptorProto* service,
+ const string& name,
+ const string& input_type,
+ const string& output_type) {
+ MethodDescriptorProto* result = service->add_method();
+ result->set_name(name);
+ result->set_input_type(input_type);
+ result->set_output_type(output_type);
+ return result;
+}
+
+// Empty enums technically aren't allowed. We need to insert a dummy value
+// into them.
+void AddEmptyEnum(FileDescriptorProto* file, const string& name) {
+ AddEnumValue(AddEnum(file, name), name + "_DUMMY", 1);
+}
+
+class MockErrorCollector : public DescriptorPool::ErrorCollector {
+ public:
+ MockErrorCollector() {}
+ ~MockErrorCollector() {}
+
+ string text_;
+ string warning_text_;
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(const string& filename,
+ const string& element_name, const Message* descriptor,
+ ErrorLocation location, const string& message) {
+ const char* location_name = NULL;
+ switch (location) {
+ case NAME : location_name = "NAME" ; break;
+ case NUMBER : location_name = "NUMBER" ; break;
+ case TYPE : location_name = "TYPE" ; break;
+ case EXTENDEE : location_name = "EXTENDEE" ; break;
+ case DEFAULT_VALUE: location_name = "DEFAULT_VALUE"; break;
+ case OPTION_NAME : location_name = "OPTION_NAME" ; break;
+ case OPTION_VALUE : location_name = "OPTION_VALUE" ; break;
+ case INPUT_TYPE : location_name = "INPUT_TYPE" ; break;
+ case OUTPUT_TYPE : location_name = "OUTPUT_TYPE" ; break;
+ case OTHER : location_name = "OTHER" ; break;
+ }
+
+ strings::SubstituteAndAppend(
+ &text_, "$0: $1: $2: $3\n",
+ filename, element_name, location_name, message);
+ }
+
+ // implements ErrorCollector ---------------------------------------
+ void AddWarning(const string& filename, const string& element_name,
+ const Message* descriptor, ErrorLocation location,
+ const string& message) {
+ const char* location_name = NULL;
+ switch (location) {
+ case NAME : location_name = "NAME" ; break;
+ case NUMBER : location_name = "NUMBER" ; break;
+ case TYPE : location_name = "TYPE" ; break;
+ case EXTENDEE : location_name = "EXTENDEE" ; break;
+ case DEFAULT_VALUE: location_name = "DEFAULT_VALUE"; break;
+ case OPTION_NAME : location_name = "OPTION_NAME" ; break;
+ case OPTION_VALUE : location_name = "OPTION_VALUE" ; break;
+ case INPUT_TYPE : location_name = "INPUT_TYPE" ; break;
+ case OUTPUT_TYPE : location_name = "OUTPUT_TYPE" ; break;
+ case OTHER : location_name = "OTHER" ; break;
+ }
+
+ strings::SubstituteAndAppend(
+ &warning_text_, "$0: $1: $2: $3\n",
+ filename, element_name, location_name, message);
+ }
+};
+
+// ===================================================================
+
+// Test simple files.
+class FileDescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following definitions:
+ //
+ // // in "foo.proto"
+ // message FooMessage { extensions 1; }
+ // enum FooEnum {FOO_ENUM_VALUE = 1;}
+ // service FooService {}
+ // extend FooMessage { optional int32 foo_extension = 1; }
+ //
+ // // in "bar.proto"
+ // package bar_package;
+ // message BarMessage { extensions 1; }
+ // enum BarEnum {BAR_ENUM_VALUE = 1;}
+ // service BarService {}
+ // extend BarMessage { optional int32 bar_extension = 1; }
+ //
+ // Also, we have an empty file "baz.proto". This file's purpose is to
+ // make sure that even though it has the same package as foo.proto,
+ // searching it for members of foo.proto won't work.
+
+ FileDescriptorProto foo_file;
+ foo_file.set_name("foo.proto");
+ AddExtensionRange(AddMessage(&foo_file, "FooMessage"), 1, 2);
+ AddEnumValue(AddEnum(&foo_file, "FooEnum"), "FOO_ENUM_VALUE", 1);
+ AddService(&foo_file, "FooService");
+ AddExtension(&foo_file, "FooMessage", "foo_extension", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+
+ FileDescriptorProto bar_file;
+ bar_file.set_name("bar.proto");
+ bar_file.set_package("bar_package");
+ bar_file.add_dependency("foo.proto");
+ AddExtensionRange(AddMessage(&bar_file, "BarMessage"), 1, 2);
+ AddEnumValue(AddEnum(&bar_file, "BarEnum"), "BAR_ENUM_VALUE", 1);
+ AddService(&bar_file, "BarService");
+ AddExtension(&bar_file, "bar_package.BarMessage", "bar_extension", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+
+ FileDescriptorProto baz_file;
+ baz_file.set_name("baz.proto");
+
+ // Build the descriptors and get the pointers.
+ foo_file_ = pool_.BuildFile(foo_file);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ bar_file_ = pool_.BuildFile(bar_file);
+ ASSERT_TRUE(bar_file_ != NULL);
+
+ baz_file_ = pool_.BuildFile(baz_file);
+ ASSERT_TRUE(baz_file_ != NULL);
+
+ ASSERT_EQ(1, foo_file_->message_type_count());
+ foo_message_ = foo_file_->message_type(0);
+ ASSERT_EQ(1, foo_file_->enum_type_count());
+ foo_enum_ = foo_file_->enum_type(0);
+ ASSERT_EQ(1, foo_enum_->value_count());
+ foo_enum_value_ = foo_enum_->value(0);
+ ASSERT_EQ(1, foo_file_->service_count());
+ foo_service_ = foo_file_->service(0);
+ ASSERT_EQ(1, foo_file_->extension_count());
+ foo_extension_ = foo_file_->extension(0);
+
+ ASSERT_EQ(1, bar_file_->message_type_count());
+ bar_message_ = bar_file_->message_type(0);
+ ASSERT_EQ(1, bar_file_->enum_type_count());
+ bar_enum_ = bar_file_->enum_type(0);
+ ASSERT_EQ(1, bar_enum_->value_count());
+ bar_enum_value_ = bar_enum_->value(0);
+ ASSERT_EQ(1, bar_file_->service_count());
+ bar_service_ = bar_file_->service(0);
+ ASSERT_EQ(1, bar_file_->extension_count());
+ bar_extension_ = bar_file_->extension(0);
+ }
+
+ DescriptorPool pool_;
+
+ const FileDescriptor* foo_file_;
+ const FileDescriptor* bar_file_;
+ const FileDescriptor* baz_file_;
+
+ const Descriptor* foo_message_;
+ const EnumDescriptor* foo_enum_;
+ const EnumValueDescriptor* foo_enum_value_;
+ const ServiceDescriptor* foo_service_;
+ const FieldDescriptor* foo_extension_;
+
+ const Descriptor* bar_message_;
+ const EnumDescriptor* bar_enum_;
+ const EnumValueDescriptor* bar_enum_value_;
+ const ServiceDescriptor* bar_service_;
+ const FieldDescriptor* bar_extension_;
+};
+
+TEST_F(FileDescriptorTest, Name) {
+ EXPECT_EQ("foo.proto", foo_file_->name());
+ EXPECT_EQ("bar.proto", bar_file_->name());
+ EXPECT_EQ("baz.proto", baz_file_->name());
+}
+
+TEST_F(FileDescriptorTest, Package) {
+ EXPECT_EQ("", foo_file_->package());
+ EXPECT_EQ("bar_package", bar_file_->package());
+}
+
+TEST_F(FileDescriptorTest, Dependencies) {
+ EXPECT_EQ(0, foo_file_->dependency_count());
+ EXPECT_EQ(1, bar_file_->dependency_count());
+ EXPECT_EQ(foo_file_, bar_file_->dependency(0));
+}
+
+TEST_F(FileDescriptorTest, FindMessageTypeByName) {
+ EXPECT_EQ(foo_message_, foo_file_->FindMessageTypeByName("FooMessage"));
+ EXPECT_EQ(bar_message_, bar_file_->FindMessageTypeByName("BarMessage"));
+
+ EXPECT_TRUE(foo_file_->FindMessageTypeByName("BarMessage") == NULL);
+ EXPECT_TRUE(bar_file_->FindMessageTypeByName("FooMessage") == NULL);
+ EXPECT_TRUE(baz_file_->FindMessageTypeByName("FooMessage") == NULL);
+
+ EXPECT_TRUE(foo_file_->FindMessageTypeByName("NoSuchMessage") == NULL);
+ EXPECT_TRUE(foo_file_->FindMessageTypeByName("FooEnum") == NULL);
+}
+
+TEST_F(FileDescriptorTest, FindEnumTypeByName) {
+ EXPECT_EQ(foo_enum_, foo_file_->FindEnumTypeByName("FooEnum"));
+ EXPECT_EQ(bar_enum_, bar_file_->FindEnumTypeByName("BarEnum"));
+
+ EXPECT_TRUE(foo_file_->FindEnumTypeByName("BarEnum") == NULL);
+ EXPECT_TRUE(bar_file_->FindEnumTypeByName("FooEnum") == NULL);
+ EXPECT_TRUE(baz_file_->FindEnumTypeByName("FooEnum") == NULL);
+
+ EXPECT_TRUE(foo_file_->FindEnumTypeByName("NoSuchEnum") == NULL);
+ EXPECT_TRUE(foo_file_->FindEnumTypeByName("FooMessage") == NULL);
+}
+
+TEST_F(FileDescriptorTest, FindEnumValueByName) {
+ EXPECT_EQ(foo_enum_value_, foo_file_->FindEnumValueByName("FOO_ENUM_VALUE"));
+ EXPECT_EQ(bar_enum_value_, bar_file_->FindEnumValueByName("BAR_ENUM_VALUE"));
+
+ EXPECT_TRUE(foo_file_->FindEnumValueByName("BAR_ENUM_VALUE") == NULL);
+ EXPECT_TRUE(bar_file_->FindEnumValueByName("FOO_ENUM_VALUE") == NULL);
+ EXPECT_TRUE(baz_file_->FindEnumValueByName("FOO_ENUM_VALUE") == NULL);
+
+ EXPECT_TRUE(foo_file_->FindEnumValueByName("NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(foo_file_->FindEnumValueByName("FooMessage") == NULL);
+}
+
+TEST_F(FileDescriptorTest, FindServiceByName) {
+ EXPECT_EQ(foo_service_, foo_file_->FindServiceByName("FooService"));
+ EXPECT_EQ(bar_service_, bar_file_->FindServiceByName("BarService"));
+
+ EXPECT_TRUE(foo_file_->FindServiceByName("BarService") == NULL);
+ EXPECT_TRUE(bar_file_->FindServiceByName("FooService") == NULL);
+ EXPECT_TRUE(baz_file_->FindServiceByName("FooService") == NULL);
+
+ EXPECT_TRUE(foo_file_->FindServiceByName("NoSuchService") == NULL);
+ EXPECT_TRUE(foo_file_->FindServiceByName("FooMessage") == NULL);
+}
+
+TEST_F(FileDescriptorTest, FindExtensionByName) {
+ EXPECT_EQ(foo_extension_, foo_file_->FindExtensionByName("foo_extension"));
+ EXPECT_EQ(bar_extension_, bar_file_->FindExtensionByName("bar_extension"));
+
+ EXPECT_TRUE(foo_file_->FindExtensionByName("bar_extension") == NULL);
+ EXPECT_TRUE(bar_file_->FindExtensionByName("foo_extension") == NULL);
+ EXPECT_TRUE(baz_file_->FindExtensionByName("foo_extension") == NULL);
+
+ EXPECT_TRUE(foo_file_->FindExtensionByName("no_such_extension") == NULL);
+ EXPECT_TRUE(foo_file_->FindExtensionByName("FooMessage") == NULL);
+}
+
+TEST_F(FileDescriptorTest, FindExtensionByNumber) {
+ EXPECT_EQ(foo_extension_, pool_.FindExtensionByNumber(foo_message_, 1));
+ EXPECT_EQ(bar_extension_, pool_.FindExtensionByNumber(bar_message_, 1));
+
+ EXPECT_TRUE(pool_.FindExtensionByNumber(foo_message_, 2) == NULL);
+}
+
+TEST_F(FileDescriptorTest, BuildAgain) {
+ // Test that if te call BuildFile again on the same input we get the same
+ // FileDescriptor back.
+ FileDescriptorProto file;
+ foo_file_->CopyTo(&file);
+ EXPECT_EQ(foo_file_, pool_.BuildFile(file));
+
+ // But if we change the file then it won't work.
+ file.set_package("some.other.package");
+ EXPECT_TRUE(pool_.BuildFile(file) == NULL);
+}
+
+TEST_F(FileDescriptorTest, BuildAgainWithSyntax) {
+ // Test that if te call BuildFile again on the same input we get the same
+ // FileDescriptor back even if syntax param is specified.
+ FileDescriptorProto proto_syntax2;
+ proto_syntax2.set_name("foo_syntax2");
+ proto_syntax2.set_syntax("proto2");
+
+ const FileDescriptor* proto2_descriptor = pool_.BuildFile(proto_syntax2);
+ EXPECT_TRUE(proto2_descriptor != NULL);
+ EXPECT_EQ(proto2_descriptor, pool_.BuildFile(proto_syntax2));
+
+ FileDescriptorProto implicit_proto2;
+ implicit_proto2.set_name("foo_implicit_syntax2");
+
+ const FileDescriptor* implicit_proto2_descriptor =
+ pool_.BuildFile(implicit_proto2);
+ EXPECT_TRUE(implicit_proto2_descriptor != NULL);
+ // We get the same FileDescriptor back if syntax param is explicitly
+ // specified.
+ implicit_proto2.set_syntax("proto2");
+ EXPECT_EQ(implicit_proto2_descriptor, pool_.BuildFile(implicit_proto2));
+
+ FileDescriptorProto proto_syntax3;
+ proto_syntax3.set_name("foo_syntax3");
+ proto_syntax3.set_syntax("proto3");
+
+ const FileDescriptor* proto3_descriptor = pool_.BuildFile(proto_syntax3);
+ EXPECT_TRUE(proto3_descriptor != NULL);
+ EXPECT_EQ(proto3_descriptor, pool_.BuildFile(proto_syntax3));
+}
+
+TEST_F(FileDescriptorTest, Syntax) {
+ FileDescriptorProto proto;
+ proto.set_name("foo");
+ // Enable the test when we also populate the syntax for proto2.
+#if 0
+ {
+ proto.set_syntax("proto2");
+ DescriptorPool pool;
+ const FileDescriptor* file = pool.BuildFile(proto);
+ EXPECT_TRUE(file != NULL);
+ EXPECT_EQ(FileDescriptor::SYNTAX_PROTO2, file->syntax());
+ FileDescriptorProto other;
+ file->CopyTo(&other);
+ EXPECT_EQ("proto2", other.syntax());
+ }
+#endif
+ {
+ proto.set_syntax("proto3");
+ DescriptorPool pool;
+ const FileDescriptor* file = pool.BuildFile(proto);
+ EXPECT_TRUE(file != NULL);
+ EXPECT_EQ(FileDescriptor::SYNTAX_PROTO3, file->syntax());
+ FileDescriptorProto other;
+ file->CopyTo(&other);
+ EXPECT_EQ("proto3", other.syntax());
+ }
+}
+
+// ===================================================================
+
+// Test simple flat messages and fields.
+class DescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following definitions:
+ //
+ // // in "foo.proto"
+ // message TestForeign {}
+ // enum TestEnum {}
+ //
+ // message TestMessage {
+ // required string foo = 1;
+ // optional TestEnum bar = 6;
+ // repeated TestForeign baz = 500000000;
+ // optional group qux = 15 {}
+ // }
+ //
+ // // in "bar.proto"
+ // package corge.grault;
+ // message TestMessage2 {
+ // required string foo = 1;
+ // required string bar = 2;
+ // required string quux = 6;
+ // }
+ //
+ // // in "map.proto"
+ // message TestMessage3 {
+ // map<int32, int32> map_int32_int32 = 1;
+ // }
+ //
+ // // in "json.proto"
+ // message TestMessage4 {
+ // optional int32 field_name1 = 1;
+ // optional int32 fieldName2 = 2;
+ // optional int32 FieldName3 = 3;
+ // optional int32 _field_name4 = 4;
+ // optional int32 FIELD_NAME5 = 5;
+ // optional int32 field_name6 = 6 [json_name = "@type"];
+ // }
+ //
+ // We cheat and use TestForeign as the type for qux rather than create
+ // an actual nested type.
+ //
+ // Since all primitive types (including string) use the same building
+ // code, there's no need to test each one individually.
+ //
+ // TestMessage2 is primarily here to test FindFieldByName and friends.
+ // All messages created from the same DescriptorPool share the same lookup
+ // table, so we need to insure that they don't interfere.
+
+ FileDescriptorProto foo_file;
+ foo_file.set_name("foo.proto");
+ AddMessage(&foo_file, "TestForeign");
+ AddEmptyEnum(&foo_file, "TestEnum");
+
+ DescriptorProto* message = AddMessage(&foo_file, "TestMessage");
+ AddField(message, "foo", 1,
+ FieldDescriptorProto::LABEL_REQUIRED,
+ FieldDescriptorProto::TYPE_STRING);
+ AddField(message, "bar", 6,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_ENUM)
+ ->set_type_name("TestEnum");
+ AddField(message, "baz", 500000000,
+ FieldDescriptorProto::LABEL_REPEATED,
+ FieldDescriptorProto::TYPE_MESSAGE)
+ ->set_type_name("TestForeign");
+ AddField(message, "qux", 15,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_GROUP)
+ ->set_type_name("TestForeign");
+
+ FileDescriptorProto bar_file;
+ bar_file.set_name("bar.proto");
+ bar_file.set_package("corge.grault");
+
+ DescriptorProto* message2 = AddMessage(&bar_file, "TestMessage2");
+ AddField(message2, "foo", 1,
+ FieldDescriptorProto::LABEL_REQUIRED,
+ FieldDescriptorProto::TYPE_STRING);
+ AddField(message2, "bar", 2,
+ FieldDescriptorProto::LABEL_REQUIRED,
+ FieldDescriptorProto::TYPE_STRING);
+ AddField(message2, "quux", 6,
+ FieldDescriptorProto::LABEL_REQUIRED,
+ FieldDescriptorProto::TYPE_STRING);
+
+ FileDescriptorProto map_file;
+ map_file.set_name("map.proto");
+ DescriptorProto* message3 = AddMessage(&map_file, "TestMessage3");
+
+ DescriptorProto* entry = AddNestedMessage(message3, "MapInt32Int32Entry");
+ AddField(entry, "key", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(entry, "value", 2,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ entry->mutable_options()->set_map_entry(true);
+
+ AddField(message3, "map_int32_int32", 1,
+ FieldDescriptorProto::LABEL_REPEATED,
+ FieldDescriptorProto::TYPE_MESSAGE)
+ ->set_type_name("MapInt32Int32Entry");
+
+ FileDescriptorProto json_file;
+ json_file.set_name("json.proto");
+ json_file.set_syntax("proto3");
+ DescriptorProto* message4 = AddMessage(&json_file, "TestMessage4");
+ AddField(message4, "field_name1", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message4, "fieldName2", 2,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message4, "FieldName3", 3,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message4, "_field_name4", 4,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message4, "FIELD_NAME5", 5,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message4, "field_name6", 6,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32)
+ ->set_json_name("@type");
+
+ // Build the descriptors and get the pointers.
+ foo_file_ = pool_.BuildFile(foo_file);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ bar_file_ = pool_.BuildFile(bar_file);
+ ASSERT_TRUE(bar_file_ != NULL);
+
+ map_file_ = pool_.BuildFile(map_file);
+ ASSERT_TRUE(map_file_ != NULL);
+
+ json_file_ = pool_.BuildFile(json_file);
+ ASSERT_TRUE(json_file_ != NULL);
+
+ ASSERT_EQ(1, foo_file_->enum_type_count());
+ enum_ = foo_file_->enum_type(0);
+
+ ASSERT_EQ(2, foo_file_->message_type_count());
+ foreign_ = foo_file_->message_type(0);
+ message_ = foo_file_->message_type(1);
+
+ ASSERT_EQ(4, message_->field_count());
+ foo_ = message_->field(0);
+ bar_ = message_->field(1);
+ baz_ = message_->field(2);
+ qux_ = message_->field(3);
+
+ ASSERT_EQ(1, bar_file_->message_type_count());
+ message2_ = bar_file_->message_type(0);
+
+ ASSERT_EQ(3, message2_->field_count());
+ foo2_ = message2_->field(0);
+ bar2_ = message2_->field(1);
+ quux2_ = message2_->field(2);
+
+ ASSERT_EQ(1, map_file_->message_type_count());
+ message3_ = map_file_->message_type(0);
+
+ ASSERT_EQ(1, message3_->field_count());
+ map_ = message3_->field(0);
+
+ ASSERT_EQ(1, json_file_->message_type_count());
+ message4_ = json_file_->message_type(0);
+ }
+
+ void CopyWithJsonName(const Descriptor* message, DescriptorProto* proto) {
+ message->CopyTo(proto);
+ message->CopyJsonNameTo(proto);
+ }
+
+ DescriptorPool pool_;
+
+ const FileDescriptor* foo_file_;
+ const FileDescriptor* bar_file_;
+ const FileDescriptor* map_file_;
+ const FileDescriptor* json_file_;
+
+ const Descriptor* message_;
+ const Descriptor* message2_;
+ const Descriptor* message3_;
+ const Descriptor* message4_;
+ const Descriptor* foreign_;
+ const EnumDescriptor* enum_;
+
+ const FieldDescriptor* foo_;
+ const FieldDescriptor* bar_;
+ const FieldDescriptor* baz_;
+ const FieldDescriptor* qux_;
+
+ const FieldDescriptor* foo2_;
+ const FieldDescriptor* bar2_;
+ const FieldDescriptor* quux2_;
+
+ const FieldDescriptor* map_;
+};
+
+TEST_F(DescriptorTest, Name) {
+ EXPECT_EQ("TestMessage", message_->name());
+ EXPECT_EQ("TestMessage", message_->full_name());
+ EXPECT_EQ(foo_file_, message_->file());
+
+ EXPECT_EQ("TestMessage2", message2_->name());
+ EXPECT_EQ("corge.grault.TestMessage2", message2_->full_name());
+ EXPECT_EQ(bar_file_, message2_->file());
+}
+
+TEST_F(DescriptorTest, ContainingType) {
+ EXPECT_TRUE(message_->containing_type() == NULL);
+ EXPECT_TRUE(message2_->containing_type() == NULL);
+}
+
+TEST_F(DescriptorTest, FieldsByIndex) {
+ ASSERT_EQ(4, message_->field_count());
+ EXPECT_EQ(foo_, message_->field(0));
+ EXPECT_EQ(bar_, message_->field(1));
+ EXPECT_EQ(baz_, message_->field(2));
+ EXPECT_EQ(qux_, message_->field(3));
+}
+
+TEST_F(DescriptorTest, FindFieldByName) {
+ // All messages in the same DescriptorPool share a single lookup table for
+ // fields. So, in addition to testing that FindFieldByName finds the fields
+ // of the message, we need to test that it does *not* find the fields of
+ // *other* messages.
+
+ EXPECT_EQ(foo_, message_->FindFieldByName("foo"));
+ EXPECT_EQ(bar_, message_->FindFieldByName("bar"));
+ EXPECT_EQ(baz_, message_->FindFieldByName("baz"));
+ EXPECT_EQ(qux_, message_->FindFieldByName("qux"));
+ EXPECT_TRUE(message_->FindFieldByName("no_such_field") == NULL);
+ EXPECT_TRUE(message_->FindFieldByName("quux") == NULL);
+
+ EXPECT_EQ(foo2_ , message2_->FindFieldByName("foo" ));
+ EXPECT_EQ(bar2_ , message2_->FindFieldByName("bar" ));
+ EXPECT_EQ(quux2_, message2_->FindFieldByName("quux"));
+ EXPECT_TRUE(message2_->FindFieldByName("baz") == NULL);
+ EXPECT_TRUE(message2_->FindFieldByName("qux") == NULL);
+}
+
+TEST_F(DescriptorTest, FindFieldByNumber) {
+ EXPECT_EQ(foo_, message_->FindFieldByNumber(1));
+ EXPECT_EQ(bar_, message_->FindFieldByNumber(6));
+ EXPECT_EQ(baz_, message_->FindFieldByNumber(500000000));
+ EXPECT_EQ(qux_, message_->FindFieldByNumber(15));
+ EXPECT_TRUE(message_->FindFieldByNumber(837592) == NULL);
+ EXPECT_TRUE(message_->FindFieldByNumber(2) == NULL);
+
+ EXPECT_EQ(foo2_ , message2_->FindFieldByNumber(1));
+ EXPECT_EQ(bar2_ , message2_->FindFieldByNumber(2));
+ EXPECT_EQ(quux2_, message2_->FindFieldByNumber(6));
+ EXPECT_TRUE(message2_->FindFieldByNumber(15) == NULL);
+ EXPECT_TRUE(message2_->FindFieldByNumber(500000000) == NULL);
+}
+
+TEST_F(DescriptorTest, FieldName) {
+ EXPECT_EQ("foo", foo_->name());
+ EXPECT_EQ("bar", bar_->name());
+ EXPECT_EQ("baz", baz_->name());
+ EXPECT_EQ("qux", qux_->name());
+}
+
+TEST_F(DescriptorTest, FieldFullName) {
+ EXPECT_EQ("TestMessage.foo", foo_->full_name());
+ EXPECT_EQ("TestMessage.bar", bar_->full_name());
+ EXPECT_EQ("TestMessage.baz", baz_->full_name());
+ EXPECT_EQ("TestMessage.qux", qux_->full_name());
+
+ EXPECT_EQ("corge.grault.TestMessage2.foo", foo2_->full_name());
+ EXPECT_EQ("corge.grault.TestMessage2.bar", bar2_->full_name());
+ EXPECT_EQ("corge.grault.TestMessage2.quux", quux2_->full_name());
+}
+
+TEST_F(DescriptorTest, FieldJsonName) {
+ EXPECT_EQ("fieldName1", message4_->field(0)->json_name());
+ EXPECT_EQ("fieldName2", message4_->field(1)->json_name());
+ EXPECT_EQ("fieldName3", message4_->field(2)->json_name());
+ EXPECT_EQ("fieldName4", message4_->field(3)->json_name());
+ EXPECT_EQ("fIELDNAME5", message4_->field(4)->json_name());
+ EXPECT_EQ("@type", message4_->field(5)->json_name());
+
+ DescriptorProto proto;
+ message4_->CopyTo(&proto);
+ ASSERT_EQ(6, proto.field_size());
+ EXPECT_FALSE(proto.field(0).has_json_name());
+ EXPECT_FALSE(proto.field(1).has_json_name());
+ EXPECT_FALSE(proto.field(2).has_json_name());
+ EXPECT_FALSE(proto.field(3).has_json_name());
+ EXPECT_FALSE(proto.field(4).has_json_name());
+ EXPECT_EQ("@type", proto.field(5).json_name());
+
+ proto.Clear();
+ CopyWithJsonName(message4_, &proto);
+ ASSERT_EQ(6, proto.field_size());
+ EXPECT_EQ("fieldName1", proto.field(0).json_name());
+ EXPECT_EQ("fieldName2", proto.field(1).json_name());
+ EXPECT_EQ("fieldName3", proto.field(2).json_name());
+ EXPECT_EQ("fieldName4", proto.field(3).json_name());
+ EXPECT_EQ("fIELDNAME5", proto.field(4).json_name());
+ EXPECT_EQ("@type", proto.field(5).json_name());
+}
+
+TEST_F(DescriptorTest, FieldFile) {
+ EXPECT_EQ(foo_file_, foo_->file());
+ EXPECT_EQ(foo_file_, bar_->file());
+ EXPECT_EQ(foo_file_, baz_->file());
+ EXPECT_EQ(foo_file_, qux_->file());
+
+ EXPECT_EQ(bar_file_, foo2_->file());
+ EXPECT_EQ(bar_file_, bar2_->file());
+ EXPECT_EQ(bar_file_, quux2_->file());
+}
+
+TEST_F(DescriptorTest, FieldIndex) {
+ EXPECT_EQ(0, foo_->index());
+ EXPECT_EQ(1, bar_->index());
+ EXPECT_EQ(2, baz_->index());
+ EXPECT_EQ(3, qux_->index());
+}
+
+TEST_F(DescriptorTest, FieldNumber) {
+ EXPECT_EQ( 1, foo_->number());
+ EXPECT_EQ( 6, bar_->number());
+ EXPECT_EQ(500000000, baz_->number());
+ EXPECT_EQ( 15, qux_->number());
+}
+
+TEST_F(DescriptorTest, FieldType) {
+ EXPECT_EQ(FieldDescriptor::TYPE_STRING , foo_->type());
+ EXPECT_EQ(FieldDescriptor::TYPE_ENUM , bar_->type());
+ EXPECT_EQ(FieldDescriptor::TYPE_MESSAGE, baz_->type());
+ EXPECT_EQ(FieldDescriptor::TYPE_GROUP , qux_->type());
+}
+
+TEST_F(DescriptorTest, FieldLabel) {
+ EXPECT_EQ(FieldDescriptor::LABEL_REQUIRED, foo_->label());
+ EXPECT_EQ(FieldDescriptor::LABEL_OPTIONAL, bar_->label());
+ EXPECT_EQ(FieldDescriptor::LABEL_REPEATED, baz_->label());
+ EXPECT_EQ(FieldDescriptor::LABEL_OPTIONAL, qux_->label());
+
+ EXPECT_TRUE (foo_->is_required());
+ EXPECT_FALSE(foo_->is_optional());
+ EXPECT_FALSE(foo_->is_repeated());
+
+ EXPECT_FALSE(bar_->is_required());
+ EXPECT_TRUE (bar_->is_optional());
+ EXPECT_FALSE(bar_->is_repeated());
+
+ EXPECT_FALSE(baz_->is_required());
+ EXPECT_FALSE(baz_->is_optional());
+ EXPECT_TRUE (baz_->is_repeated());
+}
+
+TEST_F(DescriptorTest, IsMap) {
+ EXPECT_TRUE(map_->is_map());
+ EXPECT_FALSE(baz_->is_map());
+ EXPECT_TRUE(map_->message_type()->options().map_entry());
+}
+
+TEST_F(DescriptorTest, FieldHasDefault) {
+ EXPECT_FALSE(foo_->has_default_value());
+ EXPECT_FALSE(bar_->has_default_value());
+ EXPECT_FALSE(baz_->has_default_value());
+ EXPECT_FALSE(qux_->has_default_value());
+}
+
+TEST_F(DescriptorTest, FieldContainingType) {
+ EXPECT_EQ(message_, foo_->containing_type());
+ EXPECT_EQ(message_, bar_->containing_type());
+ EXPECT_EQ(message_, baz_->containing_type());
+ EXPECT_EQ(message_, qux_->containing_type());
+
+ EXPECT_EQ(message2_, foo2_ ->containing_type());
+ EXPECT_EQ(message2_, bar2_ ->containing_type());
+ EXPECT_EQ(message2_, quux2_->containing_type());
+}
+
+TEST_F(DescriptorTest, FieldMessageType) {
+ EXPECT_TRUE(foo_->message_type() == NULL);
+ EXPECT_TRUE(bar_->message_type() == NULL);
+
+ EXPECT_EQ(foreign_, baz_->message_type());
+ EXPECT_EQ(foreign_, qux_->message_type());
+}
+
+TEST_F(DescriptorTest, FieldEnumType) {
+ EXPECT_TRUE(foo_->enum_type() == NULL);
+ EXPECT_TRUE(baz_->enum_type() == NULL);
+ EXPECT_TRUE(qux_->enum_type() == NULL);
+
+ EXPECT_EQ(enum_, bar_->enum_type());
+}
+
+// ===================================================================
+
+// Test simple flat messages and fields.
+class OneofDescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following definitions:
+ //
+ // package garply;
+ // message TestOneof {
+ // optional int32 a = 1;
+ // oneof foo {
+ // string b = 2;
+ // TestOneof c = 3;
+ // }
+ // oneof bar {
+ // float d = 4;
+ // }
+ // }
+
+ FileDescriptorProto baz_file;
+ baz_file.set_name("baz.proto");
+ baz_file.set_package("garply");
+
+ DescriptorProto* oneof_message = AddMessage(&baz_file, "TestOneof");
+ oneof_message->add_oneof_decl()->set_name("foo");
+ oneof_message->add_oneof_decl()->set_name("bar");
+
+ AddField(oneof_message, "a", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(oneof_message, "b", 2,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_STRING);
+ oneof_message->mutable_field(1)->set_oneof_index(0);
+ AddField(oneof_message, "c", 3,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_MESSAGE);
+ oneof_message->mutable_field(2)->set_oneof_index(0);
+ oneof_message->mutable_field(2)->set_type_name("TestOneof");
+
+ AddField(oneof_message, "d", 4,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_FLOAT);
+ oneof_message->mutable_field(3)->set_oneof_index(1);
+
+ // Build the descriptors and get the pointers.
+ baz_file_ = pool_.BuildFile(baz_file);
+ ASSERT_TRUE(baz_file_ != NULL);
+
+ ASSERT_EQ(1, baz_file_->message_type_count());
+ oneof_message_ = baz_file_->message_type(0);
+
+ ASSERT_EQ(2, oneof_message_->oneof_decl_count());
+ oneof_ = oneof_message_->oneof_decl(0);
+ oneof2_ = oneof_message_->oneof_decl(1);
+
+ ASSERT_EQ(4, oneof_message_->field_count());
+ a_ = oneof_message_->field(0);
+ b_ = oneof_message_->field(1);
+ c_ = oneof_message_->field(2);
+ d_ = oneof_message_->field(3);
+ }
+
+ DescriptorPool pool_;
+
+ const FileDescriptor* baz_file_;
+
+ const Descriptor* oneof_message_;
+
+ const OneofDescriptor* oneof_;
+ const OneofDescriptor* oneof2_;
+ const FieldDescriptor* a_;
+ const FieldDescriptor* b_;
+ const FieldDescriptor* c_;
+ const FieldDescriptor* d_;
+ const FieldDescriptor* e_;
+ const FieldDescriptor* f_;
+};
+
+TEST_F(OneofDescriptorTest, Normal) {
+ EXPECT_EQ("foo", oneof_->name());
+ EXPECT_EQ("garply.TestOneof.foo", oneof_->full_name());
+ EXPECT_EQ(0, oneof_->index());
+ ASSERT_EQ(2, oneof_->field_count());
+ EXPECT_EQ(b_, oneof_->field(0));
+ EXPECT_EQ(c_, oneof_->field(1));
+ EXPECT_TRUE(a_->containing_oneof() == NULL);
+ EXPECT_EQ(oneof_, b_->containing_oneof());
+ EXPECT_EQ(oneof_, c_->containing_oneof());
+}
+
+TEST_F(OneofDescriptorTest, FindByName) {
+ EXPECT_EQ(oneof_, oneof_message_->FindOneofByName("foo"));
+ EXPECT_EQ(oneof2_, oneof_message_->FindOneofByName("bar"));
+ EXPECT_TRUE(oneof_message_->FindOneofByName("no_such_oneof") == NULL);
+}
+
+// ===================================================================
+
+class StylizedFieldNamesTest : public testing::Test {
+ protected:
+ void SetUp() {
+ FileDescriptorProto file;
+ file.set_name("foo.proto");
+
+ AddExtensionRange(AddMessage(&file, "ExtendableMessage"), 1, 1000);
+
+ DescriptorProto* message = AddMessage(&file, "TestMessage");
+ AddField(message, "foo_foo", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message, "FooBar", 2,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message, "fooBaz", 3,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message, "fooFoo", 4, // Camel-case conflict with foo_foo.
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddField(message, "foobar", 5, // Lower-case conflict with FooBar.
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+
+ AddNestedExtension(message, "ExtendableMessage", "bar_foo", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddNestedExtension(message, "ExtendableMessage", "BarBar", 2,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddNestedExtension(message, "ExtendableMessage", "BarBaz", 3,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddNestedExtension(message, "ExtendableMessage", "barFoo", 4, // Conflict
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddNestedExtension(message, "ExtendableMessage", "barbar", 5, // Conflict
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+
+ AddExtension(&file, "ExtendableMessage", "baz_foo", 11,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddExtension(&file, "ExtendableMessage", "BazBar", 12,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddExtension(&file, "ExtendableMessage", "BazBaz", 13,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddExtension(&file, "ExtendableMessage", "bazFoo", 14, // Conflict
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddExtension(&file, "ExtendableMessage", "bazbar", 15, // Conflict
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+
+ file_ = pool_.BuildFile(file);
+ ASSERT_TRUE(file_ != NULL);
+ ASSERT_EQ(2, file_->message_type_count());
+ message_ = file_->message_type(1);
+ ASSERT_EQ("TestMessage", message_->name());
+ ASSERT_EQ(5, message_->field_count());
+ ASSERT_EQ(5, message_->extension_count());
+ ASSERT_EQ(5, file_->extension_count());
+ }
+
+ DescriptorPool pool_;
+ const FileDescriptor* file_;
+ const Descriptor* message_;
+};
+
+TEST_F(StylizedFieldNamesTest, LowercaseName) {
+ EXPECT_EQ("foo_foo", message_->field(0)->lowercase_name());
+ EXPECT_EQ("foobar" , message_->field(1)->lowercase_name());
+ EXPECT_EQ("foobaz" , message_->field(2)->lowercase_name());
+ EXPECT_EQ("foofoo" , message_->field(3)->lowercase_name());
+ EXPECT_EQ("foobar" , message_->field(4)->lowercase_name());
+
+ EXPECT_EQ("bar_foo", message_->extension(0)->lowercase_name());
+ EXPECT_EQ("barbar" , message_->extension(1)->lowercase_name());
+ EXPECT_EQ("barbaz" , message_->extension(2)->lowercase_name());
+ EXPECT_EQ("barfoo" , message_->extension(3)->lowercase_name());
+ EXPECT_EQ("barbar" , message_->extension(4)->lowercase_name());
+
+ EXPECT_EQ("baz_foo", file_->extension(0)->lowercase_name());
+ EXPECT_EQ("bazbar" , file_->extension(1)->lowercase_name());
+ EXPECT_EQ("bazbaz" , file_->extension(2)->lowercase_name());
+ EXPECT_EQ("bazfoo" , file_->extension(3)->lowercase_name());
+ EXPECT_EQ("bazbar" , file_->extension(4)->lowercase_name());
+}
+
+TEST_F(StylizedFieldNamesTest, CamelcaseName) {
+ EXPECT_EQ("fooFoo", message_->field(0)->camelcase_name());
+ EXPECT_EQ("fooBar", message_->field(1)->camelcase_name());
+ EXPECT_EQ("fooBaz", message_->field(2)->camelcase_name());
+ EXPECT_EQ("fooFoo", message_->field(3)->camelcase_name());
+ EXPECT_EQ("foobar", message_->field(4)->camelcase_name());
+
+ EXPECT_EQ("barFoo", message_->extension(0)->camelcase_name());
+ EXPECT_EQ("barBar", message_->extension(1)->camelcase_name());
+ EXPECT_EQ("barBaz", message_->extension(2)->camelcase_name());
+ EXPECT_EQ("barFoo", message_->extension(3)->camelcase_name());
+ EXPECT_EQ("barbar", message_->extension(4)->camelcase_name());
+
+ EXPECT_EQ("bazFoo", file_->extension(0)->camelcase_name());
+ EXPECT_EQ("bazBar", file_->extension(1)->camelcase_name());
+ EXPECT_EQ("bazBaz", file_->extension(2)->camelcase_name());
+ EXPECT_EQ("bazFoo", file_->extension(3)->camelcase_name());
+ EXPECT_EQ("bazbar", file_->extension(4)->camelcase_name());
+}
+
+TEST_F(StylizedFieldNamesTest, FindByLowercaseName) {
+ EXPECT_EQ(message_->field(0),
+ message_->FindFieldByLowercaseName("foo_foo"));
+ EXPECT_EQ(message_->field(1),
+ message_->FindFieldByLowercaseName("foobar"));
+ EXPECT_EQ(message_->field(2),
+ message_->FindFieldByLowercaseName("foobaz"));
+ EXPECT_TRUE(message_->FindFieldByLowercaseName("FooBar") == NULL);
+ EXPECT_TRUE(message_->FindFieldByLowercaseName("fooBaz") == NULL);
+ EXPECT_TRUE(message_->FindFieldByLowercaseName("bar_foo") == NULL);
+ EXPECT_TRUE(message_->FindFieldByLowercaseName("nosuchfield") == NULL);
+
+ EXPECT_EQ(message_->extension(0),
+ message_->FindExtensionByLowercaseName("bar_foo"));
+ EXPECT_EQ(message_->extension(1),
+ message_->FindExtensionByLowercaseName("barbar"));
+ EXPECT_EQ(message_->extension(2),
+ message_->FindExtensionByLowercaseName("barbaz"));
+ EXPECT_TRUE(message_->FindExtensionByLowercaseName("BarBar") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByLowercaseName("barBaz") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByLowercaseName("foo_foo") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByLowercaseName("nosuchfield") == NULL);
+
+ EXPECT_EQ(file_->extension(0),
+ file_->FindExtensionByLowercaseName("baz_foo"));
+ EXPECT_EQ(file_->extension(1),
+ file_->FindExtensionByLowercaseName("bazbar"));
+ EXPECT_EQ(file_->extension(2),
+ file_->FindExtensionByLowercaseName("bazbaz"));
+ EXPECT_TRUE(file_->FindExtensionByLowercaseName("BazBar") == NULL);
+ EXPECT_TRUE(file_->FindExtensionByLowercaseName("bazBaz") == NULL);
+ EXPECT_TRUE(file_->FindExtensionByLowercaseName("nosuchfield") == NULL);
+}
+
+TEST_F(StylizedFieldNamesTest, FindByCamelcaseName) {
+ EXPECT_EQ(message_->field(0),
+ message_->FindFieldByCamelcaseName("fooFoo"));
+ EXPECT_EQ(message_->field(1),
+ message_->FindFieldByCamelcaseName("fooBar"));
+ EXPECT_EQ(message_->field(2),
+ message_->FindFieldByCamelcaseName("fooBaz"));
+ EXPECT_TRUE(message_->FindFieldByCamelcaseName("foo_foo") == NULL);
+ EXPECT_TRUE(message_->FindFieldByCamelcaseName("FooBar") == NULL);
+ EXPECT_TRUE(message_->FindFieldByCamelcaseName("barFoo") == NULL);
+ EXPECT_TRUE(message_->FindFieldByCamelcaseName("nosuchfield") == NULL);
+
+ EXPECT_EQ(message_->extension(0),
+ message_->FindExtensionByCamelcaseName("barFoo"));
+ EXPECT_EQ(message_->extension(1),
+ message_->FindExtensionByCamelcaseName("barBar"));
+ EXPECT_EQ(message_->extension(2),
+ message_->FindExtensionByCamelcaseName("barBaz"));
+ EXPECT_TRUE(message_->FindExtensionByCamelcaseName("bar_foo") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByCamelcaseName("BarBar") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByCamelcaseName("fooFoo") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByCamelcaseName("nosuchfield") == NULL);
+
+ EXPECT_EQ(file_->extension(0),
+ file_->FindExtensionByCamelcaseName("bazFoo"));
+ EXPECT_EQ(file_->extension(1),
+ file_->FindExtensionByCamelcaseName("bazBar"));
+ EXPECT_EQ(file_->extension(2),
+ file_->FindExtensionByCamelcaseName("bazBaz"));
+ EXPECT_TRUE(file_->FindExtensionByCamelcaseName("baz_foo") == NULL);
+ EXPECT_TRUE(file_->FindExtensionByCamelcaseName("BazBar") == NULL);
+ EXPECT_TRUE(file_->FindExtensionByCamelcaseName("nosuchfield") == NULL);
+}
+
+// ===================================================================
+
+// Test enum descriptors.
+class EnumDescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following definitions:
+ //
+ // // in "foo.proto"
+ // enum TestEnum {
+ // FOO = 1;
+ // BAR = 2;
+ // }
+ //
+ // // in "bar.proto"
+ // package corge.grault;
+ // enum TestEnum2 {
+ // FOO = 1;
+ // BAZ = 3;
+ // }
+ //
+ // TestEnum2 is primarily here to test FindValueByName and friends.
+ // All enums created from the same DescriptorPool share the same lookup
+ // table, so we need to insure that they don't interfere.
+
+ // TestEnum
+ FileDescriptorProto foo_file;
+ foo_file.set_name("foo.proto");
+
+ EnumDescriptorProto* enum_proto = AddEnum(&foo_file, "TestEnum");
+ AddEnumValue(enum_proto, "FOO", 1);
+ AddEnumValue(enum_proto, "BAR", 2);
+
+ // TestEnum2
+ FileDescriptorProto bar_file;
+ bar_file.set_name("bar.proto");
+ bar_file.set_package("corge.grault");
+
+ EnumDescriptorProto* enum2_proto = AddEnum(&bar_file, "TestEnum2");
+ AddEnumValue(enum2_proto, "FOO", 1);
+ AddEnumValue(enum2_proto, "BAZ", 3);
+
+ // Build the descriptors and get the pointers.
+ foo_file_ = pool_.BuildFile(foo_file);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ bar_file_ = pool_.BuildFile(bar_file);
+ ASSERT_TRUE(bar_file_ != NULL);
+
+ ASSERT_EQ(1, foo_file_->enum_type_count());
+ enum_ = foo_file_->enum_type(0);
+
+ ASSERT_EQ(2, enum_->value_count());
+ foo_ = enum_->value(0);
+ bar_ = enum_->value(1);
+
+ ASSERT_EQ(1, bar_file_->enum_type_count());
+ enum2_ = bar_file_->enum_type(0);
+
+ ASSERT_EQ(2, enum2_->value_count());
+ foo2_ = enum2_->value(0);
+ baz2_ = enum2_->value(1);
+ }
+
+ DescriptorPool pool_;
+
+ const FileDescriptor* foo_file_;
+ const FileDescriptor* bar_file_;
+
+ const EnumDescriptor* enum_;
+ const EnumDescriptor* enum2_;
+
+ const EnumValueDescriptor* foo_;
+ const EnumValueDescriptor* bar_;
+
+ const EnumValueDescriptor* foo2_;
+ const EnumValueDescriptor* baz2_;
+};
+
+TEST_F(EnumDescriptorTest, Name) {
+ EXPECT_EQ("TestEnum", enum_->name());
+ EXPECT_EQ("TestEnum", enum_->full_name());
+ EXPECT_EQ(foo_file_, enum_->file());
+
+ EXPECT_EQ("TestEnum2", enum2_->name());
+ EXPECT_EQ("corge.grault.TestEnum2", enum2_->full_name());
+ EXPECT_EQ(bar_file_, enum2_->file());
+}
+
+TEST_F(EnumDescriptorTest, ContainingType) {
+ EXPECT_TRUE(enum_->containing_type() == NULL);
+ EXPECT_TRUE(enum2_->containing_type() == NULL);
+}
+
+TEST_F(EnumDescriptorTest, ValuesByIndex) {
+ ASSERT_EQ(2, enum_->value_count());
+ EXPECT_EQ(foo_, enum_->value(0));
+ EXPECT_EQ(bar_, enum_->value(1));
+}
+
+TEST_F(EnumDescriptorTest, FindValueByName) {
+ EXPECT_EQ(foo_ , enum_ ->FindValueByName("FOO"));
+ EXPECT_EQ(bar_ , enum_ ->FindValueByName("BAR"));
+ EXPECT_EQ(foo2_, enum2_->FindValueByName("FOO"));
+ EXPECT_EQ(baz2_, enum2_->FindValueByName("BAZ"));
+
+ EXPECT_TRUE(enum_ ->FindValueByName("NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(enum_ ->FindValueByName("BAZ" ) == NULL);
+ EXPECT_TRUE(enum2_->FindValueByName("BAR" ) == NULL);
+}
+
+TEST_F(EnumDescriptorTest, FindValueByNumber) {
+ EXPECT_EQ(foo_ , enum_ ->FindValueByNumber(1));
+ EXPECT_EQ(bar_ , enum_ ->FindValueByNumber(2));
+ EXPECT_EQ(foo2_, enum2_->FindValueByNumber(1));
+ EXPECT_EQ(baz2_, enum2_->FindValueByNumber(3));
+
+ EXPECT_TRUE(enum_ ->FindValueByNumber(416) == NULL);
+ EXPECT_TRUE(enum_ ->FindValueByNumber(3) == NULL);
+ EXPECT_TRUE(enum2_->FindValueByNumber(2) == NULL);
+}
+
+TEST_F(EnumDescriptorTest, ValueName) {
+ EXPECT_EQ("FOO", foo_->name());
+ EXPECT_EQ("BAR", bar_->name());
+}
+
+TEST_F(EnumDescriptorTest, ValueFullName) {
+ EXPECT_EQ("FOO", foo_->full_name());
+ EXPECT_EQ("BAR", bar_->full_name());
+ EXPECT_EQ("corge.grault.FOO", foo2_->full_name());
+ EXPECT_EQ("corge.grault.BAZ", baz2_->full_name());
+}
+
+TEST_F(EnumDescriptorTest, ValueIndex) {
+ EXPECT_EQ(0, foo_->index());
+ EXPECT_EQ(1, bar_->index());
+}
+
+TEST_F(EnumDescriptorTest, ValueNumber) {
+ EXPECT_EQ(1, foo_->number());
+ EXPECT_EQ(2, bar_->number());
+}
+
+TEST_F(EnumDescriptorTest, ValueType) {
+ EXPECT_EQ(enum_ , foo_ ->type());
+ EXPECT_EQ(enum_ , bar_ ->type());
+ EXPECT_EQ(enum2_, foo2_->type());
+ EXPECT_EQ(enum2_, baz2_->type());
+}
+
+// ===================================================================
+
+// Test service descriptors.
+class ServiceDescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following messages and service:
+ // // in "foo.proto"
+ // message FooRequest {}
+ // message FooResponse {}
+ // message BarRequest {}
+ // message BarResponse {}
+ // message BazRequest {}
+ // message BazResponse {}
+ //
+ // service TestService {
+ // rpc Foo(FooRequest) returns (FooResponse);
+ // rpc Bar(BarRequest) returns (BarResponse);
+ // }
+ //
+ // // in "bar.proto"
+ // package corge.grault
+ // service TestService2 {
+ // rpc Foo(FooRequest) returns (FooResponse);
+ // rpc Baz(BazRequest) returns (BazResponse);
+ // }
+
+ FileDescriptorProto foo_file;
+ foo_file.set_name("foo.proto");
+
+ AddMessage(&foo_file, "FooRequest");
+ AddMessage(&foo_file, "FooResponse");
+ AddMessage(&foo_file, "BarRequest");
+ AddMessage(&foo_file, "BarResponse");
+ AddMessage(&foo_file, "BazRequest");
+ AddMessage(&foo_file, "BazResponse");
+
+ ServiceDescriptorProto* service = AddService(&foo_file, "TestService");
+ AddMethod(service, "Foo", "FooRequest", "FooResponse");
+ AddMethod(service, "Bar", "BarRequest", "BarResponse");
+
+ FileDescriptorProto bar_file;
+ bar_file.set_name("bar.proto");
+ bar_file.set_package("corge.grault");
+ bar_file.add_dependency("foo.proto");
+
+ ServiceDescriptorProto* service2 = AddService(&bar_file, "TestService2");
+ AddMethod(service2, "Foo", "FooRequest", "FooResponse");
+ AddMethod(service2, "Baz", "BazRequest", "BazResponse");
+
+ // Build the descriptors and get the pointers.
+ foo_file_ = pool_.BuildFile(foo_file);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ bar_file_ = pool_.BuildFile(bar_file);
+ ASSERT_TRUE(bar_file_ != NULL);
+
+ ASSERT_EQ(6, foo_file_->message_type_count());
+ foo_request_ = foo_file_->message_type(0);
+ foo_response_ = foo_file_->message_type(1);
+ bar_request_ = foo_file_->message_type(2);
+ bar_response_ = foo_file_->message_type(3);
+ baz_request_ = foo_file_->message_type(4);
+ baz_response_ = foo_file_->message_type(5);
+
+ ASSERT_EQ(1, foo_file_->service_count());
+ service_ = foo_file_->service(0);
+
+ ASSERT_EQ(2, service_->method_count());
+ foo_ = service_->method(0);
+ bar_ = service_->method(1);
+
+ ASSERT_EQ(1, bar_file_->service_count());
+ service2_ = bar_file_->service(0);
+
+ ASSERT_EQ(2, service2_->method_count());
+ foo2_ = service2_->method(0);
+ baz2_ = service2_->method(1);
+ }
+
+ DescriptorPool pool_;
+
+ const FileDescriptor* foo_file_;
+ const FileDescriptor* bar_file_;
+
+ const Descriptor* foo_request_;
+ const Descriptor* foo_response_;
+ const Descriptor* bar_request_;
+ const Descriptor* bar_response_;
+ const Descriptor* baz_request_;
+ const Descriptor* baz_response_;
+
+ const ServiceDescriptor* service_;
+ const ServiceDescriptor* service2_;
+
+ const MethodDescriptor* foo_;
+ const MethodDescriptor* bar_;
+
+ const MethodDescriptor* foo2_;
+ const MethodDescriptor* baz2_;
+};
+
+TEST_F(ServiceDescriptorTest, Name) {
+ EXPECT_EQ("TestService", service_->name());
+ EXPECT_EQ("TestService", service_->full_name());
+ EXPECT_EQ(foo_file_, service_->file());
+
+ EXPECT_EQ("TestService2", service2_->name());
+ EXPECT_EQ("corge.grault.TestService2", service2_->full_name());
+ EXPECT_EQ(bar_file_, service2_->file());
+}
+
+TEST_F(ServiceDescriptorTest, MethodsByIndex) {
+ ASSERT_EQ(2, service_->method_count());
+ EXPECT_EQ(foo_, service_->method(0));
+ EXPECT_EQ(bar_, service_->method(1));
+}
+
+TEST_F(ServiceDescriptorTest, FindMethodByName) {
+ EXPECT_EQ(foo_ , service_ ->FindMethodByName("Foo"));
+ EXPECT_EQ(bar_ , service_ ->FindMethodByName("Bar"));
+ EXPECT_EQ(foo2_, service2_->FindMethodByName("Foo"));
+ EXPECT_EQ(baz2_, service2_->FindMethodByName("Baz"));
+
+ EXPECT_TRUE(service_ ->FindMethodByName("NoSuchMethod") == NULL);
+ EXPECT_TRUE(service_ ->FindMethodByName("Baz" ) == NULL);
+ EXPECT_TRUE(service2_->FindMethodByName("Bar" ) == NULL);
+}
+
+TEST_F(ServiceDescriptorTest, MethodName) {
+ EXPECT_EQ("Foo", foo_->name());
+ EXPECT_EQ("Bar", bar_->name());
+}
+
+TEST_F(ServiceDescriptorTest, MethodFullName) {
+ EXPECT_EQ("TestService.Foo", foo_->full_name());
+ EXPECT_EQ("TestService.Bar", bar_->full_name());
+ EXPECT_EQ("corge.grault.TestService2.Foo", foo2_->full_name());
+ EXPECT_EQ("corge.grault.TestService2.Baz", baz2_->full_name());
+}
+
+TEST_F(ServiceDescriptorTest, MethodIndex) {
+ EXPECT_EQ(0, foo_->index());
+ EXPECT_EQ(1, bar_->index());
+}
+
+TEST_F(ServiceDescriptorTest, MethodParent) {
+ EXPECT_EQ(service_, foo_->service());
+ EXPECT_EQ(service_, bar_->service());
+}
+
+TEST_F(ServiceDescriptorTest, MethodInputType) {
+ EXPECT_EQ(foo_request_, foo_->input_type());
+ EXPECT_EQ(bar_request_, bar_->input_type());
+}
+
+TEST_F(ServiceDescriptorTest, MethodOutputType) {
+ EXPECT_EQ(foo_response_, foo_->output_type());
+ EXPECT_EQ(bar_response_, bar_->output_type());
+}
+
+// ===================================================================
+
+// Test nested types.
+class NestedDescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following definitions:
+ //
+ // // in "foo.proto"
+ // message TestMessage {
+ // message Foo {}
+ // message Bar {}
+ // enum Baz { A = 1; }
+ // enum Qux { B = 1; }
+ // }
+ //
+ // // in "bar.proto"
+ // package corge.grault;
+ // message TestMessage2 {
+ // message Foo {}
+ // message Baz {}
+ // enum Qux { A = 1; }
+ // enum Quux { C = 1; }
+ // }
+ //
+ // TestMessage2 is primarily here to test FindNestedTypeByName and friends.
+ // All messages created from the same DescriptorPool share the same lookup
+ // table, so we need to insure that they don't interfere.
+ //
+ // We add enum values to the enums in order to test searching for enum
+ // values across a message's scope.
+
+ FileDescriptorProto foo_file;
+ foo_file.set_name("foo.proto");
+
+ DescriptorProto* message = AddMessage(&foo_file, "TestMessage");
+ AddNestedMessage(message, "Foo");
+ AddNestedMessage(message, "Bar");
+ EnumDescriptorProto* baz = AddNestedEnum(message, "Baz");
+ AddEnumValue(baz, "A", 1);
+ EnumDescriptorProto* qux = AddNestedEnum(message, "Qux");
+ AddEnumValue(qux, "B", 1);
+
+ FileDescriptorProto bar_file;
+ bar_file.set_name("bar.proto");
+ bar_file.set_package("corge.grault");
+
+ DescriptorProto* message2 = AddMessage(&bar_file, "TestMessage2");
+ AddNestedMessage(message2, "Foo");
+ AddNestedMessage(message2, "Baz");
+ EnumDescriptorProto* qux2 = AddNestedEnum(message2, "Qux");
+ AddEnumValue(qux2, "A", 1);
+ EnumDescriptorProto* quux2 = AddNestedEnum(message2, "Quux");
+ AddEnumValue(quux2, "C", 1);
+
+ // Build the descriptors and get the pointers.
+ foo_file_ = pool_.BuildFile(foo_file);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ bar_file_ = pool_.BuildFile(bar_file);
+ ASSERT_TRUE(bar_file_ != NULL);
+
+ ASSERT_EQ(1, foo_file_->message_type_count());
+ message_ = foo_file_->message_type(0);
+
+ ASSERT_EQ(2, message_->nested_type_count());
+ foo_ = message_->nested_type(0);
+ bar_ = message_->nested_type(1);
+
+ ASSERT_EQ(2, message_->enum_type_count());
+ baz_ = message_->enum_type(0);
+ qux_ = message_->enum_type(1);
+
+ ASSERT_EQ(1, baz_->value_count());
+ a_ = baz_->value(0);
+ ASSERT_EQ(1, qux_->value_count());
+ b_ = qux_->value(0);
+
+ ASSERT_EQ(1, bar_file_->message_type_count());
+ message2_ = bar_file_->message_type(0);
+
+ ASSERT_EQ(2, message2_->nested_type_count());
+ foo2_ = message2_->nested_type(0);
+ baz2_ = message2_->nested_type(1);
+
+ ASSERT_EQ(2, message2_->enum_type_count());
+ qux2_ = message2_->enum_type(0);
+ quux2_ = message2_->enum_type(1);
+
+ ASSERT_EQ(1, qux2_->value_count());
+ a2_ = qux2_->value(0);
+ ASSERT_EQ(1, quux2_->value_count());
+ c2_ = quux2_->value(0);
+ }
+
+ DescriptorPool pool_;
+
+ const FileDescriptor* foo_file_;
+ const FileDescriptor* bar_file_;
+
+ const Descriptor* message_;
+ const Descriptor* message2_;
+
+ const Descriptor* foo_;
+ const Descriptor* bar_;
+ const EnumDescriptor* baz_;
+ const EnumDescriptor* qux_;
+ const EnumValueDescriptor* a_;
+ const EnumValueDescriptor* b_;
+
+ const Descriptor* foo2_;
+ const Descriptor* baz2_;
+ const EnumDescriptor* qux2_;
+ const EnumDescriptor* quux2_;
+ const EnumValueDescriptor* a2_;
+ const EnumValueDescriptor* c2_;
+};
+
+TEST_F(NestedDescriptorTest, MessageName) {
+ EXPECT_EQ("Foo", foo_ ->name());
+ EXPECT_EQ("Bar", bar_ ->name());
+ EXPECT_EQ("Foo", foo2_->name());
+ EXPECT_EQ("Baz", baz2_->name());
+
+ EXPECT_EQ("TestMessage.Foo", foo_->full_name());
+ EXPECT_EQ("TestMessage.Bar", bar_->full_name());
+ EXPECT_EQ("corge.grault.TestMessage2.Foo", foo2_->full_name());
+ EXPECT_EQ("corge.grault.TestMessage2.Baz", baz2_->full_name());
+}
+
+TEST_F(NestedDescriptorTest, MessageContainingType) {
+ EXPECT_EQ(message_ , foo_ ->containing_type());
+ EXPECT_EQ(message_ , bar_ ->containing_type());
+ EXPECT_EQ(message2_, foo2_->containing_type());
+ EXPECT_EQ(message2_, baz2_->containing_type());
+}
+
+TEST_F(NestedDescriptorTest, NestedMessagesByIndex) {
+ ASSERT_EQ(2, message_->nested_type_count());
+ EXPECT_EQ(foo_, message_->nested_type(0));
+ EXPECT_EQ(bar_, message_->nested_type(1));
+}
+
+TEST_F(NestedDescriptorTest, FindFieldByNameDoesntFindNestedTypes) {
+ EXPECT_TRUE(message_->FindFieldByName("Foo") == NULL);
+ EXPECT_TRUE(message_->FindFieldByName("Qux") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByName("Foo") == NULL);
+ EXPECT_TRUE(message_->FindExtensionByName("Qux") == NULL);
+}
+
+TEST_F(NestedDescriptorTest, FindNestedTypeByName) {
+ EXPECT_EQ(foo_ , message_ ->FindNestedTypeByName("Foo"));
+ EXPECT_EQ(bar_ , message_ ->FindNestedTypeByName("Bar"));
+ EXPECT_EQ(foo2_, message2_->FindNestedTypeByName("Foo"));
+ EXPECT_EQ(baz2_, message2_->FindNestedTypeByName("Baz"));
+
+ EXPECT_TRUE(message_ ->FindNestedTypeByName("NoSuchType") == NULL);
+ EXPECT_TRUE(message_ ->FindNestedTypeByName("Baz" ) == NULL);
+ EXPECT_TRUE(message2_->FindNestedTypeByName("Bar" ) == NULL);
+
+ EXPECT_TRUE(message_->FindNestedTypeByName("Qux") == NULL);
+}
+
+TEST_F(NestedDescriptorTest, EnumName) {
+ EXPECT_EQ("Baz" , baz_ ->name());
+ EXPECT_EQ("Qux" , qux_ ->name());
+ EXPECT_EQ("Qux" , qux2_->name());
+ EXPECT_EQ("Quux", quux2_->name());
+
+ EXPECT_EQ("TestMessage.Baz", baz_->full_name());
+ EXPECT_EQ("TestMessage.Qux", qux_->full_name());
+ EXPECT_EQ("corge.grault.TestMessage2.Qux" , qux2_ ->full_name());
+ EXPECT_EQ("corge.grault.TestMessage2.Quux", quux2_->full_name());
+}
+
+TEST_F(NestedDescriptorTest, EnumContainingType) {
+ EXPECT_EQ(message_ , baz_ ->containing_type());
+ EXPECT_EQ(message_ , qux_ ->containing_type());
+ EXPECT_EQ(message2_, qux2_ ->containing_type());
+ EXPECT_EQ(message2_, quux2_->containing_type());
+}
+
+TEST_F(NestedDescriptorTest, NestedEnumsByIndex) {
+ ASSERT_EQ(2, message_->nested_type_count());
+ EXPECT_EQ(foo_, message_->nested_type(0));
+ EXPECT_EQ(bar_, message_->nested_type(1));
+}
+
+TEST_F(NestedDescriptorTest, FindEnumTypeByName) {
+ EXPECT_EQ(baz_ , message_ ->FindEnumTypeByName("Baz" ));
+ EXPECT_EQ(qux_ , message_ ->FindEnumTypeByName("Qux" ));
+ EXPECT_EQ(qux2_ , message2_->FindEnumTypeByName("Qux" ));
+ EXPECT_EQ(quux2_, message2_->FindEnumTypeByName("Quux"));
+
+ EXPECT_TRUE(message_ ->FindEnumTypeByName("NoSuchType") == NULL);
+ EXPECT_TRUE(message_ ->FindEnumTypeByName("Quux" ) == NULL);
+ EXPECT_TRUE(message2_->FindEnumTypeByName("Baz" ) == NULL);
+
+ EXPECT_TRUE(message_->FindEnumTypeByName("Foo") == NULL);
+}
+
+TEST_F(NestedDescriptorTest, FindEnumValueByName) {
+ EXPECT_EQ(a_ , message_ ->FindEnumValueByName("A"));
+ EXPECT_EQ(b_ , message_ ->FindEnumValueByName("B"));
+ EXPECT_EQ(a2_, message2_->FindEnumValueByName("A"));
+ EXPECT_EQ(c2_, message2_->FindEnumValueByName("C"));
+
+ EXPECT_TRUE(message_ ->FindEnumValueByName("NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(message_ ->FindEnumValueByName("C" ) == NULL);
+ EXPECT_TRUE(message2_->FindEnumValueByName("B" ) == NULL);
+
+ EXPECT_TRUE(message_->FindEnumValueByName("Foo") == NULL);
+}
+
+// ===================================================================
+
+// Test extensions.
+class ExtensionDescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following definitions:
+ //
+ // enum Baz {}
+ // message Qux {}
+ //
+ // message Foo {
+ // extensions 10 to 19;
+ // extensions 30 to 39;
+ // }
+ // extends Foo with optional int32 foo_int32 = 10;
+ // extends Foo with repeated TestEnum foo_enum = 19;
+ // message Bar {
+ // extends Foo with optional Qux foo_message = 30;
+ // // (using Qux as the group type)
+ // extends Foo with repeated group foo_group = 39;
+ // }
+
+ FileDescriptorProto foo_file;
+ foo_file.set_name("foo.proto");
+
+ AddEmptyEnum(&foo_file, "Baz");
+ AddMessage(&foo_file, "Qux");
+
+ DescriptorProto* foo = AddMessage(&foo_file, "Foo");
+ AddExtensionRange(foo, 10, 20);
+ AddExtensionRange(foo, 30, 40);
+
+ AddExtension(&foo_file, "Foo", "foo_int32", 10,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ AddExtension(&foo_file, "Foo", "foo_enum", 19,
+ FieldDescriptorProto::LABEL_REPEATED,
+ FieldDescriptorProto::TYPE_ENUM)
+ ->set_type_name("Baz");
+
+ DescriptorProto* bar = AddMessage(&foo_file, "Bar");
+ AddNestedExtension(bar, "Foo", "foo_message", 30,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_MESSAGE)
+ ->set_type_name("Qux");
+ AddNestedExtension(bar, "Foo", "foo_group", 39,
+ FieldDescriptorProto::LABEL_REPEATED,
+ FieldDescriptorProto::TYPE_GROUP)
+ ->set_type_name("Qux");
+
+ // Build the descriptors and get the pointers.
+ foo_file_ = pool_.BuildFile(foo_file);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ ASSERT_EQ(1, foo_file_->enum_type_count());
+ baz_ = foo_file_->enum_type(0);
+
+ ASSERT_EQ(3, foo_file_->message_type_count());
+ qux_ = foo_file_->message_type(0);
+ foo_ = foo_file_->message_type(1);
+ bar_ = foo_file_->message_type(2);
+ }
+
+ DescriptorPool pool_;
+
+ const FileDescriptor* foo_file_;
+
+ const Descriptor* foo_;
+ const Descriptor* bar_;
+ const EnumDescriptor* baz_;
+ const Descriptor* qux_;
+};
+
+TEST_F(ExtensionDescriptorTest, ExtensionRanges) {
+ EXPECT_EQ(0, bar_->extension_range_count());
+ ASSERT_EQ(2, foo_->extension_range_count());
+
+ EXPECT_EQ(10, foo_->extension_range(0)->start);
+ EXPECT_EQ(30, foo_->extension_range(1)->start);
+
+ EXPECT_EQ(20, foo_->extension_range(0)->end);
+ EXPECT_EQ(40, foo_->extension_range(1)->end);
+};
+
+TEST_F(ExtensionDescriptorTest, Extensions) {
+ EXPECT_EQ(0, foo_->extension_count());
+ ASSERT_EQ(2, foo_file_->extension_count());
+ ASSERT_EQ(2, bar_->extension_count());
+
+ EXPECT_TRUE(foo_file_->extension(0)->is_extension());
+ EXPECT_TRUE(foo_file_->extension(1)->is_extension());
+ EXPECT_TRUE(bar_->extension(0)->is_extension());
+ EXPECT_TRUE(bar_->extension(1)->is_extension());
+
+ EXPECT_EQ("foo_int32" , foo_file_->extension(0)->name());
+ EXPECT_EQ("foo_enum" , foo_file_->extension(1)->name());
+ EXPECT_EQ("foo_message", bar_->extension(0)->name());
+ EXPECT_EQ("foo_group" , bar_->extension(1)->name());
+
+ EXPECT_EQ(10, foo_file_->extension(0)->number());
+ EXPECT_EQ(19, foo_file_->extension(1)->number());
+ EXPECT_EQ(30, bar_->extension(0)->number());
+ EXPECT_EQ(39, bar_->extension(1)->number());
+
+ EXPECT_EQ(FieldDescriptor::TYPE_INT32 , foo_file_->extension(0)->type());
+ EXPECT_EQ(FieldDescriptor::TYPE_ENUM , foo_file_->extension(1)->type());
+ EXPECT_EQ(FieldDescriptor::TYPE_MESSAGE, bar_->extension(0)->type());
+ EXPECT_EQ(FieldDescriptor::TYPE_GROUP , bar_->extension(1)->type());
+
+ EXPECT_EQ(baz_, foo_file_->extension(1)->enum_type());
+ EXPECT_EQ(qux_, bar_->extension(0)->message_type());
+ EXPECT_EQ(qux_, bar_->extension(1)->message_type());
+
+ EXPECT_EQ(FieldDescriptor::LABEL_OPTIONAL, foo_file_->extension(0)->label());
+ EXPECT_EQ(FieldDescriptor::LABEL_REPEATED, foo_file_->extension(1)->label());
+ EXPECT_EQ(FieldDescriptor::LABEL_OPTIONAL, bar_->extension(0)->label());
+ EXPECT_EQ(FieldDescriptor::LABEL_REPEATED, bar_->extension(1)->label());
+
+ EXPECT_EQ(foo_, foo_file_->extension(0)->containing_type());
+ EXPECT_EQ(foo_, foo_file_->extension(1)->containing_type());
+ EXPECT_EQ(foo_, bar_->extension(0)->containing_type());
+ EXPECT_EQ(foo_, bar_->extension(1)->containing_type());
+
+ EXPECT_TRUE(foo_file_->extension(0)->extension_scope() == NULL);
+ EXPECT_TRUE(foo_file_->extension(1)->extension_scope() == NULL);
+ EXPECT_EQ(bar_, bar_->extension(0)->extension_scope());
+ EXPECT_EQ(bar_, bar_->extension(1)->extension_scope());
+};
+
+TEST_F(ExtensionDescriptorTest, IsExtensionNumber) {
+ EXPECT_FALSE(foo_->IsExtensionNumber( 9));
+ EXPECT_TRUE (foo_->IsExtensionNumber(10));
+ EXPECT_TRUE (foo_->IsExtensionNumber(19));
+ EXPECT_FALSE(foo_->IsExtensionNumber(20));
+ EXPECT_FALSE(foo_->IsExtensionNumber(29));
+ EXPECT_TRUE (foo_->IsExtensionNumber(30));
+ EXPECT_TRUE (foo_->IsExtensionNumber(39));
+ EXPECT_FALSE(foo_->IsExtensionNumber(40));
+}
+
+TEST_F(ExtensionDescriptorTest, FindExtensionByName) {
+ // Note that FileDescriptor::FindExtensionByName() is tested by
+ // FileDescriptorTest.
+ ASSERT_EQ(2, bar_->extension_count());
+
+ EXPECT_EQ(bar_->extension(0), bar_->FindExtensionByName("foo_message"));
+ EXPECT_EQ(bar_->extension(1), bar_->FindExtensionByName("foo_group" ));
+
+ EXPECT_TRUE(bar_->FindExtensionByName("no_such_extension") == NULL);
+ EXPECT_TRUE(foo_->FindExtensionByName("foo_int32") == NULL);
+ EXPECT_TRUE(foo_->FindExtensionByName("foo_message") == NULL);
+}
+
+TEST_F(ExtensionDescriptorTest, FindAllExtensions) {
+ vector<const FieldDescriptor*> extensions;
+ pool_.FindAllExtensions(foo_, &extensions);
+ ASSERT_EQ(4, extensions.size());
+ EXPECT_EQ(10, extensions[0]->number());
+ EXPECT_EQ(19, extensions[1]->number());
+ EXPECT_EQ(30, extensions[2]->number());
+ EXPECT_EQ(39, extensions[3]->number());
+}
+
+TEST_F(ExtensionDescriptorTest, DuplicateFieldNumber) {
+ DescriptorPool pool;
+ FileDescriptorProto file_proto;
+ // Add "google/protobuf/descriptor.proto".
+ FileDescriptorProto::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+ // Add "foo.proto":
+ // import "google/protobuf/descriptor.proto";
+ // extend google.protobuf.FieldOptions {
+ // optional int32 option1 = 1000;
+ // }
+ file_proto.Clear();
+ file_proto.set_name("foo.proto");
+ file_proto.add_dependency("google/protobuf/descriptor.proto");
+ AddExtension(&file_proto, "google.protobuf.FieldOptions", "option1", 1000,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+ // Add "bar.proto":
+ // import "google/protobuf/descriptor.proto";
+ // extend google.protobuf.FieldOptions {
+ // optional int32 option2 = 1000;
+ // }
+ file_proto.Clear();
+ file_proto.set_name("bar.proto");
+ file_proto.add_dependency("google/protobuf/descriptor.proto");
+ AddExtension(&file_proto, "google.protobuf.FieldOptions", "option2", 1000,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ // Currently we only generate a warning for conflicting extension numbers.
+ // TODO(xiaofeng): Change it to an error.
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+}
+
+// ===================================================================
+
+// Test reserved fields.
+class ReservedDescriptorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ // Build descriptors for the following definitions:
+ //
+ // message Foo {
+ // reserved 2, 9 to 11, 15;
+ // reserved "foo", "bar";
+ // }
+
+ FileDescriptorProto foo_file;
+ foo_file.set_name("foo.proto");
+
+ DescriptorProto* foo = AddMessage(&foo_file, "Foo");
+ AddReservedRange(foo, 2, 3);
+ AddReservedRange(foo, 9, 12);
+ AddReservedRange(foo, 15, 16);
+
+ foo->add_reserved_name("foo");
+ foo->add_reserved_name("bar");
+
+ // Build the descriptors and get the pointers.
+ foo_file_ = pool_.BuildFile(foo_file);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ ASSERT_EQ(1, foo_file_->message_type_count());
+ foo_ = foo_file_->message_type(0);
+ }
+
+ DescriptorPool pool_;
+ const FileDescriptor* foo_file_;
+ const Descriptor* foo_;
+};
+
+TEST_F(ReservedDescriptorTest, ReservedRanges) {
+ ASSERT_EQ(3, foo_->reserved_range_count());
+
+ EXPECT_EQ(2, foo_->reserved_range(0)->start);
+ EXPECT_EQ(3, foo_->reserved_range(0)->end);
+
+ EXPECT_EQ(9, foo_->reserved_range(1)->start);
+ EXPECT_EQ(12, foo_->reserved_range(1)->end);
+
+ EXPECT_EQ(15, foo_->reserved_range(2)->start);
+ EXPECT_EQ(16, foo_->reserved_range(2)->end);
+};
+
+TEST_F(ReservedDescriptorTest, IsReservedNumber) {
+ EXPECT_FALSE(foo_->IsReservedNumber(1));
+ EXPECT_TRUE (foo_->IsReservedNumber(2));
+ EXPECT_FALSE(foo_->IsReservedNumber(3));
+ EXPECT_FALSE(foo_->IsReservedNumber(8));
+ EXPECT_TRUE (foo_->IsReservedNumber(9));
+ EXPECT_TRUE (foo_->IsReservedNumber(10));
+ EXPECT_TRUE (foo_->IsReservedNumber(11));
+ EXPECT_FALSE(foo_->IsReservedNumber(12));
+ EXPECT_FALSE(foo_->IsReservedNumber(13));
+ EXPECT_FALSE(foo_->IsReservedNumber(14));
+ EXPECT_TRUE (foo_->IsReservedNumber(15));
+ EXPECT_FALSE(foo_->IsReservedNumber(16));
+};
+
+TEST_F(ReservedDescriptorTest, ReservedNames) {
+ ASSERT_EQ(2, foo_->reserved_name_count());
+
+ EXPECT_EQ("foo", foo_->reserved_name(0));
+ EXPECT_EQ("bar", foo_->reserved_name(1));
+};
+
+TEST_F(ReservedDescriptorTest, IsReservedName) {
+ EXPECT_TRUE (foo_->IsReservedName("foo"));
+ EXPECT_TRUE (foo_->IsReservedName("bar"));
+ EXPECT_FALSE(foo_->IsReservedName("baz"));
+};
+
+// ===================================================================
+
+class MiscTest : public testing::Test {
+ protected:
+ // Function which makes a field descriptor of the given type.
+ const FieldDescriptor* GetFieldDescriptorOfType(FieldDescriptor::Type type) {
+ FileDescriptorProto file_proto;
+ file_proto.set_name("foo.proto");
+ AddEmptyEnum(&file_proto, "DummyEnum");
+
+ DescriptorProto* message = AddMessage(&file_proto, "TestMessage");
+ FieldDescriptorProto* field =
+ AddField(message, "foo", 1, FieldDescriptorProto::LABEL_OPTIONAL,
+ static_cast<FieldDescriptorProto::Type>(static_cast<int>(type)));
+
+ if (type == FieldDescriptor::TYPE_MESSAGE ||
+ type == FieldDescriptor::TYPE_GROUP) {
+ field->set_type_name("TestMessage");
+ } else if (type == FieldDescriptor::TYPE_ENUM) {
+ field->set_type_name("DummyEnum");
+ }
+
+ // Build the descriptors and get the pointers.
+ pool_.reset(new DescriptorPool());
+ const FileDescriptor* file = pool_->BuildFile(file_proto);
+
+ if (file != NULL &&
+ file->message_type_count() == 1 &&
+ file->message_type(0)->field_count() == 1) {
+ return file->message_type(0)->field(0);
+ } else {
+ return NULL;
+ }
+ }
+
+ const char* GetTypeNameForFieldType(FieldDescriptor::Type type) {
+ const FieldDescriptor* field = GetFieldDescriptorOfType(type);
+ return field != NULL ? field->type_name() : "";
+ }
+
+ FieldDescriptor::CppType GetCppTypeForFieldType(FieldDescriptor::Type type) {
+ const FieldDescriptor* field = GetFieldDescriptorOfType(type);
+ return field != NULL ? field->cpp_type() :
+ static_cast<FieldDescriptor::CppType>(0);
+ }
+
+ const char* GetCppTypeNameForFieldType(FieldDescriptor::Type type) {
+ const FieldDescriptor* field = GetFieldDescriptorOfType(type);
+ return field != NULL ? field->cpp_type_name() : "";
+ }
+
+ const Descriptor* GetMessageDescriptorForFieldType(
+ FieldDescriptor::Type type) {
+ const FieldDescriptor* field = GetFieldDescriptorOfType(type);
+ return field != NULL ? field->message_type() : NULL;
+ }
+
+ const EnumDescriptor* GetEnumDescriptorForFieldType(
+ FieldDescriptor::Type type) {
+ const FieldDescriptor* field = GetFieldDescriptorOfType(type);
+ return field != NULL ? field->enum_type() : NULL;
+ }
+
+ google::protobuf::scoped_ptr<DescriptorPool> pool_;
+};
+
+TEST_F(MiscTest, TypeNames) {
+ // Test that correct type names are returned.
+
+ typedef FieldDescriptor FD; // avoid ugly line wrapping
+
+ EXPECT_STREQ("double" , GetTypeNameForFieldType(FD::TYPE_DOUBLE ));
+ EXPECT_STREQ("float" , GetTypeNameForFieldType(FD::TYPE_FLOAT ));
+ EXPECT_STREQ("int64" , GetTypeNameForFieldType(FD::TYPE_INT64 ));
+ EXPECT_STREQ("uint64" , GetTypeNameForFieldType(FD::TYPE_UINT64 ));
+ EXPECT_STREQ("int32" , GetTypeNameForFieldType(FD::TYPE_INT32 ));
+ EXPECT_STREQ("fixed64" , GetTypeNameForFieldType(FD::TYPE_FIXED64 ));
+ EXPECT_STREQ("fixed32" , GetTypeNameForFieldType(FD::TYPE_FIXED32 ));
+ EXPECT_STREQ("bool" , GetTypeNameForFieldType(FD::TYPE_BOOL ));
+ EXPECT_STREQ("string" , GetTypeNameForFieldType(FD::TYPE_STRING ));
+ EXPECT_STREQ("group" , GetTypeNameForFieldType(FD::TYPE_GROUP ));
+ EXPECT_STREQ("message" , GetTypeNameForFieldType(FD::TYPE_MESSAGE ));
+ EXPECT_STREQ("bytes" , GetTypeNameForFieldType(FD::TYPE_BYTES ));
+ EXPECT_STREQ("uint32" , GetTypeNameForFieldType(FD::TYPE_UINT32 ));
+ EXPECT_STREQ("enum" , GetTypeNameForFieldType(FD::TYPE_ENUM ));
+ EXPECT_STREQ("sfixed32", GetTypeNameForFieldType(FD::TYPE_SFIXED32));
+ EXPECT_STREQ("sfixed64", GetTypeNameForFieldType(FD::TYPE_SFIXED64));
+ EXPECT_STREQ("sint32" , GetTypeNameForFieldType(FD::TYPE_SINT32 ));
+ EXPECT_STREQ("sint64" , GetTypeNameForFieldType(FD::TYPE_SINT64 ));
+}
+
+TEST_F(MiscTest, StaticTypeNames) {
+ // Test that correct type names are returned.
+
+ typedef FieldDescriptor FD; // avoid ugly line wrapping
+
+ EXPECT_STREQ("double" , FD::TypeName(FD::TYPE_DOUBLE ));
+ EXPECT_STREQ("float" , FD::TypeName(FD::TYPE_FLOAT ));
+ EXPECT_STREQ("int64" , FD::TypeName(FD::TYPE_INT64 ));
+ EXPECT_STREQ("uint64" , FD::TypeName(FD::TYPE_UINT64 ));
+ EXPECT_STREQ("int32" , FD::TypeName(FD::TYPE_INT32 ));
+ EXPECT_STREQ("fixed64" , FD::TypeName(FD::TYPE_FIXED64 ));
+ EXPECT_STREQ("fixed32" , FD::TypeName(FD::TYPE_FIXED32 ));
+ EXPECT_STREQ("bool" , FD::TypeName(FD::TYPE_BOOL ));
+ EXPECT_STREQ("string" , FD::TypeName(FD::TYPE_STRING ));
+ EXPECT_STREQ("group" , FD::TypeName(FD::TYPE_GROUP ));
+ EXPECT_STREQ("message" , FD::TypeName(FD::TYPE_MESSAGE ));
+ EXPECT_STREQ("bytes" , FD::TypeName(FD::TYPE_BYTES ));
+ EXPECT_STREQ("uint32" , FD::TypeName(FD::TYPE_UINT32 ));
+ EXPECT_STREQ("enum" , FD::TypeName(FD::TYPE_ENUM ));
+ EXPECT_STREQ("sfixed32", FD::TypeName(FD::TYPE_SFIXED32));
+ EXPECT_STREQ("sfixed64", FD::TypeName(FD::TYPE_SFIXED64));
+ EXPECT_STREQ("sint32" , FD::TypeName(FD::TYPE_SINT32 ));
+ EXPECT_STREQ("sint64" , FD::TypeName(FD::TYPE_SINT64 ));
+}
+
+TEST_F(MiscTest, CppTypes) {
+ // Test that CPP types are assigned correctly.
+
+ typedef FieldDescriptor FD; // avoid ugly line wrapping
+
+ EXPECT_EQ(FD::CPPTYPE_DOUBLE , GetCppTypeForFieldType(FD::TYPE_DOUBLE ));
+ EXPECT_EQ(FD::CPPTYPE_FLOAT , GetCppTypeForFieldType(FD::TYPE_FLOAT ));
+ EXPECT_EQ(FD::CPPTYPE_INT64 , GetCppTypeForFieldType(FD::TYPE_INT64 ));
+ EXPECT_EQ(FD::CPPTYPE_UINT64 , GetCppTypeForFieldType(FD::TYPE_UINT64 ));
+ EXPECT_EQ(FD::CPPTYPE_INT32 , GetCppTypeForFieldType(FD::TYPE_INT32 ));
+ EXPECT_EQ(FD::CPPTYPE_UINT64 , GetCppTypeForFieldType(FD::TYPE_FIXED64 ));
+ EXPECT_EQ(FD::CPPTYPE_UINT32 , GetCppTypeForFieldType(FD::TYPE_FIXED32 ));
+ EXPECT_EQ(FD::CPPTYPE_BOOL , GetCppTypeForFieldType(FD::TYPE_BOOL ));
+ EXPECT_EQ(FD::CPPTYPE_STRING , GetCppTypeForFieldType(FD::TYPE_STRING ));
+ EXPECT_EQ(FD::CPPTYPE_MESSAGE, GetCppTypeForFieldType(FD::TYPE_GROUP ));
+ EXPECT_EQ(FD::CPPTYPE_MESSAGE, GetCppTypeForFieldType(FD::TYPE_MESSAGE ));
+ EXPECT_EQ(FD::CPPTYPE_STRING , GetCppTypeForFieldType(FD::TYPE_BYTES ));
+ EXPECT_EQ(FD::CPPTYPE_UINT32 , GetCppTypeForFieldType(FD::TYPE_UINT32 ));
+ EXPECT_EQ(FD::CPPTYPE_ENUM , GetCppTypeForFieldType(FD::TYPE_ENUM ));
+ EXPECT_EQ(FD::CPPTYPE_INT32 , GetCppTypeForFieldType(FD::TYPE_SFIXED32));
+ EXPECT_EQ(FD::CPPTYPE_INT64 , GetCppTypeForFieldType(FD::TYPE_SFIXED64));
+ EXPECT_EQ(FD::CPPTYPE_INT32 , GetCppTypeForFieldType(FD::TYPE_SINT32 ));
+ EXPECT_EQ(FD::CPPTYPE_INT64 , GetCppTypeForFieldType(FD::TYPE_SINT64 ));
+}
+
+TEST_F(MiscTest, CppTypeNames) {
+ // Test that correct CPP type names are returned.
+
+ typedef FieldDescriptor FD; // avoid ugly line wrapping
+
+ EXPECT_STREQ("double" , GetCppTypeNameForFieldType(FD::TYPE_DOUBLE ));
+ EXPECT_STREQ("float" , GetCppTypeNameForFieldType(FD::TYPE_FLOAT ));
+ EXPECT_STREQ("int64" , GetCppTypeNameForFieldType(FD::TYPE_INT64 ));
+ EXPECT_STREQ("uint64" , GetCppTypeNameForFieldType(FD::TYPE_UINT64 ));
+ EXPECT_STREQ("int32" , GetCppTypeNameForFieldType(FD::TYPE_INT32 ));
+ EXPECT_STREQ("uint64" , GetCppTypeNameForFieldType(FD::TYPE_FIXED64 ));
+ EXPECT_STREQ("uint32" , GetCppTypeNameForFieldType(FD::TYPE_FIXED32 ));
+ EXPECT_STREQ("bool" , GetCppTypeNameForFieldType(FD::TYPE_BOOL ));
+ EXPECT_STREQ("string" , GetCppTypeNameForFieldType(FD::TYPE_STRING ));
+ EXPECT_STREQ("message", GetCppTypeNameForFieldType(FD::TYPE_GROUP ));
+ EXPECT_STREQ("message", GetCppTypeNameForFieldType(FD::TYPE_MESSAGE ));
+ EXPECT_STREQ("string" , GetCppTypeNameForFieldType(FD::TYPE_BYTES ));
+ EXPECT_STREQ("uint32" , GetCppTypeNameForFieldType(FD::TYPE_UINT32 ));
+ EXPECT_STREQ("enum" , GetCppTypeNameForFieldType(FD::TYPE_ENUM ));
+ EXPECT_STREQ("int32" , GetCppTypeNameForFieldType(FD::TYPE_SFIXED32));
+ EXPECT_STREQ("int64" , GetCppTypeNameForFieldType(FD::TYPE_SFIXED64));
+ EXPECT_STREQ("int32" , GetCppTypeNameForFieldType(FD::TYPE_SINT32 ));
+ EXPECT_STREQ("int64" , GetCppTypeNameForFieldType(FD::TYPE_SINT64 ));
+}
+
+TEST_F(MiscTest, StaticCppTypeNames) {
+ // Test that correct CPP type names are returned.
+
+ typedef FieldDescriptor FD; // avoid ugly line wrapping
+
+ EXPECT_STREQ("int32" , FD::CppTypeName(FD::CPPTYPE_INT32 ));
+ EXPECT_STREQ("int64" , FD::CppTypeName(FD::CPPTYPE_INT64 ));
+ EXPECT_STREQ("uint32" , FD::CppTypeName(FD::CPPTYPE_UINT32 ));
+ EXPECT_STREQ("uint64" , FD::CppTypeName(FD::CPPTYPE_UINT64 ));
+ EXPECT_STREQ("double" , FD::CppTypeName(FD::CPPTYPE_DOUBLE ));
+ EXPECT_STREQ("float" , FD::CppTypeName(FD::CPPTYPE_FLOAT ));
+ EXPECT_STREQ("bool" , FD::CppTypeName(FD::CPPTYPE_BOOL ));
+ EXPECT_STREQ("enum" , FD::CppTypeName(FD::CPPTYPE_ENUM ));
+ EXPECT_STREQ("string" , FD::CppTypeName(FD::CPPTYPE_STRING ));
+ EXPECT_STREQ("message", FD::CppTypeName(FD::CPPTYPE_MESSAGE));
+}
+
+TEST_F(MiscTest, MessageType) {
+ // Test that message_type() is NULL for non-aggregate fields
+
+ typedef FieldDescriptor FD; // avoid ugly line wrapping
+
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_DOUBLE ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_FLOAT ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_INT64 ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_UINT64 ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_INT32 ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_FIXED64 ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_FIXED32 ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_BOOL ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_STRING ));
+ EXPECT_TRUE(NULL != GetMessageDescriptorForFieldType(FD::TYPE_GROUP ));
+ EXPECT_TRUE(NULL != GetMessageDescriptorForFieldType(FD::TYPE_MESSAGE ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_BYTES ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_UINT32 ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_ENUM ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_SFIXED32));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_SFIXED64));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_SINT32 ));
+ EXPECT_TRUE(NULL == GetMessageDescriptorForFieldType(FD::TYPE_SINT64 ));
+}
+
+TEST_F(MiscTest, EnumType) {
+ // Test that enum_type() is NULL for non-enum fields
+
+ typedef FieldDescriptor FD; // avoid ugly line wrapping
+
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_DOUBLE ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_FLOAT ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_INT64 ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_UINT64 ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_INT32 ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_FIXED64 ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_FIXED32 ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_BOOL ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_STRING ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_GROUP ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_MESSAGE ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_BYTES ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_UINT32 ));
+ EXPECT_TRUE(NULL != GetEnumDescriptorForFieldType(FD::TYPE_ENUM ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_SFIXED32));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_SFIXED64));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_SINT32 ));
+ EXPECT_TRUE(NULL == GetEnumDescriptorForFieldType(FD::TYPE_SINT64 ));
+}
+
+
+TEST_F(MiscTest, DefaultValues) {
+ // Test that setting default values works.
+ FileDescriptorProto file_proto;
+ file_proto.set_name("foo.proto");
+
+ EnumDescriptorProto* enum_type_proto = AddEnum(&file_proto, "DummyEnum");
+ AddEnumValue(enum_type_proto, "A", 1);
+ AddEnumValue(enum_type_proto, "B", 2);
+
+ DescriptorProto* message_proto = AddMessage(&file_proto, "TestMessage");
+
+ typedef FieldDescriptorProto FD; // avoid ugly line wrapping
+ const FD::Label label = FD::LABEL_OPTIONAL;
+
+ // Create fields of every CPP type with default values.
+ AddField(message_proto, "int32" , 1, label, FD::TYPE_INT32 )
+ ->set_default_value("-1");
+ AddField(message_proto, "int64" , 2, label, FD::TYPE_INT64 )
+ ->set_default_value("-1000000000000");
+ AddField(message_proto, "uint32", 3, label, FD::TYPE_UINT32)
+ ->set_default_value("42");
+ AddField(message_proto, "uint64", 4, label, FD::TYPE_UINT64)
+ ->set_default_value("2000000000000");
+ AddField(message_proto, "float" , 5, label, FD::TYPE_FLOAT )
+ ->set_default_value("4.5");
+ AddField(message_proto, "double", 6, label, FD::TYPE_DOUBLE)
+ ->set_default_value("10e100");
+ AddField(message_proto, "bool" , 7, label, FD::TYPE_BOOL )
+ ->set_default_value("true");
+ AddField(message_proto, "string", 8, label, FD::TYPE_STRING)
+ ->set_default_value("hello");
+ AddField(message_proto, "data" , 9, label, FD::TYPE_BYTES )
+ ->set_default_value("\\001\\002\\003");
+
+ FieldDescriptorProto* enum_field =
+ AddField(message_proto, "enum", 10, label, FD::TYPE_ENUM);
+ enum_field->set_type_name("DummyEnum");
+ enum_field->set_default_value("B");
+
+ // Strings are allowed to have empty defaults. (At one point, due to
+ // a bug, empty defaults for strings were rejected. Oops.)
+ AddField(message_proto, "empty_string", 11, label, FD::TYPE_STRING)
+ ->set_default_value("");
+
+ // Add a second set of fields with implicit defalut values.
+ AddField(message_proto, "implicit_int32" , 21, label, FD::TYPE_INT32 );
+ AddField(message_proto, "implicit_int64" , 22, label, FD::TYPE_INT64 );
+ AddField(message_proto, "implicit_uint32", 23, label, FD::TYPE_UINT32);
+ AddField(message_proto, "implicit_uint64", 24, label, FD::TYPE_UINT64);
+ AddField(message_proto, "implicit_float" , 25, label, FD::TYPE_FLOAT );
+ AddField(message_proto, "implicit_double", 26, label, FD::TYPE_DOUBLE);
+ AddField(message_proto, "implicit_bool" , 27, label, FD::TYPE_BOOL );
+ AddField(message_proto, "implicit_string", 28, label, FD::TYPE_STRING);
+ AddField(message_proto, "implicit_data" , 29, label, FD::TYPE_BYTES );
+ AddField(message_proto, "implicit_enum" , 30, label, FD::TYPE_ENUM)
+ ->set_type_name("DummyEnum");
+
+ // Build it.
+ DescriptorPool pool;
+ const FileDescriptor* file = pool.BuildFile(file_proto);
+ ASSERT_TRUE(file != NULL);
+
+ ASSERT_EQ(1, file->enum_type_count());
+ const EnumDescriptor* enum_type = file->enum_type(0);
+ ASSERT_EQ(2, enum_type->value_count());
+ const EnumValueDescriptor* enum_value_a = enum_type->value(0);
+ const EnumValueDescriptor* enum_value_b = enum_type->value(1);
+
+ ASSERT_EQ(1, file->message_type_count());
+ const Descriptor* message = file->message_type(0);
+
+ ASSERT_EQ(21, message->field_count());
+
+ // Check the default values.
+ ASSERT_TRUE(message->field(0)->has_default_value());
+ ASSERT_TRUE(message->field(1)->has_default_value());
+ ASSERT_TRUE(message->field(2)->has_default_value());
+ ASSERT_TRUE(message->field(3)->has_default_value());
+ ASSERT_TRUE(message->field(4)->has_default_value());
+ ASSERT_TRUE(message->field(5)->has_default_value());
+ ASSERT_TRUE(message->field(6)->has_default_value());
+ ASSERT_TRUE(message->field(7)->has_default_value());
+ ASSERT_TRUE(message->field(8)->has_default_value());
+ ASSERT_TRUE(message->field(9)->has_default_value());
+ ASSERT_TRUE(message->field(10)->has_default_value());
+
+ EXPECT_EQ(-1 , message->field(0)->default_value_int32 ());
+ EXPECT_EQ(-GOOGLE_ULONGLONG(1000000000000),
+ message->field(1)->default_value_int64 ());
+ EXPECT_EQ(42 , message->field(2)->default_value_uint32());
+ EXPECT_EQ(GOOGLE_ULONGLONG(2000000000000),
+ message->field(3)->default_value_uint64());
+ EXPECT_EQ(4.5 , message->field(4)->default_value_float ());
+ EXPECT_EQ(10e100 , message->field(5)->default_value_double());
+ EXPECT_TRUE( message->field(6)->default_value_bool ());
+ EXPECT_EQ("hello" , message->field(7)->default_value_string());
+ EXPECT_EQ("\001\002\003" , message->field(8)->default_value_string());
+ EXPECT_EQ(enum_value_b , message->field(9)->default_value_enum ());
+ EXPECT_EQ("" , message->field(10)->default_value_string());
+
+ ASSERT_FALSE(message->field(11)->has_default_value());
+ ASSERT_FALSE(message->field(12)->has_default_value());
+ ASSERT_FALSE(message->field(13)->has_default_value());
+ ASSERT_FALSE(message->field(14)->has_default_value());
+ ASSERT_FALSE(message->field(15)->has_default_value());
+ ASSERT_FALSE(message->field(16)->has_default_value());
+ ASSERT_FALSE(message->field(17)->has_default_value());
+ ASSERT_FALSE(message->field(18)->has_default_value());
+ ASSERT_FALSE(message->field(19)->has_default_value());
+ ASSERT_FALSE(message->field(20)->has_default_value());
+
+ EXPECT_EQ(0 , message->field(11)->default_value_int32 ());
+ EXPECT_EQ(0 , message->field(12)->default_value_int64 ());
+ EXPECT_EQ(0 , message->field(13)->default_value_uint32());
+ EXPECT_EQ(0 , message->field(14)->default_value_uint64());
+ EXPECT_EQ(0.0f , message->field(15)->default_value_float ());
+ EXPECT_EQ(0.0 , message->field(16)->default_value_double());
+ EXPECT_FALSE( message->field(17)->default_value_bool ());
+ EXPECT_EQ("" , message->field(18)->default_value_string());
+ EXPECT_EQ("" , message->field(19)->default_value_string());
+ EXPECT_EQ(enum_value_a, message->field(20)->default_value_enum());
+}
+
+TEST_F(MiscTest, FieldOptions) {
+ // Try setting field options.
+
+ FileDescriptorProto file_proto;
+ file_proto.set_name("foo.proto");
+
+ DescriptorProto* message_proto = AddMessage(&file_proto, "TestMessage");
+ AddField(message_proto, "foo", 1,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ FieldDescriptorProto* bar_proto =
+ AddField(message_proto, "bar", 2,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+
+ FieldOptions* options = bar_proto->mutable_options();
+ options->set_ctype(FieldOptions::CORD);
+
+ // Build the descriptors and get the pointers.
+ DescriptorPool pool;
+ const FileDescriptor* file = pool.BuildFile(file_proto);
+ ASSERT_TRUE(file != NULL);
+
+ ASSERT_EQ(1, file->message_type_count());
+ const Descriptor* message = file->message_type(0);
+
+ ASSERT_EQ(2, message->field_count());
+ const FieldDescriptor* foo = message->field(0);
+ const FieldDescriptor* bar = message->field(1);
+
+ // "foo" had no options set, so it should return the default options.
+ EXPECT_EQ(&FieldOptions::default_instance(), &foo->options());
+
+ // "bar" had options set.
+ EXPECT_NE(&FieldOptions::default_instance(), options);
+ EXPECT_TRUE(bar->options().has_ctype());
+ EXPECT_EQ(FieldOptions::CORD, bar->options().ctype());
+}
+
+// ===================================================================
+enum DescriptorPoolMode {
+ NO_DATABASE,
+ FALLBACK_DATABASE
+};
+
+class AllowUnknownDependenciesTest
+ : public testing::TestWithParam<DescriptorPoolMode> {
+ protected:
+ DescriptorPoolMode mode() {
+ return GetParam();
+ }
+
+ virtual void SetUp() {
+ FileDescriptorProto foo_proto, bar_proto;
+
+ switch (mode()) {
+ case NO_DATABASE:
+ pool_.reset(new DescriptorPool);
+ break;
+ case FALLBACK_DATABASE:
+ pool_.reset(new DescriptorPool(&db_));
+ break;
+ }
+
+ pool_->AllowUnknownDependencies();
+
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: 'foo.proto'"
+ "dependency: 'bar.proto'"
+ "dependency: 'baz.proto'"
+ "message_type {"
+ " name: 'Foo'"
+ " field { name:'bar' number:1 label:LABEL_OPTIONAL type_name:'Bar' }"
+ " field { name:'baz' number:2 label:LABEL_OPTIONAL type_name:'Baz' }"
+ " field { name:'qux' number:3 label:LABEL_OPTIONAL"
+ " type_name: '.corge.Qux'"
+ " type: TYPE_ENUM"
+ " options {"
+ " uninterpreted_option {"
+ " name {"
+ " name_part: 'grault'"
+ " is_extension: true"
+ " }"
+ " positive_int_value: 1234"
+ " }"
+ " }"
+ " }"
+ "}",
+ &foo_proto));
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: 'bar.proto'"
+ "message_type { name: 'Bar' }",
+ &bar_proto));
+
+ // Collect pointers to stuff.
+ bar_file_ = BuildFile(bar_proto);
+ ASSERT_TRUE(bar_file_ != NULL);
+
+ ASSERT_EQ(1, bar_file_->message_type_count());
+ bar_type_ = bar_file_->message_type(0);
+
+ foo_file_ = BuildFile(foo_proto);
+ ASSERT_TRUE(foo_file_ != NULL);
+
+ ASSERT_EQ(1, foo_file_->message_type_count());
+ foo_type_ = foo_file_->message_type(0);
+
+ ASSERT_EQ(3, foo_type_->field_count());
+ bar_field_ = foo_type_->field(0);
+ baz_field_ = foo_type_->field(1);
+ qux_field_ = foo_type_->field(2);
+ }
+
+ const FileDescriptor* BuildFile(const FileDescriptorProto& proto) {
+ switch (mode()) {
+ case NO_DATABASE:
+ return pool_->BuildFile(proto);
+ break;
+ case FALLBACK_DATABASE: {
+ EXPECT_TRUE(db_.Add(proto));
+ return pool_->FindFileByName(proto.name());
+ }
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return NULL;
+ }
+
+ const FileDescriptor* bar_file_;
+ const Descriptor* bar_type_;
+ const FileDescriptor* foo_file_;
+ const Descriptor* foo_type_;
+ const FieldDescriptor* bar_field_;
+ const FieldDescriptor* baz_field_;
+ const FieldDescriptor* qux_field_;
+
+ SimpleDescriptorDatabase db_; // used if in FALLBACK_DATABASE mode.
+ google::protobuf::scoped_ptr<DescriptorPool> pool_;
+};
+
+TEST_P(AllowUnknownDependenciesTest, PlaceholderFile) {
+ ASSERT_EQ(2, foo_file_->dependency_count());
+ EXPECT_EQ(bar_file_, foo_file_->dependency(0));
+ EXPECT_FALSE(bar_file_->is_placeholder());
+
+ const FileDescriptor* baz_file = foo_file_->dependency(1);
+ EXPECT_EQ("baz.proto", baz_file->name());
+ EXPECT_EQ(0, baz_file->message_type_count());
+ EXPECT_TRUE(baz_file->is_placeholder());
+
+ // Placeholder files should not be findable.
+ EXPECT_EQ(bar_file_, pool_->FindFileByName(bar_file_->name()));
+ EXPECT_TRUE(pool_->FindFileByName(baz_file->name()) == NULL);
+
+ // Copy*To should not crash for placeholder files.
+ FileDescriptorProto baz_file_proto;
+ baz_file->CopyTo(&baz_file_proto);
+ baz_file->CopySourceCodeInfoTo(&baz_file_proto);
+ EXPECT_FALSE(baz_file_proto.has_source_code_info());
+}
+
+TEST_P(AllowUnknownDependenciesTest, PlaceholderTypes) {
+ ASSERT_EQ(FieldDescriptor::TYPE_MESSAGE, bar_field_->type());
+ EXPECT_EQ(bar_type_, bar_field_->message_type());
+ EXPECT_FALSE(bar_type_->is_placeholder());
+
+ ASSERT_EQ(FieldDescriptor::TYPE_MESSAGE, baz_field_->type());
+ const Descriptor* baz_type = baz_field_->message_type();
+ EXPECT_EQ("Baz", baz_type->name());
+ EXPECT_EQ("Baz", baz_type->full_name());
+ EXPECT_EQ(0, baz_type->extension_range_count());
+ EXPECT_TRUE(baz_type->is_placeholder());
+
+ ASSERT_EQ(FieldDescriptor::TYPE_ENUM, qux_field_->type());
+ const EnumDescriptor* qux_type = qux_field_->enum_type();
+ EXPECT_EQ("Qux", qux_type->name());
+ EXPECT_EQ("corge.Qux", qux_type->full_name());
+ EXPECT_TRUE(qux_type->is_placeholder());
+
+ // Placeholder types should not be findable.
+ EXPECT_EQ(bar_type_, pool_->FindMessageTypeByName(bar_type_->full_name()));
+ EXPECT_TRUE(pool_->FindMessageTypeByName(baz_type->full_name()) == NULL);
+ EXPECT_TRUE(pool_->FindEnumTypeByName(qux_type->full_name()) == NULL);
+}
+
+TEST_P(AllowUnknownDependenciesTest, CopyTo) {
+ // FieldDescriptor::CopyTo() should write non-fully-qualified type names
+ // for placeholder types which were not originally fully-qualified.
+ FieldDescriptorProto proto;
+
+ // Bar is not a placeholder, so it is fully-qualified.
+ bar_field_->CopyTo(&proto);
+ EXPECT_EQ(".Bar", proto.type_name());
+ EXPECT_EQ(FieldDescriptorProto::TYPE_MESSAGE, proto.type());
+
+ // Baz is an unqualified placeholder.
+ proto.Clear();
+ baz_field_->CopyTo(&proto);
+ EXPECT_EQ("Baz", proto.type_name());
+ EXPECT_FALSE(proto.has_type());
+
+ // Qux is a fully-qualified placeholder.
+ proto.Clear();
+ qux_field_->CopyTo(&proto);
+ EXPECT_EQ(".corge.Qux", proto.type_name());
+ EXPECT_EQ(FieldDescriptorProto::TYPE_ENUM, proto.type());
+}
+
+TEST_P(AllowUnknownDependenciesTest, CustomOptions) {
+ // Qux should still have the uninterpreted option attached.
+ ASSERT_EQ(1, qux_field_->options().uninterpreted_option_size());
+ const UninterpretedOption& option =
+ qux_field_->options().uninterpreted_option(0);
+ ASSERT_EQ(1, option.name_size());
+ EXPECT_EQ("grault", option.name(0).name_part());
+}
+
+TEST_P(AllowUnknownDependenciesTest, UnknownExtendee) {
+ // Test that we can extend an unknown type. This is slightly tricky because
+ // it means that the placeholder type must have an extension range.
+
+ FileDescriptorProto extension_proto;
+
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: 'extension.proto'"
+ "extension { extendee: 'UnknownType' name:'some_extension' number:123"
+ " label:LABEL_OPTIONAL type:TYPE_INT32 }",
+ &extension_proto));
+ const FileDescriptor* file = BuildFile(extension_proto);
+
+ ASSERT_TRUE(file != NULL);
+
+ ASSERT_EQ(1, file->extension_count());
+ const Descriptor* extendee = file->extension(0)->containing_type();
+ EXPECT_EQ("UnknownType", extendee->name());
+ EXPECT_TRUE(extendee->is_placeholder());
+ ASSERT_EQ(1, extendee->extension_range_count());
+ EXPECT_EQ(1, extendee->extension_range(0)->start);
+ EXPECT_EQ(FieldDescriptor::kMaxNumber + 1, extendee->extension_range(0)->end);
+}
+
+TEST_P(AllowUnknownDependenciesTest, CustomOption) {
+ // Test that we can use a custom option without having parsed
+ // descriptor.proto.
+
+ FileDescriptorProto option_proto;
+
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"unknown_custom_options.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { "
+ " extendee: \"google.protobuf.FileOptions\" "
+ " name: \"some_option\" "
+ " number: 123456 "
+ " label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 "
+ "} "
+ "options { "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"some_option\" "
+ " is_extension: true "
+ " } "
+ " positive_int_value: 1234 "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"unknown_option\" "
+ " is_extension: true "
+ " } "
+ " positive_int_value: 1234 "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"optimize_for\" "
+ " is_extension: false "
+ " } "
+ " identifier_value: \"SPEED\" "
+ " } "
+ "}",
+ &option_proto));
+
+ const FileDescriptor* file = BuildFile(option_proto);
+ ASSERT_TRUE(file != NULL);
+
+ // Verify that no extension options were set, but they were left as
+ // uninterpreted_options.
+ vector<const FieldDescriptor*> fields;
+ file->options().GetReflection()->ListFields(file->options(), &fields);
+ ASSERT_EQ(2, fields.size());
+ EXPECT_TRUE(file->options().has_optimize_for());
+ EXPECT_EQ(2, file->options().uninterpreted_option_size());
+}
+
+TEST_P(AllowUnknownDependenciesTest,
+ UndeclaredDependencyTriggersBuildOfDependency) {
+ // Crazy case: suppose foo.proto refers to a symbol without declaring the
+ // dependency that finds it. In the event that the pool is backed by a
+ // DescriptorDatabase, the pool will attempt to find the symbol in the
+ // database. If successful, it will build the undeclared dependency to verify
+ // that the file does indeed contain the symbol. If that file fails to build,
+ // then its descriptors must be rolled back. However, we still want foo.proto
+ // to build successfully, since we are allowing unknown dependencies.
+
+ FileDescriptorProto undeclared_dep_proto;
+ // We make this file fail to build by giving it two fields with tag 1.
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"invalid_file_as_undeclared_dep.proto\" "
+ "package: \"undeclared\" "
+ "message_type: { "
+ " name: \"Quux\" "
+ " field { "
+ " name:'qux' number:1 label:LABEL_OPTIONAL type: TYPE_INT32 "
+ " }"
+ " field { "
+ " name:'quux' number:1 label:LABEL_OPTIONAL type: TYPE_INT64 "
+ " }"
+ "}",
+ &undeclared_dep_proto));
+ // We can't use the BuildFile() helper because we don't actually want to build
+ // it into the descriptor pool in the fallback database case: it just needs to
+ // be sitting in the database so that it gets built during the building of
+ // test.proto below.
+ switch (mode()) {
+ case NO_DATABASE: {
+ ASSERT_TRUE(pool_->BuildFile(undeclared_dep_proto) == NULL);
+ break;
+ }
+ case FALLBACK_DATABASE: {
+ ASSERT_TRUE(db_.Add(undeclared_dep_proto));
+ }
+ }
+
+ FileDescriptorProto test_proto;
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"test.proto\" "
+ "message_type: { "
+ " name: \"Corge\" "
+ " field { "
+ " name:'quux' number:1 label: LABEL_OPTIONAL "
+ " type_name:'undeclared.Quux' type: TYPE_MESSAGE "
+ " }"
+ "}",
+ &test_proto));
+
+ const FileDescriptor* file = BuildFile(test_proto);
+ ASSERT_TRUE(file != NULL);
+ GOOGLE_LOG(INFO) << file->DebugString();
+
+ EXPECT_EQ(0, file->dependency_count());
+ ASSERT_EQ(1, file->message_type_count());
+ const Descriptor* corge_desc = file->message_type(0);
+ ASSERT_EQ("Corge", corge_desc->name());
+ ASSERT_EQ(1, corge_desc->field_count());
+ EXPECT_FALSE(corge_desc->is_placeholder());
+
+ const FieldDescriptor* quux_field = corge_desc->field(0);
+ ASSERT_EQ(FieldDescriptor::TYPE_MESSAGE, quux_field->type());
+ ASSERT_EQ("Quux", quux_field->message_type()->name());
+ ASSERT_EQ("undeclared.Quux", quux_field->message_type()->full_name());
+ EXPECT_TRUE(quux_field->message_type()->is_placeholder());
+ // The place holder type should not be findable.
+ ASSERT_TRUE(pool_->FindMessageTypeByName("undeclared.Quux") == NULL);
+}
+
+INSTANTIATE_TEST_CASE_P(DatabaseSource,
+ AllowUnknownDependenciesTest,
+ testing::Values(NO_DATABASE, FALLBACK_DATABASE));
+
+// ===================================================================
+
+TEST(CustomOptions, OptionLocations) {
+ const Descriptor* message =
+ protobuf_unittest::TestMessageWithCustomOptions::descriptor();
+ const FileDescriptor* file = message->file();
+ const FieldDescriptor* field = message->FindFieldByName("field1");
+ const OneofDescriptor* oneof = message->FindOneofByName("AnOneof");
+ const EnumDescriptor* enm = message->FindEnumTypeByName("AnEnum");
+ // TODO(benjy): Support EnumValue options, once the compiler does.
+ const ServiceDescriptor* service =
+ file->FindServiceByName("TestServiceWithCustomOptions");
+ const MethodDescriptor* method = service->FindMethodByName("Foo");
+
+ EXPECT_EQ(GOOGLE_LONGLONG(9876543210),
+ file->options().GetExtension(protobuf_unittest::file_opt1));
+ EXPECT_EQ(-56,
+ message->options().GetExtension(protobuf_unittest::message_opt1));
+ EXPECT_EQ(GOOGLE_LONGLONG(8765432109),
+ field->options().GetExtension(protobuf_unittest::field_opt1));
+ EXPECT_EQ(42, // Check that we get the default for an option we don't set.
+ field->options().GetExtension(protobuf_unittest::field_opt2));
+ EXPECT_EQ(-99,
+ oneof->options().GetExtension(protobuf_unittest::oneof_opt1));
+ EXPECT_EQ(-789,
+ enm->options().GetExtension(protobuf_unittest::enum_opt1));
+ EXPECT_EQ(123,
+ enm->value(1)->options().GetExtension(
+ protobuf_unittest::enum_value_opt1));
+ EXPECT_EQ(GOOGLE_LONGLONG(-9876543210),
+ service->options().GetExtension(protobuf_unittest::service_opt1));
+ EXPECT_EQ(protobuf_unittest::METHODOPT1_VAL2,
+ method->options().GetExtension(protobuf_unittest::method_opt1));
+
+ // See that the regular options went through unscathed.
+ EXPECT_TRUE(message->options().has_message_set_wire_format());
+ EXPECT_EQ(FieldOptions::CORD, field->options().ctype());
+}
+
+TEST(CustomOptions, OptionTypes) {
+ const MessageOptions* options = NULL;
+
+ options =
+ &protobuf_unittest::CustomOptionMinIntegerValues::descriptor()->options();
+ EXPECT_EQ(false , options->GetExtension(protobuf_unittest::bool_opt));
+ EXPECT_EQ(kint32min, options->GetExtension(protobuf_unittest::int32_opt));
+ EXPECT_EQ(kint64min, options->GetExtension(protobuf_unittest::int64_opt));
+ EXPECT_EQ(0 , options->GetExtension(protobuf_unittest::uint32_opt));
+ EXPECT_EQ(0 , options->GetExtension(protobuf_unittest::uint64_opt));
+ EXPECT_EQ(kint32min, options->GetExtension(protobuf_unittest::sint32_opt));
+ EXPECT_EQ(kint64min, options->GetExtension(protobuf_unittest::sint64_opt));
+ EXPECT_EQ(0 , options->GetExtension(protobuf_unittest::fixed32_opt));
+ EXPECT_EQ(0 , options->GetExtension(protobuf_unittest::fixed64_opt));
+ EXPECT_EQ(kint32min, options->GetExtension(protobuf_unittest::sfixed32_opt));
+ EXPECT_EQ(kint64min, options->GetExtension(protobuf_unittest::sfixed64_opt));
+
+ options =
+ &protobuf_unittest::CustomOptionMaxIntegerValues::descriptor()->options();
+ EXPECT_EQ(true , options->GetExtension(protobuf_unittest::bool_opt));
+ EXPECT_EQ(kint32max , options->GetExtension(protobuf_unittest::int32_opt));
+ EXPECT_EQ(kint64max , options->GetExtension(protobuf_unittest::int64_opt));
+ EXPECT_EQ(kuint32max, options->GetExtension(protobuf_unittest::uint32_opt));
+ EXPECT_EQ(kuint64max, options->GetExtension(protobuf_unittest::uint64_opt));
+ EXPECT_EQ(kint32max , options->GetExtension(protobuf_unittest::sint32_opt));
+ EXPECT_EQ(kint64max , options->GetExtension(protobuf_unittest::sint64_opt));
+ EXPECT_EQ(kuint32max, options->GetExtension(protobuf_unittest::fixed32_opt));
+ EXPECT_EQ(kuint64max, options->GetExtension(protobuf_unittest::fixed64_opt));
+ EXPECT_EQ(kint32max , options->GetExtension(protobuf_unittest::sfixed32_opt));
+ EXPECT_EQ(kint64max , options->GetExtension(protobuf_unittest::sfixed64_opt));
+
+ options =
+ &protobuf_unittest::CustomOptionOtherValues::descriptor()->options();
+ EXPECT_EQ(-100, options->GetExtension(protobuf_unittest::int32_opt));
+ EXPECT_FLOAT_EQ(12.3456789,
+ options->GetExtension(protobuf_unittest::float_opt));
+ EXPECT_DOUBLE_EQ(1.234567890123456789,
+ options->GetExtension(protobuf_unittest::double_opt));
+ EXPECT_EQ("Hello, \"World\"",
+ options->GetExtension(protobuf_unittest::string_opt));
+
+ EXPECT_EQ(string("Hello\0World", 11),
+ options->GetExtension(protobuf_unittest::bytes_opt));
+
+ EXPECT_EQ(protobuf_unittest::DummyMessageContainingEnum::TEST_OPTION_ENUM_TYPE2,
+ options->GetExtension(protobuf_unittest::enum_opt));
+
+ options =
+ &protobuf_unittest::SettingRealsFromPositiveInts::descriptor()->options();
+ EXPECT_FLOAT_EQ(12, options->GetExtension(protobuf_unittest::float_opt));
+ EXPECT_DOUBLE_EQ(154, options->GetExtension(protobuf_unittest::double_opt));
+
+ options =
+ &protobuf_unittest::SettingRealsFromNegativeInts::descriptor()->options();
+ EXPECT_FLOAT_EQ(-12, options->GetExtension(protobuf_unittest::float_opt));
+ EXPECT_DOUBLE_EQ(-154, options->GetExtension(protobuf_unittest::double_opt));
+}
+
+TEST(CustomOptions, ComplexExtensionOptions) {
+ const MessageOptions* options =
+ &protobuf_unittest::VariousComplexOptions::descriptor()->options();
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt1).foo(), 42);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt1).
+ GetExtension(protobuf_unittest::quux), 324);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt1).
+ GetExtension(protobuf_unittest::corge).qux(), 876);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).baz(), 987);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).
+ GetExtension(protobuf_unittest::grault), 654);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).bar().foo(),
+ 743);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).bar().
+ GetExtension(protobuf_unittest::quux), 1999);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).bar().
+ GetExtension(protobuf_unittest::corge).qux(), 2008);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).
+ GetExtension(protobuf_unittest::garply).foo(), 741);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).
+ GetExtension(protobuf_unittest::garply).
+ GetExtension(protobuf_unittest::quux), 1998);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).
+ GetExtension(protobuf_unittest::garply).
+ GetExtension(protobuf_unittest::corge).qux(), 2121);
+ EXPECT_EQ(options->GetExtension(
+ protobuf_unittest::ComplexOptionType2::ComplexOptionType4::complex_opt4).
+ waldo(), 1971);
+ EXPECT_EQ(options->GetExtension(protobuf_unittest::complex_opt2).
+ fred().waldo(), 321);
+ EXPECT_EQ(9, options->GetExtension(protobuf_unittest::complex_opt3).qux());
+ EXPECT_EQ(22, options->GetExtension(protobuf_unittest::complex_opt3).
+ complexoptiontype5().plugh());
+ EXPECT_EQ(24, options->GetExtension(protobuf_unittest::complexopt6).xyzzy());
+}
+
+TEST(CustomOptions, OptionsFromOtherFile) {
+ // Test that to use a custom option, we only need to import the file
+ // defining the option; we do not also have to import descriptor.proto.
+ DescriptorPool pool;
+
+ FileDescriptorProto file_proto;
+ FileDescriptorProto::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ protobuf_unittest::TestMessageWithCustomOptions::descriptor()
+ ->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"custom_options_import.proto\" "
+ "package: \"protobuf_unittest\" "
+ "dependency: \"google/protobuf/unittest_custom_options.proto\" "
+ "options { "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"file_opt1\" "
+ " is_extension: true "
+ " } "
+ " positive_int_value: 1234 "
+ " } "
+ // Test a non-extension option too. (At one point this failed due to a
+ // bug.)
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"java_package\" "
+ " is_extension: false "
+ " } "
+ " string_value: \"foo\" "
+ " } "
+ // Test that enum-typed options still work too. (At one point this also
+ // failed due to a bug.)
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"optimize_for\" "
+ " is_extension: false "
+ " } "
+ " identifier_value: \"SPEED\" "
+ " } "
+ "}"
+ ,
+ &file_proto));
+
+ const FileDescriptor* file = pool.BuildFile(file_proto);
+ ASSERT_TRUE(file != NULL);
+ EXPECT_EQ(1234, file->options().GetExtension(protobuf_unittest::file_opt1));
+ EXPECT_TRUE(file->options().has_java_package());
+ EXPECT_EQ("foo", file->options().java_package());
+ EXPECT_TRUE(file->options().has_optimize_for());
+ EXPECT_EQ(FileOptions::SPEED, file->options().optimize_for());
+}
+
+TEST(CustomOptions, MessageOptionThreeFieldsSet) {
+ // This tests a bug which previously existed in custom options parsing. The
+ // bug occurred when you defined a custom option with message type and then
+ // set three fields of that option on a single definition (see the example
+ // below). The bug is a bit hard to explain, so check the change history if
+ // you want to know more.
+ DescriptorPool pool;
+
+ FileDescriptorProto file_proto;
+ FileDescriptorProto::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ protobuf_unittest::TestMessageWithCustomOptions::descriptor()
+ ->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ // The following represents the definition:
+ //
+ // import "google/protobuf/unittest_custom_options.proto"
+ // package protobuf_unittest;
+ // message Foo {
+ // option (complex_opt1).foo = 1234;
+ // option (complex_opt1).foo2 = 1234;
+ // option (complex_opt1).foo3 = 1234;
+ // }
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"custom_options_import.proto\" "
+ "package: \"protobuf_unittest\" "
+ "dependency: \"google/protobuf/unittest_custom_options.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ " options { "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt1\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"foo\" "
+ " is_extension: false "
+ " } "
+ " positive_int_value: 1234 "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt1\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"foo2\" "
+ " is_extension: false "
+ " } "
+ " positive_int_value: 1234 "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt1\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"foo3\" "
+ " is_extension: false "
+ " } "
+ " positive_int_value: 1234 "
+ " } "
+ " } "
+ "}",
+ &file_proto));
+
+ const FileDescriptor* file = pool.BuildFile(file_proto);
+ ASSERT_TRUE(file != NULL);
+ ASSERT_EQ(1, file->message_type_count());
+
+ const MessageOptions& options = file->message_type(0)->options();
+ EXPECT_EQ(1234, options.GetExtension(protobuf_unittest::complex_opt1).foo());
+}
+
+TEST(CustomOptions, MessageOptionRepeatedLeafFieldSet) {
+ // This test verifies that repeated fields in custom options can be
+ // given multiple values by repeating the option with a different value.
+ // This test checks repeated leaf values. Each repeated custom value
+ // appears in a different uninterpreted_option, which will be concatenated
+ // when they are merged into the final option value.
+ DescriptorPool pool;
+
+ FileDescriptorProto file_proto;
+ FileDescriptorProto::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ protobuf_unittest::TestMessageWithCustomOptions::descriptor()
+ ->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ // The following represents the definition:
+ //
+ // import "google/protobuf/unittest_custom_options.proto"
+ // package protobuf_unittest;
+ // message Foo {
+ // option (complex_opt1).foo4 = 12;
+ // option (complex_opt1).foo4 = 34;
+ // option (complex_opt1).foo4 = 56;
+ // }
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"custom_options_import.proto\" "
+ "package: \"protobuf_unittest\" "
+ "dependency: \"google/protobuf/unittest_custom_options.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ " options { "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt1\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"foo4\" "
+ " is_extension: false "
+ " } "
+ " positive_int_value: 12 "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt1\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"foo4\" "
+ " is_extension: false "
+ " } "
+ " positive_int_value: 34 "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt1\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"foo4\" "
+ " is_extension: false "
+ " } "
+ " positive_int_value: 56 "
+ " } "
+ " } "
+ "}",
+ &file_proto));
+
+ const FileDescriptor* file = pool.BuildFile(file_proto);
+ ASSERT_TRUE(file != NULL);
+ ASSERT_EQ(1, file->message_type_count());
+
+ const MessageOptions& options = file->message_type(0)->options();
+ EXPECT_EQ(3, options.GetExtension(protobuf_unittest::complex_opt1).foo4_size());
+ EXPECT_EQ(12, options.GetExtension(protobuf_unittest::complex_opt1).foo4(0));
+ EXPECT_EQ(34, options.GetExtension(protobuf_unittest::complex_opt1).foo4(1));
+ EXPECT_EQ(56, options.GetExtension(protobuf_unittest::complex_opt1).foo4(2));
+}
+
+TEST(CustomOptions, MessageOptionRepeatedMsgFieldSet) {
+ // This test verifies that repeated fields in custom options can be
+ // given multiple values by repeating the option with a different value.
+ // This test checks repeated message values. Each repeated custom value
+ // appears in a different uninterpreted_option, which will be concatenated
+ // when they are merged into the final option value.
+ DescriptorPool pool;
+
+ FileDescriptorProto file_proto;
+ FileDescriptorProto::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ protobuf_unittest::TestMessageWithCustomOptions::descriptor()
+ ->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ // The following represents the definition:
+ //
+ // import "google/protobuf/unittest_custom_options.proto"
+ // package protobuf_unittest;
+ // message Foo {
+ // option (complex_opt2).barney = {waldo: 1};
+ // option (complex_opt2).barney = {waldo: 10};
+ // option (complex_opt2).barney = {waldo: 100};
+ // }
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"custom_options_import.proto\" "
+ "package: \"protobuf_unittest\" "
+ "dependency: \"google/protobuf/unittest_custom_options.proto\" "
+ "message_type { "
+ " name: \"Foo\" "
+ " options { "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt2\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"barney\" "
+ " is_extension: false "
+ " } "
+ " aggregate_value: \"waldo: 1\" "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt2\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"barney\" "
+ " is_extension: false "
+ " } "
+ " aggregate_value: \"waldo: 10\" "
+ " } "
+ " uninterpreted_option { "
+ " name { "
+ " name_part: \"complex_opt2\" "
+ " is_extension: true "
+ " } "
+ " name { "
+ " name_part: \"barney\" "
+ " is_extension: false "
+ " } "
+ " aggregate_value: \"waldo: 100\" "
+ " } "
+ " } "
+ "}",
+ &file_proto));
+
+ const FileDescriptor* file = pool.BuildFile(file_proto);
+ ASSERT_TRUE(file != NULL);
+ ASSERT_EQ(1, file->message_type_count());
+
+ const MessageOptions& options = file->message_type(0)->options();
+ EXPECT_EQ(3, options.GetExtension(
+ protobuf_unittest::complex_opt2).barney_size());
+ EXPECT_EQ(1,options.GetExtension(
+ protobuf_unittest::complex_opt2).barney(0).waldo());
+ EXPECT_EQ(10, options.GetExtension(
+ protobuf_unittest::complex_opt2).barney(1).waldo());
+ EXPECT_EQ(100, options.GetExtension(
+ protobuf_unittest::complex_opt2).barney(2).waldo());
+}
+
+// Check that aggregate options were parsed and saved correctly in
+// the appropriate descriptors.
+TEST(CustomOptions, AggregateOptions) {
+ const Descriptor* msg = protobuf_unittest::AggregateMessage::descriptor();
+ const FileDescriptor* file = msg->file();
+ const FieldDescriptor* field = msg->FindFieldByName("fieldname");
+ const EnumDescriptor* enumd = file->FindEnumTypeByName("AggregateEnum");
+ const EnumValueDescriptor* enumv = enumd->FindValueByName("VALUE");
+ const ServiceDescriptor* service = file->FindServiceByName(
+ "AggregateService");
+ const MethodDescriptor* method = service->FindMethodByName("Method");
+
+ // Tests for the different types of data embedded in fileopt
+ const protobuf_unittest::Aggregate& file_options =
+ file->options().GetExtension(protobuf_unittest::fileopt);
+ EXPECT_EQ(100, file_options.i());
+ EXPECT_EQ("FileAnnotation", file_options.s());
+ EXPECT_EQ("NestedFileAnnotation", file_options.sub().s());
+ EXPECT_EQ("FileExtensionAnnotation",
+ file_options.file().GetExtension(protobuf_unittest::fileopt).s());
+ EXPECT_EQ("EmbeddedMessageSetElement",
+ file_options.mset().GetExtension(
+ protobuf_unittest::AggregateMessageSetElement
+ ::message_set_extension).s());
+
+ // Simple tests for all the other types of annotations
+ EXPECT_EQ("MessageAnnotation",
+ msg->options().GetExtension(protobuf_unittest::msgopt).s());
+ EXPECT_EQ("FieldAnnotation",
+ field->options().GetExtension(protobuf_unittest::fieldopt).s());
+ EXPECT_EQ("EnumAnnotation",
+ enumd->options().GetExtension(protobuf_unittest::enumopt).s());
+ EXPECT_EQ("EnumValueAnnotation",
+ enumv->options().GetExtension(protobuf_unittest::enumvalopt).s());
+ EXPECT_EQ("ServiceAnnotation",
+ service->options().GetExtension(protobuf_unittest::serviceopt).s());
+ EXPECT_EQ("MethodAnnotation",
+ method->options().GetExtension(protobuf_unittest::methodopt).s());
+}
+
+TEST(CustomOptions, UnusedImportWarning) {
+ DescriptorPool pool;
+
+ FileDescriptorProto file_proto;
+ FileDescriptorProto::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ protobuf_unittest::TestMessageWithCustomOptions::descriptor()
+ ->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ pool.AddUnusedImportTrackFile("custom_options_import.proto");
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"custom_options_import.proto\" "
+ "package: \"protobuf_unittest\" "
+ "dependency: \"google/protobuf/unittest_custom_options.proto\" ",
+ &file_proto));
+
+ MockErrorCollector error_collector;
+ EXPECT_TRUE(pool.BuildFileCollectingErrors(file_proto, &error_collector));
+ EXPECT_EQ("", error_collector.warning_text_);
+}
+
+// Verifies that proto files can correctly be parsed, even if the
+// custom options defined in the file are incompatible with those
+// compiled in the binary. See http://b/19276250.
+TEST(CustomOptions, OptionsWithRequiredEnums) {
+ DescriptorPool pool;
+
+ FileDescriptorProto file_proto;
+ MessageOptions::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ // Create a new file descriptor proto containing a subset of the
+ // messages defined in google/protobuf/unittest_custom_options.proto.
+ file_proto.Clear();
+ file_proto.set_name("unittest_custom_options.proto");
+ file_proto.set_package("protobuf_unittest");
+ file_proto.add_dependency("google/protobuf/descriptor.proto");
+
+ // Add the "required_enum_opt" extension.
+ FieldDescriptorProto* extension = file_proto.add_extension();
+ protobuf_unittest::OldOptionType::descriptor()->file()
+ ->FindExtensionByName("required_enum_opt")->CopyTo(extension);
+
+ // Add a test message that uses the "required_enum_opt" option.
+ DescriptorProto* test_message_type = file_proto.add_message_type();
+ protobuf_unittest::TestMessageWithRequiredEnumOption::descriptor()
+ ->CopyTo(test_message_type);
+
+ // Instruct the extension to use NewOptionType instead of
+ // OldOptionType, and add the descriptor of NewOptionType.
+ extension->set_type_name(".protobuf_unittest.NewOptionType");
+ DescriptorProto* new_option_type = file_proto.add_message_type();
+ protobuf_unittest::NewOptionType::descriptor()
+ ->CopyTo(new_option_type);
+
+ // Replace the value of the "required_enum_opt" option used in the
+ // test message with an enum value that only exists in NewOptionType.
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "uninterpreted_option { "
+ " name { "
+ " name_part: 'required_enum_opt' "
+ " is_extension: true "
+ " } "
+ " aggregate_value: 'value: NEW_VALUE' "
+ "}",
+ test_message_type->mutable_options()));
+
+ // Add the file descriptor to the pool.
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ // Find the test message.
+ const Descriptor* test_message = pool.FindMessageTypeByName(
+ "protobuf_unittest.TestMessageWithRequiredEnumOption");
+ ASSERT_TRUE(test_message != NULL);
+
+ const MessageOptions& options = test_message->options();
+ // Extract the "required_enum_opt" option. Since the binary does not
+ // know that the extension was updated, this will still return an
+ // OldOptionType message.
+ ASSERT_TRUE(
+ options.HasExtension(protobuf_unittest::required_enum_opt));
+ const protobuf_unittest::OldOptionType& old_enum_opt =
+ options.GetExtension(protobuf_unittest::required_enum_opt);
+
+ // Confirm that the required enum field is missing.
+ EXPECT_FALSE(old_enum_opt.IsInitialized());
+ EXPECT_FALSE(old_enum_opt.has_value());
+
+ string buf;
+ // Verify that the required enum field does show up when the option
+ // is re-parsed as a NewOptionType message;
+ protobuf_unittest::NewOptionType new_enum_opt;
+ EXPECT_TRUE(old_enum_opt.AppendPartialToString(&buf));
+ EXPECT_TRUE(new_enum_opt.ParseFromString(buf));
+ EXPECT_EQ(protobuf_unittest::NewOptionType::NEW_VALUE, new_enum_opt.value());
+}
+
+// ===================================================================
+
+class ValidationErrorTest : public testing::Test {
+ protected:
+ // Parse file_text as a FileDescriptorProto in text format and add it
+ // to the DescriptorPool. Expect no errors.
+ const FileDescriptor* BuildFile(const string& file_text) {
+ FileDescriptorProto file_proto;
+ EXPECT_TRUE(TextFormat::ParseFromString(file_text, &file_proto));
+ return GOOGLE_CHECK_NOTNULL(pool_.BuildFile(file_proto));
+ }
+
+ // Parse file_text as a FileDescriptorProto in text format and add it
+ // to the DescriptorPool. Expect errors to be produced which match the
+ // given error text.
+ void BuildFileWithErrors(const string& file_text,
+ const string& expected_errors) {
+ FileDescriptorProto file_proto;
+ ASSERT_TRUE(TextFormat::ParseFromString(file_text, &file_proto));
+
+ MockErrorCollector error_collector;
+ EXPECT_TRUE(
+ pool_.BuildFileCollectingErrors(file_proto, &error_collector) == NULL);
+ EXPECT_EQ(expected_errors, error_collector.text_);
+ }
+
+ // Parse file_text as a FileDescriptorProto in text format and add it
+ // to the DescriptorPool. Expect errors to be produced which match the
+ // given warning text.
+ void BuildFileWithWarnings(const string& file_text,
+ const string& expected_warnings) {
+ FileDescriptorProto file_proto;
+ ASSERT_TRUE(TextFormat::ParseFromString(file_text, &file_proto));
+
+ MockErrorCollector error_collector;
+ EXPECT_TRUE(pool_.BuildFileCollectingErrors(file_proto, &error_collector));
+ EXPECT_EQ(expected_warnings, error_collector.warning_text_);
+ }
+
+ // Builds some already-parsed file in our test pool.
+ void BuildFileInTestPool(const FileDescriptor* file) {
+ FileDescriptorProto file_proto;
+ file->CopyTo(&file_proto);
+ ASSERT_TRUE(pool_.BuildFile(file_proto) != NULL);
+ }
+
+ // Build descriptor.proto in our test pool. This allows us to extend it in
+ // the test pool, so we can test custom options.
+ void BuildDescriptorMessagesInTestPool() {
+ BuildFileInTestPool(DescriptorProto::descriptor()->file());
+ }
+
+ DescriptorPool pool_;
+};
+
+TEST_F(ValidationErrorTest, AlreadyDefined) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" }"
+ "message_type { name: \"Foo\" }",
+
+ "foo.proto: Foo: NAME: \"Foo\" is already defined.\n");
+}
+
+TEST_F(ValidationErrorTest, AlreadyDefinedInPackage) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "package: \"foo.bar\" "
+ "message_type { name: \"Foo\" }"
+ "message_type { name: \"Foo\" }",
+
+ "foo.proto: foo.bar.Foo: NAME: \"Foo\" is already defined in "
+ "\"foo.bar\".\n");
+}
+
+TEST_F(ValidationErrorTest, AlreadyDefinedInOtherFile) {
+ BuildFile(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" }");
+
+ BuildFileWithErrors(
+ "name: \"bar.proto\" "
+ "message_type { name: \"Foo\" }",
+
+ "bar.proto: Foo: NAME: \"Foo\" is already defined in file "
+ "\"foo.proto\".\n");
+}
+
+TEST_F(ValidationErrorTest, PackageAlreadyDefined) {
+ BuildFile(
+ "name: \"foo.proto\" "
+ "message_type { name: \"foo\" }");
+ BuildFileWithErrors(
+ "name: \"bar.proto\" "
+ "package: \"foo.bar\"",
+
+ "bar.proto: foo: NAME: \"foo\" is already defined (as something other "
+ "than a package) in file \"foo.proto\".\n");
+}
+
+TEST_F(ValidationErrorTest, EnumValueAlreadyDefinedInParent) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type { name: \"Foo\" value { name: \"FOO\" number: 1 } } "
+ "enum_type { name: \"Bar\" value { name: \"FOO\" number: 1 } } ",
+
+ "foo.proto: FOO: NAME: \"FOO\" is already defined.\n"
+ "foo.proto: FOO: NAME: Note that enum values use C++ scoping rules, "
+ "meaning that enum values are siblings of their type, not children of "
+ "it. Therefore, \"FOO\" must be unique within the global scope, not "
+ "just within \"Bar\".\n");
+}
+
+TEST_F(ValidationErrorTest, EnumValueAlreadyDefinedInParentNonGlobal) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "package: \"pkg\" "
+ "enum_type { name: \"Foo\" value { name: \"FOO\" number: 1 } } "
+ "enum_type { name: \"Bar\" value { name: \"FOO\" number: 1 } } ",
+
+ "foo.proto: pkg.FOO: NAME: \"FOO\" is already defined in \"pkg\".\n"
+ "foo.proto: pkg.FOO: NAME: Note that enum values use C++ scoping rules, "
+ "meaning that enum values are siblings of their type, not children of "
+ "it. Therefore, \"FOO\" must be unique within \"pkg\", not just within "
+ "\"Bar\".\n");
+}
+
+TEST_F(ValidationErrorTest, MissingName) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { }",
+
+ "foo.proto: : NAME: Missing name.\n");
+}
+
+TEST_F(ValidationErrorTest, InvalidName) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"$\" }",
+
+ "foo.proto: $: NAME: \"$\" is not a valid identifier.\n");
+}
+
+TEST_F(ValidationErrorTest, InvalidPackageName) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "package: \"foo.$\"",
+
+ "foo.proto: foo.$: NAME: \"$\" is not a valid identifier.\n");
+}
+
+TEST_F(ValidationErrorTest, MissingFileName) {
+ BuildFileWithErrors(
+ "",
+
+ ": : OTHER: Missing field: FileDescriptorProto.name.\n");
+}
+
+TEST_F(ValidationErrorTest, DupeDependency) {
+ BuildFile("name: \"foo.proto\"");
+ BuildFileWithErrors(
+ "name: \"bar.proto\" "
+ "dependency: \"foo.proto\" "
+ "dependency: \"foo.proto\" ",
+
+ "bar.proto: bar.proto: OTHER: Import \"foo.proto\" was listed twice.\n");
+}
+
+TEST_F(ValidationErrorTest, UnknownDependency) {
+ BuildFileWithErrors(
+ "name: \"bar.proto\" "
+ "dependency: \"foo.proto\" ",
+
+ "bar.proto: bar.proto: OTHER: Import \"foo.proto\" has not been loaded.\n");
+}
+
+TEST_F(ValidationErrorTest, InvalidPublicDependencyIndex) {
+ BuildFile("name: \"foo.proto\"");
+ BuildFileWithErrors(
+ "name: \"bar.proto\" "
+ "dependency: \"foo.proto\" "
+ "public_dependency: 1",
+ "bar.proto: bar.proto: OTHER: Invalid public dependency index.\n");
+}
+
+TEST_F(ValidationErrorTest, ForeignUnimportedPackageNoCrash) {
+ // Used to crash: If we depend on a non-existent file and then refer to a
+ // package defined in a file that we didn't import, and that package is
+ // nested within a parent package which this file is also in, and we don't
+ // include that parent package in the name (i.e. we do a relative lookup)...
+ // Yes, really.
+ BuildFile(
+ "name: 'foo.proto' "
+ "package: 'outer.foo' ");
+ BuildFileWithErrors(
+ "name: 'bar.proto' "
+ "dependency: 'baz.proto' "
+ "package: 'outer.bar' "
+ "message_type { "
+ " name: 'Bar' "
+ " field { name:'bar' number:1 label:LABEL_OPTIONAL type_name:'foo.Foo' }"
+ "}",
+
+ "bar.proto: bar.proto: OTHER: Import \"baz.proto\" has not been loaded.\n"
+ "bar.proto: outer.bar.Bar.bar: TYPE: \"outer.foo\" seems to be defined in "
+ "\"foo.proto\", which is not imported by \"bar.proto\". To use it here, "
+ "please add the necessary import.\n");
+}
+
+TEST_F(ValidationErrorTest, DupeFile) {
+ BuildFile(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" }");
+ // Note: We should *not* get redundant errors about "Foo" already being
+ // defined.
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" } "
+ // Add another type so that the files aren't identical (in which case there
+ // would be no error).
+ "enum_type { name: \"Bar\" }",
+
+ "foo.proto: foo.proto: OTHER: A file with this name is already in the "
+ "pool.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldInExtensionRange) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"foo\" number: 9 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name: \"bar\" number: 10 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name: \"baz\" number: 19 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name: \"qux\" number: 20 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " extension_range { start: 10 end: 20 }"
+ "}",
+
+ "foo.proto: Foo.bar: NUMBER: Extension range 10 to 19 includes field "
+ "\"bar\" (10).\n"
+ "foo.proto: Foo.baz: NUMBER: Extension range 10 to 19 includes field "
+ "\"baz\" (19).\n");
+}
+
+TEST_F(ValidationErrorTest, OverlappingExtensionRanges) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension_range { start: 10 end: 20 }"
+ " extension_range { start: 20 end: 30 }"
+ " extension_range { start: 19 end: 21 }"
+ "}",
+
+ "foo.proto: Foo: NUMBER: Extension range 19 to 20 overlaps with "
+ "already-defined range 10 to 19.\n"
+ "foo.proto: Foo: NUMBER: Extension range 19 to 20 overlaps with "
+ "already-defined range 20 to 29.\n");
+}
+
+TEST_F(ValidationErrorTest, ReservedFieldError) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"foo\" number: 15 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " reserved_range { start: 10 end: 20 }"
+ "}",
+
+ "foo.proto: Foo.foo: NUMBER: Field \"foo\" uses reserved number 15.\n");
+}
+
+TEST_F(ValidationErrorTest, ReservedExtensionRangeError) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension_range { start: 10 end: 20 }"
+ " reserved_range { start: 5 end: 15 }"
+ "}",
+
+ "foo.proto: Foo: NUMBER: Extension range 10 to 19"
+ " overlaps with reserved range 5 to 14.\n");
+}
+
+TEST_F(ValidationErrorTest, ReservedExtensionRangeAdjacent) {
+ BuildFile(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension_range { start: 10 end: 20 }"
+ " reserved_range { start: 5 end: 10 }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest, ReservedRangeOverlap) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " reserved_range { start: 10 end: 20 }"
+ " reserved_range { start: 5 end: 15 }"
+ "}",
+
+ "foo.proto: Foo: NUMBER: Reserved range 5 to 14"
+ " overlaps with already-defined range 10 to 19.\n");
+}
+
+TEST_F(ValidationErrorTest, ReservedNameError) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"foo\" number: 15 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name: \"bar\" number: 16 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name: \"baz\" number: 17 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " reserved_name: \"foo\""
+ " reserved_name: \"bar\""
+ "}",
+
+ "foo.proto: Foo.foo: NAME: Field name \"foo\" is reserved.\n"
+ "foo.proto: Foo.bar: NAME: Field name \"bar\" is reserved.\n");
+}
+
+TEST_F(ValidationErrorTest, ReservedNameRedundant) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " reserved_name: \"foo\""
+ " reserved_name: \"foo\""
+ "}",
+
+ "foo.proto: foo: NAME: Field name \"foo\" is reserved multiple times.\n");
+}
+
+TEST_F(ValidationErrorTest, ReservedFieldsDebugString) {
+ const FileDescriptor* file = BuildFile(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " reserved_name: \"foo\""
+ " reserved_name: \"bar\""
+ " reserved_range { start: 5 end: 6 }"
+ " reserved_range { start: 10 end: 20 }"
+ "}");
+
+ ASSERT_EQ(
+ "syntax = \"proto2\";\n\n"
+ "message Foo {\n"
+ " reserved 5, 10 to 19;\n"
+ " reserved \"foo\", \"bar\";\n"
+ "}\n\n",
+ file->DebugString());
+}
+
+TEST_F(ValidationErrorTest, InvalidDefaults) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+
+ // Invalid number.
+ " field { name: \"foo\" number: 1 label: LABEL_OPTIONAL type: TYPE_INT32"
+ " default_value: \"abc\" }"
+
+ // Empty default value.
+ " field { name: \"bar\" number: 2 label: LABEL_OPTIONAL type: TYPE_INT32"
+ " default_value: \"\" }"
+
+ // Invalid boolean.
+ " field { name: \"baz\" number: 3 label: LABEL_OPTIONAL type: TYPE_BOOL"
+ " default_value: \"abc\" }"
+
+ // Messages can't have defaults.
+ " field { name: \"qux\" number: 4 label: LABEL_OPTIONAL type: TYPE_MESSAGE"
+ " default_value: \"abc\" type_name: \"Foo\" }"
+
+ // Same thing, but we don't know that this field has message type until
+ // we look up the type name.
+ " field { name: \"quux\" number: 5 label: LABEL_OPTIONAL"
+ " default_value: \"abc\" type_name: \"Foo\" }"
+
+ // Repeateds can't have defaults.
+ " field { name: \"corge\" number: 6 label: LABEL_REPEATED type: TYPE_INT32"
+ " default_value: \"1\" }"
+ "}",
+
+ "foo.proto: Foo.foo: DEFAULT_VALUE: Couldn't parse default value \"abc\".\n"
+ "foo.proto: Foo.bar: DEFAULT_VALUE: Couldn't parse default value \"\".\n"
+ "foo.proto: Foo.baz: DEFAULT_VALUE: Boolean default must be true or "
+ "false.\n"
+ "foo.proto: Foo.qux: DEFAULT_VALUE: Messages can't have default values.\n"
+ "foo.proto: Foo.corge: DEFAULT_VALUE: Repeated fields can't have default "
+ "values.\n"
+ // This ends up being reported later because the error is detected at
+ // cross-linking time.
+ "foo.proto: Foo.quux: DEFAULT_VALUE: Messages can't have default "
+ "values.\n");
+}
+
+TEST_F(ValidationErrorTest, NegativeFieldNumber) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"foo\" number: -1 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+
+ "foo.proto: Foo.foo: NUMBER: Field numbers must be positive integers.\n");
+}
+
+TEST_F(ValidationErrorTest, HugeFieldNumber) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"foo\" number: 0x70000000 "
+ " label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+
+ "foo.proto: Foo.foo: NUMBER: Field numbers cannot be greater than "
+ "536870911.\n");
+}
+
+TEST_F(ValidationErrorTest, ReservedFieldNumber) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field {name:\"foo\" number: 18999 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field {name:\"bar\" number: 19000 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field {name:\"baz\" number: 19999 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field {name:\"qux\" number: 20000 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+
+ "foo.proto: Foo.bar: NUMBER: Field numbers 19000 through 19999 are "
+ "reserved for the protocol buffer library implementation.\n"
+ "foo.proto: Foo.baz: NUMBER: Field numbers 19000 through 19999 are "
+ "reserved for the protocol buffer library implementation.\n");
+}
+
+TEST_F(ValidationErrorTest, ExtensionMissingExtendee) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension { name: \"foo\" number: 1 label: LABEL_OPTIONAL"
+ " type_name: \"Foo\" }"
+ "}",
+
+ "foo.proto: Foo.foo: EXTENDEE: FieldDescriptorProto.extendee not set for "
+ "extension field.\n");
+}
+
+TEST_F(ValidationErrorTest, NonExtensionWithExtendee) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Bar\""
+ " extension_range { start: 1 end: 2 }"
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"foo\" number: 1 label: LABEL_OPTIONAL"
+ " type_name: \"Foo\" extendee: \"Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: EXTENDEE: FieldDescriptorProto.extendee set for "
+ "non-extension field.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldOneofIndexTooLarge) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 1 }"
+ " field { name:\"dummy\" number:2 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " oneof_decl { name:\"bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: OTHER: FieldDescriptorProto.oneof_index 1 is out of "
+ "range for type \"Foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, FieldOneofIndexNegative) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: -1 }"
+ " field { name:\"dummy\" number:2 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " oneof_decl { name:\"bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: OTHER: FieldDescriptorProto.oneof_index -1 is out of "
+ "range for type \"Foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, OneofFieldsConsecutiveDefinition) {
+ // Fields belonging to the same oneof must be defined consecutively.
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo1\" number: 1 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " field { name:\"bar\" number: 2 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name:\"foo2\" number: 3 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " oneof_decl { name:\"foos\" }"
+ "}",
+
+ "foo.proto: Foo.bar: OTHER: Fields in the same oneof must be defined "
+ "consecutively. \"bar\" cannot be defined before the completion of the "
+ "\"foos\" oneof definition.\n");
+
+ // Prevent interleaved fields, which belong to different oneofs.
+ BuildFileWithErrors(
+ "name: \"foo2.proto\" "
+ "message_type {"
+ " name: \"Foo2\""
+ " field { name:\"foo1\" number: 1 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " field { name:\"bar1\" number: 2 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 1 }"
+ " field { name:\"foo2\" number: 3 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " field { name:\"bar2\" number: 4 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 1 }"
+ " oneof_decl { name:\"foos\" }"
+ " oneof_decl { name:\"bars\" }"
+ "}",
+ "foo2.proto: Foo2.bar1: OTHER: Fields in the same oneof must be defined "
+ "consecutively. \"bar1\" cannot be defined before the completion of the "
+ "\"foos\" oneof definition.\n"
+ "foo2.proto: Foo2.foo2: OTHER: Fields in the same oneof must be defined "
+ "consecutively. \"foo2\" cannot be defined before the completion of the "
+ "\"bars\" oneof definition.\n");
+
+ // Another case for normal fields and different oneof fields interleave.
+ BuildFileWithErrors(
+ "name: \"foo3.proto\" "
+ "message_type {"
+ " name: \"Foo3\""
+ " field { name:\"foo1\" number: 1 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " field { name:\"bar1\" number: 2 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 1 }"
+ " field { name:\"baz\" number: 3 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name:\"foo2\" number: 4 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " oneof_index: 0 }"
+ " oneof_decl { name:\"foos\" }"
+ " oneof_decl { name:\"bars\" }"
+ "}",
+ "foo3.proto: Foo3.baz: OTHER: Fields in the same oneof must be defined "
+ "consecutively. \"baz\" cannot be defined before the completion of the "
+ "\"foos\" oneof definition.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldNumberConflict) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"foo\" number: 1 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name: \"bar\" number: 1 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+
+ "foo.proto: Foo.bar: NUMBER: Field number 1 has already been used in "
+ "\"Foo\" by field \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, BadMessageSetExtensionType) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"MessageSet\""
+ " options { message_set_wire_format: true }"
+ " extension_range { start: 4 end: 5 }"
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " extension { name:\"foo\" number:4 label:LABEL_OPTIONAL type:TYPE_INT32"
+ " extendee: \"MessageSet\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: Extensions of MessageSets must be optional "
+ "messages.\n");
+}
+
+TEST_F(ValidationErrorTest, BadMessageSetExtensionLabel) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"MessageSet\""
+ " options { message_set_wire_format: true }"
+ " extension_range { start: 4 end: 5 }"
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " extension { name:\"foo\" number:4 label:LABEL_REPEATED type:TYPE_MESSAGE"
+ " type_name: \"Foo\" extendee: \"MessageSet\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: Extensions of MessageSets must be optional "
+ "messages.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldInMessageSet) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " options { message_set_wire_format: true }"
+ " field { name: \"foo\" number: 1 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+
+ "foo.proto: Foo.foo: NAME: MessageSets cannot have fields, only "
+ "extensions.\n");
+}
+
+TEST_F(ValidationErrorTest, NegativeExtensionRangeNumber) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension_range { start: -10 end: -1 }"
+ "}",
+
+ "foo.proto: Foo: NUMBER: Extension numbers must be positive integers.\n");
+}
+
+TEST_F(ValidationErrorTest, HugeExtensionRangeNumber) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension_range { start: 1 end: 0x70000000 }"
+ "}",
+
+ "foo.proto: Foo: NUMBER: Extension numbers cannot be greater than "
+ "536870911.\n");
+}
+
+TEST_F(ValidationErrorTest, ExtensionRangeEndBeforeStart) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension_range { start: 10 end: 10 }"
+ " extension_range { start: 10 end: 5 }"
+ "}",
+
+ "foo.proto: Foo: NUMBER: Extension range end number must be greater than "
+ "start number.\n"
+ "foo.proto: Foo: NUMBER: Extension range end number must be greater than "
+ "start number.\n");
+}
+
+TEST_F(ValidationErrorTest, EmptyEnum) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type { name: \"Foo\" }"
+ // Also use the empty enum in a message to make sure there are no crashes
+ // during validation (possible if the code attempts to derive a default
+ // value for the field).
+ "message_type {"
+ " name: \"Bar\""
+ " field { name: \"foo\" number: 1 label:LABEL_OPTIONAL type_name:\"Foo\" }"
+ " field { name: \"bar\" number: 2 label:LABEL_OPTIONAL type_name:\"Foo\" "
+ " default_value: \"NO_SUCH_VALUE\" }"
+ "}",
+
+ "foo.proto: Foo: NAME: Enums must contain at least one value.\n"
+ "foo.proto: Bar.bar: DEFAULT_VALUE: Enum type \"Foo\" has no value named "
+ "\"NO_SUCH_VALUE\".\n");
+}
+
+TEST_F(ValidationErrorTest, UndefinedExtendee) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " extension { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_INT32"
+ " extendee: \"Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: EXTENDEE: \"Bar\" is not defined.\n");
+}
+
+TEST_F(ValidationErrorTest, NonMessageExtendee) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type { name: \"Bar\" value { name:\"DUMMY\" number:0 } }"
+ "message_type {"
+ " name: \"Foo\""
+ " extension { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_INT32"
+ " extendee: \"Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: EXTENDEE: \"Bar\" is not a message type.\n");
+}
+
+TEST_F(ValidationErrorTest, NotAnExtensionNumber) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Bar\""
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " extension { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_INT32"
+ " extendee: \"Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: NUMBER: \"Bar\" does not declare 1 as an extension "
+ "number.\n");
+}
+
+TEST_F(ValidationErrorTest, RequiredExtension) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Bar\""
+ " extension_range { start: 1000 end: 10000 }"
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " extension {"
+ " name:\"foo\""
+ " number:1000"
+ " label:LABEL_REQUIRED"
+ " type:TYPE_INT32"
+ " extendee: \"Bar\""
+ " }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: Message extensions cannot have required "
+ "fields.\n");
+}
+
+TEST_F(ValidationErrorTest, UndefinedFieldType) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: \"Bar\" is not defined.\n");
+}
+
+TEST_F(ValidationErrorTest, UndefinedFieldTypeWithDefault) {
+ // See b/12533582. Previously this failed because the default value was not
+ // accepted by the parser, which assumed an enum type, leading to an unclear
+ // error message. We want this input to yield a validation error instead,
+ // since the unknown type is the primary problem.
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"int\" "
+ " default_value:\"1\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: \"int\" is not defined.\n");
+}
+
+TEST_F(ValidationErrorTest, UndefinedNestedFieldType) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " nested_type { name:\"Baz\" }"
+ " field { name:\"foo\" number:1"
+ " label:LABEL_OPTIONAL"
+ " type_name:\"Foo.Baz.Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: \"Foo.Baz.Bar\" is not defined.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldTypeDefinedInUndeclaredDependency) {
+ BuildFile(
+ "name: \"bar.proto\" "
+ "message_type { name: \"Bar\" } ");
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\" }"
+ "}",
+ "foo.proto: Foo.foo: TYPE: \"Bar\" seems to be defined in \"bar.proto\", "
+ "which is not imported by \"foo.proto\". To use it here, please add the "
+ "necessary import.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldTypeDefinedInIndirectDependency) {
+ // Test for hidden dependencies.
+ //
+ // // bar.proto
+ // message Bar{}
+ //
+ // // forward.proto
+ // import "bar.proto"
+ //
+ // // foo.proto
+ // import "forward.proto"
+ // message Foo {
+ // optional Bar foo = 1; // Error, needs to import bar.proto explicitly.
+ // }
+ //
+ BuildFile(
+ "name: \"bar.proto\" "
+ "message_type { name: \"Bar\" }");
+
+ BuildFile(
+ "name: \"forward.proto\""
+ "dependency: \"bar.proto\"");
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"forward.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\" }"
+ "}",
+ "foo.proto: Foo.foo: TYPE: \"Bar\" seems to be defined in \"bar.proto\", "
+ "which is not imported by \"foo.proto\". To use it here, please add the "
+ "necessary import.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldTypeDefinedInPublicDependency) {
+ // Test for public dependencies.
+ //
+ // // bar.proto
+ // message Bar{}
+ //
+ // // forward.proto
+ // import public "bar.proto"
+ //
+ // // foo.proto
+ // import "forward.proto"
+ // message Foo {
+ // optional Bar foo = 1; // Correct. "bar.proto" is public imported into
+ // // forward.proto, so when "foo.proto" imports
+ // // "forward.proto", it imports "bar.proto" too.
+ // }
+ //
+ BuildFile(
+ "name: \"bar.proto\" "
+ "message_type { name: \"Bar\" }");
+
+ BuildFile(
+ "name: \"forward.proto\""
+ "dependency: \"bar.proto\" "
+ "public_dependency: 0");
+
+ BuildFile(
+ "name: \"foo.proto\" "
+ "dependency: \"forward.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\" }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest, FieldTypeDefinedInTransitivePublicDependency) {
+ // Test for public dependencies.
+ //
+ // // bar.proto
+ // message Bar{}
+ //
+ // // forward.proto
+ // import public "bar.proto"
+ //
+ // // forward2.proto
+ // import public "forward.proto"
+ //
+ // // foo.proto
+ // import "forward2.proto"
+ // message Foo {
+ // optional Bar foo = 1; // Correct, public imports are transitive.
+ // }
+ //
+ BuildFile(
+ "name: \"bar.proto\" "
+ "message_type { name: \"Bar\" }");
+
+ BuildFile(
+ "name: \"forward.proto\""
+ "dependency: \"bar.proto\" "
+ "public_dependency: 0");
+
+ BuildFile(
+ "name: \"forward2.proto\""
+ "dependency: \"forward.proto\" "
+ "public_dependency: 0");
+
+ BuildFile(
+ "name: \"foo.proto\" "
+ "dependency: \"forward2.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\" }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest,
+ FieldTypeDefinedInPrivateDependencyOfPublicDependency) {
+ // Test for public dependencies.
+ //
+ // // bar.proto
+ // message Bar{}
+ //
+ // // forward.proto
+ // import "bar.proto"
+ //
+ // // forward2.proto
+ // import public "forward.proto"
+ //
+ // // foo.proto
+ // import "forward2.proto"
+ // message Foo {
+ // optional Bar foo = 1; // Error, the "bar.proto" is not public imported
+ // // into "forward.proto", so will not be imported
+ // // into either "forward2.proto" or "foo.proto".
+ // }
+ //
+ BuildFile(
+ "name: \"bar.proto\" "
+ "message_type { name: \"Bar\" }");
+
+ BuildFile(
+ "name: \"forward.proto\""
+ "dependency: \"bar.proto\"");
+
+ BuildFile(
+ "name: \"forward2.proto\""
+ "dependency: \"forward.proto\" "
+ "public_dependency: 0");
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"forward2.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\" }"
+ "}",
+ "foo.proto: Foo.foo: TYPE: \"Bar\" seems to be defined in \"bar.proto\", "
+ "which is not imported by \"foo.proto\". To use it here, please add the "
+ "necessary import.\n");
+}
+
+
+TEST_F(ValidationErrorTest, SearchMostLocalFirst) {
+ // The following should produce an error that Bar.Baz is resolved but
+ // not defined:
+ // message Bar { message Baz {} }
+ // message Foo {
+ // message Bar {
+ // // Placing "message Baz{}" here, or removing Foo.Bar altogether,
+ // // would fix the error.
+ // }
+ // optional Bar.Baz baz = 1;
+ // }
+ // An one point the lookup code incorrectly did not produce an error in this
+ // case, because when looking for Bar.Baz, it would try "Foo.Bar.Baz" first,
+ // fail, and ten try "Bar.Baz" and succeed, even though "Bar" should actually
+ // refer to the inner Bar, not the outer one.
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Bar\""
+ " nested_type { name: \"Baz\" }"
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " nested_type { name: \"Bar\" }"
+ " field { name:\"baz\" number:1 label:LABEL_OPTIONAL"
+ " type_name:\"Bar.Baz\" }"
+ "}",
+
+ "foo.proto: Foo.baz: TYPE: \"Bar.Baz\" is resolved to \"Foo.Bar.Baz\","
+ " which is not defined. The innermost scope is searched first in name "
+ "resolution. Consider using a leading '.'(i.e., \".Bar.Baz\") to start "
+ "from the outermost scope.\n");
+}
+
+TEST_F(ValidationErrorTest, SearchMostLocalFirst2) {
+ // This test would find the most local "Bar" first, and does, but
+ // proceeds to find the outer one because the inner one's not an
+ // aggregate.
+ BuildFile(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Bar\""
+ " nested_type { name: \"Baz\" }"
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " field { name: \"Bar\" number:1 type:TYPE_BYTES } "
+ " field { name:\"baz\" number:2 label:LABEL_OPTIONAL"
+ " type_name:\"Bar.Baz\" }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest, PackageOriginallyDeclaredInTransitiveDependent) {
+ // Imagine we have the following:
+ //
+ // foo.proto:
+ // package foo.bar;
+ // bar.proto:
+ // package foo.bar;
+ // import "foo.proto";
+ // message Bar {}
+ // baz.proto:
+ // package foo;
+ // import "bar.proto"
+ // message Baz { optional bar.Bar qux = 1; }
+ //
+ // When validating baz.proto, we will look up "bar.Bar". As part of this
+ // lookup, we first lookup "bar" then try to find "Bar" within it. "bar"
+ // should resolve to "foo.bar". Note, though, that "foo.bar" was originally
+ // defined in foo.proto, which is not a direct dependency of baz.proto. The
+ // implementation of FindSymbol() normally only returns symbols in direct
+ // dependencies, not indirect ones. This test insures that this does not
+ // prevent it from finding "foo.bar".
+
+ BuildFile(
+ "name: \"foo.proto\" "
+ "package: \"foo.bar\" ");
+ BuildFile(
+ "name: \"bar.proto\" "
+ "package: \"foo.bar\" "
+ "dependency: \"foo.proto\" "
+ "message_type { name: \"Bar\" }");
+ BuildFile(
+ "name: \"baz.proto\" "
+ "package: \"foo\" "
+ "dependency: \"bar.proto\" "
+ "message_type { "
+ " name: \"Baz\" "
+ " field { name:\"qux\" number:1 label:LABEL_OPTIONAL "
+ " type_name:\"bar.Bar\" }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest, FieldTypeNotAType) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL "
+ " type_name:\".Foo.bar\" }"
+ " field { name:\"bar\" number:2 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: \".Foo.bar\" is not a type.\n");
+}
+
+TEST_F(ValidationErrorTest, RelativeFieldTypeNotAType) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " nested_type {"
+ " name: \"Bar\""
+ " field { name:\"Baz\" number:2 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " }"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL "
+ " type_name:\"Bar.Baz\" }"
+ "}",
+ "foo.proto: Foo.foo: TYPE: \"Bar.Baz\" is not a type.\n");
+}
+
+TEST_F(ValidationErrorTest, FieldTypeMayBeItsName) {
+ BuildFile(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Bar\""
+ "}"
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"Bar\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\" }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest, EnumFieldTypeIsMessage) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Bar\" } "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_ENUM"
+ " type_name:\"Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: \"Bar\" is not an enum type.\n");
+}
+
+TEST_F(ValidationErrorTest, MessageFieldTypeIsEnum) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type { name: \"Bar\" value { name:\"DUMMY\" number:0 } } "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_MESSAGE"
+ " type_name:\"Bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: \"Bar\" is not a message type.\n");
+}
+
+TEST_F(ValidationErrorTest, BadEnumDefaultValue) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type { name: \"Bar\" value { name:\"DUMMY\" number:0 } } "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\""
+ " default_value:\"NO_SUCH_VALUE\" }"
+ "}",
+
+ "foo.proto: Foo.foo: DEFAULT_VALUE: Enum type \"Bar\" has no value named "
+ "\"NO_SUCH_VALUE\".\n");
+}
+
+TEST_F(ValidationErrorTest, EnumDefaultValueIsInteger) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type { name: \"Bar\" value { name:\"DUMMY\" number:0 } } "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type_name:\"Bar\""
+ " default_value:\"0\" }"
+ "}",
+
+ "foo.proto: Foo.foo: DEFAULT_VALUE: Default value for an enum field must "
+ "be an identifier.\n");
+}
+
+TEST_F(ValidationErrorTest, PrimitiveWithTypeName) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_INT32"
+ " type_name:\"Foo\" }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: Field with primitive type has type_name.\n");
+}
+
+TEST_F(ValidationErrorTest, NonPrimitiveWithoutTypeName) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_MESSAGE }"
+ "}",
+
+ "foo.proto: Foo.foo: TYPE: Field with message or enum type missing "
+ "type_name.\n");
+}
+
+TEST_F(ValidationErrorTest, OneofWithNoFields) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " oneof_decl { name:\"bar\" }"
+ "}",
+
+ "foo.proto: Foo.bar: NAME: Oneof must have at least one field.\n");
+}
+
+TEST_F(ValidationErrorTest, OneofLabelMismatch) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"Foo\""
+ " field { name:\"foo\" number:1 label:LABEL_REPEATED type:TYPE_INT32 "
+ " oneof_index:0 }"
+ " oneof_decl { name:\"bar\" }"
+ "}",
+
+ "foo.proto: Foo.foo: NAME: Fields of oneofs must themselves have label "
+ "LABEL_OPTIONAL.\n");
+}
+
+TEST_F(ValidationErrorTest, InputTypeNotDefined) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" } "
+ "service {"
+ " name: \"TestService\""
+ " method { name: \"A\" input_type: \"Bar\" output_type: \"Foo\" }"
+ "}",
+
+ "foo.proto: TestService.A: INPUT_TYPE: \"Bar\" is not defined.\n"
+ );
+}
+
+TEST_F(ValidationErrorTest, InputTypeNotAMessage) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" } "
+ "enum_type { name: \"Bar\" value { name:\"DUMMY\" number:0 } } "
+ "service {"
+ " name: \"TestService\""
+ " method { name: \"A\" input_type: \"Bar\" output_type: \"Foo\" }"
+ "}",
+
+ "foo.proto: TestService.A: INPUT_TYPE: \"Bar\" is not a message type.\n"
+ );
+}
+
+TEST_F(ValidationErrorTest, OutputTypeNotDefined) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" } "
+ "service {"
+ " name: \"TestService\""
+ " method { name: \"A\" input_type: \"Foo\" output_type: \"Bar\" }"
+ "}",
+
+ "foo.proto: TestService.A: OUTPUT_TYPE: \"Bar\" is not defined.\n"
+ );
+}
+
+TEST_F(ValidationErrorTest, OutputTypeNotAMessage) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" } "
+ "enum_type { name: \"Bar\" value { name:\"DUMMY\" number:0 } } "
+ "service {"
+ " name: \"TestService\""
+ " method { name: \"A\" input_type: \"Foo\" output_type: \"Bar\" }"
+ "}",
+
+ "foo.proto: TestService.A: OUTPUT_TYPE: \"Bar\" is not a message type.\n"
+ );
+}
+
+
+TEST_F(ValidationErrorTest, IllegalPackedField) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {\n"
+ " name: \"Foo\""
+ " field { name:\"packed_string\" number:1 label:LABEL_REPEATED "
+ " type:TYPE_STRING "
+ " options { uninterpreted_option {"
+ " name { name_part: \"packed\" is_extension: false }"
+ " identifier_value: \"true\" }}}\n"
+ " field { name:\"packed_message\" number:3 label:LABEL_REPEATED "
+ " type_name: \"Foo\""
+ " options { uninterpreted_option {"
+ " name { name_part: \"packed\" is_extension: false }"
+ " identifier_value: \"true\" }}}\n"
+ " field { name:\"optional_int32\" number: 4 label: LABEL_OPTIONAL "
+ " type:TYPE_INT32 "
+ " options { uninterpreted_option {"
+ " name { name_part: \"packed\" is_extension: false }"
+ " identifier_value: \"true\" }}}\n"
+ "}",
+
+ "foo.proto: Foo.packed_string: TYPE: [packed = true] can only be "
+ "specified for repeated primitive fields.\n"
+ "foo.proto: Foo.packed_message: TYPE: [packed = true] can only be "
+ "specified for repeated primitive fields.\n"
+ "foo.proto: Foo.optional_int32: TYPE: [packed = true] can only be "
+ "specified for repeated primitive fields.\n"
+ );
+}
+
+TEST_F(ValidationErrorTest, OptionWrongType) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"TestMessage\" "
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_STRING "
+ " options { uninterpreted_option { name { name_part: \"ctype\" "
+ " is_extension: false }"
+ " positive_int_value: 1 }"
+ " }"
+ " }"
+ "}\n",
+
+ "foo.proto: TestMessage.foo: OPTION_VALUE: Value must be identifier for "
+ "enum-valued option \"google.protobuf.FieldOptions.ctype\".\n");
+}
+
+TEST_F(ValidationErrorTest, OptionExtendsAtomicType) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"TestMessage\" "
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_STRING "
+ " options { uninterpreted_option { name { name_part: \"ctype\" "
+ " is_extension: false }"
+ " name { name_part: \"foo\" "
+ " is_extension: true }"
+ " positive_int_value: 1 }"
+ " }"
+ " }"
+ "}\n",
+
+ "foo.proto: TestMessage.foo: OPTION_NAME: Option \"ctype\" is an "
+ "atomic type, not a message.\n");
+}
+
+TEST_F(ValidationErrorTest, DupOption) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"TestMessage\" "
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_UINT32 "
+ " options { uninterpreted_option { name { name_part: \"ctype\" "
+ " is_extension: false }"
+ " identifier_value: \"CORD\" }"
+ " uninterpreted_option { name { name_part: \"ctype\" "
+ " is_extension: false }"
+ " identifier_value: \"CORD\" }"
+ " }"
+ " }"
+ "}\n",
+
+ "foo.proto: TestMessage.foo: OPTION_NAME: Option \"ctype\" was "
+ "already set.\n");
+}
+
+TEST_F(ValidationErrorTest, InvalidOptionName) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type { "
+ " name: \"TestMessage\" "
+ " field { name:\"foo\" number:1 label:LABEL_OPTIONAL type:TYPE_BOOL "
+ " options { uninterpreted_option { "
+ " name { name_part: \"uninterpreted_option\" "
+ " is_extension: false }"
+ " positive_int_value: 1 "
+ " }"
+ " }"
+ " }"
+ "}\n",
+
+ "foo.proto: TestMessage.foo: OPTION_NAME: Option must not use "
+ "reserved name \"uninterpreted_option\".\n");
+}
+
+TEST_F(ValidationErrorTest, RepeatedMessageOption) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "message_type: { name: \"Bar\" field: { "
+ " name: \"foo\" number: 1 label: LABEL_OPTIONAL type: TYPE_INT32 } "
+ "} "
+ "extension { name: \"bar\" number: 7672757 label: LABEL_REPEATED "
+ " type: TYPE_MESSAGE type_name: \"Bar\" "
+ " extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"bar\" "
+ " is_extension: true } "
+ " name { name_part: \"foo\" "
+ " is_extension: false } "
+ " positive_int_value: 1 } }",
+
+ "foo.proto: foo.proto: OPTION_NAME: Option field \"(bar)\" is a "
+ "repeated message. Repeated message options must be initialized "
+ "using an aggregate value.\n");
+}
+
+TEST_F(ValidationErrorTest, ResolveUndefinedOption) {
+ // The following should produce an eror that baz.bar is resolved but not
+ // defined.
+ // foo.proto:
+ // package baz
+ // import google/protobuf/descriptor.proto
+ // message Bar { optional int32 foo = 1; }
+ // extend FileOptions { optional Bar bar = 7672757; }
+ //
+ // qux.proto:
+ // package qux.baz
+ // option (baz.bar).foo = 1;
+ //
+ // Although "baz.bar" is already defined, the lookup code will try
+ // "qux.baz.bar", since it's the match from the innermost scope, which will
+ // cause a symbol not defined error.
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFile(
+ "name: \"foo.proto\" "
+ "package: \"baz\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "message_type: { name: \"Bar\" field: { "
+ " name: \"foo\" number: 1 label: LABEL_OPTIONAL type: TYPE_INT32 } "
+ "} "
+ "extension { name: \"bar\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_MESSAGE type_name: \"Bar\" "
+ " extendee: \"google.protobuf.FileOptions\" }");
+
+ BuildFileWithErrors(
+ "name: \"qux.proto\" "
+ "package: \"qux.baz\" "
+ "options { uninterpreted_option { name { name_part: \"baz.bar\" "
+ " is_extension: true } "
+ " name { name_part: \"foo\" "
+ " is_extension: false } "
+ " positive_int_value: 1 } }",
+
+ "qux.proto: qux.proto: OPTION_NAME: Option \"(baz.bar)\" is resolved to "
+ "\"(qux.baz.bar)\","
+ " which is not defined. The innermost scope is searched first in name "
+ "resolution. Consider using a leading '.'(i.e., \"(.baz.bar)\") to start "
+ "from the outermost scope.\n");
+}
+
+TEST_F(ValidationErrorTest, UnknownOption) {
+ BuildFileWithErrors(
+ "name: \"qux.proto\" "
+ "package: \"qux.baz\" "
+ "options { uninterpreted_option { name { name_part: \"baaz.bar\" "
+ " is_extension: true } "
+ " name { name_part: \"foo\" "
+ " is_extension: false } "
+ " positive_int_value: 1 } }",
+
+ "qux.proto: qux.proto: OPTION_NAME: Option \"(baaz.bar)\" unknown.\n");
+}
+
+TEST_F(ValidationErrorTest, CustomOptionConflictingFieldNumber) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo1\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"google.protobuf.FieldOptions\" }"
+ "extension { name: \"foo2\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"google.protobuf.FieldOptions\" }",
+
+ "foo.proto: foo2: NUMBER: Extension number 7672757 has already been used "
+ "in \"google.protobuf.FieldOptions\" by extension \"foo1\".\n");
+}
+
+TEST_F(ValidationErrorTest, Int32OptionValueOutOfPositiveRange) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " positive_int_value: 0x80000000 } "
+ "}",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value out of range "
+ "for int32 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, Int32OptionValueOutOfNegativeRange) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " negative_int_value: -0x80000001 } "
+ "}",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value out of range "
+ "for int32 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, Int32OptionValueIsNotPositiveInt) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " string_value: \"5\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be integer "
+ "for int32 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, Int64OptionValueOutOfRange) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_INT64 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " positive_int_value: 0x8000000000000000 } "
+ "}",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value out of range "
+ "for int64 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, Int64OptionValueIsNotPositiveInt) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_INT64 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " identifier_value: \"5\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be integer "
+ "for int64 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, UInt32OptionValueOutOfRange) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_UINT32 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " positive_int_value: 0x100000000 } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value out of range "
+ "for uint32 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, UInt32OptionValueIsNotPositiveInt) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_UINT32 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " double_value: -5.6 } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be non-negative integer "
+ "for uint32 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, UInt64OptionValueIsNotPositiveInt) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_UINT64 extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " negative_int_value: -5 } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be non-negative integer "
+ "for uint64 option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, FloatOptionValueIsNotNumber) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_FLOAT extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " string_value: \"bar\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be number "
+ "for float option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, DoubleOptionValueIsNotNumber) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_DOUBLE extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " string_value: \"bar\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be number "
+ "for double option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, BoolOptionValueIsNotTrueOrFalse) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_BOOL extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " identifier_value: \"bar\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be \"true\" or \"false\" "
+ "for boolean option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, EnumOptionValueIsNotIdentifier) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "enum_type { name: \"FooEnum\" value { name: \"BAR\" number: 1 } "
+ " value { name: \"BAZ\" number: 2 } }"
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_ENUM type_name: \"FooEnum\" "
+ " extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " string_value: \"QUUX\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be identifier for "
+ "enum-valued option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, EnumOptionValueIsNotEnumValueName) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "enum_type { name: \"FooEnum\" value { name: \"BAR\" number: 1 } "
+ " value { name: \"BAZ\" number: 2 } }"
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_ENUM type_name: \"FooEnum\" "
+ " extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " identifier_value: \"QUUX\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Enum type \"FooEnum\" has no value "
+ "named \"QUUX\" for option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, EnumOptionValueIsSiblingEnumValueName) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "enum_type { name: \"FooEnum1\" value { name: \"BAR\" number: 1 } "
+ " value { name: \"BAZ\" number: 2 } }"
+ "enum_type { name: \"FooEnum2\" value { name: \"QUX\" number: 1 } "
+ " value { name: \"QUUX\" number: 2 } }"
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_ENUM type_name: \"FooEnum1\" "
+ " extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " identifier_value: \"QUUX\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Enum type \"FooEnum1\" has no value "
+ "named \"QUUX\" for option \"foo\". This appears to be a value from a "
+ "sibling type.\n");
+}
+
+TEST_F(ValidationErrorTest, StringOptionValueIsNotString) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_STRING extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " identifier_value: \"QUUX\" } }",
+
+ "foo.proto: foo.proto: OPTION_VALUE: Value must be quoted string for "
+ "string option \"foo\".\n");
+}
+
+TEST_F(ValidationErrorTest, DuplicateExtensionFieldNumber) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFile(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"option1\" number: 1000 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"google.protobuf.FileOptions\" }");
+
+ BuildFileWithWarnings(
+ "name: \"bar.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "extension { name: \"option2\" number: 1000 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"google.protobuf.FileOptions\" }",
+ "bar.proto: option2: NUMBER: Extension number 1000 has already been used "
+ "in \"google.protobuf.FileOptions\" by extension \"option1\" defined in "
+ "foo.proto.\n");
+}
+
+// Helper function for tests that check for aggregate value parsing
+// errors. The "value" argument is embedded inside the
+// "uninterpreted_option" portion of the result.
+static string EmbedAggregateValue(const char* value) {
+ return strings::Substitute(
+ "name: \"foo.proto\" "
+ "dependency: \"google/protobuf/descriptor.proto\" "
+ "message_type { name: \"Foo\" } "
+ "extension { name: \"foo\" number: 7672757 label: LABEL_OPTIONAL "
+ " type: TYPE_MESSAGE type_name: \"Foo\" "
+ " extendee: \"google.protobuf.FileOptions\" }"
+ "options { uninterpreted_option { name { name_part: \"foo\" "
+ " is_extension: true } "
+ " $0 } }",
+ value);
+}
+
+TEST_F(ValidationErrorTest, AggregateValueNotFound) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ EmbedAggregateValue("string_value: \"\""),
+ "foo.proto: foo.proto: OPTION_VALUE: Option \"foo\" is a message. "
+ "To set the entire message, use syntax like "
+ "\"foo = { <proto text format> }\". To set fields within it, use "
+ "syntax like \"foo.foo = value\".\n");
+}
+
+TEST_F(ValidationErrorTest, AggregateValueParseError) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ EmbedAggregateValue("aggregate_value: \"1+2\""),
+ "foo.proto: foo.proto: OPTION_VALUE: Error while parsing option "
+ "value for \"foo\": Expected identifier, got: 1\n");
+}
+
+TEST_F(ValidationErrorTest, AggregateValueUnknownFields) {
+ BuildDescriptorMessagesInTestPool();
+
+ BuildFileWithErrors(
+ EmbedAggregateValue("aggregate_value: \"x:100\""),
+ "foo.proto: foo.proto: OPTION_VALUE: Error while parsing option "
+ "value for \"foo\": Message type \"Foo\" has no field named \"x\".\n");
+}
+
+TEST_F(ValidationErrorTest, NotLiteImportsLite) {
+ BuildFile(
+ "name: \"bar.proto\" "
+ "options { optimize_for: LITE_RUNTIME } ");
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"bar.proto\" ",
+
+ "foo.proto: foo.proto: OTHER: Files that do not use optimize_for = "
+ "LITE_RUNTIME cannot import files which do use this option. This file "
+ "is not lite, but it imports \"bar.proto\" which is.\n");
+}
+
+TEST_F(ValidationErrorTest, LiteExtendsNotLite) {
+ BuildFile(
+ "name: \"bar.proto\" "
+ "message_type: {"
+ " name: \"Bar\""
+ " extension_range { start: 1 end: 1000 }"
+ "}");
+
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "dependency: \"bar.proto\" "
+ "options { optimize_for: LITE_RUNTIME } "
+ "extension { name: \"ext\" number: 123 label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 extendee: \"Bar\" }",
+
+ "foo.proto: ext: EXTENDEE: Extensions to non-lite types can only be "
+ "declared in non-lite files. Note that you cannot extend a non-lite "
+ "type to contain a lite type, but the reverse is allowed.\n");
+}
+
+TEST_F(ValidationErrorTest, NoLiteServices) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "options {"
+ " optimize_for: LITE_RUNTIME"
+ " cc_generic_services: true"
+ " java_generic_services: true"
+ "} "
+ "service { name: \"Foo\" }",
+
+ "foo.proto: Foo: NAME: Files with optimize_for = LITE_RUNTIME cannot "
+ "define services unless you set both options cc_generic_services and "
+ "java_generic_sevices to false.\n");
+
+ BuildFile(
+ "name: \"bar.proto\" "
+ "options {"
+ " optimize_for: LITE_RUNTIME"
+ " cc_generic_services: false"
+ " java_generic_services: false"
+ "} "
+ "service { name: \"Bar\" }");
+}
+
+TEST_F(ValidationErrorTest, RollbackAfterError) {
+ // Build a file which contains every kind of construct but references an
+ // undefined type. All these constructs will be added to the symbol table
+ // before the undefined type error is noticed. The DescriptorPool will then
+ // have to roll everything back.
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_OPTIONAL type:TYPE_INT32 number:1 }"
+ "} "
+ "enum_type {"
+ " name: \"TestEnum\""
+ " value { name:\"BAR\" number:1 }"
+ "} "
+ "service {"
+ " name: \"TestService\""
+ " method {"
+ " name: \"Baz\""
+ " input_type: \"NoSuchType\"" // error
+ " output_type: \"TestMessage\""
+ " }"
+ "}",
+
+ "foo.proto: TestService.Baz: INPUT_TYPE: \"NoSuchType\" is not defined.\n"
+ );
+
+ // Make sure that if we build the same file again with the error fixed,
+ // it works. If the above rollback was incomplete, then some symbols will
+ // be left defined, and this second attempt will fail since it tries to
+ // re-define the same symbols.
+ BuildFile(
+ "name: \"foo.proto\" "
+ "message_type {"
+ " name: \"TestMessage\""
+ " field { name:\"foo\" label:LABEL_OPTIONAL type:TYPE_INT32 number:1 }"
+ "} "
+ "enum_type {"
+ " name: \"TestEnum\""
+ " value { name:\"BAR\" number:1 }"
+ "} "
+ "service {"
+ " name: \"TestService\""
+ " method { name:\"Baz\""
+ " input_type:\"TestMessage\""
+ " output_type:\"TestMessage\" }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest, ErrorsReportedToLogError) {
+ // Test that errors are reported to GOOGLE_LOG(ERROR) if no error collector is
+ // provided.
+
+ FileDescriptorProto file_proto;
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: \"foo.proto\" "
+ "message_type { name: \"Foo\" } "
+ "message_type { name: \"Foo\" } ",
+ &file_proto));
+
+ vector<string> errors;
+
+ {
+ ScopedMemoryLog log;
+ EXPECT_TRUE(pool_.BuildFile(file_proto) == NULL);
+ errors = log.GetMessages(ERROR);
+ }
+
+ ASSERT_EQ(2, errors.size());
+
+ EXPECT_EQ("Invalid proto descriptor for file \"foo.proto\":", errors[0]);
+ EXPECT_EQ(" Foo: \"Foo\" is already defined.", errors[1]);
+}
+
+TEST_F(ValidationErrorTest, DisallowEnumAlias) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type {"
+ " name: \"Bar\""
+ " value { name:\"ENUM_A\" number:0 }"
+ " value { name:\"ENUM_B\" number:0 }"
+ "}",
+ "foo.proto: Bar: NUMBER: "
+ "\"ENUM_B\" uses the same enum value as \"ENUM_A\". "
+ "If this is intended, set 'option allow_alias = true;' to the enum "
+ "definition.\n");
+}
+
+TEST_F(ValidationErrorTest, AllowEnumAlias) {
+ BuildFile(
+ "name: \"foo.proto\" "
+ "enum_type {"
+ " name: \"Bar\""
+ " value { name:\"ENUM_A\" number:0 }"
+ " value { name:\"ENUM_B\" number:0 }"
+ " options { allow_alias: true }"
+ "}");
+}
+
+TEST_F(ValidationErrorTest, UnusedImportWarning) {
+ pool_.AddUnusedImportTrackFile("bar.proto");
+ BuildFile(
+ "name: \"bar.proto\" "
+ "message_type { name: \"Bar\" }");
+
+ pool_.AddUnusedImportTrackFile("base.proto");
+ BuildFile(
+ "name: \"base.proto\" "
+ "message_type { name: \"Base\" }");
+
+ pool_.AddUnusedImportTrackFile("baz.proto");
+ BuildFile(
+ "name: \"baz.proto\" "
+ "message_type { name: \"Baz\" }");
+
+ pool_.AddUnusedImportTrackFile("public.proto");
+ BuildFile(
+ "name: \"public.proto\" "
+ "dependency: \"bar.proto\""
+ "public_dependency: 0");
+
+ // // forward.proto
+ // import "base.proto" // No warning: Base message is used.
+ // import "bar.proto" // Will log a warning.
+ // import public "baz.proto" // No warning: Do not track import public.
+ // import "public.proto" // No warning: public.proto has import public.
+ // message Forward {
+ // optional Base base = 1;
+ // }
+ //
+ pool_.AddUnusedImportTrackFile("forward.proto");
+ BuildFileWithWarnings(
+ "name: \"forward.proto\""
+ "dependency: \"base.proto\""
+ "dependency: \"bar.proto\""
+ "dependency: \"baz.proto\""
+ "dependency: \"public.proto\""
+ "public_dependency: 2 "
+ "message_type {"
+ " name: \"Forward\""
+ " field { name:\"base\" number:1 label:LABEL_OPTIONAL type_name:\"Base\" }"
+ "}",
+ "forward.proto: bar.proto: OTHER: Import bar.proto but not used.\n");
+}
+
+namespace {
+void FillValidMapEntry(FileDescriptorProto* file_proto) {
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "name: 'foo.proto' "
+ "message_type { "
+ " name: 'Foo' "
+ " field { "
+ " name: 'foo_map' number: 1 label:LABEL_REPEATED "
+ " type_name: 'FooMapEntry' "
+ " } "
+ " nested_type { "
+ " name: 'FooMapEntry' "
+ " options { map_entry: true } "
+ " field { "
+ " name: 'key' number: 1 type:TYPE_INT32 label:LABEL_OPTIONAL "
+ " } "
+ " field { "
+ " name: 'value' number: 2 type:TYPE_INT32 label:LABEL_OPTIONAL "
+ " } "
+ " } "
+ "} "
+ "message_type { "
+ " name: 'Bar' "
+ " extension_range { start: 1 end: 10 }"
+ "} ",
+ file_proto));
+}
+static const char* kMapEntryErrorMessage =
+ "foo.proto: Foo.foo_map: OTHER: map_entry should not be set explicitly. "
+ "Use map<KeyType, ValueType> instead.\n";
+static const char* kMapEntryKeyTypeErrorMessage =
+ "foo.proto: Foo.foo_map: TYPE: Key in map fields cannot be float/double, "
+ "bytes or message types.\n";
+
+} // namespace
+
+TEST_F(ValidationErrorTest, MapEntryBase) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ BuildFile(file_proto.DebugString());
+}
+
+TEST_F(ValidationErrorTest, MapEntryExtensionRange) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "extension_range { "
+ " start: 10 end: 20 "
+ "} ",
+ file_proto.mutable_message_type(0)->mutable_nested_type(0));
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryExtension) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "extension { "
+ " name: 'foo_ext' extendee: '.Bar' number: 5"
+ "} ",
+ file_proto.mutable_message_type(0)->mutable_nested_type(0));
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryNestedType) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "nested_type { "
+ " name: 'Bar' "
+ "} ",
+ file_proto.mutable_message_type(0)->mutable_nested_type(0));
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryEnumTypes) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "enum_type { "
+ " name: 'BarEnum' "
+ " value { name: 'BAR_BAR' number:0 } "
+ "} ",
+ file_proto.mutable_message_type(0)->mutable_nested_type(0));
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryExtraField) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "field { "
+ " name: 'other_field' "
+ " label: LABEL_OPTIONAL "
+ " type: TYPE_INT32 "
+ " number: 3 "
+ "} ",
+ file_proto.mutable_message_type(0)->mutable_nested_type(0));
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryMessageName) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ file_proto.mutable_message_type(0)->mutable_nested_type(0)->set_name(
+ "OtherMapEntry");
+ file_proto.mutable_message_type(0)->mutable_field(0)->set_type_name(
+ "OtherMapEntry");
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryNoneRepeatedMapEntry) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ file_proto.mutable_message_type(0)->mutable_field(0)->set_label(
+ FieldDescriptorProto::LABEL_OPTIONAL);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryDifferentContainingType) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ // Move the nested MapEntry message into the top level, which should not pass
+ // the validation.
+ file_proto.mutable_message_type()->AddAllocated(
+ file_proto.mutable_message_type(0)->mutable_nested_type()->ReleaseLast());
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryKeyName) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->set_name("Key");
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryKeyLabel) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->set_label(FieldDescriptorProto::LABEL_REQUIRED);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryKeyNumber) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->set_number(3);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryValueName) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* value = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(1);
+ value->set_name("Value");
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryValueLabel) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* value = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(1);
+ value->set_label(FieldDescriptorProto::LABEL_REQUIRED);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryValueNumber) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* value = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(1);
+ value->set_number(3);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryKeyTypeFloat) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->set_type(FieldDescriptorProto::TYPE_FLOAT);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryKeyTypeErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryKeyTypeDouble) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->set_type(FieldDescriptorProto::TYPE_DOUBLE);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryKeyTypeErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryKeyTypeBytes) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->set_type(FieldDescriptorProto::TYPE_BYTES);
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryKeyTypeErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryKeyTypeEnum) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->clear_type();
+ key->set_type_name("BarEnum");
+ EnumDescriptorProto* enum_proto = file_proto.add_enum_type();
+ enum_proto->set_name("BarEnum");
+ EnumValueDescriptorProto* enum_value_proto = enum_proto->add_value();
+ enum_value_proto->set_name("BAR_VALUE0");
+ enum_value_proto->set_number(0);
+ BuildFileWithErrors(file_proto.DebugString(),
+ "foo.proto: Foo.foo_map: TYPE: Key in map fields cannot "
+ "be enum types.\n");
+ // Enum keys are not allowed in proto3 as well.
+ // Get rid of extensions for proto3 to make it proto3 compatible.
+ file_proto.mutable_message_type()->RemoveLast();
+ file_proto.set_syntax("proto3");
+ BuildFileWithErrors(file_proto.DebugString(),
+ "foo.proto: Foo.foo_map: TYPE: Key in map fields cannot "
+ "be enum types.\n");
+}
+
+
+TEST_F(ValidationErrorTest, MapEntryKeyTypeMessage) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ FieldDescriptorProto* key = file_proto.mutable_message_type(0)
+ ->mutable_nested_type(0)
+ ->mutable_field(0);
+ key->clear_type();
+ key->set_type_name(".Bar");
+ BuildFileWithErrors(file_proto.DebugString(), kMapEntryKeyTypeErrorMessage);
+}
+
+TEST_F(ValidationErrorTest, MapEntryConflictsWithField) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "field { "
+ " name: 'FooMapEntry' "
+ " type: TYPE_INT32 "
+ " label: LABEL_OPTIONAL "
+ " number: 100 "
+ "}",
+ file_proto.mutable_message_type(0));
+ BuildFileWithErrors(
+ file_proto.DebugString(),
+ "foo.proto: Foo.FooMapEntry: NAME: \"FooMapEntry\" is already defined in "
+ "\"Foo\".\n"
+ "foo.proto: Foo.foo_map: TYPE: \"FooMapEntry\" is not defined.\n"
+ "foo.proto: Foo: NAME: Expanded map entry type FooMapEntry conflicts "
+ "with an existing field.\n");
+}
+
+TEST_F(ValidationErrorTest, MapEntryConflictsWithMessage) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "nested_type { "
+ " name: 'FooMapEntry' "
+ "}",
+ file_proto.mutable_message_type(0));
+ BuildFileWithErrors(
+ file_proto.DebugString(),
+ "foo.proto: Foo.FooMapEntry: NAME: \"FooMapEntry\" is already defined in "
+ "\"Foo\".\n"
+ "foo.proto: Foo: NAME: Expanded map entry type FooMapEntry conflicts "
+ "with an existing nested message type.\n");
+}
+
+TEST_F(ValidationErrorTest, MapEntryConflictsWithEnum) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "enum_type { "
+ " name: 'FooMapEntry' "
+ " value { name: 'ENTRY_FOO' number: 0 }"
+ "}",
+ file_proto.mutable_message_type(0));
+ BuildFileWithErrors(
+ file_proto.DebugString(),
+ "foo.proto: Foo.FooMapEntry: NAME: \"FooMapEntry\" is already defined in "
+ "\"Foo\".\n"
+ "foo.proto: Foo: NAME: Expanded map entry type FooMapEntry conflicts "
+ "with an existing enum type.\n");
+}
+
+TEST_F(ValidationErrorTest, MapEntryConflictsWithOneof) {
+ FileDescriptorProto file_proto;
+ FillValidMapEntry(&file_proto);
+ TextFormat::MergeFromString(
+ "oneof_decl { "
+ " name: 'FooMapEntry' "
+ "}"
+ "field { "
+ " name: 'int_field' "
+ " type: TYPE_INT32 "
+ " label: LABEL_OPTIONAL "
+ " oneof_index: 0 "
+ " number: 100 "
+ "} ",
+ file_proto.mutable_message_type(0));
+ BuildFileWithErrors(
+ file_proto.DebugString(),
+ "foo.proto: Foo.FooMapEntry: NAME: \"FooMapEntry\" is already defined in "
+ "\"Foo\".\n"
+ "foo.proto: Foo.foo_map: TYPE: \"FooMapEntry\" is not defined.\n"
+ "foo.proto: Foo: NAME: Expanded map entry type FooMapEntry conflicts "
+ "with an existing oneof type.\n");
+}
+
+TEST_F(ValidationErrorTest, MapEntryUsesNoneZeroEnumDefaultValue) {
+ BuildFileWithErrors(
+ "name: \"foo.proto\" "
+ "enum_type {"
+ " name: \"Bar\""
+ " value { name:\"ENUM_A\" number:1 }"
+ " value { name:\"ENUM_B\" number:2 }"
+ "}"
+ "message_type {"
+ " name: 'Foo' "
+ " field { "
+ " name: 'foo_map' number: 1 label:LABEL_REPEATED "
+ " type_name: 'FooMapEntry' "
+ " } "
+ " nested_type { "
+ " name: 'FooMapEntry' "
+ " options { map_entry: true } "
+ " field { "
+ " name: 'key' number: 1 type:TYPE_INT32 label:LABEL_OPTIONAL "
+ " } "
+ " field { "
+ " name: 'value' number: 2 type_name:\"Bar\" label:LABEL_OPTIONAL "
+ " } "
+ " } "
+ "}",
+ "foo.proto: Foo.foo_map: "
+ "TYPE: Enum value in map must define 0 as the first value.\n");
+}
+
+TEST_F(ValidationErrorTest, Proto3RequiredFields) {
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " field { name:'foo' number:1 label:LABEL_REQUIRED type:TYPE_INT32 } "
+ "}",
+ "foo.proto: Foo.foo: OTHER: Required fields are not allowed in "
+ "proto3.\n");
+
+ // applied to nested types as well.
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " nested_type { "
+ " name : 'Bar' "
+ " field { name:'bar' number:1 label:LABEL_REQUIRED type:TYPE_INT32 } "
+ " } "
+ "}",
+ "foo.proto: Foo.Bar.bar: OTHER: Required fields are not allowed in "
+ "proto3.\n");
+
+ // optional and repeated fields are OK.
+ BuildFile(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " field { name:'foo' number:1 label:LABEL_OPTIONAL type:TYPE_INT32 } "
+ " field { name:'bar' number:2 label:LABEL_REPEATED type:TYPE_INT32 } "
+ "}");
+}
+
+TEST_F(ValidationErrorTest, ValidateProto3DefaultValue) {
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " field { name:'foo' number:1 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " default_value: '1' }"
+ "}",
+ "foo.proto: Foo.foo: OTHER: Explicit default values are not allowed in "
+ "proto3.\n");
+
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " nested_type { "
+ " name : 'Bar' "
+ " field { name:'bar' number:1 label:LABEL_OPTIONAL type:TYPE_INT32 "
+ " default_value: '1' }"
+ " } "
+ "}",
+ "foo.proto: Foo.Bar.bar: OTHER: Explicit default values are not allowed "
+ "in proto3.\n");
+}
+
+TEST_F(ValidationErrorTest, ValidateProto3ExtensionRange) {
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " field { name:'foo' number:1 label:LABEL_OPTIONAL type:TYPE_INT32 } "
+ " extension_range { start:10 end:100 } "
+ "}",
+ "foo.proto: Foo: OTHER: Extension ranges are not allowed in "
+ "proto3.\n");
+
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " nested_type { "
+ " name : 'Bar' "
+ " field { name:'bar' number:1 label:LABEL_OPTIONAL type:TYPE_INT32 } "
+ " extension_range { start:10 end:100 } "
+ " } "
+ "}",
+ "foo.proto: Foo.Bar: OTHER: Extension ranges are not allowed in "
+ "proto3.\n");
+}
+
+TEST_F(ValidationErrorTest, ValidateProto3MessageSetWireFormat) {
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " options { message_set_wire_format: true } "
+ "}",
+ "foo.proto: Foo: OTHER: MessageSet is not supported "
+ "in proto3.\n");
+}
+
+TEST_F(ValidationErrorTest, ValidateProto3Enum) {
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "enum_type { "
+ " name: 'FooEnum' "
+ " value { name: 'FOO_FOO' number:1 } "
+ "}",
+ "foo.proto: FooEnum: OTHER: The first enum value must be "
+ "zero in proto3.\n");
+
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " enum_type { "
+ " name: 'FooEnum' "
+ " value { name: 'FOO_FOO' number:1 } "
+ " } "
+ "}",
+ "foo.proto: Foo.FooEnum: OTHER: The first enum value must be "
+ "zero in proto3.\n");
+
+ // valid case.
+ BuildFile(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "enum_type { "
+ " name: 'FooEnum' "
+ " value { name: 'FOO_FOO' number:0 } "
+ "}");
+}
+
+TEST_F(ValidationErrorTest, ValidateProto3Group) {
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " nested_type { "
+ " name: 'FooGroup' "
+ " } "
+ " field { name:'foo_group' number: 1 label:LABEL_OPTIONAL "
+ " type: TYPE_GROUP type_name:'FooGroup' } "
+ "}",
+ "foo.proto: Foo.foo_group: TYPE: Groups are not supported in proto3 "
+ "syntax.\n");
+}
+
+
+TEST_F(ValidationErrorTest, ValidateProto3EnumFromProto2) {
+ // Define an enum in a proto2 file.
+ BuildFile(
+ "name: 'foo.proto' "
+ "package: 'foo' "
+ "syntax: 'proto2' "
+ "enum_type { "
+ " name: 'FooEnum' "
+ " value { name: 'DEFAULT_OPTION' number:0 } "
+ "}");
+
+ // Now try to refer to it. (All tests in the fixture use the same pool, so we
+ // can refer to the enum above in this definition.)
+ BuildFileWithErrors(
+ "name: 'bar.proto' "
+ "dependency: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type { "
+ " name: 'Foo' "
+ " field { name:'bar' number:1 label:LABEL_OPTIONAL type:TYPE_ENUM "
+ " type_name: 'foo.FooEnum' }"
+ "}",
+ "bar.proto: Foo.bar: TYPE: Enum type \"foo.FooEnum\" is not a proto3 "
+ "enum, but is used in \"Foo\" which is a proto3 message type.\n");
+}
+
+TEST_F(ValidationErrorTest, ValidateProto3Extension) {
+ // Valid for options.
+ DescriptorPool pool;
+ FileDescriptorProto file_proto;
+ // Add "google/protobuf/descriptor.proto".
+ FileDescriptorProto::descriptor()->file()->CopyTo(&file_proto);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+ // Add "foo.proto":
+ // import "google/protobuf/descriptor.proto";
+ // extend google.protobuf.FieldOptions {
+ // optional int32 option1 = 1000;
+ // }
+ file_proto.Clear();
+ file_proto.set_name("foo.proto");
+ file_proto.set_syntax("proto3");
+ file_proto.add_dependency("google/protobuf/descriptor.proto");
+ AddExtension(&file_proto, "google.protobuf.FieldOptions", "option1", 1000,
+ FieldDescriptorProto::LABEL_OPTIONAL,
+ FieldDescriptorProto::TYPE_INT32);
+ ASSERT_TRUE(pool.BuildFile(file_proto) != NULL);
+
+ // Copy and change the package of the descriptor.proto
+ BuildFile(
+ "name: 'google.protobuf.proto' "
+ "syntax: 'proto2' "
+ "message_type { "
+ " name: 'Container' extension_range { start: 1 end: 1000 } "
+ "}");
+ BuildFileWithErrors(
+ "name: 'bar.proto' "
+ "syntax: 'proto3' "
+ "dependency: 'google.protobuf.proto' "
+ "extension { "
+ " name: 'bar' number: 1 label: LABEL_OPTIONAL type: TYPE_INT32 "
+ " extendee: 'Container' "
+ "}",
+ "bar.proto: bar: OTHER: Extensions in proto3 are only allowed for "
+ "defining options.\n");
+}
+
+// Test that field names that may conflict in JSON is not allowed by protoc.
+TEST_F(ValidationErrorTest, ValidateProto3JsonName) {
+ // The comparison is case-insensitive.
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type {"
+ " name: 'Foo'"
+ " field { name:'name' number:1 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name:'Name' number:2 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+ "foo.proto: Foo: OTHER: The JSON camel-case name of field \"Name\" "
+ "conflicts with field \"name\". This is not allowed in proto3.\n");
+ // Underscores are ignored.
+ BuildFileWithErrors(
+ "name: 'foo.proto' "
+ "syntax: 'proto3' "
+ "message_type {"
+ " name: 'Foo'"
+ " field { name:'ab' number:1 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ " field { name:'_a__b_' number:2 label:LABEL_OPTIONAL type:TYPE_INT32 }"
+ "}",
+ "foo.proto: Foo: OTHER: The JSON camel-case name of field \"_a__b_\" "
+ "conflicts with field \"ab\". This is not allowed in proto3.\n");
+}
+
+// ===================================================================
+// DescriptorDatabase
+
+static void AddToDatabase(SimpleDescriptorDatabase* database,
+ const char* file_text) {
+ FileDescriptorProto file_proto;
+ EXPECT_TRUE(TextFormat::ParseFromString(file_text, &file_proto));
+ database->Add(file_proto);
+}
+
+class DatabaseBackedPoolTest : public testing::Test {
+ protected:
+ DatabaseBackedPoolTest() {}
+
+ SimpleDescriptorDatabase database_;
+
+ virtual void SetUp() {
+ AddToDatabase(&database_,
+ "name: 'foo.proto' "
+ "message_type { name:'Foo' extension_range { start: 1 end: 100 } } "
+ "enum_type { name:'TestEnum' value { name:'DUMMY' number:0 } } "
+ "service { name:'TestService' } ");
+ AddToDatabase(&database_,
+ "name: 'bar.proto' "
+ "dependency: 'foo.proto' "
+ "message_type { name:'Bar' } "
+ "extension { name:'foo_ext' extendee: '.Foo' number:5 "
+ " label:LABEL_OPTIONAL type:TYPE_INT32 } ");
+ // Baz has an undeclared dependency on Foo.
+ AddToDatabase(&database_,
+ "name: 'baz.proto' "
+ "message_type { "
+ " name:'Baz' "
+ " field { name:'foo' number:1 label:LABEL_OPTIONAL type_name:'Foo' } "
+ "}");
+ }
+
+ // We can't inject a file containing errors into a DescriptorPool, so we
+ // need an actual mock DescriptorDatabase to test errors.
+ class ErrorDescriptorDatabase : public DescriptorDatabase {
+ public:
+ ErrorDescriptorDatabase() {}
+ ~ErrorDescriptorDatabase() {}
+
+ // implements DescriptorDatabase ---------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output) {
+ // error.proto and error2.proto cyclically import each other.
+ if (filename == "error.proto") {
+ output->Clear();
+ output->set_name("error.proto");
+ output->add_dependency("error2.proto");
+ return true;
+ } else if (filename == "error2.proto") {
+ output->Clear();
+ output->set_name("error2.proto");
+ output->add_dependency("error.proto");
+ return true;
+ } else {
+ return false;
+ }
+ }
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output) {
+ return false;
+ }
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ return false;
+ }
+ };
+
+ // A DescriptorDatabase that counts how many times each method has been
+ // called and forwards to some other DescriptorDatabase.
+ class CallCountingDatabase : public DescriptorDatabase {
+ public:
+ CallCountingDatabase(DescriptorDatabase* wrapped_db)
+ : wrapped_db_(wrapped_db) {
+ Clear();
+ }
+ ~CallCountingDatabase() {}
+
+ DescriptorDatabase* wrapped_db_;
+
+ int call_count_;
+
+ void Clear() {
+ call_count_ = 0;
+ }
+
+ // implements DescriptorDatabase ---------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output) {
+ ++call_count_;
+ return wrapped_db_->FindFileByName(filename, output);
+ }
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output) {
+ ++call_count_;
+ return wrapped_db_->FindFileContainingSymbol(symbol_name, output);
+ }
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ ++call_count_;
+ return wrapped_db_->FindFileContainingExtension(
+ containing_type, field_number, output);
+ }
+ };
+
+ // A DescriptorDatabase which falsely always returns foo.proto when searching
+ // for any symbol or extension number. This shouldn't cause the
+ // DescriptorPool to reload foo.proto if it is already loaded.
+ class FalsePositiveDatabase : public DescriptorDatabase {
+ public:
+ FalsePositiveDatabase(DescriptorDatabase* wrapped_db)
+ : wrapped_db_(wrapped_db) {}
+ ~FalsePositiveDatabase() {}
+
+ DescriptorDatabase* wrapped_db_;
+
+ // implements DescriptorDatabase ---------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output) {
+ return wrapped_db_->FindFileByName(filename, output);
+ }
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output) {
+ return FindFileByName("foo.proto", output);
+ }
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ return FindFileByName("foo.proto", output);
+ }
+ };
+};
+
+TEST_F(DatabaseBackedPoolTest, FindFileByName) {
+ DescriptorPool pool(&database_);
+
+ const FileDescriptor* foo = pool.FindFileByName("foo.proto");
+ ASSERT_TRUE(foo != NULL);
+ EXPECT_EQ("foo.proto", foo->name());
+ ASSERT_EQ(1, foo->message_type_count());
+ EXPECT_EQ("Foo", foo->message_type(0)->name());
+
+ EXPECT_EQ(foo, pool.FindFileByName("foo.proto"));
+
+ EXPECT_TRUE(pool.FindFileByName("no_such_file.proto") == NULL);
+}
+
+TEST_F(DatabaseBackedPoolTest, FindDependencyBeforeDependent) {
+ DescriptorPool pool(&database_);
+
+ const FileDescriptor* foo = pool.FindFileByName("foo.proto");
+ ASSERT_TRUE(foo != NULL);
+ EXPECT_EQ("foo.proto", foo->name());
+ ASSERT_EQ(1, foo->message_type_count());
+ EXPECT_EQ("Foo", foo->message_type(0)->name());
+
+ const FileDescriptor* bar = pool.FindFileByName("bar.proto");
+ ASSERT_TRUE(bar != NULL);
+ EXPECT_EQ("bar.proto", bar->name());
+ ASSERT_EQ(1, bar->message_type_count());
+ EXPECT_EQ("Bar", bar->message_type(0)->name());
+
+ ASSERT_EQ(1, bar->dependency_count());
+ EXPECT_EQ(foo, bar->dependency(0));
+}
+
+TEST_F(DatabaseBackedPoolTest, FindDependentBeforeDependency) {
+ DescriptorPool pool(&database_);
+
+ const FileDescriptor* bar = pool.FindFileByName("bar.proto");
+ ASSERT_TRUE(bar != NULL);
+ EXPECT_EQ("bar.proto", bar->name());
+ ASSERT_EQ(1, bar->message_type_count());
+ ASSERT_EQ("Bar", bar->message_type(0)->name());
+
+ const FileDescriptor* foo = pool.FindFileByName("foo.proto");
+ ASSERT_TRUE(foo != NULL);
+ EXPECT_EQ("foo.proto", foo->name());
+ ASSERT_EQ(1, foo->message_type_count());
+ ASSERT_EQ("Foo", foo->message_type(0)->name());
+
+ ASSERT_EQ(1, bar->dependency_count());
+ EXPECT_EQ(foo, bar->dependency(0));
+}
+
+TEST_F(DatabaseBackedPoolTest, FindFileContainingSymbol) {
+ DescriptorPool pool(&database_);
+
+ const FileDescriptor* file = pool.FindFileContainingSymbol("Foo");
+ ASSERT_TRUE(file != NULL);
+ EXPECT_EQ("foo.proto", file->name());
+ EXPECT_EQ(file, pool.FindFileByName("foo.proto"));
+
+ EXPECT_TRUE(pool.FindFileContainingSymbol("NoSuchSymbol") == NULL);
+}
+
+TEST_F(DatabaseBackedPoolTest, FindMessageTypeByName) {
+ DescriptorPool pool(&database_);
+
+ const Descriptor* type = pool.FindMessageTypeByName("Foo");
+ ASSERT_TRUE(type != NULL);
+ EXPECT_EQ("Foo", type->name());
+ EXPECT_EQ(type->file(), pool.FindFileByName("foo.proto"));
+
+ EXPECT_TRUE(pool.FindMessageTypeByName("NoSuchType") == NULL);
+}
+
+TEST_F(DatabaseBackedPoolTest, FindExtensionByNumber) {
+ DescriptorPool pool(&database_);
+
+ const Descriptor* foo = pool.FindMessageTypeByName("Foo");
+ ASSERT_TRUE(foo != NULL);
+
+ const FieldDescriptor* extension = pool.FindExtensionByNumber(foo, 5);
+ ASSERT_TRUE(extension != NULL);
+ EXPECT_EQ("foo_ext", extension->name());
+ EXPECT_EQ(extension->file(), pool.FindFileByName("bar.proto"));
+
+ EXPECT_TRUE(pool.FindExtensionByNumber(foo, 12) == NULL);
+}
+
+TEST_F(DatabaseBackedPoolTest, FindAllExtensions) {
+ DescriptorPool pool(&database_);
+
+ const Descriptor* foo = pool.FindMessageTypeByName("Foo");
+
+ for (int i = 0; i < 2; ++i) {
+ // Repeat the lookup twice, to check that we get consistent
+ // results despite the fallback database lookup mutating the pool.
+ vector<const FieldDescriptor*> extensions;
+ pool.FindAllExtensions(foo, &extensions);
+ ASSERT_EQ(1, extensions.size());
+ EXPECT_EQ(5, extensions[0]->number());
+ }
+}
+
+TEST_F(DatabaseBackedPoolTest, ErrorWithoutErrorCollector) {
+ ErrorDescriptorDatabase error_database;
+ DescriptorPool pool(&error_database);
+
+ vector<string> errors;
+
+ {
+ ScopedMemoryLog log;
+ EXPECT_TRUE(pool.FindFileByName("error.proto") == NULL);
+ errors = log.GetMessages(ERROR);
+ }
+
+ EXPECT_FALSE(errors.empty());
+}
+
+TEST_F(DatabaseBackedPoolTest, ErrorWithErrorCollector) {
+ ErrorDescriptorDatabase error_database;
+ MockErrorCollector error_collector;
+ DescriptorPool pool(&error_database, &error_collector);
+
+ EXPECT_TRUE(pool.FindFileByName("error.proto") == NULL);
+ EXPECT_EQ(
+ "error.proto: error.proto: OTHER: File recursively imports itself: "
+ "error.proto -> error2.proto -> error.proto\n"
+ "error2.proto: error2.proto: OTHER: Import \"error.proto\" was not "
+ "found or had errors.\n"
+ "error.proto: error.proto: OTHER: Import \"error2.proto\" was not "
+ "found or had errors.\n",
+ error_collector.text_);
+}
+
+TEST_F(DatabaseBackedPoolTest, UndeclaredDependencyOnUnbuiltType) {
+ // Check that we find and report undeclared dependencies on types that exist
+ // in the descriptor database but that have not not been built yet.
+ MockErrorCollector error_collector;
+ DescriptorPool pool(&database_, &error_collector);
+ EXPECT_TRUE(pool.FindMessageTypeByName("Baz") == NULL);
+ EXPECT_EQ(
+ "baz.proto: Baz.foo: TYPE: \"Foo\" seems to be defined in \"foo.proto\", "
+ "which is not imported by \"baz.proto\". To use it here, please add "
+ "the necessary import.\n",
+ error_collector.text_);
+}
+
+TEST_F(DatabaseBackedPoolTest, RollbackAfterError) {
+ // Make sure that all traces of bad types are removed from the pool. This used
+ // to be b/4529436, due to the fact that a symbol resolution failure could
+ // potentially cause another file to be recursively built, which would trigger
+ // a checkpoint _past_ possibly invalid symbols.
+ // Baz is defined in the database, but the file is invalid because it is
+ // missing a necessary import.
+ DescriptorPool pool(&database_);
+ EXPECT_TRUE(pool.FindMessageTypeByName("Baz") == NULL);
+ // Make sure that searching again for the file or the type fails.
+ EXPECT_TRUE(pool.FindFileByName("baz.proto") == NULL);
+ EXPECT_TRUE(pool.FindMessageTypeByName("Baz") == NULL);
+}
+
+TEST_F(DatabaseBackedPoolTest, UnittestProto) {
+ // Try to load all of unittest.proto from a DescriptorDatabase. This should
+ // thoroughly test all paths through DescriptorBuilder to insure that there
+ // are no deadlocking problems when pool_->mutex_ is non-NULL.
+ const FileDescriptor* original_file =
+ protobuf_unittest::TestAllTypes::descriptor()->file();
+
+ DescriptorPoolDatabase database(*DescriptorPool::generated_pool());
+ DescriptorPool pool(&database);
+ const FileDescriptor* file_from_database =
+ pool.FindFileByName(original_file->name());
+
+ ASSERT_TRUE(file_from_database != NULL);
+
+ FileDescriptorProto original_file_proto;
+ original_file->CopyTo(&original_file_proto);
+
+ FileDescriptorProto file_from_database_proto;
+ file_from_database->CopyTo(&file_from_database_proto);
+
+ EXPECT_EQ(original_file_proto.DebugString(),
+ file_from_database_proto.DebugString());
+
+ // Also verify that CopyTo() did not omit any information.
+ EXPECT_EQ(original_file->DebugString(),
+ file_from_database->DebugString());
+}
+
+TEST_F(DatabaseBackedPoolTest, DoesntRetryDbUnnecessarily) {
+ // Searching for a child of an existing descriptor should never fall back
+ // to the DescriptorDatabase even if it isn't found, because we know all
+ // children are already loaded.
+ CallCountingDatabase call_counter(&database_);
+ DescriptorPool pool(&call_counter);
+
+ const FileDescriptor* file = pool.FindFileByName("foo.proto");
+ ASSERT_TRUE(file != NULL);
+ const Descriptor* foo = pool.FindMessageTypeByName("Foo");
+ ASSERT_TRUE(foo != NULL);
+ const EnumDescriptor* test_enum = pool.FindEnumTypeByName("TestEnum");
+ ASSERT_TRUE(test_enum != NULL);
+ const ServiceDescriptor* test_service = pool.FindServiceByName("TestService");
+ ASSERT_TRUE(test_service != NULL);
+
+ EXPECT_NE(0, call_counter.call_count_);
+ call_counter.Clear();
+
+ EXPECT_TRUE(foo->FindFieldByName("no_such_field") == NULL);
+ EXPECT_TRUE(foo->FindExtensionByName("no_such_extension") == NULL);
+ EXPECT_TRUE(foo->FindNestedTypeByName("NoSuchMessageType") == NULL);
+ EXPECT_TRUE(foo->FindEnumTypeByName("NoSuchEnumType") == NULL);
+ EXPECT_TRUE(foo->FindEnumValueByName("NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(test_enum->FindValueByName("NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(test_service->FindMethodByName("NoSuchMethod") == NULL);
+
+ EXPECT_TRUE(file->FindMessageTypeByName("NoSuchMessageType") == NULL);
+ EXPECT_TRUE(file->FindEnumTypeByName("NoSuchEnumType") == NULL);
+ EXPECT_TRUE(file->FindEnumValueByName("NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(file->FindServiceByName("NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(file->FindExtensionByName("no_such_extension") == NULL);
+
+ EXPECT_TRUE(pool.FindFileContainingSymbol("Foo.no.such.field") == NULL);
+ EXPECT_TRUE(pool.FindFileContainingSymbol("Foo.no_such_field") == NULL);
+ EXPECT_TRUE(pool.FindMessageTypeByName("Foo.NoSuchMessageType") == NULL);
+ EXPECT_TRUE(pool.FindFieldByName("Foo.no_such_field") == NULL);
+ EXPECT_TRUE(pool.FindExtensionByName("Foo.no_such_extension") == NULL);
+ EXPECT_TRUE(pool.FindEnumTypeByName("Foo.NoSuchEnumType") == NULL);
+ EXPECT_TRUE(pool.FindEnumValueByName("Foo.NO_SUCH_VALUE") == NULL);
+ EXPECT_TRUE(pool.FindMethodByName("TestService.NoSuchMethod") == NULL);
+
+ EXPECT_EQ(0, call_counter.call_count_);
+}
+
+TEST_F(DatabaseBackedPoolTest, DoesntReloadFilesUncesessarily) {
+ // If FindFileContainingSymbol() or FindFileContainingExtension() return a
+ // file that is already in the DescriptorPool, it should not attempt to
+ // reload the file.
+ FalsePositiveDatabase false_positive_database(&database_);
+ MockErrorCollector error_collector;
+ DescriptorPool pool(&false_positive_database, &error_collector);
+
+ // First make sure foo.proto is loaded.
+ const Descriptor* foo = pool.FindMessageTypeByName("Foo");
+ ASSERT_TRUE(foo != NULL);
+
+ // Try inducing false positives.
+ EXPECT_TRUE(pool.FindMessageTypeByName("NoSuchSymbol") == NULL);
+ EXPECT_TRUE(pool.FindExtensionByNumber(foo, 22) == NULL);
+
+ // No errors should have been reported. (If foo.proto was incorrectly
+ // loaded multiple times, errors would have been reported.)
+ EXPECT_EQ("", error_collector.text_);
+}
+
+// DescriptorDatabase that attempts to induce exponentially-bad performance
+// in DescriptorPool. For every positive N, the database contains a file
+// fileN.proto, which defines a message MessageN, which contains fields of
+// type MessageK for all K in [0,N). Message0 is not defined anywhere
+// (file0.proto exists, but is empty), so every other file and message type
+// will fail to build.
+//
+// If the DescriptorPool is not careful to memoize errors, an attempt to
+// build a descriptor for MessageN can require O(2^N) time.
+class ExponentialErrorDatabase : public DescriptorDatabase {
+ public:
+ ExponentialErrorDatabase() {}
+ ~ExponentialErrorDatabase() {}
+
+ // implements DescriptorDatabase ---------------------------------
+ bool FindFileByName(const string& filename,
+ FileDescriptorProto* output) {
+ int file_num = -1;
+ FullMatch(filename, "file", ".proto", &file_num);
+ if (file_num > -1) {
+ return PopulateFile(file_num, output);
+ } else {
+ return false;
+ }
+ }
+ bool FindFileContainingSymbol(const string& symbol_name,
+ FileDescriptorProto* output) {
+ int file_num = -1;
+ FullMatch(symbol_name, "Message", "", &file_num);
+ if (file_num > 0) {
+ return PopulateFile(file_num, output);
+ } else {
+ return false;
+ }
+ }
+ bool FindFileContainingExtension(const string& containing_type,
+ int field_number,
+ FileDescriptorProto* output) {
+ return false;
+ }
+
+ private:
+ void FullMatch(const string& name,
+ const string& begin_with,
+ const string& end_with,
+ int* file_num) {
+ int begin_size = begin_with.size();
+ int end_size = end_with.size();
+ if (name.substr(0, begin_size) != begin_with ||
+ name.substr(name.size()- end_size, end_size) != end_with) {
+ return;
+ }
+ safe_strto32(name.substr(begin_size, name.size() - end_size - begin_size),
+ file_num);
+ }
+
+ bool PopulateFile(int file_num, FileDescriptorProto* output) {
+ using strings::Substitute;
+ GOOGLE_CHECK_GE(file_num, 0);
+ output->Clear();
+ output->set_name(Substitute("file$0.proto", file_num));
+ // file0.proto doesn't define Message0
+ if (file_num > 0) {
+ DescriptorProto* message = output->add_message_type();
+ message->set_name(Substitute("Message$0", file_num));
+ for (int i = 0; i < file_num; ++i) {
+ output->add_dependency(Substitute("file$0.proto", i));
+ FieldDescriptorProto* field = message->add_field();
+ field->set_name(Substitute("field$0", i));
+ field->set_number(i);
+ field->set_label(FieldDescriptorProto::LABEL_OPTIONAL);
+ field->set_type(FieldDescriptorProto::TYPE_MESSAGE);
+ field->set_type_name(Substitute("Message$0", i));
+ }
+ }
+ return true;
+ }
+};
+
+TEST_F(DatabaseBackedPoolTest, DoesntReloadKnownBadFiles) {
+ ExponentialErrorDatabase error_database;
+ DescriptorPool pool(&error_database);
+
+ GOOGLE_LOG(INFO) << "A timeout in this test probably indicates a real bug.";
+
+ EXPECT_TRUE(pool.FindFileByName("file40.proto") == NULL);
+ EXPECT_TRUE(pool.FindMessageTypeByName("Message40") == NULL);
+}
+
+TEST_F(DatabaseBackedPoolTest, DoesntFallbackOnWrongType) {
+ // If a lookup finds a symbol of the wrong type (e.g. we pass a type name
+ // to FindFieldByName()), we should fail fast, without checking the fallback
+ // database.
+ CallCountingDatabase call_counter(&database_);
+ DescriptorPool pool(&call_counter);
+
+ const FileDescriptor* file = pool.FindFileByName("foo.proto");
+ ASSERT_TRUE(file != NULL);
+ const Descriptor* foo = pool.FindMessageTypeByName("Foo");
+ ASSERT_TRUE(foo != NULL);
+ const EnumDescriptor* test_enum = pool.FindEnumTypeByName("TestEnum");
+ ASSERT_TRUE(test_enum != NULL);
+
+ EXPECT_NE(0, call_counter.call_count_);
+ call_counter.Clear();
+
+ EXPECT_TRUE(pool.FindMessageTypeByName("TestEnum") == NULL);
+ EXPECT_TRUE(pool.FindFieldByName("Foo") == NULL);
+ EXPECT_TRUE(pool.FindExtensionByName("Foo") == NULL);
+ EXPECT_TRUE(pool.FindEnumTypeByName("Foo") == NULL);
+ EXPECT_TRUE(pool.FindEnumValueByName("Foo") == NULL);
+ EXPECT_TRUE(pool.FindServiceByName("Foo") == NULL);
+ EXPECT_TRUE(pool.FindMethodByName("Foo") == NULL);
+
+ EXPECT_EQ(0, call_counter.call_count_);
+}
+
+// ===================================================================
+
+class AbortingErrorCollector : public DescriptorPool::ErrorCollector {
+ public:
+ AbortingErrorCollector() {}
+
+ virtual void AddError(
+ const string &filename,
+ const string &element_name,
+ const Message *message,
+ ErrorLocation location,
+ const string &error_message) {
+ GOOGLE_LOG(FATAL) << "AddError() called unexpectedly: " << filename << " ["
+ << element_name << "]: " << error_message;
+ }
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(AbortingErrorCollector);
+};
+
+// A source tree containing only one file.
+class SingletonSourceTree : public compiler::SourceTree {
+ public:
+ SingletonSourceTree(const string& filename, const string& contents)
+ : filename_(filename), contents_(contents) {}
+
+ virtual io::ZeroCopyInputStream* Open(const string& filename) {
+ return filename == filename_ ?
+ new io::ArrayInputStream(contents_.data(), contents_.size()) : NULL;
+ }
+
+ private:
+ const string filename_;
+ const string contents_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(SingletonSourceTree);
+};
+
+const char *const kSourceLocationTestInput =
+ "syntax = \"proto2\";\n"
+ "message A {\n"
+ " optional int32 a = 1;\n"
+ " message B {\n"
+ " required double b = 1;\n"
+ " }\n"
+ "}\n"
+ "enum Indecision {\n"
+ " YES = 1;\n"
+ " NO = 2;\n"
+ " MAYBE = 3;\n"
+ "}\n"
+ "service S {\n"
+ " rpc Method(A) returns (A.B);\n"
+ // Put an empty line here to make the source location range match.
+ "\n"
+ "}\n"
+ "message MessageWithExtensions {\n"
+ " extensions 1000 to max;\n"
+ "}\n"
+ "extend MessageWithExtensions {\n"
+ " optional int32 int32_extension = 1001;\n"
+ "}\n"
+ "message C {\n"
+ " extend MessageWithExtensions {\n"
+ " optional C message_extension = 1002;\n"
+ " }\n"
+ "}\n";
+
+class SourceLocationTest : public testing::Test {
+ public:
+ SourceLocationTest()
+ : source_tree_("/test/test.proto", kSourceLocationTestInput),
+ db_(&source_tree_),
+ pool_(&db_, &collector_) {}
+
+ static string PrintSourceLocation(const SourceLocation &loc) {
+ return strings::Substitute("$0:$1-$2:$3",
+ 1 + loc.start_line,
+ 1 + loc.start_column,
+ 1 + loc.end_line,
+ 1 + loc.end_column);
+ }
+
+ private:
+ AbortingErrorCollector collector_;
+ SingletonSourceTree source_tree_;
+ compiler::SourceTreeDescriptorDatabase db_;
+
+ protected:
+ DescriptorPool pool_;
+};
+
+// TODO(adonovan): implement support for option fields and for
+// subparts of declarations.
+
+TEST_F(SourceLocationTest, GetSourceLocation) {
+ SourceLocation loc;
+
+ const FileDescriptor *file_desc =
+ GOOGLE_CHECK_NOTNULL(pool_.FindFileByName("/test/test.proto"));
+
+ const Descriptor *a_desc = file_desc->FindMessageTypeByName("A");
+ EXPECT_TRUE(a_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("2:1-7:2", PrintSourceLocation(loc));
+
+ const Descriptor *a_b_desc = a_desc->FindNestedTypeByName("B");
+ EXPECT_TRUE(a_b_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("4:3-6:4", PrintSourceLocation(loc));
+
+ const EnumDescriptor *e_desc = file_desc->FindEnumTypeByName("Indecision");
+ EXPECT_TRUE(e_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("8:1-12:2", PrintSourceLocation(loc));
+
+ const EnumValueDescriptor *yes_desc = e_desc->FindValueByName("YES");
+ EXPECT_TRUE(yes_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("9:3-9:13", PrintSourceLocation(loc));
+
+ const ServiceDescriptor *s_desc = file_desc->FindServiceByName("S");
+ EXPECT_TRUE(s_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("13:1-16:2", PrintSourceLocation(loc));
+
+ const MethodDescriptor *m_desc = s_desc->FindMethodByName("Method");
+ EXPECT_TRUE(m_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("14:3-14:31", PrintSourceLocation(loc));
+
+}
+
+TEST_F(SourceLocationTest, ExtensionSourceLocation) {
+ SourceLocation loc;
+
+ const FileDescriptor *file_desc =
+ GOOGLE_CHECK_NOTNULL(pool_.FindFileByName("/test/test.proto"));
+
+ const FieldDescriptor *int32_extension_desc =
+ file_desc->FindExtensionByName("int32_extension");
+ EXPECT_TRUE(int32_extension_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("21:3-21:41", PrintSourceLocation(loc));
+
+ const Descriptor *c_desc = file_desc->FindMessageTypeByName("C");
+ EXPECT_TRUE(c_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("23:1-27:2", PrintSourceLocation(loc));
+
+ const FieldDescriptor *message_extension_desc =
+ c_desc->FindExtensionByName("message_extension");
+ EXPECT_TRUE(message_extension_desc->GetSourceLocation(&loc));
+ EXPECT_EQ("25:5-25:41", PrintSourceLocation(loc));
+}
+
+// Missing SourceCodeInfo doesn't cause crash:
+TEST_F(SourceLocationTest, GetSourceLocation_MissingSourceCodeInfo) {
+ SourceLocation loc;
+
+ const FileDescriptor *file_desc =
+ GOOGLE_CHECK_NOTNULL(pool_.FindFileByName("/test/test.proto"));
+
+ FileDescriptorProto proto;
+ file_desc->CopyTo(&proto); // Note, this discards the SourceCodeInfo.
+ EXPECT_FALSE(proto.has_source_code_info());
+
+ DescriptorPool bad1_pool(&pool_);
+ const FileDescriptor* bad1_file_desc =
+ GOOGLE_CHECK_NOTNULL(bad1_pool.BuildFile(proto));
+ const Descriptor *bad1_a_desc = bad1_file_desc->FindMessageTypeByName("A");
+ EXPECT_FALSE(bad1_a_desc->GetSourceLocation(&loc));
+}
+
+// Corrupt SourceCodeInfo doesn't cause crash:
+TEST_F(SourceLocationTest, GetSourceLocation_BogusSourceCodeInfo) {
+ SourceLocation loc;
+
+ const FileDescriptor *file_desc =
+ GOOGLE_CHECK_NOTNULL(pool_.FindFileByName("/test/test.proto"));
+
+ FileDescriptorProto proto;
+ file_desc->CopyTo(&proto); // Note, this discards the SourceCodeInfo.
+ EXPECT_FALSE(proto.has_source_code_info());
+ SourceCodeInfo_Location *loc_msg =
+ proto.mutable_source_code_info()->add_location();
+ loc_msg->add_path(1);
+ loc_msg->add_path(2);
+ loc_msg->add_path(3);
+ loc_msg->add_span(4);
+ loc_msg->add_span(5);
+ loc_msg->add_span(6);
+
+ DescriptorPool bad2_pool(&pool_);
+ const FileDescriptor* bad2_file_desc =
+ GOOGLE_CHECK_NOTNULL(bad2_pool.BuildFile(proto));
+ const Descriptor *bad2_a_desc = bad2_file_desc->FindMessageTypeByName("A");
+ EXPECT_FALSE(bad2_a_desc->GetSourceLocation(&loc));
+}
+
+// ===================================================================
+
+const char* const kCopySourceCodeInfoToTestInput =
+ "syntax = \"proto2\";\n"
+ "message Foo {}\n";
+
+// Required since source code information is not preserved by
+// FileDescriptorTest.
+class CopySourceCodeInfoToTest : public testing::Test {
+ public:
+ CopySourceCodeInfoToTest()
+ : source_tree_("/test/test.proto", kCopySourceCodeInfoToTestInput),
+ db_(&source_tree_),
+ pool_(&db_, &collector_) {}
+
+ private:
+ AbortingErrorCollector collector_;
+ SingletonSourceTree source_tree_;
+ compiler::SourceTreeDescriptorDatabase db_;
+
+ protected:
+ DescriptorPool pool_;
+};
+
+TEST_F(CopySourceCodeInfoToTest, CopyTo_DoesNotCopySourceCodeInfo) {
+ const FileDescriptor* file_desc =
+ GOOGLE_CHECK_NOTNULL(pool_.FindFileByName("/test/test.proto"));
+ FileDescriptorProto file_desc_proto;
+ ASSERT_FALSE(file_desc_proto.has_source_code_info());
+
+ file_desc->CopyTo(&file_desc_proto);
+ EXPECT_FALSE(file_desc_proto.has_source_code_info());
+}
+
+TEST_F(CopySourceCodeInfoToTest, CopySourceCodeInfoTo) {
+ const FileDescriptor* file_desc =
+ GOOGLE_CHECK_NOTNULL(pool_.FindFileByName("/test/test.proto"));
+ FileDescriptorProto file_desc_proto;
+ ASSERT_FALSE(file_desc_proto.has_source_code_info());
+
+ file_desc->CopySourceCodeInfoTo(&file_desc_proto);
+ const SourceCodeInfo& info = file_desc_proto.source_code_info();
+ ASSERT_EQ(4, info.location_size());
+ // Get the Foo message location
+ const SourceCodeInfo_Location& foo_location = info.location(2);
+ ASSERT_EQ(2, foo_location.path_size());
+ EXPECT_EQ(FileDescriptorProto::kMessageTypeFieldNumber, foo_location.path(0));
+ EXPECT_EQ(0, foo_location.path(1)); // Foo is the first message defined
+ ASSERT_EQ(3, foo_location.span_size()); // Foo spans one line
+ EXPECT_EQ(1, foo_location.span(0)); // Foo is declared on line 1
+ EXPECT_EQ(0, foo_location.span(1)); // Foo starts at column 0
+ EXPECT_EQ(14, foo_location.span(2)); // Foo ends on column 14
+}
+
+// ===================================================================
+
+
+} // namespace descriptor_unittest
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/drop_unknown_fields_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/drop_unknown_fields_test.cc
new file mode 100644
index 0000000000..6f16dc5341
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/drop_unknown_fields_test.cc
@@ -0,0 +1,88 @@
+// 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.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/unittest_drop_unknown_fields.pb.h>
+#include <google/protobuf/dynamic_message.h>
+#include <gtest/gtest.h>
+
+namespace google {
+using unittest_drop_unknown_fields::Foo;
+using unittest_drop_unknown_fields::FooWithExtraFields;
+
+namespace protobuf {
+
+TEST(DropUnknownFieldsTest, GeneratedMessage) {
+ FooWithExtraFields foo_with_extra_fields;
+ foo_with_extra_fields.set_int32_value(1);
+ foo_with_extra_fields.set_enum_value(FooWithExtraFields::QUX);
+ foo_with_extra_fields.set_extra_int32_value(2);
+
+ Foo foo;
+ ASSERT_TRUE(foo.ParseFromString(foo_with_extra_fields.SerializeAsString()));
+ EXPECT_EQ(1, foo.int32_value());
+ EXPECT_EQ(static_cast<int>(FooWithExtraFields::QUX),
+ static_cast<int>(foo.enum_value()));
+ // We don't generate unknown field accessors but the UnknownFieldSet is
+ // still exposed through reflection API.
+ EXPECT_TRUE(foo.GetReflection()->GetUnknownFields(foo).empty());
+
+ ASSERT_TRUE(foo_with_extra_fields.ParseFromString(foo.SerializeAsString()));
+ EXPECT_EQ(1, foo_with_extra_fields.int32_value());
+ EXPECT_EQ(FooWithExtraFields::QUX, foo_with_extra_fields.enum_value());
+ // The "extra_int32_value" field should be lost.
+ EXPECT_EQ(0, foo_with_extra_fields.extra_int32_value());
+}
+
+TEST(DropUnknownFieldsTest, DynamicMessage) {
+ FooWithExtraFields foo_with_extra_fields;
+ foo_with_extra_fields.set_int32_value(1);
+ foo_with_extra_fields.set_enum_value(FooWithExtraFields::QUX);
+ foo_with_extra_fields.set_extra_int32_value(2);
+
+ google::protobuf::DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<google::protobuf::Message> foo(
+ factory.GetPrototype(Foo::descriptor())->New());
+ ASSERT_TRUE(foo->ParseFromString(foo_with_extra_fields.SerializeAsString()));
+ EXPECT_TRUE(foo->GetReflection()->GetUnknownFields(*foo).empty());
+
+ ASSERT_TRUE(foo_with_extra_fields.ParseFromString(foo->SerializeAsString()));
+ EXPECT_EQ(1, foo_with_extra_fields.int32_value());
+ EXPECT_EQ(FooWithExtraFields::QUX, foo_with_extra_fields.enum_value());
+ // The "extra_int32_value" field should be lost.
+ EXPECT_EQ(0, foo_with_extra_fields.extra_int32_value());
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.cc
new file mode 100644
index 0000000000..94ece18ea4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.cc
@@ -0,0 +1,422 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/duration.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/duration.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* Duration_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Duration_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fduration_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fduration_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fduration_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/duration.proto");
+ GOOGLE_CHECK(file != NULL);
+ Duration_descriptor_ = file->message_type(0);
+ static const int Duration_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Duration, seconds_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Duration, nanos_),
+ };
+ Duration_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Duration_descriptor_,
+ Duration::default_instance_,
+ Duration_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Duration),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Duration, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Duration, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fduration_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Duration_descriptor_, &Duration::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fduration_2eproto() {
+ delete Duration::default_instance_;
+ delete Duration_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fduration_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fduration_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n\036google/protobuf/duration.proto\022\017google"
+ ".protobuf\"*\n\010Duration\022\017\n\007seconds\030\001 \001(\003\022\r"
+ "\n\005nanos\030\002 \001(\005B|\n\023com.google.protobufB\rDu"
+ "rationProtoP\001Z*github.com/golang/protobu"
+ "f/ptypes/duration\240\001\001\242\002\003GPB\252\002\036Google.Prot"
+ "obuf.WellKnownTypesb\006proto3", 227);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/duration.proto", &protobuf_RegisterTypes);
+ Duration::default_instance_ = new Duration();
+ Duration::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fduration_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fduration_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fduration_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fduration_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fduration_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Duration::kSecondsFieldNumber;
+const int Duration::kNanosFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Duration::Duration()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Duration)
+}
+
+void Duration::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Duration::Duration(const Duration& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Duration)
+}
+
+void Duration::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ seconds_ = GOOGLE_LONGLONG(0);
+ nanos_ = 0;
+}
+
+Duration::~Duration() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Duration)
+ SharedDtor();
+}
+
+void Duration::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void Duration::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Duration::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Duration_descriptor_;
+}
+
+const Duration& Duration::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fduration_2eproto();
+ return *default_instance_;
+}
+
+Duration* Duration::default_instance_ = NULL;
+
+Duration* Duration::New(::google::protobuf::Arena* arena) const {
+ Duration* n = new Duration;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Duration::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Duration)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(Duration, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<Duration*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(seconds_, nanos_);
+
+#undef ZR_HELPER_
+#undef ZR_
+
+}
+
+bool Duration::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Duration)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional int64 seconds = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int64, ::google::protobuf::internal::WireFormatLite::TYPE_INT64>(
+ input, &seconds_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_nanos;
+ break;
+ }
+
+ // optional int32 nanos = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_nanos:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &nanos_)));
+
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Duration)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Duration)
+ return false;
+#undef DO_
+}
+
+void Duration::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Duration)
+ // optional int64 seconds = 1;
+ if (this->seconds() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt64(1, this->seconds(), output);
+ }
+
+ // optional int32 nanos = 2;
+ if (this->nanos() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(2, this->nanos(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Duration)
+}
+
+::google::protobuf::uint8* Duration::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Duration)
+ // optional int64 seconds = 1;
+ if (this->seconds() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt64ToArray(1, this->seconds(), target);
+ }
+
+ // optional int32 nanos = 2;
+ if (this->nanos() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(2, this->nanos(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Duration)
+ return target;
+}
+
+int Duration::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Duration)
+ int total_size = 0;
+
+ // optional int64 seconds = 1;
+ if (this->seconds() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int64Size(
+ this->seconds());
+ }
+
+ // optional int32 nanos = 2;
+ if (this->nanos() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->nanos());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Duration::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Duration)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Duration* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Duration>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Duration)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Duration)
+ MergeFrom(*source);
+ }
+}
+
+void Duration::MergeFrom(const Duration& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Duration)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.seconds() != 0) {
+ set_seconds(from.seconds());
+ }
+ if (from.nanos() != 0) {
+ set_nanos(from.nanos());
+ }
+}
+
+void Duration::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Duration)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Duration::CopyFrom(const Duration& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Duration)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Duration::IsInitialized() const {
+
+ return true;
+}
+
+void Duration::Swap(Duration* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Duration::InternalSwap(Duration* other) {
+ std::swap(seconds_, other->seconds_);
+ std::swap(nanos_, other->nanos_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Duration::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Duration_descriptor_;
+ metadata.reflection = Duration_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Duration
+
+// optional int64 seconds = 1;
+void Duration::clear_seconds() {
+ seconds_ = GOOGLE_LONGLONG(0);
+}
+ ::google::protobuf::int64 Duration::seconds() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Duration.seconds)
+ return seconds_;
+}
+ void Duration::set_seconds(::google::protobuf::int64 value) {
+
+ seconds_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Duration.seconds)
+}
+
+// optional int32 nanos = 2;
+void Duration::clear_nanos() {
+ nanos_ = 0;
+}
+ ::google::protobuf::int32 Duration::nanos() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Duration.nanos)
+ return nanos_;
+}
+ void Duration::set_nanos(::google::protobuf::int32 value) {
+
+ nanos_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Duration.nanos)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.h
new file mode 100644
index 0000000000..ad47963943
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/duration.pb.h
@@ -0,0 +1,176 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/duration.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fduration_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fduration_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fduration_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fduration_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fduration_2eproto();
+
+class Duration;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT Duration : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Duration) */ {
+ public:
+ Duration();
+ virtual ~Duration();
+
+ Duration(const Duration& from);
+
+ inline Duration& operator=(const Duration& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Duration& default_instance();
+
+ void Swap(Duration* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Duration* New() const { return New(NULL); }
+
+ Duration* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Duration& from);
+ void MergeFrom(const Duration& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Duration* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional int64 seconds = 1;
+ void clear_seconds();
+ static const int kSecondsFieldNumber = 1;
+ ::google::protobuf::int64 seconds() const;
+ void set_seconds(::google::protobuf::int64 value);
+
+ // optional int32 nanos = 2;
+ void clear_nanos();
+ static const int kNanosFieldNumber = 2;
+ ::google::protobuf::int32 nanos() const;
+ void set_nanos(::google::protobuf::int32 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Duration)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::int64 seconds_;
+ ::google::protobuf::int32 nanos_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fduration_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fduration_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fduration_2eproto();
+
+ void InitAsDefaultInstance();
+ static Duration* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// Duration
+
+// optional int64 seconds = 1;
+inline void Duration::clear_seconds() {
+ seconds_ = GOOGLE_LONGLONG(0);
+}
+inline ::google::protobuf::int64 Duration::seconds() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Duration.seconds)
+ return seconds_;
+}
+inline void Duration::set_seconds(::google::protobuf::int64 value) {
+
+ seconds_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Duration.seconds)
+}
+
+// optional int32 nanos = 2;
+inline void Duration::clear_nanos() {
+ nanos_ = 0;
+}
+inline ::google::protobuf::int32 Duration::nanos() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Duration.nanos)
+ return nanos_;
+}
+inline void Duration::set_nanos(::google::protobuf::int32 value) {
+
+ nanos_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Duration.nanos)
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fduration_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/duration.proto b/third_party/protobuf/3.0.0/src/google/protobuf/duration.proto
new file mode 100644
index 0000000000..96c1796d65
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/duration.proto
@@ -0,0 +1,98 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option go_package = "github.com/golang/protobuf/ptypes/duration";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "DurationProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+// A Duration represents a signed, fixed-length span of time represented
+// as a count of seconds and fractions of seconds at nanosecond
+// resolution. It is independent of any calendar and concepts like "day"
+// or "month". It is related to Timestamp in that the difference between
+// two Timestamp values is a Duration and it can be added or subtracted
+// from a Timestamp. Range is approximately +-10,000 years.
+//
+// Example 1: Compute Duration from two Timestamps in pseudo code.
+//
+// Timestamp start = ...;
+// Timestamp end = ...;
+// Duration duration = ...;
+//
+// duration.seconds = end.seconds - start.seconds;
+// duration.nanos = end.nanos - start.nanos;
+//
+// if (duration.seconds < 0 && duration.nanos > 0) {
+// duration.seconds += 1;
+// duration.nanos -= 1000000000;
+// } else if (durations.seconds > 0 && duration.nanos < 0) {
+// duration.seconds -= 1;
+// duration.nanos += 1000000000;
+// }
+//
+// Example 2: Compute Timestamp from Timestamp + Duration in pseudo code.
+//
+// Timestamp start = ...;
+// Duration duration = ...;
+// Timestamp end = ...;
+//
+// end.seconds = start.seconds + duration.seconds;
+// end.nanos = start.nanos + duration.nanos;
+//
+// if (end.nanos < 0) {
+// end.seconds -= 1;
+// end.nanos += 1000000000;
+// } else if (end.nanos >= 1000000000) {
+// end.seconds += 1;
+// end.nanos -= 1000000000;
+// }
+//
+//
+message Duration {
+
+ // Signed seconds of the span of time. Must be from -315,576,000,000
+ // to +315,576,000,000 inclusive.
+ int64 seconds = 1;
+
+ // Signed fractions of a second at nanosecond resolution of the span
+ // of time. Durations less than one second are represented with a 0
+ // `seconds` field and a positive or negative `nanos` field. For durations
+ // of one second or more, a non-zero value for the `nanos` field must be
+ // of the same sign as the `seconds` field. Must be from -999,999,999
+ // to +999,999,999 inclusive.
+ int32 nanos = 2;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.cc b/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.cc
new file mode 100644
index 0000000000..5d914bf63e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.cc
@@ -0,0 +1,873 @@
+// 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.
+//
+// DynamicMessage is implemented by constructing a data structure which
+// has roughly the same memory layout as a generated message would have.
+// Then, we use GeneratedMessageReflection to implement our reflection
+// interface. All the other operations we need to implement (e.g.
+// parsing, copying, etc.) are already implemented in terms of
+// Reflection, so the rest is easy.
+//
+// The up side of this strategy is that it's very efficient. We don't
+// need to use hash_maps or generic representations of fields. The
+// down side is that this is a low-level memory management hack which
+// can be tricky to get right.
+//
+// As mentioned in the header, we only expose a DynamicMessageFactory
+// publicly, not the DynamicMessage class itself. This is because
+// GenericMessageReflection wants to have a pointer to a "default"
+// copy of the class, with all fields initialized to their default
+// values. We only want to construct one of these per message type,
+// so DynamicMessageFactory stores a cache of default messages for
+// each type it sees (each unique Descriptor pointer). The code
+// refers to the "default" copy of the class as the "prototype".
+//
+// Note on memory allocation: This module often calls "operator new()"
+// to allocate untyped memory, rather than calling something like
+// "new uint8[]". This is because "operator new()" means "Give me some
+// space which I can use as I please." while "new uint8[]" means "Give
+// me an array of 8-bit integers.". In practice, the later may return
+// a pointer that is not aligned correctly for general use. I believe
+// Item 8 of "More Effective C++" discusses this in more detail, though
+// I don't have the book on me right now so I'm not sure.
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/common.h>
+
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/generated_message_reflection.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/map_field_inl.h>
+#include <google/protobuf/reflection_ops.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/map_type_handler.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/map_field.h>
+
+namespace google {
+namespace protobuf {
+
+using internal::WireFormat;
+using internal::ExtensionSet;
+using internal::GeneratedMessageReflection;
+using internal::MapField;
+using internal::DynamicMapField;
+
+
+using internal::ArenaStringPtr;
+
+// ===================================================================
+// Some helper tables and functions...
+
+namespace {
+
+bool IsMapFieldInApi(const FieldDescriptor* field) {
+ return field->is_map();
+}
+
+// Compute the byte size of the in-memory representation of the field.
+int FieldSpaceUsed(const FieldDescriptor* field) {
+ typedef FieldDescriptor FD; // avoid line wrapping
+ if (field->label() == FD::LABEL_REPEATED) {
+ switch (field->cpp_type()) {
+ case FD::CPPTYPE_INT32 : return sizeof(RepeatedField<int32 >);
+ case FD::CPPTYPE_INT64 : return sizeof(RepeatedField<int64 >);
+ case FD::CPPTYPE_UINT32 : return sizeof(RepeatedField<uint32 >);
+ case FD::CPPTYPE_UINT64 : return sizeof(RepeatedField<uint64 >);
+ case FD::CPPTYPE_DOUBLE : return sizeof(RepeatedField<double >);
+ case FD::CPPTYPE_FLOAT : return sizeof(RepeatedField<float >);
+ case FD::CPPTYPE_BOOL : return sizeof(RepeatedField<bool >);
+ case FD::CPPTYPE_ENUM : return sizeof(RepeatedField<int >);
+ case FD::CPPTYPE_MESSAGE:
+ if (IsMapFieldInApi(field)) {
+ return sizeof(DynamicMapField);
+ } else {
+ return sizeof(RepeatedPtrField<Message>);
+ }
+
+ case FD::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ return sizeof(RepeatedPtrField<string>);
+ }
+ break;
+ }
+ } else {
+ switch (field->cpp_type()) {
+ case FD::CPPTYPE_INT32 : return sizeof(int32 );
+ case FD::CPPTYPE_INT64 : return sizeof(int64 );
+ case FD::CPPTYPE_UINT32 : return sizeof(uint32 );
+ case FD::CPPTYPE_UINT64 : return sizeof(uint64 );
+ case FD::CPPTYPE_DOUBLE : return sizeof(double );
+ case FD::CPPTYPE_FLOAT : return sizeof(float );
+ case FD::CPPTYPE_BOOL : return sizeof(bool );
+ case FD::CPPTYPE_ENUM : return sizeof(int );
+
+ case FD::CPPTYPE_MESSAGE:
+ return sizeof(Message*);
+
+ case FD::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ return sizeof(ArenaStringPtr);
+ }
+ break;
+ }
+ }
+
+ GOOGLE_LOG(DFATAL) << "Can't get here.";
+ return 0;
+}
+
+// Compute the byte size of in-memory representation of the oneof fields
+// in default oneof instance.
+int OneofFieldSpaceUsed(const FieldDescriptor* field) {
+ typedef FieldDescriptor FD; // avoid line wrapping
+ switch (field->cpp_type()) {
+ case FD::CPPTYPE_INT32 : return sizeof(int32 );
+ case FD::CPPTYPE_INT64 : return sizeof(int64 );
+ case FD::CPPTYPE_UINT32 : return sizeof(uint32 );
+ case FD::CPPTYPE_UINT64 : return sizeof(uint64 );
+ case FD::CPPTYPE_DOUBLE : return sizeof(double );
+ case FD::CPPTYPE_FLOAT : return sizeof(float );
+ case FD::CPPTYPE_BOOL : return sizeof(bool );
+ case FD::CPPTYPE_ENUM : return sizeof(int );
+
+ case FD::CPPTYPE_MESSAGE:
+ return sizeof(Message*);
+
+ case FD::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default:
+ case FieldOptions::STRING:
+ return sizeof(ArenaStringPtr);
+ }
+ break;
+ }
+
+ GOOGLE_LOG(DFATAL) << "Can't get here.";
+ return 0;
+}
+
+inline int DivideRoundingUp(int i, int j) {
+ return (i + (j - 1)) / j;
+}
+
+static const int kSafeAlignment = sizeof(uint64);
+static const int kMaxOneofUnionSize = sizeof(uint64);
+
+inline int AlignTo(int offset, int alignment) {
+ return DivideRoundingUp(offset, alignment) * alignment;
+}
+
+// Rounds the given byte offset up to the next offset aligned such that any
+// type may be stored at it.
+inline int AlignOffset(int offset) {
+ return AlignTo(offset, kSafeAlignment);
+}
+
+#define bitsizeof(T) (sizeof(T) * 8)
+
+} // namespace
+
+// ===================================================================
+
+class DynamicMessage : public Message {
+ public:
+ struct TypeInfo {
+ int size;
+ int has_bits_offset;
+ int oneof_case_offset;
+ int unknown_fields_offset;
+ int extensions_offset;
+ int is_default_instance_offset;
+
+ // Not owned by the TypeInfo.
+ DynamicMessageFactory* factory; // The factory that created this object.
+ const DescriptorPool* pool; // The factory's DescriptorPool.
+ const Descriptor* type; // Type of this DynamicMessage.
+
+ // Warning: The order in which the following pointers are defined is
+ // important (the prototype must be deleted *before* the offsets).
+ google::protobuf::scoped_array<int> offsets;
+ google::protobuf::scoped_ptr<const GeneratedMessageReflection> reflection;
+ // Don't use a scoped_ptr to hold the prototype: the destructor for
+ // DynamicMessage needs to know whether it is the prototype, and does so by
+ // looking back at this field. This would assume details about the
+ // implementation of scoped_ptr.
+ const DynamicMessage* prototype;
+ void* default_oneof_instance;
+
+ TypeInfo() : prototype(NULL), default_oneof_instance(NULL) {}
+
+ ~TypeInfo() {
+ delete prototype;
+ operator delete(default_oneof_instance);
+ }
+ };
+
+ DynamicMessage(const TypeInfo* type_info);
+ ~DynamicMessage();
+
+ // Called on the prototype after construction to initialize message fields.
+ void CrossLinkPrototypes();
+
+ // implements Message ----------------------------------------------
+
+ Message* New() const;
+ Message* New(::google::protobuf::Arena* arena) const;
+ ::google::protobuf::Arena* GetArena() const { return NULL; };
+
+ int GetCachedSize() const;
+ void SetCachedSize(int size) const;
+
+ Metadata GetMetadata() const;
+
+ // We actually allocate more memory than sizeof(*this) when this
+ // class's memory is allocated via the global operator new. Thus, we need to
+ // manually call the global operator delete. Calling the destructor is taken
+ // care of for us. This makes DynamicMessage compatible with -fsized-delete.
+ // It doesn't work for MSVC though.
+#ifndef _MSC_VER
+ static void operator delete(void* ptr) {
+ ::operator delete(ptr);
+ }
+#endif // !_MSC_VER
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DynamicMessage);
+ DynamicMessage(const TypeInfo* type_info, ::google::protobuf::Arena* arena);
+ void SharedCtor();
+
+ inline bool is_prototype() const {
+ return type_info_->prototype == this ||
+ // If type_info_->prototype is NULL, then we must be constructing
+ // the prototype now, which means we must be the prototype.
+ type_info_->prototype == NULL;
+ }
+
+ inline void* OffsetToPointer(int offset) {
+ return reinterpret_cast<uint8*>(this) + offset;
+ }
+ inline const void* OffsetToPointer(int offset) const {
+ return reinterpret_cast<const uint8*>(this) + offset;
+ }
+
+ const TypeInfo* type_info_;
+ // TODO(kenton): Make this an atomic<int> when C++ supports it.
+ mutable int cached_byte_size_;
+};
+
+DynamicMessage::DynamicMessage(const TypeInfo* type_info)
+ : type_info_(type_info),
+ cached_byte_size_(0) {
+ SharedCtor();
+}
+
+DynamicMessage::DynamicMessage(const TypeInfo* type_info,
+ ::google::protobuf::Arena* arena)
+ : type_info_(type_info),
+ cached_byte_size_(0) {
+ SharedCtor();
+}
+
+void DynamicMessage::SharedCtor() {
+ // We need to call constructors for various fields manually and set
+ // default values where appropriate. We use placement new to call
+ // constructors. If you haven't heard of placement new, I suggest Googling
+ // it now. We use placement new even for primitive types that don't have
+ // constructors for consistency. (In theory, placement new should be used
+ // any time you are trying to convert untyped memory to typed memory, though
+ // in practice that's not strictly necessary for types that don't have a
+ // constructor.)
+
+ const Descriptor* descriptor = type_info_->type;
+
+ // Initialize oneof cases.
+ for (int i = 0 ; i < descriptor->oneof_decl_count(); ++i) {
+ new(OffsetToPointer(type_info_->oneof_case_offset + sizeof(uint32) * i))
+ uint32(0);
+ }
+
+ if (type_info_->is_default_instance_offset != -1) {
+ *reinterpret_cast<bool*>(
+ OffsetToPointer(type_info_->is_default_instance_offset)) = false;
+ }
+
+ new(OffsetToPointer(type_info_->unknown_fields_offset)) UnknownFieldSet;
+
+ if (type_info_->extensions_offset != -1) {
+ new(OffsetToPointer(type_info_->extensions_offset)) ExtensionSet;
+ }
+
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ const FieldDescriptor* field = descriptor->field(i);
+ void* field_ptr = OffsetToPointer(type_info_->offsets[i]);
+ if (field->containing_oneof()) {
+ continue;
+ }
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ if (!field->is_repeated()) { \
+ new(field_ptr) TYPE(field->default_value_##TYPE()); \
+ } else { \
+ new(field_ptr) RepeatedField<TYPE>(); \
+ } \
+ break;
+
+ HANDLE_TYPE(INT32 , int32 );
+ HANDLE_TYPE(INT64 , int64 );
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE(FLOAT , float );
+ HANDLE_TYPE(BOOL , bool );
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_ENUM:
+ if (!field->is_repeated()) {
+ new(field_ptr) int(field->default_value_enum()->number());
+ } else {
+ new(field_ptr) RepeatedField<int>();
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ if (!field->is_repeated()) {
+ const string* default_value;
+ if (is_prototype()) {
+ default_value = &field->default_value_string();
+ } else {
+ default_value =
+ &(reinterpret_cast<const ArenaStringPtr*>(
+ type_info_->prototype->OffsetToPointer(
+ type_info_->offsets[i]))->Get(NULL));
+ }
+ ArenaStringPtr* asp = new(field_ptr) ArenaStringPtr();
+ asp->UnsafeSetDefault(default_value);
+ } else {
+ new(field_ptr) RepeatedPtrField<string>();
+ }
+ break;
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_MESSAGE: {
+ if (!field->is_repeated()) {
+ new(field_ptr) Message*(NULL);
+ } else {
+ if (IsMapFieldInApi(field)) {
+ new (field_ptr) DynamicMapField(
+ type_info_->factory->GetPrototypeNoLock(field->message_type()));
+ } else {
+ new (field_ptr) RepeatedPtrField<Message>();
+ }
+ }
+ break;
+ }
+ }
+ }
+}
+
+DynamicMessage::~DynamicMessage() {
+ const Descriptor* descriptor = type_info_->type;
+
+ reinterpret_cast<UnknownFieldSet*>(
+ OffsetToPointer(type_info_->unknown_fields_offset))->~UnknownFieldSet();
+
+ if (type_info_->extensions_offset != -1) {
+ reinterpret_cast<ExtensionSet*>(
+ OffsetToPointer(type_info_->extensions_offset))->~ExtensionSet();
+ }
+
+ // We need to manually run the destructors for repeated fields and strings,
+ // just as we ran their constructors in the DynamicMessage constructor.
+ // We also need to manually delete oneof fields if it is set and is string
+ // or message.
+ // Additionally, if any singular embedded messages have been allocated, we
+ // need to delete them, UNLESS we are the prototype message of this type,
+ // in which case any embedded messages are other prototypes and shouldn't
+ // be touched.
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ const FieldDescriptor* field = descriptor->field(i);
+ if (field->containing_oneof()) {
+ void* field_ptr = OffsetToPointer(
+ type_info_->oneof_case_offset
+ + sizeof(uint32) * field->containing_oneof()->index());
+ if (*(reinterpret_cast<const uint32*>(field_ptr)) ==
+ field->number()) {
+ field_ptr = OffsetToPointer(type_info_->offsets[
+ descriptor->field_count() + field->containing_oneof()->index()]);
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_STRING) {
+ switch (field->options().ctype()) {
+ default:
+ case FieldOptions::STRING: {
+ const ::std::string* default_value =
+ &(reinterpret_cast<const ArenaStringPtr*>(
+ reinterpret_cast<uint8*>(
+ type_info_->default_oneof_instance)
+ + type_info_->offsets[i])
+ ->Get(NULL));
+ reinterpret_cast<ArenaStringPtr*>(field_ptr)->Destroy(
+ default_value, NULL);
+ break;
+ }
+ }
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ delete *reinterpret_cast<Message**>(field_ptr);
+ }
+ }
+ continue;
+ }
+ void* field_ptr = OffsetToPointer(type_info_->offsets[i]);
+
+ if (field->is_repeated()) {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case FieldDescriptor::CPPTYPE_##UPPERCASE : \
+ reinterpret_cast<RepeatedField<LOWERCASE>*>(field_ptr) \
+ ->~RepeatedField<LOWERCASE>(); \
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, int);
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ reinterpret_cast<RepeatedPtrField<string>*>(field_ptr)
+ ->~RepeatedPtrField<string>();
+ break;
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (IsMapFieldInApi(field)) {
+ reinterpret_cast<DynamicMapField*>(field_ptr)->~DynamicMapField();
+ } else {
+ reinterpret_cast<RepeatedPtrField<Message>*>(field_ptr)
+ ->~RepeatedPtrField<Message>();
+ }
+ break;
+ }
+
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_STRING) {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING: {
+ const ::std::string* default_value =
+ &(reinterpret_cast<const ArenaStringPtr*>(
+ type_info_->prototype->OffsetToPointer(
+ type_info_->offsets[i]))->Get(NULL));
+ reinterpret_cast<ArenaStringPtr*>(field_ptr)->Destroy(
+ default_value, NULL);
+ break;
+ }
+ }
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (!is_prototype()) {
+ Message* message = *reinterpret_cast<Message**>(field_ptr);
+ if (message != NULL) {
+ delete message;
+ }
+ }
+ }
+ }
+}
+
+void DynamicMessage::CrossLinkPrototypes() {
+ // This should only be called on the prototype message.
+ GOOGLE_CHECK(is_prototype());
+
+ DynamicMessageFactory* factory = type_info_->factory;
+ const Descriptor* descriptor = type_info_->type;
+
+ // Cross-link default messages.
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ const FieldDescriptor* field = descriptor->field(i);
+ void* field_ptr = OffsetToPointer(type_info_->offsets[i]);
+ if (field->containing_oneof()) {
+ field_ptr = reinterpret_cast<uint8*>(
+ type_info_->default_oneof_instance) + type_info_->offsets[i];
+ }
+
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ !field->is_repeated()) {
+ // For fields with message types, we need to cross-link with the
+ // prototype for the field's type.
+ // For singular fields, the field is just a pointer which should
+ // point to the prototype.
+ *reinterpret_cast<const Message**>(field_ptr) =
+ factory->GetPrototypeNoLock(field->message_type());
+ }
+ }
+
+ // Set as the default instance -- this affects field-presence semantics for
+ // proto3.
+ if (type_info_->is_default_instance_offset != -1) {
+ void* is_default_instance_ptr =
+ OffsetToPointer(type_info_->is_default_instance_offset);
+ *reinterpret_cast<bool*>(is_default_instance_ptr) = true;
+ }
+}
+
+Message* DynamicMessage::New() const {
+ void* new_base = operator new(type_info_->size);
+ memset(new_base, 0, type_info_->size);
+ return new(new_base) DynamicMessage(type_info_);
+}
+
+Message* DynamicMessage::New(::google::protobuf::Arena* arena) const {
+ if (arena != NULL) {
+ Message* message = New();
+ arena->Own(message);
+ return message;
+ } else {
+ return New();
+ }
+}
+
+int DynamicMessage::GetCachedSize() const {
+ return cached_byte_size_;
+}
+
+void DynamicMessage::SetCachedSize(int size) const {
+ // This is theoretically not thread-compatible, but in practice it works
+ // because if multiple threads write this simultaneously, they will be
+ // writing the exact same value.
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ cached_byte_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+
+Metadata DynamicMessage::GetMetadata() const {
+ Metadata metadata;
+ metadata.descriptor = type_info_->type;
+ metadata.reflection = type_info_->reflection.get();
+ return metadata;
+}
+
+// ===================================================================
+
+struct DynamicMessageFactory::PrototypeMap {
+ typedef hash_map<const Descriptor*, const DynamicMessage::TypeInfo*> Map;
+ Map map_;
+};
+
+DynamicMessageFactory::DynamicMessageFactory()
+ : pool_(NULL), delegate_to_generated_factory_(false),
+ prototypes_(new PrototypeMap) {
+}
+
+DynamicMessageFactory::DynamicMessageFactory(const DescriptorPool* pool)
+ : pool_(pool), delegate_to_generated_factory_(false),
+ prototypes_(new PrototypeMap) {
+}
+
+DynamicMessageFactory::~DynamicMessageFactory() {
+ for (PrototypeMap::Map::iterator iter = prototypes_->map_.begin();
+ iter != prototypes_->map_.end(); ++iter) {
+ DeleteDefaultOneofInstance(iter->second->type,
+ iter->second->offsets.get(),
+ iter->second->default_oneof_instance);
+ delete iter->second;
+ }
+}
+
+const Message* DynamicMessageFactory::GetPrototype(const Descriptor* type) {
+ MutexLock lock(&prototypes_mutex_);
+ return GetPrototypeNoLock(type);
+}
+
+const Message* DynamicMessageFactory::GetPrototypeNoLock(
+ const Descriptor* type) {
+ if (delegate_to_generated_factory_ &&
+ type->file()->pool() == DescriptorPool::generated_pool()) {
+ return MessageFactory::generated_factory()->GetPrototype(type);
+ }
+
+ const DynamicMessage::TypeInfo** target = &prototypes_->map_[type];
+ if (*target != NULL) {
+ // Already exists.
+ return (*target)->prototype;
+ }
+
+ DynamicMessage::TypeInfo* type_info = new DynamicMessage::TypeInfo;
+ *target = type_info;
+
+ type_info->type = type;
+ type_info->pool = (pool_ == NULL) ? type->file()->pool() : pool_;
+ type_info->factory = this;
+
+ // We need to construct all the structures passed to
+ // GeneratedMessageReflection's constructor. This includes:
+ // - A block of memory that contains space for all the message's fields.
+ // - An array of integers indicating the byte offset of each field within
+ // this block.
+ // - A big bitfield containing a bit for each field indicating whether
+ // or not that field is set.
+
+ // Compute size and offsets.
+ int* offsets = new int[type->field_count() + type->oneof_decl_count()];
+ type_info->offsets.reset(offsets);
+
+ // Decide all field offsets by packing in order.
+ // We place the DynamicMessage object itself at the beginning of the allocated
+ // space.
+ int size = sizeof(DynamicMessage);
+ size = AlignOffset(size);
+
+ // Next the has_bits, which is an array of uint32s.
+ if (type->file()->syntax() == FileDescriptor::SYNTAX_PROTO3) {
+ type_info->has_bits_offset = -1;
+ } else {
+ type_info->has_bits_offset = size;
+ int has_bits_array_size =
+ DivideRoundingUp(type->field_count(), bitsizeof(uint32));
+ size += has_bits_array_size * sizeof(uint32);
+ size = AlignOffset(size);
+ }
+
+ // The is_default_instance member, if any.
+ if (type->file()->syntax() == FileDescriptor::SYNTAX_PROTO3) {
+ type_info->is_default_instance_offset = size;
+ size += sizeof(bool);
+ size = AlignOffset(size);
+ } else {
+ type_info->is_default_instance_offset = -1;
+ }
+
+ // The oneof_case, if any. It is an array of uint32s.
+ if (type->oneof_decl_count() > 0) {
+ type_info->oneof_case_offset = size;
+ size += type->oneof_decl_count() * sizeof(uint32);
+ size = AlignOffset(size);
+ }
+
+ // The ExtensionSet, if any.
+ if (type->extension_range_count() > 0) {
+ type_info->extensions_offset = size;
+ size += sizeof(ExtensionSet);
+ size = AlignOffset(size);
+ } else {
+ // No extensions.
+ type_info->extensions_offset = -1;
+ }
+
+ // All the fields.
+ for (int i = 0; i < type->field_count(); i++) {
+ // Make sure field is aligned to avoid bus errors.
+ // Oneof fields do not use any space.
+ if (!type->field(i)->containing_oneof()) {
+ int field_size = FieldSpaceUsed(type->field(i));
+ size = AlignTo(size, std::min(kSafeAlignment, field_size));
+ offsets[i] = size;
+ size += field_size;
+ }
+ }
+
+ // The oneofs.
+ for (int i = 0; i < type->oneof_decl_count(); i++) {
+ size = AlignTo(size, kSafeAlignment);
+ offsets[type->field_count() + i] = size;
+ size += kMaxOneofUnionSize;
+ }
+
+ // Add the UnknownFieldSet to the end.
+ size = AlignOffset(size);
+ type_info->unknown_fields_offset = size;
+ size += sizeof(UnknownFieldSet);
+
+ // Align the final size to make sure no clever allocators think that
+ // alignment is not necessary.
+ size = AlignOffset(size);
+ type_info->size = size;
+
+ // Allocate the prototype.
+ void* base = operator new(size);
+ memset(base, 0, size);
+ // The prototype in type_info has to be set before creating the prototype
+ // instance on memory. e.g., message Foo { map<int32, Foo> a = 1; }. When
+ // creating prototype for Foo, prototype of the map entry will also be
+ // created, which needs the address of the prototype of Foo (the value in
+ // map). To break the cyclic dependency, we have to assgin the address of
+ // prototype into type_info first.
+ type_info->prototype = static_cast<DynamicMessage*>(base);
+ DynamicMessage* prototype = new(base) DynamicMessage(type_info);
+
+ // Construct the reflection object.
+ if (type->oneof_decl_count() > 0) {
+ // Compute the size of default oneof instance and offsets of default
+ // oneof fields.
+ int oneof_size = 0;
+ for (int i = 0; i < type->oneof_decl_count(); i++) {
+ for (int j = 0; j < type->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = type->oneof_decl(i)->field(j);
+ int field_size = OneofFieldSpaceUsed(field);
+ oneof_size = AlignTo(oneof_size, std::min(kSafeAlignment, field_size));
+ offsets[field->index()] = oneof_size;
+ oneof_size += field_size;
+ }
+ }
+ // Construct default oneof instance.
+ type_info->default_oneof_instance = ::operator new(oneof_size);
+ ConstructDefaultOneofInstance(type_info->type,
+ type_info->offsets.get(),
+ type_info->default_oneof_instance);
+ type_info->reflection.reset(
+ new GeneratedMessageReflection(
+ type_info->type,
+ type_info->prototype,
+ type_info->offsets.get(),
+ type_info->has_bits_offset,
+ type_info->unknown_fields_offset,
+ type_info->extensions_offset,
+ type_info->default_oneof_instance,
+ type_info->oneof_case_offset,
+ type_info->pool,
+ this,
+ type_info->size,
+ -1 /* arena_offset */,
+ type_info->is_default_instance_offset));
+ } else {
+ type_info->reflection.reset(
+ new GeneratedMessageReflection(
+ type_info->type,
+ type_info->prototype,
+ type_info->offsets.get(),
+ type_info->has_bits_offset,
+ type_info->unknown_fields_offset,
+ type_info->extensions_offset,
+ type_info->pool,
+ this,
+ type_info->size,
+ -1 /* arena_offset */,
+ type_info->is_default_instance_offset));
+ }
+ // Cross link prototypes.
+ prototype->CrossLinkPrototypes();
+
+ return prototype;
+}
+
+void DynamicMessageFactory::ConstructDefaultOneofInstance(
+ const Descriptor* type,
+ const int offsets[],
+ void* default_oneof_instance) {
+ for (int i = 0; i < type->oneof_decl_count(); i++) {
+ for (int j = 0; j < type->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = type->oneof_decl(i)->field(j);
+ void* field_ptr = reinterpret_cast<uint8*>(
+ default_oneof_instance) + offsets[field->index()];
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ new(field_ptr) TYPE(field->default_value_##TYPE()); \
+ break;
+
+ HANDLE_TYPE(INT32 , int32 );
+ HANDLE_TYPE(INT64 , int64 );
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE(FLOAT , float );
+ HANDLE_TYPE(BOOL , bool );
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_ENUM:
+ new(field_ptr) int(field->default_value_enum()->number());
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default:
+ case FieldOptions::STRING:
+ ArenaStringPtr* asp = new (field_ptr) ArenaStringPtr();
+ asp->UnsafeSetDefault(&field->default_value_string());
+ break;
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_MESSAGE: {
+ new(field_ptr) Message*(NULL);
+ break;
+ }
+ }
+ }
+ }
+}
+
+void DynamicMessageFactory::DeleteDefaultOneofInstance(
+ const Descriptor* type,
+ const int offsets[],
+ void* default_oneof_instance) {
+ for (int i = 0; i < type->oneof_decl_count(); i++) {
+ for (int j = 0; j < type->oneof_decl(i)->field_count(); j++) {
+ const FieldDescriptor* field = type->oneof_decl(i)->field(j);
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_STRING) {
+ switch (field->options().ctype()) {
+ default:
+ case FieldOptions::STRING:
+ break;
+ }
+ }
+ }
+ }
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.h b/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.h
new file mode 100644
index 0000000000..f74cd7dd25
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message.h
@@ -0,0 +1,152 @@
+// 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.
+//
+// Defines an implementation of Message which can emulate types which are not
+// known at compile-time.
+
+#ifndef GOOGLE_PROTOBUF_DYNAMIC_MESSAGE_H__
+#define GOOGLE_PROTOBUF_DYNAMIC_MESSAGE_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/message.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/mutex.h>
+
+namespace google {
+namespace protobuf {
+
+// Defined in other files.
+class Descriptor; // descriptor.h
+class DescriptorPool; // descriptor.h
+
+// Constructs implementations of Message which can emulate types which are not
+// known at compile-time.
+//
+// Sometimes you want to be able to manipulate protocol types that you don't
+// know about at compile time. It would be nice to be able to construct
+// a Message object which implements the message type given by any arbitrary
+// Descriptor. DynamicMessage provides this.
+//
+// As it turns out, a DynamicMessage needs to construct extra
+// information about its type in order to operate. Most of this information
+// can be shared between all DynamicMessages of the same type. But, caching
+// this information in some sort of global map would be a bad idea, since
+// the cached information for a particular descriptor could outlive the
+// descriptor itself. To avoid this problem, DynamicMessageFactory
+// encapsulates this "cache". All DynamicMessages of the same type created
+// from the same factory will share the same support data. Any Descriptors
+// used with a particular factory must outlive the factory.
+class LIBPROTOBUF_EXPORT DynamicMessageFactory : public MessageFactory {
+ public:
+ // Construct a DynamicMessageFactory that will search for extensions in
+ // the DescriptorPool in which the extendee is defined.
+ DynamicMessageFactory();
+
+ // Construct a DynamicMessageFactory that will search for extensions in
+ // the given DescriptorPool.
+ //
+ // DEPRECATED: Use CodedInputStream::SetExtensionRegistry() to tell the
+ // parser to look for extensions in an alternate pool. However, note that
+ // this is almost never what you want to do. Almost all users should use
+ // the zero-arg constructor.
+ DynamicMessageFactory(const DescriptorPool* pool);
+
+ ~DynamicMessageFactory();
+
+ // Call this to tell the DynamicMessageFactory that if it is given a
+ // Descriptor d for which:
+ // d->file()->pool() == DescriptorPool::generated_pool(),
+ // then it should delegate to MessageFactory::generated_factory() instead
+ // of constructing a dynamic implementation of the message. In theory there
+ // is no down side to doing this, so it may become the default in the future.
+ void SetDelegateToGeneratedFactory(bool enable) {
+ delegate_to_generated_factory_ = enable;
+ }
+
+ // implements MessageFactory ---------------------------------------
+
+ // Given a Descriptor, constructs the default (prototype) Message of that
+ // type. You can then call that message's New() method to construct a
+ // mutable message of that type.
+ //
+ // Calling this method twice with the same Descriptor returns the same
+ // object. The returned object remains property of the factory and will
+ // be destroyed when the factory is destroyed. Also, any objects created
+ // by calling the prototype's New() method share some data with the
+ // prototype, so these must be destroyed before the DynamicMessageFactory
+ // is destroyed.
+ //
+ // The given descriptor must outlive the returned message, and hence must
+ // outlive the DynamicMessageFactory.
+ //
+ // The method is thread-safe.
+ const Message* GetPrototype(const Descriptor* type);
+
+ private:
+ const DescriptorPool* pool_;
+ bool delegate_to_generated_factory_;
+
+ // This struct just contains a hash_map. We can't #include <google/protobuf/stubs/hash.h> from
+ // this header due to hacks needed for hash_map portability in the open source
+ // release. Namely, stubs/hash.h, which defines hash_map portably, is not a
+ // public header (for good reason), but dynamic_message.h is, and public
+ // headers may only #include other public headers.
+ struct PrototypeMap;
+ google::protobuf::scoped_ptr<PrototypeMap> prototypes_;
+ mutable Mutex prototypes_mutex_;
+
+ friend class DynamicMessage;
+ const Message* GetPrototypeNoLock(const Descriptor* type);
+
+ // Construct default oneof instance for reflection usage if oneof
+ // is defined.
+ static void ConstructDefaultOneofInstance(const Descriptor* type,
+ const int offsets[],
+ void* default_oneof_instance);
+ // Delete default oneof instance. Called by ~DynamicMessageFactory.
+ static void DeleteDefaultOneofInstance(const Descriptor* type,
+ const int offsets[],
+ void* default_oneof_instance);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DynamicMessageFactory);
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_DYNAMIC_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message_unittest.cc
new file mode 100644
index 0000000000..fe51d8cfdc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/dynamic_message_unittest.cc
@@ -0,0 +1,291 @@
+// 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.
+//
+// Since the reflection interface for DynamicMessage is implemented by
+// GenericMessageReflection, the only thing we really have to test is
+// that DynamicMessage correctly sets up the information that
+// GenericMessageReflection needs to use. So, we focus on that in this
+// test. Other tests, such as generic_message_reflection_unittest and
+// reflection_ops_unittest, cover the rest of the functionality used by
+// DynamicMessage.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_no_field_presence.pb.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+class DynamicMessageTest : public testing::Test {
+ protected:
+ DescriptorPool pool_;
+ DynamicMessageFactory factory_;
+ const Descriptor* descriptor_;
+ const Message* prototype_;
+ const Descriptor* extensions_descriptor_;
+ const Message* extensions_prototype_;
+ const Descriptor* packed_descriptor_;
+ const Message* packed_prototype_;
+ const Descriptor* oneof_descriptor_;
+ const Message* oneof_prototype_;
+ const Descriptor* proto3_descriptor_;
+ const Message* proto3_prototype_;
+
+ DynamicMessageTest(): factory_(&pool_) {}
+
+ virtual void SetUp() {
+ // We want to make sure that DynamicMessage works (particularly with
+ // extensions) even if we use descriptors that are *not* from compiled-in
+ // types, so we make copies of the descriptors for unittest.proto and
+ // unittest_import.proto.
+ FileDescriptorProto unittest_file;
+ FileDescriptorProto unittest_import_file;
+ FileDescriptorProto unittest_import_public_file;
+ FileDescriptorProto unittest_no_field_presence_file;
+
+ unittest::TestAllTypes::descriptor()->file()->CopyTo(&unittest_file);
+ unittest_import::ImportMessage::descriptor()->file()->CopyTo(
+ &unittest_import_file);
+ unittest_import::PublicImportMessage::descriptor()->file()->CopyTo(
+ &unittest_import_public_file);
+ proto2_nofieldpresence_unittest::TestAllTypes::descriptor()->
+ file()->CopyTo(&unittest_no_field_presence_file);
+
+ ASSERT_TRUE(pool_.BuildFile(unittest_import_public_file) != NULL);
+ ASSERT_TRUE(pool_.BuildFile(unittest_import_file) != NULL);
+ ASSERT_TRUE(pool_.BuildFile(unittest_file) != NULL);
+ ASSERT_TRUE(pool_.BuildFile(unittest_no_field_presence_file) != NULL);
+
+ descriptor_ = pool_.FindMessageTypeByName("protobuf_unittest.TestAllTypes");
+ ASSERT_TRUE(descriptor_ != NULL);
+ prototype_ = factory_.GetPrototype(descriptor_);
+
+ extensions_descriptor_ =
+ pool_.FindMessageTypeByName("protobuf_unittest.TestAllExtensions");
+ ASSERT_TRUE(extensions_descriptor_ != NULL);
+ extensions_prototype_ = factory_.GetPrototype(extensions_descriptor_);
+
+ packed_descriptor_ =
+ pool_.FindMessageTypeByName("protobuf_unittest.TestPackedTypes");
+ ASSERT_TRUE(packed_descriptor_ != NULL);
+ packed_prototype_ = factory_.GetPrototype(packed_descriptor_);
+
+ oneof_descriptor_ =
+ pool_.FindMessageTypeByName("protobuf_unittest.TestOneof2");
+ ASSERT_TRUE(oneof_descriptor_ != NULL);
+ oneof_prototype_ = factory_.GetPrototype(oneof_descriptor_);
+
+ proto3_descriptor_ =
+ pool_.FindMessageTypeByName(
+ "proto2_nofieldpresence_unittest.TestAllTypes");
+ ASSERT_TRUE(proto3_descriptor_ != NULL);
+ proto3_prototype_ = factory_.GetPrototype(proto3_descriptor_);
+ }
+};
+
+TEST_F(DynamicMessageTest, Descriptor) {
+ // Check that the descriptor on the DynamicMessage matches the descriptor
+ // passed to GetPrototype().
+ EXPECT_EQ(prototype_->GetDescriptor(), descriptor_);
+}
+
+TEST_F(DynamicMessageTest, OnePrototype) {
+ // Check that requesting the same prototype twice produces the same object.
+ EXPECT_EQ(prototype_, factory_.GetPrototype(descriptor_));
+}
+
+TEST_F(DynamicMessageTest, Defaults) {
+ // Check that all default values are set correctly in the initial message.
+ TestUtil::ReflectionTester reflection_tester(descriptor_);
+ reflection_tester.ExpectClearViaReflection(*prototype_);
+}
+
+TEST_F(DynamicMessageTest, IndependentOffsets) {
+ // Check that all fields have independent offsets by setting each
+ // one to a unique value then checking that they all still have those
+ // unique values (i.e. they don't stomp each other).
+ google::protobuf::scoped_ptr<Message> message(prototype_->New());
+ TestUtil::ReflectionTester reflection_tester(descriptor_);
+
+ reflection_tester.SetAllFieldsViaReflection(message.get());
+ reflection_tester.ExpectAllFieldsSetViaReflection(*message);
+}
+
+TEST_F(DynamicMessageTest, Extensions) {
+ // Check that extensions work.
+ google::protobuf::scoped_ptr<Message> message(extensions_prototype_->New());
+ TestUtil::ReflectionTester reflection_tester(extensions_descriptor_);
+
+ reflection_tester.SetAllFieldsViaReflection(message.get());
+ reflection_tester.ExpectAllFieldsSetViaReflection(*message);
+}
+
+TEST_F(DynamicMessageTest, PackedFields) {
+ // Check that packed fields work properly.
+ google::protobuf::scoped_ptr<Message> message(packed_prototype_->New());
+ TestUtil::ReflectionTester reflection_tester(packed_descriptor_);
+
+ reflection_tester.SetPackedFieldsViaReflection(message.get());
+ reflection_tester.ExpectPackedFieldsSetViaReflection(*message);
+}
+
+TEST_F(DynamicMessageTest, Oneof) {
+ // Check that oneof fields work properly.
+ google::protobuf::scoped_ptr<Message> message(oneof_prototype_->New());
+
+ // Check default values.
+ const Descriptor* descriptor = message->GetDescriptor();
+ const Reflection* reflection = message->GetReflection();
+ EXPECT_EQ(0, reflection->GetInt32(
+ *message, descriptor->FindFieldByName("foo_int")));
+ EXPECT_EQ("", reflection->GetString(
+ *message, descriptor->FindFieldByName("foo_string")));
+ EXPECT_EQ("", reflection->GetString(
+ *message, descriptor->FindFieldByName("foo_cord")));
+ EXPECT_EQ("", reflection->GetString(
+ *message, descriptor->FindFieldByName("foo_string_piece")));
+ EXPECT_EQ("", reflection->GetString(
+ *message, descriptor->FindFieldByName("foo_bytes")));
+ EXPECT_EQ(unittest::TestOneof2::FOO, reflection->GetEnum(
+ *message, descriptor->FindFieldByName("foo_enum"))->number());
+ const Descriptor* nested_descriptor;
+ const Message* nested_prototype;
+ nested_descriptor =
+ pool_.FindMessageTypeByName("protobuf_unittest.TestOneof2.NestedMessage");
+ nested_prototype = factory_.GetPrototype(nested_descriptor);
+ EXPECT_EQ(nested_prototype,
+ &reflection->GetMessage(
+ *message, descriptor->FindFieldByName("foo_message")));
+ const Descriptor* foogroup_descriptor;
+ const Message* foogroup_prototype;
+ foogroup_descriptor =
+ pool_.FindMessageTypeByName("protobuf_unittest.TestOneof2.FooGroup");
+ foogroup_prototype = factory_.GetPrototype(foogroup_descriptor);
+ EXPECT_EQ(foogroup_prototype,
+ &reflection->GetMessage(
+ *message, descriptor->FindFieldByName("foogroup")));
+ EXPECT_NE(foogroup_prototype,
+ &reflection->GetMessage(
+ *message, descriptor->FindFieldByName("foo_lazy_message")));
+ EXPECT_EQ(5, reflection->GetInt32(
+ *message, descriptor->FindFieldByName("bar_int")));
+ EXPECT_EQ("STRING", reflection->GetString(
+ *message, descriptor->FindFieldByName("bar_string")));
+ EXPECT_EQ("CORD", reflection->GetString(
+ *message, descriptor->FindFieldByName("bar_cord")));
+ EXPECT_EQ("SPIECE", reflection->GetString(
+ *message, descriptor->FindFieldByName("bar_string_piece")));
+ EXPECT_EQ("BYTES", reflection->GetString(
+ *message, descriptor->FindFieldByName("bar_bytes")));
+ EXPECT_EQ(unittest::TestOneof2::BAR, reflection->GetEnum(
+ *message, descriptor->FindFieldByName("bar_enum"))->number());
+
+ // Check set functions.
+ TestUtil::ReflectionTester reflection_tester(oneof_descriptor_);
+ reflection_tester.SetOneofViaReflection(message.get());
+ reflection_tester.ExpectOneofSetViaReflection(*message);
+}
+
+TEST_F(DynamicMessageTest, SpaceUsed) {
+ // Test that SpaceUsed() works properly
+
+ // Since we share the implementation with generated messages, we don't need
+ // to test very much here. Just make sure it appears to be working.
+
+ google::protobuf::scoped_ptr<Message> message(prototype_->New());
+ TestUtil::ReflectionTester reflection_tester(descriptor_);
+
+ int initial_space_used = message->SpaceUsed();
+
+ reflection_tester.SetAllFieldsViaReflection(message.get());
+ EXPECT_LT(initial_space_used, message->SpaceUsed());
+}
+
+TEST_F(DynamicMessageTest, Arena) {
+ Arena arena;
+ Message* message = prototype_->New(&arena);
+ (void)message; // avoid unused-variable error.
+ // Return without freeing: should not leak.
+}
+
+TEST_F(DynamicMessageTest, Proto3) {
+ Message* message = proto3_prototype_->New();
+ const Reflection* refl = message->GetReflection();
+ const Descriptor* desc = message->GetDescriptor();
+
+ // Just test a single primtive and single message field here to make sure we
+ // are getting the no-field-presence semantics elsewhere. DynamicMessage uses
+ // GeneratedMessageReflection under the hood, so the rest should be fine as
+ // long as GMR recognizes that we're using a proto3 message.
+ const FieldDescriptor* optional_int32 =
+ desc->FindFieldByName("optional_int32");
+ const FieldDescriptor* optional_msg =
+ desc->FindFieldByName("optional_nested_message");
+ EXPECT_TRUE(optional_int32 != NULL);
+ EXPECT_TRUE(optional_msg != NULL);
+
+ EXPECT_EQ(false, refl->HasField(*message, optional_int32));
+ refl->SetInt32(message, optional_int32, 42);
+ EXPECT_EQ(true, refl->HasField(*message, optional_int32));
+ refl->SetInt32(message, optional_int32, 0);
+ EXPECT_EQ(false, refl->HasField(*message, optional_int32));
+
+ EXPECT_EQ(false, refl->HasField(*message, optional_msg));
+ refl->MutableMessage(message, optional_msg);
+ EXPECT_EQ(true, refl->HasField(*message, optional_msg));
+ delete refl->ReleaseMessage(message, optional_msg);
+ EXPECT_EQ(false, refl->HasField(*message, optional_msg));
+
+ // Also ensure that the default instance handles field presence properly.
+ EXPECT_EQ(false, refl->HasField(*proto3_prototype_, optional_msg));
+
+ delete message;
+}
+
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.cc
new file mode 100644
index 0000000000..83775753ad
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.cc
@@ -0,0 +1,316 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/empty.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/empty.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* Empty_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Empty_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fempty_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fempty_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fempty_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/empty.proto");
+ GOOGLE_CHECK(file != NULL);
+ Empty_descriptor_ = file->message_type(0);
+ static const int Empty_offsets_[1] = {
+ };
+ Empty_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Empty_descriptor_,
+ Empty::default_instance_,
+ Empty_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Empty),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Empty, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Empty, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fempty_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Empty_descriptor_, &Empty::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fempty_2eproto() {
+ delete Empty::default_instance_;
+ delete Empty_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fempty_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fempty_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n\033google/protobuf/empty.proto\022\017google.pr"
+ "otobuf\"\007\n\005EmptyBy\n\023com.google.protobufB\n"
+ "EmptyProtoP\001Z\'github.com/golang/protobuf"
+ "/ptypes/empty\240\001\001\370\001\001\242\002\003GPB\252\002\036Google.Proto"
+ "buf.WellKnownTypesb\006proto3", 186);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/empty.proto", &protobuf_RegisterTypes);
+ Empty::default_instance_ = new Empty();
+ Empty::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fempty_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fempty_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fempty_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fempty_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fempty_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Empty::Empty()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Empty)
+}
+
+Empty::Empty(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.Empty)
+}
+
+void Empty::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Empty::Empty(const Empty& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Empty)
+}
+
+void Empty::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+}
+
+Empty::~Empty() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Empty)
+ SharedDtor();
+}
+
+void Empty::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void Empty::ArenaDtor(void* object) {
+ Empty* _this = reinterpret_cast< Empty* >(object);
+ (void)_this;
+}
+void Empty::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void Empty::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Empty::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Empty_descriptor_;
+}
+
+const Empty& Empty::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fempty_2eproto();
+ return *default_instance_;
+}
+
+Empty* Empty::default_instance_ = NULL;
+
+Empty* Empty::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<Empty>(arena);
+}
+
+void Empty::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Empty)
+}
+
+bool Empty::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Empty)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ handle_unusual:
+ if (tag == 0 ||
+ ::google::protobuf::internal::WireFormatLite::GetTagWireType(tag) ==
+ ::google::protobuf::internal::WireFormatLite::WIRETYPE_END_GROUP) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Empty)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Empty)
+ return false;
+#undef DO_
+}
+
+void Empty::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Empty)
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Empty)
+}
+
+::google::protobuf::uint8* Empty::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Empty)
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Empty)
+ return target;
+}
+
+int Empty::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Empty)
+ int total_size = 0;
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Empty::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Empty)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Empty* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Empty>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Empty)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Empty)
+ MergeFrom(*source);
+ }
+}
+
+void Empty::MergeFrom(const Empty& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Empty)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+}
+
+void Empty::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Empty)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Empty::CopyFrom(const Empty& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Empty)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Empty::IsInitialized() const {
+
+ return true;
+}
+
+void Empty::Swap(Empty* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ Empty temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void Empty::UnsafeArenaSwap(Empty* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void Empty::InternalSwap(Empty* other) {
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Empty::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Empty_descriptor_;
+ metadata.reflection = Empty_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Empty
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.h
new file mode 100644
index 0000000000..8e78733b50
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/empty.pb.h
@@ -0,0 +1,147 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/empty.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fempty_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fempty_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fempty_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fempty_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fempty_2eproto();
+
+class Empty;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT Empty : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Empty) */ {
+ public:
+ Empty();
+ virtual ~Empty();
+
+ Empty(const Empty& from);
+
+ inline Empty& operator=(const Empty& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Empty& default_instance();
+
+ void UnsafeArenaSwap(Empty* other);
+ void Swap(Empty* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Empty* New() const { return New(NULL); }
+
+ Empty* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Empty& from);
+ void MergeFrom(const Empty& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Empty* other);
+ protected:
+ explicit Empty(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Empty)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fempty_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fempty_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fempty_2eproto();
+
+ void InitAsDefaultInstance();
+ static Empty* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// Empty
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fempty_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/empty.proto b/third_party/protobuf/3.0.0/src/google/protobuf/empty.proto
new file mode 100644
index 0000000000..37f4cd10ee
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/empty.proto
@@ -0,0 +1,53 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option go_package = "github.com/golang/protobuf/ptypes/empty";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "EmptyProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+option cc_enable_arenas = true;
+
+// A generic empty message that you can re-use to avoid defining duplicated
+// empty messages in your APIs. A typical example is to use it as the request
+// or the response type of an API method. For instance:
+//
+// service Foo {
+// rpc Bar(google.protobuf.Empty) returns (google.protobuf.Empty);
+// }
+//
+// The JSON representation for `Empty` is empty JSON object `{}`.
+message Empty {}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/extension_set.cc b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set.cc
new file mode 100644
index 0000000000..7d20a0f8f8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set.cc
@@ -0,0 +1,1816 @@
+// 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.
+
+#include <google/protobuf/stubs/hash.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/once.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/message_lite.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/stubs/map_util.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+namespace {
+
+inline WireFormatLite::FieldType real_type(FieldType type) {
+ GOOGLE_DCHECK(type > 0 && type <= WireFormatLite::MAX_FIELD_TYPE);
+ return static_cast<WireFormatLite::FieldType>(type);
+}
+
+inline WireFormatLite::CppType cpp_type(FieldType type) {
+ return WireFormatLite::FieldTypeToCppType(real_type(type));
+}
+
+inline bool is_packable(WireFormatLite::WireType type) {
+ switch (type) {
+ case WireFormatLite::WIRETYPE_VARINT:
+ case WireFormatLite::WIRETYPE_FIXED64:
+ case WireFormatLite::WIRETYPE_FIXED32:
+ return true;
+ case WireFormatLite::WIRETYPE_LENGTH_DELIMITED:
+ case WireFormatLite::WIRETYPE_START_GROUP:
+ case WireFormatLite::WIRETYPE_END_GROUP:
+ return false;
+
+ // Do not add a default statement. Let the compiler complain when someone
+ // adds a new wire type.
+ }
+ GOOGLE_LOG(FATAL) << "can't reach here.";
+ return false;
+}
+
+// Registry stuff.
+typedef hash_map<pair<const MessageLite*, int>,
+ ExtensionInfo> ExtensionRegistry;
+ExtensionRegistry* registry_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(registry_init_);
+
+void DeleteRegistry() {
+ delete registry_;
+ registry_ = NULL;
+}
+
+void InitRegistry() {
+ registry_ = new ExtensionRegistry;
+ OnShutdown(&DeleteRegistry);
+}
+
+// This function is only called at startup, so there is no need for thread-
+// safety.
+void Register(const MessageLite* containing_type,
+ int number, ExtensionInfo info) {
+ ::google::protobuf::GoogleOnceInit(&registry_init_, &InitRegistry);
+
+ if (!InsertIfNotPresent(registry_, std::make_pair(containing_type, number),
+ info)) {
+ GOOGLE_LOG(FATAL) << "Multiple extension registrations for type \""
+ << containing_type->GetTypeName()
+ << "\", field number " << number << ".";
+ }
+}
+
+const ExtensionInfo* FindRegisteredExtension(
+ const MessageLite* containing_type, int number) {
+ return (registry_ == NULL)
+ ? NULL
+ : FindOrNull(*registry_, std::make_pair(containing_type, number));
+}
+
+} // namespace
+
+ExtensionFinder::~ExtensionFinder() {}
+
+bool GeneratedExtensionFinder::Find(int number, ExtensionInfo* output) {
+ const ExtensionInfo* extension =
+ FindRegisteredExtension(containing_type_, number);
+ if (extension == NULL) {
+ return false;
+ } else {
+ *output = *extension;
+ return true;
+ }
+}
+
+void ExtensionSet::RegisterExtension(const MessageLite* containing_type,
+ int number, FieldType type,
+ bool is_repeated, bool is_packed) {
+ GOOGLE_CHECK_NE(type, WireFormatLite::TYPE_ENUM);
+ GOOGLE_CHECK_NE(type, WireFormatLite::TYPE_MESSAGE);
+ GOOGLE_CHECK_NE(type, WireFormatLite::TYPE_GROUP);
+ ExtensionInfo info(type, is_repeated, is_packed);
+ Register(containing_type, number, info);
+}
+
+static bool CallNoArgValidityFunc(const void* arg, int number) {
+ // Note: Must use C-style cast here rather than reinterpret_cast because
+ // the C++ standard at one point did not allow casts between function and
+ // data pointers and some compilers enforce this for C++-style casts. No
+ // compiler enforces it for C-style casts since lots of C-style code has
+ // relied on these kinds of casts for a long time, despite being
+ // technically undefined. See:
+ // http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#195
+ // Also note: Some compilers do not allow function pointers to be "const".
+ // Which makes sense, I suppose, because it's meaningless.
+ return ((EnumValidityFunc*)arg)(number);
+}
+
+void ExtensionSet::RegisterEnumExtension(const MessageLite* containing_type,
+ int number, FieldType type,
+ bool is_repeated, bool is_packed,
+ EnumValidityFunc* is_valid) {
+ GOOGLE_CHECK_EQ(type, WireFormatLite::TYPE_ENUM);
+ ExtensionInfo info(type, is_repeated, is_packed);
+ info.enum_validity_check.func = CallNoArgValidityFunc;
+ // See comment in CallNoArgValidityFunc() about why we use a c-style cast.
+ info.enum_validity_check.arg = (void*)is_valid;
+ Register(containing_type, number, info);
+}
+
+void ExtensionSet::RegisterMessageExtension(const MessageLite* containing_type,
+ int number, FieldType type,
+ bool is_repeated, bool is_packed,
+ const MessageLite* prototype) {
+ GOOGLE_CHECK(type == WireFormatLite::TYPE_MESSAGE ||
+ type == WireFormatLite::TYPE_GROUP);
+ ExtensionInfo info(type, is_repeated, is_packed);
+ info.message_prototype = prototype;
+ Register(containing_type, number, info);
+}
+
+
+// ===================================================================
+// Constructors and basic methods.
+
+ExtensionSet::ExtensionSet(::google::protobuf::Arena* arena)
+ : arena_(arena) {
+ if (arena_ != NULL) {
+ arena_->OwnDestructor(&extensions_);
+ }
+}
+
+ExtensionSet::ExtensionSet() : arena_(NULL) {}
+
+ExtensionSet::~ExtensionSet() {
+ // Deletes all allocated extensions.
+ if (arena_ == NULL) {
+ for (ExtensionMap::iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ iter->second.Free();
+ }
+ }
+}
+
+// Defined in extension_set_heavy.cc.
+// void ExtensionSet::AppendToList(const Descriptor* containing_type,
+// const DescriptorPool* pool,
+// vector<const FieldDescriptor*>* output) const
+
+bool ExtensionSet::Has(int number) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) return false;
+ GOOGLE_DCHECK(!iter->second.is_repeated);
+ return !iter->second.is_cleared;
+}
+
+int ExtensionSet::NumExtensions() const {
+ int result = 0;
+ for (ExtensionMap::const_iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ if (!iter->second.is_cleared) {
+ ++result;
+ }
+ }
+ return result;
+}
+
+int ExtensionSet::ExtensionSize(int number) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) return false;
+ return iter->second.GetSize();
+}
+
+FieldType ExtensionSet::ExtensionType(int number) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) {
+ GOOGLE_LOG(DFATAL) << "Don't lookup extension types if they aren't present (1). ";
+ return 0;
+ }
+ if (iter->second.is_cleared) {
+ GOOGLE_LOG(DFATAL) << "Don't lookup extension types if they aren't present (2). ";
+ }
+ return iter->second.type;
+}
+
+void ExtensionSet::ClearExtension(int number) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) return;
+ iter->second.Clear();
+}
+
+// ===================================================================
+// Field accessors
+
+namespace {
+
+enum Cardinality {
+ REPEATED,
+ OPTIONAL
+};
+
+} // namespace
+
+#define GOOGLE_DCHECK_TYPE(EXTENSION, LABEL, CPPTYPE) \
+ GOOGLE_DCHECK_EQ((EXTENSION).is_repeated ? REPEATED : OPTIONAL, LABEL); \
+ GOOGLE_DCHECK_EQ(cpp_type((EXTENSION).type), WireFormatLite::CPPTYPE_##CPPTYPE)
+
+// -------------------------------------------------------------------
+// Primitives
+
+#define PRIMITIVE_ACCESSORS(UPPERCASE, LOWERCASE, CAMELCASE) \
+ \
+LOWERCASE ExtensionSet::Get##CAMELCASE(int number, \
+ LOWERCASE default_value) const { \
+ ExtensionMap::const_iterator iter = extensions_.find(number); \
+ if (iter == extensions_.end() || iter->second.is_cleared) { \
+ return default_value; \
+ } else { \
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, UPPERCASE); \
+ return iter->second.LOWERCASE##_value; \
+ } \
+} \
+ \
+void ExtensionSet::Set##CAMELCASE(int number, FieldType type, \
+ LOWERCASE value, \
+ const FieldDescriptor* descriptor) { \
+ Extension* extension; \
+ if (MaybeNewExtension(number, descriptor, &extension)) { \
+ extension->type = type; \
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_##UPPERCASE); \
+ extension->is_repeated = false; \
+ } else { \
+ GOOGLE_DCHECK_TYPE(*extension, OPTIONAL, UPPERCASE); \
+ } \
+ extension->is_cleared = false; \
+ extension->LOWERCASE##_value = value; \
+} \
+ \
+LOWERCASE ExtensionSet::GetRepeated##CAMELCASE(int number, int index) const { \
+ ExtensionMap::const_iterator iter = extensions_.find(number); \
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty)."; \
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, UPPERCASE); \
+ return iter->second.repeated_##LOWERCASE##_value->Get(index); \
+} \
+ \
+void ExtensionSet::SetRepeated##CAMELCASE( \
+ int number, int index, LOWERCASE value) { \
+ ExtensionMap::iterator iter = extensions_.find(number); \
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty)."; \
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, UPPERCASE); \
+ iter->second.repeated_##LOWERCASE##_value->Set(index, value); \
+} \
+ \
+void ExtensionSet::Add##CAMELCASE(int number, FieldType type, \
+ bool packed, LOWERCASE value, \
+ const FieldDescriptor* descriptor) { \
+ Extension* extension; \
+ if (MaybeNewExtension(number, descriptor, &extension)) { \
+ extension->type = type; \
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_##UPPERCASE); \
+ extension->is_repeated = true; \
+ extension->is_packed = packed; \
+ extension->repeated_##LOWERCASE##_value = \
+ Arena::CreateMessage<RepeatedField<LOWERCASE> >(arena_); \
+ } else { \
+ GOOGLE_DCHECK_TYPE(*extension, REPEATED, UPPERCASE); \
+ GOOGLE_DCHECK_EQ(extension->is_packed, packed); \
+ } \
+ extension->repeated_##LOWERCASE##_value->Add(value); \
+}
+
+PRIMITIVE_ACCESSORS( INT32, int32, Int32)
+PRIMITIVE_ACCESSORS( INT64, int64, Int64)
+PRIMITIVE_ACCESSORS(UINT32, uint32, UInt32)
+PRIMITIVE_ACCESSORS(UINT64, uint64, UInt64)
+PRIMITIVE_ACCESSORS( FLOAT, float, Float)
+PRIMITIVE_ACCESSORS(DOUBLE, double, Double)
+PRIMITIVE_ACCESSORS( BOOL, bool, Bool)
+
+#undef PRIMITIVE_ACCESSORS
+
+const void* ExtensionSet::GetRawRepeatedField(int number,
+ const void* default_value) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) {
+ return default_value;
+ }
+ // We assume that all the RepeatedField<>* pointers have the same
+ // size and alignment within the anonymous union in Extension.
+ return iter->second.repeated_int32_value;
+}
+
+void* ExtensionSet::MutableRawRepeatedField(int number, FieldType field_type,
+ bool packed,
+ const FieldDescriptor* desc) {
+ Extension* extension;
+
+ // We instantiate an empty Repeated{,Ptr}Field if one doesn't exist for this
+ // extension.
+ if (MaybeNewExtension(number, desc, &extension)) {
+ extension->is_repeated = true;
+ extension->type = field_type;
+ extension->is_packed = packed;
+
+ switch (WireFormatLite::FieldTypeToCppType(
+ static_cast<WireFormatLite::FieldType>(field_type))) {
+ case WireFormatLite::CPPTYPE_INT32:
+ extension->repeated_int32_value =
+ Arena::CreateMessage<RepeatedField<int32> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_INT64:
+ extension->repeated_int64_value =
+ Arena::CreateMessage<RepeatedField<int64> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_UINT32:
+ extension->repeated_uint32_value =
+ Arena::CreateMessage<RepeatedField<uint32> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_UINT64:
+ extension->repeated_uint64_value =
+ Arena::CreateMessage<RepeatedField<uint64> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_DOUBLE:
+ extension->repeated_double_value =
+ Arena::CreateMessage<RepeatedField<double> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_FLOAT:
+ extension->repeated_float_value =
+ Arena::CreateMessage<RepeatedField<float> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_BOOL:
+ extension->repeated_bool_value =
+ Arena::CreateMessage<RepeatedField<bool> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_ENUM:
+ extension->repeated_enum_value =
+ Arena::CreateMessage<RepeatedField<int> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_STRING:
+ extension->repeated_string_value =
+ Arena::CreateMessage<RepeatedPtrField< ::std::string> >(arena_);
+ break;
+ case WireFormatLite::CPPTYPE_MESSAGE:
+ extension->repeated_message_value =
+ Arena::CreateMessage<RepeatedPtrField<MessageLite> >(arena_);
+ break;
+ }
+ }
+
+ // We assume that all the RepeatedField<>* pointers have the same
+ // size and alignment within the anonymous union in Extension.
+ return extension->repeated_int32_value;
+}
+
+// Compatible version using old call signature. Does not create extensions when
+// the don't already exist; instead, just GOOGLE_CHECK-fails.
+void* ExtensionSet::MutableRawRepeatedField(int number) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter == extensions_.end()) << "Extension not found.";
+ // We assume that all the RepeatedField<>* pointers have the same
+ // size and alignment within the anonymous union in Extension.
+ return iter->second.repeated_int32_value;
+}
+
+
+// -------------------------------------------------------------------
+// Enums
+
+int ExtensionSet::GetEnum(int number, int default_value) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end() || iter->second.is_cleared) {
+ // Not present. Return the default value.
+ return default_value;
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, ENUM);
+ return iter->second.enum_value;
+ }
+}
+
+void ExtensionSet::SetEnum(int number, FieldType type, int value,
+ const FieldDescriptor* descriptor) {
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_ENUM);
+ extension->is_repeated = false;
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, OPTIONAL, ENUM);
+ }
+ extension->is_cleared = false;
+ extension->enum_value = value;
+}
+
+int ExtensionSet::GetRepeatedEnum(int number, int index) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, ENUM);
+ return iter->second.repeated_enum_value->Get(index);
+}
+
+void ExtensionSet::SetRepeatedEnum(int number, int index, int value) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, ENUM);
+ iter->second.repeated_enum_value->Set(index, value);
+}
+
+void ExtensionSet::AddEnum(int number, FieldType type,
+ bool packed, int value,
+ const FieldDescriptor* descriptor) {
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_ENUM);
+ extension->is_repeated = true;
+ extension->is_packed = packed;
+ extension->repeated_enum_value =
+ Arena::CreateMessage<RepeatedField<int> >(arena_);
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, REPEATED, ENUM);
+ GOOGLE_DCHECK_EQ(extension->is_packed, packed);
+ }
+ extension->repeated_enum_value->Add(value);
+}
+
+// -------------------------------------------------------------------
+// Strings
+
+const string& ExtensionSet::GetString(int number,
+ const string& default_value) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end() || iter->second.is_cleared) {
+ // Not present. Return the default value.
+ return default_value;
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, STRING);
+ return *iter->second.string_value;
+ }
+}
+
+string* ExtensionSet::MutableString(int number, FieldType type,
+ const FieldDescriptor* descriptor) {
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_STRING);
+ extension->is_repeated = false;
+ extension->string_value = Arena::Create<string>(arena_);
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, OPTIONAL, STRING);
+ }
+ extension->is_cleared = false;
+ return extension->string_value;
+}
+
+const string& ExtensionSet::GetRepeatedString(int number, int index) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, STRING);
+ return iter->second.repeated_string_value->Get(index);
+}
+
+string* ExtensionSet::MutableRepeatedString(int number, int index) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, STRING);
+ return iter->second.repeated_string_value->Mutable(index);
+}
+
+string* ExtensionSet::AddString(int number, FieldType type,
+ const FieldDescriptor* descriptor) {
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_STRING);
+ extension->is_repeated = true;
+ extension->is_packed = false;
+ extension->repeated_string_value =
+ Arena::CreateMessage<RepeatedPtrField<string> >(arena_);
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, REPEATED, STRING);
+ }
+ return extension->repeated_string_value->Add();
+}
+
+// -------------------------------------------------------------------
+// Messages
+
+const MessageLite& ExtensionSet::GetMessage(
+ int number, const MessageLite& default_value) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) {
+ // Not present. Return the default value.
+ return default_value;
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, MESSAGE);
+ if (iter->second.is_lazy) {
+ return iter->second.lazymessage_value->GetMessage(default_value);
+ } else {
+ return *iter->second.message_value;
+ }
+ }
+}
+
+// Defined in extension_set_heavy.cc.
+// const MessageLite& ExtensionSet::GetMessage(int number,
+// const Descriptor* message_type,
+// MessageFactory* factory) const
+
+MessageLite* ExtensionSet::MutableMessage(int number, FieldType type,
+ const MessageLite& prototype,
+ const FieldDescriptor* descriptor) {
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_MESSAGE);
+ extension->is_repeated = false;
+ extension->is_lazy = false;
+ extension->message_value = prototype.New(arena_);
+ extension->is_cleared = false;
+ return extension->message_value;
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, OPTIONAL, MESSAGE);
+ extension->is_cleared = false;
+ if (extension->is_lazy) {
+ return extension->lazymessage_value->MutableMessage(prototype);
+ } else {
+ return extension->message_value;
+ }
+ }
+}
+
+// Defined in extension_set_heavy.cc.
+// MessageLite* ExtensionSet::MutableMessage(int number, FieldType type,
+// const Descriptor* message_type,
+// MessageFactory* factory)
+
+void ExtensionSet::SetAllocatedMessage(int number, FieldType type,
+ const FieldDescriptor* descriptor,
+ MessageLite* message) {
+ if (message == NULL) {
+ ClearExtension(number);
+ return;
+ }
+ ::google::protobuf::Arena* message_arena = message->GetArena();
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_MESSAGE);
+ extension->is_repeated = false;
+ extension->is_lazy = false;
+ if (message_arena == arena_) {
+ extension->message_value = message;
+ } else if (message_arena == NULL) {
+ extension->message_value = message;
+ arena_->Own(message); // not NULL because not equal to message_arena
+ } else {
+ extension->message_value = message->New(arena_);
+ extension->message_value->CheckTypeAndMergeFrom(*message);
+ }
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, OPTIONAL, MESSAGE);
+ if (extension->is_lazy) {
+ extension->lazymessage_value->SetAllocatedMessage(message);
+ } else {
+ if (arena_ == NULL) {
+ delete extension->message_value;
+ }
+ if (message_arena == arena_) {
+ extension->message_value = message;
+ } else if (message_arena == NULL) {
+ extension->message_value = message;
+ arena_->Own(message); // not NULL because not equal to message_arena
+ } else {
+ extension->message_value = message->New(arena_);
+ extension->message_value->CheckTypeAndMergeFrom(*message);
+ }
+ }
+ }
+ extension->is_cleared = false;
+}
+
+void ExtensionSet::UnsafeArenaSetAllocatedMessage(
+ int number, FieldType type, const FieldDescriptor* descriptor,
+ MessageLite* message) {
+ if (message == NULL) {
+ ClearExtension(number);
+ return;
+ }
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_MESSAGE);
+ extension->is_repeated = false;
+ extension->is_lazy = false;
+ extension->message_value = message;
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, OPTIONAL, MESSAGE);
+ if (extension->is_lazy) {
+ extension->lazymessage_value->UnsafeArenaSetAllocatedMessage(message);
+ } else {
+ if (arena_ == NULL) {
+ delete extension->message_value;
+ }
+ extension->message_value = message;
+ }
+ }
+ extension->is_cleared = false;
+}
+
+
+MessageLite* ExtensionSet::ReleaseMessage(int number,
+ const MessageLite& prototype) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) {
+ // Not present. Return NULL.
+ return NULL;
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, MESSAGE);
+ MessageLite* ret = NULL;
+ if (iter->second.is_lazy) {
+ ret = iter->second.lazymessage_value->ReleaseMessage(prototype);
+ if (arena_ == NULL) {
+ delete iter->second.lazymessage_value;
+ }
+ } else {
+ if (arena_ == NULL) {
+ ret = iter->second.message_value;
+ } else {
+ // ReleaseMessage() always returns a heap-allocated message, and we are
+ // on an arena, so we need to make a copy of this message to return.
+ ret = (iter->second.message_value)->New();
+ ret->CheckTypeAndMergeFrom(*iter->second.message_value);
+ }
+ }
+ extensions_.erase(number);
+ return ret;
+ }
+}
+
+MessageLite* ExtensionSet::UnsafeArenaReleaseMessage(
+ int number, const MessageLite& prototype) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ if (iter == extensions_.end()) {
+ // Not present. Return NULL.
+ return NULL;
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, MESSAGE);
+ MessageLite* ret = NULL;
+ if (iter->second.is_lazy) {
+ ret =
+ iter->second.lazymessage_value->UnsafeArenaReleaseMessage(prototype);
+ if (arena_ == NULL) {
+ delete iter->second.lazymessage_value;
+ }
+ } else {
+ ret = iter->second.message_value;
+ }
+ extensions_.erase(number);
+ return ret;
+ }
+}
+
+// Defined in extension_set_heavy.cc.
+// MessageLite* ExtensionSet::ReleaseMessage(const FieldDescriptor* descriptor,
+// MessageFactory* factory);
+
+const MessageLite& ExtensionSet::GetRepeatedMessage(
+ int number, int index) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, MESSAGE);
+ return iter->second.repeated_message_value->Get(index);
+}
+
+MessageLite* ExtensionSet::MutableRepeatedMessage(int number, int index) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+ GOOGLE_DCHECK_TYPE(iter->second, REPEATED, MESSAGE);
+ return iter->second.repeated_message_value->Mutable(index);
+}
+
+MessageLite* ExtensionSet::AddMessage(int number, FieldType type,
+ const MessageLite& prototype,
+ const FieldDescriptor* descriptor) {
+ Extension* extension;
+ if (MaybeNewExtension(number, descriptor, &extension)) {
+ extension->type = type;
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), WireFormatLite::CPPTYPE_MESSAGE);
+ extension->is_repeated = true;
+ extension->repeated_message_value =
+ Arena::CreateMessage<RepeatedPtrField<MessageLite> >(arena_);
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, REPEATED, MESSAGE);
+ }
+
+ // RepeatedPtrField<MessageLite> does not know how to Add() since it cannot
+ // allocate an abstract object, so we have to be tricky.
+ MessageLite* result = extension->repeated_message_value
+ ->AddFromCleared<GenericTypeHandler<MessageLite> >();
+ if (result == NULL) {
+ result = prototype.New(arena_);
+ extension->repeated_message_value->AddAllocated(result);
+ }
+ return result;
+}
+
+// Defined in extension_set_heavy.cc.
+// MessageLite* ExtensionSet::AddMessage(int number, FieldType type,
+// const Descriptor* message_type,
+// MessageFactory* factory)
+
+#undef GOOGLE_DCHECK_TYPE
+
+void ExtensionSet::RemoveLast(int number) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+
+ Extension* extension = &iter->second;
+ GOOGLE_DCHECK(extension->is_repeated);
+
+ switch(cpp_type(extension->type)) {
+ case WireFormatLite::CPPTYPE_INT32:
+ extension->repeated_int32_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_INT64:
+ extension->repeated_int64_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_UINT32:
+ extension->repeated_uint32_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_UINT64:
+ extension->repeated_uint64_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_FLOAT:
+ extension->repeated_float_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_DOUBLE:
+ extension->repeated_double_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_BOOL:
+ extension->repeated_bool_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_ENUM:
+ extension->repeated_enum_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_STRING:
+ extension->repeated_string_value->RemoveLast();
+ break;
+ case WireFormatLite::CPPTYPE_MESSAGE:
+ extension->repeated_message_value->RemoveLast();
+ break;
+ }
+}
+
+MessageLite* ExtensionSet::ReleaseLast(int number) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+
+ Extension* extension = &iter->second;
+ GOOGLE_DCHECK(extension->is_repeated);
+ GOOGLE_DCHECK(cpp_type(extension->type) == WireFormatLite::CPPTYPE_MESSAGE);
+ return extension->repeated_message_value->ReleaseLast();
+}
+
+void ExtensionSet::SwapElements(int number, int index1, int index2) {
+ ExtensionMap::iterator iter = extensions_.find(number);
+ GOOGLE_CHECK(iter != extensions_.end()) << "Index out-of-bounds (field is empty).";
+
+ Extension* extension = &iter->second;
+ GOOGLE_DCHECK(extension->is_repeated);
+
+ switch(cpp_type(extension->type)) {
+ case WireFormatLite::CPPTYPE_INT32:
+ extension->repeated_int32_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_INT64:
+ extension->repeated_int64_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_UINT32:
+ extension->repeated_uint32_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_UINT64:
+ extension->repeated_uint64_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_FLOAT:
+ extension->repeated_float_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_DOUBLE:
+ extension->repeated_double_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_BOOL:
+ extension->repeated_bool_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_ENUM:
+ extension->repeated_enum_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_STRING:
+ extension->repeated_string_value->SwapElements(index1, index2);
+ break;
+ case WireFormatLite::CPPTYPE_MESSAGE:
+ extension->repeated_message_value->SwapElements(index1, index2);
+ break;
+ }
+}
+
+// ===================================================================
+
+void ExtensionSet::Clear() {
+ for (ExtensionMap::iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ iter->second.Clear();
+ }
+}
+
+void ExtensionSet::MergeFrom(const ExtensionSet& other) {
+ for (ExtensionMap::const_iterator iter = other.extensions_.begin();
+ iter != other.extensions_.end(); ++iter) {
+ const Extension& other_extension = iter->second;
+ InternalExtensionMergeFrom(iter->first, other_extension);
+ }
+}
+
+void ExtensionSet::InternalExtensionMergeFrom(
+ int number, const Extension& other_extension) {
+ if (other_extension.is_repeated) {
+ Extension* extension;
+ bool is_new = MaybeNewExtension(number, other_extension.descriptor,
+ &extension);
+ if (is_new) {
+ // Extension did not already exist in set.
+ extension->type = other_extension.type;
+ extension->is_packed = other_extension.is_packed;
+ extension->is_repeated = true;
+ } else {
+ GOOGLE_DCHECK_EQ(extension->type, other_extension.type);
+ GOOGLE_DCHECK_EQ(extension->is_packed, other_extension.is_packed);
+ GOOGLE_DCHECK(extension->is_repeated);
+ }
+
+ switch (cpp_type(other_extension.type)) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE, REPEATED_TYPE) \
+ case WireFormatLite::CPPTYPE_##UPPERCASE: \
+ if (is_new) { \
+ extension->repeated_##LOWERCASE##_value = \
+ Arena::CreateMessage<REPEATED_TYPE >(arena_); \
+ } \
+ extension->repeated_##LOWERCASE##_value->MergeFrom( \
+ *other_extension.repeated_##LOWERCASE##_value); \
+ break;
+
+ HANDLE_TYPE( INT32, int32, RepeatedField < int32>);
+ HANDLE_TYPE( INT64, int64, RepeatedField < int64>);
+ HANDLE_TYPE( UINT32, uint32, RepeatedField < uint32>);
+ HANDLE_TYPE( UINT64, uint64, RepeatedField < uint64>);
+ HANDLE_TYPE( FLOAT, float, RepeatedField < float>);
+ HANDLE_TYPE( DOUBLE, double, RepeatedField < double>);
+ HANDLE_TYPE( BOOL, bool, RepeatedField < bool>);
+ HANDLE_TYPE( ENUM, enum, RepeatedField < int>);
+ HANDLE_TYPE( STRING, string, RepeatedPtrField< string>);
+#undef HANDLE_TYPE
+
+ case WireFormatLite::CPPTYPE_MESSAGE:
+ if (is_new) {
+ extension->repeated_message_value =
+ Arena::CreateMessage<RepeatedPtrField<MessageLite> >(arena_);
+ }
+ // We can't call RepeatedPtrField<MessageLite>::MergeFrom() because
+ // it would attempt to allocate new objects.
+ RepeatedPtrField<MessageLite>* other_repeated_message =
+ other_extension.repeated_message_value;
+ for (int i = 0; i < other_repeated_message->size(); i++) {
+ const MessageLite& other_message = other_repeated_message->Get(i);
+ MessageLite* target = extension->repeated_message_value
+ ->AddFromCleared<GenericTypeHandler<MessageLite> >();
+ if (target == NULL) {
+ target = other_message.New(arena_);
+ extension->repeated_message_value->AddAllocated(target);
+ }
+ target->CheckTypeAndMergeFrom(other_message);
+ }
+ break;
+ }
+ } else {
+ if (!other_extension.is_cleared) {
+ switch (cpp_type(other_extension.type)) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE, CAMELCASE) \
+ case WireFormatLite::CPPTYPE_##UPPERCASE: \
+ Set##CAMELCASE(number, other_extension.type, \
+ other_extension.LOWERCASE##_value, \
+ other_extension.descriptor); \
+ break;
+
+ HANDLE_TYPE( INT32, int32, Int32);
+ HANDLE_TYPE( INT64, int64, Int64);
+ HANDLE_TYPE(UINT32, uint32, UInt32);
+ HANDLE_TYPE(UINT64, uint64, UInt64);
+ HANDLE_TYPE( FLOAT, float, Float);
+ HANDLE_TYPE(DOUBLE, double, Double);
+ HANDLE_TYPE( BOOL, bool, Bool);
+ HANDLE_TYPE( ENUM, enum, Enum);
+#undef HANDLE_TYPE
+ case WireFormatLite::CPPTYPE_STRING:
+ SetString(number, other_extension.type,
+ *other_extension.string_value,
+ other_extension.descriptor);
+ break;
+ case WireFormatLite::CPPTYPE_MESSAGE: {
+ Extension* extension;
+ bool is_new = MaybeNewExtension(number,
+ other_extension.descriptor,
+ &extension);
+ if (is_new) {
+ extension->type = other_extension.type;
+ extension->is_packed = other_extension.is_packed;
+ extension->is_repeated = false;
+ if (other_extension.is_lazy) {
+ extension->is_lazy = true;
+ extension->lazymessage_value =
+ other_extension.lazymessage_value->New(arena_);
+ extension->lazymessage_value->MergeFrom(
+ *other_extension.lazymessage_value);
+ } else {
+ extension->is_lazy = false;
+ extension->message_value =
+ other_extension.message_value->New(arena_);
+ extension->message_value->CheckTypeAndMergeFrom(
+ *other_extension.message_value);
+ }
+ } else {
+ GOOGLE_DCHECK_EQ(extension->type, other_extension.type);
+ GOOGLE_DCHECK_EQ(extension->is_packed,other_extension.is_packed);
+ GOOGLE_DCHECK(!extension->is_repeated);
+ if (other_extension.is_lazy) {
+ if (extension->is_lazy) {
+ extension->lazymessage_value->MergeFrom(
+ *other_extension.lazymessage_value);
+ } else {
+ extension->message_value->CheckTypeAndMergeFrom(
+ other_extension.lazymessage_value->GetMessage(
+ *extension->message_value));
+ }
+ } else {
+ if (extension->is_lazy) {
+ extension->lazymessage_value->MutableMessage(
+ *other_extension.message_value)->CheckTypeAndMergeFrom(
+ *other_extension.message_value);
+ } else {
+ extension->message_value->CheckTypeAndMergeFrom(
+ *other_extension.message_value);
+ }
+ }
+ }
+ extension->is_cleared = false;
+ break;
+ }
+ }
+ }
+ }
+}
+
+void ExtensionSet::Swap(ExtensionSet* x) {
+ if (GetArenaNoVirtual() == x->GetArenaNoVirtual()) {
+ extensions_.swap(x->extensions_);
+ } else {
+ // TODO(cfallin, rohananil): We maybe able to optimize a case where we are
+ // swapping from heap to arena-allocated extension set, by just Own()'ing
+ // the extensions.
+ ExtensionSet extension_set;
+ extension_set.MergeFrom(*x);
+ x->Clear();
+ x->MergeFrom(*this);
+ Clear();
+ MergeFrom(extension_set);
+ }
+}
+
+void ExtensionSet::SwapExtension(ExtensionSet* other,
+ int number) {
+ if (this == other) return;
+ ExtensionMap::iterator this_iter = extensions_.find(number);
+ ExtensionMap::iterator other_iter = other->extensions_.find(number);
+
+ if (this_iter == extensions_.end() &&
+ other_iter == other->extensions_.end()) {
+ return;
+ }
+
+ if (this_iter != extensions_.end() &&
+ other_iter != other->extensions_.end()) {
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ using std::swap;
+ swap(this_iter->second, other_iter->second);
+ } else {
+ // TODO(cfallin, rohananil): We could further optimize these cases,
+ // especially avoid creation of ExtensionSet, and move MergeFrom logic
+ // into Extensions itself (which takes arena as an argument).
+ // We do it this way to reuse the copy-across-arenas logic already
+ // implemented in ExtensionSet's MergeFrom.
+ ExtensionSet temp;
+ temp.InternalExtensionMergeFrom(number, other_iter->second);
+ ExtensionMap::iterator temp_iter = temp.extensions_.find(number);
+ other_iter->second.Clear();
+ other->InternalExtensionMergeFrom(number, this_iter->second);
+ this_iter->second.Clear();
+ InternalExtensionMergeFrom(number, temp_iter->second);
+ }
+ return;
+ }
+
+ if (this_iter == extensions_.end()) {
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ extensions_.insert(std::make_pair(number, other_iter->second));
+ } else {
+ InternalExtensionMergeFrom(number, other_iter->second);
+ }
+ other->extensions_.erase(number);
+ return;
+ }
+
+ if (other_iter == other->extensions_.end()) {
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ other->extensions_.insert(std::make_pair(number, this_iter->second));
+ } else {
+ other->InternalExtensionMergeFrom(number, this_iter->second);
+ }
+ extensions_.erase(number);
+ return;
+ }
+}
+
+bool ExtensionSet::IsInitialized() const {
+ // Extensions are never required. However, we need to check that all
+ // embedded messages are initialized.
+ for (ExtensionMap::const_iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ const Extension& extension = iter->second;
+ if (cpp_type(extension.type) == WireFormatLite::CPPTYPE_MESSAGE) {
+ if (extension.is_repeated) {
+ for (int i = 0; i < extension.repeated_message_value->size(); i++) {
+ if (!extension.repeated_message_value->Get(i).IsInitialized()) {
+ return false;
+ }
+ }
+ } else {
+ if (!extension.is_cleared) {
+ if (extension.is_lazy) {
+ if (!extension.lazymessage_value->IsInitialized()) return false;
+ } else {
+ if (!extension.message_value->IsInitialized()) return false;
+ }
+ }
+ }
+ }
+ }
+
+ return true;
+}
+
+bool ExtensionSet::FindExtensionInfoFromTag(
+ uint32 tag, ExtensionFinder* extension_finder, int* field_number,
+ ExtensionInfo* extension, bool* was_packed_on_wire) {
+ *field_number = WireFormatLite::GetTagFieldNumber(tag);
+ WireFormatLite::WireType wire_type = WireFormatLite::GetTagWireType(tag);
+ return FindExtensionInfoFromFieldNumber(wire_type, *field_number,
+ extension_finder, extension,
+ was_packed_on_wire);
+}
+
+bool ExtensionSet::FindExtensionInfoFromFieldNumber(
+ int wire_type, int field_number, ExtensionFinder* extension_finder,
+ ExtensionInfo* extension, bool* was_packed_on_wire) {
+ if (!extension_finder->Find(field_number, extension)) {
+ return false;
+ }
+
+ WireFormatLite::WireType expected_wire_type =
+ WireFormatLite::WireTypeForFieldType(real_type(extension->type));
+
+ // Check if this is a packed field.
+ *was_packed_on_wire = false;
+ if (extension->is_repeated &&
+ wire_type == WireFormatLite::WIRETYPE_LENGTH_DELIMITED &&
+ is_packable(expected_wire_type)) {
+ *was_packed_on_wire = true;
+ return true;
+ }
+ // Otherwise the wire type must match.
+ return expected_wire_type == wire_type;
+}
+
+bool ExtensionSet::ParseField(uint32 tag, io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ FieldSkipper* field_skipper) {
+ int number;
+ bool was_packed_on_wire;
+ ExtensionInfo extension;
+ if (!FindExtensionInfoFromTag(
+ tag, extension_finder, &number, &extension, &was_packed_on_wire)) {
+ return field_skipper->SkipField(input, tag);
+ } else {
+ return ParseFieldWithExtensionInfo(
+ number, was_packed_on_wire, extension, input, field_skipper);
+ }
+}
+
+bool ExtensionSet::ParseFieldWithExtensionInfo(
+ int number, bool was_packed_on_wire, const ExtensionInfo& extension,
+ io::CodedInputStream* input,
+ FieldSkipper* field_skipper) {
+ // Explicitly not read extension.is_packed, instead check whether the field
+ // was encoded in packed form on the wire.
+ if (was_packed_on_wire) {
+ uint32 size;
+ if (!input->ReadVarint32(&size)) return false;
+ io::CodedInputStream::Limit limit = input->PushLimit(size);
+
+ switch (extension.type) {
+#define HANDLE_TYPE(UPPERCASE, CPP_CAMELCASE, CPP_LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ while (input->BytesUntilLimit() > 0) { \
+ CPP_LOWERCASE value; \
+ if (!WireFormatLite::ReadPrimitive< \
+ CPP_LOWERCASE, WireFormatLite::TYPE_##UPPERCASE>( \
+ input, &value)) return false; \
+ Add##CPP_CAMELCASE(number, WireFormatLite::TYPE_##UPPERCASE, \
+ extension.is_packed, value, \
+ extension.descriptor); \
+ } \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, Int32, int32);
+ HANDLE_TYPE( SINT64, Int64, int64);
+ HANDLE_TYPE( FIXED32, UInt32, uint32);
+ HANDLE_TYPE( FIXED64, UInt64, uint64);
+ HANDLE_TYPE(SFIXED32, Int32, int32);
+ HANDLE_TYPE(SFIXED64, Int64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+#undef HANDLE_TYPE
+
+ case WireFormatLite::TYPE_ENUM:
+ while (input->BytesUntilLimit() > 0) {
+ int value;
+ if (!WireFormatLite::ReadPrimitive<int, WireFormatLite::TYPE_ENUM>(
+ input, &value)) return false;
+ if (extension.enum_validity_check.func(
+ extension.enum_validity_check.arg, value)) {
+ AddEnum(number, WireFormatLite::TYPE_ENUM, extension.is_packed,
+ value, extension.descriptor);
+ } else {
+ // Invalid value. Treat as unknown.
+ field_skipper->SkipUnknownEnum(number, value);
+ }
+ }
+ break;
+
+ case WireFormatLite::TYPE_STRING:
+ case WireFormatLite::TYPE_BYTES:
+ case WireFormatLite::TYPE_GROUP:
+ case WireFormatLite::TYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Non-primitive types can't be packed.";
+ break;
+ }
+
+ input->PopLimit(limit);
+ } else {
+ switch (extension.type) {
+#define HANDLE_TYPE(UPPERCASE, CPP_CAMELCASE, CPP_LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: { \
+ CPP_LOWERCASE value; \
+ if (!WireFormatLite::ReadPrimitive< \
+ CPP_LOWERCASE, WireFormatLite::TYPE_##UPPERCASE>( \
+ input, &value)) return false; \
+ if (extension.is_repeated) { \
+ Add##CPP_CAMELCASE(number, WireFormatLite::TYPE_##UPPERCASE, \
+ extension.is_packed, value, \
+ extension.descriptor); \
+ } else { \
+ Set##CPP_CAMELCASE(number, WireFormatLite::TYPE_##UPPERCASE, value, \
+ extension.descriptor); \
+ } \
+ } break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, Int32, int32);
+ HANDLE_TYPE( SINT64, Int64, int64);
+ HANDLE_TYPE( FIXED32, UInt32, uint32);
+ HANDLE_TYPE( FIXED64, UInt64, uint64);
+ HANDLE_TYPE(SFIXED32, Int32, int32);
+ HANDLE_TYPE(SFIXED64, Int64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+#undef HANDLE_TYPE
+
+ case WireFormatLite::TYPE_ENUM: {
+ int value;
+ if (!WireFormatLite::ReadPrimitive<int, WireFormatLite::TYPE_ENUM>(
+ input, &value)) return false;
+
+ if (!extension.enum_validity_check.func(
+ extension.enum_validity_check.arg, value)) {
+ // Invalid value. Treat as unknown.
+ field_skipper->SkipUnknownEnum(number, value);
+ } else if (extension.is_repeated) {
+ AddEnum(number, WireFormatLite::TYPE_ENUM, extension.is_packed, value,
+ extension.descriptor);
+ } else {
+ SetEnum(number, WireFormatLite::TYPE_ENUM, value,
+ extension.descriptor);
+ }
+ break;
+ }
+
+ case WireFormatLite::TYPE_STRING: {
+ string* value = extension.is_repeated ?
+ AddString(number, WireFormatLite::TYPE_STRING, extension.descriptor) :
+ MutableString(number, WireFormatLite::TYPE_STRING,
+ extension.descriptor);
+ if (!WireFormatLite::ReadString(input, value)) return false;
+ break;
+ }
+
+ case WireFormatLite::TYPE_BYTES: {
+ string* value = extension.is_repeated ?
+ AddString(number, WireFormatLite::TYPE_BYTES, extension.descriptor) :
+ MutableString(number, WireFormatLite::TYPE_BYTES,
+ extension.descriptor);
+ if (!WireFormatLite::ReadBytes(input, value)) return false;
+ break;
+ }
+
+ case WireFormatLite::TYPE_GROUP: {
+ MessageLite* value = extension.is_repeated ?
+ AddMessage(number, WireFormatLite::TYPE_GROUP,
+ *extension.message_prototype, extension.descriptor) :
+ MutableMessage(number, WireFormatLite::TYPE_GROUP,
+ *extension.message_prototype, extension.descriptor);
+ if (!WireFormatLite::ReadGroup(number, input, value)) return false;
+ break;
+ }
+
+ case WireFormatLite::TYPE_MESSAGE: {
+ MessageLite* value = extension.is_repeated ?
+ AddMessage(number, WireFormatLite::TYPE_MESSAGE,
+ *extension.message_prototype, extension.descriptor) :
+ MutableMessage(number, WireFormatLite::TYPE_MESSAGE,
+ *extension.message_prototype, extension.descriptor);
+ if (!WireFormatLite::ReadMessage(input, value)) return false;
+ break;
+ }
+ }
+ }
+
+ return true;
+}
+
+bool ExtensionSet::ParseField(uint32 tag, io::CodedInputStream* input,
+ const MessageLite* containing_type) {
+ FieldSkipper skipper;
+ GeneratedExtensionFinder finder(containing_type);
+ return ParseField(tag, input, &finder, &skipper);
+}
+
+bool ExtensionSet::ParseField(uint32 tag, io::CodedInputStream* input,
+ const MessageLite* containing_type,
+ io::CodedOutputStream* unknown_fields) {
+ CodedOutputStreamFieldSkipper skipper(unknown_fields);
+ GeneratedExtensionFinder finder(containing_type);
+ return ParseField(tag, input, &finder, &skipper);
+}
+
+// Defined in extension_set_heavy.cc.
+// bool ExtensionSet::ParseField(uint32 tag, io::CodedInputStream* input,
+// const MessageLite* containing_type,
+// UnknownFieldSet* unknown_fields)
+
+// Defined in extension_set_heavy.cc.
+// bool ExtensionSet::ParseMessageSet(io::CodedInputStream* input,
+// const MessageLite* containing_type,
+// UnknownFieldSet* unknown_fields);
+
+void ExtensionSet::SerializeWithCachedSizes(
+ int start_field_number, int end_field_number,
+ io::CodedOutputStream* output) const {
+ ExtensionMap::const_iterator iter;
+ for (iter = extensions_.lower_bound(start_field_number);
+ iter != extensions_.end() && iter->first < end_field_number;
+ ++iter) {
+ iter->second.SerializeFieldWithCachedSizes(iter->first, output);
+ }
+}
+
+int ExtensionSet::ByteSize() const {
+ int total_size = 0;
+
+ for (ExtensionMap::const_iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ total_size += iter->second.ByteSize(iter->first);
+ }
+
+ return total_size;
+}
+
+// Defined in extension_set_heavy.cc.
+// int ExtensionSet::SpaceUsedExcludingSelf() const
+
+bool ExtensionSet::MaybeNewExtension(int number,
+ const FieldDescriptor* descriptor,
+ Extension** result) {
+ pair<ExtensionMap::iterator, bool> insert_result =
+ extensions_.insert(std::make_pair(number, Extension()));
+ *result = &insert_result.first->second;
+ (*result)->descriptor = descriptor;
+ return insert_result.second;
+}
+
+// ===================================================================
+// Methods of ExtensionSet::Extension
+
+void ExtensionSet::Extension::Clear() {
+ if (is_repeated) {
+ switch (cpp_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case WireFormatLite::CPPTYPE_##UPPERCASE: \
+ repeated_##LOWERCASE##_value->Clear(); \
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE( UINT32, uint32);
+ HANDLE_TYPE( UINT64, uint64);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( DOUBLE, double);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, enum);
+ HANDLE_TYPE( STRING, string);
+ HANDLE_TYPE(MESSAGE, message);
+#undef HANDLE_TYPE
+ }
+ } else {
+ if (!is_cleared) {
+ switch (cpp_type(type)) {
+ case WireFormatLite::CPPTYPE_STRING:
+ string_value->clear();
+ break;
+ case WireFormatLite::CPPTYPE_MESSAGE:
+ if (is_lazy) {
+ lazymessage_value->Clear();
+ } else {
+ message_value->Clear();
+ }
+ break;
+ default:
+ // No need to do anything. Get*() will return the default value
+ // as long as is_cleared is true and Set*() will overwrite the
+ // previous value.
+ break;
+ }
+
+ is_cleared = true;
+ }
+ }
+}
+
+void ExtensionSet::Extension::SerializeFieldWithCachedSizes(
+ int number,
+ io::CodedOutputStream* output) const {
+ if (is_repeated) {
+ if (is_packed) {
+ if (cached_size == 0) return;
+
+ WireFormatLite::WriteTag(number,
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED, output);
+ output->WriteVarint32(cached_size);
+
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ for (int i = 0; i < repeated_##LOWERCASE##_value->size(); i++) { \
+ WireFormatLite::Write##CAMELCASE##NoTag( \
+ repeated_##LOWERCASE##_value->Get(i), output); \
+ } \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, SInt32, int32);
+ HANDLE_TYPE( SINT64, SInt64, int64);
+ HANDLE_TYPE( FIXED32, Fixed32, uint32);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+ HANDLE_TYPE( ENUM, Enum, enum);
+#undef HANDLE_TYPE
+
+ case WireFormatLite::TYPE_STRING:
+ case WireFormatLite::TYPE_BYTES:
+ case WireFormatLite::TYPE_GROUP:
+ case WireFormatLite::TYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Non-primitive types can't be packed.";
+ break;
+ }
+ } else {
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ for (int i = 0; i < repeated_##LOWERCASE##_value->size(); i++) { \
+ WireFormatLite::Write##CAMELCASE(number, \
+ repeated_##LOWERCASE##_value->Get(i), output); \
+ } \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, SInt32, int32);
+ HANDLE_TYPE( SINT64, SInt64, int64);
+ HANDLE_TYPE( FIXED32, Fixed32, uint32);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+ HANDLE_TYPE( STRING, String, string);
+ HANDLE_TYPE( BYTES, Bytes, string);
+ HANDLE_TYPE( ENUM, Enum, enum);
+ HANDLE_TYPE( GROUP, Group, message);
+ HANDLE_TYPE( MESSAGE, Message, message);
+#undef HANDLE_TYPE
+ }
+ }
+ } else if (!is_cleared) {
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, VALUE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ WireFormatLite::Write##CAMELCASE(number, VALUE, output); \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32_value);
+ HANDLE_TYPE( INT64, Int64, int64_value);
+ HANDLE_TYPE( UINT32, UInt32, uint32_value);
+ HANDLE_TYPE( UINT64, UInt64, uint64_value);
+ HANDLE_TYPE( SINT32, SInt32, int32_value);
+ HANDLE_TYPE( SINT64, SInt64, int64_value);
+ HANDLE_TYPE( FIXED32, Fixed32, uint32_value);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64_value);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32_value);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64_value);
+ HANDLE_TYPE( FLOAT, Float, float_value);
+ HANDLE_TYPE( DOUBLE, Double, double_value);
+ HANDLE_TYPE( BOOL, Bool, bool_value);
+ HANDLE_TYPE( STRING, String, *string_value);
+ HANDLE_TYPE( BYTES, Bytes, *string_value);
+ HANDLE_TYPE( ENUM, Enum, enum_value);
+ HANDLE_TYPE( GROUP, Group, *message_value);
+#undef HANDLE_TYPE
+ case WireFormatLite::TYPE_MESSAGE:
+ if (is_lazy) {
+ lazymessage_value->WriteMessage(number, output);
+ } else {
+ WireFormatLite::WriteMessage(number, *message_value, output);
+ }
+ break;
+ }
+ }
+}
+
+int ExtensionSet::Extension::ByteSize(int number) const {
+ int result = 0;
+
+ if (is_repeated) {
+ if (is_packed) {
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ for (int i = 0; i < repeated_##LOWERCASE##_value->size(); i++) { \
+ result += WireFormatLite::CAMELCASE##Size( \
+ repeated_##LOWERCASE##_value->Get(i)); \
+ } \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, SInt32, int32);
+ HANDLE_TYPE( SINT64, SInt64, int64);
+ HANDLE_TYPE( ENUM, Enum, enum);
+#undef HANDLE_TYPE
+
+ // Stuff with fixed size.
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ result += WireFormatLite::k##CAMELCASE##Size * \
+ repeated_##LOWERCASE##_value->size(); \
+ break
+ HANDLE_TYPE( FIXED32, Fixed32, uint32);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+#undef HANDLE_TYPE
+
+ case WireFormatLite::TYPE_STRING:
+ case WireFormatLite::TYPE_BYTES:
+ case WireFormatLite::TYPE_GROUP:
+ case WireFormatLite::TYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Non-primitive types can't be packed.";
+ break;
+ }
+
+ cached_size = result;
+ if (result > 0) {
+ result += io::CodedOutputStream::VarintSize32(result);
+ result += io::CodedOutputStream::VarintSize32(
+ WireFormatLite::MakeTag(number,
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED));
+ }
+ } else {
+ int tag_size = WireFormatLite::TagSize(number, real_type(type));
+
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ result += tag_size * repeated_##LOWERCASE##_value->size(); \
+ for (int i = 0; i < repeated_##LOWERCASE##_value->size(); i++) { \
+ result += WireFormatLite::CAMELCASE##Size( \
+ repeated_##LOWERCASE##_value->Get(i)); \
+ } \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, SInt32, int32);
+ HANDLE_TYPE( SINT64, SInt64, int64);
+ HANDLE_TYPE( STRING, String, string);
+ HANDLE_TYPE( BYTES, Bytes, string);
+ HANDLE_TYPE( ENUM, Enum, enum);
+ HANDLE_TYPE( GROUP, Group, message);
+ HANDLE_TYPE( MESSAGE, Message, message);
+#undef HANDLE_TYPE
+
+ // Stuff with fixed size.
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ result += (tag_size + WireFormatLite::k##CAMELCASE##Size) * \
+ repeated_##LOWERCASE##_value->size(); \
+ break
+ HANDLE_TYPE( FIXED32, Fixed32, uint32);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+#undef HANDLE_TYPE
+ }
+ }
+ } else if (!is_cleared) {
+ result += WireFormatLite::TagSize(number, real_type(type));
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ result += WireFormatLite::CAMELCASE##Size(LOWERCASE); \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32_value);
+ HANDLE_TYPE( INT64, Int64, int64_value);
+ HANDLE_TYPE( UINT32, UInt32, uint32_value);
+ HANDLE_TYPE( UINT64, UInt64, uint64_value);
+ HANDLE_TYPE( SINT32, SInt32, int32_value);
+ HANDLE_TYPE( SINT64, SInt64, int64_value);
+ HANDLE_TYPE( STRING, String, *string_value);
+ HANDLE_TYPE( BYTES, Bytes, *string_value);
+ HANDLE_TYPE( ENUM, Enum, enum_value);
+ HANDLE_TYPE( GROUP, Group, *message_value);
+#undef HANDLE_TYPE
+ case WireFormatLite::TYPE_MESSAGE: {
+ if (is_lazy) {
+ int size = lazymessage_value->ByteSize();
+ result += io::CodedOutputStream::VarintSize32(size) + size;
+ } else {
+ result += WireFormatLite::MessageSize(*message_value);
+ }
+ break;
+ }
+
+ // Stuff with fixed size.
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE) \
+ case WireFormatLite::TYPE_##UPPERCASE: \
+ result += WireFormatLite::k##CAMELCASE##Size; \
+ break
+ HANDLE_TYPE( FIXED32, Fixed32);
+ HANDLE_TYPE( FIXED64, Fixed64);
+ HANDLE_TYPE(SFIXED32, SFixed32);
+ HANDLE_TYPE(SFIXED64, SFixed64);
+ HANDLE_TYPE( FLOAT, Float);
+ HANDLE_TYPE( DOUBLE, Double);
+ HANDLE_TYPE( BOOL, Bool);
+#undef HANDLE_TYPE
+ }
+ }
+
+ return result;
+}
+
+int ExtensionSet::Extension::GetSize() const {
+ GOOGLE_DCHECK(is_repeated);
+ switch (cpp_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case WireFormatLite::CPPTYPE_##UPPERCASE: \
+ return repeated_##LOWERCASE##_value->size()
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE( UINT32, uint32);
+ HANDLE_TYPE( UINT64, uint64);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( DOUBLE, double);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, enum);
+ HANDLE_TYPE( STRING, string);
+ HANDLE_TYPE(MESSAGE, message);
+#undef HANDLE_TYPE
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return 0;
+}
+
+// This function deletes all allocated objects. This function should be only
+// called if the Extension was created with an arena.
+void ExtensionSet::Extension::Free() {
+ if (is_repeated) {
+ switch (cpp_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case WireFormatLite::CPPTYPE_##UPPERCASE: \
+ delete repeated_##LOWERCASE##_value; \
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE( UINT32, uint32);
+ HANDLE_TYPE( UINT64, uint64);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( DOUBLE, double);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, enum);
+ HANDLE_TYPE( STRING, string);
+ HANDLE_TYPE(MESSAGE, message);
+#undef HANDLE_TYPE
+ }
+ } else {
+ switch (cpp_type(type)) {
+ case WireFormatLite::CPPTYPE_STRING:
+ delete string_value;
+ break;
+ case WireFormatLite::CPPTYPE_MESSAGE:
+ if (is_lazy) {
+ delete lazymessage_value;
+ } else {
+ delete message_value;
+ }
+ break;
+ default:
+ break;
+ }
+ }
+}
+
+// Defined in extension_set_heavy.cc.
+// int ExtensionSet::Extension::SpaceUsedExcludingSelf() const
+
+// ==================================================================
+// Default repeated field instances for iterator-compatible accessors
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(repeated_primitive_generic_type_traits_once_init_);
+GOOGLE_PROTOBUF_DECLARE_ONCE(repeated_string_type_traits_once_init_);
+GOOGLE_PROTOBUF_DECLARE_ONCE(repeated_message_generic_type_traits_once_init_);
+
+void RepeatedPrimitiveGenericTypeTraits::InitializeDefaultRepeatedFields() {
+ default_repeated_field_int32_ = new RepeatedField<int32>;
+ default_repeated_field_int64_ = new RepeatedField<int64>;
+ default_repeated_field_uint32_ = new RepeatedField<uint32>;
+ default_repeated_field_uint64_ = new RepeatedField<uint64>;
+ default_repeated_field_double_ = new RepeatedField<double>;
+ default_repeated_field_float_ = new RepeatedField<float>;
+ default_repeated_field_bool_ = new RepeatedField<bool>;
+ OnShutdown(&DestroyDefaultRepeatedFields);
+}
+
+void RepeatedPrimitiveGenericTypeTraits::DestroyDefaultRepeatedFields() {
+ delete default_repeated_field_int32_;
+ delete default_repeated_field_int64_;
+ delete default_repeated_field_uint32_;
+ delete default_repeated_field_uint64_;
+ delete default_repeated_field_double_;
+ delete default_repeated_field_float_;
+ delete default_repeated_field_bool_;
+}
+
+void RepeatedStringTypeTraits::InitializeDefaultRepeatedFields() {
+ default_repeated_field_ = new RepeatedFieldType;
+ OnShutdown(&DestroyDefaultRepeatedFields);
+}
+
+void RepeatedStringTypeTraits::DestroyDefaultRepeatedFields() {
+ delete default_repeated_field_;
+}
+
+void RepeatedMessageGenericTypeTraits::InitializeDefaultRepeatedFields() {
+ default_repeated_field_ = new RepeatedFieldType;
+ OnShutdown(&DestroyDefaultRepeatedFields);
+}
+
+void RepeatedMessageGenericTypeTraits::DestroyDefaultRepeatedFields() {
+ delete default_repeated_field_;
+}
+
+const RepeatedField<int32>*
+RepeatedPrimitiveGenericTypeTraits::default_repeated_field_int32_ = NULL;
+const RepeatedField<int64>*
+RepeatedPrimitiveGenericTypeTraits::default_repeated_field_int64_ = NULL;
+const RepeatedField<uint32>*
+RepeatedPrimitiveGenericTypeTraits::default_repeated_field_uint32_ = NULL;
+const RepeatedField<uint64>*
+RepeatedPrimitiveGenericTypeTraits::default_repeated_field_uint64_ = NULL;
+const RepeatedField<double>*
+RepeatedPrimitiveGenericTypeTraits::default_repeated_field_double_ = NULL;
+const RepeatedField<float>*
+RepeatedPrimitiveGenericTypeTraits::default_repeated_field_float_ = NULL;
+const RepeatedField<bool>*
+RepeatedPrimitiveGenericTypeTraits::default_repeated_field_bool_ = NULL;
+const RepeatedStringTypeTraits::RepeatedFieldType*
+RepeatedStringTypeTraits::default_repeated_field_ = NULL;
+const RepeatedMessageGenericTypeTraits::RepeatedFieldType*
+RepeatedMessageGenericTypeTraits::default_repeated_field_ = NULL;
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/extension_set.h b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set.h
new file mode 100644
index 0000000000..3e1d1ef5eb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set.h
@@ -0,0 +1,1318 @@
+// 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 header is logically internal, but is made public because it is used
+// from protocol-compiler-generated code, which may reside in other components.
+
+#ifndef GOOGLE_PROTOBUF_EXTENSION_SET_H__
+#define GOOGLE_PROTOBUF_EXTENSION_SET_H__
+
+#include <vector>
+#include <map>
+#include <utility>
+#include <string>
+
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/once.h>
+
+#include <google/protobuf/repeated_field.h>
+
+namespace google {
+
+namespace protobuf {
+ class Arena;
+ class Descriptor; // descriptor.h
+ class FieldDescriptor; // descriptor.h
+ class DescriptorPool; // descriptor.h
+ class MessageLite; // message_lite.h
+ class Message; // message.h
+ class MessageFactory; // message.h
+ class UnknownFieldSet; // unknown_field_set.h
+ namespace io {
+ class CodedInputStream; // coded_stream.h
+ class CodedOutputStream; // coded_stream.h
+ }
+ namespace internal {
+ class FieldSkipper; // wire_format_lite.h
+ }
+}
+
+namespace protobuf {
+namespace internal {
+
+// Used to store values of type WireFormatLite::FieldType without having to
+// #include wire_format_lite.h. Also, ensures that we use only one byte to
+// store these values, which is important to keep the layout of
+// ExtensionSet::Extension small.
+typedef uint8 FieldType;
+
+// A function which, given an integer value, returns true if the number
+// matches one of the defined values for the corresponding enum type. This
+// is used with RegisterEnumExtension, below.
+typedef bool EnumValidityFunc(int number);
+
+// Version of the above which takes an argument. This is needed to deal with
+// extensions that are not compiled in.
+typedef bool EnumValidityFuncWithArg(const void* arg, int number);
+
+// Information about a registered extension.
+struct ExtensionInfo {
+ inline ExtensionInfo() {}
+ inline ExtensionInfo(FieldType type_param, bool isrepeated, bool ispacked)
+ : type(type_param), is_repeated(isrepeated), is_packed(ispacked),
+ descriptor(NULL) {}
+
+ FieldType type;
+ bool is_repeated;
+ bool is_packed;
+
+ struct EnumValidityCheck {
+ EnumValidityFuncWithArg* func;
+ const void* arg;
+ };
+
+ union {
+ EnumValidityCheck enum_validity_check;
+ const MessageLite* message_prototype;
+ };
+
+ // The descriptor for this extension, if one exists and is known. May be
+ // NULL. Must not be NULL if the descriptor for the extension does not
+ // live in the same pool as the descriptor for the containing type.
+ const FieldDescriptor* descriptor;
+};
+
+// Abstract interface for an object which looks up extension definitions. Used
+// when parsing.
+class LIBPROTOBUF_EXPORT ExtensionFinder {
+ public:
+ virtual ~ExtensionFinder();
+
+ // Find the extension with the given containing type and number.
+ virtual bool Find(int number, ExtensionInfo* output) = 0;
+};
+
+// Implementation of ExtensionFinder which finds extensions defined in .proto
+// files which have been compiled into the binary.
+class LIBPROTOBUF_EXPORT GeneratedExtensionFinder : public ExtensionFinder {
+ public:
+ GeneratedExtensionFinder(const MessageLite* containing_type)
+ : containing_type_(containing_type) {}
+ virtual ~GeneratedExtensionFinder() {}
+
+ // Returns true and fills in *output if found, otherwise returns false.
+ virtual bool Find(int number, ExtensionInfo* output);
+
+ private:
+ const MessageLite* containing_type_;
+};
+
+// A FieldSkipper used for parsing MessageSet.
+class MessageSetFieldSkipper;
+
+// Note: extension_set_heavy.cc defines DescriptorPoolExtensionFinder for
+// finding extensions from a DescriptorPool.
+
+// This is an internal helper class intended for use within the protocol buffer
+// library and generated classes. Clients should not use it directly. Instead,
+// use the generated accessors such as GetExtension() of the class being
+// extended.
+//
+// This class manages extensions for a protocol message object. The
+// message's HasExtension(), GetExtension(), MutableExtension(), and
+// ClearExtension() methods are just thin wrappers around the embedded
+// ExtensionSet. When parsing, if a tag number is encountered which is
+// inside one of the message type's extension ranges, the tag is passed
+// off to the ExtensionSet for parsing. Etc.
+class LIBPROTOBUF_EXPORT ExtensionSet {
+ public:
+ ExtensionSet();
+ explicit ExtensionSet(::google::protobuf::Arena* arena);
+ ~ExtensionSet();
+
+ // These are called at startup by protocol-compiler-generated code to
+ // register known extensions. The registrations are used by ParseField()
+ // to look up extensions for parsed field numbers. Note that dynamic parsing
+ // does not use ParseField(); only protocol-compiler-generated parsing
+ // methods do.
+ static void RegisterExtension(const MessageLite* containing_type,
+ int number, FieldType type,
+ bool is_repeated, bool is_packed);
+ static void RegisterEnumExtension(const MessageLite* containing_type,
+ int number, FieldType type,
+ bool is_repeated, bool is_packed,
+ EnumValidityFunc* is_valid);
+ static void RegisterMessageExtension(const MessageLite* containing_type,
+ int number, FieldType type,
+ bool is_repeated, bool is_packed,
+ const MessageLite* prototype);
+
+ // =================================================================
+
+ // Add all fields which are currently present to the given vector. This
+ // is useful to implement Reflection::ListFields().
+ void AppendToList(const Descriptor* containing_type,
+ const DescriptorPool* pool,
+ std::vector<const FieldDescriptor*>* output) const;
+
+ // =================================================================
+ // Accessors
+ //
+ // Generated message classes include type-safe templated wrappers around
+ // these methods. Generally you should use those rather than call these
+ // directly, unless you are doing low-level memory management.
+ //
+ // When calling any of these accessors, the extension number requested
+ // MUST exist in the DescriptorPool provided to the constructor. Otherwise,
+ // the method will fail an assert. Normally, though, you would not call
+ // these directly; you would either call the generated accessors of your
+ // message class (e.g. GetExtension()) or you would call the accessors
+ // of the reflection interface. In both cases, it is impossible to
+ // trigger this assert failure: the generated accessors only accept
+ // linked-in extension types as parameters, while the Reflection interface
+ // requires you to provide the FieldDescriptor describing the extension.
+ //
+ // When calling any of these accessors, a protocol-compiler-generated
+ // implementation of the extension corresponding to the number MUST
+ // be linked in, and the FieldDescriptor used to refer to it MUST be
+ // the one generated by that linked-in code. Otherwise, the method will
+ // die on an assert failure. The message objects returned by the message
+ // accessors are guaranteed to be of the correct linked-in type.
+ //
+ // These methods pretty much match Reflection except that:
+ // - They're not virtual.
+ // - They identify fields by number rather than FieldDescriptors.
+ // - They identify enum values using integers rather than descriptors.
+ // - Strings provide Mutable() in addition to Set() accessors.
+
+ bool Has(int number) const;
+ int ExtensionSize(int number) const; // Size of a repeated extension.
+ int NumExtensions() const; // The number of extensions
+ FieldType ExtensionType(int number) const;
+ void ClearExtension(int number);
+
+ // singular fields -------------------------------------------------
+
+ int32 GetInt32 (int number, int32 default_value) const;
+ int64 GetInt64 (int number, int64 default_value) const;
+ uint32 GetUInt32(int number, uint32 default_value) const;
+ uint64 GetUInt64(int number, uint64 default_value) const;
+ float GetFloat (int number, float default_value) const;
+ double GetDouble(int number, double default_value) const;
+ bool GetBool (int number, bool default_value) const;
+ int GetEnum (int number, int default_value) const;
+ const string & GetString (int number, const string& default_value) const;
+ const MessageLite& GetMessage(int number,
+ const MessageLite& default_value) const;
+ const MessageLite& GetMessage(int number, const Descriptor* message_type,
+ MessageFactory* factory) const;
+
+ // |descriptor| may be NULL so long as it is known that the descriptor for
+ // the extension lives in the same pool as the descriptor for the containing
+ // type.
+#define desc const FieldDescriptor* descriptor // avoid line wrapping
+ void SetInt32 (int number, FieldType type, int32 value, desc);
+ void SetInt64 (int number, FieldType type, int64 value, desc);
+ void SetUInt32(int number, FieldType type, uint32 value, desc);
+ void SetUInt64(int number, FieldType type, uint64 value, desc);
+ void SetFloat (int number, FieldType type, float value, desc);
+ void SetDouble(int number, FieldType type, double value, desc);
+ void SetBool (int number, FieldType type, bool value, desc);
+ void SetEnum (int number, FieldType type, int value, desc);
+ void SetString(int number, FieldType type, const string& value, desc);
+ string * MutableString (int number, FieldType type, desc);
+ MessageLite* MutableMessage(int number, FieldType type,
+ const MessageLite& prototype, desc);
+ MessageLite* MutableMessage(const FieldDescriptor* decsriptor,
+ MessageFactory* factory);
+ // Adds the given message to the ExtensionSet, taking ownership of the
+ // message object. Existing message with the same number will be deleted.
+ // If "message" is NULL, this is equivalent to "ClearExtension(number)".
+ void SetAllocatedMessage(int number, FieldType type,
+ const FieldDescriptor* descriptor,
+ MessageLite* message);
+ void UnsafeArenaSetAllocatedMessage(int number, FieldType type,
+ const FieldDescriptor* descriptor,
+ MessageLite* message);
+ MessageLite* ReleaseMessage(int number, const MessageLite& prototype);
+ MessageLite* UnsafeArenaReleaseMessage(
+ int number, const MessageLite& prototype);
+
+ MessageLite* ReleaseMessage(const FieldDescriptor* descriptor,
+ MessageFactory* factory);
+ MessageLite* UnsafeArenaReleaseMessage(const FieldDescriptor* descriptor,
+ MessageFactory* factory);
+#undef desc
+ ::google::protobuf::Arena* GetArenaNoVirtual() const { return arena_; }
+
+ // repeated fields -------------------------------------------------
+
+ // Fetches a RepeatedField extension by number; returns |default_value|
+ // if no such extension exists. User should not touch this directly; it is
+ // used by the GetRepeatedExtension() method.
+ const void* GetRawRepeatedField(int number, const void* default_value) const;
+ // Fetches a mutable version of a RepeatedField extension by number,
+ // instantiating one if none exists. Similar to above, user should not use
+ // this directly; it underlies MutableRepeatedExtension().
+ void* MutableRawRepeatedField(int number, FieldType field_type,
+ bool packed, const FieldDescriptor* desc);
+
+ // This is an overload of MutableRawRepeatedField to maintain compatibility
+ // with old code using a previous API. This version of
+ // MutableRawRepeatedField() will GOOGLE_CHECK-fail on a missing extension.
+ // (E.g.: borg/clients/internal/proto1/proto2_reflection.cc.)
+ void* MutableRawRepeatedField(int number);
+
+ int32 GetRepeatedInt32 (int number, int index) const;
+ int64 GetRepeatedInt64 (int number, int index) const;
+ uint32 GetRepeatedUInt32(int number, int index) const;
+ uint64 GetRepeatedUInt64(int number, int index) const;
+ float GetRepeatedFloat (int number, int index) const;
+ double GetRepeatedDouble(int number, int index) const;
+ bool GetRepeatedBool (int number, int index) const;
+ int GetRepeatedEnum (int number, int index) const;
+ const string & GetRepeatedString (int number, int index) const;
+ const MessageLite& GetRepeatedMessage(int number, int index) const;
+
+ void SetRepeatedInt32 (int number, int index, int32 value);
+ void SetRepeatedInt64 (int number, int index, int64 value);
+ void SetRepeatedUInt32(int number, int index, uint32 value);
+ void SetRepeatedUInt64(int number, int index, uint64 value);
+ void SetRepeatedFloat (int number, int index, float value);
+ void SetRepeatedDouble(int number, int index, double value);
+ void SetRepeatedBool (int number, int index, bool value);
+ void SetRepeatedEnum (int number, int index, int value);
+ void SetRepeatedString(int number, int index, const string& value);
+ string * MutableRepeatedString (int number, int index);
+ MessageLite* MutableRepeatedMessage(int number, int index);
+
+#define desc const FieldDescriptor* descriptor // avoid line wrapping
+ void AddInt32 (int number, FieldType type, bool packed, int32 value, desc);
+ void AddInt64 (int number, FieldType type, bool packed, int64 value, desc);
+ void AddUInt32(int number, FieldType type, bool packed, uint32 value, desc);
+ void AddUInt64(int number, FieldType type, bool packed, uint64 value, desc);
+ void AddFloat (int number, FieldType type, bool packed, float value, desc);
+ void AddDouble(int number, FieldType type, bool packed, double value, desc);
+ void AddBool (int number, FieldType type, bool packed, bool value, desc);
+ void AddEnum (int number, FieldType type, bool packed, int value, desc);
+ void AddString(int number, FieldType type, const string& value, desc);
+ string * AddString (int number, FieldType type, desc);
+ MessageLite* AddMessage(int number, FieldType type,
+ const MessageLite& prototype, desc);
+ MessageLite* AddMessage(const FieldDescriptor* descriptor,
+ MessageFactory* factory);
+ void AddAllocatedMessage(const FieldDescriptor* descriptor,
+ MessageLite* new_entry);
+#undef desc
+
+ void RemoveLast(int number);
+ MessageLite* ReleaseLast(int number);
+ void SwapElements(int number, int index1, int index2);
+
+ // -----------------------------------------------------------------
+ // TODO(kenton): Hardcore memory management accessors
+
+ // =================================================================
+ // convenience methods for implementing methods of Message
+ //
+ // These could all be implemented in terms of the other methods of this
+ // class, but providing them here helps keep the generated code size down.
+
+ void Clear();
+ void MergeFrom(const ExtensionSet& other);
+ void Swap(ExtensionSet* other);
+ void SwapExtension(ExtensionSet* other, int number);
+ bool IsInitialized() const;
+
+ // Parses a single extension from the input. The input should start out
+ // positioned immediately after the tag.
+ bool ParseField(uint32 tag, io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ FieldSkipper* field_skipper);
+
+ // Specific versions for lite or full messages (constructs the appropriate
+ // FieldSkipper automatically). |containing_type| is the default
+ // instance for the containing message; it is used only to look up the
+ // extension by number. See RegisterExtension(), above. Unlike the other
+ // methods of ExtensionSet, this only works for generated message types --
+ // it looks up extensions registered using RegisterExtension().
+ bool ParseField(uint32 tag, io::CodedInputStream* input,
+ const MessageLite* containing_type);
+ bool ParseField(uint32 tag, io::CodedInputStream* input,
+ const Message* containing_type,
+ UnknownFieldSet* unknown_fields);
+ bool ParseField(uint32 tag, io::CodedInputStream* input,
+ const MessageLite* containing_type,
+ io::CodedOutputStream* unknown_fields);
+
+ // Parse an entire message in MessageSet format. Such messages have no
+ // fields, only extensions.
+ bool ParseMessageSet(io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ MessageSetFieldSkipper* field_skipper);
+
+ // Specific versions for lite or full messages (constructs the appropriate
+ // FieldSkipper automatically).
+ bool ParseMessageSet(io::CodedInputStream* input,
+ const MessageLite* containing_type);
+ bool ParseMessageSet(io::CodedInputStream* input,
+ const Message* containing_type,
+ UnknownFieldSet* unknown_fields);
+
+ // Write all extension fields with field numbers in the range
+ // [start_field_number, end_field_number)
+ // to the output stream, using the cached sizes computed when ByteSize() was
+ // last called. Note that the range bounds are inclusive-exclusive.
+ void SerializeWithCachedSizes(int start_field_number,
+ int end_field_number,
+ io::CodedOutputStream* output) const;
+
+ // Same as SerializeWithCachedSizes, but without any bounds checking.
+ // The caller must ensure that target has sufficient capacity for the
+ // serialized extensions.
+ //
+ // Returns a pointer past the last written byte.
+ uint8* InternalSerializeWithCachedSizesToArray(int start_field_number,
+ int end_field_number,
+ bool deterministic,
+ uint8* target) const;
+
+ // Like above but serializes in MessageSet format.
+ void SerializeMessageSetWithCachedSizes(io::CodedOutputStream* output) const;
+ uint8* InternalSerializeMessageSetWithCachedSizesToArray(bool deterministic,
+ uint8* target) const;
+
+ // For backward-compatibility, versions of two of the above methods that
+ // are never forced to serialize deterministically.
+ uint8* SerializeWithCachedSizesToArray(int start_field_number,
+ int end_field_number,
+ uint8* target) const;
+ uint8* SerializeMessageSetWithCachedSizesToArray(uint8* target) const;
+
+ // Returns the total serialized size of all the extensions.
+ int ByteSize() const;
+
+ // Like ByteSize() but uses MessageSet format.
+ int MessageSetByteSize() const;
+
+ // Returns (an estimate of) the total number of bytes used for storing the
+ // extensions in memory, excluding sizeof(*this). If the ExtensionSet is
+ // for a lite message (and thus possibly contains lite messages), the results
+ // are undefined (might work, might crash, might corrupt data, might not even
+ // be linked in). It's up to the protocol compiler to avoid calling this on
+ // such ExtensionSets (easy enough since lite messages don't implement
+ // SpaceUsed()).
+ int SpaceUsedExcludingSelf() const;
+
+ private:
+
+ // Interface of a lazily parsed singular message extension.
+ class LIBPROTOBUF_EXPORT LazyMessageExtension {
+ public:
+ LazyMessageExtension() {}
+ virtual ~LazyMessageExtension() {}
+
+ virtual LazyMessageExtension* New(::google::protobuf::Arena* arena) const = 0;
+ virtual const MessageLite& GetMessage(
+ const MessageLite& prototype) const = 0;
+ virtual MessageLite* MutableMessage(const MessageLite& prototype) = 0;
+ virtual void SetAllocatedMessage(MessageLite *message) = 0;
+ virtual void UnsafeArenaSetAllocatedMessage(MessageLite *message) = 0;
+ virtual MessageLite* ReleaseMessage(const MessageLite& prototype) = 0;
+ virtual MessageLite* UnsafeArenaReleaseMessage(
+ const MessageLite& prototype) = 0;
+
+ virtual bool IsInitialized() const = 0;
+ virtual int ByteSize() const = 0;
+ virtual int SpaceUsed() const = 0;
+
+ virtual void MergeFrom(const LazyMessageExtension& other) = 0;
+ virtual void Clear() = 0;
+
+ virtual bool ReadMessage(const MessageLite& prototype,
+ io::CodedInputStream* input) = 0;
+ virtual void WriteMessage(int number,
+ io::CodedOutputStream* output) const = 0;
+ virtual uint8* WriteMessageToArray(int number, uint8* target) const = 0;
+ virtual uint8* InternalWriteMessageToArray(int number, bool,
+ uint8* target) const {
+ // TODO(gpike): make this pure virtual. This is a placeholder because we
+ // need to update third_party/upb, for example.
+ return WriteMessageToArray(number, target);
+ }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(LazyMessageExtension);
+ };
+ struct Extension {
+ // The order of these fields packs Extension into 24 bytes when using 8
+ // byte alignment. Consider this when adding or removing fields here.
+ union {
+ int32 int32_value;
+ int64 int64_value;
+ uint32 uint32_value;
+ uint64 uint64_value;
+ float float_value;
+ double double_value;
+ bool bool_value;
+ int enum_value;
+ string* string_value;
+ MessageLite* message_value;
+ LazyMessageExtension* lazymessage_value;
+
+ RepeatedField <int32 >* repeated_int32_value;
+ RepeatedField <int64 >* repeated_int64_value;
+ RepeatedField <uint32 >* repeated_uint32_value;
+ RepeatedField <uint64 >* repeated_uint64_value;
+ RepeatedField <float >* repeated_float_value;
+ RepeatedField <double >* repeated_double_value;
+ RepeatedField <bool >* repeated_bool_value;
+ RepeatedField <int >* repeated_enum_value;
+ RepeatedPtrField<string >* repeated_string_value;
+ RepeatedPtrField<MessageLite>* repeated_message_value;
+ };
+
+ FieldType type;
+ bool is_repeated;
+
+ // For singular types, indicates if the extension is "cleared". This
+ // happens when an extension is set and then later cleared by the caller.
+ // We want to keep the Extension object around for reuse, so instead of
+ // removing it from the map, we just set is_cleared = true. This has no
+ // meaning for repeated types; for those, the size of the RepeatedField
+ // simply becomes zero when cleared.
+ bool is_cleared : 4;
+
+ // For singular message types, indicates whether lazy parsing is enabled
+ // for this extension. This field is only valid when type == TYPE_MESSAGE
+ // and !is_repeated because we only support lazy parsing for singular
+ // message types currently. If is_lazy = true, the extension is stored in
+ // lazymessage_value. Otherwise, the extension will be message_value.
+ bool is_lazy : 4;
+
+ // For repeated types, this indicates if the [packed=true] option is set.
+ bool is_packed;
+
+ // For packed fields, the size of the packed data is recorded here when
+ // ByteSize() is called then used during serialization.
+ // TODO(kenton): Use atomic<int> when C++ supports it.
+ mutable int cached_size;
+
+ // The descriptor for this extension, if one exists and is known. May be
+ // NULL. Must not be NULL if the descriptor for the extension does not
+ // live in the same pool as the descriptor for the containing type.
+ const FieldDescriptor* descriptor;
+
+ // Some helper methods for operations on a single Extension.
+ void SerializeFieldWithCachedSizes(
+ int number,
+ io::CodedOutputStream* output) const;
+ uint8* InternalSerializeFieldWithCachedSizesToArray(
+ int number,
+ bool deterministic,
+ uint8* target) const;
+ void SerializeMessageSetItemWithCachedSizes(
+ int number,
+ io::CodedOutputStream* output) const;
+ uint8* InternalSerializeMessageSetItemWithCachedSizesToArray(
+ int number,
+ bool deterministic,
+ uint8* target) const;
+ int ByteSize(int number) const;
+ int MessageSetItemByteSize(int number) const;
+ void Clear();
+ int GetSize() const;
+ void Free();
+ int SpaceUsedExcludingSelf() const;
+ };
+ typedef std::map<int, Extension> ExtensionMap;
+
+
+ // Merges existing Extension from other_extension
+ void InternalExtensionMergeFrom(int number, const Extension& other_extension);
+
+ // Returns true and fills field_number and extension if extension is found.
+ // Note to support packed repeated field compatibility, it also fills whether
+ // the tag on wire is packed, which can be different from
+ // extension->is_packed (whether packed=true is specified).
+ bool FindExtensionInfoFromTag(uint32 tag, ExtensionFinder* extension_finder,
+ int* field_number, ExtensionInfo* extension,
+ bool* was_packed_on_wire);
+
+ // Returns true and fills extension if extension is found.
+ // Note to support packed repeated field compatibility, it also fills whether
+ // the tag on wire is packed, which can be different from
+ // extension->is_packed (whether packed=true is specified).
+ bool FindExtensionInfoFromFieldNumber(int wire_type, int field_number,
+ ExtensionFinder* extension_finder,
+ ExtensionInfo* extension,
+ bool* was_packed_on_wire);
+
+ // Parses a single extension from the input. The input should start out
+ // positioned immediately after the wire tag. This method is called in
+ // ParseField() after field number and was_packed_on_wire is extracted from
+ // the wire tag and ExtensionInfo is found by the field number.
+ bool ParseFieldWithExtensionInfo(int field_number,
+ bool was_packed_on_wire,
+ const ExtensionInfo& extension,
+ io::CodedInputStream* input,
+ FieldSkipper* field_skipper);
+
+ // Like ParseField(), but this method may parse singular message extensions
+ // lazily depending on the value of FLAGS_eagerly_parse_message_sets.
+ bool ParseFieldMaybeLazily(int wire_type, int field_number,
+ io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ MessageSetFieldSkipper* field_skipper);
+
+ // Gets the extension with the given number, creating it if it does not
+ // already exist. Returns true if the extension did not already exist.
+ bool MaybeNewExtension(int number, const FieldDescriptor* descriptor,
+ Extension** result);
+
+ // Gets the repeated extension for the given descriptor, creating it if
+ // it does not exist.
+ Extension* MaybeNewRepeatedExtension(const FieldDescriptor* descriptor);
+
+ // Parse a single MessageSet item -- called just after the item group start
+ // tag has been read.
+ bool ParseMessageSetItem(io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ MessageSetFieldSkipper* field_skipper);
+
+ // Hack: RepeatedPtrFieldBase declares ExtensionSet as a friend. This
+ // friendship should automatically extend to ExtensionSet::Extension, but
+ // unfortunately some older compilers (e.g. GCC 3.4.4) do not implement this
+ // correctly. So, we must provide helpers for calling methods of that
+ // class.
+
+ // Defined in extension_set_heavy.cc.
+ static inline int RepeatedMessage_SpaceUsedExcludingSelf(
+ RepeatedPtrFieldBase* field);
+
+ // The Extension struct is small enough to be passed by value, so we use it
+ // directly as the value type in the map rather than use pointers. We use
+ // a map rather than hash_map here because we expect most ExtensionSets will
+ // only contain a small number of extensions whereas hash_map is optimized
+ // for 100 elements or more. Also, we want AppendToList() to order fields
+ // by field number.
+ ExtensionMap extensions_;
+ ::google::protobuf::Arena* arena_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionSet);
+};
+
+// These are just for convenience...
+inline void ExtensionSet::SetString(int number, FieldType type,
+ const string& value,
+ const FieldDescriptor* descriptor) {
+ MutableString(number, type, descriptor)->assign(value);
+}
+inline void ExtensionSet::SetRepeatedString(int number, int index,
+ const string& value) {
+ MutableRepeatedString(number, index)->assign(value);
+}
+inline void ExtensionSet::AddString(int number, FieldType type,
+ const string& value,
+ const FieldDescriptor* descriptor) {
+ AddString(number, type, descriptor)->assign(value);
+}
+
+// ===================================================================
+// Glue for generated extension accessors
+
+// -------------------------------------------------------------------
+// Template magic
+
+// First we have a set of classes representing "type traits" for different
+// field types. A type traits class knows how to implement basic accessors
+// for extensions of a particular type given an ExtensionSet. The signature
+// for a type traits class looks like this:
+//
+// class TypeTraits {
+// public:
+// typedef ? ConstType;
+// typedef ? MutableType;
+// // TypeTraits for singular fields and repeated fields will define the
+// // symbol "Singular" or "Repeated" respectively. These two symbols will
+// // be used in extension accessors to distinguish between singular
+// // extensions and repeated extensions. If the TypeTraits for the passed
+// // in extension doesn't have the expected symbol defined, it means the
+// // user is passing a repeated extension to a singular accessor, or the
+// // opposite. In that case the C++ compiler will generate an error
+// // message "no matching member function" to inform the user.
+// typedef ? Singular
+// typedef ? Repeated
+//
+// static inline ConstType Get(int number, const ExtensionSet& set);
+// static inline void Set(int number, ConstType value, ExtensionSet* set);
+// static inline MutableType Mutable(int number, ExtensionSet* set);
+//
+// // Variants for repeated fields.
+// static inline ConstType Get(int number, const ExtensionSet& set,
+// int index);
+// static inline void Set(int number, int index,
+// ConstType value, ExtensionSet* set);
+// static inline MutableType Mutable(int number, int index,
+// ExtensionSet* set);
+// static inline void Add(int number, ConstType value, ExtensionSet* set);
+// static inline MutableType Add(int number, ExtensionSet* set);
+// };
+//
+// Not all of these methods make sense for all field types. For example, the
+// "Mutable" methods only make sense for strings and messages, and the
+// repeated methods only make sense for repeated types. So, each type
+// traits class implements only the set of methods from this signature that it
+// actually supports. This will cause a compiler error if the user tries to
+// access an extension using a method that doesn't make sense for its type.
+// For example, if "foo" is an extension of type "optional int32", then if you
+// try to write code like:
+// my_message.MutableExtension(foo)
+// you will get a compile error because PrimitiveTypeTraits<int32> does not
+// have a "Mutable()" method.
+
+// -------------------------------------------------------------------
+// PrimitiveTypeTraits
+
+// Since the ExtensionSet has different methods for each primitive type,
+// we must explicitly define the methods of the type traits class for each
+// known type.
+template <typename Type>
+class PrimitiveTypeTraits {
+ public:
+ typedef Type ConstType;
+ typedef Type MutableType;
+ typedef PrimitiveTypeTraits<Type> Singular;
+
+ static inline ConstType Get(int number, const ExtensionSet& set,
+ ConstType default_value);
+ static inline void Set(int number, FieldType field_type,
+ ConstType value, ExtensionSet* set);
+};
+
+template <typename Type>
+class RepeatedPrimitiveTypeTraits {
+ public:
+ typedef Type ConstType;
+ typedef Type MutableType;
+ typedef RepeatedPrimitiveTypeTraits<Type> Repeated;
+
+ typedef RepeatedField<Type> RepeatedFieldType;
+
+ static inline Type Get(int number, const ExtensionSet& set, int index);
+ static inline void Set(int number, int index, Type value, ExtensionSet* set);
+ static inline void Add(int number, FieldType field_type,
+ bool is_packed, Type value, ExtensionSet* set);
+
+ static inline const RepeatedField<ConstType>&
+ GetRepeated(int number, const ExtensionSet& set);
+ static inline RepeatedField<Type>*
+ MutableRepeated(int number, FieldType field_type,
+ bool is_packed, ExtensionSet* set);
+
+ static const RepeatedFieldType* GetDefaultRepeatedField();
+};
+
+LIBPROTOBUF_EXPORT extern ProtobufOnceType repeated_primitive_generic_type_traits_once_init_;
+
+class LIBPROTOBUF_EXPORT RepeatedPrimitiveGenericTypeTraits {
+ private:
+ template<typename Type> friend class RepeatedPrimitiveTypeTraits;
+ static void InitializeDefaultRepeatedFields();
+ static void DestroyDefaultRepeatedFields();
+ static const RepeatedField<int32>* default_repeated_field_int32_;
+ static const RepeatedField<int64>* default_repeated_field_int64_;
+ static const RepeatedField<uint32>* default_repeated_field_uint32_;
+ static const RepeatedField<uint64>* default_repeated_field_uint64_;
+ static const RepeatedField<double>* default_repeated_field_double_;
+ static const RepeatedField<float>* default_repeated_field_float_;
+ static const RepeatedField<bool>* default_repeated_field_bool_;
+};
+
+#define PROTOBUF_DEFINE_PRIMITIVE_TYPE(TYPE, METHOD) \
+template<> inline TYPE PrimitiveTypeTraits<TYPE>::Get( \
+ int number, const ExtensionSet& set, TYPE default_value) { \
+ return set.Get##METHOD(number, default_value); \
+} \
+template<> inline void PrimitiveTypeTraits<TYPE>::Set( \
+ int number, FieldType field_type, TYPE value, ExtensionSet* set) { \
+ set->Set##METHOD(number, field_type, value, NULL); \
+} \
+ \
+template<> inline TYPE RepeatedPrimitiveTypeTraits<TYPE>::Get( \
+ int number, const ExtensionSet& set, int index) { \
+ return set.GetRepeated##METHOD(number, index); \
+} \
+template<> inline void RepeatedPrimitiveTypeTraits<TYPE>::Set( \
+ int number, int index, TYPE value, ExtensionSet* set) { \
+ set->SetRepeated##METHOD(number, index, value); \
+} \
+template<> inline void RepeatedPrimitiveTypeTraits<TYPE>::Add( \
+ int number, FieldType field_type, bool is_packed, \
+ TYPE value, ExtensionSet* set) { \
+ set->Add##METHOD(number, field_type, is_packed, value, NULL); \
+} \
+template<> inline const RepeatedField<TYPE>* \
+ RepeatedPrimitiveTypeTraits<TYPE>::GetDefaultRepeatedField() { \
+ ::google::protobuf::GoogleOnceInit( \
+ &repeated_primitive_generic_type_traits_once_init_, \
+ &RepeatedPrimitiveGenericTypeTraits::InitializeDefaultRepeatedFields); \
+ return RepeatedPrimitiveGenericTypeTraits:: \
+ default_repeated_field_##TYPE##_; \
+} \
+template<> inline const RepeatedField<TYPE>& \
+ RepeatedPrimitiveTypeTraits<TYPE>::GetRepeated(int number, \
+ const ExtensionSet& set) { \
+ return *reinterpret_cast<const RepeatedField<TYPE>*>( \
+ set.GetRawRepeatedField( \
+ number, GetDefaultRepeatedField())); \
+} \
+template<> inline RepeatedField<TYPE>* \
+ RepeatedPrimitiveTypeTraits<TYPE>::MutableRepeated(int number, \
+ FieldType field_type, \
+ bool is_packed, \
+ ExtensionSet* set) { \
+ return reinterpret_cast<RepeatedField<TYPE>*>( \
+ set->MutableRawRepeatedField(number, field_type, is_packed, NULL)); \
+}
+
+PROTOBUF_DEFINE_PRIMITIVE_TYPE( int32, Int32)
+PROTOBUF_DEFINE_PRIMITIVE_TYPE( int64, Int64)
+PROTOBUF_DEFINE_PRIMITIVE_TYPE(uint32, UInt32)
+PROTOBUF_DEFINE_PRIMITIVE_TYPE(uint64, UInt64)
+PROTOBUF_DEFINE_PRIMITIVE_TYPE( float, Float)
+PROTOBUF_DEFINE_PRIMITIVE_TYPE(double, Double)
+PROTOBUF_DEFINE_PRIMITIVE_TYPE( bool, Bool)
+
+#undef PROTOBUF_DEFINE_PRIMITIVE_TYPE
+
+// -------------------------------------------------------------------
+// StringTypeTraits
+
+// Strings support both Set() and Mutable().
+class LIBPROTOBUF_EXPORT StringTypeTraits {
+ public:
+ typedef const string& ConstType;
+ typedef string* MutableType;
+ typedef StringTypeTraits Singular;
+
+ static inline const string& Get(int number, const ExtensionSet& set,
+ ConstType default_value) {
+ return set.GetString(number, default_value);
+ }
+ static inline void Set(int number, FieldType field_type,
+ const string& value, ExtensionSet* set) {
+ set->SetString(number, field_type, value, NULL);
+ }
+ static inline string* Mutable(int number, FieldType field_type,
+ ExtensionSet* set) {
+ return set->MutableString(number, field_type, NULL);
+ }
+};
+
+LIBPROTOBUF_EXPORT extern ProtobufOnceType repeated_string_type_traits_once_init_;
+
+class LIBPROTOBUF_EXPORT RepeatedStringTypeTraits {
+ public:
+ typedef const string& ConstType;
+ typedef string* MutableType;
+ typedef RepeatedStringTypeTraits Repeated;
+
+ typedef RepeatedPtrField<string> RepeatedFieldType;
+
+ static inline const string& Get(int number, const ExtensionSet& set,
+ int index) {
+ return set.GetRepeatedString(number, index);
+ }
+ static inline void Set(int number, int index,
+ const string& value, ExtensionSet* set) {
+ set->SetRepeatedString(number, index, value);
+ }
+ static inline string* Mutable(int number, int index, ExtensionSet* set) {
+ return set->MutableRepeatedString(number, index);
+ }
+ static inline void Add(int number, FieldType field_type,
+ bool /*is_packed*/, const string& value,
+ ExtensionSet* set) {
+ set->AddString(number, field_type, value, NULL);
+ }
+ static inline string* Add(int number, FieldType field_type,
+ ExtensionSet* set) {
+ return set->AddString(number, field_type, NULL);
+ }
+ static inline const RepeatedPtrField<string>&
+ GetRepeated(int number, const ExtensionSet& set) {
+ return *reinterpret_cast<const RepeatedPtrField<string>*>(
+ set.GetRawRepeatedField(number, GetDefaultRepeatedField()));
+ }
+
+ static inline RepeatedPtrField<string>*
+ MutableRepeated(int number, FieldType field_type,
+ bool is_packed, ExtensionSet* set) {
+ return reinterpret_cast<RepeatedPtrField<string>*>(
+ set->MutableRawRepeatedField(number, field_type,
+ is_packed, NULL));
+ }
+
+ static const RepeatedFieldType* GetDefaultRepeatedField() {
+ ::google::protobuf::GoogleOnceInit(&repeated_string_type_traits_once_init_,
+ &InitializeDefaultRepeatedFields);
+ return default_repeated_field_;
+ }
+
+ private:
+ static void InitializeDefaultRepeatedFields();
+ static void DestroyDefaultRepeatedFields();
+ static const RepeatedFieldType *default_repeated_field_;
+};
+
+// -------------------------------------------------------------------
+// EnumTypeTraits
+
+// ExtensionSet represents enums using integers internally, so we have to
+// static_cast around.
+template <typename Type, bool IsValid(int)>
+class EnumTypeTraits {
+ public:
+ typedef Type ConstType;
+ typedef Type MutableType;
+ typedef EnumTypeTraits<Type, IsValid> Singular;
+
+ static inline ConstType Get(int number, const ExtensionSet& set,
+ ConstType default_value) {
+ return static_cast<Type>(set.GetEnum(number, default_value));
+ }
+ static inline void Set(int number, FieldType field_type,
+ ConstType value, ExtensionSet* set) {
+ GOOGLE_DCHECK(IsValid(value));
+ set->SetEnum(number, field_type, value, NULL);
+ }
+};
+
+template <typename Type, bool IsValid(int)>
+class RepeatedEnumTypeTraits {
+ public:
+ typedef Type ConstType;
+ typedef Type MutableType;
+ typedef RepeatedEnumTypeTraits<Type, IsValid> Repeated;
+
+ typedef RepeatedField<Type> RepeatedFieldType;
+
+ static inline ConstType Get(int number, const ExtensionSet& set, int index) {
+ return static_cast<Type>(set.GetRepeatedEnum(number, index));
+ }
+ static inline void Set(int number, int index,
+ ConstType value, ExtensionSet* set) {
+ GOOGLE_DCHECK(IsValid(value));
+ set->SetRepeatedEnum(number, index, value);
+ }
+ static inline void Add(int number, FieldType field_type,
+ bool is_packed, ConstType value, ExtensionSet* set) {
+ GOOGLE_DCHECK(IsValid(value));
+ set->AddEnum(number, field_type, is_packed, value, NULL);
+ }
+ static inline const RepeatedField<Type>& GetRepeated(int number,
+ const ExtensionSet&
+ set) {
+ // Hack: the `Extension` struct stores a RepeatedField<int> for enums.
+ // RepeatedField<int> cannot implicitly convert to RepeatedField<EnumType>
+ // so we need to do some casting magic. See message.h for similar
+ // contortions for non-extension fields.
+ return *reinterpret_cast<const RepeatedField<Type>*>(
+ set.GetRawRepeatedField(number, GetDefaultRepeatedField()));
+ }
+
+ static inline RepeatedField<Type>* MutableRepeated(int number,
+ FieldType field_type,
+ bool is_packed,
+ ExtensionSet* set) {
+ return reinterpret_cast<RepeatedField<Type>*>(
+ set->MutableRawRepeatedField(number, field_type, is_packed, NULL));
+ }
+
+ static const RepeatedFieldType* GetDefaultRepeatedField() {
+ // Hack: as noted above, repeated enum fields are internally stored as a
+ // RepeatedField<int>. We need to be able to instantiate global static
+ // objects to return as default (empty) repeated fields on non-existent
+ // extensions. We would not be able to know a-priori all of the enum types
+ // (values of |Type|) to instantiate all of these, so we just re-use int32's
+ // default repeated field object.
+ return reinterpret_cast<const RepeatedField<Type>*>(
+ RepeatedPrimitiveTypeTraits<int32>::GetDefaultRepeatedField());
+ }
+};
+
+// -------------------------------------------------------------------
+// MessageTypeTraits
+
+// ExtensionSet guarantees that when manipulating extensions with message
+// types, the implementation used will be the compiled-in class representing
+// that type. So, we can static_cast down to the exact type we expect.
+template <typename Type>
+class MessageTypeTraits {
+ public:
+ typedef const Type& ConstType;
+ typedef Type* MutableType;
+ typedef MessageTypeTraits<Type> Singular;
+
+ static inline ConstType Get(int number, const ExtensionSet& set,
+ ConstType default_value) {
+ return static_cast<const Type&>(
+ set.GetMessage(number, default_value));
+ }
+ static inline MutableType Mutable(int number, FieldType field_type,
+ ExtensionSet* set) {
+ return static_cast<Type*>(
+ set->MutableMessage(number, field_type, Type::default_instance(), NULL));
+ }
+ static inline void SetAllocated(int number, FieldType field_type,
+ MutableType message, ExtensionSet* set) {
+ set->SetAllocatedMessage(number, field_type, NULL, message);
+ }
+ static inline void UnsafeArenaSetAllocated(int number, FieldType field_type,
+ MutableType message,
+ ExtensionSet* set) {
+ set->UnsafeArenaSetAllocatedMessage(number, field_type, NULL, message);
+ }
+ static inline MutableType Release(int number, FieldType /* field_type */,
+ ExtensionSet* set) {
+ return static_cast<Type*>(set->ReleaseMessage(
+ number, Type::default_instance()));
+ }
+ static inline MutableType UnsafeArenaRelease(int number,
+ FieldType /* field_type */,
+ ExtensionSet* set) {
+ return static_cast<Type*>(set->UnsafeArenaReleaseMessage(
+ number, Type::default_instance()));
+ }
+};
+
+// forward declaration
+class RepeatedMessageGenericTypeTraits;
+
+template <typename Type>
+class RepeatedMessageTypeTraits {
+ public:
+ typedef const Type& ConstType;
+ typedef Type* MutableType;
+ typedef RepeatedMessageTypeTraits<Type> Repeated;
+
+ typedef RepeatedPtrField<Type> RepeatedFieldType;
+
+ static inline ConstType Get(int number, const ExtensionSet& set, int index) {
+ return static_cast<const Type&>(set.GetRepeatedMessage(number, index));
+ }
+ static inline MutableType Mutable(int number, int index, ExtensionSet* set) {
+ return static_cast<Type*>(set->MutableRepeatedMessage(number, index));
+ }
+ static inline MutableType Add(int number, FieldType field_type,
+ ExtensionSet* set) {
+ return static_cast<Type*>(
+ set->AddMessage(number, field_type, Type::default_instance(), NULL));
+ }
+ static inline const RepeatedPtrField<Type>& GetRepeated(int number,
+ const ExtensionSet&
+ set) {
+ // See notes above in RepeatedEnumTypeTraits::GetRepeated(): same
+ // casting hack applies here, because a RepeatedPtrField<MessageLite>
+ // cannot naturally become a RepeatedPtrType<Type> even though Type is
+ // presumably a message. google::protobuf::Message goes through similar contortions
+ // with a reinterpret_cast<>.
+ return *reinterpret_cast<const RepeatedPtrField<Type>*>(
+ set.GetRawRepeatedField(number, GetDefaultRepeatedField()));
+ }
+ static inline RepeatedPtrField<Type>* MutableRepeated(int number,
+ FieldType field_type,
+ bool is_packed,
+ ExtensionSet* set) {
+ return reinterpret_cast<RepeatedPtrField<Type>*>(
+ set->MutableRawRepeatedField(number, field_type, is_packed, NULL));
+ }
+
+ static const RepeatedFieldType* GetDefaultRepeatedField();
+};
+
+LIBPROTOBUF_EXPORT extern ProtobufOnceType repeated_message_generic_type_traits_once_init_;
+
+// This class exists only to hold a generic default empty repeated field for all
+// message-type repeated field extensions.
+class LIBPROTOBUF_EXPORT RepeatedMessageGenericTypeTraits {
+ public:
+ typedef RepeatedPtrField< ::google::protobuf::MessageLite*> RepeatedFieldType;
+ private:
+ template<typename Type> friend class RepeatedMessageTypeTraits;
+ static void InitializeDefaultRepeatedFields();
+ static void DestroyDefaultRepeatedFields();
+ static const RepeatedFieldType* default_repeated_field_;
+};
+
+template<typename Type> inline
+ const typename RepeatedMessageTypeTraits<Type>::RepeatedFieldType*
+ RepeatedMessageTypeTraits<Type>::GetDefaultRepeatedField() {
+ ::google::protobuf::GoogleOnceInit(
+ &repeated_message_generic_type_traits_once_init_,
+ &RepeatedMessageGenericTypeTraits::InitializeDefaultRepeatedFields);
+ return reinterpret_cast<const RepeatedFieldType*>(
+ RepeatedMessageGenericTypeTraits::default_repeated_field_);
+}
+
+// -------------------------------------------------------------------
+// ExtensionIdentifier
+
+// This is the type of actual extension objects. E.g. if you have:
+// extends Foo with optional int32 bar = 1234;
+// then "bar" will be defined in C++ as:
+// ExtensionIdentifier<Foo, PrimitiveTypeTraits<int32>, 1, false> bar(1234);
+//
+// Note that we could, in theory, supply the field number as a template
+// parameter, and thus make an instance of ExtensionIdentifier have no
+// actual contents. However, if we did that, then using at extension
+// identifier would not necessarily cause the compiler to output any sort
+// of reference to any simple defined in the extension's .pb.o file. Some
+// linkers will actually drop object files that are not explicitly referenced,
+// but that would be bad because it would cause this extension to not be
+// registered at static initialization, and therefore using it would crash.
+
+template <typename ExtendeeType, typename TypeTraitsType,
+ FieldType field_type, bool is_packed>
+class ExtensionIdentifier {
+ public:
+ typedef TypeTraitsType TypeTraits;
+ typedef ExtendeeType Extendee;
+
+ ExtensionIdentifier(int number, typename TypeTraits::ConstType default_value)
+ : number_(number), default_value_(default_value) {}
+ inline int number() const { return number_; }
+ typename TypeTraits::ConstType default_value() const {
+ return default_value_;
+ }
+
+ private:
+ const int number_;
+ typename TypeTraits::ConstType default_value_;
+};
+
+// -------------------------------------------------------------------
+// Generated accessors
+
+// This macro should be expanded in the context of a generated type which
+// has extensions.
+//
+// We use "_proto_TypeTraits" as a type name below because "TypeTraits"
+// causes problems if the class has a nested message or enum type with that
+// name and "_TypeTraits" is technically reserved for the C++ library since
+// it starts with an underscore followed by a capital letter.
+//
+// For similar reason, we use "_field_type" and "_is_packed" as parameter names
+// below, so that "field_type" and "is_packed" can be used as field names.
+#define GOOGLE_PROTOBUF_EXTENSION_ACCESSORS(CLASSNAME) \
+ /* Has, Size, Clear */ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline bool HasExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) const { \
+ return _extensions_.Has(id.number()); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline void ClearExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \
+ _extensions_.ClearExtension(id.number()); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline int ExtensionSize( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) const { \
+ return _extensions_.ExtensionSize(id.number()); \
+ } \
+ \
+ /* Singular accessors */ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Singular::ConstType GetExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) const { \
+ return _proto_TypeTraits::Get(id.number(), _extensions_, \
+ id.default_value()); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Singular::MutableType MutableExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \
+ return _proto_TypeTraits::Mutable(id.number(), _field_type, \
+ &_extensions_); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline void SetExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \
+ typename _proto_TypeTraits::Singular::ConstType value) { \
+ _proto_TypeTraits::Set(id.number(), _field_type, value, &_extensions_); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline void SetAllocatedExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \
+ typename _proto_TypeTraits::Singular::MutableType value) { \
+ _proto_TypeTraits::SetAllocated(id.number(), _field_type, \
+ value, &_extensions_); \
+ } \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline void UnsafeArenaSetAllocatedExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \
+ typename _proto_TypeTraits::Singular::MutableType value) { \
+ _proto_TypeTraits::UnsafeArenaSetAllocated(id.number(), _field_type, \
+ value, &_extensions_); \
+ } \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Singular::MutableType ReleaseExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \
+ return _proto_TypeTraits::Release(id.number(), _field_type, \
+ &_extensions_); \
+ } \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Singular::MutableType \
+ UnsafeArenaReleaseExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \
+ return _proto_TypeTraits::UnsafeArenaRelease(id.number(), _field_type, \
+ &_extensions_); \
+ } \
+ \
+ /* Repeated accessors */ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Repeated::ConstType GetExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \
+ int index) const { \
+ return _proto_TypeTraits::Get(id.number(), _extensions_, index); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Repeated::MutableType MutableExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \
+ int index) { \
+ return _proto_TypeTraits::Mutable(id.number(), index, &_extensions_); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline void SetExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \
+ int index, typename _proto_TypeTraits::Repeated::ConstType value) { \
+ _proto_TypeTraits::Set(id.number(), index, value, &_extensions_); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Repeated::MutableType AddExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \
+ return _proto_TypeTraits::Add(id.number(), _field_type, &_extensions_); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline void AddExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \
+ typename _proto_TypeTraits::Repeated::ConstType value) { \
+ _proto_TypeTraits::Add(id.number(), _field_type, _is_packed, \
+ value, &_extensions_); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline const typename _proto_TypeTraits::Repeated::RepeatedFieldType& \
+ GetRepeatedExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, \
+ _is_packed>& id) const { \
+ return _proto_TypeTraits::GetRepeated(id.number(), _extensions_); \
+ } \
+ \
+ template <typename _proto_TypeTraits, \
+ ::google::protobuf::internal::FieldType _field_type, \
+ bool _is_packed> \
+ inline typename _proto_TypeTraits::Repeated::RepeatedFieldType* \
+ MutableRepeatedExtension( \
+ const ::google::protobuf::internal::ExtensionIdentifier< \
+ CLASSNAME, _proto_TypeTraits, _field_type, \
+ _is_packed>& id) { \
+ return _proto_TypeTraits::MutableRepeated(id.number(), _field_type, \
+ _is_packed, &_extensions_); \
+ }
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_EXTENSION_SET_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/extension_set_heavy.cc b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set_heavy.cc
new file mode 100644
index 0000000000..b26a246c7d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set_heavy.cc
@@ -0,0 +1,801 @@
+// 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.
+//
+// Contains methods defined in extension_set.h which cannot be part of the
+// lite library because they use descriptors or reflection.
+
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+
+namespace google {
+
+namespace protobuf {
+namespace internal {
+
+// A FieldSkipper used to store unknown MessageSet fields into UnknownFieldSet.
+class MessageSetFieldSkipper
+ : public UnknownFieldSetFieldSkipper {
+ public:
+ explicit MessageSetFieldSkipper(UnknownFieldSet* unknown_fields)
+ : UnknownFieldSetFieldSkipper(unknown_fields) {}
+ virtual ~MessageSetFieldSkipper() {}
+
+ virtual bool SkipMessageSetField(io::CodedInputStream* input,
+ int field_number);
+};
+bool MessageSetFieldSkipper::SkipMessageSetField(
+ io::CodedInputStream* input, int field_number) {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ if (unknown_fields_ == NULL) {
+ return input->Skip(length);
+ } else {
+ return input->ReadString(
+ unknown_fields_->AddLengthDelimited(field_number), length);
+ }
+}
+
+
+// Implementation of ExtensionFinder which finds extensions in a given
+// DescriptorPool, using the given MessageFactory to construct sub-objects.
+// This class is implemented in extension_set_heavy.cc.
+class DescriptorPoolExtensionFinder : public ExtensionFinder {
+ public:
+ DescriptorPoolExtensionFinder(const DescriptorPool* pool,
+ MessageFactory* factory,
+ const Descriptor* containing_type)
+ : pool_(pool), factory_(factory), containing_type_(containing_type) {}
+ virtual ~DescriptorPoolExtensionFinder() {}
+
+ virtual bool Find(int number, ExtensionInfo* output);
+
+ private:
+ const DescriptorPool* pool_;
+ MessageFactory* factory_;
+ const Descriptor* containing_type_;
+};
+
+void ExtensionSet::AppendToList(
+ const Descriptor* containing_type,
+ const DescriptorPool* pool,
+ std::vector<const FieldDescriptor*>* output) const {
+ for (ExtensionMap::const_iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ bool has = false;
+ if (iter->second.is_repeated) {
+ has = iter->second.GetSize() > 0;
+ } else {
+ has = !iter->second.is_cleared;
+ }
+
+ if (has) {
+ // TODO(kenton): Looking up each field by number is somewhat unfortunate.
+ // Is there a better way? The problem is that descriptors are lazily-
+ // initialized, so they might not even be constructed until
+ // AppendToList() is called.
+
+ if (iter->second.descriptor == NULL) {
+ output->push_back(pool->FindExtensionByNumber(
+ containing_type, iter->first));
+ } else {
+ output->push_back(iter->second.descriptor);
+ }
+ }
+ }
+}
+
+inline FieldDescriptor::Type real_type(FieldType type) {
+ GOOGLE_DCHECK(type > 0 && type <= FieldDescriptor::MAX_TYPE);
+ return static_cast<FieldDescriptor::Type>(type);
+}
+
+inline FieldDescriptor::CppType cpp_type(FieldType type) {
+ return FieldDescriptor::TypeToCppType(
+ static_cast<FieldDescriptor::Type>(type));
+}
+
+inline WireFormatLite::FieldType field_type(FieldType type) {
+ GOOGLE_DCHECK(type > 0 && type <= WireFormatLite::MAX_FIELD_TYPE);
+ return static_cast<WireFormatLite::FieldType>(type);
+}
+
+#define GOOGLE_DCHECK_TYPE(EXTENSION, LABEL, CPPTYPE) \
+ GOOGLE_DCHECK_EQ((EXTENSION).is_repeated ? FieldDescriptor::LABEL_REPEATED \
+ : FieldDescriptor::LABEL_OPTIONAL, \
+ FieldDescriptor::LABEL_##LABEL); \
+ GOOGLE_DCHECK_EQ(cpp_type((EXTENSION).type), FieldDescriptor::CPPTYPE_##CPPTYPE)
+
+const MessageLite& ExtensionSet::GetMessage(int number,
+ const Descriptor* message_type,
+ MessageFactory* factory) const {
+ ExtensionMap::const_iterator iter = extensions_.find(number);
+ if (iter == extensions_.end() || iter->second.is_cleared) {
+ // Not present. Return the default value.
+ return *factory->GetPrototype(message_type);
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, MESSAGE);
+ if (iter->second.is_lazy) {
+ return iter->second.lazymessage_value->GetMessage(
+ *factory->GetPrototype(message_type));
+ } else {
+ return *iter->second.message_value;
+ }
+ }
+}
+
+MessageLite* ExtensionSet::MutableMessage(const FieldDescriptor* descriptor,
+ MessageFactory* factory) {
+ Extension* extension;
+ if (MaybeNewExtension(descriptor->number(), descriptor, &extension)) {
+ extension->type = descriptor->type();
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), FieldDescriptor::CPPTYPE_MESSAGE);
+ extension->is_repeated = false;
+ extension->is_packed = false;
+ const MessageLite* prototype =
+ factory->GetPrototype(descriptor->message_type());
+ extension->is_lazy = false;
+ extension->message_value = prototype->New(arena_);
+ extension->is_cleared = false;
+ return extension->message_value;
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, OPTIONAL, MESSAGE);
+ extension->is_cleared = false;
+ if (extension->is_lazy) {
+ return extension->lazymessage_value->MutableMessage(
+ *factory->GetPrototype(descriptor->message_type()));
+ } else {
+ return extension->message_value;
+ }
+ }
+}
+
+MessageLite* ExtensionSet::ReleaseMessage(const FieldDescriptor* descriptor,
+ MessageFactory* factory) {
+ ExtensionMap::iterator iter = extensions_.find(descriptor->number());
+ if (iter == extensions_.end()) {
+ // Not present. Return NULL.
+ return NULL;
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, MESSAGE);
+ MessageLite* ret = NULL;
+ if (iter->second.is_lazy) {
+ ret = iter->second.lazymessage_value->ReleaseMessage(
+ *factory->GetPrototype(descriptor->message_type()));
+ if (arena_ == NULL) {
+ delete iter->second.lazymessage_value;
+ }
+ } else {
+ if (arena_ != NULL) {
+ ret = (iter->second.message_value)->New();
+ ret->CheckTypeAndMergeFrom(*(iter->second.message_value));
+ } else {
+ ret = iter->second.message_value;
+ }
+ }
+ extensions_.erase(descriptor->number());
+ return ret;
+ }
+}
+
+MessageLite* ExtensionSet::UnsafeArenaReleaseMessage(
+ const FieldDescriptor* descriptor, MessageFactory* factory) {
+ ExtensionMap::iterator iter = extensions_.find(descriptor->number());
+ if (iter == extensions_.end()) {
+ // Not present. Return NULL.
+ return NULL;
+ } else {
+ GOOGLE_DCHECK_TYPE(iter->second, OPTIONAL, MESSAGE);
+ MessageLite* ret = NULL;
+ if (iter->second.is_lazy) {
+ ret = iter->second.lazymessage_value->UnsafeArenaReleaseMessage(
+ *factory->GetPrototype(descriptor->message_type()));
+ if (arena_ == NULL) {
+ delete iter->second.lazymessage_value;
+ }
+ } else {
+ ret = iter->second.message_value;
+ }
+ extensions_.erase(descriptor->number());
+ return ret;
+ }
+}
+
+ExtensionSet::Extension* ExtensionSet::MaybeNewRepeatedExtension(const FieldDescriptor* descriptor) {
+ Extension* extension;
+ if (MaybeNewExtension(descriptor->number(), descriptor, &extension)) {
+ extension->type = descriptor->type();
+ GOOGLE_DCHECK_EQ(cpp_type(extension->type), FieldDescriptor::CPPTYPE_MESSAGE);
+ extension->is_repeated = true;
+ extension->repeated_message_value =
+ ::google::protobuf::Arena::CreateMessage<RepeatedPtrField<MessageLite> >(arena_);
+ } else {
+ GOOGLE_DCHECK_TYPE(*extension, REPEATED, MESSAGE);
+ }
+ return extension;
+}
+
+MessageLite* ExtensionSet::AddMessage(const FieldDescriptor* descriptor,
+ MessageFactory* factory) {
+ Extension* extension = MaybeNewRepeatedExtension(descriptor);
+
+ // RepeatedPtrField<Message> does not know how to Add() since it cannot
+ // allocate an abstract object, so we have to be tricky.
+ MessageLite* result = extension->repeated_message_value
+ ->AddFromCleared<GenericTypeHandler<MessageLite> >();
+ if (result == NULL) {
+ const MessageLite* prototype;
+ if (extension->repeated_message_value->size() == 0) {
+ prototype = factory->GetPrototype(descriptor->message_type());
+ GOOGLE_CHECK(prototype != NULL);
+ } else {
+ prototype = &extension->repeated_message_value->Get(0);
+ }
+ result = prototype->New(arena_);
+ extension->repeated_message_value->AddAllocated(result);
+ }
+ return result;
+}
+
+void ExtensionSet::AddAllocatedMessage(const FieldDescriptor* descriptor,
+ MessageLite* new_entry) {
+ Extension* extension = MaybeNewRepeatedExtension(descriptor);
+
+ extension->repeated_message_value->AddAllocated(new_entry);
+}
+
+static bool ValidateEnumUsingDescriptor(const void* arg, int number) {
+ return reinterpret_cast<const EnumDescriptor*>(arg)
+ ->FindValueByNumber(number) != NULL;
+}
+
+bool DescriptorPoolExtensionFinder::Find(int number, ExtensionInfo* output) {
+ const FieldDescriptor* extension =
+ pool_->FindExtensionByNumber(containing_type_, number);
+ if (extension == NULL) {
+ return false;
+ } else {
+ output->type = extension->type();
+ output->is_repeated = extension->is_repeated();
+ output->is_packed = extension->options().packed();
+ output->descriptor = extension;
+ if (extension->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ output->message_prototype =
+ factory_->GetPrototype(extension->message_type());
+ GOOGLE_CHECK(output->message_prototype != NULL)
+ << "Extension factory's GetPrototype() returned NULL for extension: "
+ << extension->full_name();
+ } else if (extension->cpp_type() == FieldDescriptor::CPPTYPE_ENUM) {
+ output->enum_validity_check.func = ValidateEnumUsingDescriptor;
+ output->enum_validity_check.arg = extension->enum_type();
+ }
+
+ return true;
+ }
+}
+
+bool ExtensionSet::ParseField(uint32 tag, io::CodedInputStream* input,
+ const Message* containing_type,
+ UnknownFieldSet* unknown_fields) {
+ UnknownFieldSetFieldSkipper skipper(unknown_fields);
+ if (input->GetExtensionPool() == NULL) {
+ GeneratedExtensionFinder finder(containing_type);
+ return ParseField(tag, input, &finder, &skipper);
+ } else {
+ DescriptorPoolExtensionFinder finder(input->GetExtensionPool(),
+ input->GetExtensionFactory(),
+ containing_type->GetDescriptor());
+ return ParseField(tag, input, &finder, &skipper);
+ }
+}
+
+bool ExtensionSet::ParseMessageSet(io::CodedInputStream* input,
+ const Message* containing_type,
+ UnknownFieldSet* unknown_fields) {
+ MessageSetFieldSkipper skipper(unknown_fields);
+ if (input->GetExtensionPool() == NULL) {
+ GeneratedExtensionFinder finder(containing_type);
+ return ParseMessageSet(input, &finder, &skipper);
+ } else {
+ DescriptorPoolExtensionFinder finder(input->GetExtensionPool(),
+ input->GetExtensionFactory(),
+ containing_type->GetDescriptor());
+ return ParseMessageSet(input, &finder, &skipper);
+ }
+}
+
+int ExtensionSet::SpaceUsedExcludingSelf() const {
+ int total_size =
+ extensions_.size() * sizeof(ExtensionMap::value_type);
+ for (ExtensionMap::const_iterator iter = extensions_.begin(),
+ end = extensions_.end();
+ iter != end;
+ ++iter) {
+ total_size += iter->second.SpaceUsedExcludingSelf();
+ }
+ return total_size;
+}
+
+inline int ExtensionSet::RepeatedMessage_SpaceUsedExcludingSelf(
+ RepeatedPtrFieldBase* field) {
+ return field->SpaceUsedExcludingSelf<GenericTypeHandler<Message> >();
+}
+
+int ExtensionSet::Extension::SpaceUsedExcludingSelf() const {
+ int total_size = 0;
+ if (is_repeated) {
+ switch (cpp_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case FieldDescriptor::CPPTYPE_##UPPERCASE: \
+ total_size += sizeof(*repeated_##LOWERCASE##_value) + \
+ repeated_##LOWERCASE##_value->SpaceUsedExcludingSelf();\
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE( UINT32, uint32);
+ HANDLE_TYPE( UINT64, uint64);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( DOUBLE, double);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, enum);
+ HANDLE_TYPE( STRING, string);
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ // repeated_message_value is actually a RepeatedPtrField<MessageLite>,
+ // but MessageLite has no SpaceUsed(), so we must directly call
+ // RepeatedPtrFieldBase::SpaceUsedExcludingSelf() with a different type
+ // handler.
+ total_size += sizeof(*repeated_message_value) +
+ RepeatedMessage_SpaceUsedExcludingSelf(repeated_message_value);
+ break;
+ }
+ } else {
+ switch (cpp_type(type)) {
+ case FieldDescriptor::CPPTYPE_STRING:
+ total_size += sizeof(*string_value) +
+ StringSpaceUsedExcludingSelf(*string_value);
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (is_lazy) {
+ total_size += lazymessage_value->SpaceUsed();
+ } else {
+ total_size += down_cast<Message*>(message_value)->SpaceUsed();
+ }
+ break;
+ default:
+ // No extra storage costs for primitive types.
+ break;
+ }
+ }
+ return total_size;
+}
+
+// The Serialize*ToArray methods are only needed in the heavy library, as
+// the lite library only generates SerializeWithCachedSizes.
+uint8* ExtensionSet::SerializeWithCachedSizesToArray(int start_field_number,
+ int end_field_number,
+ uint8* target) const {
+ return InternalSerializeWithCachedSizesToArray(
+ start_field_number, end_field_number, false, target);
+}
+
+uint8* ExtensionSet::SerializeMessageSetWithCachedSizesToArray(
+ uint8* target) const {
+ return InternalSerializeMessageSetWithCachedSizesToArray(false, target);
+}
+
+uint8* ExtensionSet::InternalSerializeWithCachedSizesToArray(
+ int start_field_number, int end_field_number,
+ bool deterministic, uint8* target) const {
+ ExtensionMap::const_iterator iter;
+ for (iter = extensions_.lower_bound(start_field_number);
+ iter != extensions_.end() && iter->first < end_field_number;
+ ++iter) {
+ target = iter->second.InternalSerializeFieldWithCachedSizesToArray(
+ iter->first, deterministic, target);
+ }
+ return target;
+}
+
+uint8* ExtensionSet::InternalSerializeMessageSetWithCachedSizesToArray(
+ bool deterministic, uint8* target) const {
+ ExtensionMap::const_iterator iter;
+ for (iter = extensions_.begin(); iter != extensions_.end(); ++iter) {
+ target = iter->second.InternalSerializeMessageSetItemWithCachedSizesToArray(
+ iter->first, deterministic, target);
+ }
+ return target;
+}
+
+uint8* ExtensionSet::Extension::InternalSerializeFieldWithCachedSizesToArray(
+ int number, bool deterministic, uint8* target) const {
+ if (is_repeated) {
+ if (is_packed) {
+ if (cached_size == 0) return target;
+
+ target = WireFormatLite::WriteTagToArray(number,
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED, target);
+ target = WireFormatLite::WriteInt32NoTagToArray(cached_size, target);
+
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case FieldDescriptor::TYPE_##UPPERCASE: \
+ for (int i = 0; i < repeated_##LOWERCASE##_value->size(); i++) { \
+ target = WireFormatLite::Write##CAMELCASE##NoTagToArray( \
+ repeated_##LOWERCASE##_value->Get(i), target); \
+ } \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, SInt32, int32);
+ HANDLE_TYPE( SINT64, SInt64, int64);
+ HANDLE_TYPE( FIXED32, Fixed32, uint32);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+ HANDLE_TYPE( ENUM, Enum, enum);
+#undef HANDLE_TYPE
+
+ case WireFormatLite::TYPE_STRING:
+ case WireFormatLite::TYPE_BYTES:
+ case WireFormatLite::TYPE_GROUP:
+ case WireFormatLite::TYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Non-primitive types can't be packed.";
+ break;
+ }
+ } else {
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case FieldDescriptor::TYPE_##UPPERCASE: \
+ for (int i = 0; i < repeated_##LOWERCASE##_value->size(); i++) { \
+ target = WireFormatLite::Write##CAMELCASE##ToArray(number, \
+ repeated_##LOWERCASE##_value->Get(i), target); \
+ } \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32);
+ HANDLE_TYPE( INT64, Int64, int64);
+ HANDLE_TYPE( UINT32, UInt32, uint32);
+ HANDLE_TYPE( UINT64, UInt64, uint64);
+ HANDLE_TYPE( SINT32, SInt32, int32);
+ HANDLE_TYPE( SINT64, SInt64, int64);
+ HANDLE_TYPE( FIXED32, Fixed32, uint32);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64);
+ HANDLE_TYPE( FLOAT, Float, float);
+ HANDLE_TYPE( DOUBLE, Double, double);
+ HANDLE_TYPE( BOOL, Bool, bool);
+ HANDLE_TYPE( STRING, String, string);
+ HANDLE_TYPE( BYTES, Bytes, string);
+ HANDLE_TYPE( ENUM, Enum, enum);
+#undef HANDLE_TYPE
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, LOWERCASE) \
+ case FieldDescriptor::TYPE_##UPPERCASE: \
+ for (int i = 0; i < repeated_##LOWERCASE##_value->size(); i++) { \
+ target = WireFormatLite::InternalWrite##CAMELCASE##ToArray( \
+ number, repeated_##LOWERCASE##_value->Get(i), \
+ deterministic, target); \
+ } \
+ break
+
+ HANDLE_TYPE( GROUP, Group, message);
+ HANDLE_TYPE( MESSAGE, Message, message);
+#undef HANDLE_TYPE
+ }
+ }
+ } else if (!is_cleared) {
+ switch (real_type(type)) {
+#define HANDLE_TYPE(UPPERCASE, CAMELCASE, VALUE) \
+ case FieldDescriptor::TYPE_##UPPERCASE: \
+ target = WireFormatLite::Write##CAMELCASE##ToArray( \
+ number, VALUE, target); \
+ break
+
+ HANDLE_TYPE( INT32, Int32, int32_value);
+ HANDLE_TYPE( INT64, Int64, int64_value);
+ HANDLE_TYPE( UINT32, UInt32, uint32_value);
+ HANDLE_TYPE( UINT64, UInt64, uint64_value);
+ HANDLE_TYPE( SINT32, SInt32, int32_value);
+ HANDLE_TYPE( SINT64, SInt64, int64_value);
+ HANDLE_TYPE( FIXED32, Fixed32, uint32_value);
+ HANDLE_TYPE( FIXED64, Fixed64, uint64_value);
+ HANDLE_TYPE(SFIXED32, SFixed32, int32_value);
+ HANDLE_TYPE(SFIXED64, SFixed64, int64_value);
+ HANDLE_TYPE( FLOAT, Float, float_value);
+ HANDLE_TYPE( DOUBLE, Double, double_value);
+ HANDLE_TYPE( BOOL, Bool, bool_value);
+ HANDLE_TYPE( STRING, String, *string_value);
+ HANDLE_TYPE( BYTES, Bytes, *string_value);
+ HANDLE_TYPE( ENUM, Enum, enum_value);
+ HANDLE_TYPE( GROUP, Group, *message_value);
+#undef HANDLE_TYPE
+ case FieldDescriptor::TYPE_MESSAGE:
+ if (is_lazy) {
+ target = lazymessage_value->InternalWriteMessageToArray(
+ number, deterministic, target);
+ } else {
+ target = WireFormatLite::InternalWriteMessageToArray(
+ number, *message_value, deterministic, target);
+ }
+ break;
+ }
+ }
+ return target;
+}
+
+uint8*
+ExtensionSet::Extension::InternalSerializeMessageSetItemWithCachedSizesToArray(
+ int number, bool deterministic, uint8* target) const {
+ if (type != WireFormatLite::TYPE_MESSAGE || is_repeated) {
+ // Not a valid MessageSet extension, but serialize it the normal way.
+ GOOGLE_LOG(WARNING) << "Invalid message set extension.";
+ return InternalSerializeFieldWithCachedSizesToArray(number, deterministic,
+ target);
+ }
+
+ if (is_cleared) return target;
+
+ // Start group.
+ target = io::CodedOutputStream::WriteTagToArray(
+ WireFormatLite::kMessageSetItemStartTag, target);
+ // Write type ID.
+ target = WireFormatLite::WriteUInt32ToArray(
+ WireFormatLite::kMessageSetTypeIdNumber, number, target);
+ // Write message.
+ if (is_lazy) {
+ target = lazymessage_value->WriteMessageToArray(
+ WireFormatLite::kMessageSetMessageNumber, target);
+ } else {
+ target = WireFormatLite::WriteMessageToArray(
+ WireFormatLite::kMessageSetMessageNumber, *message_value, target);
+ }
+ // End group.
+ target = io::CodedOutputStream::WriteTagToArray(
+ WireFormatLite::kMessageSetItemEndTag, target);
+ return target;
+}
+
+
+bool ExtensionSet::ParseFieldMaybeLazily(
+ int wire_type, int field_number, io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ MessageSetFieldSkipper* field_skipper) {
+ return ParseField(WireFormatLite::MakeTag(
+ field_number, static_cast<WireFormatLite::WireType>(wire_type)),
+ input, extension_finder, field_skipper);
+}
+
+bool ExtensionSet::ParseMessageSet(io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ MessageSetFieldSkipper* field_skipper) {
+ while (true) {
+ const uint32 tag = input->ReadTag();
+ switch (tag) {
+ case 0:
+ return true;
+ case WireFormatLite::kMessageSetItemStartTag:
+ if (!ParseMessageSetItem(input, extension_finder, field_skipper)) {
+ return false;
+ }
+ break;
+ default:
+ if (!ParseField(tag, input, extension_finder, field_skipper)) {
+ return false;
+ }
+ break;
+ }
+ }
+}
+
+bool ExtensionSet::ParseMessageSet(io::CodedInputStream* input,
+ const MessageLite* containing_type) {
+ MessageSetFieldSkipper skipper(NULL);
+ GeneratedExtensionFinder finder(containing_type);
+ return ParseMessageSet(input, &finder, &skipper);
+}
+
+bool ExtensionSet::ParseMessageSetItem(io::CodedInputStream* input,
+ ExtensionFinder* extension_finder,
+ MessageSetFieldSkipper* field_skipper) {
+ // TODO(kenton): It would be nice to share code between this and
+ // WireFormatLite::ParseAndMergeMessageSetItem(), but I think the
+ // differences would be hard to factor out.
+
+ // This method parses a group which should contain two fields:
+ // required int32 type_id = 2;
+ // required data message = 3;
+
+ uint32 last_type_id = 0;
+
+ // If we see message data before the type_id, we'll append it to this so
+ // we can parse it later.
+ string message_data;
+
+ while (true) {
+ const uint32 tag = input->ReadTag();
+ if (tag == 0) return false;
+
+ switch (tag) {
+ case WireFormatLite::kMessageSetTypeIdTag: {
+ uint32 type_id;
+ if (!input->ReadVarint32(&type_id)) return false;
+ last_type_id = type_id;
+
+ if (!message_data.empty()) {
+ // We saw some message data before the type_id. Have to parse it
+ // now.
+ io::CodedInputStream sub_input(
+ reinterpret_cast<const uint8*>(message_data.data()),
+ message_data.size());
+ if (!ParseFieldMaybeLazily(WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ last_type_id, &sub_input,
+ extension_finder, field_skipper)) {
+ return false;
+ }
+ message_data.clear();
+ }
+
+ break;
+ }
+
+ case WireFormatLite::kMessageSetMessageTag: {
+ if (last_type_id == 0) {
+ // We haven't seen a type_id yet. Append this data to message_data.
+ string temp;
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ if (!input->ReadString(&temp, length)) return false;
+ io::StringOutputStream output_stream(&message_data);
+ io::CodedOutputStream coded_output(&output_stream);
+ coded_output.WriteVarint32(length);
+ coded_output.WriteString(temp);
+ } else {
+ // Already saw type_id, so we can parse this directly.
+ if (!ParseFieldMaybeLazily(WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ last_type_id, input,
+ extension_finder, field_skipper)) {
+ return false;
+ }
+ }
+
+ break;
+ }
+
+ case WireFormatLite::kMessageSetItemEndTag: {
+ return true;
+ }
+
+ default: {
+ if (!field_skipper->SkipField(input, tag)) return false;
+ }
+ }
+ }
+}
+
+void ExtensionSet::Extension::SerializeMessageSetItemWithCachedSizes(
+ int number,
+ io::CodedOutputStream* output) const {
+ if (type != WireFormatLite::TYPE_MESSAGE || is_repeated) {
+ // Not a valid MessageSet extension, but serialize it the normal way.
+ SerializeFieldWithCachedSizes(number, output);
+ return;
+ }
+
+ if (is_cleared) return;
+
+ // Start group.
+ output->WriteTag(WireFormatLite::kMessageSetItemStartTag);
+
+ // Write type ID.
+ WireFormatLite::WriteUInt32(WireFormatLite::kMessageSetTypeIdNumber,
+ number,
+ output);
+ // Write message.
+ if (is_lazy) {
+ lazymessage_value->WriteMessage(
+ WireFormatLite::kMessageSetMessageNumber, output);
+ } else {
+ WireFormatLite::WriteMessageMaybeToArray(
+ WireFormatLite::kMessageSetMessageNumber,
+ *message_value,
+ output);
+ }
+
+ // End group.
+ output->WriteTag(WireFormatLite::kMessageSetItemEndTag);
+}
+
+int ExtensionSet::Extension::MessageSetItemByteSize(int number) const {
+ if (type != WireFormatLite::TYPE_MESSAGE || is_repeated) {
+ // Not a valid MessageSet extension, but compute the byte size for it the
+ // normal way.
+ return ByteSize(number);
+ }
+
+ if (is_cleared) return 0;
+
+ int our_size = WireFormatLite::kMessageSetItemTagsSize;
+
+ // type_id
+ our_size += io::CodedOutputStream::VarintSize32(number);
+
+ // message
+ int message_size = 0;
+ if (is_lazy) {
+ message_size = lazymessage_value->ByteSize();
+ } else {
+ message_size = message_value->ByteSize();
+ }
+
+ our_size += io::CodedOutputStream::VarintSize32(message_size);
+ our_size += message_size;
+
+ return our_size;
+}
+
+void ExtensionSet::SerializeMessageSetWithCachedSizes(
+ io::CodedOutputStream* output) const {
+ for (ExtensionMap::const_iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ iter->second.SerializeMessageSetItemWithCachedSizes(iter->first, output);
+ }
+}
+
+int ExtensionSet::MessageSetByteSize() const {
+ int total_size = 0;
+
+ for (ExtensionMap::const_iterator iter = extensions_.begin();
+ iter != extensions_.end(); ++iter) {
+ total_size += iter->second.MessageSetItemByteSize(iter->first);
+ }
+
+ return total_size;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/extension_set_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set_unittest.cc
new file mode 100644
index 0000000000..688afedbef
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/extension_set_unittest.cc
@@ -0,0 +1,1275 @@
+// 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.
+
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_mset.pb.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+
+namespace protobuf {
+namespace internal {
+namespace {
+
+// This test closely mirrors google/protobuf/compiler/cpp/unittest.cc
+// except that it uses extensions rather than regular fields.
+
+TEST(ExtensionSetTest, Defaults) {
+ // Check that all default values are set correctly in the initial message.
+ unittest::TestAllExtensions message;
+
+ TestUtil::ExpectExtensionsClear(message);
+
+ // Messages should return pointers to default instances until first use.
+ // (This is not checked by ExpectClear() since it is not actually true after
+ // the fields have been set and then cleared.)
+ EXPECT_EQ(&unittest::OptionalGroup_extension::default_instance(),
+ &message.GetExtension(unittest::optionalgroup_extension));
+ EXPECT_EQ(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &message.GetExtension(unittest::optional_nested_message_extension));
+ EXPECT_EQ(&unittest::ForeignMessage::default_instance(),
+ &message.GetExtension(
+ unittest::optional_foreign_message_extension));
+ EXPECT_EQ(&unittest_import::ImportMessage::default_instance(),
+ &message.GetExtension(unittest::optional_import_message_extension));
+}
+
+TEST(ExtensionSetTest, Accessors) {
+ // Set every field to a unique value then go back and check all those
+ // values.
+ unittest::TestAllExtensions message;
+
+ TestUtil::SetAllExtensions(&message);
+ TestUtil::ExpectAllExtensionsSet(message);
+
+ TestUtil::ModifyRepeatedExtensions(&message);
+ TestUtil::ExpectRepeatedExtensionsModified(message);
+}
+
+TEST(ExtensionSetTest, Clear) {
+ // Set every field to a unique value, clear the message, then check that
+ // it is cleared.
+ unittest::TestAllExtensions message;
+
+ TestUtil::SetAllExtensions(&message);
+ message.Clear();
+ TestUtil::ExpectExtensionsClear(message);
+
+ // Unlike with the defaults test, we do NOT expect that requesting embedded
+ // messages will return a pointer to the default instance. Instead, they
+ // should return the objects that were created when mutable_blah() was
+ // called.
+ EXPECT_NE(&unittest::OptionalGroup_extension::default_instance(),
+ &message.GetExtension(unittest::optionalgroup_extension));
+ EXPECT_NE(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &message.GetExtension(unittest::optional_nested_message_extension));
+ EXPECT_NE(&unittest::ForeignMessage::default_instance(),
+ &message.GetExtension(
+ unittest::optional_foreign_message_extension));
+ EXPECT_NE(&unittest_import::ImportMessage::default_instance(),
+ &message.GetExtension(unittest::optional_import_message_extension));
+
+ // Make sure setting stuff again after clearing works. (This takes slightly
+ // different code paths since the objects are reused.)
+ TestUtil::SetAllExtensions(&message);
+ TestUtil::ExpectAllExtensionsSet(message);
+}
+
+TEST(ExtensionSetTest, ClearOneField) {
+ // Set every field to a unique value, then clear one value and insure that
+ // only that one value is cleared.
+ unittest::TestAllExtensions message;
+
+ TestUtil::SetAllExtensions(&message);
+ int64 original_value =
+ message.GetExtension(unittest::optional_int64_extension);
+
+ // Clear the field and make sure it shows up as cleared.
+ message.ClearExtension(unittest::optional_int64_extension);
+ EXPECT_FALSE(message.HasExtension(unittest::optional_int64_extension));
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_int64_extension));
+
+ // Other adjacent fields should not be cleared.
+ EXPECT_TRUE(message.HasExtension(unittest::optional_int32_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_uint32_extension));
+
+ // Make sure if we set it again, then all fields are set.
+ message.SetExtension(unittest::optional_int64_extension, original_value);
+ TestUtil::ExpectAllExtensionsSet(message);
+}
+
+TEST(ExtensionSetTest, SetAllocatedExtension) {
+ unittest::TestAllExtensions message;
+ EXPECT_FALSE(message.HasExtension(
+ unittest::optional_foreign_message_extension));
+ // Add a extension using SetAllocatedExtension
+ unittest::ForeignMessage* foreign_message = new unittest::ForeignMessage();
+ message.SetAllocatedExtension(unittest::optional_foreign_message_extension,
+ foreign_message);
+ EXPECT_TRUE(message.HasExtension(
+ unittest::optional_foreign_message_extension));
+ EXPECT_EQ(foreign_message,
+ message.MutableExtension(
+ unittest::optional_foreign_message_extension));
+ EXPECT_EQ(foreign_message,
+ &message.GetExtension(
+ unittest::optional_foreign_message_extension));
+
+ // SetAllocatedExtension should delete the previously existing extension.
+ // (We reply on unittest to check memory leaks for this case)
+ message.SetAllocatedExtension(unittest::optional_foreign_message_extension,
+ new unittest::ForeignMessage());
+
+ // SetAllocatedExtension with a NULL parameter is equivalent to ClearExtenion.
+ message.SetAllocatedExtension(unittest::optional_foreign_message_extension,
+ NULL);
+ EXPECT_FALSE(message.HasExtension(
+ unittest::optional_foreign_message_extension));
+}
+
+TEST(ExtensionSetTest, ReleaseExtension) {
+ proto2_wireformat_unittest::TestMessageSet message;
+ EXPECT_FALSE(message.HasExtension(
+ unittest::TestMessageSetExtension1::message_set_extension));
+ // Add a extension using SetAllocatedExtension
+ unittest::TestMessageSetExtension1* extension =
+ new unittest::TestMessageSetExtension1();
+ message.SetAllocatedExtension(
+ unittest::TestMessageSetExtension1::message_set_extension,
+ extension);
+ EXPECT_TRUE(message.HasExtension(
+ unittest::TestMessageSetExtension1::message_set_extension));
+ // Release the extension using ReleaseExtension
+ unittest::TestMessageSetExtension1* released_extension =
+ message.ReleaseExtension(
+ unittest::TestMessageSetExtension1::message_set_extension);
+ EXPECT_EQ(extension, released_extension);
+ EXPECT_FALSE(message.HasExtension(
+ unittest::TestMessageSetExtension1::message_set_extension));
+ // ReleaseExtension will return the underlying object even after
+ // ClearExtension is called.
+ message.SetAllocatedExtension(
+ unittest::TestMessageSetExtension1::message_set_extension,
+ extension);
+ message.ClearExtension(
+ unittest::TestMessageSetExtension1::message_set_extension);
+ released_extension = message.ReleaseExtension(
+ unittest::TestMessageSetExtension1::message_set_extension);
+ EXPECT_TRUE(released_extension != NULL);
+ delete released_extension;
+}
+
+TEST(ExtensionSetTest, ArenaUnsafeArenaSetAllocatedAndRelease) {
+ ::google::protobuf::Arena arena;
+ unittest::TestAllExtensions* message =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena);
+ unittest::ForeignMessage extension;
+ message->UnsafeArenaSetAllocatedExtension(
+ unittest::optional_foreign_message_extension,
+ &extension);
+ // No copy when set.
+ unittest::ForeignMessage* mutable_extension =
+ message->MutableExtension(unittest::optional_foreign_message_extension);
+ EXPECT_EQ(&extension, mutable_extension);
+ // No copy when unsafe released.
+ unittest::ForeignMessage* released_extension =
+ message->UnsafeArenaReleaseExtension(
+ unittest::optional_foreign_message_extension);
+ EXPECT_EQ(&extension, released_extension);
+ EXPECT_FALSE(message->HasExtension(
+ unittest::optional_foreign_message_extension));
+ // Set the ownership back and let the destructors run. It should not take
+ // ownership, so this should not crash.
+ message->UnsafeArenaSetAllocatedExtension(
+ unittest::optional_foreign_message_extension,
+ &extension);
+}
+
+TEST(ExtensionSetTest, UnsafeArenaSetAllocatedAndRelease) {
+ unittest::TestAllExtensions message;
+ unittest::ForeignMessage* extension = new unittest::ForeignMessage();
+ message.UnsafeArenaSetAllocatedExtension(
+ unittest::optional_foreign_message_extension,
+ extension);
+ // No copy when set.
+ unittest::ForeignMessage* mutable_extension =
+ message.MutableExtension(unittest::optional_foreign_message_extension);
+ EXPECT_EQ(extension, mutable_extension);
+ // No copy when unsafe released.
+ unittest::ForeignMessage* released_extension =
+ message.UnsafeArenaReleaseExtension(
+ unittest::optional_foreign_message_extension);
+ EXPECT_EQ(extension, released_extension);
+ EXPECT_FALSE(message.HasExtension(
+ unittest::optional_foreign_message_extension));
+ // Set the ownership back and let the destructors run. It should take
+ // ownership, so this should not leak.
+ message.UnsafeArenaSetAllocatedExtension(
+ unittest::optional_foreign_message_extension,
+ extension);
+}
+
+TEST(ExtensionSetTest, ArenaUnsafeArenaReleaseOfHeapAlloc) {
+ ::google::protobuf::Arena arena;
+ unittest::TestAllExtensions* message =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena);
+ unittest::ForeignMessage* extension = new unittest::ForeignMessage;
+ message->SetAllocatedExtension(
+ unittest::optional_foreign_message_extension,
+ extension);
+ // The arena should maintain ownership of the heap allocated proto because we
+ // used UnsafeArenaReleaseExtension. The leak checker will ensure this.
+ unittest::ForeignMessage* released_extension =
+ message->UnsafeArenaReleaseExtension(
+ unittest::optional_foreign_message_extension);
+ EXPECT_EQ(extension, released_extension);
+ EXPECT_FALSE(message->HasExtension(
+ unittest::optional_foreign_message_extension));
+}
+
+
+TEST(ExtensionSetTest, CopyFrom) {
+ unittest::TestAllExtensions message1, message2;
+
+ TestUtil::SetAllExtensions(&message1);
+ message2.CopyFrom(message1);
+ TestUtil::ExpectAllExtensionsSet(message2);
+ message2.CopyFrom(message1); // exercise copy when fields already exist
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(ExtensioSetTest, CopyFromPacked) {
+ unittest::TestPackedExtensions message1, message2;
+
+ TestUtil::SetPackedExtensions(&message1);
+ message2.CopyFrom(message1);
+ TestUtil::ExpectPackedExtensionsSet(message2);
+ message2.CopyFrom(message1); // exercise copy when fields already exist
+ TestUtil::ExpectPackedExtensionsSet(message2);
+}
+
+TEST(ExtensionSetTest, CopyFromUpcasted) {
+ unittest::TestAllExtensions message1, message2;
+ const Message& upcasted_message = message1;
+
+ TestUtil::SetAllExtensions(&message1);
+ message2.CopyFrom(upcasted_message);
+ TestUtil::ExpectAllExtensionsSet(message2);
+ // exercise copy when fields already exist
+ message2.CopyFrom(upcasted_message);
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(ExtensionSetTest, SwapWithEmpty) {
+ unittest::TestAllExtensions message1, message2;
+ TestUtil::SetAllExtensions(&message1);
+
+ TestUtil::ExpectAllExtensionsSet(message1);
+ TestUtil::ExpectExtensionsClear(message2);
+ message1.Swap(&message2);
+ TestUtil::ExpectAllExtensionsSet(message2);
+ TestUtil::ExpectExtensionsClear(message1);
+}
+
+TEST(ExtensionSetTest, SwapWithSelf) {
+ unittest::TestAllExtensions message;
+ TestUtil::SetAllExtensions(&message);
+
+ TestUtil::ExpectAllExtensionsSet(message);
+ message.Swap(&message);
+ TestUtil::ExpectAllExtensionsSet(message);
+}
+
+TEST(ExtensionSetTest, SwapExtension) {
+ unittest::TestAllExtensions message1;
+ unittest::TestAllExtensions message2;
+
+ TestUtil::SetAllExtensions(&message1);
+ vector<const FieldDescriptor*> fields;
+
+ // Swap empty fields.
+ const Reflection* reflection = message1.GetReflection();
+ reflection->SwapFields(&message1, &message2, fields);
+ TestUtil::ExpectAllExtensionsSet(message1);
+ TestUtil::ExpectExtensionsClear(message2);
+
+ // Swap two extensions.
+ fields.push_back(
+ reflection->FindKnownExtensionByNumber(12));
+ fields.push_back(
+ reflection->FindKnownExtensionByNumber(25));
+ reflection->SwapFields(&message1, &message2, fields);
+
+ EXPECT_TRUE(message1.HasExtension(unittest::optional_int32_extension));
+ EXPECT_FALSE(message1.HasExtension(unittest::optional_double_extension));
+ EXPECT_FALSE(message1.HasExtension(unittest::optional_cord_extension));
+
+ EXPECT_FALSE(message2.HasExtension(unittest::optional_int32_extension));
+ EXPECT_TRUE(message2.HasExtension(unittest::optional_double_extension));
+ EXPECT_TRUE(message2.HasExtension(unittest::optional_cord_extension));
+}
+
+TEST(ExtensionSetTest, SwapExtensionWithEmpty) {
+ unittest::TestAllExtensions message1;
+ unittest::TestAllExtensions message2;
+ unittest::TestAllExtensions message3;
+
+ TestUtil::SetAllExtensions(&message3);
+
+ const Reflection* reflection = message3.GetReflection();
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message3, &fields);
+
+ reflection->SwapFields(&message1, &message2, fields);
+
+ TestUtil::ExpectExtensionsClear(message1);
+ TestUtil::ExpectExtensionsClear(message2);
+}
+
+TEST(ExtensionSetTest, SwapExtensionBothFull) {
+ unittest::TestAllExtensions message1;
+ unittest::TestAllExtensions message2;
+
+ TestUtil::SetAllExtensions(&message1);
+ TestUtil::SetAllExtensions(&message2);
+
+ const Reflection* reflection = message1.GetReflection();
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message1, &fields);
+
+ reflection->SwapFields(&message1, &message2, fields);
+
+ TestUtil::ExpectAllExtensionsSet(message1);
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(ExtensionSetTest, ArenaSetAllExtension) {
+ ::google::protobuf::Arena arena1;
+ unittest::TestAllExtensions* message1 =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena1);
+ TestUtil::SetAllExtensions(message1);
+ TestUtil::ExpectAllExtensionsSet(*message1);
+}
+
+TEST(ExtensionSetTest, ArenaCopyConstructor) {
+ ::google::protobuf::Arena arena1;
+ unittest::TestAllExtensions* message1 =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena1);
+ TestUtil::SetAllExtensions(message1);
+ unittest::TestAllExtensions message2(*message1);
+ arena1.Reset();
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(ExtensionSetTest, ArenaMergeFrom) {
+ ::google::protobuf::Arena arena1;
+ unittest::TestAllExtensions* message1 =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena1);
+ TestUtil::SetAllExtensions(message1);
+ unittest::TestAllExtensions message2;
+ message2.MergeFrom(*message1);
+ arena1.Reset();
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(ExtensionSetTest, ArenaSetAllocatedMessageAndRelease) {
+ ::google::protobuf::Arena arena;
+ unittest::TestAllExtensions* message =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena);
+ EXPECT_FALSE(message->HasExtension(
+ unittest::optional_foreign_message_extension));
+ // Add a extension using SetAllocatedExtension
+ unittest::ForeignMessage* foreign_message = new unittest::ForeignMessage();
+ message->SetAllocatedExtension(unittest::optional_foreign_message_extension,
+ foreign_message);
+ // foreign_message is now owned by the arena.
+ EXPECT_EQ(foreign_message,
+ message->MutableExtension(
+ unittest::optional_foreign_message_extension));
+
+ // Underlying message is copied, and returned.
+ unittest::ForeignMessage* released_message = message->ReleaseExtension(
+ unittest::optional_foreign_message_extension);
+ delete released_message;
+ EXPECT_FALSE(message->HasExtension(
+ unittest::optional_foreign_message_extension));
+}
+
+TEST(ExtensionSetTest, SwapExtensionBothFullWithArena) {
+ ::google::protobuf::Arena arena1;
+ google::protobuf::scoped_ptr<google::protobuf::Arena> arena2(new ::google::protobuf::Arena());
+
+ unittest::TestAllExtensions* message1 =
+ Arena::CreateMessage<unittest::TestAllExtensions>(&arena1);
+ unittest::TestAllExtensions* message2 =
+ Arena::CreateMessage<unittest::TestAllExtensions>(arena2.get());
+
+ TestUtil::SetAllExtensions(message1);
+ TestUtil::SetAllExtensions(message2);
+ message1->SetExtension(unittest::optional_int32_extension, 1);
+ message2->SetExtension(unittest::optional_int32_extension, 2);
+ message1->Swap(message2);
+ EXPECT_EQ(2, message1->GetExtension(unittest::optional_int32_extension));
+ EXPECT_EQ(1, message2->GetExtension(unittest::optional_int32_extension));
+ // Re-set the original values so ExpectAllExtensionsSet is happy.
+ message1->SetExtension(unittest::optional_int32_extension, 101);
+ message2->SetExtension(unittest::optional_int32_extension, 101);
+ TestUtil::ExpectAllExtensionsSet(*message1);
+ TestUtil::ExpectAllExtensionsSet(*message2);
+ arena2.reset(NULL);
+ TestUtil::ExpectAllExtensionsSet(*message1);
+ // Test corner cases, when one is empty and other is not.
+ ::google::protobuf::Arena arena3, arena4;
+
+ unittest::TestAllExtensions* message3 =
+ Arena::CreateMessage<unittest::TestAllExtensions>(&arena3);
+ unittest::TestAllExtensions* message4 =
+ Arena::CreateMessage<unittest::TestAllExtensions>(&arena4);
+ TestUtil::SetAllExtensions(message3);
+ message3->Swap(message4);
+ arena3.Reset();
+ TestUtil::ExpectAllExtensionsSet(*message4);
+}
+
+TEST(ExtensionSetTest, SwapFieldsOfExtensionBothFullWithArena) {
+ google::protobuf::Arena arena1;
+ google::protobuf::Arena* arena2 = new ::google::protobuf::Arena();
+
+ unittest::TestAllExtensions* message1 =
+ Arena::CreateMessage<unittest::TestAllExtensions>(&arena1);
+ unittest::TestAllExtensions* message2 =
+ Arena::CreateMessage<unittest::TestAllExtensions>(arena2);
+
+ TestUtil::SetAllExtensions(message1);
+ TestUtil::SetAllExtensions(message2);
+
+ const Reflection* reflection = message1->GetReflection();
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(*message1, &fields);
+ reflection->SwapFields(message1, message2, fields);
+ TestUtil::ExpectAllExtensionsSet(*message1);
+ TestUtil::ExpectAllExtensionsSet(*message2);
+ delete arena2;
+ TestUtil::ExpectAllExtensionsSet(*message1);
+}
+
+TEST(ExtensionSetTest, SwapExtensionWithSelf) {
+ unittest::TestAllExtensions message1;
+
+ TestUtil::SetAllExtensions(&message1);
+
+ vector<const FieldDescriptor*> fields;
+ const Reflection* reflection = message1.GetReflection();
+ reflection->ListFields(message1, &fields);
+ reflection->SwapFields(&message1, &message1, fields);
+
+ TestUtil::ExpectAllExtensionsSet(message1);
+}
+
+TEST(ExtensionSetTest, SerializationToArray) {
+ // Serialize as TestAllExtensions and parse as TestAllTypes to insure wire
+ // compatibility of extensions.
+ //
+ // This checks serialization to a flat array by explicitly reserving space in
+ // the string and calling the generated message's
+ // SerializeWithCachedSizesToArray.
+ unittest::TestAllExtensions source;
+ unittest::TestAllTypes destination;
+ TestUtil::SetAllExtensions(&source);
+ int size = source.ByteSize();
+ string data;
+ data.resize(size);
+ uint8* target = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = source.SerializeWithCachedSizesToArray(target);
+ EXPECT_EQ(size, end - target);
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::ExpectAllFieldsSet(destination);
+}
+
+TEST(ExtensionSetTest, SerializationToStream) {
+ // Serialize as TestAllExtensions and parse as TestAllTypes to insure wire
+ // compatibility of extensions.
+ //
+ // This checks serialization to an output stream by creating an array output
+ // stream that can only buffer 1 byte at a time - this prevents the message
+ // from ever jumping to the fast path, ensuring that serialization happens via
+ // the CodedOutputStream.
+ unittest::TestAllExtensions source;
+ unittest::TestAllTypes destination;
+ TestUtil::SetAllExtensions(&source);
+ int size = source.ByteSize();
+ string data;
+ data.resize(size);
+ {
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ source.SerializeWithCachedSizes(&output_stream);
+ ASSERT_FALSE(output_stream.HadError());
+ }
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::ExpectAllFieldsSet(destination);
+}
+
+TEST(ExtensionSetTest, PackedSerializationToArray) {
+ // Serialize as TestPackedExtensions and parse as TestPackedTypes to insure
+ // wire compatibility of extensions.
+ //
+ // This checks serialization to a flat array by explicitly reserving space in
+ // the string and calling the generated message's
+ // SerializeWithCachedSizesToArray.
+ unittest::TestPackedExtensions source;
+ unittest::TestPackedTypes destination;
+ TestUtil::SetPackedExtensions(&source);
+ int size = source.ByteSize();
+ string data;
+ data.resize(size);
+ uint8* target = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = source.SerializeWithCachedSizesToArray(target);
+ EXPECT_EQ(size, end - target);
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::ExpectPackedFieldsSet(destination);
+}
+
+TEST(ExtensionSetTest, PackedSerializationToStream) {
+ // Serialize as TestPackedExtensions and parse as TestPackedTypes to insure
+ // wire compatibility of extensions.
+ //
+ // This checks serialization to an output stream by creating an array output
+ // stream that can only buffer 1 byte at a time - this prevents the message
+ // from ever jumping to the fast path, ensuring that serialization happens via
+ // the CodedOutputStream.
+ unittest::TestPackedExtensions source;
+ unittest::TestPackedTypes destination;
+ TestUtil::SetPackedExtensions(&source);
+ int size = source.ByteSize();
+ string data;
+ data.resize(size);
+ {
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ source.SerializeWithCachedSizes(&output_stream);
+ ASSERT_FALSE(output_stream.HadError());
+ }
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::ExpectPackedFieldsSet(destination);
+}
+
+TEST(ExtensionSetTest, Parsing) {
+ // Serialize as TestAllTypes and parse as TestAllExtensions.
+ unittest::TestAllTypes source;
+ unittest::TestAllExtensions destination;
+ string data;
+
+ TestUtil::SetAllFields(&source);
+ source.SerializeToString(&data);
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::SetOneofFields(&destination);
+ TestUtil::ExpectAllExtensionsSet(destination);
+}
+
+TEST(ExtensionSetTest, PackedParsing) {
+ // Serialize as TestPackedTypes and parse as TestPackedExtensions.
+ unittest::TestPackedTypes source;
+ unittest::TestPackedExtensions destination;
+ string data;
+
+ TestUtil::SetPackedFields(&source);
+ source.SerializeToString(&data);
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::ExpectPackedExtensionsSet(destination);
+}
+
+TEST(ExtensionSetTest, PackedToUnpackedParsing) {
+ unittest::TestPackedTypes source;
+ unittest::TestUnpackedExtensions destination;
+ string data;
+
+ TestUtil::SetPackedFields(&source);
+ source.SerializeToString(&data);
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::ExpectUnpackedExtensionsSet(destination);
+
+ // Reserialize
+ unittest::TestUnpackedTypes unpacked;
+ TestUtil::SetUnpackedFields(&unpacked);
+ EXPECT_TRUE(unpacked.SerializeAsString() == destination.SerializeAsString());
+
+ // Make sure we can add extensions.
+ destination.AddExtension(unittest::unpacked_int32_extension, 1);
+ destination.AddExtension(unittest::unpacked_enum_extension,
+ protobuf_unittest::FOREIGN_BAR);
+}
+
+TEST(ExtensionSetTest, UnpackedToPackedParsing) {
+ unittest::TestUnpackedTypes source;
+ unittest::TestPackedExtensions destination;
+ string data;
+
+ TestUtil::SetUnpackedFields(&source);
+ source.SerializeToString(&data);
+ EXPECT_TRUE(destination.ParseFromString(data));
+ TestUtil::ExpectPackedExtensionsSet(destination);
+
+ // Reserialize
+ unittest::TestPackedTypes packed;
+ TestUtil::SetPackedFields(&packed);
+ EXPECT_TRUE(packed.SerializeAsString() == destination.SerializeAsString());
+
+ // Make sure we can add extensions.
+ destination.AddExtension(unittest::packed_int32_extension, 1);
+ destination.AddExtension(unittest::packed_enum_extension,
+ protobuf_unittest::FOREIGN_BAR);
+}
+
+TEST(ExtensionSetTest, IsInitialized) {
+ // Test that IsInitialized() returns false if required fields in nested
+ // extensions are missing.
+ unittest::TestAllExtensions message;
+
+ EXPECT_TRUE(message.IsInitialized());
+
+ message.MutableExtension(unittest::TestRequired::single);
+ EXPECT_FALSE(message.IsInitialized());
+
+ message.MutableExtension(unittest::TestRequired::single)->set_a(1);
+ EXPECT_FALSE(message.IsInitialized());
+ message.MutableExtension(unittest::TestRequired::single)->set_b(2);
+ EXPECT_FALSE(message.IsInitialized());
+ message.MutableExtension(unittest::TestRequired::single)->set_c(3);
+ EXPECT_TRUE(message.IsInitialized());
+
+ message.AddExtension(unittest::TestRequired::multi);
+ EXPECT_FALSE(message.IsInitialized());
+
+ message.MutableExtension(unittest::TestRequired::multi, 0)->set_a(1);
+ EXPECT_FALSE(message.IsInitialized());
+ message.MutableExtension(unittest::TestRequired::multi, 0)->set_b(2);
+ EXPECT_FALSE(message.IsInitialized());
+ message.MutableExtension(unittest::TestRequired::multi, 0)->set_c(3);
+ EXPECT_TRUE(message.IsInitialized());
+}
+
+TEST(ExtensionSetTest, MutableString) {
+ // Test the mutable string accessors.
+ unittest::TestAllExtensions message;
+
+ message.MutableExtension(unittest::optional_string_extension)->assign("foo");
+ EXPECT_TRUE(message.HasExtension(unittest::optional_string_extension));
+ EXPECT_EQ("foo", message.GetExtension(unittest::optional_string_extension));
+
+ message.AddExtension(unittest::repeated_string_extension)->assign("bar");
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_string_extension));
+ EXPECT_EQ("bar",
+ message.GetExtension(unittest::repeated_string_extension, 0));
+}
+
+TEST(ExtensionSetTest, SpaceUsedExcludingSelf) {
+ // Scalar primitive extensions should increase the extension set size by a
+ // minimum of the size of the primitive type.
+#define TEST_SCALAR_EXTENSIONS_SPACE_USED(type, value) \
+ do { \
+ unittest::TestAllExtensions message; \
+ const int base_size = message.SpaceUsed(); \
+ message.SetExtension(unittest::optional_##type##_extension, value); \
+ int min_expected_size = base_size + \
+ sizeof(message.GetExtension(unittest::optional_##type##_extension)); \
+ EXPECT_LE(min_expected_size, message.SpaceUsed()); \
+ } while (0)
+
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(int32 , 101);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(int64 , 102);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(uint32 , 103);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(uint64 , 104);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(sint32 , 105);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(sint64 , 106);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(fixed32 , 107);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(fixed64 , 108);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(sfixed32, 109);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(sfixed64, 110);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(float , 111);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(double , 112);
+ TEST_SCALAR_EXTENSIONS_SPACE_USED(bool , true);
+#undef TEST_SCALAR_EXTENSIONS_SPACE_USED
+ {
+ unittest::TestAllExtensions message;
+ const int base_size = message.SpaceUsed();
+ message.SetExtension(unittest::optional_nested_enum_extension,
+ unittest::TestAllTypes::FOO);
+ int min_expected_size = base_size +
+ sizeof(message.GetExtension(unittest::optional_nested_enum_extension));
+ EXPECT_LE(min_expected_size, message.SpaceUsed());
+ }
+ {
+ // Strings may cause extra allocations depending on their length; ensure
+ // that gets included as well.
+ unittest::TestAllExtensions message;
+ const int base_size = message.SpaceUsed();
+ const string s("this is a fairly large string that will cause some "
+ "allocation in order to store it in the extension");
+ message.SetExtension(unittest::optional_string_extension, s);
+ int min_expected_size = base_size + s.length();
+ EXPECT_LE(min_expected_size, message.SpaceUsed());
+ }
+ {
+ // Messages also have additional allocation that need to be counted.
+ unittest::TestAllExtensions message;
+ const int base_size = message.SpaceUsed();
+ unittest::ForeignMessage foreign;
+ foreign.set_c(42);
+ message.MutableExtension(unittest::optional_foreign_message_extension)->
+ CopyFrom(foreign);
+ int min_expected_size = base_size + foreign.SpaceUsed();
+ EXPECT_LE(min_expected_size, message.SpaceUsed());
+ }
+
+ // Repeated primitive extensions will increase space used by at least a
+ // RepeatedField<T>, and will cause additional allocations when the array
+ // gets too big for the initial space.
+ // This macro:
+ // - Adds a value to the repeated extension, then clears it, establishing
+ // the base size.
+ // - Adds a small number of values, testing that it doesn't increase the
+ // SpaceUsed()
+ // - Adds a large number of values (requiring allocation in the repeated
+ // field), and ensures that that allocation is included in SpaceUsed()
+#define TEST_REPEATED_EXTENSIONS_SPACE_USED(type, cpptype, value) \
+ do { \
+ unittest::TestAllExtensions message; \
+ const int base_size = message.SpaceUsed(); \
+ int min_expected_size = sizeof(RepeatedField<cpptype>) + base_size; \
+ message.AddExtension(unittest::repeated_##type##_extension, value); \
+ message.ClearExtension(unittest::repeated_##type##_extension); \
+ const int empty_repeated_field_size = message.SpaceUsed(); \
+ EXPECT_LE(min_expected_size, empty_repeated_field_size) << #type; \
+ message.AddExtension(unittest::repeated_##type##_extension, value); \
+ message.AddExtension(unittest::repeated_##type##_extension, value); \
+ EXPECT_EQ(empty_repeated_field_size, message.SpaceUsed()) << #type; \
+ message.ClearExtension(unittest::repeated_##type##_extension); \
+ for (int i = 0; i < 16; ++i) { \
+ message.AddExtension(unittest::repeated_##type##_extension, value); \
+ } \
+ int expected_size = sizeof(cpptype) * (16 - \
+ kMinRepeatedFieldAllocationSize) + empty_repeated_field_size; \
+ EXPECT_EQ(expected_size, message.SpaceUsed()) << #type; \
+ } while (0)
+
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(int32 , int32 , 101);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(int64 , int64 , 102);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(uint32 , uint32, 103);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(uint64 , uint64, 104);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(sint32 , int32 , 105);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(sint64 , int64 , 106);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(fixed32 , uint32, 107);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(fixed64 , uint64, 108);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(sfixed32, int32 , 109);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(sfixed64, int64 , 110);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(float , float , 111);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(double , double, 112);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(bool , bool , true);
+ TEST_REPEATED_EXTENSIONS_SPACE_USED(nested_enum, int,
+ unittest::TestAllTypes::FOO);
+#undef TEST_REPEATED_EXTENSIONS_SPACE_USED
+ // Repeated strings
+ {
+ unittest::TestAllExtensions message;
+ const int base_size = message.SpaceUsed();
+ int min_expected_size = sizeof(RepeatedPtrField<string>) + base_size;
+ const string value(256, 'x');
+ // Once items are allocated, they may stick around even when cleared so
+ // without the hardcore memory management accessors there isn't a notion of
+ // the empty repeated field memory usage as there is with primitive types.
+ for (int i = 0; i < 16; ++i) {
+ message.AddExtension(unittest::repeated_string_extension, value);
+ }
+ min_expected_size += (sizeof(value) + value.size()) *
+ (16 - kMinRepeatedFieldAllocationSize);
+ EXPECT_LE(min_expected_size, message.SpaceUsed());
+ }
+ // Repeated messages
+ {
+ unittest::TestAllExtensions message;
+ const int base_size = message.SpaceUsed();
+ int min_expected_size = sizeof(RepeatedPtrField<unittest::ForeignMessage>) +
+ base_size;
+ unittest::ForeignMessage prototype;
+ prototype.set_c(2);
+ for (int i = 0; i < 16; ++i) {
+ message.AddExtension(unittest::repeated_foreign_message_extension)->
+ CopyFrom(prototype);
+ }
+ min_expected_size +=
+ (16 - kMinRepeatedFieldAllocationSize) * prototype.SpaceUsed();
+ EXPECT_LE(min_expected_size, message.SpaceUsed());
+ }
+}
+
+// N.B.: We do not test range-based for here because we remain C++03 compatible.
+template<typename T, typename M, typename ID>
+inline T SumAllExtensions(const M& message, ID extension, T zero) {
+ T sum = zero;
+ typename RepeatedField<T>::const_iterator iter =
+ message.GetRepeatedExtension(extension).begin();
+ typename RepeatedField<T>::const_iterator end =
+ message.GetRepeatedExtension(extension).end();
+ for (; iter != end; ++iter) {
+ sum += *iter;
+ }
+ return sum;
+}
+
+template<typename T, typename M, typename ID>
+inline void IncAllExtensions(M* message, ID extension,
+ T val) {
+ typename RepeatedField<T>::iterator iter =
+ message->MutableRepeatedExtension(extension)->begin();
+ typename RepeatedField<T>::iterator end =
+ message->MutableRepeatedExtension(extension)->end();
+ for (; iter != end; ++iter) {
+ *iter += val;
+ }
+}
+
+TEST(ExtensionSetTest, RepeatedFields) {
+ unittest::TestAllExtensions message;
+
+ // Test empty repeated-field case (b/12926163)
+ ASSERT_EQ(0, message.GetRepeatedExtension(
+ unittest::repeated_int32_extension).size());
+ ASSERT_EQ(0, message.GetRepeatedExtension(
+ unittest::repeated_nested_enum_extension).size());
+ ASSERT_EQ(0, message.GetRepeatedExtension(
+ unittest::repeated_string_extension).size());
+ ASSERT_EQ(0, message.GetRepeatedExtension(
+ unittest::repeated_nested_message_extension).size());
+
+ unittest::TestAllTypes::NestedMessage nested_message;
+ nested_message.set_bb(42);
+ unittest::TestAllTypes::NestedEnum nested_enum =
+ unittest::TestAllTypes::NestedEnum_MIN;
+
+ for (int i = 0; i < 10; ++i) {
+ message.AddExtension(unittest::repeated_int32_extension, 1);
+ message.AddExtension(unittest::repeated_int64_extension, 2);
+ message.AddExtension(unittest::repeated_uint32_extension, 3);
+ message.AddExtension(unittest::repeated_uint64_extension, 4);
+ message.AddExtension(unittest::repeated_sint32_extension, 5);
+ message.AddExtension(unittest::repeated_sint64_extension, 6);
+ message.AddExtension(unittest::repeated_fixed32_extension, 7);
+ message.AddExtension(unittest::repeated_fixed64_extension, 8);
+ message.AddExtension(unittest::repeated_sfixed32_extension, 7);
+ message.AddExtension(unittest::repeated_sfixed64_extension, 8);
+ message.AddExtension(unittest::repeated_float_extension, 9.0);
+ message.AddExtension(unittest::repeated_double_extension, 10.0);
+ message.AddExtension(unittest::repeated_bool_extension, true);
+ message.AddExtension(unittest::repeated_nested_enum_extension, nested_enum);
+ message.AddExtension(unittest::repeated_string_extension,
+ ::std::string("test"));
+ message.AddExtension(unittest::repeated_bytes_extension,
+ ::std::string("test\xFF"));
+ message.AddExtension(
+ unittest::repeated_nested_message_extension)->CopyFrom(nested_message);
+ message.AddExtension(unittest::repeated_nested_enum_extension,
+ nested_enum);
+ }
+
+ ASSERT_EQ(10, SumAllExtensions<int32>(
+ message, unittest::repeated_int32_extension, 0));
+ IncAllExtensions<int32>(
+ &message, unittest::repeated_int32_extension, 1);
+ ASSERT_EQ(20, SumAllExtensions<int32>(
+ message, unittest::repeated_int32_extension, 0));
+
+ ASSERT_EQ(20, SumAllExtensions<int64>(
+ message, unittest::repeated_int64_extension, 0));
+ IncAllExtensions<int64>(
+ &message, unittest::repeated_int64_extension, 1);
+ ASSERT_EQ(30, SumAllExtensions<int64>(
+ message, unittest::repeated_int64_extension, 0));
+
+ ASSERT_EQ(30, SumAllExtensions<uint32>(
+ message, unittest::repeated_uint32_extension, 0));
+ IncAllExtensions<uint32>(
+ &message, unittest::repeated_uint32_extension, 1);
+ ASSERT_EQ(40, SumAllExtensions<uint32>(
+ message, unittest::repeated_uint32_extension, 0));
+
+ ASSERT_EQ(40, SumAllExtensions<uint64>(
+ message, unittest::repeated_uint64_extension, 0));
+ IncAllExtensions<uint64>(
+ &message, unittest::repeated_uint64_extension, 1);
+ ASSERT_EQ(50, SumAllExtensions<uint64>(
+ message, unittest::repeated_uint64_extension, 0));
+
+ ASSERT_EQ(50, SumAllExtensions<int32>(
+ message, unittest::repeated_sint32_extension, 0));
+ IncAllExtensions<int32>(
+ &message, unittest::repeated_sint32_extension, 1);
+ ASSERT_EQ(60, SumAllExtensions<int32>(
+ message, unittest::repeated_sint32_extension, 0));
+
+ ASSERT_EQ(60, SumAllExtensions<int64>(
+ message, unittest::repeated_sint64_extension, 0));
+ IncAllExtensions<int64>(
+ &message, unittest::repeated_sint64_extension, 1);
+ ASSERT_EQ(70, SumAllExtensions<int64>(
+ message, unittest::repeated_sint64_extension, 0));
+
+ ASSERT_EQ(70, SumAllExtensions<uint32>(
+ message, unittest::repeated_fixed32_extension, 0));
+ IncAllExtensions<uint32>(
+ &message, unittest::repeated_fixed32_extension, 1);
+ ASSERT_EQ(80, SumAllExtensions<uint32>(
+ message, unittest::repeated_fixed32_extension, 0));
+
+ ASSERT_EQ(80, SumAllExtensions<uint64>(
+ message, unittest::repeated_fixed64_extension, 0));
+ IncAllExtensions<uint64>(
+ &message, unittest::repeated_fixed64_extension, 1);
+ ASSERT_EQ(90, SumAllExtensions<uint64>(
+ message, unittest::repeated_fixed64_extension, 0));
+
+ // Usually, floating-point arithmetic cannot be trusted to be exact, so it is
+ // a Bad Idea to assert equality in a test like this. However, we're dealing
+ // with integers with a small number of significant mantissa bits, so we
+ // should actually have exact precision here.
+ ASSERT_EQ(90, SumAllExtensions<float>(
+ message, unittest::repeated_float_extension, 0));
+ IncAllExtensions<float>(
+ &message, unittest::repeated_float_extension, 1);
+ ASSERT_EQ(100, SumAllExtensions<float>(
+ message, unittest::repeated_float_extension, 0));
+
+ ASSERT_EQ(100, SumAllExtensions<double>(
+ message, unittest::repeated_double_extension, 0));
+ IncAllExtensions<double>(
+ &message, unittest::repeated_double_extension, 1);
+ ASSERT_EQ(110, SumAllExtensions<double>(
+ message, unittest::repeated_double_extension, 0));
+
+ RepeatedPtrField< ::std::string>::iterator string_iter;
+ RepeatedPtrField< ::std::string>::iterator string_end;
+ for (string_iter = message.MutableRepeatedExtension(
+ unittest::repeated_string_extension)->begin(),
+ string_end = message.MutableRepeatedExtension(
+ unittest::repeated_string_extension)->end();
+ string_iter != string_end; ++string_iter) {
+ *string_iter += "test";
+ }
+ RepeatedPtrField< ::std::string>::const_iterator string_const_iter;
+ RepeatedPtrField< ::std::string>::const_iterator string_const_end;
+ for (string_const_iter = message.GetRepeatedExtension(
+ unittest::repeated_string_extension).begin(),
+ string_const_end = message.GetRepeatedExtension(
+ unittest::repeated_string_extension).end();
+ string_iter != string_end; ++string_iter) {
+ ASSERT_TRUE(*string_iter == "testtest");
+ }
+
+ RepeatedField<unittest::TestAllTypes_NestedEnum>::iterator enum_iter;
+ RepeatedField<unittest::TestAllTypes_NestedEnum>::iterator enum_end;
+ for (enum_iter = message.MutableRepeatedExtension(
+ unittest::repeated_nested_enum_extension)->begin(),
+ enum_end = message.MutableRepeatedExtension(
+ unittest::repeated_nested_enum_extension)->end();
+ enum_iter != enum_end; ++enum_iter) {
+ *enum_iter = unittest::TestAllTypes::NestedEnum_MAX;
+ }
+ RepeatedField<unittest::TestAllTypes_NestedEnum>::const_iterator
+ enum_const_iter;
+ RepeatedField<unittest::TestAllTypes_NestedEnum>::const_iterator
+ enum_const_end;
+ for (enum_const_iter = message.GetRepeatedExtension(
+ unittest::repeated_nested_enum_extension).begin(),
+ enum_const_end = message.GetRepeatedExtension(
+ unittest::repeated_nested_enum_extension).end();
+ enum_iter != enum_end; ++enum_iter) {
+ ASSERT_EQ(*enum_const_iter, unittest::TestAllTypes::NestedEnum_MAX);
+ }
+
+ RepeatedPtrField<unittest::TestAllTypes_NestedMessage>::iterator
+ msg_iter;
+ RepeatedPtrField<unittest::TestAllTypes_NestedMessage>::iterator
+ msg_end;
+ for (msg_iter = message.MutableRepeatedExtension(
+ unittest::repeated_nested_message_extension)->begin(),
+ msg_end = message.MutableRepeatedExtension(
+ unittest::repeated_nested_message_extension)->end();
+ msg_iter != msg_end; ++msg_iter) {
+ msg_iter->set_bb(1234);
+ }
+ RepeatedPtrField<unittest::TestAllTypes_NestedMessage>::
+ const_iterator msg_const_iter;
+ RepeatedPtrField<unittest::TestAllTypes_NestedMessage>::
+ const_iterator msg_const_end;
+ for (msg_const_iter = message.GetRepeatedExtension(
+ unittest::repeated_nested_message_extension).begin(),
+ msg_const_end = message.GetRepeatedExtension(
+ unittest::repeated_nested_message_extension).end();
+ msg_const_iter != msg_const_end; ++msg_const_iter) {
+ ASSERT_EQ(msg_const_iter->bb(), 1234);
+ }
+
+ // Test range-based for as well, but only if compiled as C++11.
+#if __cplusplus >= 201103L
+ // Test one primitive field.
+ for (auto& x : *message.MutableRepeatedExtension(
+ unittest::repeated_int32_extension)) {
+ x = 4321;
+ }
+ for (const auto& x : message.GetRepeatedExtension(
+ unittest::repeated_int32_extension)) {
+ ASSERT_EQ(x, 4321);
+ }
+ // Test one string field.
+ for (auto& x : *message.MutableRepeatedExtension(
+ unittest::repeated_string_extension)) {
+ x = "test_range_based_for";
+ }
+ for (const auto& x : message.GetRepeatedExtension(
+ unittest::repeated_string_extension)) {
+ ASSERT_TRUE(x == "test_range_based_for");
+ }
+ // Test one message field.
+ for (auto& x : *message.MutableRepeatedExtension(
+ unittest::repeated_nested_message_extension)) {
+ x.set_bb(4321);
+ }
+ for (const auto& x : *message.MutableRepeatedExtension(
+ unittest::repeated_nested_message_extension)) {
+ ASSERT_EQ(x.bb(), 4321);
+ }
+#endif
+}
+
+// From b/12926163
+TEST(ExtensionSetTest, AbsentExtension) {
+ unittest::TestAllExtensions message;
+ message.MutableRepeatedExtension(unittest::repeated_nested_message_extension)
+ ->Add()->set_bb(123);
+ ASSERT_EQ(1, message.ExtensionSize(
+ unittest::repeated_nested_message_extension));
+ EXPECT_EQ(
+ 123, message.GetExtension(
+ unittest::repeated_nested_message_extension, 0).bb());
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+
+TEST(ExtensionSetTest, InvalidEnumDeath) {
+ unittest::TestAllExtensions message;
+ EXPECT_DEBUG_DEATH(
+ message.SetExtension(unittest::optional_foreign_enum_extension,
+ static_cast<unittest::ForeignEnum>(53)),
+ "IsValid");
+}
+
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST(ExtensionSetTest, DynamicExtensions) {
+ // Test adding a dynamic extension to a compiled-in message object.
+
+ FileDescriptorProto dynamic_proto;
+ dynamic_proto.set_name("dynamic_extensions_test.proto");
+ dynamic_proto.add_dependency(
+ unittest::TestAllExtensions::descriptor()->file()->name());
+ dynamic_proto.set_package("dynamic_extensions");
+
+ // Copy the fields and nested types from TestDynamicExtensions into our new
+ // proto, converting the fields into extensions.
+ const Descriptor* template_descriptor =
+ unittest::TestDynamicExtensions::descriptor();
+ DescriptorProto template_descriptor_proto;
+ template_descriptor->CopyTo(&template_descriptor_proto);
+ dynamic_proto.mutable_message_type()->MergeFrom(
+ template_descriptor_proto.nested_type());
+ dynamic_proto.mutable_enum_type()->MergeFrom(
+ template_descriptor_proto.enum_type());
+ dynamic_proto.mutable_extension()->MergeFrom(
+ template_descriptor_proto.field());
+
+ // For each extension that we added...
+ for (int i = 0; i < dynamic_proto.extension_size(); i++) {
+ // Set its extendee to TestAllExtensions.
+ FieldDescriptorProto* extension = dynamic_proto.mutable_extension(i);
+ extension->set_extendee(
+ unittest::TestAllExtensions::descriptor()->full_name());
+
+ // If the field refers to one of the types nested in TestDynamicExtensions,
+ // make it refer to the type in our dynamic proto instead.
+ string prefix = "." + template_descriptor->full_name() + ".";
+ if (extension->has_type_name()) {
+ string* type_name = extension->mutable_type_name();
+ if (HasPrefixString(*type_name, prefix)) {
+ type_name->replace(0, prefix.size(), ".dynamic_extensions.");
+ }
+ }
+ }
+
+ // Now build the file, using the generated pool as an underlay.
+ DescriptorPool dynamic_pool(DescriptorPool::generated_pool());
+ const FileDescriptor* file = dynamic_pool.BuildFile(dynamic_proto);
+ ASSERT_TRUE(file != NULL);
+ DynamicMessageFactory dynamic_factory(&dynamic_pool);
+ dynamic_factory.SetDelegateToGeneratedFactory(true);
+
+ // Construct a message that we can parse with the extensions we defined.
+ // Since the extensions were based off of the fields of TestDynamicExtensions,
+ // we can use that message to create this test message.
+ string data;
+ {
+ unittest::TestDynamicExtensions message;
+ message.set_scalar_extension(123);
+ message.set_enum_extension(unittest::FOREIGN_BAR);
+ message.set_dynamic_enum_extension(
+ unittest::TestDynamicExtensions::DYNAMIC_BAZ);
+ message.mutable_message_extension()->set_c(456);
+ message.mutable_dynamic_message_extension()->set_dynamic_field(789);
+ message.add_repeated_extension("foo");
+ message.add_repeated_extension("bar");
+ message.add_packed_extension(12);
+ message.add_packed_extension(-34);
+ message.add_packed_extension(56);
+ message.add_packed_extension(-78);
+
+ // Also add some unknown fields.
+
+ // An unknown enum value (for a known field).
+ message.mutable_unknown_fields()->AddVarint(
+ unittest::TestDynamicExtensions::kDynamicEnumExtensionFieldNumber,
+ 12345);
+ // A regular unknown field.
+ message.mutable_unknown_fields()->AddLengthDelimited(54321, "unknown");
+
+ message.SerializeToString(&data);
+ }
+
+ // Now we can parse this using our dynamic extension definitions...
+ unittest::TestAllExtensions message;
+ {
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ input.SetExtensionRegistry(&dynamic_pool, &dynamic_factory);
+ ASSERT_TRUE(message.ParseFromCodedStream(&input));
+ ASSERT_TRUE(input.ConsumedEntireMessage());
+ }
+
+ // Can we print it?
+ EXPECT_EQ(
+ "[dynamic_extensions.scalar_extension]: 123\n"
+ "[dynamic_extensions.enum_extension]: FOREIGN_BAR\n"
+ "[dynamic_extensions.dynamic_enum_extension]: DYNAMIC_BAZ\n"
+ "[dynamic_extensions.message_extension] {\n"
+ " c: 456\n"
+ "}\n"
+ "[dynamic_extensions.dynamic_message_extension] {\n"
+ " dynamic_field: 789\n"
+ "}\n"
+ "[dynamic_extensions.repeated_extension]: \"foo\"\n"
+ "[dynamic_extensions.repeated_extension]: \"bar\"\n"
+ "[dynamic_extensions.packed_extension]: 12\n"
+ "[dynamic_extensions.packed_extension]: -34\n"
+ "[dynamic_extensions.packed_extension]: 56\n"
+ "[dynamic_extensions.packed_extension]: -78\n"
+ "2002: 12345\n"
+ "54321: \"unknown\"\n",
+ message.DebugString());
+
+ // Can we serialize it?
+ // (Don't use EXPECT_EQ because we don't want to dump raw binary data to the
+ // terminal on failure.)
+ EXPECT_TRUE(message.SerializeAsString() == data);
+
+ // What if we parse using the reflection-based parser?
+ {
+ unittest::TestAllExtensions message2;
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ input.SetExtensionRegistry(&dynamic_pool, &dynamic_factory);
+ ASSERT_TRUE(WireFormat::ParseAndMergePartial(&input, &message2));
+ ASSERT_TRUE(input.ConsumedEntireMessage());
+ EXPECT_EQ(message.DebugString(), message2.DebugString());
+ }
+
+ // Are the embedded generated types actually using the generated objects?
+ {
+ const FieldDescriptor* message_extension =
+ file->FindExtensionByName("message_extension");
+ ASSERT_TRUE(message_extension != NULL);
+ const Message& sub_message =
+ message.GetReflection()->GetMessage(message, message_extension);
+ const unittest::ForeignMessage* typed_sub_message =
+#ifdef GOOGLE_PROTOBUF_NO_RTTI
+ static_cast<const unittest::ForeignMessage*>(&sub_message);
+#else
+ dynamic_cast<const unittest::ForeignMessage*>(&sub_message);
+#endif
+ ASSERT_TRUE(typed_sub_message != NULL);
+ EXPECT_EQ(456, typed_sub_message->c());
+ }
+
+ // What does GetMessage() return for the embedded dynamic type if it isn't
+ // present?
+ {
+ const FieldDescriptor* dynamic_message_extension =
+ file->FindExtensionByName("dynamic_message_extension");
+ ASSERT_TRUE(dynamic_message_extension != NULL);
+ const Message& parent = unittest::TestAllExtensions::default_instance();
+ const Message& sub_message =
+ parent.GetReflection()->GetMessage(parent, dynamic_message_extension,
+ &dynamic_factory);
+ const Message* prototype =
+ dynamic_factory.GetPrototype(dynamic_message_extension->message_type());
+ EXPECT_EQ(prototype, &sub_message);
+ }
+}
+
+} // namespace
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.cc
new file mode 100644
index 0000000000..ed05fe575b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.cc
@@ -0,0 +1,402 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/field_mask.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/field_mask.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* FieldMask_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ FieldMask_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2ffield_5fmask_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2ffield_5fmask_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2ffield_5fmask_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/field_mask.proto");
+ GOOGLE_CHECK(file != NULL);
+ FieldMask_descriptor_ = file->message_type(0);
+ static const int FieldMask_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldMask, paths_),
+ };
+ FieldMask_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ FieldMask_descriptor_,
+ FieldMask::default_instance_,
+ FieldMask_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(FieldMask),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldMask, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FieldMask, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2ffield_5fmask_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ FieldMask_descriptor_, &FieldMask::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2ffield_5fmask_2eproto() {
+ delete FieldMask::default_instance_;
+ delete FieldMask_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2ffield_5fmask_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2ffield_5fmask_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n google/protobuf/field_mask.proto\022\017goog"
+ "le.protobuf\"\032\n\tFieldMask\022\r\n\005paths\030\001 \003(\tB"
+ "Q\n\023com.google.protobufB\016FieldMaskProtoP\001"
+ "\240\001\001\242\002\003GPB\252\002\036Google.Protobuf.WellKnownTyp"
+ "esb\006proto3", 170);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/field_mask.proto", &protobuf_RegisterTypes);
+ FieldMask::default_instance_ = new FieldMask();
+ FieldMask::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2ffield_5fmask_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2ffield_5fmask_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2ffield_5fmask_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2ffield_5fmask_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2ffield_5fmask_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FieldMask::kPathsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+FieldMask::FieldMask()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.FieldMask)
+}
+
+void FieldMask::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+FieldMask::FieldMask(const FieldMask& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.FieldMask)
+}
+
+void FieldMask::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+}
+
+FieldMask::~FieldMask() {
+ // @@protoc_insertion_point(destructor:google.protobuf.FieldMask)
+ SharedDtor();
+}
+
+void FieldMask::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void FieldMask::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* FieldMask::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FieldMask_descriptor_;
+}
+
+const FieldMask& FieldMask::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2ffield_5fmask_2eproto();
+ return *default_instance_;
+}
+
+FieldMask* FieldMask::default_instance_ = NULL;
+
+FieldMask* FieldMask::New(::google::protobuf::Arena* arena) const {
+ FieldMask* n = new FieldMask;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void FieldMask::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.FieldMask)
+ paths_.Clear();
+}
+
+bool FieldMask::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.FieldMask)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // repeated string paths = 1;
+ case 1: {
+ if (tag == 10) {
+ parse_paths:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->add_paths()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->paths(this->paths_size() - 1).data(),
+ this->paths(this->paths_size() - 1).length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.FieldMask.paths"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(10)) goto parse_paths;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.FieldMask)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.FieldMask)
+ return false;
+#undef DO_
+}
+
+void FieldMask::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.FieldMask)
+ // repeated string paths = 1;
+ for (int i = 0; i < this->paths_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->paths(i).data(), this->paths(i).length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.FieldMask.paths");
+ ::google::protobuf::internal::WireFormatLite::WriteString(
+ 1, this->paths(i), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.FieldMask)
+}
+
+::google::protobuf::uint8* FieldMask::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.FieldMask)
+ // repeated string paths = 1;
+ for (int i = 0; i < this->paths_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->paths(i).data(), this->paths(i).length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.FieldMask.paths");
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteStringToArray(1, this->paths(i), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.FieldMask)
+ return target;
+}
+
+int FieldMask::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.FieldMask)
+ int total_size = 0;
+
+ // repeated string paths = 1;
+ total_size += 1 * this->paths_size();
+ for (int i = 0; i < this->paths_size(); i++) {
+ total_size += ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->paths(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void FieldMask::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.FieldMask)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const FieldMask* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const FieldMask>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.FieldMask)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.FieldMask)
+ MergeFrom(*source);
+ }
+}
+
+void FieldMask::MergeFrom(const FieldMask& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.FieldMask)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ paths_.MergeFrom(from.paths_);
+}
+
+void FieldMask::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.FieldMask)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void FieldMask::CopyFrom(const FieldMask& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.FieldMask)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool FieldMask::IsInitialized() const {
+
+ return true;
+}
+
+void FieldMask::Swap(FieldMask* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void FieldMask::InternalSwap(FieldMask* other) {
+ paths_.UnsafeArenaSwap(&other->paths_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata FieldMask::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = FieldMask_descriptor_;
+ metadata.reflection = FieldMask_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// FieldMask
+
+// repeated string paths = 1;
+int FieldMask::paths_size() const {
+ return paths_.size();
+}
+void FieldMask::clear_paths() {
+ paths_.Clear();
+}
+ const ::std::string& FieldMask::paths(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldMask.paths)
+ return paths_.Get(index);
+}
+ ::std::string* FieldMask::mutable_paths(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldMask.paths)
+ return paths_.Mutable(index);
+}
+ void FieldMask::set_paths(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldMask.paths)
+ paths_.Mutable(index)->assign(value);
+}
+ void FieldMask::set_paths(int index, const char* value) {
+ paths_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldMask.paths)
+}
+ void FieldMask::set_paths(int index, const char* value, size_t size) {
+ paths_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldMask.paths)
+}
+ ::std::string* FieldMask::add_paths() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.FieldMask.paths)
+ return paths_.Add();
+}
+ void FieldMask::add_paths(const ::std::string& value) {
+ paths_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FieldMask.paths)
+}
+ void FieldMask::add_paths(const char* value) {
+ paths_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.FieldMask.paths)
+}
+ void FieldMask::add_paths(const char* value, size_t size) {
+ paths_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.FieldMask.paths)
+}
+ const ::google::protobuf::RepeatedPtrField< ::std::string>&
+FieldMask::paths() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FieldMask.paths)
+ return paths_;
+}
+ ::google::protobuf::RepeatedPtrField< ::std::string>*
+FieldMask::mutable_paths() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FieldMask.paths)
+ return &paths_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.h
new file mode 100644
index 0000000000..7a19c4aa64
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.pb.h
@@ -0,0 +1,206 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/field_mask.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2ffield_5fmask_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2ffield_5fmask_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ffield_5fmask_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2ffield_5fmask_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2ffield_5fmask_2eproto();
+
+class FieldMask;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT FieldMask : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.FieldMask) */ {
+ public:
+ FieldMask();
+ virtual ~FieldMask();
+
+ FieldMask(const FieldMask& from);
+
+ inline FieldMask& operator=(const FieldMask& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const FieldMask& default_instance();
+
+ void Swap(FieldMask* other);
+
+ // implements Message ----------------------------------------------
+
+ inline FieldMask* New() const { return New(NULL); }
+
+ FieldMask* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const FieldMask& from);
+ void MergeFrom(const FieldMask& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(FieldMask* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // repeated string paths = 1;
+ int paths_size() const;
+ void clear_paths();
+ static const int kPathsFieldNumber = 1;
+ const ::std::string& paths(int index) const;
+ ::std::string* mutable_paths(int index);
+ void set_paths(int index, const ::std::string& value);
+ void set_paths(int index, const char* value);
+ void set_paths(int index, const char* value, size_t size);
+ ::std::string* add_paths();
+ void add_paths(const ::std::string& value);
+ void add_paths(const char* value);
+ void add_paths(const char* value, size_t size);
+ const ::google::protobuf::RepeatedPtrField< ::std::string>& paths() const;
+ ::google::protobuf::RepeatedPtrField< ::std::string>* mutable_paths();
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.FieldMask)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::RepeatedPtrField< ::std::string> paths_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ffield_5fmask_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2ffield_5fmask_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2ffield_5fmask_2eproto();
+
+ void InitAsDefaultInstance();
+ static FieldMask* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// FieldMask
+
+// repeated string paths = 1;
+inline int FieldMask::paths_size() const {
+ return paths_.size();
+}
+inline void FieldMask::clear_paths() {
+ paths_.Clear();
+}
+inline const ::std::string& FieldMask::paths(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FieldMask.paths)
+ return paths_.Get(index);
+}
+inline ::std::string* FieldMask::mutable_paths(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.FieldMask.paths)
+ return paths_.Mutable(index);
+}
+inline void FieldMask::set_paths(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.FieldMask.paths)
+ paths_.Mutable(index)->assign(value);
+}
+inline void FieldMask::set_paths(int index, const char* value) {
+ paths_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.FieldMask.paths)
+}
+inline void FieldMask::set_paths(int index, const char* value, size_t size) {
+ paths_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.FieldMask.paths)
+}
+inline ::std::string* FieldMask::add_paths() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.FieldMask.paths)
+ return paths_.Add();
+}
+inline void FieldMask::add_paths(const ::std::string& value) {
+ paths_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.FieldMask.paths)
+}
+inline void FieldMask::add_paths(const char* value) {
+ paths_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.FieldMask.paths)
+}
+inline void FieldMask::add_paths(const char* value, size_t size) {
+ paths_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.FieldMask.paths)
+}
+inline const ::google::protobuf::RepeatedPtrField< ::std::string>&
+FieldMask::paths() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.FieldMask.paths)
+ return paths_;
+}
+inline ::google::protobuf::RepeatedPtrField< ::std::string>*
+FieldMask::mutable_paths() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.FieldMask.paths)
+ return &paths_;
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2ffield_5fmask_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.proto b/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.proto
new file mode 100644
index 0000000000..c51de09a83
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/field_mask.proto
@@ -0,0 +1,246 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "FieldMaskProto";
+option java_multiple_files = true;
+option objc_class_prefix = "GPB";
+option java_generate_equals_and_hash = true;
+
+// `FieldMask` represents a set of symbolic field paths, for example:
+//
+// paths: "f.a"
+// paths: "f.b.d"
+//
+// Here `f` represents a field in some root message, `a` and `b`
+// fields in the message found in `f`, and `d` a field found in the
+// message in `f.b`.
+//
+// Field masks are used to specify a subset of fields that should be
+// returned by a get operation or modified by an update operation.
+// Field masks also have a custom JSON encoding (see below).
+//
+// # Field Masks in Projections
+//
+// When used in the context of a projection, a response message or
+// sub-message is filtered by the API to only contain those fields as
+// specified in the mask. For example, if the mask in the previous
+// example is applied to a response message as follows:
+//
+// f {
+// a : 22
+// b {
+// d : 1
+// x : 2
+// }
+// y : 13
+// }
+// z: 8
+//
+// The result will not contain specific values for fields x,y and z
+// (their value will be set to the default, and omitted in proto text
+// output):
+//
+//
+// f {
+// a : 22
+// b {
+// d : 1
+// }
+// }
+//
+// A repeated field is not allowed except at the last position of a
+// field mask.
+//
+// If a FieldMask object is not present in a get operation, the
+// operation applies to all fields (as if a FieldMask of all fields
+// had been specified).
+//
+// Note that a field mask does not necessarily apply to the
+// top-level response message. In case of a REST get operation, the
+// field mask applies directly to the response, but in case of a REST
+// list operation, the mask instead applies to each individual message
+// in the returned resource list. In case of a REST custom method,
+// other definitions may be used. Where the mask applies will be
+// clearly documented together with its declaration in the API. In
+// any case, the effect on the returned resource/resources is required
+// behavior for APIs.
+//
+// # Field Masks in Update Operations
+//
+// A field mask in update operations specifies which fields of the
+// targeted resource are going to be updated. The API is required
+// to only change the values of the fields as specified in the mask
+// and leave the others untouched. If a resource is passed in to
+// describe the updated values, the API ignores the values of all
+// fields not covered by the mask.
+//
+// If a repeated field is specified for an update operation, the existing
+// repeated values in the target resource will be overwritten by the new values.
+// Note that a repeated field is only allowed in the last position of a field
+// mask.
+//
+// If a sub-message is specified in the last position of the field mask for an
+// update operation, then the existing sub-message in the target resource is
+// overwritten. Given the target message:
+//
+// f {
+// b {
+// d : 1
+// x : 2
+// }
+// c : 1
+// }
+//
+// And an update message:
+//
+// f {
+// b {
+// d : 10
+// }
+// }
+//
+// then if the field mask is:
+//
+// paths: "f.b"
+//
+// then the result will be:
+//
+// f {
+// b {
+// d : 10
+// }
+// c : 1
+// }
+//
+// However, if the update mask was:
+//
+// paths: "f.b.d"
+//
+// then the result would be:
+//
+// f {
+// b {
+// d : 10
+// x : 2
+// }
+// c : 1
+// }
+//
+// In order to reset a field's value to the default, the field must
+// be in the mask and set to the default value in the provided resource.
+// Hence, in order to reset all fields of a resource, provide a default
+// instance of the resource and set all fields in the mask, or do
+// not provide a mask as described below.
+//
+// If a field mask is not present on update, the operation applies to
+// all fields (as if a field mask of all fields has been specified).
+// Note that in the presence of schema evolution, this may mean that
+// fields the client does not know and has therefore not filled into
+// the request will be reset to their default. If this is unwanted
+// behavior, a specific service may require a client to always specify
+// a field mask, producing an error if not.
+//
+// As with get operations, the location of the resource which
+// describes the updated values in the request message depends on the
+// operation kind. In any case, the effect of the field mask is
+// required to be honored by the API.
+//
+// ## Considerations for HTTP REST
+//
+// The HTTP kind of an update operation which uses a field mask must
+// be set to PATCH instead of PUT in order to satisfy HTTP semantics
+// (PUT must only be used for full updates).
+//
+// # JSON Encoding of Field Masks
+//
+// In JSON, a field mask is encoded as a single string where paths are
+// separated by a comma. Fields name in each path are converted
+// to/from lower-camel naming conventions.
+//
+// As an example, consider the following message declarations:
+//
+// message Profile {
+// User user = 1;
+// Photo photo = 2;
+// }
+// message User {
+// string display_name = 1;
+// string address = 2;
+// }
+//
+// In proto a field mask for `Profile` may look as such:
+//
+// mask {
+// paths: "user.display_name"
+// paths: "photo"
+// }
+//
+// In JSON, the same mask is represented as below:
+//
+// {
+// mask: "user.displayName,photo"
+// }
+//
+// # Field Masks and Oneof Fields
+//
+// Field masks treat fields in oneofs just as regular fields. Consider the
+// following message:
+//
+// message SampleMessage {
+// oneof test_oneof {
+// string name = 4;
+// SubMessage sub_message = 9;
+// }
+// }
+//
+// The field mask can be:
+//
+// mask {
+// paths: "name"
+// }
+//
+// Or:
+//
+// mask {
+// paths: "sub_message"
+// }
+//
+// Note that oneof type names ("test_oneof" in this case) cannot be used in
+// paths.
+message FieldMask {
+ // The set of field mask paths.
+ repeated string paths = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_reflection.h b/third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_reflection.h
new file mode 100644
index 0000000000..fdcdc27790
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_reflection.h
@@ -0,0 +1,88 @@
+// 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: jasonh@google.com (Jason Hsueh)
+//
+// This header is logically internal, but is made public because it is used
+// from protocol-compiler-generated code, which may reside in other components.
+// It provides reflection support for generated enums, and is included in
+// generated .pb.h files and should have minimal dependencies. The methods are
+// implemented in generated_message_reflection.cc.
+
+#ifndef GOOGLE_PROTOBUF_GENERATED_ENUM_REFLECTION_H__
+#define GOOGLE_PROTOBUF_GENERATED_ENUM_REFLECTION_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/template_util.h>
+#include <google/protobuf/generated_enum_util.h>
+
+namespace google {
+namespace protobuf {
+ class EnumDescriptor;
+} // namespace protobuf
+
+namespace protobuf {
+
+// Returns the EnumDescriptor for enum type E, which must be a
+// proto-declared enum type. Code generated by the protocol compiler
+// will include specializations of this template for each enum type declared.
+template <typename E>
+const EnumDescriptor* GetEnumDescriptor();
+
+namespace internal {
+
+// Helper for EnumType_Parse functions: try to parse the string 'name' as an
+// enum name of the given type, returning true and filling in value on success,
+// or returning false and leaving value unchanged on failure.
+LIBPROTOBUF_EXPORT bool ParseNamedEnum(const EnumDescriptor* descriptor,
+ const string& name,
+ int* value);
+
+template<typename EnumType>
+bool ParseNamedEnum(const EnumDescriptor* descriptor,
+ const string& name,
+ EnumType* value) {
+ int tmp;
+ if (!ParseNamedEnum(descriptor, name, &tmp)) return false;
+ *value = static_cast<EnumType>(tmp);
+ return true;
+}
+
+// Just a wrapper around printing the name of a value. The main point of this
+// function is not to be inlined, so that you can do this without including
+// descriptor.h.
+LIBPROTOBUF_EXPORT const string& NameOfEnum(const EnumDescriptor* descriptor, int value);
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_GENERATED_ENUM_REFLECTION_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_util.h
new file mode 100644
index 0000000000..e4242055e9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/generated_enum_util.h
@@ -0,0 +1,46 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_GENERATED_ENUM_UTIL_H__
+#define GOOGLE_PROTOBUF_GENERATED_ENUM_UTIL_H__
+
+#include <google/protobuf/stubs/template_util.h>
+
+namespace google {
+namespace protobuf {
+
+// This type trait can be used to cause templates to only match proto2 enum
+// types.
+template <typename T> struct is_proto_enum : ::google::protobuf::internal::false_type {};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_GENERATED_ENUM_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.cc b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.cc
new file mode 100644
index 0000000000..d1f7b5ca32
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.cc
@@ -0,0 +1,2319 @@
+// 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.
+
+#include <algorithm>
+#include <set>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/generated_message_reflection.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/map_field.h>
+#include <google/protobuf/repeated_field.h>
+
+
+#define GOOGLE_PROTOBUF_HAS_ONEOF
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+namespace {
+bool IsMapFieldInApi(const FieldDescriptor* field) {
+ return field->is_map();
+}
+} // anonymous namespace
+
+bool ParseNamedEnum(const EnumDescriptor* descriptor,
+ const string& name,
+ int* value) {
+ const EnumValueDescriptor* d = descriptor->FindValueByName(name);
+ if (d == NULL) return false;
+ *value = d->number();
+ return true;
+}
+
+const string& NameOfEnum(const EnumDescriptor* descriptor, int value) {
+ const EnumValueDescriptor* d = descriptor->FindValueByNumber(value);
+ return (d == NULL ? GetEmptyString() : d->name());
+}
+
+namespace {
+inline bool SupportsArenas(const Descriptor* descriptor) {
+ return descriptor->file()->options().cc_enable_arenas();
+}
+} // anonymous namespace
+
+// ===================================================================
+// Helpers for reporting usage errors (e.g. trying to use GetInt32() on
+// a string field).
+
+namespace {
+
+void ReportReflectionUsageError(
+ const Descriptor* descriptor, const FieldDescriptor* field,
+ const char* method, const char* description) {
+ GOOGLE_LOG(FATAL)
+ << "Protocol Buffer reflection usage error:\n"
+ " Method : google::protobuf::Reflection::" << method << "\n"
+ " Message type: " << descriptor->full_name() << "\n"
+ " Field : " << field->full_name() << "\n"
+ " Problem : " << description;
+}
+
+const char* cpptype_names_[FieldDescriptor::MAX_CPPTYPE + 1] = {
+ "INVALID_CPPTYPE",
+ "CPPTYPE_INT32",
+ "CPPTYPE_INT64",
+ "CPPTYPE_UINT32",
+ "CPPTYPE_UINT64",
+ "CPPTYPE_DOUBLE",
+ "CPPTYPE_FLOAT",
+ "CPPTYPE_BOOL",
+ "CPPTYPE_ENUM",
+ "CPPTYPE_STRING",
+ "CPPTYPE_MESSAGE"
+};
+
+static void ReportReflectionUsageTypeError(
+ const Descriptor* descriptor, const FieldDescriptor* field,
+ const char* method,
+ FieldDescriptor::CppType expected_type) {
+ GOOGLE_LOG(FATAL)
+ << "Protocol Buffer reflection usage error:\n"
+ " Method : google::protobuf::Reflection::" << method << "\n"
+ " Message type: " << descriptor->full_name() << "\n"
+ " Field : " << field->full_name() << "\n"
+ " Problem : Field is not the right type for this message:\n"
+ " Expected : " << cpptype_names_[expected_type] << "\n"
+ " Field type: " << cpptype_names_[field->cpp_type()];
+}
+
+static void ReportReflectionUsageEnumTypeError(
+ const Descriptor* descriptor, const FieldDescriptor* field,
+ const char* method, const EnumValueDescriptor* value) {
+ GOOGLE_LOG(FATAL)
+ << "Protocol Buffer reflection usage error:\n"
+ " Method : google::protobuf::Reflection::" << method << "\n"
+ " Message type: " << descriptor->full_name() << "\n"
+ " Field : " << field->full_name() << "\n"
+ " Problem : Enum value did not match field type:\n"
+ " Expected : " << field->enum_type()->full_name() << "\n"
+ " Actual : " << value->full_name();
+}
+
+#define USAGE_CHECK(CONDITION, METHOD, ERROR_DESCRIPTION) \
+ if (!(CONDITION)) \
+ ReportReflectionUsageError(descriptor_, field, #METHOD, ERROR_DESCRIPTION)
+#define USAGE_CHECK_EQ(A, B, METHOD, ERROR_DESCRIPTION) \
+ USAGE_CHECK((A) == (B), METHOD, ERROR_DESCRIPTION)
+#define USAGE_CHECK_NE(A, B, METHOD, ERROR_DESCRIPTION) \
+ USAGE_CHECK((A) != (B), METHOD, ERROR_DESCRIPTION)
+
+#define USAGE_CHECK_TYPE(METHOD, CPPTYPE) \
+ if (field->cpp_type() != FieldDescriptor::CPPTYPE_##CPPTYPE) \
+ ReportReflectionUsageTypeError(descriptor_, field, #METHOD, \
+ FieldDescriptor::CPPTYPE_##CPPTYPE)
+
+#define USAGE_CHECK_ENUM_VALUE(METHOD) \
+ if (value->type() != field->enum_type()) \
+ ReportReflectionUsageEnumTypeError(descriptor_, field, #METHOD, value)
+
+#define USAGE_CHECK_MESSAGE_TYPE(METHOD) \
+ USAGE_CHECK_EQ(field->containing_type(), descriptor_, \
+ METHOD, "Field does not match message type.");
+#define USAGE_CHECK_SINGULAR(METHOD) \
+ USAGE_CHECK_NE(field->label(), FieldDescriptor::LABEL_REPEATED, METHOD, \
+ "Field is repeated; the method requires a singular field.")
+#define USAGE_CHECK_REPEATED(METHOD) \
+ USAGE_CHECK_EQ(field->label(), FieldDescriptor::LABEL_REPEATED, METHOD, \
+ "Field is singular; the method requires a repeated field.")
+
+#define USAGE_CHECK_ALL(METHOD, LABEL, CPPTYPE) \
+ USAGE_CHECK_MESSAGE_TYPE(METHOD); \
+ USAGE_CHECK_##LABEL(METHOD); \
+ USAGE_CHECK_TYPE(METHOD, CPPTYPE)
+
+} // namespace
+
+// ===================================================================
+
+GeneratedMessageReflection::GeneratedMessageReflection(
+ const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ const DescriptorPool* descriptor_pool,
+ MessageFactory* factory,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset)
+ : descriptor_ (descriptor),
+ default_instance_ (default_instance),
+ offsets_ (offsets),
+ has_bits_offset_ (has_bits_offset),
+ unknown_fields_offset_(unknown_fields_offset),
+ extensions_offset_(extensions_offset),
+ arena_offset_ (arena_offset),
+ is_default_instance_offset_(is_default_instance_offset),
+ object_size_ (object_size),
+ descriptor_pool_ ((descriptor_pool == NULL) ?
+ DescriptorPool::generated_pool() :
+ descriptor_pool),
+ message_factory_ (factory) {
+}
+
+GeneratedMessageReflection::GeneratedMessageReflection(
+ const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ const void* default_oneof_instance,
+ int oneof_case_offset,
+ const DescriptorPool* descriptor_pool,
+ MessageFactory* factory,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset)
+ : descriptor_ (descriptor),
+ default_instance_ (default_instance),
+ default_oneof_instance_ (default_oneof_instance),
+ offsets_ (offsets),
+ has_bits_offset_ (has_bits_offset),
+ oneof_case_offset_(oneof_case_offset),
+ unknown_fields_offset_(unknown_fields_offset),
+ extensions_offset_(extensions_offset),
+ arena_offset_ (arena_offset),
+ is_default_instance_offset_(is_default_instance_offset),
+ object_size_ (object_size),
+ descriptor_pool_ ((descriptor_pool == NULL) ?
+ DescriptorPool::generated_pool() :
+ descriptor_pool),
+ message_factory_ (factory) {
+}
+
+GeneratedMessageReflection::~GeneratedMessageReflection() {}
+
+namespace {
+UnknownFieldSet* empty_unknown_field_set_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(empty_unknown_field_set_once_);
+
+void DeleteEmptyUnknownFieldSet() {
+ delete empty_unknown_field_set_;
+ empty_unknown_field_set_ = NULL;
+}
+
+void InitEmptyUnknownFieldSet() {
+ empty_unknown_field_set_ = new UnknownFieldSet;
+ internal::OnShutdown(&DeleteEmptyUnknownFieldSet);
+}
+
+const UnknownFieldSet& GetEmptyUnknownFieldSet() {
+ ::google::protobuf::GoogleOnceInit(&empty_unknown_field_set_once_, &InitEmptyUnknownFieldSet);
+ return *empty_unknown_field_set_;
+}
+} // namespace
+
+const UnknownFieldSet& GeneratedMessageReflection::GetUnknownFields(
+ const Message& message) const {
+ if (descriptor_->file()->syntax() == FileDescriptor::SYNTAX_PROTO3) {
+ return GetEmptyUnknownFieldSet();
+ }
+ if (unknown_fields_offset_ == kUnknownFieldSetInMetadata) {
+ return GetInternalMetadataWithArena(message).unknown_fields();
+ }
+ const void* ptr = reinterpret_cast<const uint8*>(&message) +
+ unknown_fields_offset_;
+ return *reinterpret_cast<const UnknownFieldSet*>(ptr);
+}
+
+UnknownFieldSet* GeneratedMessageReflection::MutableUnknownFields(
+ Message* message) const {
+ if (unknown_fields_offset_ == kUnknownFieldSetInMetadata) {
+ return MutableInternalMetadataWithArena(message)->
+ mutable_unknown_fields();
+ }
+ void* ptr = reinterpret_cast<uint8*>(message) + unknown_fields_offset_;
+ return reinterpret_cast<UnknownFieldSet*>(ptr);
+}
+
+int GeneratedMessageReflection::SpaceUsed(const Message& message) const {
+ // object_size_ already includes the in-memory representation of each field
+ // in the message, so we only need to account for additional memory used by
+ // the fields.
+ int total_size = object_size_;
+
+ total_size += GetUnknownFields(message).SpaceUsedExcludingSelf();
+
+ if (extensions_offset_ != -1) {
+ total_size += GetExtensionSet(message).SpaceUsedExcludingSelf();
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+
+ if (field->is_repeated()) {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case FieldDescriptor::CPPTYPE_##UPPERCASE : \
+ total_size += GetRaw<RepeatedField<LOWERCASE> >(message, field) \
+ .SpaceUsedExcludingSelf(); \
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, int);
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ total_size += GetRaw<RepeatedPtrField<string> >(message, field)
+ .SpaceUsedExcludingSelf();
+ break;
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (IsMapFieldInApi(field)) {
+ total_size +=
+ GetRaw<MapFieldBase>(message, field).SpaceUsedExcludingSelf();
+ } else {
+ // We don't know which subclass of RepeatedPtrFieldBase the type is,
+ // so we use RepeatedPtrFieldBase directly.
+ total_size +=
+ GetRaw<RepeatedPtrFieldBase>(message, field)
+ .SpaceUsedExcludingSelf<GenericTypeHandler<Message> >();
+ }
+
+ break;
+ }
+ } else {
+ if (field->containing_oneof() && !HasOneofField(message, field)) {
+ continue;
+ }
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32 :
+ case FieldDescriptor::CPPTYPE_INT64 :
+ case FieldDescriptor::CPPTYPE_UINT32:
+ case FieldDescriptor::CPPTYPE_UINT64:
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ case FieldDescriptor::CPPTYPE_FLOAT :
+ case FieldDescriptor::CPPTYPE_BOOL :
+ case FieldDescriptor::CPPTYPE_ENUM :
+ // Field is inline, so we've already counted it.
+ break;
+
+ case FieldDescriptor::CPPTYPE_STRING: {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING: {
+ // Initially, the string points to the default value stored in
+ // the prototype. Only count the string if it has been changed
+ // from the default value.
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ const string* ptr =
+ &GetField<ArenaStringPtr>(message, field).Get(default_ptr);
+
+ if (ptr != default_ptr) {
+ // string fields are represented by just a pointer, so also
+ // include sizeof(string) as well.
+ total_size += sizeof(*ptr) + StringSpaceUsedExcludingSelf(*ptr);
+ }
+ break;
+ }
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (&message == default_instance_) {
+ // For singular fields, the prototype just stores a pointer to the
+ // external type's prototype, so there is no extra memory usage.
+ } else {
+ const Message* sub_message = GetRaw<const Message*>(message, field);
+ if (sub_message != NULL) {
+ total_size += sub_message->SpaceUsed();
+ }
+ }
+ break;
+ }
+ }
+ }
+
+ return total_size;
+}
+
+void GeneratedMessageReflection::SwapField(
+ Message* message1,
+ Message* message2,
+ const FieldDescriptor* field) const {
+ if (field->is_repeated()) {
+ switch (field->cpp_type()) {
+#define SWAP_ARRAYS(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ MutableRaw<RepeatedField<TYPE> >(message1, field)->Swap( \
+ MutableRaw<RepeatedField<TYPE> >(message2, field)); \
+ break;
+
+ SWAP_ARRAYS(INT32 , int32 );
+ SWAP_ARRAYS(INT64 , int64 );
+ SWAP_ARRAYS(UINT32, uint32);
+ SWAP_ARRAYS(UINT64, uint64);
+ SWAP_ARRAYS(FLOAT , float );
+ SWAP_ARRAYS(DOUBLE, double);
+ SWAP_ARRAYS(BOOL , bool );
+ SWAP_ARRAYS(ENUM , int );
+#undef SWAP_ARRAYS
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ MutableRaw<RepeatedPtrFieldBase>(message1, field)->
+ Swap<GenericTypeHandler<string> >(
+ MutableRaw<RepeatedPtrFieldBase>(message2, field));
+ break;
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (IsMapFieldInApi(field)) {
+ MutableRaw<MapFieldBase>(message1, field)->
+ MutableRepeatedField()->
+ Swap<GenericTypeHandler<google::protobuf::Message> >(
+ MutableRaw<MapFieldBase>(message2, field)->
+ MutableRepeatedField());
+ } else {
+ MutableRaw<RepeatedPtrFieldBase>(message1, field)->
+ Swap<GenericTypeHandler<google::protobuf::Message> >(
+ MutableRaw<RepeatedPtrFieldBase>(message2, field));
+ }
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Unimplemented type: " << field->cpp_type();
+ }
+ } else {
+ switch (field->cpp_type()) {
+#define SWAP_VALUES(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ std::swap(*MutableRaw<TYPE>(message1, field), \
+ *MutableRaw<TYPE>(message2, field)); \
+ break;
+
+ SWAP_VALUES(INT32 , int32 );
+ SWAP_VALUES(INT64 , int64 );
+ SWAP_VALUES(UINT32, uint32);
+ SWAP_VALUES(UINT64, uint64);
+ SWAP_VALUES(FLOAT , float );
+ SWAP_VALUES(DOUBLE, double);
+ SWAP_VALUES(BOOL , bool );
+ SWAP_VALUES(ENUM , int );
+#undef SWAP_VALUES
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (GetArena(message1) == GetArena(message2)) {
+ std::swap(*MutableRaw<Message*>(message1, field),
+ *MutableRaw<Message*>(message2, field));
+ } else {
+ Message** sub_msg1 = MutableRaw<Message*>(message1, field);
+ Message** sub_msg2 = MutableRaw<Message*>(message2, field);
+ if (*sub_msg1 == NULL && *sub_msg2 == NULL) break;
+ if (*sub_msg1 && *sub_msg2) {
+ (*sub_msg1)->GetReflection()->Swap(*sub_msg1, *sub_msg2);
+ break;
+ }
+ if (*sub_msg1 == NULL) {
+ *sub_msg1 = (*sub_msg2)->New(message1->GetArena());
+ (*sub_msg1)->CopyFrom(**sub_msg2);
+ ClearField(message2, field);
+ } else {
+ *sub_msg2 = (*sub_msg1)->New(message2->GetArena());
+ (*sub_msg2)->CopyFrom(**sub_msg1);
+ ClearField(message1, field);
+ }
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ {
+ Arena* arena1 = GetArena(message1);
+ Arena* arena2 = GetArena(message2);
+ ArenaStringPtr* string1 =
+ MutableRaw<ArenaStringPtr>(message1, field);
+ ArenaStringPtr* string2 =
+ MutableRaw<ArenaStringPtr>(message2, field);
+ if (arena1 == arena2) {
+ string1->Swap(string2);
+ } else {
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ const string temp = string1->Get(default_ptr);
+ string1->Set(default_ptr, string2->Get(default_ptr), arena1);
+ string2->Set(default_ptr, temp, arena2);
+ }
+ }
+ break;
+ }
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Unimplemented type: " << field->cpp_type();
+ }
+ }
+}
+
+void GeneratedMessageReflection::SwapOneofField(
+ Message* message1,
+ Message* message2,
+ const OneofDescriptor* oneof_descriptor) const {
+ uint32 oneof_case1 = GetOneofCase(*message1, oneof_descriptor);
+ uint32 oneof_case2 = GetOneofCase(*message2, oneof_descriptor);
+
+ int32 temp_int32;
+ int64 temp_int64;
+ uint32 temp_uint32;
+ uint64 temp_uint64;
+ float temp_float;
+ double temp_double;
+ bool temp_bool;
+ int temp_int;
+ Message* temp_message = NULL;
+ string temp_string;
+
+ // Stores message1's oneof field to a temp variable.
+ const FieldDescriptor* field1 = NULL;
+ if (oneof_case1 > 0) {
+ field1 = descriptor_->FindFieldByNumber(oneof_case1);
+ //oneof_descriptor->field(oneof_case1);
+ switch (field1->cpp_type()) {
+#define GET_TEMP_VALUE(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ temp_##TYPE = GetField<TYPE>(*message1, field1); \
+ break;
+
+ GET_TEMP_VALUE(INT32 , int32 );
+ GET_TEMP_VALUE(INT64 , int64 );
+ GET_TEMP_VALUE(UINT32, uint32);
+ GET_TEMP_VALUE(UINT64, uint64);
+ GET_TEMP_VALUE(FLOAT , float );
+ GET_TEMP_VALUE(DOUBLE, double);
+ GET_TEMP_VALUE(BOOL , bool );
+ GET_TEMP_VALUE(ENUM , int );
+#undef GET_TEMP_VALUE
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ temp_message = ReleaseMessage(message1, field1);
+ break;
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ temp_string = GetString(*message1, field1);
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Unimplemented type: " << field1->cpp_type();
+ }
+ }
+
+ // Sets message1's oneof field from the message2's oneof field.
+ if (oneof_case2 > 0) {
+ const FieldDescriptor* field2 =
+ descriptor_->FindFieldByNumber(oneof_case2);
+ switch (field2->cpp_type()) {
+#define SET_ONEOF_VALUE1(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ SetField<TYPE>(message1, field2, GetField<TYPE>(*message2, field2)); \
+ break;
+
+ SET_ONEOF_VALUE1(INT32 , int32 );
+ SET_ONEOF_VALUE1(INT64 , int64 );
+ SET_ONEOF_VALUE1(UINT32, uint32);
+ SET_ONEOF_VALUE1(UINT64, uint64);
+ SET_ONEOF_VALUE1(FLOAT , float );
+ SET_ONEOF_VALUE1(DOUBLE, double);
+ SET_ONEOF_VALUE1(BOOL , bool );
+ SET_ONEOF_VALUE1(ENUM , int );
+#undef SET_ONEOF_VALUE1
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ SetAllocatedMessage(message1,
+ ReleaseMessage(message2, field2),
+ field2);
+ break;
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ SetString(message1, field2, GetString(*message2, field2));
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Unimplemented type: " << field2->cpp_type();
+ }
+ } else {
+ ClearOneof(message1, oneof_descriptor);
+ }
+
+ // Sets message2's oneof field from the temp variable.
+ if (oneof_case1 > 0) {
+ switch (field1->cpp_type()) {
+#define SET_ONEOF_VALUE2(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ SetField<TYPE>(message2, field1, temp_##TYPE); \
+ break;
+
+ SET_ONEOF_VALUE2(INT32 , int32 );
+ SET_ONEOF_VALUE2(INT64 , int64 );
+ SET_ONEOF_VALUE2(UINT32, uint32);
+ SET_ONEOF_VALUE2(UINT64, uint64);
+ SET_ONEOF_VALUE2(FLOAT , float );
+ SET_ONEOF_VALUE2(DOUBLE, double);
+ SET_ONEOF_VALUE2(BOOL , bool );
+ SET_ONEOF_VALUE2(ENUM , int );
+#undef SET_ONEOF_VALUE2
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ SetAllocatedMessage(message2, temp_message, field1);
+ break;
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ SetString(message2, field1, temp_string);
+ break;
+
+ default:
+ GOOGLE_LOG(FATAL) << "Unimplemented type: " << field1->cpp_type();
+ }
+ } else {
+ ClearOneof(message2, oneof_descriptor);
+ }
+}
+
+void GeneratedMessageReflection::Swap(
+ Message* message1,
+ Message* message2) const {
+ if (message1 == message2) return;
+
+ // TODO(kenton): Other Reflection methods should probably check this too.
+ GOOGLE_CHECK_EQ(message1->GetReflection(), this)
+ << "First argument to Swap() (of type \""
+ << message1->GetDescriptor()->full_name()
+ << "\") is not compatible with this reflection object (which is for type \""
+ << descriptor_->full_name()
+ << "\"). Note that the exact same class is required; not just the same "
+ "descriptor.";
+ GOOGLE_CHECK_EQ(message2->GetReflection(), this)
+ << "Second argument to Swap() (of type \""
+ << message2->GetDescriptor()->full_name()
+ << "\") is not compatible with this reflection object (which is for type \""
+ << descriptor_->full_name()
+ << "\"). Note that the exact same class is required; not just the same "
+ "descriptor.";
+
+ // Check that both messages are in the same arena (or both on the heap). We
+ // need to copy all data if not, due to ownership semantics.
+ if (GetArena(message1) != GetArena(message2)) {
+ // Slow copy path.
+ // Use our arena as temp space, if available.
+ Message* temp = message1->New(GetArena(message1));
+ temp->MergeFrom(*message1);
+ message1->CopyFrom(*message2);
+ message2->CopyFrom(*temp);
+ if (GetArena(message1) == NULL) {
+ delete temp;
+ }
+ return;
+ }
+
+ if (has_bits_offset_ != -1) {
+ uint32* has_bits1 = MutableHasBits(message1);
+ uint32* has_bits2 = MutableHasBits(message2);
+ int has_bits_size = (descriptor_->field_count() + 31) / 32;
+
+ for (int i = 0; i < has_bits_size; i++) {
+ std::swap(has_bits1[i], has_bits2[i]);
+ }
+ }
+
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (!field->containing_oneof()) {
+ SwapField(message1, message2, field);
+ }
+ }
+
+ for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
+ SwapOneofField(message1, message2, descriptor_->oneof_decl(i));
+ }
+
+ if (extensions_offset_ != -1) {
+ MutableExtensionSet(message1)->Swap(MutableExtensionSet(message2));
+ }
+
+ MutableUnknownFields(message1)->Swap(MutableUnknownFields(message2));
+}
+
+void GeneratedMessageReflection::SwapFields(
+ Message* message1,
+ Message* message2,
+ const vector<const FieldDescriptor*>& fields) const {
+ if (message1 == message2) return;
+
+ // TODO(kenton): Other Reflection methods should probably check this too.
+ GOOGLE_CHECK_EQ(message1->GetReflection(), this)
+ << "First argument to SwapFields() (of type \""
+ << message1->GetDescriptor()->full_name()
+ << "\") is not compatible with this reflection object (which is for type \""
+ << descriptor_->full_name()
+ << "\"). Note that the exact same class is required; not just the same "
+ "descriptor.";
+ GOOGLE_CHECK_EQ(message2->GetReflection(), this)
+ << "Second argument to SwapFields() (of type \""
+ << message2->GetDescriptor()->full_name()
+ << "\") is not compatible with this reflection object (which is for type \""
+ << descriptor_->full_name()
+ << "\"). Note that the exact same class is required; not just the same "
+ "descriptor.";
+
+ std::set<int> swapped_oneof;
+
+ for (int i = 0; i < fields.size(); i++) {
+ const FieldDescriptor* field = fields[i];
+ if (field->is_extension()) {
+ MutableExtensionSet(message1)->SwapExtension(
+ MutableExtensionSet(message2),
+ field->number());
+ } else {
+ if (field->containing_oneof()) {
+ int oneof_index = field->containing_oneof()->index();
+ // Only swap the oneof field once.
+ if (swapped_oneof.find(oneof_index) != swapped_oneof.end()) {
+ continue;
+ }
+ swapped_oneof.insert(oneof_index);
+ SwapOneofField(message1, message2, field->containing_oneof());
+ } else {
+ // Swap has bit.
+ SwapBit(message1, message2, field);
+ // Swap field.
+ SwapField(message1, message2, field);
+ }
+ }
+ }
+}
+
+// -------------------------------------------------------------------
+
+bool GeneratedMessageReflection::HasField(const Message& message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK_MESSAGE_TYPE(HasField);
+ USAGE_CHECK_SINGULAR(HasField);
+
+ if (field->is_extension()) {
+ return GetExtensionSet(message).Has(field->number());
+ } else {
+ if (field->containing_oneof()) {
+ return HasOneofField(message, field);
+ } else {
+ return HasBit(message, field);
+ }
+ }
+}
+
+int GeneratedMessageReflection::FieldSize(const Message& message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK_MESSAGE_TYPE(FieldSize);
+ USAGE_CHECK_REPEATED(FieldSize);
+
+ if (field->is_extension()) {
+ return GetExtensionSet(message).ExtensionSize(field->number());
+ } else {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case FieldDescriptor::CPPTYPE_##UPPERCASE : \
+ return GetRaw<RepeatedField<LOWERCASE> >(message, field).size()
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, int);
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (IsMapFieldInApi(field)) {
+ return GetRaw<MapFieldBase>(message, field).GetRepeatedField().size();
+ } else {
+ return GetRaw<RepeatedPtrFieldBase>(message, field).size();
+ }
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return 0;
+ }
+}
+
+void GeneratedMessageReflection::ClearField(
+ Message* message, const FieldDescriptor* field) const {
+ USAGE_CHECK_MESSAGE_TYPE(ClearField);
+
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->ClearExtension(field->number());
+ } else if (!field->is_repeated()) {
+ if (field->containing_oneof()) {
+ ClearOneofField(message, field);
+ return;
+ }
+
+ if (HasBit(*message, field)) {
+ ClearBit(message, field);
+
+ // We need to set the field back to its default value.
+ switch (field->cpp_type()) {
+#define CLEAR_TYPE(CPPTYPE, TYPE) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ *MutableRaw<TYPE>(message, field) = \
+ field->default_value_##TYPE(); \
+ break;
+
+ CLEAR_TYPE(INT32 , int32 );
+ CLEAR_TYPE(INT64 , int64 );
+ CLEAR_TYPE(UINT32, uint32);
+ CLEAR_TYPE(UINT64, uint64);
+ CLEAR_TYPE(FLOAT , float );
+ CLEAR_TYPE(DOUBLE, double);
+ CLEAR_TYPE(BOOL , bool );
+#undef CLEAR_TYPE
+
+ case FieldDescriptor::CPPTYPE_ENUM:
+ *MutableRaw<int>(message, field) =
+ field->default_value_enum()->number();
+ break;
+
+ case FieldDescriptor::CPPTYPE_STRING: {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING: {
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ MutableRaw<ArenaStringPtr>(message, field)->Destroy(default_ptr,
+ GetArena(message));
+ break;
+ }
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (has_bits_offset_ == -1) {
+ // Proto3 does not have has-bits and we need to set a message field
+ // to NULL in order to indicate its un-presence.
+ if (GetArena(message) == NULL) {
+ delete *MutableRaw<Message*>(message, field);
+ }
+ *MutableRaw<Message*>(message, field) = NULL;
+ } else {
+ (*MutableRaw<Message*>(message, field))->Clear();
+ }
+ break;
+ }
+ }
+ } else {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case FieldDescriptor::CPPTYPE_##UPPERCASE : \
+ MutableRaw<RepeatedField<LOWERCASE> >(message, field)->Clear(); \
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, int);
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_STRING: {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ MutableRaw<RepeatedPtrField<string> >(message, field)->Clear();
+ break;
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_MESSAGE: {
+ if (IsMapFieldInApi(field)) {
+ MutableRaw<MapFieldBase>(message, field)
+ ->MutableRepeatedField()
+ ->Clear<GenericTypeHandler<Message> >();
+ } else {
+ // We don't know which subclass of RepeatedPtrFieldBase the type is,
+ // so we use RepeatedPtrFieldBase directly.
+ MutableRaw<RepeatedPtrFieldBase>(message, field)
+ ->Clear<GenericTypeHandler<Message> >();
+ }
+ break;
+ }
+ }
+ }
+}
+
+void GeneratedMessageReflection::RemoveLast(
+ Message* message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK_MESSAGE_TYPE(RemoveLast);
+ USAGE_CHECK_REPEATED(RemoveLast);
+
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->RemoveLast(field->number());
+ } else {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case FieldDescriptor::CPPTYPE_##UPPERCASE : \
+ MutableRaw<RepeatedField<LOWERCASE> >(message, field)->RemoveLast(); \
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, int);
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ MutableRaw<RepeatedPtrField<string> >(message, field)->RemoveLast();
+ break;
+ }
+ break;
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (IsMapFieldInApi(field)) {
+ MutableRaw<MapFieldBase>(message, field)
+ ->MutableRepeatedField()
+ ->RemoveLast<GenericTypeHandler<Message> >();
+ } else {
+ MutableRaw<RepeatedPtrFieldBase>(message, field)
+ ->RemoveLast<GenericTypeHandler<Message> >();
+ }
+ break;
+ }
+ }
+}
+
+Message* GeneratedMessageReflection::ReleaseLast(
+ Message* message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK_ALL(ReleaseLast, REPEATED, MESSAGE);
+
+ if (field->is_extension()) {
+ return static_cast<Message*>(
+ MutableExtensionSet(message)->ReleaseLast(field->number()));
+ } else {
+ if (IsMapFieldInApi(field)) {
+ return MutableRaw<MapFieldBase>(message, field)
+ ->MutableRepeatedField()
+ ->ReleaseLast<GenericTypeHandler<Message> >();
+ } else {
+ return MutableRaw<RepeatedPtrFieldBase>(message, field)
+ ->ReleaseLast<GenericTypeHandler<Message> >();
+ }
+ }
+}
+
+void GeneratedMessageReflection::SwapElements(
+ Message* message,
+ const FieldDescriptor* field,
+ int index1,
+ int index2) const {
+ USAGE_CHECK_MESSAGE_TYPE(Swap);
+ USAGE_CHECK_REPEATED(Swap);
+
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->SwapElements(field->number(), index1, index2);
+ } else {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
+ case FieldDescriptor::CPPTYPE_##UPPERCASE : \
+ MutableRaw<RepeatedField<LOWERCASE> >(message, field) \
+ ->SwapElements(index1, index2); \
+ break
+
+ HANDLE_TYPE( INT32, int32);
+ HANDLE_TYPE( INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE( FLOAT, float);
+ HANDLE_TYPE( BOOL, bool);
+ HANDLE_TYPE( ENUM, int);
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_STRING:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (IsMapFieldInApi(field)) {
+ MutableRaw<MapFieldBase>(message, field)
+ ->MutableRepeatedField()
+ ->SwapElements(index1, index2);
+ } else {
+ MutableRaw<RepeatedPtrFieldBase>(message, field)
+ ->SwapElements(index1, index2);
+ }
+ break;
+ }
+ }
+}
+
+namespace {
+// Comparison functor for sorting FieldDescriptors by field number.
+struct FieldNumberSorter {
+ bool operator()(const FieldDescriptor* left,
+ const FieldDescriptor* right) const {
+ return left->number() < right->number();
+ }
+};
+} // namespace
+
+void GeneratedMessageReflection::ListFields(
+ const Message& message,
+ vector<const FieldDescriptor*>* output) const {
+ output->clear();
+
+ // Optimization: The default instance never has any fields set.
+ if (&message == default_instance_) return;
+
+ output->reserve(descriptor_->field_count());
+ for (int i = 0; i < descriptor_->field_count(); i++) {
+ const FieldDescriptor* field = descriptor_->field(i);
+ if (field->is_repeated()) {
+ if (FieldSize(message, field) > 0) {
+ output->push_back(field);
+ }
+ } else {
+ if (field->containing_oneof()) {
+ if (HasOneofField(message, field)) {
+ output->push_back(field);
+ }
+ } else if (HasBit(message, field)) {
+ output->push_back(field);
+ }
+ }
+ }
+
+ if (extensions_offset_ != -1) {
+ GetExtensionSet(message).AppendToList(descriptor_, descriptor_pool_,
+ output);
+ }
+
+ // ListFields() must sort output by field number.
+ std::sort(output->begin(), output->end(), FieldNumberSorter());
+}
+
+// -------------------------------------------------------------------
+
+#undef DEFINE_PRIMITIVE_ACCESSORS
+#define DEFINE_PRIMITIVE_ACCESSORS(TYPENAME, TYPE, PASSTYPE, CPPTYPE) \
+ PASSTYPE GeneratedMessageReflection::Get##TYPENAME( \
+ const Message& message, const FieldDescriptor* field) const { \
+ USAGE_CHECK_ALL(Get##TYPENAME, SINGULAR, CPPTYPE); \
+ if (field->is_extension()) { \
+ return GetExtensionSet(message).Get##TYPENAME( \
+ field->number(), field->default_value_##PASSTYPE()); \
+ } else { \
+ return GetField<TYPE>(message, field); \
+ } \
+ } \
+ \
+ void GeneratedMessageReflection::Set##TYPENAME( \
+ Message* message, const FieldDescriptor* field, \
+ PASSTYPE value) const { \
+ USAGE_CHECK_ALL(Set##TYPENAME, SINGULAR, CPPTYPE); \
+ if (field->is_extension()) { \
+ return MutableExtensionSet(message)->Set##TYPENAME( \
+ field->number(), field->type(), value, field); \
+ } else { \
+ SetField<TYPE>(message, field, value); \
+ } \
+ } \
+ \
+ PASSTYPE GeneratedMessageReflection::GetRepeated##TYPENAME( \
+ const Message& message, \
+ const FieldDescriptor* field, int index) const { \
+ USAGE_CHECK_ALL(GetRepeated##TYPENAME, REPEATED, CPPTYPE); \
+ if (field->is_extension()) { \
+ return GetExtensionSet(message).GetRepeated##TYPENAME( \
+ field->number(), index); \
+ } else { \
+ return GetRepeatedField<TYPE>(message, field, index); \
+ } \
+ } \
+ \
+ void GeneratedMessageReflection::SetRepeated##TYPENAME( \
+ Message* message, const FieldDescriptor* field, \
+ int index, PASSTYPE value) const { \
+ USAGE_CHECK_ALL(SetRepeated##TYPENAME, REPEATED, CPPTYPE); \
+ if (field->is_extension()) { \
+ MutableExtensionSet(message)->SetRepeated##TYPENAME( \
+ field->number(), index, value); \
+ } else { \
+ SetRepeatedField<TYPE>(message, field, index, value); \
+ } \
+ } \
+ \
+ void GeneratedMessageReflection::Add##TYPENAME( \
+ Message* message, const FieldDescriptor* field, \
+ PASSTYPE value) const { \
+ USAGE_CHECK_ALL(Add##TYPENAME, REPEATED, CPPTYPE); \
+ if (field->is_extension()) { \
+ MutableExtensionSet(message)->Add##TYPENAME( \
+ field->number(), field->type(), field->options().packed(), value, \
+ field); \
+ } else { \
+ AddField<TYPE>(message, field, value); \
+ } \
+ }
+
+DEFINE_PRIMITIVE_ACCESSORS(Int32 , int32 , int32 , INT32 )
+DEFINE_PRIMITIVE_ACCESSORS(Int64 , int64 , int64 , INT64 )
+DEFINE_PRIMITIVE_ACCESSORS(UInt32, uint32, uint32, UINT32)
+DEFINE_PRIMITIVE_ACCESSORS(UInt64, uint64, uint64, UINT64)
+DEFINE_PRIMITIVE_ACCESSORS(Float , float , float , FLOAT )
+DEFINE_PRIMITIVE_ACCESSORS(Double, double, double, DOUBLE)
+DEFINE_PRIMITIVE_ACCESSORS(Bool , bool , bool , BOOL )
+#undef DEFINE_PRIMITIVE_ACCESSORS
+
+// -------------------------------------------------------------------
+
+string GeneratedMessageReflection::GetString(
+ const Message& message, const FieldDescriptor* field) const {
+ USAGE_CHECK_ALL(GetString, SINGULAR, STRING);
+ if (field->is_extension()) {
+ return GetExtensionSet(message).GetString(field->number(),
+ field->default_value_string());
+ } else {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING: {
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ return GetField<ArenaStringPtr>(message, field).Get(default_ptr);
+ }
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return GetEmptyString(); // Make compiler happy.
+ }
+}
+
+const string& GeneratedMessageReflection::GetStringReference(
+ const Message& message,
+ const FieldDescriptor* field, string* scratch) const {
+ USAGE_CHECK_ALL(GetStringReference, SINGULAR, STRING);
+ if (field->is_extension()) {
+ return GetExtensionSet(message).GetString(field->number(),
+ field->default_value_string());
+ } else {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING: {
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ return GetField<ArenaStringPtr>(message, field).Get(default_ptr);
+ }
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return GetEmptyString(); // Make compiler happy.
+ }
+}
+
+
+void GeneratedMessageReflection::SetString(
+ Message* message, const FieldDescriptor* field,
+ const string& value) const {
+ USAGE_CHECK_ALL(SetString, SINGULAR, STRING);
+ if (field->is_extension()) {
+ return MutableExtensionSet(message)->SetString(field->number(),
+ field->type(), value, field);
+ } else {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING: {
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ if (field->containing_oneof() && !HasOneofField(*message, field)) {
+ ClearOneof(message, field->containing_oneof());
+ MutableField<ArenaStringPtr>(message, field)->UnsafeSetDefault(
+ default_ptr);
+ }
+ MutableField<ArenaStringPtr>(message, field)->Set(default_ptr,
+ value, GetArena(message));
+ break;
+ }
+ }
+ }
+}
+
+
+string GeneratedMessageReflection::GetRepeatedString(
+ const Message& message, const FieldDescriptor* field, int index) const {
+ USAGE_CHECK_ALL(GetRepeatedString, REPEATED, STRING);
+ if (field->is_extension()) {
+ return GetExtensionSet(message).GetRepeatedString(field->number(), index);
+ } else {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ return GetRepeatedPtrField<string>(message, field, index);
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return GetEmptyString(); // Make compiler happy.
+ }
+}
+
+const string& GeneratedMessageReflection::GetRepeatedStringReference(
+ const Message& message, const FieldDescriptor* field,
+ int index, string* scratch) const {
+ USAGE_CHECK_ALL(GetRepeatedStringReference, REPEATED, STRING);
+ if (field->is_extension()) {
+ return GetExtensionSet(message).GetRepeatedString(field->number(), index);
+ } else {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ return GetRepeatedPtrField<string>(message, field, index);
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return GetEmptyString(); // Make compiler happy.
+ }
+}
+
+
+void GeneratedMessageReflection::SetRepeatedString(
+ Message* message, const FieldDescriptor* field,
+ int index, const string& value) const {
+ USAGE_CHECK_ALL(SetRepeatedString, REPEATED, STRING);
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->SetRepeatedString(
+ field->number(), index, value);
+ } else {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ *MutableRepeatedField<string>(message, field, index) = value;
+ break;
+ }
+ }
+}
+
+
+void GeneratedMessageReflection::AddString(
+ Message* message, const FieldDescriptor* field,
+ const string& value) const {
+ USAGE_CHECK_ALL(AddString, REPEATED, STRING);
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->AddString(field->number(),
+ field->type(), value, field);
+ } else {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING:
+ *AddField<string>(message, field) = value;
+ break;
+ }
+ }
+}
+
+
+// -------------------------------------------------------------------
+
+inline bool CreateUnknownEnumValues(const FileDescriptor* file) {
+ return file->syntax() == FileDescriptor::SYNTAX_PROTO3;
+}
+
+const EnumValueDescriptor* GeneratedMessageReflection::GetEnum(
+ const Message& message, const FieldDescriptor* field) const {
+ // Usage checked by GetEnumValue.
+ int value = GetEnumValue(message, field);
+ return field->enum_type()->FindValueByNumberCreatingIfUnknown(value);
+}
+
+int GeneratedMessageReflection::GetEnumValue(
+ const Message& message, const FieldDescriptor* field) const {
+ USAGE_CHECK_ALL(GetEnumValue, SINGULAR, ENUM);
+
+ int32 value;
+ if (field->is_extension()) {
+ value = GetExtensionSet(message).GetEnum(
+ field->number(), field->default_value_enum()->number());
+ } else {
+ value = GetField<int>(message, field);
+ }
+ return value;
+}
+
+void GeneratedMessageReflection::SetEnum(
+ Message* message, const FieldDescriptor* field,
+ const EnumValueDescriptor* value) const {
+ // Usage checked by SetEnumValue.
+ USAGE_CHECK_ENUM_VALUE(SetEnum);
+ SetEnumValueInternal(message, field, value->number());
+}
+
+void GeneratedMessageReflection::SetEnumValue(
+ Message* message, const FieldDescriptor* field,
+ int value) const {
+ USAGE_CHECK_ALL(SetEnumValue, SINGULAR, ENUM);
+ if (!CreateUnknownEnumValues(descriptor_->file())) {
+ // Check that the value is valid if we don't support direct storage of
+ // unknown enum values.
+ const EnumValueDescriptor* value_desc =
+ field->enum_type()->FindValueByNumber(value);
+ if (value_desc == NULL) {
+ GOOGLE_LOG(DFATAL) << "SetEnumValue accepts only valid integer values: value "
+ << value << " unexpected for field " << field->full_name();
+ // In production builds, DFATAL will not terminate the program, so we have
+ // to do something reasonable: just set the default value.
+ value = field->default_value_enum()->number();
+ }
+ }
+ SetEnumValueInternal(message, field, value);
+}
+
+void GeneratedMessageReflection::SetEnumValueInternal(
+ Message* message, const FieldDescriptor* field,
+ int value) const {
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->SetEnum(field->number(), field->type(),
+ value, field);
+ } else {
+ SetField<int>(message, field, value);
+ }
+}
+
+const EnumValueDescriptor* GeneratedMessageReflection::GetRepeatedEnum(
+ const Message& message, const FieldDescriptor* field, int index) const {
+ // Usage checked by GetRepeatedEnumValue.
+ int value = GetRepeatedEnumValue(message, field, index);
+ return field->enum_type()->FindValueByNumberCreatingIfUnknown(value);
+}
+
+int GeneratedMessageReflection::GetRepeatedEnumValue(
+ const Message& message, const FieldDescriptor* field, int index) const {
+ USAGE_CHECK_ALL(GetRepeatedEnumValue, REPEATED, ENUM);
+
+ int value;
+ if (field->is_extension()) {
+ value = GetExtensionSet(message).GetRepeatedEnum(field->number(), index);
+ } else {
+ value = GetRepeatedField<int>(message, field, index);
+ }
+ return value;
+}
+
+void GeneratedMessageReflection::SetRepeatedEnum(
+ Message* message,
+ const FieldDescriptor* field, int index,
+ const EnumValueDescriptor* value) const {
+ // Usage checked by SetRepeatedEnumValue.
+ USAGE_CHECK_ENUM_VALUE(SetRepeatedEnum);
+ SetRepeatedEnumValueInternal(message, field, index, value->number());
+}
+
+void GeneratedMessageReflection::SetRepeatedEnumValue(
+ Message* message,
+ const FieldDescriptor* field, int index,
+ int value) const {
+ USAGE_CHECK_ALL(SetRepeatedEnum, REPEATED, ENUM);
+ if (!CreateUnknownEnumValues(descriptor_->file())) {
+ // Check that the value is valid if we don't support direct storage of
+ // unknown enum values.
+ const EnumValueDescriptor* value_desc =
+ field->enum_type()->FindValueByNumber(value);
+ if (value_desc == NULL) {
+ GOOGLE_LOG(DFATAL) << "SetRepeatedEnumValue accepts only valid integer values: "
+ << "value " << value << " unexpected for field "
+ << field->full_name();
+ // In production builds, DFATAL will not terminate the program, so we have
+ // to do something reasonable: just set the default value.
+ value = field->default_value_enum()->number();
+ }
+ }
+ SetRepeatedEnumValueInternal(message, field, index, value);
+}
+
+void GeneratedMessageReflection::SetRepeatedEnumValueInternal(
+ Message* message,
+ const FieldDescriptor* field, int index,
+ int value) const {
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->SetRepeatedEnum(
+ field->number(), index, value);
+ } else {
+ SetRepeatedField<int>(message, field, index, value);
+ }
+}
+
+void GeneratedMessageReflection::AddEnum(
+ Message* message, const FieldDescriptor* field,
+ const EnumValueDescriptor* value) const {
+ // Usage checked by AddEnumValue.
+ USAGE_CHECK_ENUM_VALUE(AddEnum);
+ AddEnumValueInternal(message, field, value->number());
+}
+
+void GeneratedMessageReflection::AddEnumValue(
+ Message* message, const FieldDescriptor* field,
+ int value) const {
+ USAGE_CHECK_ALL(AddEnum, REPEATED, ENUM);
+ if (!CreateUnknownEnumValues(descriptor_->file())) {
+ // Check that the value is valid if we don't support direct storage of
+ // unknown enum values.
+ const EnumValueDescriptor* value_desc =
+ field->enum_type()->FindValueByNumber(value);
+ if (value_desc == NULL) {
+ GOOGLE_LOG(DFATAL) << "AddEnumValue accepts only valid integer values: value "
+ << value << " unexpected for field " << field->full_name();
+ // In production builds, DFATAL will not terminate the program, so we have
+ // to do something reasonable: just set the default value.
+ value = field->default_value_enum()->number();
+ }
+ }
+ AddEnumValueInternal(message, field, value);
+}
+
+void GeneratedMessageReflection::AddEnumValueInternal(
+ Message* message, const FieldDescriptor* field,
+ int value) const {
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->AddEnum(field->number(), field->type(),
+ field->options().packed(),
+ value, field);
+ } else {
+ AddField<int>(message, field, value);
+ }
+}
+
+// -------------------------------------------------------------------
+
+const Message& GeneratedMessageReflection::GetMessage(
+ const Message& message, const FieldDescriptor* field,
+ MessageFactory* factory) const {
+ USAGE_CHECK_ALL(GetMessage, SINGULAR, MESSAGE);
+
+ if (factory == NULL) factory = message_factory_;
+
+ if (field->is_extension()) {
+ return static_cast<const Message&>(
+ GetExtensionSet(message).GetMessage(
+ field->number(), field->message_type(), factory));
+ } else {
+ const Message* result;
+ result = GetRaw<const Message*>(message, field);
+ if (result == NULL) {
+ result = DefaultRaw<const Message*>(field);
+ }
+ return *result;
+ }
+}
+
+Message* GeneratedMessageReflection::MutableMessage(
+ Message* message, const FieldDescriptor* field,
+ MessageFactory* factory) const {
+ USAGE_CHECK_ALL(MutableMessage, SINGULAR, MESSAGE);
+
+ if (factory == NULL) factory = message_factory_;
+
+ if (field->is_extension()) {
+ return static_cast<Message*>(
+ MutableExtensionSet(message)->MutableMessage(field, factory));
+ } else {
+ Message* result;
+ Message** result_holder = MutableRaw<Message*>(message, field);
+
+ if (field->containing_oneof()) {
+ if (!HasOneofField(*message, field)) {
+ ClearOneof(message, field->containing_oneof());
+ result_holder = MutableField<Message*>(message, field);
+ const Message* default_message = DefaultRaw<const Message*>(field);
+ *result_holder = default_message->New(message->GetArena());
+ }
+ } else {
+ SetBit(message, field);
+ }
+
+ if (*result_holder == NULL) {
+ const Message* default_message = DefaultRaw<const Message*>(field);
+ *result_holder = default_message->New(message->GetArena());
+ }
+ result = *result_holder;
+ return result;
+ }
+}
+
+void GeneratedMessageReflection::UnsafeArenaSetAllocatedMessage(
+ Message* message,
+ Message* sub_message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK_ALL(SetAllocatedMessage, SINGULAR, MESSAGE);
+
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->SetAllocatedMessage(
+ field->number(), field->type(), field, sub_message);
+ } else {
+ if (field->containing_oneof()) {
+ if (sub_message == NULL) {
+ ClearOneof(message, field->containing_oneof());
+ return;
+ }
+ ClearOneof(message, field->containing_oneof());
+ *MutableRaw<Message*>(message, field) = sub_message;
+ SetOneofCase(message, field);
+ return;
+ }
+
+ if (sub_message == NULL) {
+ ClearBit(message, field);
+ } else {
+ SetBit(message, field);
+ }
+ Message** sub_message_holder = MutableRaw<Message*>(message, field);
+ if (GetArena(message) == NULL) {
+ delete *sub_message_holder;
+ }
+ *sub_message_holder = sub_message;
+ }
+}
+
+void GeneratedMessageReflection::SetAllocatedMessage(
+ Message* message,
+ Message* sub_message,
+ const FieldDescriptor* field) const {
+ // If message and sub-message are in different memory ownership domains
+ // (different arenas, or one is on heap and one is not), then we may need to
+ // do a copy.
+ if (sub_message != NULL &&
+ sub_message->GetArena() != message->GetArena()) {
+ if (sub_message->GetArena() == NULL && message->GetArena() != NULL) {
+ // Case 1: parent is on an arena and child is heap-allocated. We can add
+ // the child to the arena's Own() list to free on arena destruction, then
+ // set our pointer.
+ message->GetArena()->Own(sub_message);
+ UnsafeArenaSetAllocatedMessage(message, sub_message, field);
+ } else {
+ // Case 2: all other cases. We need to make a copy. MutableMessage() will
+ // either get the existing message object, or instantiate a new one as
+ // appropriate w.r.t. our arena.
+ Message* sub_message_copy = MutableMessage(message, field);
+ sub_message_copy->CopyFrom(*sub_message);
+ }
+ } else {
+ // Same memory ownership domains.
+ UnsafeArenaSetAllocatedMessage(message, sub_message, field);
+ }
+}
+
+Message* GeneratedMessageReflection::UnsafeArenaReleaseMessage(
+ Message* message,
+ const FieldDescriptor* field,
+ MessageFactory* factory) const {
+ USAGE_CHECK_ALL(ReleaseMessage, SINGULAR, MESSAGE);
+
+ if (factory == NULL) factory = message_factory_;
+
+ if (field->is_extension()) {
+ return static_cast<Message*>(
+ MutableExtensionSet(message)->UnsafeArenaReleaseMessage(field,
+ factory));
+ } else {
+ ClearBit(message, field);
+ if (field->containing_oneof()) {
+ if (HasOneofField(*message, field)) {
+ *MutableOneofCase(message, field->containing_oneof()) = 0;
+ } else {
+ return NULL;
+ }
+ }
+ Message** result = MutableRaw<Message*>(message, field);
+ Message* ret = *result;
+ *result = NULL;
+ return ret;
+ }
+}
+
+Message* GeneratedMessageReflection::ReleaseMessage(
+ Message* message,
+ const FieldDescriptor* field,
+ MessageFactory* factory) const {
+ Message* released = UnsafeArenaReleaseMessage(message, field, factory);
+ if (GetArena(message) != NULL && released != NULL) {
+ Message* copy_from_arena = released->New();
+ copy_from_arena->CopyFrom(*released);
+ released = copy_from_arena;
+ }
+ return released;
+}
+
+const Message& GeneratedMessageReflection::GetRepeatedMessage(
+ const Message& message, const FieldDescriptor* field, int index) const {
+ USAGE_CHECK_ALL(GetRepeatedMessage, REPEATED, MESSAGE);
+
+ if (field->is_extension()) {
+ return static_cast<const Message&>(
+ GetExtensionSet(message).GetRepeatedMessage(field->number(), index));
+ } else {
+ if (IsMapFieldInApi(field)) {
+ return GetRaw<MapFieldBase>(message, field)
+ .GetRepeatedField()
+ .Get<GenericTypeHandler<Message> >(index);
+ } else {
+ return GetRaw<RepeatedPtrFieldBase>(message, field)
+ .Get<GenericTypeHandler<Message> >(index);
+ }
+ }
+}
+
+Message* GeneratedMessageReflection::MutableRepeatedMessage(
+ Message* message, const FieldDescriptor* field, int index) const {
+ USAGE_CHECK_ALL(MutableRepeatedMessage, REPEATED, MESSAGE);
+
+ if (field->is_extension()) {
+ return static_cast<Message*>(
+ MutableExtensionSet(message)->MutableRepeatedMessage(
+ field->number(), index));
+ } else {
+ if (IsMapFieldInApi(field)) {
+ return MutableRaw<MapFieldBase>(message, field)
+ ->MutableRepeatedField()
+ ->Mutable<GenericTypeHandler<Message> >(index);
+ } else {
+ return MutableRaw<RepeatedPtrFieldBase>(message, field)
+ ->Mutable<GenericTypeHandler<Message> >(index);
+ }
+ }
+}
+
+Message* GeneratedMessageReflection::AddMessage(
+ Message* message, const FieldDescriptor* field,
+ MessageFactory* factory) const {
+ USAGE_CHECK_ALL(AddMessage, REPEATED, MESSAGE);
+
+ if (factory == NULL) factory = message_factory_;
+
+ if (field->is_extension()) {
+ return static_cast<Message*>(
+ MutableExtensionSet(message)->AddMessage(field, factory));
+ } else {
+ Message* result = NULL;
+
+ // We can't use AddField<Message>() because RepeatedPtrFieldBase doesn't
+ // know how to allocate one.
+ RepeatedPtrFieldBase* repeated = NULL;
+ if (IsMapFieldInApi(field)) {
+ repeated =
+ MutableRaw<MapFieldBase>(message, field)->MutableRepeatedField();
+ } else {
+ repeated = MutableRaw<RepeatedPtrFieldBase>(message, field);
+ }
+ result = repeated->AddFromCleared<GenericTypeHandler<Message> >();
+ if (result == NULL) {
+ // We must allocate a new object.
+ const Message* prototype;
+ if (repeated->size() == 0) {
+ prototype = factory->GetPrototype(field->message_type());
+ } else {
+ prototype = &repeated->Get<GenericTypeHandler<Message> >(0);
+ }
+ result = prototype->New(message->GetArena());
+ // We can guarantee here that repeated and result are either both heap
+ // allocated or arena owned. So it is safe to call the unsafe version
+ // of AddAllocated.
+ repeated->UnsafeArenaAddAllocated<GenericTypeHandler<Message> >(result);
+ }
+
+ return result;
+ }
+}
+
+void GeneratedMessageReflection::AddAllocatedMessage(
+ Message* message, const FieldDescriptor* field,
+ Message* new_entry) const {
+ USAGE_CHECK_ALL(AddAllocatedMessage, REPEATED, MESSAGE);
+
+ if (field->is_extension()) {
+ MutableExtensionSet(message)->AddAllocatedMessage(field, new_entry);
+ } else {
+ RepeatedPtrFieldBase* repeated = NULL;
+ if (IsMapFieldInApi(field)) {
+ repeated =
+ MutableRaw<MapFieldBase>(message, field)->MutableRepeatedField();
+ } else {
+ repeated = MutableRaw<RepeatedPtrFieldBase>(message, field);
+ }
+ repeated->AddAllocated<GenericTypeHandler<Message> >(new_entry);
+ }
+}
+
+void* GeneratedMessageReflection::MutableRawRepeatedField(
+ Message* message, const FieldDescriptor* field,
+ FieldDescriptor::CppType cpptype,
+ int ctype, const Descriptor* desc) const {
+ USAGE_CHECK_REPEATED("MutableRawRepeatedField");
+ if (field->cpp_type() != cpptype)
+ ReportReflectionUsageTypeError(descriptor_,
+ field, "MutableRawRepeatedField", cpptype);
+ if (ctype >= 0)
+ GOOGLE_CHECK_EQ(field->options().ctype(), ctype) << "subtype mismatch";
+ if (desc != NULL)
+ GOOGLE_CHECK_EQ(field->message_type(), desc) << "wrong submessage type";
+ if (field->is_extension()) {
+ return MutableExtensionSet(message)->MutableRawRepeatedField(
+ field->number(), field->type(), field->is_packed(), field);
+ } else {
+ // Trigger transform for MapField
+ if (IsMapFieldInApi(field)) {
+ return reinterpret_cast<MapFieldBase*>(reinterpret_cast<uint8*>(message) +
+ offsets_[field->index()])
+ ->MutableRepeatedField();
+ }
+ return reinterpret_cast<uint8*>(message) + offsets_[field->index()];
+ }
+}
+
+const void* GeneratedMessageReflection::GetRawRepeatedField(
+ const Message& message, const FieldDescriptor* field,
+ FieldDescriptor::CppType cpptype,
+ int ctype, const Descriptor* desc) const {
+ USAGE_CHECK_REPEATED("GetRawRepeatedField");
+ if (field->cpp_type() != cpptype)
+ ReportReflectionUsageTypeError(descriptor_,
+ field, "GetRawRepeatedField", cpptype);
+ if (ctype >= 0)
+ GOOGLE_CHECK_EQ(field->options().ctype(), ctype) << "subtype mismatch";
+ if (desc != NULL)
+ GOOGLE_CHECK_EQ(field->message_type(), desc) << "wrong submessage type";
+ if (field->is_extension()) {
+ // Should use extension_set::GetRawRepeatedField. However, the required
+ // parameter "default repeated value" is not very easy to get here.
+ // Map is not supported in extensions, it is acceptable to use
+ // extension_set::MutableRawRepeatedField which does not change the message.
+ return MutableExtensionSet(const_cast<Message*>(&message))
+ ->MutableRawRepeatedField(
+ field->number(), field->type(), field->is_packed(), field);
+ } else {
+ // Trigger transform for MapField
+ if (IsMapFieldInApi(field)) {
+ return &(reinterpret_cast<const MapFieldBase*>(
+ reinterpret_cast<const uint8*>(&message) +
+ offsets_[field->index()])->GetRepeatedField());
+ }
+ return reinterpret_cast<const uint8*>(&message) + offsets_[field->index()];
+ }
+}
+
+const FieldDescriptor* GeneratedMessageReflection::GetOneofFieldDescriptor(
+ const Message& message,
+ const OneofDescriptor* oneof_descriptor) const {
+ uint32 field_number = GetOneofCase(message, oneof_descriptor);
+ if (field_number == 0) {
+ return NULL;
+ }
+ return descriptor_->FindFieldByNumber(field_number);
+}
+
+bool GeneratedMessageReflection::ContainsMapKey(
+ const Message& message,
+ const FieldDescriptor* field,
+ const MapKey& key) const {
+ USAGE_CHECK(IsMapFieldInApi(field),
+ "LookupMapValue",
+ "Field is not a map field.");
+ return GetRaw<MapFieldBase>(message, field).ContainsMapKey(key);
+}
+
+bool GeneratedMessageReflection::InsertOrLookupMapValue(
+ Message* message,
+ const FieldDescriptor* field,
+ const MapKey& key,
+ MapValueRef* val) const {
+ USAGE_CHECK(IsMapFieldInApi(field),
+ "InsertOrLookupMapValue",
+ "Field is not a map field.");
+ val->SetType(field->message_type()->FindFieldByName("value")->cpp_type());
+ return MutableRaw<MapFieldBase>(message, field)->InsertOrLookupMapValue(
+ key, val);
+}
+
+bool GeneratedMessageReflection::DeleteMapValue(
+ Message* message,
+ const FieldDescriptor* field,
+ const MapKey& key) const {
+ USAGE_CHECK(IsMapFieldInApi(field),
+ "DeleteMapValue",
+ "Field is not a map field.");
+ return MutableRaw<MapFieldBase>(message, field)->DeleteMapValue(key);
+}
+
+MapIterator GeneratedMessageReflection::MapBegin(
+ Message* message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK(IsMapFieldInApi(field),
+ "MapBegin",
+ "Field is not a map field.");
+ MapIterator iter(message, field);
+ GetRaw<MapFieldBase>(*message, field).MapBegin(&iter);
+ return iter;
+}
+
+MapIterator GeneratedMessageReflection::MapEnd(
+ Message* message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK(IsMapFieldInApi(field),
+ "MapEnd",
+ "Field is not a map field.");
+ MapIterator iter(message, field);
+ GetRaw<MapFieldBase>(*message, field).MapEnd(&iter);
+ return iter;
+}
+
+int GeneratedMessageReflection::MapSize(
+ const Message& message,
+ const FieldDescriptor* field) const {
+ USAGE_CHECK(IsMapFieldInApi(field),
+ "MapSize",
+ "Field is not a map field.");
+ return GetRaw<MapFieldBase>(message, field).size();
+}
+
+// -----------------------------------------------------------------------------
+
+const FieldDescriptor* GeneratedMessageReflection::FindKnownExtensionByName(
+ const string& name) const {
+ if (extensions_offset_ == -1) return NULL;
+
+ const FieldDescriptor* result = descriptor_pool_->FindExtensionByName(name);
+ if (result != NULL && result->containing_type() == descriptor_) {
+ return result;
+ }
+
+ if (descriptor_->options().message_set_wire_format()) {
+ // MessageSet extensions may be identified by type name.
+ const Descriptor* type = descriptor_pool_->FindMessageTypeByName(name);
+ if (type != NULL) {
+ // Look for a matching extension in the foreign type's scope.
+ for (int i = 0; i < type->extension_count(); i++) {
+ const FieldDescriptor* extension = type->extension(i);
+ if (extension->containing_type() == descriptor_ &&
+ extension->type() == FieldDescriptor::TYPE_MESSAGE &&
+ extension->is_optional() &&
+ extension->message_type() == type) {
+ // Found it.
+ return extension;
+ }
+ }
+ }
+ }
+
+ return NULL;
+}
+
+const FieldDescriptor* GeneratedMessageReflection::FindKnownExtensionByNumber(
+ int number) const {
+ if (extensions_offset_ == -1) return NULL;
+ return descriptor_pool_->FindExtensionByNumber(descriptor_, number);
+}
+
+bool GeneratedMessageReflection::SupportsUnknownEnumValues() const {
+ return CreateUnknownEnumValues(descriptor_->file());
+}
+
+// ===================================================================
+// Some private helpers.
+
+// These simple template accessors obtain pointers (or references) to
+// the given field.
+template <typename Type>
+inline const Type& GeneratedMessageReflection::GetRaw(
+ const Message& message, const FieldDescriptor* field) const {
+ if (field->containing_oneof() && !HasOneofField(message, field)) {
+ return DefaultRaw<Type>(field);
+ }
+ int index = field->containing_oneof() ?
+ descriptor_->field_count() + field->containing_oneof()->index() :
+ field->index();
+ const void* ptr = reinterpret_cast<const uint8*>(&message) +
+ offsets_[index];
+ return *reinterpret_cast<const Type*>(ptr);
+}
+
+template <typename Type>
+inline Type* GeneratedMessageReflection::MutableRaw(
+ Message* message, const FieldDescriptor* field) const {
+ int index = field->containing_oneof() ?
+ descriptor_->field_count() + field->containing_oneof()->index() :
+ field->index();
+ void* ptr = reinterpret_cast<uint8*>(message) + offsets_[index];
+ return reinterpret_cast<Type*>(ptr);
+}
+
+template <typename Type>
+inline const Type& GeneratedMessageReflection::DefaultRaw(
+ const FieldDescriptor* field) const {
+ const void* ptr = field->containing_oneof() ?
+ reinterpret_cast<const uint8*>(default_oneof_instance_) +
+ offsets_[field->index()] :
+ reinterpret_cast<const uint8*>(default_instance_) +
+ offsets_[field->index()];
+ return *reinterpret_cast<const Type*>(ptr);
+}
+
+inline const uint32* GeneratedMessageReflection::GetHasBits(
+ const Message& message) const {
+ if (has_bits_offset_ == -1) { // proto3 with no has-bits.
+ return NULL;
+ }
+ const void* ptr = reinterpret_cast<const uint8*>(&message) + has_bits_offset_;
+ return reinterpret_cast<const uint32*>(ptr);
+}
+inline uint32* GeneratedMessageReflection::MutableHasBits(
+ Message* message) const {
+ if (has_bits_offset_ == -1) {
+ return NULL;
+ }
+ void* ptr = reinterpret_cast<uint8*>(message) + has_bits_offset_;
+ return reinterpret_cast<uint32*>(ptr);
+}
+
+inline uint32 GeneratedMessageReflection::GetOneofCase(
+ const Message& message,
+ const OneofDescriptor* oneof_descriptor) const {
+ const void* ptr = reinterpret_cast<const uint8*>(&message)
+ + oneof_case_offset_;
+ return reinterpret_cast<const uint32*>(ptr)[oneof_descriptor->index()];
+}
+
+inline uint32* GeneratedMessageReflection::MutableOneofCase(
+ Message* message,
+ const OneofDescriptor* oneof_descriptor) const {
+ void* ptr = reinterpret_cast<uint8*>(message) + oneof_case_offset_;
+ return &(reinterpret_cast<uint32*>(ptr)[oneof_descriptor->index()]);
+}
+
+inline const ExtensionSet& GeneratedMessageReflection::GetExtensionSet(
+ const Message& message) const {
+ GOOGLE_DCHECK_NE(extensions_offset_, -1);
+ const void* ptr = reinterpret_cast<const uint8*>(&message) +
+ extensions_offset_;
+ return *reinterpret_cast<const ExtensionSet*>(ptr);
+}
+inline ExtensionSet* GeneratedMessageReflection::MutableExtensionSet(
+ Message* message) const {
+ GOOGLE_DCHECK_NE(extensions_offset_, -1);
+ void* ptr = reinterpret_cast<uint8*>(message) + extensions_offset_;
+ return reinterpret_cast<ExtensionSet*>(ptr);
+}
+
+inline Arena* GeneratedMessageReflection::GetArena(Message* message) const {
+ if (arena_offset_ == kNoArenaPointer) {
+ return NULL;
+ }
+
+ if (unknown_fields_offset_ == kUnknownFieldSetInMetadata) {
+ // zero-overhead arena pointer overloading UnknownFields
+ return GetInternalMetadataWithArena(*message).arena();
+ }
+
+ // Baseline case: message class has a dedicated arena pointer.
+ void* ptr = reinterpret_cast<uint8*>(message) + arena_offset_;
+ return *reinterpret_cast<Arena**>(ptr);
+}
+
+inline const InternalMetadataWithArena&
+GeneratedMessageReflection::GetInternalMetadataWithArena(
+ const Message& message) const {
+ const void* ptr = reinterpret_cast<const uint8*>(&message) + arena_offset_;
+ return *reinterpret_cast<const InternalMetadataWithArena*>(ptr);
+}
+
+inline InternalMetadataWithArena*
+GeneratedMessageReflection::MutableInternalMetadataWithArena(
+ Message* message) const {
+ void* ptr = reinterpret_cast<uint8*>(message) + arena_offset_;
+ return reinterpret_cast<InternalMetadataWithArena*>(ptr);
+}
+
+inline bool
+GeneratedMessageReflection::GetIsDefaultInstance(
+ const Message& message) const {
+ if (is_default_instance_offset_ == kHasNoDefaultInstanceField) {
+ return false;
+ }
+ const void* ptr = reinterpret_cast<const uint8*>(&message) +
+ is_default_instance_offset_;
+ return *reinterpret_cast<const bool*>(ptr);
+}
+
+// Simple accessors for manipulating has_bits_.
+inline bool GeneratedMessageReflection::HasBit(
+ const Message& message, const FieldDescriptor* field) const {
+ if (has_bits_offset_ == -1) {
+ // proto3: no has-bits. All fields present except messages, which are
+ // present only if their message-field pointer is non-NULL.
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ return !GetIsDefaultInstance(message) &&
+ GetRaw<const Message*>(message, field) != NULL;
+ } else {
+ // Non-message field (and non-oneof, since that was handled in HasField()
+ // before calling us), and singular (again, checked in HasField). So, this
+ // field must be a scalar.
+
+ // Scalar primitive (numeric or string/bytes) fields are present if
+ // their value is non-zero (numeric) or non-empty (string/bytes). N.B.:
+ // we must use this definition here, rather than the "scalar fields
+ // always present" in the proto3 docs, because MergeFrom() semantics
+ // require presence as "present on wire", and reflection-based merge
+ // (which uses HasField()) needs to be consistent with this.
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default: {
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ return GetField<ArenaStringPtr>(message, field).Get(
+ default_ptr).size() > 0;
+ }
+ }
+ return false;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return GetRaw<bool>(message, field) != false;
+ case FieldDescriptor::CPPTYPE_INT32:
+ return GetRaw<int32>(message, field) != 0;
+ case FieldDescriptor::CPPTYPE_INT64:
+ return GetRaw<int64>(message, field) != 0;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return GetRaw<uint32>(message, field) != 0;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return GetRaw<uint64>(message, field) != 0;
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return GetRaw<float>(message, field) != 0.0;
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return GetRaw<double>(message, field) != 0.0;
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return GetRaw<int>(message, field) != 0;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ // handled above; avoid warning
+ GOOGLE_LOG(FATAL) << "Reached impossible case in HasBit().";
+ break;
+ }
+ }
+ }
+ return GetHasBits(message)[field->index() / 32] &
+ (1 << (field->index() % 32));
+}
+
+inline void GeneratedMessageReflection::SetBit(
+ Message* message, const FieldDescriptor* field) const {
+ if (has_bits_offset_ == -1) {
+ return;
+ }
+ MutableHasBits(message)[field->index() / 32] |= (1 << (field->index() % 32));
+}
+
+inline void GeneratedMessageReflection::ClearBit(
+ Message* message, const FieldDescriptor* field) const {
+ if (has_bits_offset_ == -1) {
+ return;
+ }
+ MutableHasBits(message)[field->index() / 32] &= ~(1 << (field->index() % 32));
+}
+
+inline void GeneratedMessageReflection::SwapBit(
+ Message* message1, Message* message2, const FieldDescriptor* field) const {
+ if (has_bits_offset_ == -1) {
+ return;
+ }
+ bool temp_has_bit = HasBit(*message1, field);
+ if (HasBit(*message2, field)) {
+ SetBit(message1, field);
+ } else {
+ ClearBit(message1, field);
+ }
+ if (temp_has_bit) {
+ SetBit(message2, field);
+ } else {
+ ClearBit(message2, field);
+ }
+}
+
+inline bool GeneratedMessageReflection::HasOneof(
+ const Message& message, const OneofDescriptor* oneof_descriptor) const {
+ return (GetOneofCase(message, oneof_descriptor) > 0);
+}
+
+inline bool GeneratedMessageReflection::HasOneofField(
+ const Message& message, const FieldDescriptor* field) const {
+ return (GetOneofCase(message, field->containing_oneof()) == field->number());
+}
+
+inline void GeneratedMessageReflection::SetOneofCase(
+ Message* message, const FieldDescriptor* field) const {
+ *MutableOneofCase(message, field->containing_oneof()) = field->number();
+}
+
+inline void GeneratedMessageReflection::ClearOneofField(
+ Message* message, const FieldDescriptor* field) const {
+ if (HasOneofField(*message, field)) {
+ ClearOneof(message, field->containing_oneof());
+ }
+}
+
+inline void GeneratedMessageReflection::ClearOneof(
+ Message* message, const OneofDescriptor* oneof_descriptor) const {
+ // TODO(jieluo): Consider to cache the unused object instead of deleting
+ // it. It will be much faster if an application switches a lot from
+ // a few oneof fields. Time/space tradeoff
+ uint32 oneof_case = GetOneofCase(*message, oneof_descriptor);
+ if (oneof_case > 0) {
+ const FieldDescriptor* field = descriptor_->FindFieldByNumber(oneof_case);
+ if (GetArena(message) == NULL) {
+ switch (field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_STRING: {
+ switch (field->options().ctype()) {
+ default: // TODO(kenton): Support other string reps.
+ case FieldOptions::STRING: {
+ const string* default_ptr =
+ &DefaultRaw<ArenaStringPtr>(field).Get(NULL);
+ MutableField<ArenaStringPtr>(message, field)->
+ Destroy(default_ptr, GetArena(message));
+ break;
+ }
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ delete *MutableRaw<Message*>(message, field);
+ break;
+ default:
+ break;
+ }
+ }
+
+ *MutableOneofCase(message, oneof_descriptor) = 0;
+ }
+}
+
+// Template implementations of basic accessors. Inline because each
+// template instance is only called from one location. These are
+// used for all types except messages.
+template <typename Type>
+inline const Type& GeneratedMessageReflection::GetField(
+ const Message& message, const FieldDescriptor* field) const {
+ return GetRaw<Type>(message, field);
+}
+
+template <typename Type>
+inline void GeneratedMessageReflection::SetField(
+ Message* message, const FieldDescriptor* field, const Type& value) const {
+ if (field->containing_oneof() && !HasOneofField(*message, field)) {
+ ClearOneof(message, field->containing_oneof());
+ }
+ *MutableRaw<Type>(message, field) = value;
+ field->containing_oneof() ?
+ SetOneofCase(message, field) : SetBit(message, field);
+}
+
+template <typename Type>
+inline Type* GeneratedMessageReflection::MutableField(
+ Message* message, const FieldDescriptor* field) const {
+ field->containing_oneof() ?
+ SetOneofCase(message, field) : SetBit(message, field);
+ return MutableRaw<Type>(message, field);
+}
+
+template <typename Type>
+inline const Type& GeneratedMessageReflection::GetRepeatedField(
+ const Message& message, const FieldDescriptor* field, int index) const {
+ return GetRaw<RepeatedField<Type> >(message, field).Get(index);
+}
+
+template <typename Type>
+inline const Type& GeneratedMessageReflection::GetRepeatedPtrField(
+ const Message& message, const FieldDescriptor* field, int index) const {
+ return GetRaw<RepeatedPtrField<Type> >(message, field).Get(index);
+}
+
+template <typename Type>
+inline void GeneratedMessageReflection::SetRepeatedField(
+ Message* message, const FieldDescriptor* field,
+ int index, Type value) const {
+ MutableRaw<RepeatedField<Type> >(message, field)->Set(index, value);
+}
+
+template <typename Type>
+inline Type* GeneratedMessageReflection::MutableRepeatedField(
+ Message* message, const FieldDescriptor* field, int index) const {
+ RepeatedPtrField<Type>* repeated =
+ MutableRaw<RepeatedPtrField<Type> >(message, field);
+ return repeated->Mutable(index);
+}
+
+template <typename Type>
+inline void GeneratedMessageReflection::AddField(
+ Message* message, const FieldDescriptor* field, const Type& value) const {
+ MutableRaw<RepeatedField<Type> >(message, field)->Add(value);
+}
+
+template <typename Type>
+inline Type* GeneratedMessageReflection::AddField(
+ Message* message, const FieldDescriptor* field) const {
+ RepeatedPtrField<Type>* repeated =
+ MutableRaw<RepeatedPtrField<Type> >(message, field);
+ return repeated->Add();
+}
+
+MessageFactory* GeneratedMessageReflection::GetMessageFactory() const {
+ return message_factory_;
+}
+
+void* GeneratedMessageReflection::RepeatedFieldData(
+ Message* message, const FieldDescriptor* field,
+ FieldDescriptor::CppType cpp_type,
+ const Descriptor* message_type) const {
+ GOOGLE_CHECK(field->is_repeated());
+ GOOGLE_CHECK(field->cpp_type() == cpp_type ||
+ (field->cpp_type() == FieldDescriptor::CPPTYPE_ENUM &&
+ cpp_type == FieldDescriptor::CPPTYPE_INT32))
+ << "The type parameter T in RepeatedFieldRef<T> API doesn't match "
+ << "the actual field type (for enums T should be the generated enum "
+ << "type or int32).";
+ if (message_type != NULL) {
+ GOOGLE_CHECK_EQ(message_type, field->message_type());
+ }
+ if (field->is_extension()) {
+ return MutableExtensionSet(message)->MutableRawRepeatedField(
+ field->number(), field->type(), field->is_packed(), field);
+ } else {
+ return reinterpret_cast<uint8*>(message) + offsets_[field->index()];
+ }
+}
+
+MapFieldBase* GeneratedMessageReflection::MapData(
+ Message* message, const FieldDescriptor* field) const {
+ USAGE_CHECK(IsMapFieldInApi(field),
+ "GetMapData",
+ "Field is not a map field.");
+ return MutableRaw<MapFieldBase>(message, field);
+}
+
+GeneratedMessageReflection*
+GeneratedMessageReflection::NewGeneratedMessageReflection(
+ const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ const void* default_oneof_instance,
+ int oneof_case_offset,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset) {
+ return new GeneratedMessageReflection(descriptor,
+ default_instance,
+ offsets,
+ has_bits_offset,
+ unknown_fields_offset,
+ extensions_offset,
+ default_oneof_instance,
+ oneof_case_offset,
+ DescriptorPool::generated_pool(),
+ MessageFactory::generated_factory(),
+ object_size,
+ arena_offset,
+ is_default_instance_offset);
+}
+
+GeneratedMessageReflection*
+GeneratedMessageReflection::NewGeneratedMessageReflection(
+ const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset) {
+ return new GeneratedMessageReflection(descriptor,
+ default_instance,
+ offsets,
+ has_bits_offset,
+ unknown_fields_offset,
+ extensions_offset,
+ DescriptorPool::generated_pool(),
+ MessageFactory::generated_factory(),
+ object_size,
+ arena_offset,
+ is_default_instance_offset);
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.h b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.h
new file mode 100644
index 0000000000..15fc802ce1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection.h
@@ -0,0 +1,683 @@
+// 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 header is logically internal, but is made public because it is used
+// from protocol-compiler-generated code, which may reside in other components.
+
+#ifndef GOOGLE_PROTOBUF_GENERATED_MESSAGE_REFLECTION_H__
+#define GOOGLE_PROTOBUF_GENERATED_MESSAGE_REFLECTION_H__
+
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/common.h>
+// TODO(jasonh): Remove this once the compiler change to directly include this
+// is released to components.
+#include <google/protobuf/generated_enum_reflection.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/unknown_field_set.h>
+
+
+namespace google {
+namespace upb {
+namespace google_opensource {
+class GMR_Handlers;
+} // namespace google_opensource
+} // namespace upb
+
+namespace protobuf {
+class DescriptorPool;
+class MapKey;
+class MapValueRef;
+}
+
+namespace protobuf {
+namespace internal {
+class DefaultEmptyOneof;
+
+// Defined in this file.
+class GeneratedMessageReflection;
+
+// Defined in other files.
+class ExtensionSet; // extension_set.h
+
+// THIS CLASS IS NOT INTENDED FOR DIRECT USE. It is intended for use
+// by generated code. This class is just a big hack that reduces code
+// size.
+//
+// A GeneratedMessageReflection is an implementation of Reflection
+// which expects all fields to be backed by simple variables located in
+// memory. The locations are given using a base pointer and a set of
+// offsets.
+//
+// It is required that the user represents fields of each type in a standard
+// way, so that GeneratedMessageReflection can cast the void* pointer to
+// the appropriate type. For primitive fields and string fields, each field
+// should be represented using the obvious C++ primitive type. Enums and
+// Messages are different:
+// - Singular Message fields are stored as a pointer to a Message. These
+// should start out NULL, except for in the default instance where they
+// should start out pointing to other default instances.
+// - Enum fields are stored as an int. This int must always contain
+// a valid value, such that EnumDescriptor::FindValueByNumber() would
+// not return NULL.
+// - Repeated fields are stored as RepeatedFields or RepeatedPtrFields
+// of whatever type the individual field would be. Strings and
+// Messages use RepeatedPtrFields while everything else uses
+// RepeatedFields.
+class LIBPROTOBUF_EXPORT GeneratedMessageReflection : public Reflection {
+ public:
+ // Constructs a GeneratedMessageReflection.
+ // Parameters:
+ // descriptor: The descriptor for the message type being implemented.
+ // default_instance: The default instance of the message. This is only
+ // used to obtain pointers to default instances of embedded
+ // messages, which GetMessage() will return if the particular
+ // sub-message has not been initialized yet. (Thus, all
+ // embedded message fields *must* have non-NULL pointers
+ // in the default instance.)
+ // offsets: An array of ints giving the byte offsets, relative to
+ // the start of the message object, of each field. These can
+ // be computed at compile time using the
+ // GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET() macro, defined
+ // below.
+ // has_bits_offset: Offset in the message of an array of uint32s of size
+ // descriptor->field_count()/32, rounded up. This is a
+ // bitfield where each bit indicates whether or not the
+ // corresponding field of the message has been initialized.
+ // The bit for field index i is obtained by the expression:
+ // has_bits[i / 32] & (1 << (i % 32))
+ // unknown_fields_offset: Offset in the message of the UnknownFieldSet for
+ // the message.
+ // extensions_offset: Offset in the message of the ExtensionSet for the
+ // message, or -1 if the message type has no extension
+ // ranges.
+ // pool: DescriptorPool to search for extension definitions. Only
+ // used by FindKnownExtensionByName() and
+ // FindKnownExtensionByNumber().
+ // factory: MessageFactory to use to construct extension messages.
+ // object_size: The size of a message object of this type, as measured
+ // by sizeof().
+ GeneratedMessageReflection(const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ const DescriptorPool* pool,
+ MessageFactory* factory,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset = -1);
+
+ // Similar with the construction above. Call this construction if the
+ // message has oneof definition.
+ // Parameters:
+ // offsets: An array of ints giving the byte offsets.
+ // For each oneof field, the offset is relative to the
+ // default_oneof_instance. These can be computed at compile
+ // time using the
+ // PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET() macro.
+ // For each none oneof field, the offset is related to
+ // the start of the message object. These can be computed
+ // at compile time using the
+ // GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET() macro.
+ // Besides offsets for all fields, this array also contains
+ // offsets for oneof unions. The offset of the i-th oneof
+ // union is offsets[descriptor->field_count() + i].
+ // default_oneof_instance: The default instance of the oneofs. It is a
+ // struct holding the default value of all oneof fields
+ // for this message. It is only used to obtain pointers
+ // to default instances of oneof fields, which Get
+ // methods will return if the field is not set.
+ // oneof_case_offset: Offset in the message of an array of uint32s of
+ // size descriptor->oneof_decl_count(). Each uint32
+ // indicates what field is set for each oneof.
+ // other parameters are the same with the construction above.
+ GeneratedMessageReflection(const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ const void* default_oneof_instance,
+ int oneof_case_offset,
+ const DescriptorPool* pool,
+ MessageFactory* factory,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset = -1);
+ ~GeneratedMessageReflection();
+
+ // Shorter-to-call helpers for the above two constructions that work if the
+ // pool and factory are the usual, namely, DescriptorPool::generated_pool()
+ // and MessageFactory::generated_factory().
+
+ static GeneratedMessageReflection* NewGeneratedMessageReflection(
+ const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ const void* default_oneof_instance,
+ int oneof_case_offset,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset = -1);
+
+ static GeneratedMessageReflection* NewGeneratedMessageReflection(
+ const Descriptor* descriptor,
+ const Message* default_instance,
+ const int offsets[],
+ int has_bits_offset,
+ int unknown_fields_offset,
+ int extensions_offset,
+ int object_size,
+ int arena_offset,
+ int is_default_instance_offset = -1);
+
+ // implements Reflection -------------------------------------------
+
+ const UnknownFieldSet& GetUnknownFields(const Message& message) const;
+ UnknownFieldSet* MutableUnknownFields(Message* message) const;
+
+ int SpaceUsed(const Message& message) const;
+
+ bool HasField(const Message& message, const FieldDescriptor* field) const;
+ int FieldSize(const Message& message, const FieldDescriptor* field) const;
+ void ClearField(Message* message, const FieldDescriptor* field) const;
+ bool HasOneof(const Message& message,
+ const OneofDescriptor* oneof_descriptor) const;
+ void ClearOneof(Message* message, const OneofDescriptor* field) const;
+ void RemoveLast(Message* message, const FieldDescriptor* field) const;
+ Message* ReleaseLast(Message* message, const FieldDescriptor* field) const;
+ void Swap(Message* message1, Message* message2) const;
+ void SwapFields(Message* message1, Message* message2,
+ const vector<const FieldDescriptor*>& fields) const;
+ void SwapElements(Message* message, const FieldDescriptor* field,
+ int index1, int index2) const;
+ void ListFields(const Message& message,
+ vector<const FieldDescriptor*>* output) const;
+
+ int32 GetInt32 (const Message& message,
+ const FieldDescriptor* field) const;
+ int64 GetInt64 (const Message& message,
+ const FieldDescriptor* field) const;
+ uint32 GetUInt32(const Message& message,
+ const FieldDescriptor* field) const;
+ uint64 GetUInt64(const Message& message,
+ const FieldDescriptor* field) const;
+ float GetFloat (const Message& message,
+ const FieldDescriptor* field) const;
+ double GetDouble(const Message& message,
+ const FieldDescriptor* field) const;
+ bool GetBool (const Message& message,
+ const FieldDescriptor* field) const;
+ string GetString(const Message& message,
+ const FieldDescriptor* field) const;
+ const string& GetStringReference(const Message& message,
+ const FieldDescriptor* field,
+ string* scratch) const;
+ const EnumValueDescriptor* GetEnum(const Message& message,
+ const FieldDescriptor* field) const;
+ int GetEnumValue(const Message& message,
+ const FieldDescriptor* field) const;
+ const Message& GetMessage(const Message& message,
+ const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const;
+
+ const FieldDescriptor* GetOneofFieldDescriptor(
+ const Message& message,
+ const OneofDescriptor* oneof_descriptor) const;
+
+ private:
+ bool ContainsMapKey(const Message& message,
+ const FieldDescriptor* field,
+ const MapKey& key) const;
+ bool InsertOrLookupMapValue(Message* message,
+ const FieldDescriptor* field,
+ const MapKey& key,
+ MapValueRef* val) const;
+ bool DeleteMapValue(Message* message,
+ const FieldDescriptor* field,
+ const MapKey& key) const;
+ MapIterator MapBegin(
+ Message* message,
+ const FieldDescriptor* field) const;
+ MapIterator MapEnd(
+ Message* message,
+ const FieldDescriptor* field) const;
+ int MapSize(const Message& message, const FieldDescriptor* field) const;
+
+ public:
+ void SetInt32 (Message* message,
+ const FieldDescriptor* field, int32 value) const;
+ void SetInt64 (Message* message,
+ const FieldDescriptor* field, int64 value) const;
+ void SetUInt32(Message* message,
+ const FieldDescriptor* field, uint32 value) const;
+ void SetUInt64(Message* message,
+ const FieldDescriptor* field, uint64 value) const;
+ void SetFloat (Message* message,
+ const FieldDescriptor* field, float value) const;
+ void SetDouble(Message* message,
+ const FieldDescriptor* field, double value) const;
+ void SetBool (Message* message,
+ const FieldDescriptor* field, bool value) const;
+ void SetString(Message* message,
+ const FieldDescriptor* field,
+ const string& value) const;
+ void SetEnum (Message* message, const FieldDescriptor* field,
+ const EnumValueDescriptor* value) const;
+ void SetEnumValue(Message* message, const FieldDescriptor* field,
+ int value) const;
+ Message* MutableMessage(Message* message, const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const;
+ void SetAllocatedMessage(Message* message,
+ Message* sub_message,
+ const FieldDescriptor* field) const;
+ Message* ReleaseMessage(Message* message, const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const;
+
+ int32 GetRepeatedInt32 (const Message& message,
+ const FieldDescriptor* field, int index) const;
+ int64 GetRepeatedInt64 (const Message& message,
+ const FieldDescriptor* field, int index) const;
+ uint32 GetRepeatedUInt32(const Message& message,
+ const FieldDescriptor* field, int index) const;
+ uint64 GetRepeatedUInt64(const Message& message,
+ const FieldDescriptor* field, int index) const;
+ float GetRepeatedFloat (const Message& message,
+ const FieldDescriptor* field, int index) const;
+ double GetRepeatedDouble(const Message& message,
+ const FieldDescriptor* field, int index) const;
+ bool GetRepeatedBool (const Message& message,
+ const FieldDescriptor* field, int index) const;
+ string GetRepeatedString(const Message& message,
+ const FieldDescriptor* field, int index) const;
+ const string& GetRepeatedStringReference(const Message& message,
+ const FieldDescriptor* field,
+ int index, string* scratch) const;
+ const EnumValueDescriptor* GetRepeatedEnum(const Message& message,
+ const FieldDescriptor* field,
+ int index) const;
+ int GetRepeatedEnumValue(const Message& message,
+ const FieldDescriptor* field,
+ int index) const;
+ const Message& GetRepeatedMessage(const Message& message,
+ const FieldDescriptor* field,
+ int index) const;
+
+ // Set the value of a field.
+ void SetRepeatedInt32 (Message* message,
+ const FieldDescriptor* field, int index, int32 value) const;
+ void SetRepeatedInt64 (Message* message,
+ const FieldDescriptor* field, int index, int64 value) const;
+ void SetRepeatedUInt32(Message* message,
+ const FieldDescriptor* field, int index, uint32 value) const;
+ void SetRepeatedUInt64(Message* message,
+ const FieldDescriptor* field, int index, uint64 value) const;
+ void SetRepeatedFloat (Message* message,
+ const FieldDescriptor* field, int index, float value) const;
+ void SetRepeatedDouble(Message* message,
+ const FieldDescriptor* field, int index, double value) const;
+ void SetRepeatedBool (Message* message,
+ const FieldDescriptor* field, int index, bool value) const;
+ void SetRepeatedString(Message* message,
+ const FieldDescriptor* field, int index,
+ const string& value) const;
+ void SetRepeatedEnum(Message* message, const FieldDescriptor* field,
+ int index, const EnumValueDescriptor* value) const;
+ void SetRepeatedEnumValue(Message* message, const FieldDescriptor* field,
+ int index, int value) const;
+ // Get a mutable pointer to a field with a message type.
+ Message* MutableRepeatedMessage(Message* message,
+ const FieldDescriptor* field,
+ int index) const;
+
+ void AddInt32 (Message* message,
+ const FieldDescriptor* field, int32 value) const;
+ void AddInt64 (Message* message,
+ const FieldDescriptor* field, int64 value) const;
+ void AddUInt32(Message* message,
+ const FieldDescriptor* field, uint32 value) const;
+ void AddUInt64(Message* message,
+ const FieldDescriptor* field, uint64 value) const;
+ void AddFloat (Message* message,
+ const FieldDescriptor* field, float value) const;
+ void AddDouble(Message* message,
+ const FieldDescriptor* field, double value) const;
+ void AddBool (Message* message,
+ const FieldDescriptor* field, bool value) const;
+ void AddString(Message* message,
+ const FieldDescriptor* field, const string& value) const;
+ void AddEnum(Message* message,
+ const FieldDescriptor* field,
+ const EnumValueDescriptor* value) const;
+ void AddEnumValue(Message* message,
+ const FieldDescriptor* field,
+ int value) const;
+ Message* AddMessage(Message* message, const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const;
+ void AddAllocatedMessage(
+ Message* message, const FieldDescriptor* field,
+ Message* new_entry) const;
+
+ const FieldDescriptor* FindKnownExtensionByName(const string& name) const;
+ const FieldDescriptor* FindKnownExtensionByNumber(int number) const;
+
+ bool SupportsUnknownEnumValues() const;
+
+ // This value for arena_offset_ indicates that there is no arena pointer in
+ // this message (e.g., old generated code).
+ static const int kNoArenaPointer = -1;
+
+ // This value for unknown_field_offset_ indicates that there is no
+ // UnknownFieldSet in this message, and that instead, we are using the
+ // Zero-Overhead Arena Pointer trick. When this is the case, arena_offset_
+ // actually indexes to an InternalMetadataWithArena instance, which can return
+ // either an arena pointer or an UnknownFieldSet or both. It is never the case
+ // that unknown_field_offset_ == kUnknownFieldSetInMetadata && arena_offset_
+ // == kNoArenaPointer.
+ static const int kUnknownFieldSetInMetadata = -1;
+
+ protected:
+ void* MutableRawRepeatedField(
+ Message* message, const FieldDescriptor* field, FieldDescriptor::CppType,
+ int ctype, const Descriptor* desc) const;
+
+ const void* GetRawRepeatedField(
+ const Message& message, const FieldDescriptor* field,
+ FieldDescriptor::CppType, int ctype,
+ const Descriptor* desc) const;
+
+ virtual MessageFactory* GetMessageFactory() const;
+
+ virtual void* RepeatedFieldData(
+ Message* message, const FieldDescriptor* field,
+ FieldDescriptor::CppType cpp_type,
+ const Descriptor* message_type) const;
+
+ private:
+ friend class GeneratedMessage;
+
+ // To parse directly into a proto2 generated class, the class GMR_Handlers
+ // needs access to member offsets and hasbits.
+ friend class upb::google_opensource::GMR_Handlers;
+
+ const Descriptor* descriptor_;
+ const Message* default_instance_;
+ const void* default_oneof_instance_;
+ const int* offsets_;
+
+ int has_bits_offset_;
+ int oneof_case_offset_;
+ int unknown_fields_offset_;
+ int extensions_offset_;
+ int arena_offset_;
+ int is_default_instance_offset_;
+ int object_size_;
+
+ static const int kHasNoDefaultInstanceField = -1;
+
+ const DescriptorPool* descriptor_pool_;
+ MessageFactory* message_factory_;
+
+ template <typename Type>
+ inline const Type& GetRaw(const Message& message,
+ const FieldDescriptor* field) const;
+ template <typename Type>
+ inline Type* MutableRaw(Message* message,
+ const FieldDescriptor* field) const;
+ template <typename Type>
+ inline const Type& DefaultRaw(const FieldDescriptor* field) const;
+ template <typename Type>
+ inline const Type& DefaultOneofRaw(const FieldDescriptor* field) const;
+
+ inline const uint32* GetHasBits(const Message& message) const;
+ inline uint32* MutableHasBits(Message* message) const;
+ inline uint32 GetOneofCase(
+ const Message& message,
+ const OneofDescriptor* oneof_descriptor) const;
+ inline uint32* MutableOneofCase(
+ Message* message,
+ const OneofDescriptor* oneof_descriptor) const;
+ inline const ExtensionSet& GetExtensionSet(const Message& message) const;
+ inline ExtensionSet* MutableExtensionSet(Message* message) const;
+ inline Arena* GetArena(Message* message) const;
+ inline const internal::InternalMetadataWithArena&
+ GetInternalMetadataWithArena(const Message& message) const;
+ inline internal::InternalMetadataWithArena*
+ MutableInternalMetadataWithArena(Message* message) const;
+
+ inline bool GetIsDefaultInstance(const Message& message) const;
+
+ inline bool HasBit(const Message& message,
+ const FieldDescriptor* field) const;
+ inline void SetBit(Message* message,
+ const FieldDescriptor* field) const;
+ inline void ClearBit(Message* message,
+ const FieldDescriptor* field) const;
+ inline void SwapBit(Message* message1,
+ Message* message2,
+ const FieldDescriptor* field) const;
+
+ // This function only swaps the field. Should swap corresponding has_bit
+ // before or after using this function.
+ void SwapField(Message* message1,
+ Message* message2,
+ const FieldDescriptor* field) const;
+
+ void SwapOneofField(Message* message1,
+ Message* message2,
+ const OneofDescriptor* oneof_descriptor) const;
+
+ inline bool HasOneofField(const Message& message,
+ const FieldDescriptor* field) const;
+ inline void SetOneofCase(Message* message,
+ const FieldDescriptor* field) const;
+ inline void ClearOneofField(Message* message,
+ const FieldDescriptor* field) const;
+
+ template <typename Type>
+ inline const Type& GetField(const Message& message,
+ const FieldDescriptor* field) const;
+ template <typename Type>
+ inline void SetField(Message* message,
+ const FieldDescriptor* field, const Type& value) const;
+ template <typename Type>
+ inline Type* MutableField(Message* message,
+ const FieldDescriptor* field) const;
+ template <typename Type>
+ inline const Type& GetRepeatedField(const Message& message,
+ const FieldDescriptor* field,
+ int index) const;
+ template <typename Type>
+ inline const Type& GetRepeatedPtrField(const Message& message,
+ const FieldDescriptor* field,
+ int index) const;
+ template <typename Type>
+ inline void SetRepeatedField(Message* message,
+ const FieldDescriptor* field, int index,
+ Type value) const;
+ template <typename Type>
+ inline Type* MutableRepeatedField(Message* message,
+ const FieldDescriptor* field,
+ int index) const;
+ template <typename Type>
+ inline void AddField(Message* message,
+ const FieldDescriptor* field, const Type& value) const;
+ template <typename Type>
+ inline Type* AddField(Message* message,
+ const FieldDescriptor* field) const;
+
+ int GetExtensionNumberOrDie(const Descriptor* type) const;
+
+ // Internal versions of EnumValue API perform no checking. Called after checks
+ // by public methods.
+ void SetEnumValueInternal(Message* message,
+ const FieldDescriptor* field,
+ int value) const;
+ void SetRepeatedEnumValueInternal(Message* message,
+ const FieldDescriptor* field,
+ int index,
+ int value) const;
+ void AddEnumValueInternal(Message* message,
+ const FieldDescriptor* field,
+ int value) const;
+
+
+ Message* UnsafeArenaReleaseMessage(Message* message,
+ const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const;
+
+ void UnsafeArenaSetAllocatedMessage(Message* message,
+ Message* sub_message,
+ const FieldDescriptor* field) const;
+
+ internal::MapFieldBase* MapData(
+ Message* message, const FieldDescriptor* field) const;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(GeneratedMessageReflection);
+};
+
+// Returns the offset of the given field within the given aggregate type.
+// This is equivalent to the ANSI C offsetof() macro. However, according
+// to the C++ standard, offsetof() only works on POD types, and GCC
+// enforces this requirement with a warning. In practice, this rule is
+// unnecessarily strict; there is probably no compiler or platform on
+// which the offsets of the direct fields of a class are non-constant.
+// Fields inherited from superclasses *can* have non-constant offsets,
+// but that's not what this macro will be used for.
+#if defined(__clang__)
+// For Clang we use __builtin_offsetof() and suppress the warning,
+// to avoid Control Flow Integrity and UBSan vptr sanitizers from
+// crashing while trying to validate the invalid reinterpet_casts.
+#define GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(TYPE, FIELD) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(TYPE, FIELD) \
+ _Pragma("clang diagnostic pop")
+#else
+// Note that we calculate relative to the pointer value 16 here since if we
+// just use zero, GCC complains about dereferencing a NULL pointer. We
+// choose 16 rather than some other number just in case the compiler would
+// be confused by an unaligned pointer.
+#define GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(TYPE, FIELD) \
+ static_cast<int>( \
+ reinterpret_cast<const char*>( \
+ &reinterpret_cast<const TYPE*>(16)->FIELD) - \
+ reinterpret_cast<const char*>(16))
+#endif
+
+#define PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET(ONEOF, FIELD) \
+ static_cast<int>( \
+ reinterpret_cast<const char*>(&(ONEOF->FIELD)) \
+ - reinterpret_cast<const char*>(ONEOF))
+
+// There are some places in proto2 where dynamic_cast would be useful as an
+// optimization. For example, take Message::MergeFrom(const Message& other).
+// For a given generated message FooMessage, we generate these two methods:
+// void MergeFrom(const FooMessage& other);
+// void MergeFrom(const Message& other);
+// The former method can be implemented directly in terms of FooMessage's
+// inline accessors, but the latter method must work with the reflection
+// interface. However, if the parameter to the latter method is actually of
+// type FooMessage, then we'd like to be able to just call the other method
+// as an optimization. So, we use dynamic_cast to check this.
+//
+// That said, dynamic_cast requires RTTI, which many people like to disable
+// for performance and code size reasons. When RTTI is not available, we
+// still need to produce correct results. So, in this case we have to fall
+// back to using reflection, which is what we would have done anyway if the
+// objects were not of the exact same class.
+//
+// dynamic_cast_if_available() implements this logic. If RTTI is
+// enabled, it does a dynamic_cast. If RTTI is disabled, it just returns
+// NULL.
+//
+// If you need to compile without RTTI, simply #define GOOGLE_PROTOBUF_NO_RTTI.
+// On MSVC, this should be detected automatically.
+template<typename To, typename From>
+inline To dynamic_cast_if_available(From from) {
+#if defined(GOOGLE_PROTOBUF_NO_RTTI) || (defined(_MSC_VER)&&!defined(_CPPRTTI))
+ return NULL;
+#else
+ return dynamic_cast<To>(from);
+#endif
+}
+
+// Tries to downcast this message to a generated message type.
+// Returns NULL if this class is not an instance of T.
+//
+// This is like dynamic_cast_if_available, except it works even when
+// dynamic_cast is not available by using Reflection. However it only works
+// with Message objects.
+//
+// TODO(haberman): can we remove dynamic_cast_if_available in favor of this?
+template <typename T>
+T* DynamicCastToGenerated(const Message* from) {
+ // Compile-time assert that T is a generated type that has a
+ // default_instance() accessor, but avoid actually calling it.
+ const T&(*get_default_instance)() = &T::default_instance;
+ (void)get_default_instance;
+
+ // Compile-time assert that T is a subclass of google::protobuf::Message.
+ const Message* unused = static_cast<T*>(NULL);
+ (void)unused;
+
+#if defined(GOOGLE_PROTOBUF_NO_RTTI) || \
+ (defined(_MSC_VER) && !defined(_CPPRTTI))
+ bool ok = &T::default_instance() ==
+ from->GetReflection()->GetMessageFactory()->GetPrototype(
+ from->GetDescriptor());
+ return ok ? down_cast<T*>(from) : NULL;
+#else
+ return dynamic_cast<T*>(from);
+#endif
+}
+
+template <typename T>
+T* DynamicCastToGenerated(Message* from) {
+ const Message* message_const = from;
+ return const_cast<T*>(DynamicCastToGenerated<const T>(message_const));
+}
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_GENERATED_MESSAGE_REFLECTION_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection_unittest.cc
new file mode 100644
index 0000000000..6276b66793
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_reflection_unittest.cc
@@ -0,0 +1,919 @@
+// 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.
+//
+// To test GeneratedMessageReflection, we actually let the protocol compiler
+// generate a full protocol message implementation and then test its
+// reflection interface. This is much easier and more maintainable than
+// trying to create our own Message class for GeneratedMessageReflection
+// to wrap.
+//
+// The tests here closely mirror some of the tests in
+// compiler/cpp/unittest, except using the reflection interface
+// rather than generated accessors.
+
+#include <google/protobuf/generated_message_reflection.h>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+// Shorthand to get a FieldDescriptor for a field of unittest::TestAllTypes.
+const FieldDescriptor* F(const string& name) {
+ const FieldDescriptor* result =
+ unittest::TestAllTypes::descriptor()->FindFieldByName(name);
+ GOOGLE_CHECK(result != NULL);
+ return result;
+}
+
+TEST(GeneratedMessageReflectionTest, Defaults) {
+ // Check that all default values are set correctly in the initial message.
+ unittest::TestAllTypes message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+
+ reflection_tester.ExpectClearViaReflection(message);
+
+ const Reflection* reflection = message.GetReflection();
+
+ // Messages should return pointers to default instances until first use.
+ // (This is not checked by ExpectClear() since it is not actually true after
+ // the fields have been set and then cleared.)
+ EXPECT_EQ(&unittest::TestAllTypes::OptionalGroup::default_instance(),
+ &reflection->GetMessage(message, F("optionalgroup")));
+ EXPECT_EQ(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &reflection->GetMessage(message, F("optional_nested_message")));
+ EXPECT_EQ(&unittest::ForeignMessage::default_instance(),
+ &reflection->GetMessage(message, F("optional_foreign_message")));
+ EXPECT_EQ(&unittest_import::ImportMessage::default_instance(),
+ &reflection->GetMessage(message, F("optional_import_message")));
+}
+
+TEST(GeneratedMessageReflectionTest, Accessors) {
+ // Set every field to a unique value then go back and check all those
+ // values.
+ unittest::TestAllTypes message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+
+ reflection_tester.SetAllFieldsViaReflection(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+ reflection_tester.ExpectAllFieldsSetViaReflection(message);
+
+ reflection_tester.ModifyRepeatedFieldsViaReflection(&message);
+ TestUtil::ExpectRepeatedFieldsModified(message);
+}
+
+TEST(GeneratedMessageReflectionTest, GetStringReference) {
+ // Test that GetStringReference() returns the underlying string when it is
+ // a normal string field.
+ unittest::TestAllTypes message;
+ message.set_optional_string("foo");
+ message.add_repeated_string("foo");
+
+ const Reflection* reflection = message.GetReflection();
+ string scratch;
+
+ EXPECT_EQ(&message.optional_string(),
+ &reflection->GetStringReference(message, F("optional_string"), &scratch))
+ << "For simple string fields, GetStringReference() should return a "
+ "reference to the underlying string.";
+ EXPECT_EQ(&message.repeated_string(0),
+ &reflection->GetRepeatedStringReference(message, F("repeated_string"),
+ 0, &scratch))
+ << "For simple string fields, GetRepeatedStringReference() should return "
+ "a reference to the underlying string.";
+}
+
+
+TEST(GeneratedMessageReflectionTest, DefaultsAfterClear) {
+ // Check that after setting all fields and then clearing, getting an
+ // embedded message does NOT return the default instance.
+ unittest::TestAllTypes message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+
+ TestUtil::SetAllFields(&message);
+ message.Clear();
+
+ const Reflection* reflection = message.GetReflection();
+
+ EXPECT_NE(&unittest::TestAllTypes::OptionalGroup::default_instance(),
+ &reflection->GetMessage(message, F("optionalgroup")));
+ EXPECT_NE(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &reflection->GetMessage(message, F("optional_nested_message")));
+ EXPECT_NE(&unittest::ForeignMessage::default_instance(),
+ &reflection->GetMessage(message, F("optional_foreign_message")));
+ EXPECT_NE(&unittest_import::ImportMessage::default_instance(),
+ &reflection->GetMessage(message, F("optional_import_message")));
+}
+
+
+TEST(GeneratedMessageReflectionTest, Swap) {
+ unittest::TestAllTypes message1;
+ unittest::TestAllTypes message2;
+
+ TestUtil::SetAllFields(&message1);
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+
+ TestUtil::ExpectClear(message1);
+ TestUtil::ExpectAllFieldsSet(message2);
+}
+
+TEST(GeneratedMessageReflectionTest, SwapWithBothSet) {
+ unittest::TestAllTypes message1;
+ unittest::TestAllTypes message2;
+
+ TestUtil::SetAllFields(&message1);
+ TestUtil::SetAllFields(&message2);
+ TestUtil::ModifyRepeatedFields(&message2);
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+
+ TestUtil::ExpectRepeatedFieldsModified(message1);
+ TestUtil::ExpectAllFieldsSet(message2);
+
+ message1.set_optional_int32(532819);
+
+ reflection->Swap(&message1, &message2);
+
+ EXPECT_EQ(532819, message2.optional_int32());
+}
+
+TEST(GeneratedMessageReflectionTest, SwapExtensions) {
+ unittest::TestAllExtensions message1;
+ unittest::TestAllExtensions message2;
+
+ TestUtil::SetAllExtensions(&message1);
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+
+ TestUtil::ExpectExtensionsClear(message1);
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(GeneratedMessageReflectionTest, SwapUnknown) {
+ unittest::TestEmptyMessage message1, message2;
+
+ message1.mutable_unknown_fields()->AddVarint(1234, 1);
+
+ EXPECT_EQ(1, message1.unknown_fields().field_count());
+ EXPECT_EQ(0, message2.unknown_fields().field_count());
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+ EXPECT_EQ(0, message1.unknown_fields().field_count());
+ EXPECT_EQ(1, message2.unknown_fields().field_count());
+}
+
+TEST(GeneratedMessageReflectionTest, SwapFields) {
+ unittest::TestAllTypes message1, message2;
+ message1.set_optional_double(12.3);
+ message1.mutable_repeated_int32()->Add(10);
+ message1.mutable_repeated_int32()->Add(20);
+
+ message2.set_optional_string("hello");
+ message2.mutable_repeated_int64()->Add(30);
+
+ vector<const FieldDescriptor*> fields;
+ const Descriptor* descriptor = message1.GetDescriptor();
+ fields.push_back(descriptor->FindFieldByName("optional_double"));
+ fields.push_back(descriptor->FindFieldByName("repeated_int32"));
+ fields.push_back(descriptor->FindFieldByName("optional_string"));
+ fields.push_back(descriptor->FindFieldByName("optional_uint64"));
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->SwapFields(&message1, &message2, fields);
+
+ EXPECT_FALSE(message1.has_optional_double());
+ EXPECT_EQ(0, message1.repeated_int32_size());
+ EXPECT_TRUE(message1.has_optional_string());
+ EXPECT_EQ("hello", message1.optional_string());
+ EXPECT_EQ(0, message1.repeated_int64_size());
+ EXPECT_FALSE(message1.has_optional_uint64());
+
+ EXPECT_TRUE(message2.has_optional_double());
+ EXPECT_EQ(12.3, message2.optional_double());
+ EXPECT_EQ(2, message2.repeated_int32_size());
+ EXPECT_EQ(10, message2.repeated_int32(0));
+ EXPECT_EQ(20, message2.repeated_int32(1));
+ EXPECT_FALSE(message2.has_optional_string());
+ EXPECT_EQ(1, message2.repeated_int64_size());
+ EXPECT_FALSE(message2.has_optional_uint64());
+}
+
+TEST(GeneratedMessageReflectionTest, SwapFieldsAll) {
+ unittest::TestAllTypes message1;
+ unittest::TestAllTypes message2;
+
+ TestUtil::SetAllFields(&message2);
+
+ vector<const FieldDescriptor*> fields;
+ const Reflection* reflection = message1.GetReflection();
+ reflection->ListFields(message2, &fields);
+ reflection->SwapFields(&message1, &message2, fields);
+
+ TestUtil::ExpectAllFieldsSet(message1);
+ TestUtil::ExpectClear(message2);
+}
+
+TEST(GeneratedMessageReflectionTest, SwapFieldsAllExtension) {
+ unittest::TestAllExtensions message1;
+ unittest::TestAllExtensions message2;
+
+ TestUtil::SetAllExtensions(&message1);
+
+ vector<const FieldDescriptor*> fields;
+ const Reflection* reflection = message1.GetReflection();
+ reflection->ListFields(message1, &fields);
+ reflection->SwapFields(&message1, &message2, fields);
+
+ TestUtil::ExpectExtensionsClear(message1);
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(GeneratedMessageReflectionTest, SwapOneof) {
+ unittest::TestOneof2 message1, message2;
+ TestUtil::SetOneof1(&message1);
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+
+ TestUtil::ExpectOneofClear(message1);
+ TestUtil::ExpectOneofSet1(message2);
+}
+
+TEST(GeneratedMessageReflectionTest, SwapOneofBothSet) {
+ unittest::TestOneof2 message1, message2;
+ TestUtil::SetOneof1(&message1);
+ TestUtil::SetOneof2(&message2);
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+
+ TestUtil::ExpectOneofSet2(message1);
+ TestUtil::ExpectOneofSet1(message2);
+}
+
+TEST(GeneratedMessageReflectionTest, SwapFieldsOneof) {
+ unittest::TestOneof2 message1, message2;
+ TestUtil::SetOneof1(&message1);
+
+ vector<const FieldDescriptor*> fields;
+ const Descriptor* descriptor = message1.GetDescriptor();
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ fields.push_back(descriptor->field(i));
+ }
+ const Reflection* reflection = message1.GetReflection();
+ reflection->SwapFields(&message1, &message2, fields);
+
+ TestUtil::ExpectOneofClear(message1);
+ TestUtil::ExpectOneofSet1(message2);
+}
+
+TEST(GeneratedMessageReflectionTest, RemoveLast) {
+ unittest::TestAllTypes message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+
+ TestUtil::SetAllFields(&message);
+
+ reflection_tester.RemoveLastRepeatedsViaReflection(&message);
+
+ TestUtil::ExpectLastRepeatedsRemoved(message);
+}
+
+TEST(GeneratedMessageReflectionTest, RemoveLastExtensions) {
+ unittest::TestAllExtensions message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllExtensions::descriptor());
+
+ TestUtil::SetAllExtensions(&message);
+
+ reflection_tester.RemoveLastRepeatedsViaReflection(&message);
+
+ TestUtil::ExpectLastRepeatedExtensionsRemoved(message);
+}
+
+TEST(GeneratedMessageReflectionTest, ReleaseLast) {
+ unittest::TestAllTypes message;
+ const Descriptor* descriptor = message.GetDescriptor();
+ TestUtil::ReflectionTester reflection_tester(descriptor);
+
+ TestUtil::SetAllFields(&message);
+
+ reflection_tester.ReleaseLastRepeatedsViaReflection(&message, false);
+
+ TestUtil::ExpectLastRepeatedsReleased(message);
+
+ // Now test that we actually release the right message.
+ message.Clear();
+ TestUtil::SetAllFields(&message);
+ ASSERT_EQ(2, message.repeated_foreign_message_size());
+ const protobuf_unittest::ForeignMessage* expected =
+ message.mutable_repeated_foreign_message(1);
+ google::protobuf::scoped_ptr<Message> released(message.GetReflection()->ReleaseLast(
+ &message, descriptor->FindFieldByName("repeated_foreign_message")));
+ EXPECT_EQ(expected, released.get());
+}
+
+TEST(GeneratedMessageReflectionTest, ReleaseLastExtensions) {
+ unittest::TestAllExtensions message;
+ const Descriptor* descriptor = message.GetDescriptor();
+ TestUtil::ReflectionTester reflection_tester(descriptor);
+
+ TestUtil::SetAllExtensions(&message);
+
+ reflection_tester.ReleaseLastRepeatedsViaReflection(&message, true);
+
+ TestUtil::ExpectLastRepeatedExtensionsReleased(message);
+
+ // Now test that we actually release the right message.
+ message.Clear();
+ TestUtil::SetAllExtensions(&message);
+ ASSERT_EQ(2, message.ExtensionSize(
+ unittest::repeated_foreign_message_extension));
+ const protobuf_unittest::ForeignMessage* expected = message.MutableExtension(
+ unittest::repeated_foreign_message_extension, 1);
+ google::protobuf::scoped_ptr<Message> released(message.GetReflection()->ReleaseLast(
+ &message, descriptor->file()->FindExtensionByName(
+ "repeated_foreign_message_extension")));
+ EXPECT_EQ(expected, released.get());
+
+}
+
+TEST(GeneratedMessageReflectionTest, SwapRepeatedElements) {
+ unittest::TestAllTypes message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+
+ TestUtil::SetAllFields(&message);
+
+ // Swap and test that fields are all swapped.
+ reflection_tester.SwapRepeatedsViaReflection(&message);
+ TestUtil::ExpectRepeatedsSwapped(message);
+
+ // Swap back and test that fields are all back to original values.
+ reflection_tester.SwapRepeatedsViaReflection(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+}
+
+TEST(GeneratedMessageReflectionTest, SwapRepeatedElementsExtension) {
+ unittest::TestAllExtensions message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllExtensions::descriptor());
+
+ TestUtil::SetAllExtensions(&message);
+
+ // Swap and test that fields are all swapped.
+ reflection_tester.SwapRepeatedsViaReflection(&message);
+ TestUtil::ExpectRepeatedExtensionsSwapped(message);
+
+ // Swap back and test that fields are all back to original values.
+ reflection_tester.SwapRepeatedsViaReflection(&message);
+ TestUtil::ExpectAllExtensionsSet(message);
+}
+
+TEST(GeneratedMessageReflectionTest, Extensions) {
+ // Set every extension to a unique value then go back and check all those
+ // values.
+ unittest::TestAllExtensions message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllExtensions::descriptor());
+
+ reflection_tester.SetAllFieldsViaReflection(&message);
+ TestUtil::ExpectAllExtensionsSet(message);
+ reflection_tester.ExpectAllFieldsSetViaReflection(message);
+
+ reflection_tester.ModifyRepeatedFieldsViaReflection(&message);
+ TestUtil::ExpectRepeatedExtensionsModified(message);
+}
+
+TEST(GeneratedMessageReflectionTest, FindExtensionTypeByNumber) {
+ const Reflection* reflection =
+ unittest::TestAllExtensions::default_instance().GetReflection();
+
+ const FieldDescriptor* extension1 =
+ unittest::TestAllExtensions::descriptor()->file()->FindExtensionByName(
+ "optional_int32_extension");
+ const FieldDescriptor* extension2 =
+ unittest::TestAllExtensions::descriptor()->file()->FindExtensionByName(
+ "repeated_string_extension");
+
+ EXPECT_EQ(extension1,
+ reflection->FindKnownExtensionByNumber(extension1->number()));
+ EXPECT_EQ(extension2,
+ reflection->FindKnownExtensionByNumber(extension2->number()));
+
+ // Non-existent extension.
+ EXPECT_TRUE(reflection->FindKnownExtensionByNumber(62341) == NULL);
+
+ // Extensions of TestAllExtensions should not show up as extensions of
+ // other types.
+ EXPECT_TRUE(unittest::TestAllTypes::default_instance().GetReflection()->
+ FindKnownExtensionByNumber(extension1->number()) == NULL);
+}
+
+TEST(GeneratedMessageReflectionTest, FindKnownExtensionByName) {
+ const Reflection* reflection =
+ unittest::TestAllExtensions::default_instance().GetReflection();
+
+ const FieldDescriptor* extension1 =
+ unittest::TestAllExtensions::descriptor()->file()->FindExtensionByName(
+ "optional_int32_extension");
+ const FieldDescriptor* extension2 =
+ unittest::TestAllExtensions::descriptor()->file()->FindExtensionByName(
+ "repeated_string_extension");
+
+ EXPECT_EQ(extension1,
+ reflection->FindKnownExtensionByName(extension1->full_name()));
+ EXPECT_EQ(extension2,
+ reflection->FindKnownExtensionByName(extension2->full_name()));
+
+ // Non-existent extension.
+ EXPECT_TRUE(reflection->FindKnownExtensionByName("no_such_ext") == NULL);
+
+ // Extensions of TestAllExtensions should not show up as extensions of
+ // other types.
+ EXPECT_TRUE(unittest::TestAllTypes::default_instance().GetReflection()->
+ FindKnownExtensionByName(extension1->full_name()) == NULL);
+}
+
+TEST(GeneratedMessageReflectionTest, SetAllocatedMessageTest) {
+ unittest::TestAllTypes from_message1;
+ unittest::TestAllTypes from_message2;
+ unittest::TestAllTypes to_message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+ reflection_tester.SetAllFieldsViaReflection(&from_message1);
+ reflection_tester.SetAllFieldsViaReflection(&from_message2);
+
+ // Before moving fields, we expect the nested messages to be NULL.
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::IS_NULL);
+
+ // After fields are moved we should get non-NULL releases.
+ reflection_tester.SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ &from_message1, &to_message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // Another move to make sure that we can SetAllocated several times.
+ reflection_tester.SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ &from_message2, &to_message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // After SetAllocatedOptionalMessageFieldsToNullViaReflection() we expect the
+ // releases to be NULL again.
+ reflection_tester.SetAllocatedOptionalMessageFieldsToNullViaReflection(
+ &to_message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::IS_NULL);
+}
+
+TEST(GeneratedMessageReflectionTest, SetAllocatedExtensionMessageTest) {
+ unittest::TestAllExtensions from_message1;
+ unittest::TestAllExtensions from_message2;
+ unittest::TestAllExtensions to_message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllExtensions::descriptor());
+ reflection_tester.SetAllFieldsViaReflection(&from_message1);
+ reflection_tester.SetAllFieldsViaReflection(&from_message2);
+
+ // Before moving fields, we expect the nested messages to be NULL.
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::IS_NULL);
+
+ // After fields are moved we should get non-NULL releases.
+ reflection_tester.SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ &from_message1, &to_message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // Another move to make sure that we can SetAllocated several times.
+ reflection_tester.SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ &from_message2, &to_message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // After SetAllocatedOptionalMessageFieldsToNullViaReflection() we expect the
+ // releases to be NULL again.
+ reflection_tester.SetAllocatedOptionalMessageFieldsToNullViaReflection(
+ &to_message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &to_message, TestUtil::ReflectionTester::IS_NULL);
+}
+
+TEST(GeneratedMessageReflectionTest, AddRepeatedMessage) {
+ unittest::TestAllTypes message;
+
+ const Reflection* reflection = message.GetReflection();
+ const Reflection* nested_reflection =
+ unittest::TestAllTypes::NestedMessage::default_instance().GetReflection();
+
+ const FieldDescriptor* nested_bb =
+ unittest::TestAllTypes::NestedMessage::descriptor()->FindFieldByName(
+ "bb");
+
+ Message* nested = reflection->AddMessage(
+ &message, F("repeated_nested_message"));
+ nested_reflection->SetInt32(nested, nested_bb, 11);
+
+ EXPECT_EQ(11, message.repeated_nested_message(0).bb());
+}
+
+TEST(GeneratedMessageReflectionTest, MutableRepeatedMessage) {
+ unittest::TestAllTypes message;
+
+ const Reflection* reflection = message.GetReflection();
+ const Reflection* nested_reflection =
+ unittest::TestAllTypes::NestedMessage::default_instance().GetReflection();
+
+ const FieldDescriptor* nested_bb =
+ unittest::TestAllTypes::NestedMessage::descriptor()->FindFieldByName(
+ "bb");
+
+ message.add_repeated_nested_message()->set_bb(12);
+
+ Message* nested = reflection->MutableRepeatedMessage(
+ &message, F("repeated_nested_message"), 0);
+ EXPECT_EQ(12, nested_reflection->GetInt32(*nested, nested_bb));
+ nested_reflection->SetInt32(nested, nested_bb, 13);
+ EXPECT_EQ(13, message.repeated_nested_message(0).bb());
+}
+
+TEST(GeneratedMessageReflectionTest, AddAllocatedMessage) {
+ unittest::TestAllTypes message;
+
+ const Reflection* reflection = message.GetReflection();
+
+ unittest::TestAllTypes::NestedMessage* nested =
+ new unittest::TestAllTypes::NestedMessage();
+ nested->set_bb(11);
+ reflection->AddAllocatedMessage(&message, F("repeated_nested_message"), nested);
+ EXPECT_EQ(1, message.repeated_nested_message_size());
+ EXPECT_EQ(11, message.repeated_nested_message(0).bb());
+}
+
+TEST(GeneratedMessageReflectionTest, ListFieldsOneOf) {
+ unittest::TestOneof2 message;
+ TestUtil::SetOneof1(&message);
+
+ const Reflection* reflection = message.GetReflection();
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message, &fields);
+ EXPECT_EQ(4, fields.size());
+}
+
+TEST(GeneratedMessageReflectionTest, Oneof) {
+ unittest::TestOneof2 message;
+ const Descriptor* descriptor = message.GetDescriptor();
+ const Reflection* reflection = message.GetReflection();
+
+ // Check default values.
+ EXPECT_EQ(0, reflection->GetInt32(
+ message, descriptor->FindFieldByName("foo_int")));
+ EXPECT_EQ("", reflection->GetString(
+ message, descriptor->FindFieldByName("foo_string")));
+ EXPECT_EQ("", reflection->GetString(
+ message, descriptor->FindFieldByName("foo_cord")));
+ EXPECT_EQ("", reflection->GetString(
+ message, descriptor->FindFieldByName("foo_string_piece")));
+ EXPECT_EQ("", reflection->GetString(
+ message, descriptor->FindFieldByName("foo_bytes")));
+ EXPECT_EQ(unittest::TestOneof2::FOO, reflection->GetEnum(
+ message, descriptor->FindFieldByName("foo_enum"))->number());
+ EXPECT_EQ(&unittest::TestOneof2::NestedMessage::default_instance(),
+ &reflection->GetMessage(
+ message, descriptor->FindFieldByName("foo_message")));
+ EXPECT_EQ(&unittest::TestOneof2::FooGroup::default_instance(),
+ &reflection->GetMessage(
+ message, descriptor->FindFieldByName("foogroup")));
+ EXPECT_NE(&unittest::TestOneof2::FooGroup::default_instance(),
+ &reflection->GetMessage(
+ message, descriptor->FindFieldByName("foo_lazy_message")));
+ EXPECT_EQ(5, reflection->GetInt32(
+ message, descriptor->FindFieldByName("bar_int")));
+ EXPECT_EQ("STRING", reflection->GetString(
+ message, descriptor->FindFieldByName("bar_string")));
+ EXPECT_EQ("CORD", reflection->GetString(
+ message, descriptor->FindFieldByName("bar_cord")));
+ EXPECT_EQ("SPIECE", reflection->GetString(
+ message, descriptor->FindFieldByName("bar_string_piece")));
+ EXPECT_EQ("BYTES", reflection->GetString(
+ message, descriptor->FindFieldByName("bar_bytes")));
+ EXPECT_EQ(unittest::TestOneof2::BAR, reflection->GetEnum(
+ message, descriptor->FindFieldByName("bar_enum"))->number());
+
+ // Check Set functions.
+ reflection->SetInt32(
+ &message, descriptor->FindFieldByName("foo_int"), 123);
+ EXPECT_EQ(123, reflection->GetInt32(
+ message, descriptor->FindFieldByName("foo_int")));
+ reflection->SetString(
+ &message, descriptor->FindFieldByName("foo_string"), "abc");
+ EXPECT_EQ("abc", reflection->GetString(
+ message, descriptor->FindFieldByName("foo_string")));
+ reflection->SetString(
+ &message, descriptor->FindFieldByName("foo_bytes"), "bytes");
+ EXPECT_EQ("bytes", reflection->GetString(
+ message, descriptor->FindFieldByName("foo_bytes")));
+ reflection->SetString(
+ &message, descriptor->FindFieldByName("bar_cord"), "change_cord");
+ EXPECT_EQ("change_cord", reflection->GetString(
+ message, descriptor->FindFieldByName("bar_cord")));
+ reflection->SetString(
+ &message, descriptor->FindFieldByName("bar_string_piece"),
+ "change_spiece");
+ EXPECT_EQ("change_spiece", reflection->GetString(
+ message, descriptor->FindFieldByName("bar_string_piece")));
+}
+
+TEST(GeneratedMessageReflectionTest, SetAllocatedOneofMessageTest) {
+ unittest::TestOneof2 from_message1;
+ unittest::TestOneof2 from_message2;
+ unittest::TestOneof2 to_message;
+ const Descriptor* descriptor = unittest::TestOneof2::descriptor();
+ const Reflection* reflection = to_message.GetReflection();
+
+ Message* released = reflection->ReleaseMessage(
+ &to_message, descriptor->FindFieldByName("foo_lazy_message"));
+ EXPECT_TRUE(released == NULL);
+ released = reflection->ReleaseMessage(
+ &to_message, descriptor->FindFieldByName("foo_message"));
+ EXPECT_TRUE(released == NULL);
+
+ TestUtil::ReflectionTester::SetOneofViaReflection(&from_message1);
+ TestUtil::ReflectionTester::ExpectOneofSetViaReflection(from_message1);
+
+ TestUtil::ReflectionTester::
+ SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ &from_message1, &to_message);
+ const Message& sub_message = reflection->GetMessage(
+ to_message, descriptor->FindFieldByName("foo_lazy_message"));
+ released = reflection->ReleaseMessage(
+ &to_message, descriptor->FindFieldByName("foo_lazy_message"));
+ EXPECT_TRUE(released != NULL);
+ EXPECT_EQ(&sub_message, released);
+ delete released;
+
+ TestUtil::ReflectionTester::SetOneofViaReflection(&from_message2);
+
+ reflection->MutableMessage(
+ &from_message2, descriptor->FindFieldByName("foo_message"));
+
+ TestUtil::ReflectionTester::
+ SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ &from_message2, &to_message);
+
+ const Message& sub_message2 = reflection->GetMessage(
+ to_message, descriptor->FindFieldByName("foo_message"));
+ released = reflection->ReleaseMessage(
+ &to_message, descriptor->FindFieldByName("foo_message"));
+ EXPECT_TRUE(released != NULL);
+ EXPECT_EQ(&sub_message2, released);
+ delete released;
+}
+
+TEST(GeneratedMessageReflectionTest, ReleaseMessageTest) {
+ unittest::TestAllTypes message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+
+ // When nothing is set, we expect all released messages to be NULL.
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &message, TestUtil::ReflectionTester::IS_NULL);
+
+ // After fields are set we should get non-NULL releases.
+ reflection_tester.SetAllFieldsViaReflection(&message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // After Clear() we may or may not get a message from ReleaseMessage().
+ // This is implementation specific.
+ reflection_tester.SetAllFieldsViaReflection(&message);
+ message.Clear();
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &message, TestUtil::ReflectionTester::CAN_BE_NULL);
+
+ // Test a different code path for setting after releasing.
+ TestUtil::SetAllFields(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+}
+
+TEST(GeneratedMessageReflectionTest, ReleaseExtensionMessageTest) {
+ unittest::TestAllExtensions message;
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllExtensions::descriptor());
+
+ // When nothing is set, we expect all released messages to be NULL.
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &message, TestUtil::ReflectionTester::IS_NULL);
+
+ // After fields are set we should get non-NULL releases.
+ reflection_tester.SetAllFieldsViaReflection(&message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // After Clear() we may or may not get a message from ReleaseMessage().
+ // This is implementation specific.
+ reflection_tester.SetAllFieldsViaReflection(&message);
+ message.Clear();
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ &message, TestUtil::ReflectionTester::CAN_BE_NULL);
+
+ // Test a different code path for setting after releasing.
+ TestUtil::SetAllExtensions(&message);
+ TestUtil::ExpectAllExtensionsSet(message);
+}
+
+TEST(GeneratedMessageReflectionTest, ReleaseOneofMessageTest) {
+ unittest::TestOneof2 message;
+ TestUtil::ReflectionTester::SetOneofViaReflection(&message);
+
+ const Descriptor* descriptor = unittest::TestOneof2::descriptor();
+ const Reflection* reflection = message.GetReflection();
+ const Message& sub_message = reflection->GetMessage(
+ message, descriptor->FindFieldByName("foo_lazy_message"));
+ Message* released = reflection->ReleaseMessage(
+ &message, descriptor->FindFieldByName("foo_lazy_message"));
+
+ EXPECT_TRUE(released != NULL);
+ EXPECT_EQ(&sub_message, released);
+ delete released;
+
+ released = reflection->ReleaseMessage(
+ &message, descriptor->FindFieldByName("foo_lazy_message"));
+ EXPECT_TRUE(released == NULL);
+}
+
+TEST(GeneratedMessageReflectionTest, ArenaReleaseMessageTest) {
+ ::google::protobuf::Arena arena;
+ unittest::TestAllTypes* message =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllTypes>(&arena);
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllTypes::descriptor());
+
+ // When nothing is set, we expect all released messages to be NULL.
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ message, TestUtil::ReflectionTester::IS_NULL);
+
+ // After fields are set we should get non-NULL releases.
+ reflection_tester.SetAllFieldsViaReflection(message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // After Clear() we may or may not get a message from ReleaseMessage().
+ // This is implementation specific.
+ reflection_tester.SetAllFieldsViaReflection(message);
+ message->Clear();
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ message, TestUtil::ReflectionTester::CAN_BE_NULL);
+}
+
+TEST(GeneratedMessageReflectionTest, ArenaReleaseExtensionMessageTest) {
+ ::google::protobuf::Arena arena;
+ unittest::TestAllExtensions* message =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena);
+ TestUtil::ReflectionTester reflection_tester(
+ unittest::TestAllExtensions::descriptor());
+
+ // When nothing is set, we expect all released messages to be NULL.
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ message, TestUtil::ReflectionTester::IS_NULL);
+
+ // After fields are set we should get non-NULL releases.
+ reflection_tester.SetAllFieldsViaReflection(message);
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ message, TestUtil::ReflectionTester::NOT_NULL);
+
+ // After Clear() we may or may not get a message from ReleaseMessage().
+ // This is implementation specific.
+ reflection_tester.SetAllFieldsViaReflection(message);
+ message->Clear();
+ reflection_tester.ExpectMessagesReleasedViaReflection(
+ message, TestUtil::ReflectionTester::CAN_BE_NULL);
+}
+
+TEST(GeneratedMessageReflectionTest, ArenaReleaseOneofMessageTest) {
+ ::google::protobuf::Arena arena;
+ unittest::TestOneof2* message =
+ ::google::protobuf::Arena::CreateMessage<unittest::TestOneof2>(&arena);
+ TestUtil::ReflectionTester::SetOneofViaReflection(message);
+
+ const Descriptor* descriptor = unittest::TestOneof2::descriptor();
+ const Reflection* reflection = message->GetReflection();
+ Message* released = reflection->ReleaseMessage(
+ message, descriptor->FindFieldByName("foo_lazy_message"));
+
+ EXPECT_TRUE(released != NULL);
+ delete released;
+
+ released = reflection->ReleaseMessage(
+ message, descriptor->FindFieldByName("foo_lazy_message"));
+ EXPECT_TRUE(released == NULL);
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+
+TEST(GeneratedMessageReflectionTest, UsageErrors) {
+ unittest::TestAllTypes message;
+ const Reflection* reflection = message.GetReflection();
+ const Descriptor* descriptor = message.GetDescriptor();
+
+#define f(NAME) descriptor->FindFieldByName(NAME)
+
+ // Testing every single failure mode would be too much work. Let's just
+ // check a few.
+ EXPECT_DEATH(
+ reflection->GetInt32(
+ message, descriptor->FindFieldByName("optional_int64")),
+ "Protocol Buffer reflection usage error:\n"
+ " Method : google::protobuf::Reflection::GetInt32\n"
+ " Message type: protobuf_unittest\\.TestAllTypes\n"
+ " Field : protobuf_unittest\\.TestAllTypes\\.optional_int64\n"
+ " Problem : Field is not the right type for this message:\n"
+ " Expected : CPPTYPE_INT32\n"
+ " Field type: CPPTYPE_INT64");
+ EXPECT_DEATH(
+ reflection->GetInt32(
+ message, descriptor->FindFieldByName("repeated_int32")),
+ "Protocol Buffer reflection usage error:\n"
+ " Method : google::protobuf::Reflection::GetInt32\n"
+ " Message type: protobuf_unittest.TestAllTypes\n"
+ " Field : protobuf_unittest.TestAllTypes.repeated_int32\n"
+ " Problem : Field is repeated; the method requires a singular field.");
+ EXPECT_DEATH(
+ reflection->GetInt32(
+ message, unittest::ForeignMessage::descriptor()->FindFieldByName("c")),
+ "Protocol Buffer reflection usage error:\n"
+ " Method : google::protobuf::Reflection::GetInt32\n"
+ " Message type: protobuf_unittest.TestAllTypes\n"
+ " Field : protobuf_unittest.ForeignMessage.c\n"
+ " Problem : Field does not match message type.");
+ EXPECT_DEATH(
+ reflection->HasField(
+ message, unittest::ForeignMessage::descriptor()->FindFieldByName("c")),
+ "Protocol Buffer reflection usage error:\n"
+ " Method : google::protobuf::Reflection::HasField\n"
+ " Message type: protobuf_unittest.TestAllTypes\n"
+ " Field : protobuf_unittest.ForeignMessage.c\n"
+ " Problem : Field does not match message type.");
+
+#undef f
+}
+
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.cc
new file mode 100644
index 0000000000..7ad6d61cbc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.cc
@@ -0,0 +1,84 @@
+// 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.
+
+#include <google/protobuf/generated_message_util.h>
+
+#include <limits>
+
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+double Infinity() {
+ return std::numeric_limits<double>::infinity();
+}
+double NaN() {
+ return std::numeric_limits<double>::quiet_NaN();
+}
+
+const ::std::string* empty_string_;
+GOOGLE_PROTOBUF_DECLARE_ONCE(empty_string_once_init_);
+
+void DeleteEmptyString() {
+ delete empty_string_;
+}
+
+void InitEmptyString() {
+ empty_string_ = new string;
+ OnShutdown(&DeleteEmptyString);
+}
+
+int StringSpaceUsedExcludingSelf(const string& str) {
+ const void* start = &str;
+ const void* end = &str + 1;
+ if (start <= str.data() && str.data() < end) {
+ // The string's data is stored inside the string object itself.
+ return 0;
+ } else {
+ return str.capacity();
+ }
+}
+
+
+
+void MergeFromFail(const char* file, int line) {
+ GOOGLE_CHECK(false) << file << ":" << line;
+ // Open-source GOOGLE_CHECK(false) is not NORETURN.
+ exit(1);
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.h
new file mode 100644
index 0000000000..8967726e77
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/generated_message_util.h
@@ -0,0 +1,127 @@
+// 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 miscellaneous helper code used by generated code --
+// including lite types -- but which should not be used directly by users.
+
+#ifndef GOOGLE_PROTOBUF_GENERATED_MESSAGE_UTIL_H__
+#define GOOGLE_PROTOBUF_GENERATED_MESSAGE_UTIL_H__
+
+#include <assert.h>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/once.h>
+
+namespace google {
+
+namespace protobuf {
+
+class Arena;
+namespace io { class CodedInputStream; }
+
+namespace internal {
+
+
+// Annotation for the compiler to emit a deprecation message if a field marked
+// with option 'deprecated=true' is used in the code, or for other things in
+// generated code which are deprecated.
+//
+// For internal use in the pb.cc files, deprecation warnings are suppressed
+// there.
+#undef DEPRECATED_PROTOBUF_FIELD
+#define PROTOBUF_DEPRECATED
+
+#define GOOGLE_PROTOBUF_DEPRECATED_ATTR
+
+
+// Constants for special floating point values.
+LIBPROTOBUF_EXPORT double Infinity();
+LIBPROTOBUF_EXPORT double NaN();
+
+// TODO(jieluo): Change to template. We have tried to use template,
+// but it causes net/rpc/python:rpcutil_test fail (the empty string will
+// init twice). It may related to swig. Change to template after we
+// found the solution.
+
+// Default empty string object. Don't use the pointer directly. Instead, call
+// GetEmptyString() to get the reference.
+LIBPROTOBUF_EXPORT extern const ::std::string* empty_string_;
+LIBPROTOBUF_EXPORT extern ProtobufOnceType empty_string_once_init_;
+LIBPROTOBUF_EXPORT void InitEmptyString();
+
+
+LIBPROTOBUF_EXPORT inline const ::std::string& GetEmptyStringAlreadyInited() {
+ assert(empty_string_ != NULL);
+ return *empty_string_;
+}
+LIBPROTOBUF_EXPORT inline const ::std::string& GetEmptyString() {
+ ::google::protobuf::GoogleOnceInit(&empty_string_once_init_, &InitEmptyString);
+ return GetEmptyStringAlreadyInited();
+}
+
+LIBPROTOBUF_EXPORT int StringSpaceUsedExcludingSelf(const string& str);
+
+
+// True if IsInitialized() is true for all elements of t. Type is expected
+// to be a RepeatedPtrField<some message type>. It's useful to have this
+// helper here to keep the protobuf compiler from ever having to emit loops in
+// IsInitialized() methods. We want the C++ compiler to inline this or not
+// as it sees fit.
+template <class Type> bool AllAreInitialized(const Type& t) {
+ for (int i = t.size(); --i >= 0; ) {
+ if (!t.Get(i).IsInitialized()) return false;
+ }
+ return true;
+}
+
+class ArenaString;
+
+// Read a length (varint32), followed by a string, from *input. Return a
+// pointer to a copy of the string that resides in *arena. Requires both
+// args to be non-NULL. If something goes wrong while reading the data
+// then NULL is returned (e.g., input does not start with a valid varint).
+LIBPROTOBUF_EXPORT ArenaString* ReadArenaString(
+ ::google::protobuf::io::CodedInputStream* input,
+ ::google::protobuf::Arena* arena);
+
+// Helper function to crash on merge failure.
+// Moved out of generated code to reduce binary size.
+LIBPROTOBUF_EXPORT void MergeFromFail(const char* file, int line) GOOGLE_ATTRIBUTE_NORETURN;
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_GENERATED_MESSAGE_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.cc
new file mode 100644
index 0000000000..a5675e79f8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.cc
@@ -0,0 +1,956 @@
+// 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 implementation is heavily optimized to make reads and writes
+// of small values (especially varints) as fast as possible. In
+// particular, we optimize for the common case that a read or a write
+// will not cross the end of the buffer, since we can avoid a lot
+// of branching in this case.
+
+#include <google/protobuf/io/coded_stream_inl.h>
+#include <algorithm>
+#include <utility>
+#include <limits.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+namespace {
+
+static const int kMaxVarintBytes = 10;
+static const int kMaxVarint32Bytes = 5;
+
+
+inline bool NextNonEmpty(ZeroCopyInputStream* input,
+ const void** data, int* size) {
+ bool success;
+ do {
+ success = input->Next(data, size);
+ } while (success && *size == 0);
+ return success;
+}
+
+} // namespace
+
+// CodedInputStream ==================================================
+
+CodedInputStream::~CodedInputStream() {
+ if (input_ != NULL) {
+ BackUpInputToCurrentPosition();
+ }
+
+ if (total_bytes_warning_threshold_ == -2) {
+ GOOGLE_LOG(WARNING) << "The total number of bytes read was " << total_bytes_read_;
+ }
+}
+
+// Static.
+int CodedInputStream::default_recursion_limit_ = 100;
+
+
+void CodedOutputStream::EnableAliasing(bool enabled) {
+ aliasing_enabled_ = enabled && output_->AllowsAliasing();
+}
+
+void CodedInputStream::BackUpInputToCurrentPosition() {
+ int backup_bytes = BufferSize() + buffer_size_after_limit_ + overflow_bytes_;
+ if (backup_bytes > 0) {
+ input_->BackUp(backup_bytes);
+
+ // total_bytes_read_ doesn't include overflow_bytes_.
+ total_bytes_read_ -= BufferSize() + buffer_size_after_limit_;
+ buffer_end_ = buffer_;
+ buffer_size_after_limit_ = 0;
+ overflow_bytes_ = 0;
+ }
+}
+
+inline void CodedInputStream::RecomputeBufferLimits() {
+ buffer_end_ += buffer_size_after_limit_;
+ int closest_limit = std::min(current_limit_, total_bytes_limit_);
+ if (closest_limit < total_bytes_read_) {
+ // The limit position is in the current buffer. We must adjust
+ // the buffer size accordingly.
+ buffer_size_after_limit_ = total_bytes_read_ - closest_limit;
+ buffer_end_ -= buffer_size_after_limit_;
+ } else {
+ buffer_size_after_limit_ = 0;
+ }
+}
+
+CodedInputStream::Limit CodedInputStream::PushLimit(int byte_limit) {
+ // Current position relative to the beginning of the stream.
+ int current_position = CurrentPosition();
+
+ Limit old_limit = current_limit_;
+
+ // security: byte_limit is possibly evil, so check for negative values
+ // and overflow.
+ if (byte_limit >= 0 &&
+ byte_limit <= INT_MAX - current_position) {
+ current_limit_ = current_position + byte_limit;
+ } else {
+ // Negative or overflow.
+ current_limit_ = INT_MAX;
+ }
+
+ // We need to enforce all limits, not just the new one, so if the previous
+ // limit was before the new requested limit, we continue to enforce the
+ // previous limit.
+ current_limit_ = std::min(current_limit_, old_limit);
+
+ RecomputeBufferLimits();
+ return old_limit;
+}
+
+void CodedInputStream::PopLimit(Limit limit) {
+ // The limit passed in is actually the *old* limit, which we returned from
+ // PushLimit().
+ current_limit_ = limit;
+ RecomputeBufferLimits();
+
+ // We may no longer be at a legitimate message end. ReadTag() needs to be
+ // called again to find out.
+ legitimate_message_end_ = false;
+}
+
+std::pair<CodedInputStream::Limit, int>
+CodedInputStream::IncrementRecursionDepthAndPushLimit(int byte_limit) {
+ return std::make_pair(PushLimit(byte_limit), --recursion_budget_);
+}
+
+CodedInputStream::Limit CodedInputStream::ReadLengthAndPushLimit() {
+ uint32 length;
+ return PushLimit(ReadVarint32(&length) ? length : 0);
+}
+
+bool CodedInputStream::DecrementRecursionDepthAndPopLimit(Limit limit) {
+ bool result = ConsumedEntireMessage();
+ PopLimit(limit);
+ GOOGLE_DCHECK_LT(recursion_budget_, recursion_limit_);
+ ++recursion_budget_;
+ return result;
+}
+
+bool CodedInputStream::CheckEntireMessageConsumedAndPopLimit(Limit limit) {
+ bool result = ConsumedEntireMessage();
+ PopLimit(limit);
+ return result;
+}
+
+int CodedInputStream::BytesUntilLimit() const {
+ if (current_limit_ == INT_MAX) return -1;
+ int current_position = CurrentPosition();
+
+ return current_limit_ - current_position;
+}
+
+void CodedInputStream::SetTotalBytesLimit(
+ int total_bytes_limit, int warning_threshold) {
+ // Make sure the limit isn't already past, since this could confuse other
+ // code.
+ int current_position = CurrentPosition();
+ total_bytes_limit_ = std::max(current_position, total_bytes_limit);
+ if (warning_threshold >= 0) {
+ total_bytes_warning_threshold_ = warning_threshold;
+ } else {
+ // warning_threshold is negative
+ total_bytes_warning_threshold_ = -1;
+ }
+ RecomputeBufferLimits();
+}
+
+int CodedInputStream::BytesUntilTotalBytesLimit() const {
+ if (total_bytes_limit_ == INT_MAX) return -1;
+ return total_bytes_limit_ - CurrentPosition();
+}
+
+void CodedInputStream::PrintTotalBytesLimitError() {
+ GOOGLE_LOG(ERROR) << "A protocol message was rejected because it was too "
+ "big (more than " << total_bytes_limit_
+ << " bytes). To increase the limit (or to disable these "
+ "warnings), see CodedInputStream::SetTotalBytesLimit() "
+ "in google/protobuf/io/coded_stream.h.";
+}
+
+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;
+ }
+
+ if (buffer_size_after_limit_ > 0) {
+ // We hit a limit inside this buffer. Advance to the limit and fail.
+ Advance(original_buffer_size);
+ return false;
+ }
+
+ count -= original_buffer_size;
+ buffer_ = NULL;
+ buffer_end_ = buffer_;
+
+ // Make sure this skip doesn't try to skip past the current limit.
+ int closest_limit = std::min(current_limit_, total_bytes_limit_);
+ int bytes_until_limit = closest_limit - total_bytes_read_;
+ if (bytes_until_limit < count) {
+ // We hit the limit. Skip up to it then fail.
+ if (bytes_until_limit > 0) {
+ total_bytes_read_ = closest_limit;
+ input_->Skip(bytes_until_limit);
+ }
+ return false;
+ }
+
+ total_bytes_read_ += count;
+ return input_->Skip(count);
+}
+
+bool CodedInputStream::GetDirectBufferPointer(const void** data, int* size) {
+ if (BufferSize() == 0 && !Refresh()) return false;
+
+ *data = buffer_;
+ *size = BufferSize();
+ return true;
+}
+
+bool CodedInputStream::ReadRaw(void* buffer, int size) {
+ return InternalReadRawInline(buffer, size);
+}
+
+bool CodedInputStream::ReadString(string* buffer, int size) {
+ if (size < 0) return false; // security: size is often user-supplied
+ return InternalReadStringInline(buffer, size);
+}
+
+bool CodedInputStream::ReadStringFallback(string* buffer, int size) {
+ if (!buffer->empty()) {
+ buffer->clear();
+ }
+
+ int closest_limit = std::min(current_limit_, total_bytes_limit_);
+ if (closest_limit != INT_MAX) {
+ int bytes_to_limit = closest_limit - CurrentPosition();
+ if (bytes_to_limit > 0 && size > 0 && size <= bytes_to_limit) {
+ buffer->reserve(size);
+ }
+ }
+
+ int current_buffer_size;
+ while ((current_buffer_size = BufferSize()) < size) {
+ // Some STL implementations "helpfully" crash on buffer->append(NULL, 0).
+ if (current_buffer_size != 0) {
+ // Note: string1.append(string2) is O(string2.size()) (as opposed to
+ // O(string1.size() + string2.size()), which would be bad).
+ buffer->append(reinterpret_cast<const char*>(buffer_),
+ current_buffer_size);
+ }
+ size -= current_buffer_size;
+ Advance(current_buffer_size);
+ if (!Refresh()) return false;
+ }
+
+ buffer->append(reinterpret_cast<const char*>(buffer_), size);
+ Advance(size);
+
+ return true;
+}
+
+
+bool CodedInputStream::ReadLittleEndian32Fallback(uint32* value) {
+ uint8 bytes[sizeof(*value)];
+
+ const uint8* ptr;
+ if (BufferSize() >= sizeof(*value)) {
+ // Fast path: Enough bytes in the buffer to read directly.
+ ptr = buffer_;
+ Advance(sizeof(*value));
+ } else {
+ // Slow path: Had to read past the end of the buffer.
+ if (!ReadRaw(bytes, sizeof(*value))) return false;
+ ptr = bytes;
+ }
+ ReadLittleEndian32FromArray(ptr, value);
+ return true;
+}
+
+bool CodedInputStream::ReadLittleEndian64Fallback(uint64* value) {
+ uint8 bytes[sizeof(*value)];
+
+ const uint8* ptr;
+ if (BufferSize() >= sizeof(*value)) {
+ // Fast path: Enough bytes in the buffer to read directly.
+ ptr = buffer_;
+ Advance(sizeof(*value));
+ } else {
+ // Slow path: Had to read past the end of the buffer.
+ if (!ReadRaw(bytes, sizeof(*value))) return false;
+ ptr = bytes;
+ }
+ ReadLittleEndian64FromArray(ptr, value);
+ return true;
+}
+
+namespace {
+
+// Read a varint from the given buffer, write it to *value, and return a pair.
+// The first part of the pair is true iff the read was successful. The second
+// part is buffer + (number of bytes read). This function is always inlined,
+// so returning a pair is costless.
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE ::std::pair<bool, const uint8*> ReadVarint32FromArray(
+ uint32 first_byte, const uint8* buffer,
+ uint32* value);
+inline ::std::pair<bool, const uint8*> ReadVarint32FromArray(
+ uint32 first_byte, const uint8* buffer, uint32* value) {
+ // Fast path: We have enough bytes left in the buffer to guarantee that
+ // this read won't cross the end, so we can skip the checks.
+ GOOGLE_DCHECK_EQ(*buffer, first_byte);
+ GOOGLE_DCHECK_EQ(first_byte & 0x80, 0x80) << first_byte;
+ const uint8* ptr = buffer;
+ uint32 b;
+ uint32 result = first_byte - 0x80;
+ ++ptr; // We just processed the first byte. Move on to the second.
+ b = *(ptr++); result += b << 7; if (!(b & 0x80)) goto done;
+ result -= 0x80 << 7;
+ b = *(ptr++); result += b << 14; if (!(b & 0x80)) goto done;
+ result -= 0x80 << 14;
+ b = *(ptr++); result += b << 21; if (!(b & 0x80)) goto done;
+ result -= 0x80 << 21;
+ b = *(ptr++); result += b << 28; if (!(b & 0x80)) goto done;
+ // "result -= 0x80 << 28" is irrevelant.
+
+ // If the input is larger than 32 bits, we still need to read it all
+ // and discard the high-order bits.
+ for (int i = 0; i < kMaxVarintBytes - kMaxVarint32Bytes; i++) {
+ b = *(ptr++); if (!(b & 0x80)) goto done;
+ }
+
+ // We have overrun the maximum size of a varint (10 bytes). Assume
+ // the data is corrupt.
+ return std::make_pair(false, ptr);
+
+ done:
+ *value = result;
+ return std::make_pair(true, ptr);
+}
+
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE::std::pair<bool, const uint8*> ReadVarint64FromArray(
+ const uint8* buffer, uint64* value);
+inline ::std::pair<bool, const uint8*> ReadVarint64FromArray(
+ const uint8* buffer, uint64* value) {
+ const uint8* ptr = buffer;
+ uint32 b;
+
+ // Splitting into 32-bit pieces gives better performance on 32-bit
+ // processors.
+ uint32 part0 = 0, part1 = 0, part2 = 0;
+
+ b = *(ptr++); part0 = b ; if (!(b & 0x80)) goto done;
+ part0 -= 0x80;
+ b = *(ptr++); part0 += b << 7; if (!(b & 0x80)) goto done;
+ part0 -= 0x80 << 7;
+ b = *(ptr++); part0 += b << 14; if (!(b & 0x80)) goto done;
+ part0 -= 0x80 << 14;
+ b = *(ptr++); part0 += b << 21; if (!(b & 0x80)) goto done;
+ part0 -= 0x80 << 21;
+ b = *(ptr++); part1 = b ; if (!(b & 0x80)) goto done;
+ part1 -= 0x80;
+ b = *(ptr++); part1 += b << 7; if (!(b & 0x80)) goto done;
+ part1 -= 0x80 << 7;
+ b = *(ptr++); part1 += b << 14; if (!(b & 0x80)) goto done;
+ part1 -= 0x80 << 14;
+ b = *(ptr++); part1 += b << 21; if (!(b & 0x80)) goto done;
+ part1 -= 0x80 << 21;
+ b = *(ptr++); part2 = b ; if (!(b & 0x80)) goto done;
+ part2 -= 0x80;
+ b = *(ptr++); part2 += b << 7; if (!(b & 0x80)) goto done;
+ // "part2 -= 0x80 << 7" is irrelevant because (0x80 << 7) << 56 is 0.
+
+ // We have overrun the maximum size of a varint (10 bytes). Assume
+ // the data is corrupt.
+ return std::make_pair(false, ptr);
+
+ done:
+ *value = (static_cast<uint64>(part0)) |
+ (static_cast<uint64>(part1) << 28) |
+ (static_cast<uint64>(part2) << 56);
+ return std::make_pair(true, ptr);
+}
+
+} // namespace
+
+bool CodedInputStream::ReadVarint32Slow(uint32* value) {
+ // Directly invoke ReadVarint64Fallback, since we already tried to optimize
+ // for one-byte varints.
+ std::pair<uint64, bool> p = ReadVarint64Fallback();
+ *value = static_cast<uint32>(p.first);
+ return p.second;
+}
+
+int64 CodedInputStream::ReadVarint32Fallback(uint32 first_byte_or_zero) {
+ if (BufferSize() >= kMaxVarintBytes ||
+ // Optimization: We're also safe if the buffer is non-empty and it ends
+ // with a byte that would terminate a varint.
+ (buffer_end_ > buffer_ && !(buffer_end_[-1] & 0x80))) {
+ GOOGLE_DCHECK_NE(first_byte_or_zero, 0)
+ << "Caller should provide us with *buffer_ when buffer is non-empty";
+ uint32 temp;
+ ::std::pair<bool, const uint8*> p =
+ ReadVarint32FromArray(first_byte_or_zero, buffer_, &temp);
+ if (!p.first) return -1;
+ buffer_ = p.second;
+ return temp;
+ } else {
+ // Really slow case: we will incur the cost of an extra function call here,
+ // but moving this out of line reduces the size of this function, which
+ // improves the common case. In micro benchmarks, this is worth about 10-15%
+ uint32 temp;
+ return ReadVarint32Slow(&temp) ? static_cast<int64>(temp) : -1;
+ }
+}
+
+int CodedInputStream::ReadVarintSizeAsIntSlow() {
+ // Directly invoke ReadVarint64Fallback, since we already tried to optimize
+ // for one-byte varints.
+ std::pair<uint64, bool> p = ReadVarint64Fallback();
+ if (!p.second || p.first > static_cast<uint64>(INT_MAX)) return -1;
+ return p.first;
+}
+
+int CodedInputStream::ReadVarintSizeAsIntFallback() {
+ if (BufferSize() >= kMaxVarintBytes ||
+ // Optimization: We're also safe if the buffer is non-empty and it ends
+ // with a byte that would terminate a varint.
+ (buffer_end_ > buffer_ && !(buffer_end_[-1] & 0x80))) {
+ uint64 temp;
+ ::std::pair<bool, const uint8*> p = ReadVarint64FromArray(buffer_, &temp);
+ if (!p.first || temp > static_cast<uint64>(INT_MAX)) return -1;
+ buffer_ = p.second;
+ return temp;
+ } else {
+ // Really slow case: we will incur the cost of an extra function call here,
+ // but moving this out of line reduces the size of this function, which
+ // improves the common case. In micro benchmarks, this is worth about 10-15%
+ return ReadVarintSizeAsIntSlow();
+ }
+}
+
+uint32 CodedInputStream::ReadTagSlow() {
+ if (buffer_ == buffer_end_) {
+ // Call refresh.
+ if (!Refresh()) {
+ // Refresh failed. Make sure that it failed due to EOF, not because
+ // we hit total_bytes_limit_, which, unlike normal limits, is not a
+ // valid place to end a message.
+ int current_position = total_bytes_read_ - buffer_size_after_limit_;
+ if (current_position >= total_bytes_limit_) {
+ // Hit total_bytes_limit_. But if we also hit the normal limit,
+ // we're still OK.
+ legitimate_message_end_ = current_limit_ == total_bytes_limit_;
+ } else {
+ legitimate_message_end_ = true;
+ }
+ return 0;
+ }
+ }
+
+ // For the slow path, just do a 64-bit read. Try to optimize for one-byte tags
+ // again, since we have now refreshed the buffer.
+ uint64 result = 0;
+ if (!ReadVarint64(&result)) return 0;
+ return static_cast<uint32>(result);
+}
+
+uint32 CodedInputStream::ReadTagFallback(uint32 first_byte_or_zero) {
+ const int buf_size = BufferSize();
+ if (buf_size >= kMaxVarintBytes ||
+ // Optimization: We're also safe if the buffer is non-empty and it ends
+ // with a byte that would terminate a varint.
+ (buf_size > 0 && !(buffer_end_[-1] & 0x80))) {
+ GOOGLE_DCHECK_EQ(first_byte_or_zero, buffer_[0]);
+ if (first_byte_or_zero == 0) {
+ ++buffer_;
+ return 0;
+ }
+ uint32 tag;
+ ::std::pair<bool, const uint8*> p =
+ ReadVarint32FromArray(first_byte_or_zero, buffer_, &tag);
+ if (!p.first) {
+ return 0;
+ }
+ buffer_ = p.second;
+ return tag;
+ } else {
+ // We are commonly at a limit when attempting to read tags. Try to quickly
+ // detect this case without making another function call.
+ if ((buf_size == 0) &&
+ ((buffer_size_after_limit_ > 0) ||
+ (total_bytes_read_ == current_limit_)) &&
+ // Make sure that the limit we hit is not total_bytes_limit_, since
+ // in that case we still need to call Refresh() so that it prints an
+ // error.
+ total_bytes_read_ - buffer_size_after_limit_ < total_bytes_limit_) {
+ // We hit a byte limit.
+ legitimate_message_end_ = true;
+ return 0;
+ }
+ return ReadTagSlow();
+ }
+}
+
+bool CodedInputStream::ReadVarint64Slow(uint64* value) {
+ // Slow path: This read might cross the end of the buffer, so we
+ // need to check and refresh the buffer if and when it does.
+
+ uint64 result = 0;
+ int count = 0;
+ uint32 b;
+
+ do {
+ if (count == kMaxVarintBytes) return false;
+ while (buffer_ == buffer_end_) {
+ if (!Refresh()) return false;
+ }
+ b = *buffer_;
+ result |= static_cast<uint64>(b & 0x7F) << (7 * count);
+ Advance(1);
+ ++count;
+ } while (b & 0x80);
+
+ *value = result;
+ return true;
+}
+
+std::pair<uint64, bool> CodedInputStream::ReadVarint64Fallback() {
+ if (BufferSize() >= kMaxVarintBytes ||
+ // Optimization: We're also safe if the buffer is non-empty and it ends
+ // with a byte that would terminate a varint.
+ (buffer_end_ > buffer_ && !(buffer_end_[-1] & 0x80))) {
+ uint64 temp;
+ ::std::pair<bool, const uint8*> p = ReadVarint64FromArray(buffer_, &temp);
+ if (!p.first) {
+ return std::make_pair(0, false);
+ }
+ buffer_ = p.second;
+ return std::make_pair(temp, true);
+ } else {
+ uint64 temp;
+ bool success = ReadVarint64Slow(&temp);
+ return std::make_pair(temp, success);
+ }
+}
+
+bool CodedInputStream::Refresh() {
+ GOOGLE_DCHECK_EQ(0, BufferSize());
+
+ if (buffer_size_after_limit_ > 0 || overflow_bytes_ > 0 ||
+ total_bytes_read_ == current_limit_) {
+ // We've hit a limit. Stop.
+ int current_position = total_bytes_read_ - buffer_size_after_limit_;
+
+ if (current_position >= total_bytes_limit_ &&
+ total_bytes_limit_ != current_limit_) {
+ // Hit total_bytes_limit_.
+ PrintTotalBytesLimitError();
+ }
+
+ return false;
+ }
+
+ if (total_bytes_warning_threshold_ >= 0 &&
+ total_bytes_read_ >= total_bytes_warning_threshold_) {
+ GOOGLE_LOG(WARNING) << "Reading dangerously large protocol message. If the "
+ "message turns out to be larger than "
+ << total_bytes_limit_ << " bytes, parsing will be halted "
+ "for security reasons. To increase the limit (or to "
+ "disable these warnings), see "
+ "CodedInputStream::SetTotalBytesLimit() in "
+ "google/protobuf/io/coded_stream.h.";
+
+ // Don't warn again for this stream, and print total size at the end.
+ total_bytes_warning_threshold_ = -2;
+ }
+
+ const void* void_buffer;
+ int buffer_size;
+ if (NextNonEmpty(input_, &void_buffer, &buffer_size)) {
+ buffer_ = reinterpret_cast<const uint8*>(void_buffer);
+ buffer_end_ = buffer_ + buffer_size;
+ GOOGLE_CHECK_GE(buffer_size, 0);
+
+ if (total_bytes_read_ <= INT_MAX - buffer_size) {
+ total_bytes_read_ += buffer_size;
+ } else {
+ // Overflow. Reset buffer_end_ to not include the bytes beyond INT_MAX.
+ // We can't get that far anyway, because total_bytes_limit_ is guaranteed
+ // to be less than it. We need to keep track of the number of bytes
+ // we discarded, though, so that we can call input_->BackUp() to back
+ // up over them on destruction.
+
+ // The following line is equivalent to:
+ // overflow_bytes_ = total_bytes_read_ + buffer_size - INT_MAX;
+ // except that it avoids overflows. Signed integer overflow has
+ // undefined results according to the C standard.
+ overflow_bytes_ = total_bytes_read_ - (INT_MAX - buffer_size);
+ buffer_end_ -= overflow_bytes_;
+ total_bytes_read_ = INT_MAX;
+ }
+
+ RecomputeBufferLimits();
+ return true;
+ } else {
+ buffer_ = NULL;
+ buffer_end_ = NULL;
+ return false;
+ }
+}
+
+// CodedOutputStream =================================================
+
+bool CodedOutputStream::default_serialization_deterministic_ = false;
+
+CodedOutputStream::CodedOutputStream(ZeroCopyOutputStream* output)
+ : output_(output),
+ buffer_(NULL),
+ buffer_size_(0),
+ total_bytes_(0),
+ had_error_(false),
+ aliasing_enabled_(false),
+ serialization_deterministic_is_overridden_(false) {
+ // Eagerly Refresh() so buffer space is immediately available.
+ Refresh();
+ // The Refresh() may have failed. If the client doesn't write any data,
+ // though, don't consider this an error. If the client does write data, then
+ // another Refresh() will be attempted and it will set the error once again.
+ had_error_ = false;
+}
+
+CodedOutputStream::CodedOutputStream(ZeroCopyOutputStream* output,
+ bool do_eager_refresh)
+ : output_(output),
+ buffer_(NULL),
+ buffer_size_(0),
+ total_bytes_(0),
+ had_error_(false),
+ aliasing_enabled_(false),
+ serialization_deterministic_is_overridden_(false) {
+ if (do_eager_refresh) {
+ // Eagerly Refresh() so buffer space is immediately available.
+ Refresh();
+ // The Refresh() may have failed. If the client doesn't write any data,
+ // though, don't consider this an error. If the client does write data, then
+ // another Refresh() will be attempted and it will set the error once again.
+ had_error_ = false;
+ }
+}
+
+CodedOutputStream::~CodedOutputStream() {
+ Trim();
+}
+
+void CodedOutputStream::Trim() {
+ if (buffer_size_ > 0) {
+ output_->BackUp(buffer_size_);
+ total_bytes_ -= buffer_size_;
+ buffer_size_ = 0;
+ buffer_ = NULL;
+ }
+}
+
+bool CodedOutputStream::Skip(int count) {
+ if (count < 0) return false;
+
+ while (count > buffer_size_) {
+ count -= buffer_size_;
+ if (!Refresh()) return false;
+ }
+
+ Advance(count);
+ return true;
+}
+
+bool CodedOutputStream::GetDirectBufferPointer(void** data, int* size) {
+ if (buffer_size_ == 0 && !Refresh()) return false;
+
+ *data = buffer_;
+ *size = buffer_size_;
+ return true;
+}
+
+void CodedOutputStream::WriteRaw(const void* data, int size) {
+ while (buffer_size_ < size) {
+ memcpy(buffer_, data, buffer_size_);
+ size -= buffer_size_;
+ data = reinterpret_cast<const uint8*>(data) + buffer_size_;
+ if (!Refresh()) return;
+ }
+
+ memcpy(buffer_, data, size);
+ Advance(size);
+}
+
+uint8* CodedOutputStream::WriteRawToArray(
+ const void* data, int size, uint8* target) {
+ memcpy(target, data, size);
+ return target + size;
+}
+
+
+void CodedOutputStream::WriteAliasedRaw(const void* data, int size) {
+ if (size < buffer_size_
+ ) {
+ WriteRaw(data, size);
+ } else {
+ Trim();
+
+ total_bytes_ += size;
+ had_error_ |= !output_->WriteAliasedRaw(data, size);
+ }
+}
+
+void CodedOutputStream::WriteLittleEndian32(uint32 value) {
+ uint8 bytes[sizeof(value)];
+
+ bool use_fast = buffer_size_ >= sizeof(value);
+ uint8* ptr = use_fast ? buffer_ : bytes;
+
+ WriteLittleEndian32ToArray(value, ptr);
+
+ if (use_fast) {
+ Advance(sizeof(value));
+ } else {
+ WriteRaw(bytes, sizeof(value));
+ }
+}
+
+void CodedOutputStream::WriteLittleEndian64(uint64 value) {
+ uint8 bytes[sizeof(value)];
+
+ bool use_fast = buffer_size_ >= sizeof(value);
+ uint8* ptr = use_fast ? buffer_ : bytes;
+
+ WriteLittleEndian64ToArray(value, ptr);
+
+ if (use_fast) {
+ Advance(sizeof(value));
+ } else {
+ WriteRaw(bytes, sizeof(value));
+ }
+}
+
+void CodedOutputStream::WriteVarint32SlowPath(uint32 value) {
+ uint8 bytes[kMaxVarint32Bytes];
+ uint8* target = &bytes[0];
+ uint8* end = WriteVarint32ToArray(value, target);
+ int size = end - target;
+ WriteRaw(bytes, size);
+}
+
+inline uint8* CodedOutputStream::WriteVarint64ToArrayInline(
+ uint64 value, uint8* target) {
+ // Splitting into 32-bit pieces gives better performance on 32-bit
+ // processors.
+ uint32 part0 = static_cast<uint32>(value );
+ uint32 part1 = static_cast<uint32>(value >> 28);
+ uint32 part2 = static_cast<uint32>(value >> 56);
+
+ int size;
+
+ // Here we can't really optimize for small numbers, since the value is
+ // split into three parts. Cheking for numbers < 128, for instance,
+ // would require three comparisons, since you'd have to make sure part1
+ // and part2 are zero. However, if the caller is using 64-bit integers,
+ // it is likely that they expect the numbers to often be very large, so
+ // we probably don't want to optimize for small numbers anyway. Thus,
+ // we end up with a hardcoded binary search tree...
+ if (part2 == 0) {
+ if (part1 == 0) {
+ if (part0 < (1 << 14)) {
+ if (part0 < (1 << 7)) {
+ size = 1; goto size1;
+ } else {
+ size = 2; goto size2;
+ }
+ } else {
+ if (part0 < (1 << 21)) {
+ size = 3; goto size3;
+ } else {
+ size = 4; goto size4;
+ }
+ }
+ } else {
+ if (part1 < (1 << 14)) {
+ if (part1 < (1 << 7)) {
+ size = 5; goto size5;
+ } else {
+ size = 6; goto size6;
+ }
+ } else {
+ if (part1 < (1 << 21)) {
+ size = 7; goto size7;
+ } else {
+ size = 8; goto size8;
+ }
+ }
+ }
+ } else {
+ if (part2 < (1 << 7)) {
+ size = 9; goto size9;
+ } else {
+ size = 10; goto size10;
+ }
+ }
+
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+
+ size10: target[9] = static_cast<uint8>((part2 >> 7) | 0x80);
+ size9 : target[8] = static_cast<uint8>((part2 ) | 0x80);
+ size8 : target[7] = static_cast<uint8>((part1 >> 21) | 0x80);
+ size7 : target[6] = static_cast<uint8>((part1 >> 14) | 0x80);
+ size6 : target[5] = static_cast<uint8>((part1 >> 7) | 0x80);
+ size5 : target[4] = static_cast<uint8>((part1 ) | 0x80);
+ size4 : target[3] = static_cast<uint8>((part0 >> 21) | 0x80);
+ size3 : target[2] = static_cast<uint8>((part0 >> 14) | 0x80);
+ size2 : target[1] = static_cast<uint8>((part0 >> 7) | 0x80);
+ size1 : target[0] = static_cast<uint8>((part0 ) | 0x80);
+
+ target[size-1] &= 0x7F;
+ return target + size;
+}
+
+void CodedOutputStream::WriteVarint64(uint64 value) {
+ if (buffer_size_ >= kMaxVarintBytes) {
+ // Fast path: We have enough bytes left in the buffer to guarantee that
+ // this write won't cross the end, so we can skip the checks.
+ uint8* target = buffer_;
+
+ uint8* end = WriteVarint64ToArrayInline(value, target);
+ int size = end - target;
+ Advance(size);
+ } else {
+ // Slow path: This write might cross the end of the buffer, so we
+ // compose the bytes first then use WriteRaw().
+ uint8 bytes[kMaxVarintBytes];
+ int size = 0;
+ while (value > 0x7F) {
+ bytes[size++] = (static_cast<uint8>(value) & 0x7F) | 0x80;
+ value >>= 7;
+ }
+ bytes[size++] = static_cast<uint8>(value) & 0x7F;
+ WriteRaw(bytes, size);
+ }
+}
+
+uint8* CodedOutputStream::WriteVarint64ToArray(
+ uint64 value, uint8* target) {
+ return WriteVarint64ToArrayInline(value, target);
+}
+
+bool CodedOutputStream::Refresh() {
+ void* void_buffer;
+ if (output_->Next(&void_buffer, &buffer_size_)) {
+ buffer_ = reinterpret_cast<uint8*>(void_buffer);
+ total_bytes_ += buffer_size_;
+ return true;
+ } else {
+ buffer_ = NULL;
+ buffer_size_ = 0;
+ had_error_ = true;
+ return false;
+ }
+}
+
+int CodedOutputStream::VarintSize32Fallback(uint32 value) {
+ if (value < (1 << 7)) {
+ return 1;
+ } else if (value < (1 << 14)) {
+ return 2;
+ } else if (value < (1 << 21)) {
+ return 3;
+ } else if (value < (1 << 28)) {
+ return 4;
+ } else {
+ return 5;
+ }
+}
+
+int CodedOutputStream::VarintSize64(uint64 value) {
+ if (value < (1ull << 35)) {
+ if (value < (1ull << 7)) {
+ return 1;
+ } else if (value < (1ull << 14)) {
+ return 2;
+ } else if (value < (1ull << 21)) {
+ return 3;
+ } else if (value < (1ull << 28)) {
+ return 4;
+ } else {
+ return 5;
+ }
+ } else {
+ if (value < (1ull << 42)) {
+ return 6;
+ } else if (value < (1ull << 49)) {
+ return 7;
+ } else if (value < (1ull << 56)) {
+ return 8;
+ } else if (value < (1ull << 63)) {
+ return 9;
+ } else {
+ return 10;
+ }
+ }
+}
+
+uint8* CodedOutputStream::WriteStringWithSizeToArray(const string& str,
+ uint8* target) {
+ GOOGLE_DCHECK_LE(str.size(), kuint32max);
+ target = WriteVarint32ToArray(str.size(), target);
+ return WriteStringToArray(str, target);
+}
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.h
new file mode 100644
index 0000000000..316da76524
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream.h
@@ -0,0 +1,1367 @@
+// 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 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 <string>
+#include <utility>
+#ifdef _MSC_VER
+ // Assuming windows is always little-endian.
+ #if !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
+ #define PROTOBUF_LITTLE_ENDIAN 1
+ #endif
+ #if _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
+#else
+ #include <sys/param.h> // __BYTE_ORDER
+ #if ((defined(__LITTLE_ENDIAN__) && !defined(__BIG_ENDIAN__)) || \
+ (defined(__BYTE_ORDER) && __BYTE_ORDER == __LITTLE_ENDIAN)) && \
+ !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
+ #define PROTOBUF_LITTLE_ENDIAN 1
+ #endif
+#endif
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+
+namespace protobuf {
+
+class DescriptorPool;
+class MessageFactory;
+
+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.
+class LIBPROTOBUF_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* 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.
+ 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.
+ GOOGLE_ATTRIBUTE_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 the above, with inlined optimizations. This should only be used
+ // by the protobuf implementation.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool InternalReadRawInline(void* buffer, int size);
+
+ // Like ReadRaw, but reads into a string.
+ //
+ // Implementation Note: ReadString() grows the string gradually as it
+ // reads in the data, rather than allocating the entire requested size
+ // upfront. This prevents denial-of-service attacks in which a client
+ // could claim that a string is going to be MAX_INT bytes long in order to
+ // crash the server because it can't allocate this much space at once.
+ bool ReadString(string* buffer, int size);
+ // Like the above, with inlined optimizations. This should only be used
+ // by the protobuf implementation.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool InternalReadStringInline(string* buffer,
+ int size);
+
+
+ // Read a 32-bit little-endian integer.
+ bool ReadLittleEndian32(uint32* value);
+ // Read a 64-bit little-endian integer.
+ bool ReadLittleEndian64(uint64* 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* ReadLittleEndian32FromArray(const uint8* buffer,
+ uint32* value);
+ // Read a 64-bit little-endian integer.
+ static const uint8* ReadLittleEndian64FromArray(const uint8* buffer,
+ uint64* 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, but may be more efficient.
+ bool ReadVarint32(uint32* value);
+ // Read an unsigned integer with Varint encoding.
+ bool ReadVarint64(uint64* 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, it 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.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE uint32 ReadTag();
+
+ // 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.)
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE std::pair<uint32, bool> ReadTagWithCutoff(
+ uint32 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.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool ExpectTag(uint32 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.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static const uint8* ExpectTagFromArray(
+ const uint8* buffer,
+ uint32 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;
+ //
+ // 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 expected);
+
+ // 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();
+
+ // 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 integer overflows or 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 integer overflows in the
+ // protocol buffers implementation, as well as 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 theoretical shortest message that could
+ // cause integer overflows is 512MB. The default limit is 64MB. Apps
+ // should set shorter limits if possible. If warning_threshold is not -1,
+ // a warning will be printed to stderr after warning_threshold bytes are
+ // read. For backwards compatibility all negative values get squashed to -1,
+ // as other negative values might have special internal meanings.
+ // An error will always be printed to stderr if the limit is reached.
+ //
+ // This is unrelated to PushLimit()/PopLimit().
+ //
+ // Hint: If you are reading this because your program is printing a
+ // warning about dangerously large protocol messages, you may be
+ // confused about what to do next. The best option is to change your
+ // design such that excessively large messages are not necessary.
+ // For example, try to design file formats to consist of many small
+ // messages rather than a single large one. If this is infeasible,
+ // you will need to increase the limit. Chances are, though, that
+ // your code never constructs a CodedInputStream on which the limit
+ // can be set. You probably parse messages by calling things like
+ // Message::ParseFromString(). In this case, you will need to change
+ // your code to instead construct some sort of ZeroCopyInputStream
+ // (e.g. an ArrayInputStream), construct a CodedInputStream around
+ // that, then call Message::ParseFromCodedStream() instead. Then
+ // you can adjust the limit. Yes, it's more work, but you're doing
+ // something unusual.
+ void SetTotalBytesLimit(int total_bytes_limit, int warning_threshold);
+
+ // The Total Bytes Limit minus the Current Position, or -1 if there
+ // is no Total Bytes Limit.
+ 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);
+
+
+ // 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* buffer_;
+ const uint8* 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 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_;
+
+ // If positive/0: Limit for bytes read after which a warning due to size
+ // should be logged.
+ // If -1: Printing of warning disabled. Can be set by client.
+ // If -2: Internal: Limit has been reached, print full size when destructing.
+ int total_bytes_warning_threshold_;
+
+ // 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.
+
+ // 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 it read otherwise. The latter has a bool
+ // indicating success or failure as part of its return type.
+ int64 ReadVarint32Fallback(uint32 first_byte_or_zero);
+ int ReadVarintSizeAsIntFallback();
+ std::pair<uint64, bool> ReadVarint64Fallback();
+ bool ReadVarint32Slow(uint32* value);
+ bool ReadVarint64Slow(uint64* value);
+ int ReadVarintSizeAsIntSlow();
+ bool ReadLittleEndian32Fallback(uint32* value);
+ bool ReadLittleEndian64Fallback(uint64* 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 ReadTagFallback(uint32 first_byte_or_zero);
+ uint32 ReadTagSlow();
+ bool ReadStringFallback(string* buffer, int size);
+
+ // Return the size of the buffer.
+ int BufferSize() const;
+
+ static const int kDefaultTotalBytesLimit = 64 << 20; // 64MB
+
+ static const int kDefaultTotalBytesWarningThreshold = 32 << 20; // 32MB
+
+ static int default_recursion_limit_; // 100 by default.
+};
+
+// 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* buffer =
+// coded_output->GetDirectBufferForNBytesAndAdvance(coded_size);
+// if (buffer != NULL) {
+// // 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 LIBPROTOBUF_EXPORT CodedOutputStream {
+ public:
+ // Create an CodedOutputStream that writes to the given ZeroCopyOutputStream.
+ explicit CodedOutputStream(ZeroCopyOutputStream* output);
+ CodedOutputStream(ZeroCopyOutputStream* output, bool do_eager_refresh);
+
+ // Destroy the CodedOutputStream and position the underlying
+ // ZeroCopyOutputStream immediately after the last byte written.
+ ~CodedOutputStream();
+
+ // 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();
+
+ // 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().
+ bool Skip(int count);
+
+ // 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);
+
+ // 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* GetDirectBufferForNBytesAndAdvance(int size);
+
+ // Write raw bytes, copying them from the given buffer.
+ void WriteRaw(const void* buffer, int size);
+ // 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* WriteRawToArray(const void* buffer, int size, uint8* target);
+
+ // Equivalent to WriteRaw(str.data(), str.size()).
+ void WriteString(const string& str);
+ // Like WriteString() but writing directly to the target array.
+ static uint8* WriteStringToArray(const string& str, uint8* target);
+ // Write the varint-encoded size of str followed by str.
+ static uint8* WriteStringWithSizeToArray(const string& str, uint8* target);
+
+
+ // 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);
+
+ // Write a 32-bit little-endian integer.
+ void WriteLittleEndian32(uint32 value);
+ // Like WriteLittleEndian32() but writing directly to the target array.
+ static uint8* WriteLittleEndian32ToArray(uint32 value, uint8* target);
+ // Write a 64-bit little-endian integer.
+ void WriteLittleEndian64(uint64 value);
+ // Like WriteLittleEndian64() but writing directly to the target array.
+ static uint8* WriteLittleEndian64ToArray(uint64 value, uint8* target);
+
+ // Write an unsigned integer with Varint encoding. Writing a 32-bit value
+ // is equivalent to casting it to uint64 and writing it as a 64-bit value,
+ // but may be more efficient.
+ void WriteVarint32(uint32 value);
+ // Like WriteVarint32() but writing directly to the target array.
+ static uint8* WriteVarint32ToArray(uint32 value, uint8* target);
+ // Write an unsigned integer with Varint encoding.
+ void WriteVarint64(uint64 value);
+ // Like WriteVarint64() but writing directly to the target array.
+ static uint8* WriteVarint64ToArray(uint64 value, uint8* 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 value);
+ // Like WriteVarint32SignExtended() but writing directly to the target array.
+ static uint8* WriteVarint32SignExtendedToArray(int32 value, uint8* 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 aformentioned optimization can't work,
+ // but GCC by default doesn't want to inline this.
+ void WriteTag(uint32 value);
+ // Like WriteTag() but writing directly to the target array.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static uint8* WriteTagToArray(uint32 value,
+ uint8* target);
+
+ // Returns the number of bytes needed to encode the given value as a varint.
+ static int VarintSize32(uint32 value);
+ // Returns the number of bytes needed to encode the given value as a varint.
+ static int VarintSize64(uint64 value);
+
+ // If negative, 10 bytes. Otheriwse, same as VarintSize32().
+ static int VarintSize32SignExtended(int32 value);
+
+ // Compile-time equivalent of VarintSize32().
+ template <uint32 Value>
+ struct StaticVarintSize32 {
+ static const int 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.
+ inline int ByteCount() const;
+
+ // Returns true if there was an underlying I/O error since this object was
+ // created.
+ bool HadError() const { return had_error_; }
+
+ // Deterministic serialization, if requested, guarantees 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 of the same binary (which may be executing on
+ // different machines) will serialize equal messages to the same bytes.
+ //
+ // Note the deterministic serialization is NOT canonical across languages; it
+ // is also unstable across different builds with schema changes due to unknown
+ // fields. Users who need canonical serialization, e.g., persistent storage in
+ // a canonical form, fingerprinting, etc., should define their own
+ // canonicalization specification and implement the serializer using
+ // reflection APIs rather than relying on this API.
+ //
+ // If determinisitc serialization is requested, the serializer will
+ // sort map entries by keys in lexicographical order or numerical order.
+ // (This is an implementation detail and may subject to change.)
+ //
+ // There are two ways to determine whether serialization should be
+ // deterministic for this CodedOutputStream. If SetSerializationDeterministic
+ // has not yet been called, then the default comes from the global default,
+ // which is false, until SetDefaultSerializationDeterministic has been called.
+ // Otherwise, SetSerializationDeterministic has been called, and the last
+ // value passed to it is all that matters.
+ void SetSerializationDeterministic(bool value) {
+ serialization_deterministic_is_overridden_ = true;
+ serialization_deterministic_override_ = value;
+ }
+ // See above. Also, note that users of this CodedOutputStream may need to
+ // call IsSerializationDeterminstic() to serialize in the intended way. This
+ // CodedOutputStream cannot enforce a desire for deterministic serialization
+ // by itself.
+ bool IsSerializationDeterminstic() const {
+ return serialization_deterministic_is_overridden_ ?
+ serialization_deterministic_override_ :
+ default_serialization_deterministic_;
+ }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CodedOutputStream);
+
+ ZeroCopyOutputStream* output_;
+ uint8* buffer_;
+ int buffer_size_;
+ int total_bytes_; // Sum of sizes of all buffers seen so far.
+ bool had_error_; // Whether an error occurred during output.
+ bool aliasing_enabled_; // See EnableAliasing().
+ // See SetSerializationDeterministic() regarding these three fields.
+ bool serialization_deterministic_is_overridden_;
+ bool serialization_deterministic_override_;
+ static bool default_serialization_deterministic_;
+
+ // Advance the buffer by a given number of bytes.
+ void Advance(int amount);
+
+ // Called when the buffer runs out to request more data. Implies an
+ // Advance(buffer_size_).
+ bool Refresh();
+
+ // Like WriteRaw() but may avoid copying if the underlying
+ // ZeroCopyOutputStream supports it.
+ void WriteAliasedRaw(const void* buffer, int size);
+
+ // If this write might cross the end of the buffer, we compose the bytes first
+ // then use WriteRaw().
+ void WriteVarint32SlowPath(uint32 value);
+
+ // Always-inlined versions of WriteVarint* functions so that code can be
+ // reused, while still controlling size. For instance, WriteVarint32ToArray()
+ // should not directly call this: since it is inlined itself, doing so
+ // would greatly increase the size of generated code. Instead, it should call
+ // WriteVarint32FallbackToArray. Meanwhile, WriteVarint32() is already
+ // out-of-line, so it should just invoke this directly to avoid any extra
+ // function call overhead.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE static uint8* WriteVarint64ToArrayInline(
+ uint64 value, uint8* target);
+
+ static int VarintSize32Fallback(uint32 value);
+
+ // See above. Other projects may use "friend" to allow them to call this.
+ static void SetDefaultSerializationDeterministic() {
+ default_serialization_deterministic_ = true;
+ }
+};
+
+// inline methods ====================================================
+// The vast majority of varints are only one byte. These inline
+// methods optimize for that case.
+
+inline bool CodedInputStream::ReadVarint32(uint32* value) {
+ uint32 v = 0;
+ if (GOOGLE_PREDICT_TRUE(buffer_ < buffer_end_)) {
+ v = *buffer_;
+ if (v < 0x80) {
+ *value = v;
+ Advance(1);
+ return true;
+ }
+ }
+ int64 result = ReadVarint32Fallback(v);
+ *value = static_cast<uint32>(result);
+ return result >= 0;
+}
+
+inline bool CodedInputStream::ReadVarint64(uint64* value) {
+ if (GOOGLE_PREDICT_TRUE(buffer_ < buffer_end_) && *buffer_ < 0x80) {
+ *value = *buffer_;
+ Advance(1);
+ return true;
+ }
+ std::pair<uint64, bool> p = ReadVarint64Fallback();
+ *value = p.first;
+ return p.second;
+}
+
+inline bool CodedInputStream::ReadVarintSizeAsInt(int* value) {
+ if (GOOGLE_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* CodedInputStream::ReadLittleEndian32FromArray(
+ const uint8* buffer,
+ uint32* value) {
+#if defined(PROTOBUF_LITTLE_ENDIAN)
+ memcpy(value, buffer, sizeof(*value));
+ return buffer + sizeof(*value);
+#else
+ *value = (static_cast<uint32>(buffer[0]) ) |
+ (static_cast<uint32>(buffer[1]) << 8) |
+ (static_cast<uint32>(buffer[2]) << 16) |
+ (static_cast<uint32>(buffer[3]) << 24);
+ return buffer + sizeof(*value);
+#endif
+}
+// static
+inline const uint8* CodedInputStream::ReadLittleEndian64FromArray(
+ const uint8* buffer,
+ uint64* value) {
+#if defined(PROTOBUF_LITTLE_ENDIAN)
+ memcpy(value, buffer, sizeof(*value));
+ return buffer + sizeof(*value);
+#else
+ uint32 part0 = (static_cast<uint32>(buffer[0]) ) |
+ (static_cast<uint32>(buffer[1]) << 8) |
+ (static_cast<uint32>(buffer[2]) << 16) |
+ (static_cast<uint32>(buffer[3]) << 24);
+ uint32 part1 = (static_cast<uint32>(buffer[4]) ) |
+ (static_cast<uint32>(buffer[5]) << 8) |
+ (static_cast<uint32>(buffer[6]) << 16) |
+ (static_cast<uint32>(buffer[7]) << 24);
+ *value = static_cast<uint64>(part0) |
+ (static_cast<uint64>(part1) << 32);
+ return buffer + sizeof(*value);
+#endif
+}
+
+inline bool CodedInputStream::ReadLittleEndian32(uint32* value) {
+#if defined(PROTOBUF_LITTLE_ENDIAN)
+ if (GOOGLE_PREDICT_TRUE(BufferSize() >= static_cast<int>(sizeof(*value)))) {
+ memcpy(value, buffer_, sizeof(*value));
+ Advance(sizeof(*value));
+ return true;
+ } else {
+ return ReadLittleEndian32Fallback(value);
+ }
+#else
+ return ReadLittleEndian32Fallback(value);
+#endif
+}
+
+inline bool CodedInputStream::ReadLittleEndian64(uint64* value) {
+#if defined(PROTOBUF_LITTLE_ENDIAN)
+ if (GOOGLE_PREDICT_TRUE(BufferSize() >= static_cast<int>(sizeof(*value)))) {
+ memcpy(value, buffer_, sizeof(*value));
+ Advance(sizeof(*value));
+ return true;
+ } else {
+ return ReadLittleEndian64Fallback(value);
+ }
+#else
+ return ReadLittleEndian64Fallback(value);
+#endif
+}
+
+inline uint32 CodedInputStream::ReadTag() {
+ uint32 v = 0;
+ if (GOOGLE_PREDICT_TRUE(buffer_ < buffer_end_)) {
+ v = *buffer_;
+ if (v < 0x80) {
+ last_tag_ = v;
+ Advance(1);
+ return v;
+ }
+ }
+ last_tag_ = ReadTagFallback(v);
+ return last_tag_;
+}
+
+inline std::pair<uint32, bool> CodedInputStream::ReadTagWithCutoff(
+ uint32 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 first_byte_or_zero = 0;
+ if (GOOGLE_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>(buffer_[0]) > 0) {
+ const uint32 kMax1ByteVarint = 0x7f;
+ uint32 tag = last_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 &&
+ GOOGLE_PREDICT_TRUE(buffer_ + 1 < buffer_end_) &&
+ GOOGLE_PREDICT_TRUE((buffer_[0] & ~buffer_[1]) >= 0x80)) {
+ const uint32 kMax2ByteVarint = (0x7f << 7) + 0x7f;
+ uint32 tag = last_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
+ last_tag_ = ReadTagFallback(first_byte_or_zero);
+ return std::make_pair(last_tag_, static_cast<uint32>(last_tag_ - 1) < cutoff);
+}
+
+inline bool CodedInputStream::LastTagWas(uint32 expected) {
+ return last_tag_ == expected;
+}
+
+inline bool CodedInputStream::ConsumedEntireMessage() {
+ return legitimate_message_end_;
+}
+
+inline bool CodedInputStream::ExpectTag(uint32 expected) {
+ if (expected < (1 << 7)) {
+ if (GOOGLE_PREDICT_TRUE(buffer_ < buffer_end_) && buffer_[0] == expected) {
+ Advance(1);
+ return true;
+ } else {
+ return false;
+ }
+ } else if (expected < (1 << 14)) {
+ if (GOOGLE_PREDICT_TRUE(BufferSize() >= 2) &&
+ buffer_[0] == static_cast<uint8>(expected | 0x80) &&
+ buffer_[1] == static_cast<uint8>(expected >> 7)) {
+ Advance(2);
+ return true;
+ } else {
+ return false;
+ }
+ } else {
+ // Don't bother optimizing for larger values.
+ return false;
+ }
+}
+
+inline const uint8* CodedInputStream::ExpectTagFromArray(
+ const uint8* buffer, uint32 expected) {
+ if (expected < (1 << 7)) {
+ if (buffer[0] == expected) {
+ return buffer + 1;
+ }
+ } else if (expected < (1 << 14)) {
+ if (buffer[0] == static_cast<uint8>(expected | 0x80) &&
+ buffer[1] == static_cast<uint8>(expected >> 7)) {
+ return buffer + 2;
+ }
+ }
+ return NULL;
+}
+
+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 uint8* CodedOutputStream::GetDirectBufferForNBytesAndAdvance(int size) {
+ if (buffer_size_ < size) {
+ return NULL;
+ } else {
+ uint8* result = buffer_;
+ Advance(size);
+ return result;
+ }
+}
+
+inline uint8* CodedOutputStream::WriteVarint32ToArray(uint32 value,
+ uint8* target) {
+ while (value >= 0x80) {
+ *target = static_cast<uint8>(value | 0x80);
+ value >>= 7;
+ ++target;
+ }
+ *target = static_cast<uint8>(value);
+ return target + 1;
+}
+
+inline void CodedOutputStream::WriteVarint32SignExtended(int32 value) {
+ if (value < 0) {
+ WriteVarint64(static_cast<uint64>(value));
+ } else {
+ WriteVarint32(static_cast<uint32>(value));
+ }
+}
+
+inline uint8* CodedOutputStream::WriteVarint32SignExtendedToArray(
+ int32 value, uint8* target) {
+ if (value < 0) {
+ return WriteVarint64ToArray(static_cast<uint64>(value), target);
+ } else {
+ return WriteVarint32ToArray(static_cast<uint32>(value), target);
+ }
+}
+
+inline uint8* CodedOutputStream::WriteLittleEndian32ToArray(uint32 value,
+ uint8* target) {
+#if defined(PROTOBUF_LITTLE_ENDIAN)
+ memcpy(target, &value, sizeof(value));
+#else
+ target[0] = static_cast<uint8>(value);
+ target[1] = static_cast<uint8>(value >> 8);
+ target[2] = static_cast<uint8>(value >> 16);
+ target[3] = static_cast<uint8>(value >> 24);
+#endif
+ return target + sizeof(value);
+}
+
+inline uint8* CodedOutputStream::WriteLittleEndian64ToArray(uint64 value,
+ uint8* target) {
+#if defined(PROTOBUF_LITTLE_ENDIAN)
+ memcpy(target, &value, sizeof(value));
+#else
+ uint32 part0 = static_cast<uint32>(value);
+ uint32 part1 = static_cast<uint32>(value >> 32);
+
+ target[0] = static_cast<uint8>(part0);
+ target[1] = static_cast<uint8>(part0 >> 8);
+ target[2] = static_cast<uint8>(part0 >> 16);
+ target[3] = static_cast<uint8>(part0 >> 24);
+ target[4] = static_cast<uint8>(part1);
+ target[5] = static_cast<uint8>(part1 >> 8);
+ target[6] = static_cast<uint8>(part1 >> 16);
+ target[7] = static_cast<uint8>(part1 >> 24);
+#endif
+ return target + sizeof(value);
+}
+
+inline void CodedOutputStream::WriteVarint32(uint32 value) {
+ if (buffer_size_ >= 5) {
+ // Fast path: We have enough bytes left in the buffer to guarantee that
+ // this write won't cross the end, so we can skip the checks.
+ uint8* target = buffer_;
+ uint8* end = WriteVarint32ToArray(value, target);
+ int size = static_cast<int>(end - target);
+ Advance(size);
+ } else {
+ WriteVarint32SlowPath(value);
+ }
+}
+
+inline void CodedOutputStream::WriteTag(uint32 value) {
+ WriteVarint32(value);
+}
+
+inline uint8* CodedOutputStream::WriteTagToArray(
+ uint32 value, uint8* target) {
+ return WriteVarint32ToArray(value, target);
+}
+
+inline int CodedOutputStream::VarintSize32(uint32 value) {
+ if (value < (1 << 7)) {
+ return 1;
+ } else {
+ return VarintSize32Fallback(value);
+ }
+}
+
+inline int CodedOutputStream::VarintSize32SignExtended(int32 value) {
+ if (value < 0) {
+ return 10; // TODO(kenton): Make this a symbolic constant.
+ } else {
+ return VarintSize32(static_cast<uint32>(value));
+ }
+}
+
+inline void CodedOutputStream::WriteString(const string& str) {
+ WriteRaw(str.data(), static_cast<int>(str.size()));
+}
+
+inline void CodedOutputStream::WriteRawMaybeAliased(
+ const void* data, int size) {
+ if (aliasing_enabled_) {
+ WriteAliasedRaw(data, size);
+ } else {
+ WriteRaw(data, size);
+ }
+}
+
+inline uint8* CodedOutputStream::WriteStringToArray(
+ const string& str, uint8* target) {
+ return WriteRawToArray(str.data(), static_cast<int>(str.size()), target);
+}
+
+inline int CodedOutputStream::ByteCount() const {
+ return total_bytes_ - buffer_size_;
+}
+
+inline void CodedInputStream::Advance(int amount) {
+ buffer_ += amount;
+}
+
+inline void CodedOutputStream::Advance(int amount) {
+ buffer_ += amount;
+ buffer_size_ -= 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_(NULL),
+ buffer_end_(NULL),
+ input_(input),
+ total_bytes_read_(0),
+ overflow_bytes_(0),
+ last_tag_(0),
+ legitimate_message_end_(false),
+ aliasing_enabled_(false),
+ current_limit_(kint32max),
+ buffer_size_after_limit_(0),
+ total_bytes_limit_(kDefaultTotalBytesLimit),
+ total_bytes_warning_threshold_(kDefaultTotalBytesWarningThreshold),
+ recursion_budget_(default_recursion_limit_),
+ recursion_limit_(default_recursion_limit_),
+ extension_pool_(NULL),
+ extension_factory_(NULL) {
+ // Eagerly Refresh() so buffer space is immediately available.
+ Refresh();
+}
+
+inline CodedInputStream::CodedInputStream(const uint8* buffer, int size)
+ : buffer_(buffer),
+ buffer_end_(buffer + size),
+ input_(NULL),
+ 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),
+ total_bytes_warning_threshold_(kDefaultTotalBytesWarningThreshold),
+ recursion_budget_(default_recursion_limit_),
+ recursion_limit_(default_recursion_limit_),
+ extension_pool_(NULL),
+ extension_factory_(NULL) {
+ // 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_ == NULL;
+}
+
+} // namespace io
+} // namespace protobuf
+
+
+#if _MSC_VER >= 1300 && !defined(__INTEL_COMPILER)
+ #pragma runtime_checks("c", restore)
+#endif // _MSC_VER && !defined(__INTEL_COMPILER)
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_CODED_STREAM_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_inl.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_inl.h
new file mode 100644
index 0000000000..d95b06e04e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_inl.h
@@ -0,0 +1,90 @@
+// 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: jasonh@google.com (Jason Hsueh)
+//
+// Implements methods of coded_stream.h that need to be inlined for performance
+// reasons, but should not be defined in a public header.
+
+#ifndef GOOGLE_PROTOBUF_IO_CODED_STREAM_INL_H__
+#define GOOGLE_PROTOBUF_IO_CODED_STREAM_INL_H__
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <string>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+inline bool CodedInputStream::InternalReadStringInline(string* buffer,
+ int size) {
+ if (size < 0) return false; // security: size is often user-supplied
+
+ if (BufferSize() >= size) {
+ STLStringResizeUninitialized(buffer, size);
+ std::pair<char*, bool> z = as_string_data(buffer);
+ if (z.second) {
+ // Oddly enough, memcpy() requires its first two args to be non-NULL even
+ // if we copy 0 bytes. So, we have ensured that z.first is non-NULL here.
+ GOOGLE_DCHECK(z.first != NULL);
+ memcpy(z.first, buffer_, size);
+ Advance(size);
+ }
+ return true;
+ }
+
+ return ReadStringFallback(buffer, size);
+}
+
+inline bool CodedInputStream::InternalReadRawInline(void* buffer, int size) {
+ int current_buffer_size;
+ while ((current_buffer_size = BufferSize()) < size) {
+ // Reading past end of buffer. Copy what we have, then refresh.
+ memcpy(buffer, buffer_, current_buffer_size);
+ buffer = reinterpret_cast<uint8*>(buffer) + current_buffer_size;
+ size -= current_buffer_size;
+ Advance(current_buffer_size);
+ if (!Refresh()) return false;
+ }
+
+ memcpy(buffer, buffer_, size);
+ Advance(size);
+
+ return true;
+}
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_CODED_STREAM_INL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_unittest.cc
new file mode 100644
index 0000000000..a8108e4572
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/coded_stream_unittest.cc
@@ -0,0 +1,1385 @@
+// 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 tests and benchmarks.
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/io/coded_stream.h>
+
+#include <limits.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+
+
+// This declares an unsigned long long integer literal in a portable way.
+// (The original macro is way too big and ruins my formatting.)
+#undef ULL
+#define ULL(x) GOOGLE_ULONGLONG(x)
+
+namespace google {
+namespace protobuf {
+namespace io {
+namespace {
+
+// ===================================================================
+// Data-Driven Test Infrastructure
+
+// TEST_1D and TEST_2D are macros I'd eventually like to see added to
+// gTest. These macros can be used to declare tests which should be
+// run multiple times, once for each item in some input array. TEST_1D
+// tests all cases in a single input array. TEST_2D tests all
+// combinations of cases from two arrays. The arrays must be statically
+// defined such that the GOOGLE_ARRAYSIZE() macro works on them. Example:
+//
+// int kCases[] = {1, 2, 3, 4}
+// TEST_1D(MyFixture, MyTest, kCases) {
+// EXPECT_GT(kCases_case, 0);
+// }
+//
+// This test iterates through the numbers 1, 2, 3, and 4 and tests that
+// they are all grater than zero. In case of failure, the exact case
+// which failed will be printed. The case type must be printable using
+// ostream::operator<<.
+
+// TODO(kenton): gTest now supports "parameterized tests" which would be
+// a better way to accomplish this. Rewrite when time permits.
+
+#define TEST_1D(FIXTURE, NAME, CASES) \
+ class FIXTURE##_##NAME##_DD : public FIXTURE { \
+ protected: \
+ template <typename CaseType> \
+ void DoSingleCase(const CaseType& CASES##_case); \
+ }; \
+ \
+ TEST_F(FIXTURE##_##NAME##_DD, NAME) { \
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(CASES); i++) { \
+ SCOPED_TRACE(testing::Message() \
+ << #CASES " case #" << i << ": " << CASES[i]); \
+ DoSingleCase(CASES[i]); \
+ } \
+ } \
+ \
+ template <typename CaseType> \
+ void FIXTURE##_##NAME##_DD::DoSingleCase(const CaseType& CASES##_case)
+
+#define TEST_2D(FIXTURE, NAME, CASES1, CASES2) \
+ class FIXTURE##_##NAME##_DD : public FIXTURE { \
+ protected: \
+ template <typename CaseType1, typename CaseType2> \
+ void DoSingleCase(const CaseType1& CASES1##_case, \
+ const CaseType2& CASES2##_case); \
+ }; \
+ \
+ TEST_F(FIXTURE##_##NAME##_DD, NAME) { \
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(CASES1); i++) { \
+ for (int j = 0; j < GOOGLE_ARRAYSIZE(CASES2); j++) { \
+ SCOPED_TRACE(testing::Message() \
+ << #CASES1 " case #" << i << ": " << CASES1[i] << ", " \
+ << #CASES2 " case #" << j << ": " << CASES2[j]); \
+ DoSingleCase(CASES1[i], CASES2[j]); \
+ } \
+ } \
+ } \
+ \
+ template <typename CaseType1, typename CaseType2> \
+ void FIXTURE##_##NAME##_DD::DoSingleCase(const CaseType1& CASES1##_case, \
+ const CaseType2& CASES2##_case)
+
+// ===================================================================
+
+class CodedStreamTest : public testing::Test {
+ protected:
+ // Helper method used by tests for bytes warning. See implementation comment
+ // for further information.
+ static void SetupTotalBytesLimitWarningTest(
+ int total_bytes_limit, int warning_threshold,
+ vector<string>* out_errors, vector<string>* out_warnings);
+
+ // Buffer used during most of the tests. This assumes tests run sequentially.
+ static const int kBufferSize = 1024 * 64;
+ static uint8 buffer_[kBufferSize];
+};
+
+uint8 CodedStreamTest::buffer_[CodedStreamTest::kBufferSize];
+
+// We test each operation over a variety of block sizes to insure that
+// we test cases where reads or writes cross buffer boundaries, cases
+// where they don't, and cases where there is so much buffer left that
+// we can use special optimized paths that don't worry about bounds
+// checks.
+const int kBlockSizes[] = {1, 2, 3, 5, 7, 13, 32, 1024};
+
+
+// -------------------------------------------------------------------
+// Varint tests.
+
+struct VarintCase {
+ uint8 bytes[10]; // Encoded bytes.
+ int size; // Encoded size, in bytes.
+ uint64 value; // Parsed value.
+};
+
+inline std::ostream& operator<<(std::ostream& os, const VarintCase& c) {
+ return os << c.value;
+}
+
+VarintCase kVarintCases[] = {
+ // 32-bit values
+ {{0x00} , 1, 0},
+ {{0x01} , 1, 1},
+ {{0x7f} , 1, 127},
+ {{0xa2, 0x74}, 2, (0x22 << 0) | (0x74 << 7)}, // 14882
+ {{0xbe, 0xf7, 0x92, 0x84, 0x0b}, 5, // 2961488830
+ (0x3e << 0) | (0x77 << 7) | (0x12 << 14) | (0x04 << 21) |
+ (ULL(0x0b) << 28)},
+
+ // 64-bit
+ {{0xbe, 0xf7, 0x92, 0x84, 0x1b}, 5, // 7256456126
+ (0x3e << 0) | (0x77 << 7) | (0x12 << 14) | (0x04 << 21) |
+ (ULL(0x1b) << 28)},
+ {{0x80, 0xe6, 0xeb, 0x9c, 0xc3, 0xc9, 0xa4, 0x49}, 8, // 41256202580718336
+ (0x00 << 0) | (0x66 << 7) | (0x6b << 14) | (0x1c << 21) |
+ (ULL(0x43) << 28) | (ULL(0x49) << 35) | (ULL(0x24) << 42) |
+ (ULL(0x49) << 49)},
+ // 11964378330978735131
+ {{0x9b, 0xa8, 0xf9, 0xc2, 0xbb, 0xd6, 0x80, 0x85, 0xa6, 0x01}, 10,
+ (0x1b << 0) | (0x28 << 7) | (0x79 << 14) | (0x42 << 21) |
+ (ULL(0x3b) << 28) | (ULL(0x56) << 35) | (ULL(0x00) << 42) |
+ (ULL(0x05) << 49) | (ULL(0x26) << 56) | (ULL(0x01) << 63)},
+};
+
+TEST_2D(CodedStreamTest, ReadVarint32, kVarintCases, kBlockSizes) {
+ memcpy(buffer_, kVarintCases_case.bytes, kVarintCases_case.size);
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ uint32 value;
+ EXPECT_TRUE(coded_input.ReadVarint32(&value));
+ EXPECT_EQ(static_cast<uint32>(kVarintCases_case.value), value);
+ }
+
+ EXPECT_EQ(kVarintCases_case.size, input.ByteCount());
+}
+
+TEST_2D(CodedStreamTest, ReadTag, kVarintCases, kBlockSizes) {
+ memcpy(buffer_, kVarintCases_case.bytes, kVarintCases_case.size);
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ uint32 expected_value = static_cast<uint32>(kVarintCases_case.value);
+ EXPECT_EQ(expected_value, coded_input.ReadTag());
+
+ EXPECT_TRUE(coded_input.LastTagWas(expected_value));
+ EXPECT_FALSE(coded_input.LastTagWas(expected_value + 1));
+ }
+
+ EXPECT_EQ(kVarintCases_case.size, input.ByteCount());
+}
+
+// This is the regression test that verifies that there is no issues
+// with the empty input buffers handling.
+TEST_F(CodedStreamTest, EmptyInputBeforeEos) {
+ class In : public ZeroCopyInputStream {
+ public:
+ In() : count_(0) {}
+ private:
+ virtual bool Next(const void** data, int* size) {
+ *data = NULL;
+ *size = 0;
+ return count_++ < 2;
+ }
+ virtual void BackUp(int count) {
+ GOOGLE_LOG(FATAL) << "Tests never call this.";
+ }
+ virtual bool Skip(int count) {
+ GOOGLE_LOG(FATAL) << "Tests never call this.";
+ return false;
+ }
+ virtual int64 ByteCount() const { return 0; }
+ int count_;
+ } in;
+ CodedInputStream input(&in);
+ input.ReadTag();
+ EXPECT_TRUE(input.ConsumedEntireMessage());
+}
+
+TEST_1D(CodedStreamTest, ExpectTag, kVarintCases) {
+ // Leave one byte at the beginning of the buffer so we can read it
+ // to force the first buffer to be loaded.
+ buffer_[0] = '\0';
+ memcpy(buffer_ + 1, kVarintCases_case.bytes, kVarintCases_case.size);
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+
+ {
+ CodedInputStream coded_input(&input);
+
+ // Read one byte to force coded_input.Refill() to be called. Otherwise,
+ // ExpectTag() will return a false negative.
+ uint8 dummy;
+ coded_input.ReadRaw(&dummy, 1);
+ EXPECT_EQ((uint)'\0', (uint)dummy);
+
+ uint32 expected_value = static_cast<uint32>(kVarintCases_case.value);
+
+ // ExpectTag() produces false negatives for large values.
+ if (kVarintCases_case.size <= 2) {
+ EXPECT_FALSE(coded_input.ExpectTag(expected_value + 1));
+ EXPECT_TRUE(coded_input.ExpectTag(expected_value));
+ } else {
+ EXPECT_FALSE(coded_input.ExpectTag(expected_value));
+ }
+ }
+
+ if (kVarintCases_case.size <= 2) {
+ EXPECT_EQ(kVarintCases_case.size + 1, input.ByteCount());
+ } else {
+ EXPECT_EQ(1, input.ByteCount());
+ }
+}
+
+TEST_1D(CodedStreamTest, ExpectTagFromArray, kVarintCases) {
+ memcpy(buffer_, kVarintCases_case.bytes, kVarintCases_case.size);
+
+ const uint32 expected_value = static_cast<uint32>(kVarintCases_case.value);
+
+ // If the expectation succeeds, it should return a pointer past the tag.
+ if (kVarintCases_case.size <= 2) {
+ EXPECT_TRUE(NULL ==
+ CodedInputStream::ExpectTagFromArray(buffer_,
+ expected_value + 1));
+ EXPECT_TRUE(buffer_ + kVarintCases_case.size ==
+ CodedInputStream::ExpectTagFromArray(buffer_, expected_value));
+ } else {
+ EXPECT_TRUE(NULL ==
+ CodedInputStream::ExpectTagFromArray(buffer_, expected_value));
+ }
+}
+
+TEST_2D(CodedStreamTest, ReadVarint64, kVarintCases, kBlockSizes) {
+ memcpy(buffer_, kVarintCases_case.bytes, kVarintCases_case.size);
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ uint64 value;
+ EXPECT_TRUE(coded_input.ReadVarint64(&value));
+ EXPECT_EQ(kVarintCases_case.value, value);
+ }
+
+ EXPECT_EQ(kVarintCases_case.size, input.ByteCount());
+}
+
+TEST_2D(CodedStreamTest, WriteVarint32, kVarintCases, kBlockSizes) {
+ if (kVarintCases_case.value > ULL(0x00000000FFFFFFFF)) {
+ // Skip this test for the 64-bit values.
+ return;
+ }
+
+ ArrayOutputStream output(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedOutputStream coded_output(&output);
+
+ coded_output.WriteVarint32(static_cast<uint32>(kVarintCases_case.value));
+ EXPECT_FALSE(coded_output.HadError());
+
+ EXPECT_EQ(kVarintCases_case.size, coded_output.ByteCount());
+ }
+
+ EXPECT_EQ(kVarintCases_case.size, output.ByteCount());
+ EXPECT_EQ(0,
+ memcmp(buffer_, kVarintCases_case.bytes, kVarintCases_case.size));
+}
+
+TEST_2D(CodedStreamTest, WriteVarint64, kVarintCases, kBlockSizes) {
+ ArrayOutputStream output(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedOutputStream coded_output(&output);
+
+ coded_output.WriteVarint64(kVarintCases_case.value);
+ EXPECT_FALSE(coded_output.HadError());
+
+ EXPECT_EQ(kVarintCases_case.size, coded_output.ByteCount());
+ }
+
+ EXPECT_EQ(kVarintCases_case.size, output.ByteCount());
+ EXPECT_EQ(0,
+ memcmp(buffer_, kVarintCases_case.bytes, kVarintCases_case.size));
+}
+
+// This test causes gcc 3.3.5 (and earlier?) to give the cryptic error:
+// "sorry, unimplemented: `method_call_expr' not supported by dump_expr"
+#if !defined(__GNUC__) || __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 3)
+
+int32 kSignExtendedVarintCases[] = {
+ 0, 1, -1, 1237894, -37895138
+};
+
+TEST_2D(CodedStreamTest, WriteVarint32SignExtended,
+ kSignExtendedVarintCases, kBlockSizes) {
+ ArrayOutputStream output(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedOutputStream coded_output(&output);
+
+ coded_output.WriteVarint32SignExtended(kSignExtendedVarintCases_case);
+ EXPECT_FALSE(coded_output.HadError());
+
+ if (kSignExtendedVarintCases_case < 0) {
+ EXPECT_EQ(10, coded_output.ByteCount());
+ } else {
+ EXPECT_LE(coded_output.ByteCount(), 5);
+ }
+ }
+
+ if (kSignExtendedVarintCases_case < 0) {
+ EXPECT_EQ(10, output.ByteCount());
+ } else {
+ EXPECT_LE(output.ByteCount(), 5);
+ }
+
+ // Read value back in as a varint64 and insure it matches.
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+
+ {
+ CodedInputStream coded_input(&input);
+
+ uint64 value;
+ EXPECT_TRUE(coded_input.ReadVarint64(&value));
+
+ EXPECT_EQ(kSignExtendedVarintCases_case, static_cast<int64>(value));
+ }
+
+ EXPECT_EQ(output.ByteCount(), input.ByteCount());
+}
+
+#endif
+
+
+// -------------------------------------------------------------------
+// Varint failure test.
+
+struct VarintErrorCase {
+ uint8 bytes[12];
+ int size;
+ bool can_parse;
+};
+
+inline std::ostream& operator<<(std::ostream& os, const VarintErrorCase& c) {
+ return os << "size " << c.size;
+}
+
+const VarintErrorCase kVarintErrorCases[] = {
+ // Control case. (Insures that there isn't something else wrong that
+ // makes parsing always fail.)
+ {{0x00}, 1, true},
+
+ // No input data.
+ {{}, 0, false},
+
+ // Input ends unexpectedly.
+ {{0xf0, 0xab}, 2, false},
+
+ // Input ends unexpectedly after 32 bits.
+ {{0xf0, 0xab, 0xc9, 0x9a, 0xf8, 0xb2}, 6, false},
+
+ // Longer than 10 bytes.
+ {{0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x01},
+ 11, false},
+};
+
+TEST_2D(CodedStreamTest, ReadVarint32Error, kVarintErrorCases, kBlockSizes) {
+ memcpy(buffer_, kVarintErrorCases_case.bytes, kVarintErrorCases_case.size);
+ ArrayInputStream input(buffer_, kVarintErrorCases_case.size,
+ kBlockSizes_case);
+ CodedInputStream coded_input(&input);
+
+ uint32 value;
+ EXPECT_EQ(kVarintErrorCases_case.can_parse, coded_input.ReadVarint32(&value));
+}
+
+TEST_2D(CodedStreamTest, ReadVarint64Error, kVarintErrorCases, kBlockSizes) {
+ memcpy(buffer_, kVarintErrorCases_case.bytes, kVarintErrorCases_case.size);
+ ArrayInputStream input(buffer_, kVarintErrorCases_case.size,
+ kBlockSizes_case);
+ CodedInputStream coded_input(&input);
+
+ uint64 value;
+ EXPECT_EQ(kVarintErrorCases_case.can_parse, coded_input.ReadVarint64(&value));
+}
+
+// -------------------------------------------------------------------
+// VarintSize
+
+struct VarintSizeCase {
+ uint64 value;
+ int size;
+};
+
+inline std::ostream& operator<<(std::ostream& os, const VarintSizeCase& c) {
+ return os << c.value;
+}
+
+VarintSizeCase kVarintSizeCases[] = {
+ {0u, 1},
+ {1u, 1},
+ {127u, 1},
+ {128u, 2},
+ {758923u, 3},
+ {4000000000u, 5},
+ {ULL(41256202580718336), 8},
+ {ULL(11964378330978735131), 10},
+};
+
+TEST_1D(CodedStreamTest, VarintSize32, kVarintSizeCases) {
+ if (kVarintSizeCases_case.value > 0xffffffffu) {
+ // Skip 64-bit values.
+ return;
+ }
+
+ EXPECT_EQ(kVarintSizeCases_case.size,
+ CodedOutputStream::VarintSize32(
+ static_cast<uint32>(kVarintSizeCases_case.value)));
+}
+
+TEST_1D(CodedStreamTest, VarintSize64, kVarintSizeCases) {
+ EXPECT_EQ(kVarintSizeCases_case.size,
+ CodedOutputStream::VarintSize64(kVarintSizeCases_case.value));
+}
+
+// -------------------------------------------------------------------
+// Fixed-size int tests
+
+struct Fixed32Case {
+ uint8 bytes[sizeof(uint32)]; // Encoded bytes.
+ uint32 value; // Parsed value.
+};
+
+struct Fixed64Case {
+ uint8 bytes[sizeof(uint64)]; // Encoded bytes.
+ uint64 value; // Parsed value.
+};
+
+inline std::ostream& operator<<(std::ostream& os, const Fixed32Case& c) {
+ return os << "0x" << std::hex << c.value << std::dec;
+}
+
+inline std::ostream& operator<<(std::ostream& os, const Fixed64Case& c) {
+ return os << "0x" << std::hex << c.value << std::dec;
+}
+
+Fixed32Case kFixed32Cases[] = {
+ {{0xef, 0xcd, 0xab, 0x90}, 0x90abcdefu},
+ {{0x12, 0x34, 0x56, 0x78}, 0x78563412u},
+};
+
+Fixed64Case kFixed64Cases[] = {
+ {{0xef, 0xcd, 0xab, 0x90, 0x12, 0x34, 0x56, 0x78}, ULL(0x7856341290abcdef)},
+ {{0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88}, ULL(0x8877665544332211)},
+};
+
+TEST_2D(CodedStreamTest, ReadLittleEndian32, kFixed32Cases, kBlockSizes) {
+ memcpy(buffer_, kFixed32Cases_case.bytes, sizeof(kFixed32Cases_case.bytes));
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ uint32 value;
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(kFixed32Cases_case.value, value);
+ }
+
+ EXPECT_EQ(sizeof(uint32), input.ByteCount());
+}
+
+TEST_2D(CodedStreamTest, ReadLittleEndian64, kFixed64Cases, kBlockSizes) {
+ memcpy(buffer_, kFixed64Cases_case.bytes, sizeof(kFixed64Cases_case.bytes));
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ uint64 value;
+ EXPECT_TRUE(coded_input.ReadLittleEndian64(&value));
+ EXPECT_EQ(kFixed64Cases_case.value, value);
+ }
+
+ EXPECT_EQ(sizeof(uint64), input.ByteCount());
+}
+
+TEST_2D(CodedStreamTest, WriteLittleEndian32, kFixed32Cases, kBlockSizes) {
+ ArrayOutputStream output(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedOutputStream coded_output(&output);
+
+ coded_output.WriteLittleEndian32(kFixed32Cases_case.value);
+ EXPECT_FALSE(coded_output.HadError());
+
+ EXPECT_EQ(sizeof(uint32), coded_output.ByteCount());
+ }
+
+ EXPECT_EQ(sizeof(uint32), output.ByteCount());
+ EXPECT_EQ(0, memcmp(buffer_, kFixed32Cases_case.bytes, sizeof(uint32)));
+}
+
+TEST_2D(CodedStreamTest, WriteLittleEndian64, kFixed64Cases, kBlockSizes) {
+ ArrayOutputStream output(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedOutputStream coded_output(&output);
+
+ coded_output.WriteLittleEndian64(kFixed64Cases_case.value);
+ EXPECT_FALSE(coded_output.HadError());
+
+ EXPECT_EQ(sizeof(uint64), coded_output.ByteCount());
+ }
+
+ EXPECT_EQ(sizeof(uint64), output.ByteCount());
+ EXPECT_EQ(0, memcmp(buffer_, kFixed64Cases_case.bytes, sizeof(uint64)));
+}
+
+// Tests using the static methods to read fixed-size values from raw arrays.
+
+TEST_1D(CodedStreamTest, ReadLittleEndian32FromArray, kFixed32Cases) {
+ memcpy(buffer_, kFixed32Cases_case.bytes, sizeof(kFixed32Cases_case.bytes));
+
+ uint32 value;
+ const uint8* end = CodedInputStream::ReadLittleEndian32FromArray(
+ buffer_, &value);
+ EXPECT_EQ(kFixed32Cases_case.value, value);
+ EXPECT_TRUE(end == buffer_ + sizeof(value));
+}
+
+TEST_1D(CodedStreamTest, ReadLittleEndian64FromArray, kFixed64Cases) {
+ memcpy(buffer_, kFixed64Cases_case.bytes, sizeof(kFixed64Cases_case.bytes));
+
+ uint64 value;
+ const uint8* end = CodedInputStream::ReadLittleEndian64FromArray(
+ buffer_, &value);
+ EXPECT_EQ(kFixed64Cases_case.value, value);
+ EXPECT_TRUE(end == buffer_ + sizeof(value));
+}
+
+// -------------------------------------------------------------------
+// Raw reads and writes
+
+const char kRawBytes[] = "Some bytes which will be written and read raw.";
+
+TEST_1D(CodedStreamTest, ReadRaw, kBlockSizes) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+ char read_buffer[sizeof(kRawBytes)];
+
+ {
+ CodedInputStream coded_input(&input);
+
+ EXPECT_TRUE(coded_input.ReadRaw(read_buffer, sizeof(kRawBytes)));
+ EXPECT_EQ(0, memcmp(kRawBytes, read_buffer, sizeof(kRawBytes)));
+ }
+
+ EXPECT_EQ(sizeof(kRawBytes), input.ByteCount());
+}
+
+TEST_1D(CodedStreamTest, WriteRaw, kBlockSizes) {
+ ArrayOutputStream output(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedOutputStream coded_output(&output);
+
+ coded_output.WriteRaw(kRawBytes, sizeof(kRawBytes));
+ EXPECT_FALSE(coded_output.HadError());
+
+ EXPECT_EQ(sizeof(kRawBytes), coded_output.ByteCount());
+ }
+
+ EXPECT_EQ(sizeof(kRawBytes), output.ByteCount());
+ EXPECT_EQ(0, memcmp(buffer_, kRawBytes, sizeof(kRawBytes)));
+}
+
+TEST_1D(CodedStreamTest, ReadString, kBlockSizes) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ EXPECT_EQ(kRawBytes, str);
+ }
+
+ EXPECT_EQ(strlen(kRawBytes), input.ByteCount());
+}
+
+// Check to make sure ReadString doesn't crash on impossibly large strings.
+TEST_1D(CodedStreamTest, ReadStringImpossiblyLarge, kBlockSizes) {
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ string str;
+ // Try to read a gigabyte.
+ EXPECT_FALSE(coded_input.ReadString(&str, 1 << 30));
+ }
+}
+
+TEST_F(CodedStreamTest, ReadStringImpossiblyLargeFromStringOnStack) {
+ // Same test as above, except directly use a buffer. This used to cause
+ // crashes while the above did not.
+ uint8 buffer[8];
+ CodedInputStream coded_input(buffer, 8);
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, 1 << 30));
+}
+
+TEST_F(CodedStreamTest, ReadStringImpossiblyLargeFromStringOnHeap) {
+ google::protobuf::scoped_array<uint8> buffer(new uint8[8]);
+ CodedInputStream coded_input(buffer.get(), 8);
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, 1 << 30));
+}
+
+TEST_1D(CodedStreamTest, ReadStringReservesMemoryOnTotalLimit, kBlockSizes) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.SetTotalBytesLimit(sizeof(kRawBytes), sizeof(kRawBytes));
+ EXPECT_EQ(sizeof(kRawBytes), coded_input.BytesUntilTotalBytesLimit());
+
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ EXPECT_EQ(sizeof(kRawBytes) - strlen(kRawBytes),
+ coded_input.BytesUntilTotalBytesLimit());
+ EXPECT_EQ(kRawBytes, str);
+ // TODO(liujisi): Replace with a more meaningful test (see cl/60966023).
+ EXPECT_GE(str.capacity(), strlen(kRawBytes));
+ }
+
+ EXPECT_EQ(strlen(kRawBytes), input.ByteCount());
+}
+
+TEST_1D(CodedStreamTest, ReadStringReservesMemoryOnPushedLimit, kBlockSizes) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.PushLimit(sizeof(buffer_));
+
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ EXPECT_EQ(kRawBytes, str);
+ // TODO(liujisi): Replace with a more meaningful test (see cl/60966023).
+ EXPECT_GE(str.capacity(), strlen(kRawBytes));
+ }
+
+ EXPECT_EQ(strlen(kRawBytes), input.ByteCount());
+}
+
+TEST_F(CodedStreamTest, ReadStringNoReservationIfLimitsNotSet) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ // Buffer size in the input must be smaller than sizeof(kRawBytes),
+ // otherwise check against capacity will fail as ReadStringInline()
+ // will handle the reading and will reserve the memory as needed.
+ ArrayInputStream input(buffer_, sizeof(buffer_), 32);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ EXPECT_EQ(kRawBytes, str);
+ // Note: this check depends on string class implementation. It
+ // expects that string will allocate more than strlen(kRawBytes)
+ // if the content of kRawBytes is appended to string in small
+ // chunks.
+ // TODO(liujisi): Replace with a more meaningful test (see cl/60966023).
+ EXPECT_GE(str.capacity(), strlen(kRawBytes));
+ }
+
+ EXPECT_EQ(strlen(kRawBytes), input.ByteCount());
+}
+
+TEST_F(CodedStreamTest, ReadStringNoReservationSizeIsNegative) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ // Buffer size in the input must be smaller than sizeof(kRawBytes),
+ // otherwise check against capacity will fail as ReadStringInline()
+ // will handle the reading and will reserve the memory as needed.
+ ArrayInputStream input(buffer_, sizeof(buffer_), 32);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.PushLimit(sizeof(buffer_));
+
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, -1));
+ // Note: this check depends on string class implementation. It
+ // expects that string will always allocate the same amount of
+ // memory for an empty string.
+ EXPECT_EQ(string().capacity(), str.capacity());
+ }
+}
+
+TEST_F(CodedStreamTest, ReadStringNoReservationSizeIsLarge) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ // Buffer size in the input must be smaller than sizeof(kRawBytes),
+ // otherwise check against capacity will fail as ReadStringInline()
+ // will handle the reading and will reserve the memory as needed.
+ ArrayInputStream input(buffer_, sizeof(buffer_), 32);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.PushLimit(sizeof(buffer_));
+
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, 1 << 30));
+ EXPECT_GT(1 << 30, str.capacity());
+ }
+}
+
+TEST_F(CodedStreamTest, ReadStringNoReservationSizeIsOverTheLimit) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ // Buffer size in the input must be smaller than sizeof(kRawBytes),
+ // otherwise check against capacity will fail as ReadStringInline()
+ // will handle the reading and will reserve the memory as needed.
+ ArrayInputStream input(buffer_, sizeof(buffer_), 32);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.PushLimit(16);
+
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ // Note: this check depends on string class implementation. It
+ // expects that string will allocate less than strlen(kRawBytes)
+ // for an empty string.
+ EXPECT_GT(strlen(kRawBytes), str.capacity());
+ }
+}
+
+TEST_F(CodedStreamTest, ReadStringNoReservationSizeIsOverTheTotalBytesLimit) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ // Buffer size in the input must be smaller than sizeof(kRawBytes),
+ // otherwise check against capacity will fail as ReadStringInline()
+ // will handle the reading and will reserve the memory as needed.
+ ArrayInputStream input(buffer_, sizeof(buffer_), 32);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.SetTotalBytesLimit(16, 16);
+
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ // Note: this check depends on string class implementation. It
+ // expects that string will allocate less than strlen(kRawBytes)
+ // for an empty string.
+ EXPECT_GT(strlen(kRawBytes), str.capacity());
+ }
+}
+
+TEST_F(CodedStreamTest,
+ ReadStringNoReservationSizeIsOverTheClosestLimit_GlobalLimitIsCloser) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ // Buffer size in the input must be smaller than sizeof(kRawBytes),
+ // otherwise check against capacity will fail as ReadStringInline()
+ // will handle the reading and will reserve the memory as needed.
+ ArrayInputStream input(buffer_, sizeof(buffer_), 32);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.PushLimit(sizeof(buffer_));
+ coded_input.SetTotalBytesLimit(16, 16);
+
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ // Note: this check depends on string class implementation. It
+ // expects that string will allocate less than strlen(kRawBytes)
+ // for an empty string.
+ EXPECT_GT(strlen(kRawBytes), str.capacity());
+ }
+}
+
+TEST_F(CodedStreamTest,
+ ReadStringNoReservationSizeIsOverTheClosestLimit_LocalLimitIsCloser) {
+ memcpy(buffer_, kRawBytes, sizeof(kRawBytes));
+ // Buffer size in the input must be smaller than sizeof(kRawBytes),
+ // otherwise check against capacity will fail as ReadStringInline()
+ // will handle the reading and will reserve the memory as needed.
+ ArrayInputStream input(buffer_, sizeof(buffer_), 32);
+
+ {
+ CodedInputStream coded_input(&input);
+ coded_input.PushLimit(16);
+ coded_input.SetTotalBytesLimit(sizeof(buffer_), sizeof(buffer_));
+ EXPECT_EQ(sizeof(buffer_), coded_input.BytesUntilTotalBytesLimit());
+
+ string str;
+ EXPECT_FALSE(coded_input.ReadString(&str, strlen(kRawBytes)));
+ // Note: this check depends on string class implementation. It
+ // expects that string will allocate less than strlen(kRawBytes)
+ // for an empty string.
+ EXPECT_GT(strlen(kRawBytes), str.capacity());
+ }
+}
+
+
+// -------------------------------------------------------------------
+// Skip
+
+const char kSkipTestBytes[] =
+ "<Before skipping><To be skipped><After skipping>";
+
+TEST_1D(CodedStreamTest, SkipInput, kBlockSizes) {
+ memcpy(buffer_, kSkipTestBytes, sizeof(kSkipTestBytes));
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, strlen("<Before skipping>")));
+ EXPECT_EQ("<Before skipping>", str);
+ EXPECT_TRUE(coded_input.Skip(strlen("<To be skipped>")));
+ EXPECT_TRUE(coded_input.ReadString(&str, strlen("<After skipping>")));
+ EXPECT_EQ("<After skipping>", str);
+ }
+
+ EXPECT_EQ(strlen(kSkipTestBytes), input.ByteCount());
+}
+
+// -------------------------------------------------------------------
+// GetDirectBufferPointer
+
+TEST_F(CodedStreamTest, GetDirectBufferPointerInput) {
+ ArrayInputStream input(buffer_, sizeof(buffer_), 8);
+ CodedInputStream coded_input(&input);
+
+ const void* ptr;
+ int size;
+
+ EXPECT_TRUE(coded_input.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_, ptr);
+ EXPECT_EQ(8, size);
+
+ // Peeking again should return the same pointer.
+ EXPECT_TRUE(coded_input.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_, ptr);
+ EXPECT_EQ(8, size);
+
+ // Skip forward in the same buffer then peek again.
+ EXPECT_TRUE(coded_input.Skip(3));
+ EXPECT_TRUE(coded_input.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_ + 3, ptr);
+ EXPECT_EQ(5, size);
+
+ // Skip to end of buffer and peek -- should get next buffer.
+ EXPECT_TRUE(coded_input.Skip(5));
+ EXPECT_TRUE(coded_input.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_ + 8, ptr);
+ EXPECT_EQ(8, size);
+}
+
+TEST_F(CodedStreamTest, GetDirectBufferPointerInlineInput) {
+ ArrayInputStream input(buffer_, sizeof(buffer_), 8);
+ CodedInputStream coded_input(&input);
+
+ const void* ptr;
+ int size;
+
+ coded_input.GetDirectBufferPointerInline(&ptr, &size);
+ EXPECT_EQ(buffer_, ptr);
+ EXPECT_EQ(8, size);
+
+ // Peeking again should return the same pointer.
+ coded_input.GetDirectBufferPointerInline(&ptr, &size);
+ EXPECT_EQ(buffer_, ptr);
+ EXPECT_EQ(8, size);
+
+ // Skip forward in the same buffer then peek again.
+ EXPECT_TRUE(coded_input.Skip(3));
+ coded_input.GetDirectBufferPointerInline(&ptr, &size);
+ EXPECT_EQ(buffer_ + 3, ptr);
+ EXPECT_EQ(5, size);
+
+ // Skip to end of buffer and peek -- should return false and provide an empty
+ // buffer. It does not try to Refresh().
+ EXPECT_TRUE(coded_input.Skip(5));
+ coded_input.GetDirectBufferPointerInline(&ptr, &size);
+ EXPECT_EQ(buffer_ + 8, ptr);
+ EXPECT_EQ(0, size);
+}
+
+TEST_F(CodedStreamTest, GetDirectBufferPointerOutput) {
+ ArrayOutputStream output(buffer_, sizeof(buffer_), 8);
+ CodedOutputStream coded_output(&output);
+
+ void* ptr;
+ int size;
+
+ EXPECT_TRUE(coded_output.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_, ptr);
+ EXPECT_EQ(8, size);
+
+ // Peeking again should return the same pointer.
+ EXPECT_TRUE(coded_output.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_, ptr);
+ EXPECT_EQ(8, size);
+
+ // Skip forward in the same buffer then peek again.
+ EXPECT_TRUE(coded_output.Skip(3));
+ EXPECT_TRUE(coded_output.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_ + 3, ptr);
+ EXPECT_EQ(5, size);
+
+ // Skip to end of buffer and peek -- should get next buffer.
+ EXPECT_TRUE(coded_output.Skip(5));
+ EXPECT_TRUE(coded_output.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_ + 8, ptr);
+ EXPECT_EQ(8, size);
+
+ // Skip over multiple buffers.
+ EXPECT_TRUE(coded_output.Skip(22));
+ EXPECT_TRUE(coded_output.GetDirectBufferPointer(&ptr, &size));
+ EXPECT_EQ(buffer_ + 30, ptr);
+ EXPECT_EQ(2, size);
+}
+
+// -------------------------------------------------------------------
+// Limits
+
+TEST_1D(CodedStreamTest, BasicLimit, kBlockSizes) {
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ CodedInputStream::Limit limit = coded_input.PushLimit(8);
+
+ // Read until we hit the limit.
+ uint32 value;
+ EXPECT_EQ(8, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(4, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+ EXPECT_FALSE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+
+ coded_input.PopLimit(limit);
+
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ }
+
+ EXPECT_EQ(12, input.ByteCount());
+}
+
+// Test what happens when we push two limits where the second (top) one is
+// shorter.
+TEST_1D(CodedStreamTest, SmallLimitOnTopOfBigLimit, kBlockSizes) {
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ CodedInputStream::Limit limit1 = coded_input.PushLimit(8);
+ EXPECT_EQ(8, coded_input.BytesUntilLimit());
+ CodedInputStream::Limit limit2 = coded_input.PushLimit(4);
+
+ uint32 value;
+
+ // Read until we hit limit2, the top and shortest limit.
+ EXPECT_EQ(4, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+ EXPECT_FALSE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+
+ coded_input.PopLimit(limit2);
+
+ // Read until we hit limit1.
+ EXPECT_EQ(4, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+ EXPECT_FALSE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+
+ coded_input.PopLimit(limit1);
+
+ // No more limits.
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ }
+
+ EXPECT_EQ(12, input.ByteCount());
+}
+
+// Test what happens when we push two limits where the second (top) one is
+// longer. In this case, the top limit is shortened to match the previous
+// limit.
+TEST_1D(CodedStreamTest, BigLimitOnTopOfSmallLimit, kBlockSizes) {
+ ArrayInputStream input(buffer_, sizeof(buffer_), kBlockSizes_case);
+
+ {
+ CodedInputStream coded_input(&input);
+
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ CodedInputStream::Limit limit1 = coded_input.PushLimit(4);
+ EXPECT_EQ(4, coded_input.BytesUntilLimit());
+ CodedInputStream::Limit limit2 = coded_input.PushLimit(8);
+
+ uint32 value;
+
+ // Read until we hit limit2. Except, wait! limit1 is shorter, so
+ // we end up hitting that first, despite having 4 bytes to go on
+ // limit2.
+ EXPECT_EQ(4, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+ EXPECT_FALSE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+
+ coded_input.PopLimit(limit2);
+
+ // OK, popped limit2, now limit1 is on top, which we've already hit.
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+ EXPECT_FALSE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_EQ(0, coded_input.BytesUntilLimit());
+
+ coded_input.PopLimit(limit1);
+
+ // No more limits.
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ }
+
+ EXPECT_EQ(8, input.ByteCount());
+}
+
+TEST_F(CodedStreamTest, ExpectAtEnd) {
+ // Test ExpectAtEnd(), which is based on limits.
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+ CodedInputStream coded_input(&input);
+
+ EXPECT_FALSE(coded_input.ExpectAtEnd());
+
+ CodedInputStream::Limit limit = coded_input.PushLimit(4);
+
+ uint32 value;
+ EXPECT_TRUE(coded_input.ReadLittleEndian32(&value));
+ EXPECT_TRUE(coded_input.ExpectAtEnd());
+
+ coded_input.PopLimit(limit);
+ EXPECT_FALSE(coded_input.ExpectAtEnd());
+}
+
+TEST_F(CodedStreamTest, NegativeLimit) {
+ // Check what happens when we push a negative limit.
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+ CodedInputStream coded_input(&input);
+
+ CodedInputStream::Limit limit = coded_input.PushLimit(-1234);
+ // BytesUntilLimit() returns -1 to mean "no limit", which actually means
+ // "the limit is INT_MAX relative to the beginning of the stream".
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ coded_input.PopLimit(limit);
+}
+
+TEST_F(CodedStreamTest, NegativeLimitAfterReading) {
+ // Check what happens when we push a negative limit.
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+ CodedInputStream coded_input(&input);
+ ASSERT_TRUE(coded_input.Skip(128));
+
+ CodedInputStream::Limit limit = coded_input.PushLimit(-64);
+ // BytesUntilLimit() returns -1 to mean "no limit", which actually means
+ // "the limit is INT_MAX relative to the beginning of the stream".
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ coded_input.PopLimit(limit);
+}
+
+TEST_F(CodedStreamTest, OverflowLimit) {
+ // Check what happens when we push a limit large enough that its absolute
+ // position is more than 2GB into the stream.
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+ CodedInputStream coded_input(&input);
+ ASSERT_TRUE(coded_input.Skip(128));
+
+ CodedInputStream::Limit limit = coded_input.PushLimit(INT_MAX);
+ // BytesUntilLimit() returns -1 to mean "no limit", which actually means
+ // "the limit is INT_MAX relative to the beginning of the stream".
+ EXPECT_EQ(-1, coded_input.BytesUntilLimit());
+ coded_input.PopLimit(limit);
+}
+
+TEST_F(CodedStreamTest, TotalBytesLimit) {
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+ CodedInputStream coded_input(&input);
+ coded_input.SetTotalBytesLimit(16, -1);
+ EXPECT_EQ(16, coded_input.BytesUntilTotalBytesLimit());
+
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, 16));
+ EXPECT_EQ(0, coded_input.BytesUntilTotalBytesLimit());
+
+ vector<string> errors;
+
+ {
+ ScopedMemoryLog error_log;
+ EXPECT_FALSE(coded_input.ReadString(&str, 1));
+ errors = error_log.GetMessages(ERROR);
+ }
+
+ ASSERT_EQ(1, errors.size());
+ EXPECT_PRED_FORMAT2(testing::IsSubstring,
+ "A protocol message was rejected because it was too big", errors[0]);
+
+ coded_input.SetTotalBytesLimit(32, -1);
+ EXPECT_EQ(16, coded_input.BytesUntilTotalBytesLimit());
+ EXPECT_TRUE(coded_input.ReadString(&str, 16));
+ EXPECT_EQ(0, coded_input.BytesUntilTotalBytesLimit());
+}
+
+TEST_F(CodedStreamTest, TotalBytesLimitNotValidMessageEnd) {
+ // total_bytes_limit_ is not a valid place for a message to end.
+
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+ CodedInputStream coded_input(&input);
+
+ // Set both total_bytes_limit and a regular limit at 16 bytes.
+ coded_input.SetTotalBytesLimit(16, -1);
+ CodedInputStream::Limit limit = coded_input.PushLimit(16);
+
+ // Read 16 bytes.
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, 16));
+
+ // Read a tag. Should fail, but report being a valid endpoint since it's
+ // a regular limit.
+ EXPECT_EQ(0, coded_input.ReadTag());
+ EXPECT_TRUE(coded_input.ConsumedEntireMessage());
+
+ // Pop the limit.
+ coded_input.PopLimit(limit);
+
+ // Read a tag. Should fail, and report *not* being a valid endpoint, since
+ // this time we're hitting the total bytes limit.
+ EXPECT_EQ(0, coded_input.ReadTag());
+ EXPECT_FALSE(coded_input.ConsumedEntireMessage());
+}
+
+// This method is used by the tests below.
+// It constructs a CodedInputStream with the given limits and tries to read 2KiB
+// of data from it. Then it returns the logged errors and warnings in the given
+// vectors.
+void CodedStreamTest::SetupTotalBytesLimitWarningTest(
+ int total_bytes_limit, int warning_threshold,
+ vector<string>* out_errors, vector<string>* out_warnings) {
+ ArrayInputStream raw_input(buffer_, sizeof(buffer_), 128);
+
+ ScopedMemoryLog scoped_log;
+ {
+ CodedInputStream input(&raw_input);
+ input.SetTotalBytesLimit(total_bytes_limit, warning_threshold);
+ string str;
+ EXPECT_TRUE(input.ReadString(&str, 2048));
+ }
+
+ *out_errors = scoped_log.GetMessages(ERROR);
+ *out_warnings = scoped_log.GetMessages(WARNING);
+}
+
+TEST_F(CodedStreamTest, TotalBytesLimitWarning) {
+ vector<string> errors;
+ vector<string> warnings;
+ SetupTotalBytesLimitWarningTest(10240, 1024, &errors, &warnings);
+
+ EXPECT_EQ(0, errors.size());
+
+ ASSERT_EQ(2, warnings.size());
+ EXPECT_PRED_FORMAT2(testing::IsSubstring,
+ "Reading dangerously large protocol message. If the message turns out to "
+ "be larger than 10240 bytes, parsing will be halted for security reasons.",
+ warnings[0]);
+ EXPECT_PRED_FORMAT2(testing::IsSubstring,
+ "The total number of bytes read was 2048",
+ warnings[1]);
+}
+
+TEST_F(CodedStreamTest, TotalBytesLimitWarningDisabled) {
+ vector<string> errors;
+ vector<string> warnings;
+
+ // Test with -1
+ SetupTotalBytesLimitWarningTest(10240, -1, &errors, &warnings);
+ EXPECT_EQ(0, errors.size());
+ EXPECT_EQ(0, warnings.size());
+
+ // Test again with -2, expecting the same result
+ SetupTotalBytesLimitWarningTest(10240, -2, &errors, &warnings);
+ EXPECT_EQ(0, errors.size());
+ EXPECT_EQ(0, warnings.size());
+}
+
+
+TEST_F(CodedStreamTest, RecursionLimit) {
+ ArrayInputStream input(buffer_, sizeof(buffer_));
+ CodedInputStream coded_input(&input);
+ coded_input.SetRecursionLimit(4);
+
+ // This is way too much testing for a counter.
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 1
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 2
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 3
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 4
+ EXPECT_FALSE(coded_input.IncrementRecursionDepth()); // 5
+ EXPECT_FALSE(coded_input.IncrementRecursionDepth()); // 6
+ coded_input.DecrementRecursionDepth(); // 5
+ EXPECT_FALSE(coded_input.IncrementRecursionDepth()); // 6
+ coded_input.DecrementRecursionDepth(); // 5
+ coded_input.DecrementRecursionDepth(); // 4
+ coded_input.DecrementRecursionDepth(); // 3
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 4
+ EXPECT_FALSE(coded_input.IncrementRecursionDepth()); // 5
+ coded_input.DecrementRecursionDepth(); // 4
+ coded_input.DecrementRecursionDepth(); // 3
+ coded_input.DecrementRecursionDepth(); // 2
+ coded_input.DecrementRecursionDepth(); // 1
+ coded_input.DecrementRecursionDepth(); // 0
+ coded_input.DecrementRecursionDepth(); // 0
+ coded_input.DecrementRecursionDepth(); // 0
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 1
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 2
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 3
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 4
+ EXPECT_FALSE(coded_input.IncrementRecursionDepth()); // 5
+
+ coded_input.SetRecursionLimit(6);
+ EXPECT_TRUE(coded_input.IncrementRecursionDepth()); // 6
+ EXPECT_FALSE(coded_input.IncrementRecursionDepth()); // 7
+}
+
+
+class ReallyBigInputStream : public ZeroCopyInputStream {
+ public:
+ ReallyBigInputStream() : backup_amount_(0), buffer_count_(0) {}
+ ~ReallyBigInputStream() {}
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size) {
+ // We only expect BackUp() to be called at the end.
+ EXPECT_EQ(0, backup_amount_);
+
+ switch (buffer_count_++) {
+ case 0:
+ *data = buffer_;
+ *size = sizeof(buffer_);
+ return true;
+ case 1:
+ // Return an enormously large buffer that, when combined with the 1k
+ // returned already, should overflow the total_bytes_read_ counter in
+ // CodedInputStream. Note that we'll only read the first 1024 bytes
+ // of this buffer so it's OK that we have it point at buffer_.
+ *data = buffer_;
+ *size = INT_MAX;
+ return true;
+ default:
+ return false;
+ }
+ }
+
+ void BackUp(int count) {
+ backup_amount_ = count;
+ }
+
+ bool Skip(int count) { GOOGLE_LOG(FATAL) << "Not implemented."; return false; }
+ int64 ByteCount() const { GOOGLE_LOG(FATAL) << "Not implemented."; return 0; }
+
+ int backup_amount_;
+
+ private:
+ char buffer_[1024];
+ int64 buffer_count_;
+};
+
+TEST_F(CodedStreamTest, InputOver2G) {
+ // CodedInputStream should gracefully handle input over 2G and call
+ // input.BackUp() with the correct number of bytes on destruction.
+ ReallyBigInputStream input;
+
+ vector<string> errors;
+
+ {
+ ScopedMemoryLog error_log;
+ CodedInputStream coded_input(&input);
+ string str;
+ EXPECT_TRUE(coded_input.ReadString(&str, 512));
+ EXPECT_TRUE(coded_input.ReadString(&str, 1024));
+ errors = error_log.GetMessages(ERROR);
+ }
+
+ EXPECT_EQ(INT_MAX - 512, input.backup_amount_);
+ EXPECT_EQ(0, errors.size());
+}
+
+// ===================================================================
+
+
+} // namespace
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.cc
new file mode 100644
index 0000000000..9c621b6a27
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.cc
@@ -0,0 +1,330 @@
+// 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: brianolson@google.com (Brian Olson)
+//
+// This file contains the implementation of classes GzipInputStream and
+// GzipOutputStream.
+
+
+#if HAVE_ZLIB
+#include <google/protobuf/io/gzip_stream.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+static const int kDefaultBufferSize = 65536;
+
+GzipInputStream::GzipInputStream(
+ ZeroCopyInputStream* sub_stream, Format format, int buffer_size)
+ : format_(format), sub_stream_(sub_stream), zerror_(Z_OK), byte_count_(0) {
+ zcontext_.state = Z_NULL;
+ zcontext_.zalloc = Z_NULL;
+ zcontext_.zfree = Z_NULL;
+ zcontext_.opaque = Z_NULL;
+ zcontext_.total_out = 0;
+ zcontext_.next_in = NULL;
+ zcontext_.avail_in = 0;
+ zcontext_.total_in = 0;
+ zcontext_.msg = NULL;
+ if (buffer_size == -1) {
+ output_buffer_length_ = kDefaultBufferSize;
+ } else {
+ output_buffer_length_ = buffer_size;
+ }
+ output_buffer_ = operator new(output_buffer_length_);
+ GOOGLE_CHECK(output_buffer_ != NULL);
+ zcontext_.next_out = static_cast<Bytef*>(output_buffer_);
+ zcontext_.avail_out = output_buffer_length_;
+ output_position_ = output_buffer_;
+}
+GzipInputStream::~GzipInputStream() {
+ operator delete(output_buffer_);
+ zerror_ = inflateEnd(&zcontext_);
+}
+
+static inline int internalInflateInit2(
+ z_stream* zcontext, GzipInputStream::Format format) {
+ int windowBitsFormat = 0;
+ switch (format) {
+ case GzipInputStream::GZIP: windowBitsFormat = 16; break;
+ case GzipInputStream::AUTO: windowBitsFormat = 32; break;
+ case GzipInputStream::ZLIB: windowBitsFormat = 0; break;
+ }
+ return inflateInit2(zcontext, /* windowBits */15 | windowBitsFormat);
+}
+
+int GzipInputStream::Inflate(int flush) {
+ if ((zerror_ == Z_OK) && (zcontext_.avail_out == 0)) {
+ // previous inflate filled output buffer. don't change input params yet.
+ } else if (zcontext_.avail_in == 0) {
+ const void* in;
+ int in_size;
+ bool first = zcontext_.next_in == NULL;
+ bool ok = sub_stream_->Next(&in, &in_size);
+ if (!ok) {
+ zcontext_.next_out = NULL;
+ zcontext_.avail_out = 0;
+ return Z_STREAM_END;
+ }
+ zcontext_.next_in = static_cast<Bytef*>(const_cast<void*>(in));
+ zcontext_.avail_in = in_size;
+ if (first) {
+ int error = internalInflateInit2(&zcontext_, format_);
+ if (error != Z_OK) {
+ return error;
+ }
+ }
+ }
+ zcontext_.next_out = static_cast<Bytef*>(output_buffer_);
+ zcontext_.avail_out = output_buffer_length_;
+ output_position_ = output_buffer_;
+ int error = inflate(&zcontext_, flush);
+ return error;
+}
+
+void GzipInputStream::DoNextOutput(const void** data, int* size) {
+ *data = output_position_;
+ *size = ((uintptr_t)zcontext_.next_out) - ((uintptr_t)output_position_);
+ output_position_ = zcontext_.next_out;
+}
+
+// implements ZeroCopyInputStream ----------------------------------
+bool GzipInputStream::Next(const void** data, int* size) {
+ bool ok = (zerror_ == Z_OK) || (zerror_ == Z_STREAM_END)
+ || (zerror_ == Z_BUF_ERROR);
+ if ((!ok) || (zcontext_.next_out == NULL)) {
+ return false;
+ }
+ if (zcontext_.next_out != output_position_) {
+ DoNextOutput(data, size);
+ return true;
+ }
+ if (zerror_ == Z_STREAM_END) {
+ if (zcontext_.next_out != NULL) {
+ // sub_stream_ may have concatenated streams to follow
+ zerror_ = inflateEnd(&zcontext_);
+ byte_count_ += zcontext_.total_out;
+ if (zerror_ != Z_OK) {
+ return false;
+ }
+ zerror_ = internalInflateInit2(&zcontext_, format_);
+ if (zerror_ != Z_OK) {
+ return false;
+ }
+ } else {
+ *data = NULL;
+ *size = 0;
+ return false;
+ }
+ }
+ zerror_ = Inflate(Z_NO_FLUSH);
+ if ((zerror_ == Z_STREAM_END) && (zcontext_.next_out == NULL)) {
+ // The underlying stream's Next returned false inside Inflate.
+ return false;
+ }
+ ok = (zerror_ == Z_OK) || (zerror_ == Z_STREAM_END)
+ || (zerror_ == Z_BUF_ERROR);
+ if (!ok) {
+ return false;
+ }
+ DoNextOutput(data, size);
+ return true;
+}
+void GzipInputStream::BackUp(int count) {
+ output_position_ = reinterpret_cast<void*>(
+ reinterpret_cast<uintptr_t>(output_position_) - count);
+}
+bool GzipInputStream::Skip(int count) {
+ const void* data;
+ int size;
+ bool ok = Next(&data, &size);
+ while (ok && (size < count)) {
+ count -= size;
+ ok = Next(&data, &size);
+ }
+ if (size > count) {
+ BackUp(size - count);
+ }
+ return ok;
+}
+int64 GzipInputStream::ByteCount() const {
+ int64 ret = byte_count_ + zcontext_.total_out;
+ if (zcontext_.next_out != NULL && output_position_ != NULL) {
+ ret += reinterpret_cast<uintptr_t>(zcontext_.next_out) -
+ reinterpret_cast<uintptr_t>(output_position_);
+ }
+ return ret;
+}
+
+// =========================================================================
+
+GzipOutputStream::Options::Options()
+ : format(GZIP),
+ buffer_size(kDefaultBufferSize),
+ compression_level(Z_DEFAULT_COMPRESSION),
+ compression_strategy(Z_DEFAULT_STRATEGY) {}
+
+GzipOutputStream::GzipOutputStream(ZeroCopyOutputStream* sub_stream) {
+ Init(sub_stream, Options());
+}
+
+GzipOutputStream::GzipOutputStream(ZeroCopyOutputStream* sub_stream,
+ const Options& options) {
+ Init(sub_stream, options);
+}
+
+void GzipOutputStream::Init(ZeroCopyOutputStream* sub_stream,
+ const Options& options) {
+ sub_stream_ = sub_stream;
+ sub_data_ = NULL;
+ sub_data_size_ = 0;
+
+ input_buffer_length_ = options.buffer_size;
+ input_buffer_ = operator new(input_buffer_length_);
+ GOOGLE_CHECK(input_buffer_ != NULL);
+
+ zcontext_.zalloc = Z_NULL;
+ zcontext_.zfree = Z_NULL;
+ zcontext_.opaque = Z_NULL;
+ zcontext_.next_out = NULL;
+ zcontext_.avail_out = 0;
+ zcontext_.total_out = 0;
+ zcontext_.next_in = NULL;
+ zcontext_.avail_in = 0;
+ zcontext_.total_in = 0;
+ zcontext_.msg = NULL;
+ // default to GZIP format
+ int windowBitsFormat = 16;
+ if (options.format == ZLIB) {
+ windowBitsFormat = 0;
+ }
+ zerror_ = deflateInit2(
+ &zcontext_,
+ options.compression_level,
+ Z_DEFLATED,
+ /* windowBits */15 | windowBitsFormat,
+ /* memLevel (default) */8,
+ options.compression_strategy);
+}
+
+GzipOutputStream::~GzipOutputStream() {
+ Close();
+ operator delete(input_buffer_);
+}
+
+// private
+int GzipOutputStream::Deflate(int flush) {
+ int error = Z_OK;
+ do {
+ if ((sub_data_ == NULL) || (zcontext_.avail_out == 0)) {
+ bool ok = sub_stream_->Next(&sub_data_, &sub_data_size_);
+ if (!ok) {
+ sub_data_ = NULL;
+ sub_data_size_ = 0;
+ return Z_BUF_ERROR;
+ }
+ GOOGLE_CHECK_GT(sub_data_size_, 0);
+ zcontext_.next_out = static_cast<Bytef*>(sub_data_);
+ zcontext_.avail_out = sub_data_size_;
+ }
+ error = deflate(&zcontext_, flush);
+ } while (error == Z_OK && zcontext_.avail_out == 0);
+ if ((flush == Z_FULL_FLUSH) || (flush == Z_FINISH)) {
+ // Notify lower layer of data.
+ sub_stream_->BackUp(zcontext_.avail_out);
+ // We don't own the buffer anymore.
+ sub_data_ = NULL;
+ sub_data_size_ = 0;
+ }
+ return error;
+}
+
+// implements ZeroCopyOutputStream ---------------------------------
+bool GzipOutputStream::Next(void** data, int* size) {
+ if ((zerror_ != Z_OK) && (zerror_ != Z_BUF_ERROR)) {
+ return false;
+ }
+ if (zcontext_.avail_in != 0) {
+ zerror_ = Deflate(Z_NO_FLUSH);
+ if (zerror_ != Z_OK) {
+ return false;
+ }
+ }
+ if (zcontext_.avail_in == 0) {
+ // all input was consumed. reset the buffer.
+ zcontext_.next_in = static_cast<Bytef*>(input_buffer_);
+ zcontext_.avail_in = input_buffer_length_;
+ *data = input_buffer_;
+ *size = input_buffer_length_;
+ } else {
+ // The loop in Deflate should consume all avail_in
+ GOOGLE_LOG(DFATAL) << "Deflate left bytes unconsumed";
+ }
+ return true;
+}
+void GzipOutputStream::BackUp(int count) {
+ GOOGLE_CHECK_GE(zcontext_.avail_in, count);
+ zcontext_.avail_in -= count;
+}
+int64 GzipOutputStream::ByteCount() const {
+ return zcontext_.total_in + zcontext_.avail_in;
+}
+
+bool GzipOutputStream::Flush() {
+ zerror_ = Deflate(Z_FULL_FLUSH);
+ // Return true if the flush succeeded or if it was a no-op.
+ return (zerror_ == Z_OK) ||
+ (zerror_ == Z_BUF_ERROR && zcontext_.avail_in == 0 &&
+ zcontext_.avail_out != 0);
+}
+
+bool GzipOutputStream::Close() {
+ if ((zerror_ != Z_OK) && (zerror_ != Z_BUF_ERROR)) {
+ return false;
+ }
+ do {
+ zerror_ = Deflate(Z_FINISH);
+ } while (zerror_ == Z_OK);
+ zerror_ = deflateEnd(&zcontext_);
+ bool ok = zerror_ == Z_OK;
+ zerror_ = Z_STREAM_END;
+ return ok;
+}
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
+
+#endif // HAVE_ZLIB
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.h
new file mode 100644
index 0000000000..15b02fe3d7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream.h
@@ -0,0 +1,209 @@
+// 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: brianolson@google.com (Brian Olson)
+//
+// This file contains the definition for classes GzipInputStream and
+// GzipOutputStream.
+//
+// GzipInputStream decompresses data from an underlying
+// ZeroCopyInputStream and provides the decompressed data as a
+// ZeroCopyInputStream.
+//
+// GzipOutputStream is an ZeroCopyOutputStream that compresses data to
+// an underlying ZeroCopyOutputStream.
+
+#ifndef GOOGLE_PROTOBUF_IO_GZIP_STREAM_H__
+#define GOOGLE_PROTOBUF_IO_GZIP_STREAM_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <zlib.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+// A ZeroCopyInputStream that reads compressed data through zlib
+class LIBPROTOBUF_EXPORT GzipInputStream : public ZeroCopyInputStream {
+ public:
+ // Format key for constructor
+ enum Format {
+ // zlib will autodetect gzip header or deflate stream
+ AUTO = 0,
+
+ // GZIP streams have some extra header data for file attributes.
+ GZIP = 1,
+
+ // Simpler zlib stream format.
+ ZLIB = 2,
+ };
+
+ // buffer_size and format may be -1 for default of 64kB and GZIP format
+ explicit GzipInputStream(
+ ZeroCopyInputStream* sub_stream,
+ Format format = AUTO,
+ int buffer_size = -1);
+ virtual ~GzipInputStream();
+
+ // Return last error message or NULL if no error.
+ inline const char* ZlibErrorMessage() const {
+ return zcontext_.msg;
+ }
+ inline int ZlibErrorCode() const {
+ return zerror_;
+ }
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size);
+ void BackUp(int count);
+ bool Skip(int count);
+ int64 ByteCount() const;
+
+ private:
+ Format format_;
+
+ ZeroCopyInputStream* sub_stream_;
+
+ z_stream zcontext_;
+ int zerror_;
+
+ void* output_buffer_;
+ void* output_position_;
+ size_t output_buffer_length_;
+ int64 byte_count_;
+
+ int Inflate(int flush);
+ void DoNextOutput(const void** data, int* size);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(GzipInputStream);
+};
+
+
+class LIBPROTOBUF_EXPORT GzipOutputStream : public ZeroCopyOutputStream {
+ public:
+ // Format key for constructor
+ enum Format {
+ // GZIP streams have some extra header data for file attributes.
+ GZIP = 1,
+
+ // Simpler zlib stream format.
+ ZLIB = 2,
+ };
+
+ struct Options {
+ // Defaults to GZIP.
+ Format format;
+
+ // What size buffer to use internally. Defaults to 64kB.
+ int buffer_size;
+
+ // A number between 0 and 9, where 0 is no compression and 9 is best
+ // compression. Defaults to Z_DEFAULT_COMPRESSION (see zlib.h).
+ int compression_level;
+
+ // Defaults to Z_DEFAULT_STRATEGY. Can also be set to Z_FILTERED,
+ // Z_HUFFMAN_ONLY, or Z_RLE. See the documentation for deflateInit2 in
+ // zlib.h for definitions of these constants.
+ int compression_strategy;
+
+ Options(); // Initializes with default values.
+ };
+
+ // Create a GzipOutputStream with default options.
+ explicit GzipOutputStream(ZeroCopyOutputStream* sub_stream);
+
+ // Create a GzipOutputStream with the given options.
+ GzipOutputStream(
+ ZeroCopyOutputStream* sub_stream,
+ const Options& options);
+
+ virtual ~GzipOutputStream();
+
+ // Return last error message or NULL if no error.
+ inline const char* ZlibErrorMessage() const {
+ return zcontext_.msg;
+ }
+ inline int ZlibErrorCode() const {
+ return zerror_;
+ }
+
+ // Flushes data written so far to zipped data in the underlying stream.
+ // It is the caller's responsibility to flush the underlying stream if
+ // necessary.
+ // Compression may be less efficient stopping and starting around flushes.
+ // Returns true if no error.
+ //
+ // Please ensure that block size is > 6. Here is an excerpt from the zlib
+ // doc that explains why:
+ //
+ // In the case of a Z_FULL_FLUSH or Z_SYNC_FLUSH, make sure that avail_out
+ // is greater than six to avoid repeated flush markers due to
+ // avail_out == 0 on return.
+ bool Flush();
+
+ // Writes out all data and closes the gzip stream.
+ // It is the caller's responsibility to close the underlying stream if
+ // necessary.
+ // Returns true if no error.
+ bool Close();
+
+ // implements ZeroCopyOutputStream ---------------------------------
+ bool Next(void** data, int* size);
+ void BackUp(int count);
+ int64 ByteCount() const;
+
+ private:
+ ZeroCopyOutputStream* sub_stream_;
+ // Result from calling Next() on sub_stream_
+ void* sub_data_;
+ int sub_data_size_;
+
+ z_stream zcontext_;
+ int zerror_;
+ void* input_buffer_;
+ size_t input_buffer_length_;
+
+ // Shared constructor code.
+ void Init(ZeroCopyOutputStream* sub_stream, const Options& options);
+
+ // Do some compression.
+ // Takes zlib flush mode.
+ // Returns zlib error code.
+ int Deflate(int flush);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(GzipOutputStream);
+};
+
+} // namespace io
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_GZIP_STREAM_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream_unittest.sh b/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream_unittest.sh
new file mode 100755
index 0000000000..16251a94d3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/gzip_stream_unittest.sh
@@ -0,0 +1,44 @@
+#!/bin/sh -x
+#
+# Protocol Buffers - Google's data interchange format
+# Copyright 2009 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: brianolson@google.com (Brian Olson)
+#
+# Test compatibility between command line gzip/gunzip binaries and
+# ZeroCopyStream versions.
+
+TESTFILE=Makefile
+
+(./zcgzip < ${TESTFILE} | gunzip | cmp - ${TESTFILE}) && \
+(gzip < ${TESTFILE} | ./zcgunzip | cmp - ${TESTFILE})
+
+# Result of "(cmd) && (cmd)" implicitly becomes result of this script
+# and thus the test.
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/package_info.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/package_info.h
new file mode 100644
index 0000000000..dc1fc91e5b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/package_info.h
@@ -0,0 +1,54 @@
+// 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 exists solely to document the google::protobuf::io namespace.
+// It is not compiled into anything, but it may be read by an automated
+// documentation generator.
+
+namespace google {
+
+namespace protobuf {
+
+// Auxiliary classes used for I/O.
+//
+// The Protocol Buffer library uses the classes in this package to deal with
+// I/O and encoding/decoding raw bytes. Most users will not need to
+// deal with this package. However, users who want to adapt the system to
+// work with their own I/O abstractions -- e.g., to allow Protocol Buffers
+// to be read from a different kind of input stream without the need for a
+// temporary buffer -- should take a closer look.
+namespace io {}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/printer.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/printer.cc
new file mode 100644
index 0000000000..7532b098bc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/printer.cc
@@ -0,0 +1,346 @@
+// 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.
+
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+Printer::Printer(ZeroCopyOutputStream* output, char variable_delimiter)
+ : variable_delimiter_(variable_delimiter),
+ output_(output),
+ buffer_(NULL),
+ buffer_size_(0),
+ offset_(0),
+ at_start_of_line_(true),
+ failed_(false),
+ annotation_collector_(NULL) {}
+
+Printer::Printer(ZeroCopyOutputStream* output, char variable_delimiter,
+ AnnotationCollector* annotation_collector)
+ : variable_delimiter_(variable_delimiter),
+ output_(output),
+ buffer_(NULL),
+ buffer_size_(0),
+ offset_(0),
+ at_start_of_line_(true),
+ failed_(false),
+ annotation_collector_(annotation_collector) {}
+
+Printer::~Printer() {
+ // Only BackUp() if we have called Next() at least once and never failed.
+ if (buffer_size_ > 0 && !failed_) {
+ output_->BackUp(buffer_size_);
+ }
+}
+
+bool Printer::GetSubstitutionRange(const char* varname,
+ pair<size_t, size_t>* range) {
+ map<string, pair<size_t, size_t> >::const_iterator iter =
+ substitutions_.find(varname);
+ if (iter == substitutions_.end()) {
+ GOOGLE_LOG(DFATAL) << " Undefined variable in annotation: " << varname;
+ return false;
+ }
+ if (iter->second.first > iter->second.second) {
+ GOOGLE_LOG(DFATAL) << " Variable used for annotation used multiple times: "
+ << varname;
+ return false;
+ }
+ *range = iter->second;
+ return true;
+}
+
+void Printer::Annotate(const char* begin_varname, const char* end_varname,
+ const string& file_path, const vector<int>& path) {
+ if (annotation_collector_ == NULL) {
+ // Can't generate signatures with this Printer.
+ return;
+ }
+ pair<size_t, size_t> begin, end;
+ if (!GetSubstitutionRange(begin_varname, &begin) ||
+ !GetSubstitutionRange(end_varname, &end)) {
+ return;
+ }
+ if (begin.first > end.second) {
+ GOOGLE_LOG(DFATAL) << " Annotation has negative length from " << begin_varname
+ << " to " << end_varname;
+ } else {
+ annotation_collector_->AddAnnotation(begin.first, end.second, file_path,
+ path);
+ }
+}
+
+void Printer::Print(const map<string, string>& variables, const char* text) {
+ int size = strlen(text);
+ int pos = 0; // The number of bytes we've written so far.
+ substitutions_.clear();
+
+ for (int i = 0; i < size; i++) {
+ if (text[i] == '\n') {
+ // Saw newline. If there is more text, we may need to insert an indent
+ // here. So, write what we have so far, including the '\n'.
+ WriteRaw(text + pos, i - pos + 1);
+ pos = i + 1;
+
+ // Setting this true will cause the next WriteRaw() to insert an indent
+ // first.
+ at_start_of_line_ = true;
+
+ } else if (text[i] == variable_delimiter_) {
+ // Saw the start of a variable name.
+
+ // Write what we have so far.
+ WriteRaw(text + pos, i - pos);
+ pos = i + 1;
+
+ // Find closing delimiter.
+ const char* end = strchr(text + pos, variable_delimiter_);
+ if (end == NULL) {
+ GOOGLE_LOG(DFATAL) << " Unclosed variable name.";
+ end = text + pos;
+ }
+ int endpos = end - text;
+
+ string varname(text + pos, endpos - pos);
+ if (varname.empty()) {
+ // Two delimiters in a row reduce to a literal delimiter character.
+ WriteRaw(&variable_delimiter_, 1);
+ } else {
+ // Replace with the variable's value.
+ map<string, string>::const_iterator iter = variables.find(varname);
+ if (iter == variables.end()) {
+ GOOGLE_LOG(DFATAL) << " Undefined variable: " << varname;
+ } else {
+ size_t begin = offset_;
+ WriteRaw(iter->second.data(), iter->second.size());
+ pair<map<string, pair<size_t, size_t> >::iterator, bool> inserted =
+ substitutions_.insert(
+ std::make_pair(varname, std::make_pair(begin, offset_)));
+ if (!inserted.second) {
+ // This variable was used multiple times. Make its span have
+ // negative length so we can detect it if it gets used in an
+ // annotation.
+ inserted.first->second = std::make_pair(1, 0);
+ }
+ }
+ }
+
+ // Advance past this variable.
+ i = endpos;
+ pos = endpos + 1;
+ }
+ }
+
+ // Write the rest.
+ WriteRaw(text + pos, size - pos);
+}
+
+void Printer::Print(const char* text) {
+ static map<string, string> empty;
+ Print(empty, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable, const string& value) {
+ map<string, string> vars;
+ vars[variable] = value;
+ Print(vars, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable1, const string& value1,
+ const char* variable2, const string& value2) {
+ map<string, string> vars;
+ vars[variable1] = value1;
+ vars[variable2] = value2;
+ Print(vars, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3) {
+ map<string, string> vars;
+ vars[variable1] = value1;
+ vars[variable2] = value2;
+ vars[variable3] = value3;
+ Print(vars, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4) {
+ map<string, string> vars;
+ vars[variable1] = value1;
+ vars[variable2] = value2;
+ vars[variable3] = value3;
+ vars[variable4] = value4;
+ Print(vars, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5) {
+ map<string, string> vars;
+ vars[variable1] = value1;
+ vars[variable2] = value2;
+ vars[variable3] = value3;
+ vars[variable4] = value4;
+ vars[variable5] = value5;
+ Print(vars, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5,
+ const char* variable6, const string& value6) {
+ map<string, string> vars;
+ vars[variable1] = value1;
+ vars[variable2] = value2;
+ vars[variable3] = value3;
+ vars[variable4] = value4;
+ vars[variable5] = value5;
+ vars[variable6] = value6;
+ Print(vars, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5,
+ const char* variable6, const string& value6,
+ const char* variable7, const string& value7) {
+ map<string, string> vars;
+ vars[variable1] = value1;
+ vars[variable2] = value2;
+ vars[variable3] = value3;
+ vars[variable4] = value4;
+ vars[variable5] = value5;
+ vars[variable6] = value6;
+ vars[variable7] = value7;
+ Print(vars, text);
+}
+
+void Printer::Print(const char* text,
+ const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5,
+ const char* variable6, const string& value6,
+ const char* variable7, const string& value7,
+ const char* variable8, const string& value8) {
+ map<string, string> vars;
+ vars[variable1] = value1;
+ vars[variable2] = value2;
+ vars[variable3] = value3;
+ vars[variable4] = value4;
+ vars[variable5] = value5;
+ vars[variable6] = value6;
+ vars[variable7] = value7;
+ vars[variable8] = value8;
+ Print(vars, text);
+}
+
+void Printer::Indent() {
+ indent_ += " ";
+}
+
+void Printer::Outdent() {
+ if (indent_.empty()) {
+ GOOGLE_LOG(DFATAL) << " Outdent() without matching Indent().";
+ return;
+ }
+
+ indent_.resize(indent_.size() - 2);
+}
+
+void Printer::PrintRaw(const string& data) {
+ WriteRaw(data.data(), data.size());
+}
+
+void Printer::PrintRaw(const char* data) {
+ if (failed_) return;
+ WriteRaw(data, strlen(data));
+}
+
+void Printer::WriteRaw(const char* data, int size) {
+ if (failed_) return;
+ if (size == 0) return;
+
+ if (at_start_of_line_ && (size > 0) && (data[0] != '\n')) {
+ // Insert an indent.
+ at_start_of_line_ = false;
+ WriteRaw(indent_.data(), indent_.size());
+ if (failed_) return;
+ }
+
+ while (size > buffer_size_) {
+ // Data exceeds space in the buffer. Copy what we can and request a
+ // new buffer.
+ memcpy(buffer_, data, buffer_size_);
+ offset_ += buffer_size_;
+ data += buffer_size_;
+ size -= buffer_size_;
+ void* void_buffer;
+ failed_ = !output_->Next(&void_buffer, &buffer_size_);
+ if (failed_) return;
+ buffer_ = reinterpret_cast<char*>(void_buffer);
+ }
+
+ // Buffer is big enough to receive the data; copy it.
+ memcpy(buffer_, data, size);
+ buffer_ += size;
+ buffer_size_ -= size;
+ offset_ += size;
+}
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/printer.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/printer.h
new file mode 100644
index 0000000000..e78e2efdcc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/printer.h
@@ -0,0 +1,353 @@
+// 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.
+//
+// Utility class for writing text to a ZeroCopyOutputStream.
+
+#ifndef GOOGLE_PROTOBUF_IO_PRINTER_H__
+#define GOOGLE_PROTOBUF_IO_PRINTER_H__
+
+#include <string>
+#include <map>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+class ZeroCopyOutputStream; // zero_copy_stream.h
+
+// Records annotations about a Printer's output.
+class LIBPROTOBUF_EXPORT AnnotationCollector {
+ public:
+ // Records that the bytes in file_path beginning with begin_offset and ending
+ // before end_offset are associated with the SourceCodeInfo-style path.
+ virtual void AddAnnotation(size_t begin_offset, size_t end_offset,
+ const string& file_path,
+ const vector<int>& path) = 0;
+
+ virtual ~AnnotationCollector() {}
+};
+
+// Records annotations about a Printer's output to the given protocol buffer,
+// assuming that the buffer has an ::Annotation message exposing path,
+// source_file, begin and end fields.
+template <typename AnnotationProto>
+class AnnotationProtoCollector : public AnnotationCollector {
+ public:
+ // annotation_proto is the protocol buffer to which new Annotations should be
+ // added. It is not owned by the AnnotationProtoCollector.
+ explicit AnnotationProtoCollector(AnnotationProto* annotation_proto)
+ : annotation_proto_(annotation_proto) {}
+
+ // Override for AnnotationCollector::AddAnnotation.
+ virtual void AddAnnotation(size_t begin_offset, size_t end_offset,
+ const string& file_path, const vector<int>& path) {
+ typename AnnotationProto::Annotation* annotation =
+ annotation_proto_->add_annotation();
+ for (int i = 0; i < path.size(); ++i) {
+ annotation->add_path(path[i]);
+ }
+ annotation->set_source_file(file_path);
+ annotation->set_begin(begin_offset);
+ annotation->set_end(end_offset);
+ }
+
+ private:
+ // The protocol buffer to which new annotations should be added.
+ AnnotationProto* const annotation_proto_;
+};
+
+// This simple utility class assists in code generation. It basically
+// allows the caller to define a set of variables and then output some
+// text with variable substitutions. Example usage:
+//
+// Printer printer(output, '$');
+// map<string, string> vars;
+// vars["name"] = "Bob";
+// printer.Print(vars, "My name is $name$.");
+//
+// The above writes "My name is Bob." to the output stream.
+//
+// Printer aggressively enforces correct usage, crashing (with assert failures)
+// in the case of undefined variables in debug builds. This helps greatly in
+// debugging code which uses it.
+//
+// If a Printer is constructed with an AnnotationCollector, it will provide it
+// with annotations that connect the Printer's output to paths that can identify
+// various descriptors. In the above example, if person_ is a descriptor that
+// identifies Bob, we can associate the output string "My name is Bob." with
+// a source path pointing to that descriptor with:
+//
+// printer.Annotate("name", person_);
+//
+// The AnnotationCollector will be sent an annotation linking the output range
+// covering "Bob" to the logical path provided by person_. Tools may use
+// this association to (for example) link "Bob" in the output back to the
+// source file that defined the person_ descriptor identifying Bob.
+//
+// Annotate can only examine variables substituted during the last call to
+// Print. It is invalid to refer to a variable that was used multiple times
+// in a single Print call.
+//
+// In full generality, one may specify a range of output text using a beginning
+// substitution variable and an ending variable. The resulting annotation will
+// span from the first character of the substituted value for the beginning
+// variable to the last character of the substituted value for the ending
+// variable. For example, the Annotate call above is equivalent to this one:
+//
+// printer.Annotate("name", "name", person_);
+//
+// This is useful if multiple variables combine to form a single span of output
+// that should be annotated with the same source path. For example:
+//
+// Printer printer(output, '$');
+// map<string, string> vars;
+// vars["first"] = "Alice";
+// vars["last"] = "Smith";
+// printer.Print(vars, "My name is $first$ $last$.");
+// printer.Annotate("first", "last", person_);
+//
+// This code would associate the span covering "Alice Smith" in the output with
+// the person_ descriptor.
+//
+// Note that the beginning variable must come before (or overlap with, in the
+// case of zero-sized substitution values) the ending variable.
+//
+// It is also sometimes useful to use variables with zero-sized values as
+// markers. This avoids issues with multiple references to the same variable
+// and also allows annotation ranges to span literal text from the Print
+// templates:
+//
+// Printer printer(output, '$');
+// map<string, string> vars;
+// vars["foo"] = "bar";
+// vars["function"] = "call";
+// vars["mark"] = "";
+// printer.Print(vars, "$function$($foo$,$foo$)$mark$");
+// printer.Annotate("function", "rmark", call_);
+//
+// This code associates the span covering "call(bar,bar)" in the output with the
+// call_ descriptor.
+
+class LIBPROTOBUF_EXPORT Printer {
+ public:
+ // Create a printer that writes text to the given output stream. Use the
+ // given character as the delimiter for variables.
+ Printer(ZeroCopyOutputStream* output, char variable_delimiter);
+
+ // Create a printer that writes text to the given output stream. Use the
+ // given character as the delimiter for variables. If annotation_collector
+ // is not null, Printer will provide it with annotations about code written
+ // to the stream. annotation_collector is not owned by Printer.
+ Printer(ZeroCopyOutputStream* output, char variable_delimiter,
+ AnnotationCollector* annotation_collector);
+
+ ~Printer();
+
+ // Link a subsitution variable emitted by the last call to Print to the object
+ // described by descriptor.
+ template <typename SomeDescriptor>
+ void Annotate(const char* varname, const SomeDescriptor* descriptor) {
+ Annotate(varname, varname, descriptor);
+ }
+
+ // Link the output range defined by the substitution variables as emitted by
+ // the last call to Print to the object described by descriptor. The range
+ // begins at begin_varname's value and ends after the last character of the
+ // value substituted for end_varname.
+ template <typename SomeDescriptor>
+ void Annotate(const char* begin_varname, const char* end_varname,
+ const SomeDescriptor* descriptor) {
+ if (annotation_collector_ == NULL) {
+ // Annotations aren't turned on for this Printer, so don't pay the cost
+ // of building the location path.
+ return;
+ }
+ vector<int> path;
+ descriptor->GetLocationPath(&path);
+ Annotate(begin_varname, end_varname, descriptor->file()->name(), path);
+ }
+
+ // Link a subsitution variable emitted by the last call to Print to the file
+ // with path file_name.
+ void Annotate(const char* varname, const string& file_name) {
+ Annotate(varname, varname, file_name);
+ }
+
+ // Link the output range defined by the substitution variables as emitted by
+ // the last call to Print to the file with path file_name. The range begins
+ // at begin_varname's value and ends after the last character of the value
+ // substituted for end_varname.
+ void Annotate(const char* begin_varname, const char* end_varname,
+ const string& file_name) {
+ if (annotation_collector_ == NULL) {
+ // Annotations aren't turned on for this Printer.
+ return;
+ }
+ vector<int> empty_path;
+ Annotate(begin_varname, end_varname, file_name, empty_path);
+ }
+
+ // Print some text after applying variable substitutions. If a particular
+ // variable in the text is not defined, this will crash. Variables to be
+ // substituted are identified by their names surrounded by delimiter
+ // characters (as given to the constructor). The variable bindings are
+ // defined by the given map.
+ void Print(const map<string, string>& variables, const char* text);
+
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable, const string& value);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable1, const string& value1,
+ const char* variable2, const string& value2);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5,
+ const char* variable6, const string& value6);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5,
+ const char* variable6, const string& value6,
+ const char* variable7, const string& value7);
+ // Like the first Print(), except the substitutions are given as parameters.
+ void Print(const char* text, const char* variable1, const string& value1,
+ const char* variable2, const string& value2,
+ const char* variable3, const string& value3,
+ const char* variable4, const string& value4,
+ const char* variable5, const string& value5,
+ const char* variable6, const string& value6,
+ const char* variable7, const string& value7,
+ const char* variable8, const string& value8);
+
+ // Indent text by two spaces. After calling Indent(), two spaces will be
+ // inserted at the beginning of each line of text. Indent() may be called
+ // multiple times to produce deeper indents.
+ void Indent();
+
+ // Reduces the current indent level by two spaces, or crashes if the indent
+ // level is zero.
+ void Outdent();
+
+ // Write a string to the output buffer.
+ // This method does not look for newlines to add indentation.
+ void PrintRaw(const string& data);
+
+ // Write a zero-delimited string to output buffer.
+ // This method does not look for newlines to add indentation.
+ void PrintRaw(const char* data);
+
+ // Write some bytes to the output buffer.
+ // This method does not look for newlines to add indentation.
+ void WriteRaw(const char* data, int size);
+
+ // True if any write to the underlying stream failed. (We don't just
+ // crash in this case because this is an I/O failure, not a programming
+ // error.)
+ bool failed() const { return failed_; }
+
+ private:
+ // Link the output range defined by the substitution variables as emitted by
+ // the last call to Print to the object found at the SourceCodeInfo-style path
+ // in a file with path file_path. The range begins at the start of
+ // begin_varname's value and ends after the last character of the value
+ // substituted for end_varname. Note that begin_varname and end_varname
+ // may refer to the same variable.
+ void Annotate(const char* begin_varname, const char* end_varname,
+ const string& file_path, const vector<int>& path);
+
+ const char variable_delimiter_;
+
+ ZeroCopyOutputStream* const output_;
+ char* buffer_;
+ int buffer_size_;
+ // The current position, in bytes, in the output stream. This is equivalent
+ // to the total number of bytes that have been written so far. This value is
+ // used to calculate annotation ranges in the substitutions_ map below.
+ size_t offset_;
+
+ string indent_;
+ bool at_start_of_line_;
+ bool failed_;
+
+ // A map from variable name to [start, end) offsets in the output buffer.
+ // These refer to the offsets used for a variable after the last call to
+ // Print. If a variable was used more than once, the entry used in
+ // this map is set to a negative-length span. For singly-used variables, the
+ // start offset is the beginning of the substitution; the end offset is the
+ // last byte of the substitution plus one (such that (end - start) is the
+ // length of the substituted string).
+ map<string, pair<size_t, size_t> > substitutions_;
+
+ // Returns true and sets range to the substitution range in the output for
+ // varname if varname was used once in the last call to Print. If varname
+ // was not used, or if it was used multiple times, returns false (and
+ // fails a debug assertion).
+ bool GetSubstitutionRange(const char* varname, pair<size_t, size_t>* range);
+
+ // If non-null, annotation_collector_ is used to store annotations about
+ // generated code.
+ AnnotationCollector* const annotation_collector_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Printer);
+};
+
+} // namespace io
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_PRINTER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/printer_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/printer_unittest.cc
new file mode 100644
index 0000000000..95f3afa218
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/printer_unittest.cc
@@ -0,0 +1,523 @@
+// 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.
+
+#include <vector>
+
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.pb.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+namespace {
+
+// Each test repeats over several block sizes in order to test both cases
+// where particular writes cross a buffer boundary and cases where they do
+// not.
+
+TEST(Printer, EmptyPrinter) {
+ char buffer[8192];
+ const int block_size = 100;
+ ArrayOutputStream output(buffer, GOOGLE_ARRAYSIZE(buffer), block_size);
+ Printer printer(&output, '\0');
+ EXPECT_TRUE(!printer.failed());
+}
+
+TEST(Printer, BasicPrinting) {
+ char buffer[8192];
+
+ for (int block_size = 1; block_size < 512; block_size *= 2) {
+ ArrayOutputStream output(buffer, sizeof(buffer), block_size);
+
+ {
+ Printer printer(&output, '\0');
+
+ printer.Print("Hello World!");
+ printer.Print(" This is the same line.\n");
+ printer.Print("But this is a new one.\nAnd this is another one.");
+
+ EXPECT_FALSE(printer.failed());
+ }
+
+ buffer[output.ByteCount()] = '\0';
+
+ EXPECT_STREQ("Hello World! This is the same line.\n"
+ "But this is a new one.\n"
+ "And this is another one.",
+ buffer);
+ }
+}
+
+TEST(Printer, WriteRaw) {
+ char buffer[8192];
+
+ for (int block_size = 1; block_size < 512; block_size *= 2) {
+ ArrayOutputStream output(buffer, sizeof(buffer), block_size);
+
+ {
+ string string_obj = "From an object\n";
+ Printer printer(&output, '$');
+ printer.WriteRaw("Hello World!", 12);
+ printer.PrintRaw(" This is the same line.\n");
+ printer.PrintRaw("But this is a new one.\nAnd this is another one.");
+ printer.WriteRaw("\n", 1);
+ printer.PrintRaw(string_obj);
+ EXPECT_FALSE(printer.failed());
+ }
+
+ buffer[output.ByteCount()] = '\0';
+
+ EXPECT_STREQ("Hello World! This is the same line.\n"
+ "But this is a new one.\n"
+ "And this is another one."
+ "\n"
+ "From an object\n",
+ buffer);
+ }
+}
+
+TEST(Printer, VariableSubstitution) {
+ char buffer[8192];
+
+ for (int block_size = 1; block_size < 512; block_size *= 2) {
+ ArrayOutputStream output(buffer, sizeof(buffer), block_size);
+
+ {
+ Printer printer(&output, '$');
+ map<string, string> vars;
+
+ vars["foo"] = "World";
+ vars["bar"] = "$foo$";
+ vars["abcdefg"] = "1234";
+
+ printer.Print(vars, "Hello $foo$!\nbar = $bar$\n");
+ printer.PrintRaw("RawBit\n");
+ printer.Print(vars, "$abcdefg$\nA literal dollar sign: $$");
+
+ vars["foo"] = "blah";
+ printer.Print(vars, "\nNow foo = $foo$.");
+
+ EXPECT_FALSE(printer.failed());
+ }
+
+ buffer[output.ByteCount()] = '\0';
+
+ EXPECT_STREQ("Hello World!\n"
+ "bar = $foo$\n"
+ "RawBit\n"
+ "1234\n"
+ "A literal dollar sign: $\n"
+ "Now foo = blah.",
+ buffer);
+ }
+}
+
+TEST(Printer, InlineVariableSubstitution) {
+ char buffer[8192];
+
+ ArrayOutputStream output(buffer, sizeof(buffer));
+
+ {
+ Printer printer(&output, '$');
+ printer.Print("Hello $foo$!\n", "foo", "World");
+ printer.PrintRaw("RawBit\n");
+ printer.Print("$foo$ $bar$\n", "foo", "one", "bar", "two");
+ EXPECT_FALSE(printer.failed());
+ }
+
+ buffer[output.ByteCount()] = '\0';
+
+ EXPECT_STREQ("Hello World!\n"
+ "RawBit\n"
+ "one two\n",
+ buffer);
+}
+
+// MockDescriptorFile defines only those members that Printer uses to write out
+// annotations.
+class MockDescriptorFile {
+ public:
+ explicit MockDescriptorFile(const string& file) : file_(file) {}
+
+ // The mock filename for this file.
+ const string& name() const { return file_; }
+
+ private:
+ string file_;
+};
+
+// MockDescriptor defines only those members that Printer uses to write out
+// annotations.
+class MockDescriptor {
+ public:
+ MockDescriptor(const string& file, const vector<int>& path)
+ : file_(file), path_(path) {}
+
+ // The mock file in which this descriptor was defined.
+ const MockDescriptorFile* file() const { return &file_; }
+
+ private:
+ // Allows access to GetLocationPath.
+ friend class ::google::protobuf::io::Printer;
+
+ // Copies the pre-stored path to output.
+ void GetLocationPath(std::vector<int>* output) const { *output = path_; }
+
+ MockDescriptorFile file_;
+ vector<int> path_;
+};
+
+TEST(Printer, AnnotateMap) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ map<string, string> vars;
+ vars["foo"] = "3";
+ vars["bar"] = "5";
+ printer.Print(vars, "012$foo$4$bar$\n");
+ vector<int> path_1;
+ path_1.push_back(33);
+ vector<int> path_2;
+ path_2.push_back(11);
+ path_2.push_back(22);
+ MockDescriptor descriptor_1("path_1", path_1);
+ MockDescriptor descriptor_2("path_2", path_2);
+ printer.Annotate("foo", "foo", &descriptor_1);
+ printer.Annotate("bar", "bar", &descriptor_2);
+ }
+ buffer[output.ByteCount()] = '\0';
+ EXPECT_STREQ("012345\n", buffer);
+ ASSERT_EQ(2, info.annotation_size());
+ const GeneratedCodeInfo::Annotation* foo = info.annotation(0).path_size() == 1
+ ? &info.annotation(0)
+ : &info.annotation(1);
+ const GeneratedCodeInfo::Annotation* bar = info.annotation(0).path_size() == 1
+ ? &info.annotation(1)
+ : &info.annotation(0);
+ ASSERT_EQ(1, foo->path_size());
+ ASSERT_EQ(2, bar->path_size());
+ EXPECT_EQ(33, foo->path(0));
+ EXPECT_EQ(11, bar->path(0));
+ EXPECT_EQ(22, bar->path(1));
+ EXPECT_EQ("path_1", foo->source_file());
+ EXPECT_EQ("path_2", bar->source_file());
+ EXPECT_EQ(3, foo->begin());
+ EXPECT_EQ(4, foo->end());
+ EXPECT_EQ(5, bar->begin());
+ EXPECT_EQ(6, bar->end());
+}
+
+TEST(Printer, AnnotateInline) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ printer.Print("012$foo$4$bar$\n", "foo", "3", "bar", "5");
+ vector<int> path_1;
+ path_1.push_back(33);
+ vector<int> path_2;
+ path_2.push_back(11);
+ path_2.push_back(22);
+ MockDescriptor descriptor_1("path_1", path_1);
+ MockDescriptor descriptor_2("path_2", path_2);
+ printer.Annotate("foo", "foo", &descriptor_1);
+ printer.Annotate("bar", "bar", &descriptor_2);
+ }
+ buffer[output.ByteCount()] = '\0';
+ EXPECT_STREQ("012345\n", buffer);
+ ASSERT_EQ(2, info.annotation_size());
+ const GeneratedCodeInfo::Annotation* foo = info.annotation(0).path_size() == 1
+ ? &info.annotation(0)
+ : &info.annotation(1);
+ const GeneratedCodeInfo::Annotation* bar = info.annotation(0).path_size() == 1
+ ? &info.annotation(1)
+ : &info.annotation(0);
+ ASSERT_EQ(1, foo->path_size());
+ ASSERT_EQ(2, bar->path_size());
+ EXPECT_EQ(33, foo->path(0));
+ EXPECT_EQ(11, bar->path(0));
+ EXPECT_EQ(22, bar->path(1));
+ EXPECT_EQ("path_1", foo->source_file());
+ EXPECT_EQ("path_2", bar->source_file());
+ EXPECT_EQ(3, foo->begin());
+ EXPECT_EQ(4, foo->end());
+ EXPECT_EQ(5, bar->begin());
+ EXPECT_EQ(6, bar->end());
+}
+
+TEST(Printer, AnnotateRange) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ printer.Print("012$foo$4$bar$\n", "foo", "3", "bar", "5");
+ vector<int> path;
+ path.push_back(33);
+ MockDescriptor descriptor("path", path);
+ printer.Annotate("foo", "bar", &descriptor);
+ }
+ buffer[output.ByteCount()] = '\0';
+ EXPECT_STREQ("012345\n", buffer);
+ ASSERT_EQ(1, info.annotation_size());
+ const GeneratedCodeInfo::Annotation* foobar = &info.annotation(0);
+ ASSERT_EQ(1, foobar->path_size());
+ EXPECT_EQ(33, foobar->path(0));
+ EXPECT_EQ("path", foobar->source_file());
+ EXPECT_EQ(3, foobar->begin());
+ EXPECT_EQ(6, foobar->end());
+}
+
+TEST(Printer, AnnotateEmptyRange) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ printer.Print("012$foo$4$baz$$bam$$bar$\n", "foo", "3", "bar", "5", "baz",
+ "", "bam", "");
+ vector<int> path;
+ path.push_back(33);
+ MockDescriptor descriptor("path", path);
+ printer.Annotate("baz", "bam", &descriptor);
+ }
+ buffer[output.ByteCount()] = '\0';
+ EXPECT_STREQ("012345\n", buffer);
+ ASSERT_EQ(1, info.annotation_size());
+ const GeneratedCodeInfo::Annotation* bazbam = &info.annotation(0);
+ ASSERT_EQ(1, bazbam->path_size());
+ EXPECT_EQ(33, bazbam->path(0));
+ EXPECT_EQ("path", bazbam->source_file());
+ EXPECT_EQ(5, bazbam->begin());
+ EXPECT_EQ(5, bazbam->end());
+}
+
+TEST(Printer, AnnotateDespiteUnrelatedMultipleUses) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ printer.Print("012$foo$4$foo$$bar$\n", "foo", "3", "bar", "5");
+ vector<int> path;
+ path.push_back(33);
+ MockDescriptor descriptor("path", path);
+ printer.Annotate("bar", "bar", &descriptor);
+ }
+ buffer[output.ByteCount()] = '\0';
+ EXPECT_STREQ("0123435\n", buffer);
+ ASSERT_EQ(1, info.annotation_size());
+ const GeneratedCodeInfo::Annotation* bar = &info.annotation(0);
+ ASSERT_EQ(1, bar->path_size());
+ EXPECT_EQ(33, bar->path(0));
+ EXPECT_EQ("path", bar->source_file());
+ EXPECT_EQ(6, bar->begin());
+ EXPECT_EQ(7, bar->end());
+}
+
+TEST(Printer, Indenting) {
+ char buffer[8192];
+
+ for (int block_size = 1; block_size < 512; block_size *= 2) {
+ ArrayOutputStream output(buffer, sizeof(buffer), block_size);
+
+ {
+ Printer printer(&output, '$');
+ map<string, string> vars;
+
+ vars["newline"] = "\n";
+
+ printer.Print("This is not indented.\n");
+ printer.Indent();
+ printer.Print("This is indented\nAnd so is this\n");
+ printer.Outdent();
+ printer.Print("But this is not.");
+ printer.Indent();
+ printer.Print(" And this is still the same line.\n"
+ "But this is indented.\n");
+ printer.PrintRaw("RawBit has indent at start\n");
+ printer.PrintRaw("but not after a raw newline\n");
+ printer.Print(vars, "Note that a newline in a variable will break "
+ "indenting, as we see$newline$here.\n");
+ printer.Indent();
+ printer.Print("And this");
+ printer.Outdent();
+ printer.Outdent();
+ printer.Print(" is double-indented\nBack to normal.");
+
+ EXPECT_FALSE(printer.failed());
+ }
+
+ buffer[output.ByteCount()] = '\0';
+
+ EXPECT_STREQ(
+ "This is not indented.\n"
+ " This is indented\n"
+ " And so is this\n"
+ "But this is not. And this is still the same line.\n"
+ " But this is indented.\n"
+ " RawBit has indent at start\n"
+ "but not after a raw newline\n"
+ "Note that a newline in a variable will break indenting, as we see\n"
+ "here.\n"
+ " And this is double-indented\n"
+ "Back to normal.",
+ buffer);
+ }
+}
+
+// Death tests do not work on Windows as of yet.
+#ifdef PROTOBUF_HAS_DEATH_TEST
+TEST(Printer, Death) {
+ char buffer[8192];
+
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ Printer printer(&output, '$');
+
+ EXPECT_DEBUG_DEATH(printer.Print("$nosuchvar$"), "Undefined variable");
+ EXPECT_DEBUG_DEATH(printer.Print("$unclosed"), "Unclosed variable name");
+ EXPECT_DEBUG_DEATH(printer.Outdent(), "without matching Indent");
+}
+
+TEST(Printer, AnnotateMultipleUsesDeath) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ printer.Print("012$foo$4$foo$\n", "foo", "3");
+ vector<int> path;
+ path.push_back(33);
+ MockDescriptor descriptor("path", path);
+ EXPECT_DEBUG_DEATH(printer.Annotate("foo", "foo", &descriptor), "multiple");
+ }
+}
+
+TEST(Printer, AnnotateNegativeLengthDeath) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ printer.Print("012$foo$4$bar$\n", "foo", "3", "bar", "5");
+ vector<int> path;
+ path.push_back(33);
+ MockDescriptor descriptor("path", path);
+ EXPECT_DEBUG_DEATH(printer.Annotate("bar", "foo", &descriptor), "negative");
+ }
+}
+
+TEST(Printer, AnnotateUndefinedDeath) {
+ char buffer[8192];
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ GeneratedCodeInfo info;
+ AnnotationProtoCollector<GeneratedCodeInfo> info_collector(&info);
+ {
+ Printer printer(&output, '$', &info_collector);
+ printer.Print("012$foo$4$foo$\n", "foo", "3");
+ vector<int> path;
+ path.push_back(33);
+ MockDescriptor descriptor("path", path);
+ EXPECT_DEBUG_DEATH(printer.Annotate("bar", "bar", &descriptor),
+ "Undefined");
+ }
+}
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST(Printer, WriteFailurePartial) {
+ char buffer[17];
+
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ Printer printer(&output, '$');
+
+ // Print 16 bytes to almost fill the buffer (should not fail).
+ printer.Print("0123456789abcdef");
+ EXPECT_FALSE(printer.failed());
+
+ // Try to print 2 chars. Only one fits.
+ printer.Print("<>");
+ EXPECT_TRUE(printer.failed());
+
+ // Anything else should fail too.
+ printer.Print(" ");
+ EXPECT_TRUE(printer.failed());
+ printer.Print("blah");
+ EXPECT_TRUE(printer.failed());
+
+ // Buffer should contain the first 17 bytes written.
+ EXPECT_EQ("0123456789abcdef<", string(buffer, sizeof(buffer)));
+}
+
+TEST(Printer, WriteFailureExact) {
+ char buffer[16];
+
+ ArrayOutputStream output(buffer, sizeof(buffer));
+ Printer printer(&output, '$');
+
+ // Print 16 bytes to fill the buffer exactly (should not fail).
+ printer.Print("0123456789abcdef");
+ EXPECT_FALSE(printer.failed());
+
+ // Try to print one more byte (should fail).
+ printer.Print(" ");
+ EXPECT_TRUE(printer.failed());
+
+ // Should not crash
+ printer.Print("blah");
+ EXPECT_TRUE(printer.failed());
+
+ // Buffer should contain the first 16 bytes written.
+ EXPECT_EQ("0123456789abcdef", string(buffer, sizeof(buffer)));
+}
+
+} // namespace
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.cc
new file mode 100644
index 0000000000..a90bb9a31e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.cc
@@ -0,0 +1,125 @@
+// 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.
+
+#include <google/protobuf/io/strtod.h>
+
+#include <cstdio>
+#include <cstring>
+#include <limits>
+#include <string>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+// ----------------------------------------------------------------------
+// NoLocaleStrtod()
+// This code will make you cry.
+// ----------------------------------------------------------------------
+
+namespace {
+
+// Returns a string identical to *input except that the character pointed to
+// by radix_pos (which should be '.') is replaced with the locale-specific
+// radix character.
+string LocalizeRadix(const char* input, const char* radix_pos) {
+ // Determine the locale-specific radix character by calling sprintf() to
+ // print the number 1.5, then stripping off the digits. As far as I can
+ // tell, this is the only portable, thread-safe way to get the C library
+ // to divuldge the locale's radix character. No, localeconv() is NOT
+ // thread-safe.
+ char temp[16];
+ int size = sprintf(temp, "%.1f", 1.5);
+ GOOGLE_CHECK_EQ(temp[0], '1');
+ GOOGLE_CHECK_EQ(temp[size-1], '5');
+ GOOGLE_CHECK_LE(size, 6);
+
+ // Now replace the '.' in the input with it.
+ string result;
+ result.reserve(strlen(input) + size - 3);
+ result.append(input, radix_pos);
+ result.append(temp + 1, size - 2);
+ result.append(radix_pos + 1);
+ return result;
+}
+
+} // namespace
+
+double NoLocaleStrtod(const char* text, char** original_endptr) {
+ // We cannot simply set the locale to "C" temporarily with setlocale()
+ // as this is not thread-safe. Instead, we try to parse in the current
+ // locale first. If parsing stops at a '.' character, then this is a
+ // pretty good hint that we're actually in some other locale in which
+ // '.' is not the radix character.
+
+ char* temp_endptr;
+ double result = strtod(text, &temp_endptr);
+ if (original_endptr != NULL) *original_endptr = temp_endptr;
+ if (*temp_endptr != '.') return result;
+
+ // Parsing halted on a '.'. Perhaps we're in a different locale? Let's
+ // try to replace the '.' with a locale-specific radix character and
+ // try again.
+ string localized = LocalizeRadix(text, temp_endptr);
+ const char* localized_cstr = localized.c_str();
+ char* localized_endptr;
+ result = strtod(localized_cstr, &localized_endptr);
+ if ((localized_endptr - localized_cstr) >
+ (temp_endptr - text)) {
+ // This attempt got further, so replacing the decimal must have helped.
+ // Update original_endptr to point at the right location.
+ if (original_endptr != NULL) {
+ // size_diff is non-zero if the localized radix has multiple bytes.
+ int size_diff = localized.size() - strlen(text);
+ // const_cast is necessary to match the strtod() interface.
+ *original_endptr = const_cast<char*>(
+ text + (localized_endptr - localized_cstr - size_diff));
+ }
+ }
+
+ return result;
+}
+
+float SafeDoubleToFloat(double value) {
+ if (value > std::numeric_limits<float>::max()) {
+ return std::numeric_limits<float>::infinity();
+ } else if (value < -std::numeric_limits<float>::max()) {
+ return -std::numeric_limits<float>::infinity();
+ } else {
+ return static_cast<float>(value);
+ }
+}
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.h
new file mode 100644
index 0000000000..f56e41c840
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/strtod.h
@@ -0,0 +1,55 @@
+// 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.
+
+// A locale-independent version of strtod(), used to parse floating
+// point default values in .proto files, where the decimal separator
+// is always a dot.
+
+#ifndef GOOGLE_PROTOBUF_IO_STRTOD_H__
+#define GOOGLE_PROTOBUF_IO_STRTOD_H__
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+// A locale-independent version of the standard strtod(), which always
+// uses a dot as the decimal separator.
+double NoLocaleStrtod(const char* str, char** endptr);
+
+// Casts a double value to a float value. If the value is outside of the
+// representable range of float, it will be converted to positive or negative
+// infinity.
+float SafeDoubleToFloat(double value);
+
+} // namespace io
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_STRTOD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.cc
new file mode 100644
index 0000000000..b3550dfbaf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.cc
@@ -0,0 +1,1139 @@
+// 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.
+//
+// Here we have a hand-written lexer. At first you might ask yourself,
+// "Hand-written text processing? Is Kenton crazy?!" Well, first of all,
+// yes I am crazy, but that's beside the point. There are actually reasons
+// why I ended up writing this this way.
+//
+// The traditional approach to lexing is to use lex to generate a lexer for
+// you. Unfortunately, lex's output is ridiculously ugly and difficult to
+// integrate cleanly with C++ code, especially abstract code or code meant
+// as a library. Better parser-generators exist but would add dependencies
+// which most users won't already have, which we'd like to avoid. (GNU flex
+// has a C++ output option, but it's still ridiculously ugly, non-abstract,
+// and not library-friendly.)
+//
+// The next approach that any good software engineer should look at is to
+// use regular expressions. And, indeed, I did. I have code which
+// implements this same class using regular expressions. It's about 200
+// lines shorter. However:
+// - Rather than error messages telling you "This string has an invalid
+// escape sequence at line 5, column 45", you get error messages like
+// "Parse error on line 5". Giving more precise errors requires adding
+// a lot of code that ends up basically as complex as the hand-coded
+// version anyway.
+// - The regular expression to match a string literal looks like this:
+// kString = new RE("(\"([^\"\\\\]|" // non-escaped
+// "\\\\[abfnrtv?\"'\\\\0-7]|" // normal escape
+// "\\\\x[0-9a-fA-F])*\"|" // hex escape
+// "\'([^\'\\\\]|" // Also support single-quotes.
+// "\\\\[abfnrtv?\"'\\\\0-7]|"
+// "\\\\x[0-9a-fA-F])*\')");
+// Verifying the correctness of this line noise is actually harder than
+// verifying the correctness of ConsumeString(), defined below. I'm not
+// even confident that the above is correct, after staring at it for some
+// time.
+// - PCRE is fast, but there's still more overhead involved than the code
+// below.
+// - Sadly, regular expressions are not part of the C standard library, so
+// using them would require depending on some other library. For the
+// open source release, this could be really annoying. Nobody likes
+// downloading one piece of software just to find that they need to
+// download something else to make it work, and in all likelihood
+// people downloading Protocol Buffers will already be doing so just
+// to make something else work. We could include a copy of PCRE with
+// our code, but that obligates us to keep it up-to-date and just seems
+// like a big waste just to save 200 lines of code.
+//
+// On a similar but unrelated note, I'm even scared to use ctype.h.
+// Apparently functions like isalpha() are locale-dependent. So, if we used
+// that, then if this code is being called from some program that doesn't
+// have its locale set to "C", it would behave strangely. We can't just set
+// the locale to "C" ourselves since we might break the calling program that
+// way, particularly if it is multi-threaded. WTF? Someone please let me
+// (Kenton) know if I'm missing something here...
+//
+// I'd love to hear about other alternatives, though, as this code isn't
+// exactly pretty.
+
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/io/strtod.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+namespace {
+
+// As mentioned above, I don't trust ctype.h due to the presence of "locales".
+// So, I have written replacement functions here. Someone please smack me if
+// this is a bad idea or if there is some way around this.
+//
+// These "character classes" are designed to be used in template methods.
+// For instance, Tokenizer::ConsumeZeroOrMore<Whitespace>() will eat
+// whitespace.
+
+// Note: No class is allowed to contain '\0', since this is used to mark end-
+// of-input and is handled specially.
+
+#define CHARACTER_CLASS(NAME, EXPRESSION) \
+ class NAME { \
+ public: \
+ static inline bool InClass(char c) { \
+ return EXPRESSION; \
+ } \
+ }
+
+CHARACTER_CLASS(Whitespace, c == ' ' || c == '\n' || c == '\t' ||
+ c == '\r' || c == '\v' || c == '\f');
+CHARACTER_CLASS(WhitespaceNoNewline, c == ' ' || c == '\t' ||
+ c == '\r' || c == '\v' || c == '\f');
+
+CHARACTER_CLASS(Unprintable, c < ' ' && c > '\0');
+
+CHARACTER_CLASS(Digit, '0' <= c && c <= '9');
+CHARACTER_CLASS(OctalDigit, '0' <= c && c <= '7');
+CHARACTER_CLASS(HexDigit, ('0' <= c && c <= '9') ||
+ ('a' <= c && c <= 'f') ||
+ ('A' <= c && c <= 'F'));
+
+CHARACTER_CLASS(Letter, ('a' <= c && c <= 'z') ||
+ ('A' <= c && c <= 'Z') ||
+ (c == '_'));
+
+CHARACTER_CLASS(Alphanumeric, ('a' <= c && c <= 'z') ||
+ ('A' <= c && c <= 'Z') ||
+ ('0' <= c && c <= '9') ||
+ (c == '_'));
+
+CHARACTER_CLASS(Escape, c == 'a' || c == 'b' || c == 'f' || c == 'n' ||
+ c == 'r' || c == 't' || c == 'v' || c == '\\' ||
+ c == '?' || c == '\'' || c == '\"');
+
+#undef CHARACTER_CLASS
+
+// Given a char, interpret it as a numeric digit and return its value.
+// This supports any number base up to 36.
+inline int DigitValue(char digit) {
+ if ('0' <= digit && digit <= '9') return digit - '0';
+ if ('a' <= digit && digit <= 'z') return digit - 'a' + 10;
+ if ('A' <= digit && digit <= 'Z') return digit - 'A' + 10;
+ return -1;
+}
+
+// Inline because it's only used in one place.
+inline char TranslateEscape(char c) {
+ switch (c) {
+ case 'a': return '\a';
+ case 'b': return '\b';
+ case 'f': return '\f';
+ case 'n': return '\n';
+ case 'r': return '\r';
+ case 't': return '\t';
+ case 'v': return '\v';
+ case '\\': return '\\';
+ case '?': return '\?'; // Trigraphs = :(
+ case '\'': return '\'';
+ case '"': return '\"';
+
+ // We expect escape sequences to have been validated separately.
+ default: return '?';
+ }
+}
+
+} // anonymous namespace
+
+ErrorCollector::~ErrorCollector() {}
+
+// ===================================================================
+
+Tokenizer::Tokenizer(ZeroCopyInputStream* input,
+ ErrorCollector* error_collector)
+ : input_(input),
+ error_collector_(error_collector),
+ buffer_(NULL),
+ buffer_size_(0),
+ buffer_pos_(0),
+ read_error_(false),
+ line_(0),
+ column_(0),
+ record_target_(NULL),
+ record_start_(-1),
+ allow_f_after_float_(false),
+ comment_style_(CPP_COMMENT_STYLE),
+ require_space_after_number_(true),
+ allow_multiline_strings_(false) {
+
+ current_.line = 0;
+ current_.column = 0;
+ current_.end_column = 0;
+ current_.type = TYPE_START;
+
+ Refresh();
+}
+
+Tokenizer::~Tokenizer() {
+ // If we had any buffer left unread, return it to the underlying stream
+ // so that someone else can read it.
+ if (buffer_size_ > buffer_pos_) {
+ input_->BackUp(buffer_size_ - buffer_pos_);
+ }
+}
+
+// -------------------------------------------------------------------
+// Internal helpers.
+
+void Tokenizer::NextChar() {
+ // Update our line and column counters based on the character being
+ // consumed.
+ if (current_char_ == '\n') {
+ ++line_;
+ column_ = 0;
+ } else if (current_char_ == '\t') {
+ column_ += kTabWidth - column_ % kTabWidth;
+ } else {
+ ++column_;
+ }
+
+ // Advance to the next character.
+ ++buffer_pos_;
+ if (buffer_pos_ < buffer_size_) {
+ current_char_ = buffer_[buffer_pos_];
+ } else {
+ Refresh();
+ }
+}
+
+void Tokenizer::Refresh() {
+ if (read_error_) {
+ current_char_ = '\0';
+ return;
+ }
+
+ // If we're in a token, append the rest of the buffer to it.
+ if (record_target_ != NULL && record_start_ < buffer_size_) {
+ record_target_->append(buffer_ + record_start_, buffer_size_ - record_start_);
+ record_start_ = 0;
+ }
+
+ const void* data = NULL;
+ buffer_ = NULL;
+ buffer_pos_ = 0;
+ do {
+ if (!input_->Next(&data, &buffer_size_)) {
+ // end of stream (or read error)
+ buffer_size_ = 0;
+ read_error_ = true;
+ current_char_ = '\0';
+ return;
+ }
+ } while (buffer_size_ == 0);
+
+ buffer_ = static_cast<const char*>(data);
+
+ current_char_ = buffer_[0];
+}
+
+inline void Tokenizer::RecordTo(string* target) {
+ record_target_ = target;
+ record_start_ = buffer_pos_;
+}
+
+inline void Tokenizer::StopRecording() {
+ // Note: The if() is necessary because some STL implementations crash when
+ // you call string::append(NULL, 0), presumably because they are trying to
+ // be helpful by detecting the NULL pointer, even though there's nothing
+ // wrong with reading zero bytes from NULL.
+ if (buffer_pos_ != record_start_) {
+ record_target_->append(buffer_ + record_start_, buffer_pos_ - record_start_);
+ }
+ record_target_ = NULL;
+ record_start_ = -1;
+}
+
+inline void Tokenizer::StartToken() {
+ current_.type = TYPE_START; // Just for the sake of initializing it.
+ current_.text.clear();
+ current_.line = line_;
+ current_.column = column_;
+ RecordTo(&current_.text);
+}
+
+inline void Tokenizer::EndToken() {
+ StopRecording();
+ current_.end_column = column_;
+}
+
+// -------------------------------------------------------------------
+// Helper methods that consume characters.
+
+template<typename CharacterClass>
+inline bool Tokenizer::LookingAt() {
+ return CharacterClass::InClass(current_char_);
+}
+
+template<typename CharacterClass>
+inline bool Tokenizer::TryConsumeOne() {
+ if (CharacterClass::InClass(current_char_)) {
+ NextChar();
+ return true;
+ } else {
+ return false;
+ }
+}
+
+inline bool Tokenizer::TryConsume(char c) {
+ if (current_char_ == c) {
+ NextChar();
+ return true;
+ } else {
+ return false;
+ }
+}
+
+template<typename CharacterClass>
+inline void Tokenizer::ConsumeZeroOrMore() {
+ while (CharacterClass::InClass(current_char_)) {
+ NextChar();
+ }
+}
+
+template<typename CharacterClass>
+inline void Tokenizer::ConsumeOneOrMore(const char* error) {
+ if (!CharacterClass::InClass(current_char_)) {
+ AddError(error);
+ } else {
+ do {
+ NextChar();
+ } while (CharacterClass::InClass(current_char_));
+ }
+}
+
+// -------------------------------------------------------------------
+// Methods that read whole patterns matching certain kinds of tokens
+// or comments.
+
+void Tokenizer::ConsumeString(char delimiter) {
+ while (true) {
+ switch (current_char_) {
+ case '\0':
+ AddError("Unexpected end of string.");
+ return;
+
+ case '\n': {
+ if (!allow_multiline_strings_) {
+ AddError("String literals cannot cross line boundaries.");
+ return;
+ }
+ NextChar();
+ break;
+ }
+
+ case '\\': {
+ // An escape sequence.
+ NextChar();
+ if (TryConsumeOne<Escape>()) {
+ // Valid escape sequence.
+ } else if (TryConsumeOne<OctalDigit>()) {
+ // Possibly followed by two more octal digits, but these will
+ // just be consumed by the main loop anyway so we don't need
+ // to do so explicitly here.
+ } else if (TryConsume('x')) {
+ if (!TryConsumeOne<HexDigit>()) {
+ AddError("Expected hex digits for escape sequence.");
+ }
+ // Possibly followed by another hex digit, but again we don't care.
+ } else if (TryConsume('u')) {
+ if (!TryConsumeOne<HexDigit>() ||
+ !TryConsumeOne<HexDigit>() ||
+ !TryConsumeOne<HexDigit>() ||
+ !TryConsumeOne<HexDigit>()) {
+ AddError("Expected four hex digits for \\u escape sequence.");
+ }
+ } else if (TryConsume('U')) {
+ // We expect 8 hex digits; but only the range up to 0x10ffff is
+ // legal.
+ if (!TryConsume('0') ||
+ !TryConsume('0') ||
+ !(TryConsume('0') || TryConsume('1')) ||
+ !TryConsumeOne<HexDigit>() ||
+ !TryConsumeOne<HexDigit>() ||
+ !TryConsumeOne<HexDigit>() ||
+ !TryConsumeOne<HexDigit>() ||
+ !TryConsumeOne<HexDigit>()) {
+ AddError("Expected eight hex digits up to 10ffff for \\U escape "
+ "sequence");
+ }
+ } else {
+ AddError("Invalid escape sequence in string literal.");
+ }
+ break;
+ }
+
+ default: {
+ if (current_char_ == delimiter) {
+ NextChar();
+ return;
+ }
+ NextChar();
+ break;
+ }
+ }
+ }
+}
+
+Tokenizer::TokenType Tokenizer::ConsumeNumber(bool started_with_zero,
+ bool started_with_dot) {
+ bool is_float = false;
+
+ if (started_with_zero && (TryConsume('x') || TryConsume('X'))) {
+ // A hex number (started with "0x").
+ ConsumeOneOrMore<HexDigit>("\"0x\" must be followed by hex digits.");
+
+ } else if (started_with_zero && LookingAt<Digit>()) {
+ // An octal number (had a leading zero).
+ ConsumeZeroOrMore<OctalDigit>();
+ if (LookingAt<Digit>()) {
+ AddError("Numbers starting with leading zero must be in octal.");
+ ConsumeZeroOrMore<Digit>();
+ }
+
+ } else {
+ // A decimal number.
+ if (started_with_dot) {
+ is_float = true;
+ ConsumeZeroOrMore<Digit>();
+ } else {
+ ConsumeZeroOrMore<Digit>();
+
+ if (TryConsume('.')) {
+ is_float = true;
+ ConsumeZeroOrMore<Digit>();
+ }
+ }
+
+ if (TryConsume('e') || TryConsume('E')) {
+ is_float = true;
+ TryConsume('-') || TryConsume('+');
+ ConsumeOneOrMore<Digit>("\"e\" must be followed by exponent.");
+ }
+
+ if (allow_f_after_float_ && (TryConsume('f') || TryConsume('F'))) {
+ is_float = true;
+ }
+ }
+
+ if (LookingAt<Letter>() && require_space_after_number_) {
+ AddError("Need space between number and identifier.");
+ } else if (current_char_ == '.') {
+ if (is_float) {
+ AddError(
+ "Already saw decimal point or exponent; can't have another one.");
+ } else {
+ AddError("Hex and octal numbers must be integers.");
+ }
+ }
+
+ return is_float ? TYPE_FLOAT : TYPE_INTEGER;
+}
+
+void Tokenizer::ConsumeLineComment(string* content) {
+ if (content != NULL) RecordTo(content);
+
+ while (current_char_ != '\0' && current_char_ != '\n') {
+ NextChar();
+ }
+ TryConsume('\n');
+
+ if (content != NULL) StopRecording();
+}
+
+void Tokenizer::ConsumeBlockComment(string* content) {
+ int start_line = line_;
+ int start_column = column_ - 2;
+
+ if (content != NULL) RecordTo(content);
+
+ while (true) {
+ while (current_char_ != '\0' &&
+ current_char_ != '*' &&
+ current_char_ != '/' &&
+ current_char_ != '\n') {
+ NextChar();
+ }
+
+ if (TryConsume('\n')) {
+ if (content != NULL) StopRecording();
+
+ // Consume leading whitespace and asterisk;
+ ConsumeZeroOrMore<WhitespaceNoNewline>();
+ if (TryConsume('*')) {
+ if (TryConsume('/')) {
+ // End of comment.
+ break;
+ }
+ }
+
+ if (content != NULL) RecordTo(content);
+ } else if (TryConsume('*') && TryConsume('/')) {
+ // End of comment.
+ if (content != NULL) {
+ StopRecording();
+ // Strip trailing "*/".
+ content->erase(content->size() - 2);
+ }
+ break;
+ } else if (TryConsume('/') && current_char_ == '*') {
+ // Note: We didn't consume the '*' because if there is a '/' after it
+ // we want to interpret that as the end of the comment.
+ AddError(
+ "\"/*\" inside block comment. Block comments cannot be nested.");
+ } else if (current_char_ == '\0') {
+ AddError("End-of-file inside block comment.");
+ error_collector_->AddError(
+ start_line, start_column, " Comment started here.");
+ if (content != NULL) StopRecording();
+ break;
+ }
+ }
+}
+
+Tokenizer::NextCommentStatus Tokenizer::TryConsumeCommentStart() {
+ if (comment_style_ == CPP_COMMENT_STYLE && TryConsume('/')) {
+ if (TryConsume('/')) {
+ return LINE_COMMENT;
+ } else if (TryConsume('*')) {
+ return BLOCK_COMMENT;
+ } else {
+ // Oops, it was just a slash. Return it.
+ current_.type = TYPE_SYMBOL;
+ current_.text = "/";
+ current_.line = line_;
+ current_.column = column_ - 1;
+ current_.end_column = column_;
+ return SLASH_NOT_COMMENT;
+ }
+ } else if (comment_style_ == SH_COMMENT_STYLE && TryConsume('#')) {
+ return LINE_COMMENT;
+ } else {
+ return NO_COMMENT;
+ }
+}
+
+// -------------------------------------------------------------------
+
+bool Tokenizer::Next() {
+ previous_ = current_;
+
+ while (!read_error_) {
+ ConsumeZeroOrMore<Whitespace>();
+
+ switch (TryConsumeCommentStart()) {
+ case LINE_COMMENT:
+ ConsumeLineComment(NULL);
+ continue;
+ case BLOCK_COMMENT:
+ ConsumeBlockComment(NULL);
+ continue;
+ case SLASH_NOT_COMMENT:
+ return true;
+ case NO_COMMENT:
+ break;
+ }
+
+ // Check for EOF before continuing.
+ if (read_error_) break;
+
+ if (LookingAt<Unprintable>() || current_char_ == '\0') {
+ AddError("Invalid control characters encountered in text.");
+ NextChar();
+ // Skip more unprintable characters, too. But, remember that '\0' is
+ // also what current_char_ is set to after EOF / read error. We have
+ // to be careful not to go into an infinite loop of trying to consume
+ // it, so make sure to check read_error_ explicitly before consuming
+ // '\0'.
+ while (TryConsumeOne<Unprintable>() ||
+ (!read_error_ && TryConsume('\0'))) {
+ // Ignore.
+ }
+
+ } else {
+ // Reading some sort of token.
+ StartToken();
+
+ if (TryConsumeOne<Letter>()) {
+ ConsumeZeroOrMore<Alphanumeric>();
+ current_.type = TYPE_IDENTIFIER;
+ } else if (TryConsume('0')) {
+ current_.type = ConsumeNumber(true, false);
+ } else if (TryConsume('.')) {
+ // This could be the beginning of a floating-point number, or it could
+ // just be a '.' symbol.
+
+ if (TryConsumeOne<Digit>()) {
+ // It's a floating-point number.
+ if (previous_.type == TYPE_IDENTIFIER &&
+ current_.line == previous_.line &&
+ current_.column == previous_.end_column) {
+ // We don't accept syntax like "blah.123".
+ error_collector_->AddError(line_, column_ - 2,
+ "Need space between identifier and decimal point.");
+ }
+ current_.type = ConsumeNumber(false, true);
+ } else {
+ current_.type = TYPE_SYMBOL;
+ }
+ } else if (TryConsumeOne<Digit>()) {
+ current_.type = ConsumeNumber(false, false);
+ } else if (TryConsume('\"')) {
+ ConsumeString('\"');
+ current_.type = TYPE_STRING;
+ } else if (TryConsume('\'')) {
+ ConsumeString('\'');
+ current_.type = TYPE_STRING;
+ } else {
+ // Check if the high order bit is set.
+ if (current_char_ & 0x80) {
+ error_collector_->AddError(line_, column_,
+ StringPrintf("Interpreting non ascii codepoint %d.",
+ static_cast<unsigned char>(current_char_)));
+ }
+ NextChar();
+ current_.type = TYPE_SYMBOL;
+ }
+
+ EndToken();
+ return true;
+ }
+ }
+
+ // EOF
+ current_.type = TYPE_END;
+ current_.text.clear();
+ current_.line = line_;
+ current_.column = column_;
+ current_.end_column = column_;
+ return false;
+}
+
+namespace {
+
+// Helper class for collecting comments and putting them in the right places.
+//
+// This basically just buffers the most recent comment until it can be decided
+// exactly where that comment should be placed. When Flush() is called, the
+// current comment goes into either prev_trailing_comments or detached_comments.
+// When the CommentCollector is destroyed, the last buffered comment goes into
+// next_leading_comments.
+class CommentCollector {
+ public:
+ CommentCollector(string* prev_trailing_comments,
+ vector<string>* detached_comments,
+ string* next_leading_comments)
+ : prev_trailing_comments_(prev_trailing_comments),
+ detached_comments_(detached_comments),
+ next_leading_comments_(next_leading_comments),
+ has_comment_(false),
+ is_line_comment_(false),
+ can_attach_to_prev_(true) {
+ if (prev_trailing_comments != NULL) prev_trailing_comments->clear();
+ if (detached_comments != NULL) detached_comments->clear();
+ if (next_leading_comments != NULL) next_leading_comments->clear();
+ }
+
+ ~CommentCollector() {
+ // Whatever is in the buffer is a leading comment.
+ if (next_leading_comments_ != NULL && has_comment_) {
+ comment_buffer_.swap(*next_leading_comments_);
+ }
+ }
+
+ // About to read a line comment. Get the comment buffer pointer in order to
+ // read into it.
+ string* GetBufferForLineComment() {
+ // We want to combine with previous line comments, but not block comments.
+ if (has_comment_ && !is_line_comment_) {
+ Flush();
+ }
+ has_comment_ = true;
+ is_line_comment_ = true;
+ return &comment_buffer_;
+ }
+
+ // About to read a block comment. Get the comment buffer pointer in order to
+ // read into it.
+ string* GetBufferForBlockComment() {
+ if (has_comment_) {
+ Flush();
+ }
+ has_comment_ = true;
+ is_line_comment_ = false;
+ return &comment_buffer_;
+ }
+
+ void ClearBuffer() {
+ comment_buffer_.clear();
+ has_comment_ = false;
+ }
+
+ // Called once we know that the comment buffer is complete and is *not*
+ // connected to the next token.
+ void Flush() {
+ if (has_comment_) {
+ if (can_attach_to_prev_) {
+ if (prev_trailing_comments_ != NULL) {
+ prev_trailing_comments_->append(comment_buffer_);
+ }
+ can_attach_to_prev_ = false;
+ } else {
+ if (detached_comments_ != NULL) {
+ detached_comments_->push_back(comment_buffer_);
+ }
+ }
+ ClearBuffer();
+ }
+ }
+
+ void DetachFromPrev() {
+ can_attach_to_prev_ = false;
+ }
+
+ private:
+ string* prev_trailing_comments_;
+ vector<string>* detached_comments_;
+ string* next_leading_comments_;
+
+ string comment_buffer_;
+
+ // True if any comments were read into comment_buffer_. This can be true even
+ // if comment_buffer_ is empty, namely if the comment was "/**/".
+ bool has_comment_;
+
+ // Is the comment in the comment buffer a line comment?
+ bool is_line_comment_;
+
+ // Is it still possible that we could be reading a comment attached to the
+ // previous token?
+ bool can_attach_to_prev_;
+};
+
+} // namespace
+
+bool Tokenizer::NextWithComments(string* prev_trailing_comments,
+ vector<string>* detached_comments,
+ string* next_leading_comments) {
+ CommentCollector collector(prev_trailing_comments, detached_comments,
+ next_leading_comments);
+
+ if (current_.type == TYPE_START) {
+ // Ignore unicode byte order mark(BOM) if it appears at the file
+ // beginning. Only UTF-8 BOM (0xEF 0xBB 0xBF) is accepted.
+ if (TryConsume((char)0xEF)) {
+ if (!TryConsume((char)0xBB) || !TryConsume((char)0xBF)) {
+ AddError("Proto file starts with 0xEF but not UTF-8 BOM. "
+ "Only UTF-8 is accepted for proto file.");
+ return false;
+ }
+ }
+ collector.DetachFromPrev();
+ } else {
+ // A comment appearing on the same line must be attached to the previous
+ // declaration.
+ ConsumeZeroOrMore<WhitespaceNoNewline>();
+ switch (TryConsumeCommentStart()) {
+ case LINE_COMMENT:
+ ConsumeLineComment(collector.GetBufferForLineComment());
+
+ // Don't allow comments on subsequent lines to be attached to a trailing
+ // comment.
+ collector.Flush();
+ break;
+ case BLOCK_COMMENT:
+ ConsumeBlockComment(collector.GetBufferForBlockComment());
+
+ ConsumeZeroOrMore<WhitespaceNoNewline>();
+ if (!TryConsume('\n')) {
+ // Oops, the next token is on the same line. If we recorded a comment
+ // we really have no idea which token it should be attached to.
+ collector.ClearBuffer();
+ return Next();
+ }
+
+ // Don't allow comments on subsequent lines to be attached to a trailing
+ // comment.
+ collector.Flush();
+ break;
+ case SLASH_NOT_COMMENT:
+ return true;
+ case NO_COMMENT:
+ if (!TryConsume('\n')) {
+ // The next token is on the same line. There are no comments.
+ return Next();
+ }
+ break;
+ }
+ }
+
+ // OK, we are now on the line *after* the previous token.
+ while (true) {
+ ConsumeZeroOrMore<WhitespaceNoNewline>();
+
+ switch (TryConsumeCommentStart()) {
+ case LINE_COMMENT:
+ ConsumeLineComment(collector.GetBufferForLineComment());
+ break;
+ case BLOCK_COMMENT:
+ ConsumeBlockComment(collector.GetBufferForBlockComment());
+
+ // Consume the rest of the line so that we don't interpret it as a
+ // blank line the next time around the loop.
+ ConsumeZeroOrMore<WhitespaceNoNewline>();
+ TryConsume('\n');
+ break;
+ case SLASH_NOT_COMMENT:
+ return true;
+ case NO_COMMENT:
+ if (TryConsume('\n')) {
+ // Completely blank line.
+ collector.Flush();
+ collector.DetachFromPrev();
+ } else {
+ bool result = Next();
+ if (!result ||
+ current_.text == "}" ||
+ current_.text == "]" ||
+ current_.text == ")") {
+ // It looks like we're at the end of a scope. In this case it
+ // makes no sense to attach a comment to the following token.
+ collector.Flush();
+ }
+ return result;
+ }
+ break;
+ }
+ }
+}
+
+// -------------------------------------------------------------------
+// Token-parsing helpers. Remember that these don't need to report
+// errors since any errors should already have been reported while
+// tokenizing. Also, these can assume that whatever text they
+// are given is text that the tokenizer actually parsed as a token
+// of the given type.
+
+bool Tokenizer::ParseInteger(const string& text, uint64 max_value,
+ uint64* output) {
+ // Sadly, we can't just use strtoul() since it is only 32-bit and strtoull()
+ // is non-standard. I hate the C standard library. :(
+
+// return strtoull(text.c_str(), NULL, 0);
+
+ const char* ptr = text.c_str();
+ int base = 10;
+ if (ptr[0] == '0') {
+ if (ptr[1] == 'x' || ptr[1] == 'X') {
+ // This is hex.
+ base = 16;
+ ptr += 2;
+ } else {
+ // This is octal.
+ base = 8;
+ }
+ }
+
+ uint64 result = 0;
+ for (; *ptr != '\0'; ptr++) {
+ int digit = DigitValue(*ptr);
+ if (digit < 0 || digit >= base) {
+ // The token provided by Tokenizer is invalid. i.e., 099 is an invalid
+ // token, but Tokenizer still think it's integer.
+ return false;
+ }
+ if (digit > max_value || result > (max_value - digit) / base) {
+ // Overflow.
+ return false;
+ }
+ result = result * base + digit;
+ }
+
+ *output = result;
+ return true;
+}
+
+double Tokenizer::ParseFloat(const string& text) {
+ const char* start = text.c_str();
+ char* end;
+ double result = NoLocaleStrtod(start, &end);
+
+ // "1e" is not a valid float, but if the tokenizer reads it, it will
+ // report an error but still return it as a valid token. We need to
+ // accept anything the tokenizer could possibly return, error or not.
+ if (*end == 'e' || *end == 'E') {
+ ++end;
+ if (*end == '-' || *end == '+') ++end;
+ }
+
+ // If the Tokenizer had allow_f_after_float_ enabled, the float may be
+ // suffixed with the letter 'f'.
+ if (*end == 'f' || *end == 'F') {
+ ++end;
+ }
+
+ GOOGLE_LOG_IF(DFATAL, end - start != text.size() || *start == '-')
+ << " Tokenizer::ParseFloat() passed text that could not have been"
+ " tokenized as a float: " << CEscape(text);
+ return result;
+}
+
+// Helper to append a Unicode code point to a string as UTF8, without bringing
+// in any external dependencies.
+static void AppendUTF8(uint32 code_point, string* output) {
+ uint32 tmp = 0;
+ int len = 0;
+ if (code_point <= 0x7f) {
+ tmp = code_point;
+ len = 1;
+ } else if (code_point <= 0x07ff) {
+ tmp = 0x0000c080 |
+ ((code_point & 0x07c0) << 2) |
+ (code_point & 0x003f);
+ len = 2;
+ } else if (code_point <= 0xffff) {
+ tmp = 0x00e08080 |
+ ((code_point & 0xf000) << 4) |
+ ((code_point & 0x0fc0) << 2) |
+ (code_point & 0x003f);
+ len = 3;
+ } else if (code_point <= 0x1fffff) {
+ tmp = 0xf0808080 |
+ ((code_point & 0x1c0000) << 6) |
+ ((code_point & 0x03f000) << 4) |
+ ((code_point & 0x000fc0) << 2) |
+ (code_point & 0x003f);
+ len = 4;
+ } else {
+ // UTF-16 is only defined for code points up to 0x10FFFF, and UTF-8 is
+ // normally only defined up to there as well.
+ StringAppendF(output, "\\U%08x", code_point);
+ return;
+ }
+ tmp = ghtonl(tmp);
+ output->append(reinterpret_cast<const char*>(&tmp) + sizeof(tmp) - len, len);
+}
+
+// Try to read <len> hex digits from ptr, and stuff the numeric result into
+// *result. Returns true if that many digits were successfully consumed.
+static bool ReadHexDigits(const char* ptr, int len, uint32* result) {
+ *result = 0;
+ if (len == 0) return false;
+ for (const char* end = ptr + len; ptr < end; ++ptr) {
+ if (*ptr == '\0') return false;
+ *result = (*result << 4) + DigitValue(*ptr);
+ }
+ return true;
+}
+
+// Handling UTF-16 surrogate pairs. UTF-16 encodes code points in the range
+// 0x10000...0x10ffff as a pair of numbers, a head surrogate followed by a trail
+// surrogate. These numbers are in a reserved range of Unicode code points, so
+// if we encounter such a pair we know how to parse it and convert it into a
+// single code point.
+static const uint32 kMinHeadSurrogate = 0xd800;
+static const uint32 kMaxHeadSurrogate = 0xdc00;
+static const uint32 kMinTrailSurrogate = 0xdc00;
+static const uint32 kMaxTrailSurrogate = 0xe000;
+
+static inline bool IsHeadSurrogate(uint32 code_point) {
+ return (code_point >= kMinHeadSurrogate) && (code_point < kMaxHeadSurrogate);
+}
+
+static inline bool IsTrailSurrogate(uint32 code_point) {
+ return (code_point >= kMinTrailSurrogate) &&
+ (code_point < kMaxTrailSurrogate);
+}
+
+// Combine a head and trail surrogate into a single Unicode code point.
+static uint32 AssembleUTF16(uint32 head_surrogate, uint32 trail_surrogate) {
+ GOOGLE_DCHECK(IsHeadSurrogate(head_surrogate));
+ GOOGLE_DCHECK(IsTrailSurrogate(trail_surrogate));
+ return 0x10000 + (((head_surrogate - kMinHeadSurrogate) << 10) |
+ (trail_surrogate - kMinTrailSurrogate));
+}
+
+// Convert the escape sequence parameter to a number of expected hex digits.
+static inline int UnicodeLength(char key) {
+ if (key == 'u') return 4;
+ if (key == 'U') return 8;
+ return 0;
+}
+
+// Given a pointer to the 'u' or 'U' starting a Unicode escape sequence, attempt
+// to parse that sequence. On success, returns a pointer to the first char
+// beyond that sequence, and fills in *code_point. On failure, returns ptr
+// itself.
+static const char* FetchUnicodePoint(const char* ptr, uint32* code_point) {
+ const char* p = ptr;
+ // Fetch the code point.
+ const int len = UnicodeLength(*p++);
+ if (!ReadHexDigits(p, len, code_point))
+ return ptr;
+ p += len;
+
+ // Check if the code point we read is a "head surrogate." If so, then we
+ // expect it to be immediately followed by another code point which is a valid
+ // "trail surrogate," and together they form a UTF-16 pair which decodes into
+ // a single Unicode point. Trail surrogates may only use \u, not \U.
+ if (IsHeadSurrogate(*code_point) && *p == '\\' && *(p + 1) == 'u') {
+ uint32 trail_surrogate;
+ if (ReadHexDigits(p + 2, 4, &trail_surrogate) &&
+ IsTrailSurrogate(trail_surrogate)) {
+ *code_point = AssembleUTF16(*code_point, trail_surrogate);
+ p += 6;
+ }
+ // If this failed, then we just emit the head surrogate as a code point.
+ // It's bogus, but so is the string.
+ }
+
+ return p;
+}
+
+// The text string must begin and end with single or double quote
+// characters.
+void Tokenizer::ParseStringAppend(const string& text, string* output) {
+ // Reminder: text[0] is always a quote character. (If text is
+ // empty, it's invalid, so we'll just return).
+ const size_t text_size = text.size();
+ if (text_size == 0) {
+ GOOGLE_LOG(DFATAL)
+ << " Tokenizer::ParseStringAppend() passed text that could not"
+ " have been tokenized as a string: " << CEscape(text);
+ return;
+ }
+
+ // Reserve room for new string. The branch is necessary because if
+ // there is already space available the reserve() call might
+ // downsize the output.
+ const size_t new_len = text_size + output->size();
+ if (new_len > output->capacity()) {
+ output->reserve(new_len);
+ }
+
+ // Loop through the string copying characters to "output" and
+ // interpreting escape sequences. Note that any invalid escape
+ // sequences or other errors were already reported while tokenizing.
+ // In this case we do not need to produce valid results.
+ for (const char* ptr = text.c_str() + 1; *ptr != '\0'; ptr++) {
+ if (*ptr == '\\' && ptr[1] != '\0') {
+ // An escape sequence.
+ ++ptr;
+
+ if (OctalDigit::InClass(*ptr)) {
+ // An octal escape. May one, two, or three digits.
+ int code = DigitValue(*ptr);
+ if (OctalDigit::InClass(ptr[1])) {
+ ++ptr;
+ code = code * 8 + DigitValue(*ptr);
+ }
+ if (OctalDigit::InClass(ptr[1])) {
+ ++ptr;
+ code = code * 8 + DigitValue(*ptr);
+ }
+ output->push_back(static_cast<char>(code));
+
+ } else if (*ptr == 'x') {
+ // A hex escape. May zero, one, or two digits. (The zero case
+ // will have been caught as an error earlier.)
+ int code = 0;
+ if (HexDigit::InClass(ptr[1])) {
+ ++ptr;
+ code = DigitValue(*ptr);
+ }
+ if (HexDigit::InClass(ptr[1])) {
+ ++ptr;
+ code = code * 16 + DigitValue(*ptr);
+ }
+ output->push_back(static_cast<char>(code));
+
+ } else if (*ptr == 'u' || *ptr == 'U') {
+ uint32 unicode;
+ const char* end = FetchUnicodePoint(ptr, &unicode);
+ if (end == ptr) {
+ // Failure: Just dump out what we saw, don't try to parse it.
+ output->push_back(*ptr);
+ } else {
+ AppendUTF8(unicode, output);
+ ptr = end - 1; // Because we're about to ++ptr.
+ }
+ } else {
+ // Some other escape code.
+ output->push_back(TranslateEscape(*ptr));
+ }
+
+ } else if (*ptr == text[0] && ptr[1] == '\0') {
+ // Ignore final quote matching the starting quote.
+ } else {
+ output->push_back(*ptr);
+ }
+ }
+}
+
+template<typename CharacterClass>
+static bool AllInClass(const string& s) {
+ for (int i = 0; i < s.size(); ++i) {
+ if (!CharacterClass::InClass(s[i]))
+ return false;
+ }
+ return true;
+}
+
+bool Tokenizer::IsIdentifier(const string& text) {
+ // Mirrors IDENTIFIER definition in Tokenizer::Next() above.
+ if (text.size() == 0)
+ return false;
+ if (!Letter::InClass(text.at(0)))
+ return false;
+ if (!AllInClass<Alphanumeric>(text.substr(1)))
+ return false;
+ return true;
+}
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.h
new file mode 100644
index 0000000000..77a873bce8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer.h
@@ -0,0 +1,411 @@
+// 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.
+//
+// Class for parsing tokenized text from a ZeroCopyInputStream.
+
+#ifndef GOOGLE_PROTOBUF_IO_TOKENIZER_H__
+#define GOOGLE_PROTOBUF_IO_TOKENIZER_H__
+
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+class ZeroCopyInputStream; // zero_copy_stream.h
+
+// Defined in this file.
+class ErrorCollector;
+class Tokenizer;
+
+// By "column number", the proto compiler refers to a count of the number
+// of bytes before a given byte, except that a tab character advances to
+// the next multiple of 8 bytes. Note in particular that column numbers
+// are zero-based, while many user interfaces use one-based column numbers.
+typedef int ColumnNumber;
+
+// Abstract interface for an object which collects the errors that occur
+// during parsing. A typical implementation might simply print the errors
+// to stdout.
+class LIBPROTOBUF_EXPORT ErrorCollector {
+ public:
+ inline ErrorCollector() {}
+ virtual ~ErrorCollector();
+
+ // Indicates that there was an error in the input at the given line and
+ // column numbers. The numbers are zero-based, so you may want to add
+ // 1 to each before printing them.
+ virtual void AddError(int line, ColumnNumber column,
+ const string& message) = 0;
+
+ // Indicates that there was a warning in the input at the given line and
+ // column numbers. The numbers are zero-based, so you may want to add
+ // 1 to each before printing them.
+ virtual void AddWarning(int line, ColumnNumber column,
+ const string& message) { }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ErrorCollector);
+};
+
+// This class converts a stream of raw text into a stream of tokens for
+// the protocol definition parser to parse. The tokens recognized are
+// similar to those that make up the C language; see the TokenType enum for
+// precise descriptions. Whitespace and comments are skipped. By default,
+// C- and C++-style comments are recognized, but other styles can be used by
+// calling set_comment_style().
+class LIBPROTOBUF_EXPORT Tokenizer {
+ public:
+ // Construct a Tokenizer that reads and tokenizes text from the given
+ // input stream and writes errors to the given error_collector.
+ // The caller keeps ownership of input and error_collector.
+ Tokenizer(ZeroCopyInputStream* input, ErrorCollector* error_collector);
+ ~Tokenizer();
+
+ enum TokenType {
+ TYPE_START, // Next() has not yet been called.
+ TYPE_END, // End of input reached. "text" is empty.
+
+ TYPE_IDENTIFIER, // A sequence of letters, digits, and underscores, not
+ // starting with a digit. It is an error for a number
+ // to be followed by an identifier with no space in
+ // between.
+ TYPE_INTEGER, // A sequence of digits representing an integer. Normally
+ // the digits are decimal, but a prefix of "0x" indicates
+ // a hex number and a leading zero indicates octal, just
+ // like with C numeric literals. A leading negative sign
+ // is NOT included in the token; it's up to the parser to
+ // interpret the unary minus operator on its own.
+ TYPE_FLOAT, // A floating point literal, with a fractional part and/or
+ // an exponent. Always in decimal. Again, never
+ // negative.
+ TYPE_STRING, // A quoted sequence of escaped characters. Either single
+ // or double quotes can be used, but they must match.
+ // A string literal cannot cross a line break.
+ TYPE_SYMBOL, // Any other printable character, like '!' or '+'.
+ // Symbols are always a single character, so "!+$%" is
+ // four tokens.
+ };
+
+ // Structure representing a token read from the token stream.
+ struct Token {
+ TokenType type;
+ string text; // The exact text of the token as it appeared in
+ // the input. e.g. tokens of TYPE_STRING will still
+ // be escaped and in quotes.
+
+ // "line" and "column" specify the position of the first character of
+ // the token within the input stream. They are zero-based.
+ int line;
+ ColumnNumber column;
+ ColumnNumber end_column;
+ };
+
+ // Get the current token. This is updated when Next() is called. Before
+ // the first call to Next(), current() has type TYPE_START and no contents.
+ const Token& current();
+
+ // Return the previous token -- i.e. what current() returned before the
+ // previous call to Next().
+ const Token& previous();
+
+ // Advance to the next token. Returns false if the end of the input is
+ // reached.
+ bool Next();
+
+ // Like Next(), but also collects comments which appear between the previous
+ // and next tokens.
+ //
+ // Comments which appear to be attached to the previous token are stored
+ // in *prev_tailing_comments. Comments which appear to be attached to the
+ // next token are stored in *next_leading_comments. Comments appearing in
+ // between which do not appear to be attached to either will be added to
+ // detached_comments. Any of these parameters can be NULL to simply discard
+ // the comments.
+ //
+ // A series of line comments appearing on consecutive lines, with no other
+ // tokens appearing on those lines, will be treated as a single comment.
+ //
+ // Only the comment content is returned; comment markers (e.g. //) are
+ // stripped out. For block comments, leading whitespace and an asterisk will
+ // be stripped from the beginning of each line other than the first. Newlines
+ // are included in the output.
+ //
+ // Examples:
+ //
+ // optional int32 foo = 1; // Comment attached to foo.
+ // // Comment attached to bar.
+ // optional int32 bar = 2;
+ //
+ // optional string baz = 3;
+ // // Comment attached to baz.
+ // // Another line attached to baz.
+ //
+ // // Comment attached to qux.
+ // //
+ // // Another line attached to qux.
+ // optional double qux = 4;
+ //
+ // // Detached comment. This is not attached to qux or corge
+ // // because there are blank lines separating it from both.
+ //
+ // optional string corge = 5;
+ // /* Block comment attached
+ // * to corge. Leading asterisks
+ // * will be removed. */
+ // /* Block comment attached to
+ // * grault. */
+ // optional int32 grault = 6;
+ bool NextWithComments(string* prev_trailing_comments,
+ vector<string>* detached_comments,
+ string* next_leading_comments);
+
+ // Parse helpers ---------------------------------------------------
+
+ // Parses a TYPE_FLOAT token. This never fails, so long as the text actually
+ // comes from a TYPE_FLOAT token parsed by Tokenizer. If it doesn't, the
+ // result is undefined (possibly an assert failure).
+ static double ParseFloat(const string& text);
+
+ // Parses a TYPE_STRING token. This never fails, so long as the text actually
+ // comes from a TYPE_STRING token parsed by Tokenizer. If it doesn't, the
+ // result is undefined (possibly an assert failure).
+ static void ParseString(const string& text, string* output);
+
+ // Identical to ParseString, but appends to output.
+ static void ParseStringAppend(const string& text, string* output);
+
+ // Parses a TYPE_INTEGER token. Returns false if the result would be
+ // greater than max_value. Otherwise, returns true and sets *output to the
+ // result. If the text is not from a Token of type TYPE_INTEGER originally
+ // parsed by a Tokenizer, the result is undefined (possibly an assert
+ // failure).
+ static bool ParseInteger(const string& text, uint64 max_value,
+ uint64* output);
+
+ // Options ---------------------------------------------------------
+
+ // Set true to allow floats to be suffixed with the letter 'f'. Tokens
+ // which would otherwise be integers but which have the 'f' suffix will be
+ // forced to be interpreted as floats. For all other purposes, the 'f' is
+ // ignored.
+ void set_allow_f_after_float(bool value) { allow_f_after_float_ = value; }
+
+ // Valid values for set_comment_style().
+ enum CommentStyle {
+ // Line comments begin with "//", block comments are delimited by "/*" and
+ // "*/".
+ CPP_COMMENT_STYLE,
+ // Line comments begin with "#". No way to write block comments.
+ SH_COMMENT_STYLE
+ };
+
+ // Sets the comment style.
+ void set_comment_style(CommentStyle style) { comment_style_ = style; }
+
+ // Whether to require whitespace between a number and a field name.
+ // Default is true. Do not use this; for Google-internal cleanup only.
+ void set_require_space_after_number(bool require) {
+ require_space_after_number_ = require;
+ }
+
+ // Whether to allow string literals to span multiple lines. Default is false.
+ // Do not use this; for Google-internal cleanup only.
+ void set_allow_multiline_strings(bool allow) {
+ allow_multiline_strings_ = allow;
+ }
+
+ // External helper: validate an identifier.
+ static bool IsIdentifier(const string& text);
+
+ // -----------------------------------------------------------------
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Tokenizer);
+
+ Token current_; // Returned by current().
+ Token previous_; // Returned by previous().
+
+ ZeroCopyInputStream* input_;
+ ErrorCollector* error_collector_;
+
+ char current_char_; // == buffer_[buffer_pos_], updated by NextChar().
+ const char* buffer_; // Current buffer returned from input_.
+ int buffer_size_; // Size of buffer_.
+ int buffer_pos_; // Current position within the buffer.
+ bool read_error_; // Did we previously encounter a read error?
+
+ // Line and column number of current_char_ within the whole input stream.
+ int line_;
+ ColumnNumber column_;
+
+ // String to which text should be appended as we advance through it.
+ // Call RecordTo(&str) to start recording and StopRecording() to stop.
+ // E.g. StartToken() calls RecordTo(&current_.text). record_start_ is the
+ // position within the current buffer where recording started.
+ string* record_target_;
+ int record_start_;
+
+ // Options.
+ bool allow_f_after_float_;
+ CommentStyle comment_style_;
+ bool require_space_after_number_;
+ bool allow_multiline_strings_;
+
+ // Since we count columns we need to interpret tabs somehow. We'll take
+ // the standard 8-character definition for lack of any way to do better.
+ // This must match the documentation of ColumnNumber.
+ static const int kTabWidth = 8;
+
+ // -----------------------------------------------------------------
+ // Helper methods.
+
+ // Consume this character and advance to the next one.
+ void NextChar();
+
+ // Read a new buffer from the input.
+ void Refresh();
+
+ inline void RecordTo(string* target);
+ inline void StopRecording();
+
+ // Called when the current character is the first character of a new
+ // token (not including whitespace or comments).
+ inline void StartToken();
+ // Called when the current character is the first character after the
+ // end of the last token. After this returns, current_.text will
+ // contain all text consumed since StartToken() was called.
+ inline void EndToken();
+
+ // Convenience method to add an error at the current line and column.
+ void AddError(const string& message) {
+ error_collector_->AddError(line_, column_, message);
+ }
+
+ // -----------------------------------------------------------------
+ // The following four methods are used to consume tokens of specific
+ // types. They are actually used to consume all characters *after*
+ // the first, since the calling function consumes the first character
+ // in order to decide what kind of token is being read.
+
+ // Read and consume a string, ending when the given delimiter is
+ // consumed.
+ void ConsumeString(char delimiter);
+
+ // Read and consume a number, returning TYPE_FLOAT or TYPE_INTEGER
+ // depending on what was read. This needs to know if the first
+ // character was a zero in order to correctly recognize hex and octal
+ // numbers.
+ // It also needs to know if the first character was a . to parse floating
+ // point correctly.
+ TokenType ConsumeNumber(bool started_with_zero, bool started_with_dot);
+
+ // Consume the rest of a line.
+ void ConsumeLineComment(string* content);
+ // Consume until "*/".
+ void ConsumeBlockComment(string* content);
+
+ enum NextCommentStatus {
+ // Started a line comment.
+ LINE_COMMENT,
+
+ // Started a block comment.
+ BLOCK_COMMENT,
+
+ // Consumed a slash, then realized it wasn't a comment. current_ has
+ // been filled in with a slash token. The caller should return it.
+ SLASH_NOT_COMMENT,
+
+ // We do not appear to be starting a comment here.
+ NO_COMMENT
+ };
+
+ // If we're at the start of a new comment, consume it and return what kind
+ // of comment it is.
+ NextCommentStatus TryConsumeCommentStart();
+
+ // -----------------------------------------------------------------
+ // These helper methods make the parsing code more readable. The
+ // "character classes" referred to are defined at the top of the .cc file.
+ // Basically it is a C++ class with one method:
+ // static bool InClass(char c);
+ // The method returns true if c is a member of this "class", like "Letter"
+ // or "Digit".
+
+ // Returns true if the current character is of the given character
+ // class, but does not consume anything.
+ template<typename CharacterClass>
+ inline bool LookingAt();
+
+ // If the current character is in the given class, consume it and return
+ // true. Otherwise return false.
+ // e.g. TryConsumeOne<Letter>()
+ template<typename CharacterClass>
+ inline bool TryConsumeOne();
+
+ // Like above, but try to consume the specific character indicated.
+ inline bool TryConsume(char c);
+
+ // Consume zero or more of the given character class.
+ template<typename CharacterClass>
+ inline void ConsumeZeroOrMore();
+
+ // Consume one or more of the given character class or log the given
+ // error message.
+ // e.g. ConsumeOneOrMore<Digit>("Expected digits.");
+ template<typename CharacterClass>
+ inline void ConsumeOneOrMore(const char* error);
+};
+
+// inline methods ====================================================
+inline const Tokenizer::Token& Tokenizer::current() {
+ return current_;
+}
+
+inline const Tokenizer::Token& Tokenizer::previous() {
+ return previous_;
+}
+
+inline void Tokenizer::ParseString(const string& text, string* output) {
+ output->clear();
+ ParseStringAppend(text, output);
+}
+
+} // namespace io
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_TOKENIZER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer_unittest.cc
new file mode 100644
index 0000000000..ae0811f892
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/tokenizer_unittest.cc
@@ -0,0 +1,996 @@
+// 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.
+
+#include <limits.h>
+#include <math.h>
+
+#include <vector>
+
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+namespace {
+
+// ===================================================================
+// Data-Driven Test Infrastructure
+
+// TODO(kenton): This is copied from coded_stream_unittest. This is
+// temporary until these fetaures are integrated into gTest itself.
+
+// TEST_1D and TEST_2D are macros I'd eventually like to see added to
+// gTest. These macros can be used to declare tests which should be
+// run multiple times, once for each item in some input array. TEST_1D
+// tests all cases in a single input array. TEST_2D tests all
+// combinations of cases from two arrays. The arrays must be statically
+// defined such that the GOOGLE_ARRAYSIZE() macro works on them. Example:
+//
+// int kCases[] = {1, 2, 3, 4}
+// TEST_1D(MyFixture, MyTest, kCases) {
+// EXPECT_GT(kCases_case, 0);
+// }
+//
+// This test iterates through the numbers 1, 2, 3, and 4 and tests that
+// they are all grater than zero. In case of failure, the exact case
+// which failed will be printed. The case type must be printable using
+// ostream::operator<<.
+
+#define TEST_1D(FIXTURE, NAME, CASES) \
+ class FIXTURE##_##NAME##_DD : public FIXTURE { \
+ protected: \
+ template <typename CaseType> \
+ void DoSingleCase(const CaseType& CASES##_case); \
+ }; \
+ \
+ TEST_F(FIXTURE##_##NAME##_DD, NAME) { \
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(CASES); i++) { \
+ SCOPED_TRACE(testing::Message() \
+ << #CASES " case #" << i << ": " << CASES[i]); \
+ DoSingleCase(CASES[i]); \
+ } \
+ } \
+ \
+ template <typename CaseType> \
+ void FIXTURE##_##NAME##_DD::DoSingleCase(const CaseType& CASES##_case)
+
+#define TEST_2D(FIXTURE, NAME, CASES1, CASES2) \
+ class FIXTURE##_##NAME##_DD : public FIXTURE { \
+ protected: \
+ template <typename CaseType1, typename CaseType2> \
+ void DoSingleCase(const CaseType1& CASES1##_case, \
+ const CaseType2& CASES2##_case); \
+ }; \
+ \
+ TEST_F(FIXTURE##_##NAME##_DD, NAME) { \
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(CASES1); i++) { \
+ for (int j = 0; j < GOOGLE_ARRAYSIZE(CASES2); j++) { \
+ SCOPED_TRACE(testing::Message() \
+ << #CASES1 " case #" << i << ": " << CASES1[i] << ", " \
+ << #CASES2 " case #" << j << ": " << CASES2[j]); \
+ DoSingleCase(CASES1[i], CASES2[j]); \
+ } \
+ } \
+ } \
+ \
+ template <typename CaseType1, typename CaseType2> \
+ void FIXTURE##_##NAME##_DD::DoSingleCase(const CaseType1& CASES1##_case, \
+ const CaseType2& CASES2##_case)
+
+// -------------------------------------------------------------------
+
+// An input stream that is basically like an ArrayInputStream but sometimes
+// returns empty buffers, just to throw us off.
+class TestInputStream : public ZeroCopyInputStream {
+ public:
+ TestInputStream(const void* data, int size, int block_size)
+ : array_stream_(data, size, block_size), counter_(0) {}
+ ~TestInputStream() {}
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size) {
+ // We'll return empty buffers starting with the first buffer, and every
+ // 3 and 5 buffers after that.
+ if (counter_ % 3 == 0 || counter_ % 5 == 0) {
+ *data = NULL;
+ *size = 0;
+ ++counter_;
+ return true;
+ } else {
+ ++counter_;
+ return array_stream_.Next(data, size);
+ }
+ }
+
+ void BackUp(int count) { return array_stream_.BackUp(count); }
+ bool Skip(int count) { return array_stream_.Skip(count); }
+ int64 ByteCount() const { return array_stream_.ByteCount(); }
+
+ private:
+ ArrayInputStream array_stream_;
+ int counter_;
+};
+
+// -------------------------------------------------------------------
+
+// An error collector which simply concatenates all its errors into a big
+// block of text which can be checked.
+class TestErrorCollector : public ErrorCollector {
+ public:
+ TestErrorCollector() {}
+ ~TestErrorCollector() {}
+
+ string text_;
+
+ // implements ErrorCollector ---------------------------------------
+ void AddError(int line, int column, const string& message) {
+ strings::SubstituteAndAppend(&text_, "$0:$1: $2\n",
+ line, column, message);
+ }
+};
+
+// -------------------------------------------------------------------
+
+// We test each operation over a variety of block sizes to insure that
+// we test cases where reads cross buffer boundaries as well as cases
+// where they don't. This is sort of a brute-force approach to this,
+// but it's easy to write and easy to understand.
+const int kBlockSizes[] = {1, 2, 3, 5, 7, 13, 32, 1024};
+
+class TokenizerTest : public testing::Test {
+ protected:
+ // For easy testing.
+ uint64 ParseInteger(const string& text) {
+ uint64 result;
+ EXPECT_TRUE(Tokenizer::ParseInteger(text, kuint64max, &result));
+ return result;
+ }
+};
+
+// ===================================================================
+
+// These tests causes gcc 3.3.5 (and earlier?) to give the cryptic error:
+// "sorry, unimplemented: `method_call_expr' not supported by dump_expr"
+#if !defined(__GNUC__) || __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 3)
+
+// In each test case, the entire input text should parse as a single token
+// of the given type.
+struct SimpleTokenCase {
+ string input;
+ Tokenizer::TokenType type;
+};
+
+inline ostream& operator<<(ostream& out,
+ const SimpleTokenCase& test_case) {
+ return out << CEscape(test_case.input);
+}
+
+SimpleTokenCase kSimpleTokenCases[] = {
+ // Test identifiers.
+ { "hello", Tokenizer::TYPE_IDENTIFIER },
+
+ // Test integers.
+ { "123", Tokenizer::TYPE_INTEGER },
+ { "0xab6", Tokenizer::TYPE_INTEGER },
+ { "0XAB6", Tokenizer::TYPE_INTEGER },
+ { "0X1234567", Tokenizer::TYPE_INTEGER },
+ { "0x89abcdef", Tokenizer::TYPE_INTEGER },
+ { "0x89ABCDEF", Tokenizer::TYPE_INTEGER },
+ { "01234567", Tokenizer::TYPE_INTEGER },
+
+ // Test floats.
+ { "123.45", Tokenizer::TYPE_FLOAT },
+ { "1.", Tokenizer::TYPE_FLOAT },
+ { "1e3", Tokenizer::TYPE_FLOAT },
+ { "1E3", Tokenizer::TYPE_FLOAT },
+ { "1e-3", Tokenizer::TYPE_FLOAT },
+ { "1e+3", Tokenizer::TYPE_FLOAT },
+ { "1.e3", Tokenizer::TYPE_FLOAT },
+ { "1.2e3", Tokenizer::TYPE_FLOAT },
+ { ".1", Tokenizer::TYPE_FLOAT },
+ { ".1e3", Tokenizer::TYPE_FLOAT },
+ { ".1e-3", Tokenizer::TYPE_FLOAT },
+ { ".1e+3", Tokenizer::TYPE_FLOAT },
+
+ // Test strings.
+ { "'hello'", Tokenizer::TYPE_STRING },
+ { "\"foo\"", Tokenizer::TYPE_STRING },
+ { "'a\"b'", Tokenizer::TYPE_STRING },
+ { "\"a'b\"", Tokenizer::TYPE_STRING },
+ { "'a\\'b'", Tokenizer::TYPE_STRING },
+ { "\"a\\\"b\"", Tokenizer::TYPE_STRING },
+ { "'\\xf'", Tokenizer::TYPE_STRING },
+ { "'\\0'", Tokenizer::TYPE_STRING },
+
+ // Test symbols.
+ { "+", Tokenizer::TYPE_SYMBOL },
+ { ".", Tokenizer::TYPE_SYMBOL },
+};
+
+TEST_2D(TokenizerTest, SimpleTokens, kSimpleTokenCases, kBlockSizes) {
+ // Set up the tokenizer.
+ TestInputStream input(kSimpleTokenCases_case.input.data(),
+ kSimpleTokenCases_case.input.size(),
+ kBlockSizes_case);
+ TestErrorCollector error_collector;
+ Tokenizer tokenizer(&input, &error_collector);
+
+ // Before Next() is called, the initial token should always be TYPE_START.
+ EXPECT_EQ(Tokenizer::TYPE_START, tokenizer.current().type);
+ EXPECT_EQ("", tokenizer.current().text);
+ EXPECT_EQ(0, tokenizer.current().line);
+ EXPECT_EQ(0, tokenizer.current().column);
+ EXPECT_EQ(0, tokenizer.current().end_column);
+
+ // Parse the token.
+ ASSERT_TRUE(tokenizer.Next());
+
+ // Check that it has the right type.
+ EXPECT_EQ(kSimpleTokenCases_case.type, tokenizer.current().type);
+ // Check that it contains the complete input text.
+ EXPECT_EQ(kSimpleTokenCases_case.input, tokenizer.current().text);
+ // Check that it is located at the beginning of the input
+ EXPECT_EQ(0, tokenizer.current().line);
+ EXPECT_EQ(0, tokenizer.current().column);
+ EXPECT_EQ(kSimpleTokenCases_case.input.size(),
+ tokenizer.current().end_column);
+
+ // There should be no more input.
+ EXPECT_FALSE(tokenizer.Next());
+
+ // After Next() returns false, the token should have type TYPE_END.
+ EXPECT_EQ(Tokenizer::TYPE_END, tokenizer.current().type);
+ EXPECT_EQ("", tokenizer.current().text);
+ EXPECT_EQ(0, tokenizer.current().line);
+ EXPECT_EQ(kSimpleTokenCases_case.input.size(), tokenizer.current().column);
+ EXPECT_EQ(kSimpleTokenCases_case.input.size(),
+ tokenizer.current().end_column);
+
+ // There should be no errors.
+ EXPECT_TRUE(error_collector.text_.empty());
+}
+
+TEST_1D(TokenizerTest, FloatSuffix, kBlockSizes) {
+ // Test the "allow_f_after_float" option.
+
+ // Set up the tokenizer.
+ const char* text = "1f 2.5f 6e3f 7F";
+ TestInputStream input(text, strlen(text), kBlockSizes_case);
+ TestErrorCollector error_collector;
+ Tokenizer tokenizer(&input, &error_collector);
+ tokenizer.set_allow_f_after_float(true);
+
+ // Advance through tokens and check that they are parsed as expected.
+ ASSERT_TRUE(tokenizer.Next());
+ EXPECT_EQ(tokenizer.current().text, "1f");
+ EXPECT_EQ(tokenizer.current().type, Tokenizer::TYPE_FLOAT);
+ ASSERT_TRUE(tokenizer.Next());
+ EXPECT_EQ(tokenizer.current().text, "2.5f");
+ EXPECT_EQ(tokenizer.current().type, Tokenizer::TYPE_FLOAT);
+ ASSERT_TRUE(tokenizer.Next());
+ EXPECT_EQ(tokenizer.current().text, "6e3f");
+ EXPECT_EQ(tokenizer.current().type, Tokenizer::TYPE_FLOAT);
+ ASSERT_TRUE(tokenizer.Next());
+ EXPECT_EQ(tokenizer.current().text, "7F");
+ EXPECT_EQ(tokenizer.current().type, Tokenizer::TYPE_FLOAT);
+
+ // There should be no more input.
+ EXPECT_FALSE(tokenizer.Next());
+ // There should be no errors.
+ EXPECT_TRUE(error_collector.text_.empty());
+}
+
+#endif
+
+// -------------------------------------------------------------------
+
+// In each case, the input is parsed to produce a list of tokens. The
+// last token in "output" must have type TYPE_END.
+struct MultiTokenCase {
+ string input;
+ Tokenizer::Token output[10]; // The compiler wants a constant array
+ // size for initialization to work. There
+ // is no reason this can't be increased if
+ // needed.
+};
+
+inline ostream& operator<<(ostream& out,
+ const MultiTokenCase& test_case) {
+ return out << CEscape(test_case.input);
+}
+
+MultiTokenCase kMultiTokenCases[] = {
+ // Test empty input.
+ { "", {
+ { Tokenizer::TYPE_END , "" , 0, 0 },
+ }},
+
+ // Test all token types at the same time.
+ { "foo 1 1.2 + 'bar'", {
+ { Tokenizer::TYPE_IDENTIFIER, "foo" , 0, 0, 3 },
+ { Tokenizer::TYPE_INTEGER , "1" , 0, 4, 5 },
+ { Tokenizer::TYPE_FLOAT , "1.2" , 0, 6, 9 },
+ { Tokenizer::TYPE_SYMBOL , "+" , 0, 10, 11 },
+ { Tokenizer::TYPE_STRING , "'bar'", 0, 12, 17 },
+ { Tokenizer::TYPE_END , "" , 0, 17, 17 },
+ }},
+
+ // Test that consecutive symbols are parsed as separate tokens.
+ { "!@+%", {
+ { Tokenizer::TYPE_SYMBOL , "!" , 0, 0, 1 },
+ { Tokenizer::TYPE_SYMBOL , "@" , 0, 1, 2 },
+ { Tokenizer::TYPE_SYMBOL , "+" , 0, 2, 3 },
+ { Tokenizer::TYPE_SYMBOL , "%" , 0, 3, 4 },
+ { Tokenizer::TYPE_END , "" , 0, 4, 4 },
+ }},
+
+ // Test that newlines affect line numbers correctly.
+ { "foo bar\nrab oof", {
+ { Tokenizer::TYPE_IDENTIFIER, "foo", 0, 0, 3 },
+ { Tokenizer::TYPE_IDENTIFIER, "bar", 0, 4, 7 },
+ { Tokenizer::TYPE_IDENTIFIER, "rab", 1, 0, 3 },
+ { Tokenizer::TYPE_IDENTIFIER, "oof", 1, 4, 7 },
+ { Tokenizer::TYPE_END , "" , 1, 7, 7 },
+ }},
+
+ // Test that tabs affect column numbers correctly.
+ { "foo\tbar \tbaz", {
+ { Tokenizer::TYPE_IDENTIFIER, "foo", 0, 0, 3 },
+ { Tokenizer::TYPE_IDENTIFIER, "bar", 0, 8, 11 },
+ { Tokenizer::TYPE_IDENTIFIER, "baz", 0, 16, 19 },
+ { Tokenizer::TYPE_END , "" , 0, 19, 19 },
+ }},
+
+ // Test that tabs in string literals affect column numbers correctly.
+ { "\"foo\tbar\" baz", {
+ { Tokenizer::TYPE_STRING , "\"foo\tbar\"", 0, 0, 12 },
+ { Tokenizer::TYPE_IDENTIFIER, "baz" , 0, 13, 16 },
+ { Tokenizer::TYPE_END , "" , 0, 16, 16 },
+ }},
+
+ // Test that line comments are ignored.
+ { "foo // This is a comment\n"
+ "bar // This is another comment", {
+ { Tokenizer::TYPE_IDENTIFIER, "foo", 0, 0, 3 },
+ { Tokenizer::TYPE_IDENTIFIER, "bar", 1, 0, 3 },
+ { Tokenizer::TYPE_END , "" , 1, 30, 30 },
+ }},
+
+ // Test that block comments are ignored.
+ { "foo /* This is a block comment */ bar", {
+ { Tokenizer::TYPE_IDENTIFIER, "foo", 0, 0, 3 },
+ { Tokenizer::TYPE_IDENTIFIER, "bar", 0, 34, 37 },
+ { Tokenizer::TYPE_END , "" , 0, 37, 37 },
+ }},
+
+ // Test that sh-style comments are not ignored by default.
+ { "foo # bar\n"
+ "baz", {
+ { Tokenizer::TYPE_IDENTIFIER, "foo", 0, 0, 3 },
+ { Tokenizer::TYPE_SYMBOL , "#" , 0, 4, 5 },
+ { Tokenizer::TYPE_IDENTIFIER, "bar", 0, 6, 9 },
+ { Tokenizer::TYPE_IDENTIFIER, "baz", 1, 0, 3 },
+ { Tokenizer::TYPE_END , "" , 1, 3, 3 },
+ }},
+
+ // Test all whitespace chars
+ { "foo\n\t\r\v\fbar", {
+ { Tokenizer::TYPE_IDENTIFIER, "foo", 0, 0, 3 },
+ { Tokenizer::TYPE_IDENTIFIER, "bar", 1, 11, 14 },
+ { Tokenizer::TYPE_END , "" , 1, 14, 14 },
+ }},
+};
+
+TEST_2D(TokenizerTest, MultipleTokens, kMultiTokenCases, kBlockSizes) {
+ // Set up the tokenizer.
+ TestInputStream input(kMultiTokenCases_case.input.data(),
+ kMultiTokenCases_case.input.size(),
+ kBlockSizes_case);
+ TestErrorCollector error_collector;
+ Tokenizer tokenizer(&input, &error_collector);
+
+ // Before Next() is called, the initial token should always be TYPE_START.
+ EXPECT_EQ(Tokenizer::TYPE_START, tokenizer.current().type);
+ EXPECT_EQ("", tokenizer.current().text);
+ EXPECT_EQ(0, tokenizer.current().line);
+ EXPECT_EQ(0, tokenizer.current().column);
+ EXPECT_EQ(0, tokenizer.current().end_column);
+
+ // Loop through all expected tokens.
+ int i = 0;
+ Tokenizer::Token token;
+ do {
+ token = kMultiTokenCases_case.output[i++];
+
+ SCOPED_TRACE(testing::Message() << "Token #" << i << ": " << token.text);
+
+ Tokenizer::Token previous = tokenizer.current();
+
+ // Next() should only return false when it hits the end token.
+ if (token.type != Tokenizer::TYPE_END) {
+ ASSERT_TRUE(tokenizer.Next());
+ } else {
+ ASSERT_FALSE(tokenizer.Next());
+ }
+
+ // Check that the previous token is set correctly.
+ EXPECT_EQ(previous.type, tokenizer.previous().type);
+ EXPECT_EQ(previous.text, tokenizer.previous().text);
+ EXPECT_EQ(previous.line, tokenizer.previous().line);
+ EXPECT_EQ(previous.column, tokenizer.previous().column);
+ EXPECT_EQ(previous.end_column, tokenizer.previous().end_column);
+
+ // Check that the token matches the expected one.
+ EXPECT_EQ(token.type, tokenizer.current().type);
+ EXPECT_EQ(token.text, tokenizer.current().text);
+ EXPECT_EQ(token.line, tokenizer.current().line);
+ EXPECT_EQ(token.column, tokenizer.current().column);
+ EXPECT_EQ(token.end_column, tokenizer.current().end_column);
+
+ } while (token.type != Tokenizer::TYPE_END);
+
+ // There should be no errors.
+ EXPECT_TRUE(error_collector.text_.empty());
+}
+
+// This test causes gcc 3.3.5 (and earlier?) to give the cryptic error:
+// "sorry, unimplemented: `method_call_expr' not supported by dump_expr"
+#if !defined(__GNUC__) || __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ > 3)
+
+TEST_1D(TokenizerTest, ShCommentStyle, kBlockSizes) {
+ // Test the "comment_style" option.
+
+ const char* text = "foo # bar\n"
+ "baz // qux\n"
+ "corge /* grault */\n"
+ "garply";
+ const char* const kTokens[] = {"foo", // "# bar" is ignored
+ "baz", "/", "/", "qux",
+ "corge", "/", "*", "grault", "*", "/",
+ "garply"};
+
+ // Set up the tokenizer.
+ TestInputStream input(text, strlen(text), kBlockSizes_case);
+ TestErrorCollector error_collector;
+ Tokenizer tokenizer(&input, &error_collector);
+ tokenizer.set_comment_style(Tokenizer::SH_COMMENT_STYLE);
+
+ // Advance through tokens and check that they are parsed as expected.
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(kTokens); i++) {
+ EXPECT_TRUE(tokenizer.Next());
+ EXPECT_EQ(tokenizer.current().text, kTokens[i]);
+ }
+
+ // There should be no more input.
+ EXPECT_FALSE(tokenizer.Next());
+ // There should be no errors.
+ EXPECT_TRUE(error_collector.text_.empty());
+}
+
+#endif
+
+// -------------------------------------------------------------------
+
+// In each case, the input is expected to have two tokens named "prev" and
+// "next" with comments in between.
+struct DocCommentCase {
+ string input;
+
+ const char* prev_trailing_comments;
+ const char* detached_comments[10];
+ const char* next_leading_comments;
+};
+
+inline ostream& operator<<(ostream& out,
+ const DocCommentCase& test_case) {
+ return out << CEscape(test_case.input);
+}
+
+DocCommentCase kDocCommentCases[] = {
+ {
+ "prev next",
+
+ "",
+ {},
+ ""
+ },
+
+ {
+ "prev /* ignored */ next",
+
+ "",
+ {},
+ ""
+ },
+
+ {
+ "prev // trailing comment\n"
+ "next",
+
+ " trailing comment\n",
+ {},
+ ""
+ },
+
+ {
+ "prev\n"
+ "// leading comment\n"
+ "// line 2\n"
+ "next",
+
+ "",
+ {},
+ " leading comment\n"
+ " line 2\n"
+ },
+
+ {
+ "prev\n"
+ "// trailing comment\n"
+ "// line 2\n"
+ "\n"
+ "next",
+
+ " trailing comment\n"
+ " line 2\n",
+ {},
+ ""
+ },
+
+ {
+ "prev // trailing comment\n"
+ "// leading comment\n"
+ "// line 2\n"
+ "next",
+
+ " trailing comment\n",
+ {},
+ " leading comment\n"
+ " line 2\n"
+ },
+
+ {
+ "prev /* trailing block comment */\n"
+ "/* leading block comment\n"
+ " * line 2\n"
+ " * line 3 */"
+ "next",
+
+ " trailing block comment ",
+ {},
+ " leading block comment\n"
+ " line 2\n"
+ " line 3 "
+ },
+
+ {
+ "prev\n"
+ "/* trailing block comment\n"
+ " * line 2\n"
+ " * line 3\n"
+ " */\n"
+ "/* leading block comment\n"
+ " * line 2\n"
+ " * line 3 */"
+ "next",
+
+ " trailing block comment\n"
+ " line 2\n"
+ " line 3\n",
+ {},
+ " leading block comment\n"
+ " line 2\n"
+ " line 3 "
+ },
+
+ {
+ "prev\n"
+ "// trailing comment\n"
+ "\n"
+ "// detached comment\n"
+ "// line 2\n"
+ "\n"
+ "// second detached comment\n"
+ "/* third detached comment\n"
+ " * line 2 */\n"
+ "// leading comment\n"
+ "next",
+
+ " trailing comment\n",
+ {
+ " detached comment\n"
+ " line 2\n",
+ " second detached comment\n",
+ " third detached comment\n"
+ " line 2 "
+ },
+ " leading comment\n"
+ },
+
+ {
+ "prev /**/\n"
+ "\n"
+ "// detached comment\n"
+ "\n"
+ "// leading comment\n"
+ "next",
+
+ "",
+ {
+ " detached comment\n"
+ },
+ " leading comment\n"
+ },
+
+ {
+ "prev /**/\n"
+ "// leading comment\n"
+ "next",
+
+ "",
+ {},
+ " leading comment\n"
+ },
+ };
+
+TEST_2D(TokenizerTest, DocComments, kDocCommentCases, kBlockSizes) {
+ // Set up the tokenizer.
+ TestInputStream input(kDocCommentCases_case.input.data(),
+ kDocCommentCases_case.input.size(),
+ kBlockSizes_case);
+ TestErrorCollector error_collector;
+ Tokenizer tokenizer(&input, &error_collector);
+
+ // Set up a second tokenizer where we'll pass all NULLs to NextWithComments().
+ TestInputStream input2(kDocCommentCases_case.input.data(),
+ kDocCommentCases_case.input.size(),
+ kBlockSizes_case);
+ Tokenizer tokenizer2(&input2, &error_collector);
+
+ tokenizer.Next();
+ tokenizer2.Next();
+
+ EXPECT_EQ("prev", tokenizer.current().text);
+ EXPECT_EQ("prev", tokenizer2.current().text);
+
+ string prev_trailing_comments;
+ vector<string> detached_comments;
+ string next_leading_comments;
+ tokenizer.NextWithComments(&prev_trailing_comments, &detached_comments,
+ &next_leading_comments);
+ tokenizer2.NextWithComments(NULL, NULL, NULL);
+ EXPECT_EQ("next", tokenizer.current().text);
+ EXPECT_EQ("next", tokenizer2.current().text);
+
+ EXPECT_EQ(kDocCommentCases_case.prev_trailing_comments,
+ prev_trailing_comments);
+
+ for (int i = 0; i < detached_comments.size(); i++) {
+ ASSERT_LT(i, GOOGLE_ARRAYSIZE(kDocCommentCases));
+ ASSERT_TRUE(kDocCommentCases_case.detached_comments[i] != NULL);
+ EXPECT_EQ(kDocCommentCases_case.detached_comments[i],
+ detached_comments[i]);
+ }
+
+ // Verify that we matched all the detached comments.
+ EXPECT_EQ(NULL,
+ kDocCommentCases_case.detached_comments[detached_comments.size()]);
+
+ EXPECT_EQ(kDocCommentCases_case.next_leading_comments,
+ next_leading_comments);
+}
+
+// -------------------------------------------------------------------
+
+// Test parse helpers. It's not really worth setting up a full data-driven
+// test here.
+TEST_F(TokenizerTest, ParseInteger) {
+ EXPECT_EQ(0, ParseInteger("0"));
+ EXPECT_EQ(123, ParseInteger("123"));
+ EXPECT_EQ(0xabcdef12u, ParseInteger("0xabcdef12"));
+ EXPECT_EQ(0xabcdef12u, ParseInteger("0xABCDEF12"));
+ EXPECT_EQ(kuint64max, ParseInteger("0xFFFFFFFFFFFFFFFF"));
+ EXPECT_EQ(01234567, ParseInteger("01234567"));
+ EXPECT_EQ(0X123, ParseInteger("0X123"));
+
+ // Test invalid integers that may still be tokenized as integers.
+ EXPECT_EQ(0, ParseInteger("0x"));
+
+ uint64 i;
+
+ // Test invalid integers that will never be tokenized as integers.
+ EXPECT_FALSE(Tokenizer::ParseInteger("zxy", kuint64max, &i));
+ EXPECT_FALSE(Tokenizer::ParseInteger("1.2", kuint64max, &i));
+ EXPECT_FALSE(Tokenizer::ParseInteger("08", kuint64max, &i));
+ EXPECT_FALSE(Tokenizer::ParseInteger("0xg", kuint64max, &i));
+ EXPECT_FALSE(Tokenizer::ParseInteger("-1", kuint64max, &i));
+
+ // Test overflows.
+ EXPECT_TRUE (Tokenizer::ParseInteger("0", 0, &i));
+ EXPECT_FALSE(Tokenizer::ParseInteger("1", 0, &i));
+ EXPECT_TRUE (Tokenizer::ParseInteger("1", 1, &i));
+ EXPECT_TRUE (Tokenizer::ParseInteger("12345", 12345, &i));
+ EXPECT_FALSE(Tokenizer::ParseInteger("12346", 12345, &i));
+ EXPECT_TRUE (Tokenizer::ParseInteger("0xFFFFFFFFFFFFFFFF" , kuint64max, &i));
+ EXPECT_FALSE(Tokenizer::ParseInteger("0x10000000000000000", kuint64max, &i));
+}
+
+TEST_F(TokenizerTest, ParseFloat) {
+ EXPECT_DOUBLE_EQ(1 , Tokenizer::ParseFloat("1."));
+ EXPECT_DOUBLE_EQ(1e3 , Tokenizer::ParseFloat("1e3"));
+ EXPECT_DOUBLE_EQ(1e3 , Tokenizer::ParseFloat("1E3"));
+ EXPECT_DOUBLE_EQ(1.5e3, Tokenizer::ParseFloat("1.5e3"));
+ EXPECT_DOUBLE_EQ(.1 , Tokenizer::ParseFloat(".1"));
+ EXPECT_DOUBLE_EQ(.25 , Tokenizer::ParseFloat(".25"));
+ EXPECT_DOUBLE_EQ(.1e3 , Tokenizer::ParseFloat(".1e3"));
+ EXPECT_DOUBLE_EQ(.25e3, Tokenizer::ParseFloat(".25e3"));
+ EXPECT_DOUBLE_EQ(.1e+3, Tokenizer::ParseFloat(".1e+3"));
+ EXPECT_DOUBLE_EQ(.1e-3, Tokenizer::ParseFloat(".1e-3"));
+ EXPECT_DOUBLE_EQ(5 , Tokenizer::ParseFloat("5"));
+ EXPECT_DOUBLE_EQ(6e-12, Tokenizer::ParseFloat("6e-12"));
+ EXPECT_DOUBLE_EQ(1.2 , Tokenizer::ParseFloat("1.2"));
+ EXPECT_DOUBLE_EQ(1.e2 , Tokenizer::ParseFloat("1.e2"));
+
+ // Test invalid integers that may still be tokenized as integers.
+ EXPECT_DOUBLE_EQ(1, Tokenizer::ParseFloat("1e"));
+ EXPECT_DOUBLE_EQ(1, Tokenizer::ParseFloat("1e-"));
+ EXPECT_DOUBLE_EQ(1, Tokenizer::ParseFloat("1.e"));
+
+ // Test 'f' suffix.
+ EXPECT_DOUBLE_EQ(1, Tokenizer::ParseFloat("1f"));
+ EXPECT_DOUBLE_EQ(1, Tokenizer::ParseFloat("1.0f"));
+ EXPECT_DOUBLE_EQ(1, Tokenizer::ParseFloat("1F"));
+
+ // These should parse successfully even though they are out of range.
+ // Overflows become infinity and underflows become zero.
+ EXPECT_EQ( 0.0, Tokenizer::ParseFloat("1e-9999999999999999999999999999"));
+ EXPECT_EQ(HUGE_VAL, Tokenizer::ParseFloat("1e+9999999999999999999999999999"));
+
+#ifdef PROTOBUF_HAS_DEATH_TEST // death tests do not work on Windows yet
+ // Test invalid integers that will never be tokenized as integers.
+ EXPECT_DEBUG_DEATH(Tokenizer::ParseFloat("zxy"),
+ "passed text that could not have been tokenized as a float");
+ EXPECT_DEBUG_DEATH(Tokenizer::ParseFloat("1-e0"),
+ "passed text that could not have been tokenized as a float");
+ EXPECT_DEBUG_DEATH(Tokenizer::ParseFloat("-1.0"),
+ "passed text that could not have been tokenized as a float");
+#endif // PROTOBUF_HAS_DEATH_TEST
+}
+
+TEST_F(TokenizerTest, ParseString) {
+ string output;
+ Tokenizer::ParseString("'hello'", &output);
+ EXPECT_EQ("hello", output);
+ Tokenizer::ParseString("\"blah\\nblah2\"", &output);
+ EXPECT_EQ("blah\nblah2", output);
+ Tokenizer::ParseString("'\\1x\\1\\123\\739\\52\\334n\\3'", &output);
+ EXPECT_EQ("\1x\1\123\739\52\334n\3", output);
+ Tokenizer::ParseString("'\\x20\\x4'", &output);
+ EXPECT_EQ("\x20\x4", output);
+
+ // Test invalid strings that may still be tokenized as strings.
+ Tokenizer::ParseString("\"\\a\\l\\v\\t", &output); // \l is invalid
+ EXPECT_EQ("\a?\v\t", output);
+ Tokenizer::ParseString("'", &output);
+ EXPECT_EQ("", output);
+ Tokenizer::ParseString("'\\", &output);
+ EXPECT_EQ("\\", output);
+
+ // Experiment with Unicode escapes. Here are one-, two- and three-byte Unicode
+ // characters.
+ Tokenizer::ParseString("'\\u0024\\u00a2\\u20ac\\U00024b62XX'", &output);
+ EXPECT_EQ("$¢€𤭢XX", output);
+ // Same thing encoded using UTF16.
+ Tokenizer::ParseString("'\\u0024\\u00a2\\u20ac\\ud852\\udf62XX'", &output);
+ EXPECT_EQ("$¢€𤭢XX", output);
+ // Here's some broken UTF16; there's a head surrogate with no tail surrogate.
+ // We just output this as if it were UTF8; it's not a defined code point, but
+ // it has a defined encoding.
+ Tokenizer::ParseString("'\\ud852XX'", &output);
+ EXPECT_EQ("\xed\xa1\x92XX", output);
+ // Malformed escape: Demons may fly out of the nose.
+ Tokenizer::ParseString("\\u0", &output);
+ EXPECT_EQ("u0", output);
+
+ // Test invalid strings that will never be tokenized as strings.
+#ifdef PROTOBUF_HAS_DEATH_TEST // death tests do not work on Windows yet
+ EXPECT_DEBUG_DEATH(Tokenizer::ParseString("", &output),
+ "passed text that could not have been tokenized as a string");
+#endif // PROTOBUF_HAS_DEATH_TEST
+}
+
+TEST_F(TokenizerTest, ParseStringAppend) {
+ // Check that ParseString and ParseStringAppend differ.
+ string output("stuff+");
+ Tokenizer::ParseStringAppend("'hello'", &output);
+ EXPECT_EQ("stuff+hello", output);
+ Tokenizer::ParseString("'hello'", &output);
+ EXPECT_EQ("hello", output);
+}
+
+// -------------------------------------------------------------------
+
+// Each case parses some input text, ignoring the tokens produced, and
+// checks that the error output matches what is expected.
+struct ErrorCase {
+ string input;
+ bool recoverable; // True if the tokenizer should be able to recover and
+ // parse more tokens after seeing this error. Cases
+ // for which this is true must end with "foo" as
+ // the last token, which the test will check for.
+ const char* errors;
+};
+
+inline ostream& operator<<(ostream& out,
+ const ErrorCase& test_case) {
+ return out << CEscape(test_case.input);
+}
+
+ErrorCase kErrorCases[] = {
+ // String errors.
+ { "'\\l' foo", true,
+ "0:2: Invalid escape sequence in string literal.\n" },
+ { "'\\X' foo", true,
+ "0:2: Invalid escape sequence in string literal.\n" },
+ { "'\\x' foo", true,
+ "0:3: Expected hex digits for escape sequence.\n" },
+ { "'foo", false,
+ "0:4: Unexpected end of string.\n" },
+ { "'bar\nfoo", true,
+ "0:4: String literals cannot cross line boundaries.\n" },
+ { "'\\u01' foo", true,
+ "0:5: Expected four hex digits for \\u escape sequence.\n" },
+ { "'\\u01' foo", true,
+ "0:5: Expected four hex digits for \\u escape sequence.\n" },
+ { "'\\uXYZ' foo", true,
+ "0:3: Expected four hex digits for \\u escape sequence.\n" },
+
+ // Integer errors.
+ { "123foo", true,
+ "0:3: Need space between number and identifier.\n" },
+
+ // Hex/octal errors.
+ { "0x foo", true,
+ "0:2: \"0x\" must be followed by hex digits.\n" },
+ { "0541823 foo", true,
+ "0:4: Numbers starting with leading zero must be in octal.\n" },
+ { "0x123z foo", true,
+ "0:5: Need space between number and identifier.\n" },
+ { "0x123.4 foo", true,
+ "0:5: Hex and octal numbers must be integers.\n" },
+ { "0123.4 foo", true,
+ "0:4: Hex and octal numbers must be integers.\n" },
+
+ // Float errors.
+ { "1e foo", true,
+ "0:2: \"e\" must be followed by exponent.\n" },
+ { "1e- foo", true,
+ "0:3: \"e\" must be followed by exponent.\n" },
+ { "1.2.3 foo", true,
+ "0:3: Already saw decimal point or exponent; can't have another one.\n" },
+ { "1e2.3 foo", true,
+ "0:3: Already saw decimal point or exponent; can't have another one.\n" },
+ { "a.1 foo", true,
+ "0:1: Need space between identifier and decimal point.\n" },
+ // allow_f_after_float not enabled, so this should be an error.
+ { "1.0f foo", true,
+ "0:3: Need space between number and identifier.\n" },
+
+ // Block comment errors.
+ { "/*", false,
+ "0:2: End-of-file inside block comment.\n"
+ "0:0: Comment started here.\n"},
+ { "/*/*/ foo", true,
+ "0:3: \"/*\" inside block comment. Block comments cannot be nested.\n"},
+
+ // Control characters. Multiple consecutive control characters should only
+ // produce one error.
+ { "\b foo", true,
+ "0:0: Invalid control characters encountered in text.\n" },
+ { "\b\b foo", true,
+ "0:0: Invalid control characters encountered in text.\n" },
+
+ // Check that control characters at end of input don't result in an
+ // infinite loop.
+ { "\b", false,
+ "0:0: Invalid control characters encountered in text.\n" },
+
+ // Check recovery from '\0'. We have to explicitly specify the length of
+ // these strings because otherwise the string constructor will just call
+ // strlen() which will see the first '\0' and think that is the end of the
+ // string.
+ { string("\0foo", 4), true,
+ "0:0: Invalid control characters encountered in text.\n" },
+ { string("\0\0foo", 5), true,
+ "0:0: Invalid control characters encountered in text.\n" },
+
+ // Check error from high order bits set
+ { "\300foo", true,
+ "0:0: Interpreting non ascii codepoint 192.\n" },
+};
+
+TEST_2D(TokenizerTest, Errors, kErrorCases, kBlockSizes) {
+ // Set up the tokenizer.
+ TestInputStream input(kErrorCases_case.input.data(),
+ kErrorCases_case.input.size(),
+ kBlockSizes_case);
+ TestErrorCollector error_collector;
+ Tokenizer tokenizer(&input, &error_collector);
+
+ // Ignore all input, except remember if the last token was "foo".
+ bool last_was_foo = false;
+ while (tokenizer.Next()) {
+ last_was_foo = tokenizer.current().text == "foo";
+ }
+
+ // Check that the errors match what was expected.
+ EXPECT_EQ(kErrorCases_case.errors, error_collector.text_);
+
+ // If the error was recoverable, make sure we saw "foo" after it.
+ if (kErrorCases_case.recoverable) {
+ EXPECT_TRUE(last_was_foo);
+ }
+}
+
+// -------------------------------------------------------------------
+
+TEST_1D(TokenizerTest, BackUpOnDestruction, kBlockSizes) {
+ string text = "foo bar";
+ TestInputStream input(text.data(), text.size(), kBlockSizes_case);
+
+ // Create a tokenizer, read one token, then destroy it.
+ {
+ TestErrorCollector error_collector;
+ Tokenizer tokenizer(&input, &error_collector);
+
+ tokenizer.Next();
+ }
+
+ // Only "foo" should have been read.
+ EXPECT_EQ(strlen("foo"), input.ByteCount());
+}
+
+
+} // namespace
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.cc
new file mode 100644
index 0000000000..186de00141
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.cc
@@ -0,0 +1,58 @@
+// 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.
+
+#include <google/protobuf/io/zero_copy_stream.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+ZeroCopyInputStream::~ZeroCopyInputStream() {}
+ZeroCopyOutputStream::~ZeroCopyOutputStream() {}
+
+
+bool ZeroCopyOutputStream::WriteAliasedRaw(const void* /* data */,
+ int /* size */) {
+ GOOGLE_LOG(FATAL) << "This ZeroCopyOutputStream doesn't support aliasing. "
+ "Reaching here usually means a ZeroCopyOutputStream "
+ "implementation bug.";
+ return false;
+}
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.h
new file mode 100644
index 0000000000..52650fc668
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream.h
@@ -0,0 +1,248 @@
+// 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 ZeroCopyInputStream and ZeroCopyOutputStream
+// interfaces, which represent abstract I/O streams to and from which
+// protocol buffers can be read and written. For a few simple
+// implementations of these interfaces, see zero_copy_stream_impl.h.
+//
+// These interfaces are different from classic I/O streams in that they
+// try to minimize the amount of data copying that needs to be done.
+// To accomplish this, responsibility for allocating buffers is moved to
+// the stream object, rather than being the responsibility of the caller.
+// So, the stream can return a buffer which actually points directly into
+// the final data structure where the bytes are to be stored, and the caller
+// can interact directly with that buffer, eliminating an intermediate copy
+// operation.
+//
+// As an example, consider the common case in which you are reading bytes
+// from an array that is already in memory (or perhaps an mmap()ed file).
+// With classic I/O streams, you would do something like:
+// char buffer[BUFFER_SIZE];
+// input->Read(buffer, BUFFER_SIZE);
+// DoSomething(buffer, BUFFER_SIZE);
+// Then, the stream basically just calls memcpy() to copy the data from
+// the array into your buffer. With a ZeroCopyInputStream, you would do
+// this instead:
+// const void* buffer;
+// int size;
+// input->Next(&buffer, &size);
+// DoSomething(buffer, size);
+// Here, no copy is performed. The input stream returns a pointer directly
+// into the backing array, and the caller ends up reading directly from it.
+//
+// If you want to be able to read the old-fashion way, you can create
+// a CodedInputStream or CodedOutputStream wrapping these objects and use
+// their ReadRaw()/WriteRaw() methods. These will, of course, add a copy
+// step, but Coded*Stream will handle buffering so at least it will be
+// reasonably efficient.
+//
+// ZeroCopyInputStream example:
+// // Read in a file and print its contents to stdout.
+// int fd = open("myfile", O_RDONLY);
+// ZeroCopyInputStream* input = new FileInputStream(fd);
+//
+// const void* buffer;
+// int size;
+// while (input->Next(&buffer, &size)) {
+// cout.write(buffer, size);
+// }
+//
+// delete input;
+// close(fd);
+//
+// ZeroCopyOutputStream example:
+// // Copy the contents of "infile" to "outfile", using plain read() for
+// // "infile" but a ZeroCopyOutputStream for "outfile".
+// int infd = open("infile", O_RDONLY);
+// int outfd = open("outfile", O_WRONLY);
+// ZeroCopyOutputStream* output = new FileOutputStream(outfd);
+//
+// void* buffer;
+// int size;
+// while (output->Next(&buffer, &size)) {
+// int bytes = read(infd, buffer, size);
+// if (bytes < size) {
+// // Reached EOF.
+// output->BackUp(size - bytes);
+// break;
+// }
+// }
+//
+// delete output;
+// close(infd);
+// close(outfd);
+
+#ifndef GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_H__
+#define GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_H__
+
+#include <string>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+
+namespace protobuf {
+namespace io {
+
+// Defined in this file.
+class ZeroCopyInputStream;
+class ZeroCopyOutputStream;
+
+// Abstract interface similar to an input stream but designed to minimize
+// copying.
+class LIBPROTOBUF_EXPORT ZeroCopyInputStream {
+ public:
+ inline ZeroCopyInputStream() {}
+ virtual ~ZeroCopyInputStream();
+
+ // Obtains a chunk of data from the stream.
+ //
+ // Preconditions:
+ // * "size" and "data" are not NULL.
+ //
+ // Postconditions:
+ // * If the returned value is false, there is no more data to return or
+ // an error occurred. All errors are permanent.
+ // * Otherwise, "size" points to the actual number of bytes read and "data"
+ // points to a pointer to a buffer containing these bytes.
+ // * Ownership of this buffer remains with the stream, and the buffer
+ // remains valid only until some other method of the stream is called
+ // or the stream is destroyed.
+ // * It is legal for the returned buffer to have zero size, as long
+ // as repeatedly calling Next() eventually yields a buffer with non-zero
+ // size.
+ virtual bool Next(const void** data, int* size) = 0;
+
+ // Backs up a number of bytes, so that the next call to Next() returns
+ // data again that was already returned by the last call to Next(). This
+ // is useful when writing procedures that are only supposed to read up
+ // to a certain point in the input, then return. If Next() returns a
+ // buffer that goes beyond what you wanted to read, you can use BackUp()
+ // to return to the point where you intended to finish.
+ //
+ // Preconditions:
+ // * The last method called must have been Next().
+ // * count must be less than or equal to the size of the last buffer
+ // returned by Next().
+ //
+ // Postconditions:
+ // * The last "count" bytes of the last buffer returned by Next() will be
+ // pushed back into the stream. Subsequent calls to Next() will return
+ // the same data again before producing new data.
+ virtual void BackUp(int count) = 0;
+
+ // Skips a number of bytes. Returns false if the end of the stream is
+ // reached or some input error occurred. In the end-of-stream case, the
+ // stream is advanced to the end of the stream (so ByteCount() will return
+ // the total size of the stream).
+ virtual bool Skip(int count) = 0;
+
+ // Returns the total number of bytes read since this object was created.
+ virtual int64 ByteCount() const = 0;
+
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ZeroCopyInputStream);
+};
+
+// Abstract interface similar to an output stream but designed to minimize
+// copying.
+class LIBPROTOBUF_EXPORT ZeroCopyOutputStream {
+ public:
+ inline ZeroCopyOutputStream() {}
+ virtual ~ZeroCopyOutputStream();
+
+ // Obtains a buffer into which data can be written. Any data written
+ // into this buffer will eventually (maybe instantly, maybe later on)
+ // be written to the output.
+ //
+ // Preconditions:
+ // * "size" and "data" are not NULL.
+ //
+ // Postconditions:
+ // * If the returned value is false, an error occurred. All errors are
+ // permanent.
+ // * Otherwise, "size" points to the actual number of bytes in the buffer
+ // and "data" points to the buffer.
+ // * Ownership of this buffer remains with the stream, and the buffer
+ // remains valid only until some other method of the stream is called
+ // or the stream is destroyed.
+ // * Any data which the caller stores in this buffer will eventually be
+ // written to the output (unless BackUp() is called).
+ // * It is legal for the returned buffer to have zero size, as long
+ // as repeatedly calling Next() eventually yields a buffer with non-zero
+ // size.
+ virtual bool Next(void** data, int* size) = 0;
+
+ // Backs up a number of bytes, so that the end of the last buffer returned
+ // by Next() is not actually written. This is needed when you finish
+ // writing all the data you want to write, but the last buffer was bigger
+ // than you needed. You don't want to write a bunch of garbage after the
+ // end of your data, so you use BackUp() to back up.
+ //
+ // Preconditions:
+ // * The last method called must have been Next().
+ // * count must be less than or equal to the size of the last buffer
+ // returned by Next().
+ // * The caller must not have written anything to the last "count" bytes
+ // of that buffer.
+ //
+ // Postconditions:
+ // * The last "count" bytes of the last buffer returned by Next() will be
+ // ignored.
+ virtual void BackUp(int count) = 0;
+
+ // Returns the total number of bytes written since this object was created.
+ virtual int64 ByteCount() const = 0;
+
+ // Write a given chunk of data to the output. Some output streams may
+ // implement this in a way that avoids copying. Check AllowsAliasing() before
+ // calling WriteAliasedRaw(). It will GOOGLE_CHECK fail if WriteAliasedRaw() is
+ // called on a stream that does not allow aliasing.
+ //
+ // 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.
+ virtual bool WriteAliasedRaw(const void* data, int size);
+ virtual bool AllowsAliasing() const { return false; }
+
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ZeroCopyOutputStream);
+};
+
+} // namespace io
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.cc
new file mode 100644
index 0000000000..7ec2b5da5c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.cc
@@ -0,0 +1,474 @@
+// 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.
+
+#ifdef _MSC_VER
+#include <io.h>
+#else
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#endif
+#include <errno.h>
+#include <iostream>
+#include <algorithm>
+
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+#ifdef _WIN32
+// Win32 lseek is broken: If invoked on a non-seekable file descriptor, its
+// return value is undefined. We re-define it to always produce an error.
+#define lseek(fd, offset, origin) ((off_t)-1)
+#endif
+
+namespace {
+
+// EINTR sucks.
+int close_no_eintr(int fd) {
+ int result;
+ do {
+ result = close(fd);
+ } while (result < 0 && errno == EINTR);
+ return result;
+}
+
+} // namespace
+
+
+// ===================================================================
+
+FileInputStream::FileInputStream(int file_descriptor, int block_size)
+ : copying_input_(file_descriptor),
+ impl_(&copying_input_, block_size) {
+}
+
+FileInputStream::~FileInputStream() {}
+
+bool FileInputStream::Close() {
+ return copying_input_.Close();
+}
+
+bool FileInputStream::Next(const void** data, int* size) {
+ return impl_.Next(data, size);
+}
+
+void FileInputStream::BackUp(int count) {
+ impl_.BackUp(count);
+}
+
+bool FileInputStream::Skip(int count) {
+ return impl_.Skip(count);
+}
+
+int64 FileInputStream::ByteCount() const {
+ return impl_.ByteCount();
+}
+
+FileInputStream::CopyingFileInputStream::CopyingFileInputStream(
+ int file_descriptor)
+ : file_(file_descriptor),
+ close_on_delete_(false),
+ is_closed_(false),
+ errno_(0),
+ previous_seek_failed_(false) {
+}
+
+FileInputStream::CopyingFileInputStream::~CopyingFileInputStream() {
+ if (close_on_delete_) {
+ if (!Close()) {
+ GOOGLE_LOG(ERROR) << "close() failed: " << strerror(errno_);
+ }
+ }
+}
+
+bool FileInputStream::CopyingFileInputStream::Close() {
+ GOOGLE_CHECK(!is_closed_);
+
+ is_closed_ = true;
+ if (close_no_eintr(file_) != 0) {
+ // The docs on close() do not specify whether a file descriptor is still
+ // open after close() fails with EIO. However, the glibc source code
+ // seems to indicate that it is not.
+ errno_ = errno;
+ return false;
+ }
+
+ return true;
+}
+
+int FileInputStream::CopyingFileInputStream::Read(void* buffer, int size) {
+ GOOGLE_CHECK(!is_closed_);
+
+ int result;
+ do {
+ result = read(file_, buffer, size);
+ } while (result < 0 && errno == EINTR);
+
+ if (result < 0) {
+ // Read error (not EOF).
+ errno_ = errno;
+ }
+
+ return result;
+}
+
+int FileInputStream::CopyingFileInputStream::Skip(int count) {
+ GOOGLE_CHECK(!is_closed_);
+
+ if (!previous_seek_failed_ &&
+ lseek(file_, count, SEEK_CUR) != (off_t)-1) {
+ // Seek succeeded.
+ return count;
+ } else {
+ // Failed to seek.
+
+ // Note to self: Don't seek again. This file descriptor doesn't
+ // support it.
+ previous_seek_failed_ = true;
+
+ // Use the default implementation.
+ return CopyingInputStream::Skip(count);
+ }
+}
+
+// ===================================================================
+
+FileOutputStream::FileOutputStream(int file_descriptor, int block_size)
+ : copying_output_(file_descriptor),
+ impl_(&copying_output_, block_size) {
+}
+
+FileOutputStream::~FileOutputStream() {
+ impl_.Flush();
+}
+
+bool FileOutputStream::Close() {
+ bool flush_succeeded = impl_.Flush();
+ return copying_output_.Close() && flush_succeeded;
+}
+
+bool FileOutputStream::Flush() {
+ return impl_.Flush();
+}
+
+bool FileOutputStream::Next(void** data, int* size) {
+ return impl_.Next(data, size);
+}
+
+void FileOutputStream::BackUp(int count) {
+ impl_.BackUp(count);
+}
+
+int64 FileOutputStream::ByteCount() const {
+ return impl_.ByteCount();
+}
+
+FileOutputStream::CopyingFileOutputStream::CopyingFileOutputStream(
+ int file_descriptor)
+ : file_(file_descriptor),
+ close_on_delete_(false),
+ is_closed_(false),
+ errno_(0) {
+}
+
+FileOutputStream::CopyingFileOutputStream::~CopyingFileOutputStream() {
+ if (close_on_delete_) {
+ if (!Close()) {
+ GOOGLE_LOG(ERROR) << "close() failed: " << strerror(errno_);
+ }
+ }
+}
+
+bool FileOutputStream::CopyingFileOutputStream::Close() {
+ GOOGLE_CHECK(!is_closed_);
+
+ is_closed_ = true;
+ if (close_no_eintr(file_) != 0) {
+ // The docs on close() do not specify whether a file descriptor is still
+ // open after close() fails with EIO. However, the glibc source code
+ // seems to indicate that it is not.
+ errno_ = errno;
+ return false;
+ }
+
+ return true;
+}
+
+bool FileOutputStream::CopyingFileOutputStream::Write(
+ const void* buffer, int size) {
+ GOOGLE_CHECK(!is_closed_);
+ int total_written = 0;
+
+ const uint8* buffer_base = reinterpret_cast<const uint8*>(buffer);
+
+ while (total_written < size) {
+ int bytes;
+ do {
+ bytes = write(file_, buffer_base + total_written, size - total_written);
+ } while (bytes < 0 && errno == EINTR);
+
+ if (bytes <= 0) {
+ // Write error.
+
+ // FIXME(kenton): According to the man page, if write() returns zero,
+ // there was no error; write() simply did not write anything. It's
+ // unclear under what circumstances this might happen, but presumably
+ // errno won't be set in this case. I am confused as to how such an
+ // event should be handled. For now I'm treating it as an error, since
+ // retrying seems like it could lead to an infinite loop. I suspect
+ // this never actually happens anyway.
+
+ if (bytes < 0) {
+ errno_ = errno;
+ }
+ return false;
+ }
+ total_written += bytes;
+ }
+
+ return true;
+}
+
+// ===================================================================
+
+IstreamInputStream::IstreamInputStream(istream* input, int block_size)
+ : copying_input_(input),
+ impl_(&copying_input_, block_size) {
+}
+
+IstreamInputStream::~IstreamInputStream() {}
+
+bool IstreamInputStream::Next(const void** data, int* size) {
+ return impl_.Next(data, size);
+}
+
+void IstreamInputStream::BackUp(int count) {
+ impl_.BackUp(count);
+}
+
+bool IstreamInputStream::Skip(int count) {
+ return impl_.Skip(count);
+}
+
+int64 IstreamInputStream::ByteCount() const {
+ return impl_.ByteCount();
+}
+
+IstreamInputStream::CopyingIstreamInputStream::CopyingIstreamInputStream(
+ istream* input)
+ : input_(input) {
+}
+
+IstreamInputStream::CopyingIstreamInputStream::~CopyingIstreamInputStream() {}
+
+int IstreamInputStream::CopyingIstreamInputStream::Read(
+ void* buffer, int size) {
+ input_->read(reinterpret_cast<char*>(buffer), size);
+ int result = input_->gcount();
+ if (result == 0 && input_->fail() && !input_->eof()) {
+ return -1;
+ }
+ return result;
+}
+
+// ===================================================================
+
+OstreamOutputStream::OstreamOutputStream(ostream* output, int block_size)
+ : copying_output_(output),
+ impl_(&copying_output_, block_size) {
+}
+
+OstreamOutputStream::~OstreamOutputStream() {
+ impl_.Flush();
+}
+
+bool OstreamOutputStream::Next(void** data, int* size) {
+ return impl_.Next(data, size);
+}
+
+void OstreamOutputStream::BackUp(int count) {
+ impl_.BackUp(count);
+}
+
+int64 OstreamOutputStream::ByteCount() const {
+ return impl_.ByteCount();
+}
+
+OstreamOutputStream::CopyingOstreamOutputStream::CopyingOstreamOutputStream(
+ ostream* output)
+ : output_(output) {
+}
+
+OstreamOutputStream::CopyingOstreamOutputStream::~CopyingOstreamOutputStream() {
+}
+
+bool OstreamOutputStream::CopyingOstreamOutputStream::Write(
+ const void* buffer, int size) {
+ output_->write(reinterpret_cast<const char*>(buffer), size);
+ return output_->good();
+}
+
+// ===================================================================
+
+ConcatenatingInputStream::ConcatenatingInputStream(
+ ZeroCopyInputStream* const streams[], int count)
+ : streams_(streams), stream_count_(count), bytes_retired_(0) {
+}
+
+ConcatenatingInputStream::~ConcatenatingInputStream() {
+}
+
+bool ConcatenatingInputStream::Next(const void** data, int* size) {
+ while (stream_count_ > 0) {
+ if (streams_[0]->Next(data, size)) return true;
+
+ // That stream is done. Advance to the next one.
+ bytes_retired_ += streams_[0]->ByteCount();
+ ++streams_;
+ --stream_count_;
+ }
+
+ // No more streams.
+ return false;
+}
+
+void ConcatenatingInputStream::BackUp(int count) {
+ if (stream_count_ > 0) {
+ streams_[0]->BackUp(count);
+ } else {
+ GOOGLE_LOG(DFATAL) << "Can't BackUp() after failed Next().";
+ }
+}
+
+bool ConcatenatingInputStream::Skip(int count) {
+ while (stream_count_ > 0) {
+ // Assume that ByteCount() can be used to find out how much we actually
+ // skipped when Skip() fails.
+ int64 target_byte_count = streams_[0]->ByteCount() + count;
+ if (streams_[0]->Skip(count)) return true;
+
+ // Hit the end of the stream. Figure out how many more bytes we still have
+ // to skip.
+ int64 final_byte_count = streams_[0]->ByteCount();
+ GOOGLE_DCHECK_LT(final_byte_count, target_byte_count);
+ count = target_byte_count - final_byte_count;
+
+ // That stream is done. Advance to the next one.
+ bytes_retired_ += final_byte_count;
+ ++streams_;
+ --stream_count_;
+ }
+
+ return false;
+}
+
+int64 ConcatenatingInputStream::ByteCount() const {
+ if (stream_count_ == 0) {
+ return bytes_retired_;
+ } else {
+ return bytes_retired_ + streams_[0]->ByteCount();
+ }
+}
+
+
+// ===================================================================
+
+LimitingInputStream::LimitingInputStream(ZeroCopyInputStream* input,
+ int64 limit)
+ : input_(input), limit_(limit) {
+ prior_bytes_read_ = input_->ByteCount();
+}
+
+LimitingInputStream::~LimitingInputStream() {
+ // If we overshot the limit, back up.
+ if (limit_ < 0) input_->BackUp(-limit_);
+}
+
+bool LimitingInputStream::Next(const void** data, int* size) {
+ if (limit_ <= 0) return false;
+ if (!input_->Next(data, size)) return false;
+
+ limit_ -= *size;
+ if (limit_ < 0) {
+ // We overshot the limit. Reduce *size to hide the rest of the buffer.
+ *size += limit_;
+ }
+ return true;
+}
+
+void LimitingInputStream::BackUp(int count) {
+ if (limit_ < 0) {
+ input_->BackUp(count - limit_);
+ limit_ = count;
+ } else {
+ input_->BackUp(count);
+ limit_ += count;
+ }
+}
+
+bool LimitingInputStream::Skip(int count) {
+ if (count > limit_) {
+ if (limit_ < 0) return false;
+ input_->Skip(limit_);
+ limit_ = 0;
+ return false;
+ } else {
+ if (!input_->Skip(count)) return false;
+ limit_ -= count;
+ return true;
+ }
+}
+
+int64 LimitingInputStream::ByteCount() const {
+ if (limit_ < 0) {
+ return input_->ByteCount() + limit_ - prior_bytes_read_;
+ } else {
+ return input_->ByteCount() - prior_bytes_read_;
+ }
+}
+
+
+// ===================================================================
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.h
new file mode 100644
index 0000000000..0746fa6afe
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl.h
@@ -0,0 +1,358 @@
+// 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 common implementations of the interfaces defined in
+// zero_copy_stream.h which are only included in the full (non-lite)
+// protobuf library. These implementations include Unix file descriptors
+// and C++ iostreams. See also: zero_copy_stream_impl_lite.h
+
+#ifndef GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_IMPL_H__
+#define GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_IMPL_H__
+
+#include <string>
+#include <iosfwd>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/stubs/common.h>
+
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+
+// ===================================================================
+
+// A ZeroCopyInputStream which reads from a file descriptor.
+//
+// FileInputStream is preferred over using an ifstream with IstreamInputStream.
+// The latter will introduce an extra layer of buffering, harming performance.
+// Also, it's conceivable that FileInputStream could someday be enhanced
+// to use zero-copy file descriptors on OSs which support them.
+class LIBPROTOBUF_EXPORT FileInputStream : public ZeroCopyInputStream {
+ public:
+ // Creates a stream that reads from the given Unix file descriptor.
+ // If a block_size is given, it specifies the number of bytes that
+ // should be read and returned with each call to Next(). Otherwise,
+ // a reasonable default is used.
+ explicit FileInputStream(int file_descriptor, int block_size = -1);
+ ~FileInputStream();
+
+ // Flushes any buffers and closes the underlying file. Returns false if
+ // an error occurs during the process; use GetErrno() to examine the error.
+ // Even if an error occurs, the file descriptor is closed when this returns.
+ bool Close();
+
+ // By default, the file descriptor is not closed when the stream is
+ // destroyed. Call SetCloseOnDelete(true) to change that. WARNING:
+ // This leaves no way for the caller to detect if close() fails. If
+ // detecting close() errors is important to you, you should arrange
+ // to close the descriptor yourself.
+ void SetCloseOnDelete(bool value) { copying_input_.SetCloseOnDelete(value); }
+
+ // If an I/O error has occurred on this file descriptor, this is the
+ // errno from that error. Otherwise, this is zero. Once an error
+ // occurs, the stream is broken and all subsequent operations will
+ // fail.
+ int GetErrno() { return copying_input_.GetErrno(); }
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size);
+ void BackUp(int count);
+ bool Skip(int count);
+ int64 ByteCount() const;
+
+ private:
+ class LIBPROTOBUF_EXPORT CopyingFileInputStream : public CopyingInputStream {
+ public:
+ CopyingFileInputStream(int file_descriptor);
+ ~CopyingFileInputStream();
+
+ bool Close();
+ void SetCloseOnDelete(bool value) { close_on_delete_ = value; }
+ int GetErrno() { return errno_; }
+
+ // implements CopyingInputStream ---------------------------------
+ int Read(void* buffer, int size);
+ int Skip(int count);
+
+ private:
+ // The file descriptor.
+ const int file_;
+ bool close_on_delete_;
+ bool is_closed_;
+
+ // The errno of the I/O error, if one has occurred. Otherwise, zero.
+ int errno_;
+
+ // Did we try to seek once and fail? If so, we assume this file descriptor
+ // doesn't support seeking and won't try again.
+ bool previous_seek_failed_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CopyingFileInputStream);
+ };
+
+ CopyingFileInputStream copying_input_;
+ CopyingInputStreamAdaptor impl_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileInputStream);
+};
+
+// ===================================================================
+
+// A ZeroCopyOutputStream which writes to a file descriptor.
+//
+// FileOutputStream is preferred over using an ofstream with
+// OstreamOutputStream. The latter will introduce an extra layer of buffering,
+// harming performance. Also, it's conceivable that FileOutputStream could
+// someday be enhanced to use zero-copy file descriptors on OSs which
+// support them.
+class LIBPROTOBUF_EXPORT FileOutputStream : public ZeroCopyOutputStream {
+ public:
+ // Creates a stream that writes to the given Unix file descriptor.
+ // If a block_size is given, it specifies the size of the buffers
+ // that should be returned by Next(). Otherwise, a reasonable default
+ // is used.
+ explicit FileOutputStream(int file_descriptor, int block_size = -1);
+ ~FileOutputStream();
+
+ // Flushes any buffers and closes the underlying file. Returns false if
+ // an error occurs during the process; use GetErrno() to examine the error.
+ // Even if an error occurs, the file descriptor is closed when this returns.
+ bool Close();
+
+ // Flushes FileOutputStream's buffers but does not close the
+ // underlying file. No special measures are taken to ensure that
+ // underlying operating system file object is synchronized to disk.
+ bool Flush();
+
+ // By default, the file descriptor is not closed when the stream is
+ // destroyed. Call SetCloseOnDelete(true) to change that. WARNING:
+ // This leaves no way for the caller to detect if close() fails. If
+ // detecting close() errors is important to you, you should arrange
+ // to close the descriptor yourself.
+ void SetCloseOnDelete(bool value) { copying_output_.SetCloseOnDelete(value); }
+
+ // If an I/O error has occurred on this file descriptor, this is the
+ // errno from that error. Otherwise, this is zero. Once an error
+ // occurs, the stream is broken and all subsequent operations will
+ // fail.
+ int GetErrno() { return copying_output_.GetErrno(); }
+
+ // implements ZeroCopyOutputStream ---------------------------------
+ bool Next(void** data, int* size);
+ void BackUp(int count);
+ int64 ByteCount() const;
+
+ private:
+ class LIBPROTOBUF_EXPORT CopyingFileOutputStream : public CopyingOutputStream {
+ public:
+ CopyingFileOutputStream(int file_descriptor);
+ ~CopyingFileOutputStream();
+
+ bool Close();
+ void SetCloseOnDelete(bool value) { close_on_delete_ = value; }
+ int GetErrno() { return errno_; }
+
+ // implements CopyingOutputStream --------------------------------
+ bool Write(const void* buffer, int size);
+
+ private:
+ // The file descriptor.
+ const int file_;
+ bool close_on_delete_;
+ bool is_closed_;
+
+ // The errno of the I/O error, if one has occurred. Otherwise, zero.
+ int errno_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CopyingFileOutputStream);
+ };
+
+ CopyingFileOutputStream copying_output_;
+ CopyingOutputStreamAdaptor impl_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileOutputStream);
+};
+
+// ===================================================================
+
+// A ZeroCopyInputStream which reads from a C++ istream.
+//
+// Note that for reading files (or anything represented by a file descriptor),
+// FileInputStream is more efficient.
+class LIBPROTOBUF_EXPORT IstreamInputStream : public ZeroCopyInputStream {
+ public:
+ // Creates a stream that reads from the given C++ istream.
+ // If a block_size is given, it specifies the number of bytes that
+ // should be read and returned with each call to Next(). Otherwise,
+ // a reasonable default is used.
+ explicit IstreamInputStream(istream* stream, int block_size = -1);
+ ~IstreamInputStream();
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size);
+ void BackUp(int count);
+ bool Skip(int count);
+ int64 ByteCount() const;
+
+ private:
+ class LIBPROTOBUF_EXPORT CopyingIstreamInputStream : public CopyingInputStream {
+ public:
+ CopyingIstreamInputStream(istream* input);
+ ~CopyingIstreamInputStream();
+
+ // implements CopyingInputStream ---------------------------------
+ int Read(void* buffer, int size);
+ // (We use the default implementation of Skip().)
+
+ private:
+ // The stream.
+ istream* input_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CopyingIstreamInputStream);
+ };
+
+ CopyingIstreamInputStream copying_input_;
+ CopyingInputStreamAdaptor impl_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(IstreamInputStream);
+};
+
+// ===================================================================
+
+// A ZeroCopyOutputStream which writes to a C++ ostream.
+//
+// Note that for writing files (or anything represented by a file descriptor),
+// FileOutputStream is more efficient.
+class LIBPROTOBUF_EXPORT OstreamOutputStream : public ZeroCopyOutputStream {
+ public:
+ // Creates a stream that writes to the given C++ ostream.
+ // If a block_size is given, it specifies the size of the buffers
+ // that should be returned by Next(). Otherwise, a reasonable default
+ // is used.
+ explicit OstreamOutputStream(ostream* stream, int block_size = -1);
+ ~OstreamOutputStream();
+
+ // implements ZeroCopyOutputStream ---------------------------------
+ bool Next(void** data, int* size);
+ void BackUp(int count);
+ int64 ByteCount() const;
+
+ private:
+ class LIBPROTOBUF_EXPORT CopyingOstreamOutputStream : public CopyingOutputStream {
+ public:
+ CopyingOstreamOutputStream(ostream* output);
+ ~CopyingOstreamOutputStream();
+
+ // implements CopyingOutputStream --------------------------------
+ bool Write(const void* buffer, int size);
+
+ private:
+ // The stream.
+ ostream* output_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CopyingOstreamOutputStream);
+ };
+
+ CopyingOstreamOutputStream copying_output_;
+ CopyingOutputStreamAdaptor impl_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(OstreamOutputStream);
+};
+
+// ===================================================================
+
+// A ZeroCopyInputStream which reads from several other streams in sequence.
+// ConcatenatingInputStream is unable to distinguish between end-of-stream
+// and read errors in the underlying streams, so it assumes any errors mean
+// end-of-stream. So, if the underlying streams fail for any other reason,
+// ConcatenatingInputStream may do odd things. It is suggested that you do
+// not use ConcatenatingInputStream on streams that might produce read errors
+// other than end-of-stream.
+class LIBPROTOBUF_EXPORT ConcatenatingInputStream : public ZeroCopyInputStream {
+ public:
+ // All streams passed in as well as the array itself must remain valid
+ // until the ConcatenatingInputStream is destroyed.
+ ConcatenatingInputStream(ZeroCopyInputStream* const streams[], int count);
+ ~ConcatenatingInputStream();
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size);
+ void BackUp(int count);
+ bool Skip(int count);
+ int64 ByteCount() const;
+
+
+ private:
+ // As streams are retired, streams_ is incremented and count_ is
+ // decremented.
+ ZeroCopyInputStream* const* streams_;
+ int stream_count_;
+ int64 bytes_retired_; // Bytes read from previous streams.
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ConcatenatingInputStream);
+};
+
+// ===================================================================
+
+// A ZeroCopyInputStream which wraps some other stream and limits it to
+// a particular byte count.
+class LIBPROTOBUF_EXPORT LimitingInputStream : public ZeroCopyInputStream {
+ public:
+ LimitingInputStream(ZeroCopyInputStream* input, int64 limit);
+ ~LimitingInputStream();
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size);
+ void BackUp(int count);
+ bool Skip(int count);
+ int64 ByteCount() const;
+
+
+ private:
+ ZeroCopyInputStream* input_;
+ int64 limit_; // Decreases as we go, becomes negative if we overshoot.
+ int64 prior_bytes_read_; // Bytes read on underlying stream at construction
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(LimitingInputStream);
+};
+
+// ===================================================================
+
+} // namespace io
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_IMPL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.cc
new file mode 100644
index 0000000000..e6ca88c21b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.cc
@@ -0,0 +1,438 @@
+// 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.
+
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+
+#include <algorithm>
+#include <limits>
+
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+namespace {
+
+// Default block size for Copying{In,Out}putStreamAdaptor.
+static const int kDefaultBlockSize = 8192;
+
+} // namespace
+
+// ===================================================================
+
+ArrayInputStream::ArrayInputStream(const void* data, int size,
+ int block_size)
+ : data_(reinterpret_cast<const uint8*>(data)),
+ size_(size),
+ block_size_(block_size > 0 ? block_size : size),
+ position_(0),
+ last_returned_size_(0) {
+}
+
+ArrayInputStream::~ArrayInputStream() {
+}
+
+bool ArrayInputStream::Next(const void** data, int* size) {
+ if (position_ < size_) {
+ last_returned_size_ = std::min(block_size_, size_ - position_);
+ *data = data_ + position_;
+ *size = last_returned_size_;
+ position_ += last_returned_size_;
+ return true;
+ } else {
+ // We're at the end of the array.
+ last_returned_size_ = 0; // Don't let caller back up.
+ return false;
+ }
+}
+
+void ArrayInputStream::BackUp(int count) {
+ GOOGLE_CHECK_GT(last_returned_size_, 0)
+ << "BackUp() can only be called after a successful Next().";
+ GOOGLE_CHECK_LE(count, last_returned_size_);
+ GOOGLE_CHECK_GE(count, 0);
+ position_ -= count;
+ last_returned_size_ = 0; // Don't let caller back up further.
+}
+
+bool ArrayInputStream::Skip(int count) {
+ GOOGLE_CHECK_GE(count, 0);
+ last_returned_size_ = 0; // Don't let caller back up.
+ if (count > size_ - position_) {
+ position_ = size_;
+ return false;
+ } else {
+ position_ += count;
+ return true;
+ }
+}
+
+int64 ArrayInputStream::ByteCount() const {
+ return position_;
+}
+
+
+// ===================================================================
+
+ArrayOutputStream::ArrayOutputStream(void* data, int size, int block_size)
+ : data_(reinterpret_cast<uint8*>(data)),
+ size_(size),
+ block_size_(block_size > 0 ? block_size : size),
+ position_(0),
+ last_returned_size_(0) {
+}
+
+ArrayOutputStream::~ArrayOutputStream() {
+}
+
+bool ArrayOutputStream::Next(void** data, int* size) {
+ if (position_ < size_) {
+ last_returned_size_ = std::min(block_size_, size_ - position_);
+ *data = data_ + position_;
+ *size = last_returned_size_;
+ position_ += last_returned_size_;
+ return true;
+ } else {
+ // We're at the end of the array.
+ last_returned_size_ = 0; // Don't let caller back up.
+ return false;
+ }
+}
+
+void ArrayOutputStream::BackUp(int count) {
+ GOOGLE_CHECK_GT(last_returned_size_, 0)
+ << "BackUp() can only be called after a successful Next().";
+ GOOGLE_CHECK_LE(count, last_returned_size_);
+ GOOGLE_CHECK_GE(count, 0);
+ position_ -= count;
+ last_returned_size_ = 0; // Don't let caller back up further.
+}
+
+int64 ArrayOutputStream::ByteCount() const {
+ return position_;
+}
+
+// ===================================================================
+
+StringOutputStream::StringOutputStream(string* target)
+ : target_(target) {
+}
+
+StringOutputStream::~StringOutputStream() {
+}
+
+bool StringOutputStream::Next(void** data, int* size) {
+ GOOGLE_CHECK(target_ != NULL);
+ int old_size = target_->size();
+
+ // Grow the string.
+ if (old_size < target_->capacity()) {
+ // Resize the string to match its capacity, since we can get away
+ // without a memory allocation this way.
+ STLStringResizeUninitialized(target_, target_->capacity());
+ } else {
+ // Size has reached capacity, try to double the size.
+ if (old_size > std::numeric_limits<int>::max() / 2) {
+ // Can not double the size otherwise it is going to cause integer
+ // overflow in the expression below: old_size * 2 ";
+ GOOGLE_LOG(ERROR) << "Cannot allocate buffer larger than kint32max for "
+ << "StringOutputStream.";
+ return false;
+ }
+ // Double the size, also make sure that the new size is at least
+ // kMinimumSize.
+ STLStringResizeUninitialized(
+ target_,
+ std::max(old_size * 2,
+ kMinimumSize + 0)); // "+ 0" works around GCC4 weirdness.
+ }
+
+ *data = mutable_string_data(target_) + old_size;
+ *size = target_->size() - old_size;
+ return true;
+}
+
+void StringOutputStream::BackUp(int count) {
+ GOOGLE_CHECK_GE(count, 0);
+ GOOGLE_CHECK(target_ != NULL);
+ GOOGLE_CHECK_LE(count, target_->size());
+ target_->resize(target_->size() - count);
+}
+
+int64 StringOutputStream::ByteCount() const {
+ GOOGLE_CHECK(target_ != NULL);
+ return target_->size();
+}
+
+void StringOutputStream::SetString(string* target) {
+ target_ = target;
+}
+
+// ===================================================================
+
+LazyStringOutputStream::LazyStringOutputStream(
+ ResultCallback<string*>* callback)
+ : StringOutputStream(NULL),
+ callback_(GOOGLE_CHECK_NOTNULL(callback)),
+ string_is_set_(false) {
+}
+
+LazyStringOutputStream::~LazyStringOutputStream() {
+}
+
+bool LazyStringOutputStream::Next(void** data, int* size) {
+ if (!string_is_set_) {
+ SetString(callback_->Run());
+ string_is_set_ = true;
+ }
+ return StringOutputStream::Next(data, size);
+}
+
+int64 LazyStringOutputStream::ByteCount() const {
+ return string_is_set_ ? StringOutputStream::ByteCount() : 0;
+}
+
+// ===================================================================
+
+CopyingInputStream::~CopyingInputStream() {}
+
+int CopyingInputStream::Skip(int count) {
+ char junk[4096];
+ int skipped = 0;
+ while (skipped < count) {
+ int bytes =
+ Read(junk, std::min(count - skipped, implicit_cast<int>(sizeof(junk))));
+ if (bytes <= 0) {
+ // EOF or read error.
+ return skipped;
+ }
+ skipped += bytes;
+ }
+ return skipped;
+}
+
+CopyingInputStreamAdaptor::CopyingInputStreamAdaptor(
+ CopyingInputStream* copying_stream, int block_size)
+ : copying_stream_(copying_stream),
+ owns_copying_stream_(false),
+ failed_(false),
+ position_(0),
+ buffer_size_(block_size > 0 ? block_size : kDefaultBlockSize),
+ buffer_used_(0),
+ backup_bytes_(0) {
+}
+
+CopyingInputStreamAdaptor::~CopyingInputStreamAdaptor() {
+ if (owns_copying_stream_) {
+ delete copying_stream_;
+ }
+}
+
+bool CopyingInputStreamAdaptor::Next(const void** data, int* size) {
+ if (failed_) {
+ // Already failed on a previous read.
+ return false;
+ }
+
+ AllocateBufferIfNeeded();
+
+ if (backup_bytes_ > 0) {
+ // We have data left over from a previous BackUp(), so just return that.
+ *data = buffer_.get() + buffer_used_ - backup_bytes_;
+ *size = backup_bytes_;
+ backup_bytes_ = 0;
+ return true;
+ }
+
+ // Read new data into the buffer.
+ buffer_used_ = copying_stream_->Read(buffer_.get(), buffer_size_);
+ if (buffer_used_ <= 0) {
+ // EOF or read error. We don't need the buffer anymore.
+ if (buffer_used_ < 0) {
+ // Read error (not EOF).
+ failed_ = true;
+ }
+ FreeBuffer();
+ return false;
+ }
+ position_ += buffer_used_;
+
+ *size = buffer_used_;
+ *data = buffer_.get();
+ return true;
+}
+
+void CopyingInputStreamAdaptor::BackUp(int count) {
+ GOOGLE_CHECK(backup_bytes_ == 0 && buffer_.get() != NULL)
+ << " BackUp() can only be called after Next().";
+ GOOGLE_CHECK_LE(count, buffer_used_)
+ << " Can't back up over more bytes than were returned by the last call"
+ " to Next().";
+ GOOGLE_CHECK_GE(count, 0)
+ << " Parameter to BackUp() can't be negative.";
+
+ backup_bytes_ = count;
+}
+
+bool CopyingInputStreamAdaptor::Skip(int count) {
+ GOOGLE_CHECK_GE(count, 0);
+
+ if (failed_) {
+ // Already failed on a previous read.
+ return false;
+ }
+
+ // First skip any bytes left over from a previous BackUp().
+ if (backup_bytes_ >= count) {
+ // We have more data left over than we're trying to skip. Just chop it.
+ backup_bytes_ -= count;
+ return true;
+ }
+
+ count -= backup_bytes_;
+ backup_bytes_ = 0;
+
+ int skipped = copying_stream_->Skip(count);
+ position_ += skipped;
+ return skipped == count;
+}
+
+int64 CopyingInputStreamAdaptor::ByteCount() const {
+ return position_ - backup_bytes_;
+}
+
+void CopyingInputStreamAdaptor::AllocateBufferIfNeeded() {
+ if (buffer_.get() == NULL) {
+ buffer_.reset(new uint8[buffer_size_]);
+ }
+}
+
+void CopyingInputStreamAdaptor::FreeBuffer() {
+ GOOGLE_CHECK_EQ(backup_bytes_, 0);
+ buffer_used_ = 0;
+ buffer_.reset();
+}
+
+// ===================================================================
+
+CopyingOutputStream::~CopyingOutputStream() {}
+
+CopyingOutputStreamAdaptor::CopyingOutputStreamAdaptor(
+ CopyingOutputStream* copying_stream, int block_size)
+ : copying_stream_(copying_stream),
+ owns_copying_stream_(false),
+ failed_(false),
+ position_(0),
+ buffer_size_(block_size > 0 ? block_size : kDefaultBlockSize),
+ buffer_used_(0) {
+}
+
+CopyingOutputStreamAdaptor::~CopyingOutputStreamAdaptor() {
+ WriteBuffer();
+ if (owns_copying_stream_) {
+ delete copying_stream_;
+ }
+}
+
+bool CopyingOutputStreamAdaptor::Flush() {
+ return WriteBuffer();
+}
+
+bool CopyingOutputStreamAdaptor::Next(void** data, int* size) {
+ if (buffer_used_ == buffer_size_) {
+ if (!WriteBuffer()) return false;
+ }
+
+ AllocateBufferIfNeeded();
+
+ *data = buffer_.get() + buffer_used_;
+ *size = buffer_size_ - buffer_used_;
+ buffer_used_ = buffer_size_;
+ return true;
+}
+
+void CopyingOutputStreamAdaptor::BackUp(int count) {
+ GOOGLE_CHECK_GE(count, 0);
+ GOOGLE_CHECK_EQ(buffer_used_, buffer_size_)
+ << " BackUp() can only be called after Next().";
+ GOOGLE_CHECK_LE(count, buffer_used_)
+ << " Can't back up over more bytes than were returned by the last call"
+ " to Next().";
+
+ buffer_used_ -= count;
+}
+
+int64 CopyingOutputStreamAdaptor::ByteCount() const {
+ return position_ + buffer_used_;
+}
+
+bool CopyingOutputStreamAdaptor::WriteBuffer() {
+ if (failed_) {
+ // Already failed on a previous write.
+ return false;
+ }
+
+ if (buffer_used_ == 0) return true;
+
+ if (copying_stream_->Write(buffer_.get(), buffer_used_)) {
+ position_ += buffer_used_;
+ buffer_used_ = 0;
+ return true;
+ } else {
+ failed_ = true;
+ FreeBuffer();
+ return false;
+ }
+}
+
+void CopyingOutputStreamAdaptor::AllocateBufferIfNeeded() {
+ if (buffer_ == NULL) {
+ buffer_.reset(new uint8[buffer_size_]);
+ }
+}
+
+void CopyingOutputStreamAdaptor::FreeBuffer() {
+ buffer_used_ = 0;
+ buffer_.reset();
+}
+
+// ===================================================================
+
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.h
new file mode 100644
index 0000000000..e4d6a024dd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_impl_lite.h
@@ -0,0 +1,410 @@
+// 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 common implementations of the interfaces defined in
+// zero_copy_stream.h which are included in the "lite" protobuf library.
+// These implementations cover I/O on raw arrays and strings, as well as
+// adaptors which make it easy to implement streams based on traditional
+// streams. Of course, many users will probably want to write their own
+// implementations of these interfaces specific to the particular I/O
+// abstractions they prefer to use, but these should cover the most common
+// cases.
+
+#ifndef GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_IMPL_LITE_H__
+#define GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_IMPL_LITE_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <iosfwd>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+
+namespace google {
+namespace protobuf {
+namespace io {
+
+// ===================================================================
+
+// A ZeroCopyInputStream backed by an in-memory array of bytes.
+class LIBPROTOBUF_EXPORT ArrayInputStream : public ZeroCopyInputStream {
+ public:
+ // Create an InputStream that returns the bytes pointed to by "data".
+ // "data" remains the property of the caller but must remain valid until
+ // the stream is destroyed. If a block_size is given, calls to Next()
+ // will return data blocks no larger than the given size. Otherwise, the
+ // first call to Next() returns the entire array. block_size is mainly
+ // useful for testing; in production you would probably never want to set
+ // it.
+ ArrayInputStream(const void* data, int size, int block_size = -1);
+ ~ArrayInputStream();
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size);
+ void BackUp(int count);
+ bool Skip(int count);
+ int64 ByteCount() const;
+
+
+ private:
+ const uint8* const data_; // The byte array.
+ const int size_; // Total size of the array.
+ const int block_size_; // How many bytes to return at a time.
+
+ int position_;
+ int last_returned_size_; // How many bytes we returned last time Next()
+ // was called (used for error checking only).
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ArrayInputStream);
+};
+
+// ===================================================================
+
+// A ZeroCopyOutputStream backed by an in-memory array of bytes.
+class LIBPROTOBUF_EXPORT ArrayOutputStream : public ZeroCopyOutputStream {
+ public:
+ // Create an OutputStream that writes to the bytes pointed to by "data".
+ // "data" remains the property of the caller but must remain valid until
+ // the stream is destroyed. If a block_size is given, calls to Next()
+ // will return data blocks no larger than the given size. Otherwise, the
+ // first call to Next() returns the entire array. block_size is mainly
+ // useful for testing; in production you would probably never want to set
+ // it.
+ ArrayOutputStream(void* data, int size, int block_size = -1);
+ ~ArrayOutputStream();
+
+ // implements ZeroCopyOutputStream ---------------------------------
+ bool Next(void** data, int* size);
+ void BackUp(int count);
+ int64 ByteCount() const;
+
+ private:
+ uint8* const data_; // The byte array.
+ const int size_; // Total size of the array.
+ const int block_size_; // How many bytes to return at a time.
+
+ int position_;
+ int last_returned_size_; // How many bytes we returned last time Next()
+ // was called (used for error checking only).
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ArrayOutputStream);
+};
+
+// ===================================================================
+
+// A ZeroCopyOutputStream which appends bytes to a string.
+class LIBPROTOBUF_EXPORT StringOutputStream : public ZeroCopyOutputStream {
+ public:
+ // Create a StringOutputStream which appends bytes to the given string.
+ // The string remains property of the caller, but it is mutated in arbitrary
+ // ways and MUST NOT be accessed in any way until you're done with the
+ // stream. Either be sure there's no further usage, or (safest) destroy the
+ // stream before using the contents.
+ //
+ // Hint: If you call target->reserve(n) before creating the stream,
+ // the first call to Next() will return at least n bytes of buffer
+ // space.
+ explicit StringOutputStream(string* target);
+ ~StringOutputStream();
+
+ // implements ZeroCopyOutputStream ---------------------------------
+ bool Next(void** data, int* size);
+ void BackUp(int count);
+ int64 ByteCount() const;
+
+ protected:
+ void SetString(string* target);
+
+ private:
+ static const int kMinimumSize = 16;
+
+ string* target_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StringOutputStream);
+};
+
+// LazyStringOutputStream is a StringOutputStream with lazy acquisition of
+// the output string from a callback. The string is owned externally, and not
+// deleted in the stream destructor.
+class LIBPROTOBUF_EXPORT LazyStringOutputStream : public StringOutputStream {
+ public:
+ // Callback should be permanent (non-self-deleting). Ownership is transferred
+ // to the LazyStringOutputStream.
+ explicit LazyStringOutputStream(ResultCallback<string*>* callback);
+ ~LazyStringOutputStream();
+
+ // implements ZeroCopyOutputStream, overriding StringOutputStream -----------
+ bool Next(void** data, int* size);
+ int64 ByteCount() const;
+
+ private:
+ const google::protobuf::scoped_ptr<ResultCallback<string*> > callback_;
+ bool string_is_set_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(LazyStringOutputStream);
+};
+
+// Note: There is no StringInputStream. Instead, just create an
+// ArrayInputStream as follows:
+// ArrayInputStream input(str.data(), str.size());
+
+// ===================================================================
+
+// A generic traditional input stream interface.
+//
+// Lots of traditional input streams (e.g. file descriptors, C stdio
+// streams, and C++ iostreams) expose an interface where every read
+// involves copying bytes into a buffer. If you want to take such an
+// interface and make a ZeroCopyInputStream based on it, simply implement
+// CopyingInputStream and then use CopyingInputStreamAdaptor.
+//
+// CopyingInputStream implementations should avoid buffering if possible.
+// CopyingInputStreamAdaptor does its own buffering and will read data
+// in large blocks.
+class LIBPROTOBUF_EXPORT CopyingInputStream {
+ public:
+ virtual ~CopyingInputStream();
+
+ // Reads up to "size" bytes into the given buffer. Returns the number of
+ // bytes read. Read() waits until at least one byte is available, or
+ // returns zero if no bytes will ever become available (EOF), or -1 if a
+ // permanent read error occurred.
+ virtual int Read(void* buffer, int size) = 0;
+
+ // Skips the next "count" bytes of input. Returns the number of bytes
+ // actually skipped. This will always be exactly equal to "count" unless
+ // EOF was reached or a permanent read error occurred.
+ //
+ // The default implementation just repeatedly calls Read() into a scratch
+ // buffer.
+ virtual int Skip(int count);
+};
+
+// A ZeroCopyInputStream which reads from a CopyingInputStream. This is
+// useful for implementing ZeroCopyInputStreams that read from traditional
+// streams. Note that this class is not really zero-copy.
+//
+// If you want to read from file descriptors or C++ istreams, this is
+// already implemented for you: use FileInputStream or IstreamInputStream
+// respectively.
+class LIBPROTOBUF_EXPORT CopyingInputStreamAdaptor : public ZeroCopyInputStream {
+ public:
+ // Creates a stream that reads from the given CopyingInputStream.
+ // If a block_size is given, it specifies the number of bytes that
+ // should be read and returned with each call to Next(). Otherwise,
+ // a reasonable default is used. The caller retains ownership of
+ // copying_stream unless SetOwnsCopyingStream(true) is called.
+ explicit CopyingInputStreamAdaptor(CopyingInputStream* copying_stream,
+ int block_size = -1);
+ ~CopyingInputStreamAdaptor();
+
+ // Call SetOwnsCopyingStream(true) to tell the CopyingInputStreamAdaptor to
+ // delete the underlying CopyingInputStream when it is destroyed.
+ void SetOwnsCopyingStream(bool value) { owns_copying_stream_ = value; }
+
+ // implements ZeroCopyInputStream ----------------------------------
+ bool Next(const void** data, int* size);
+ void BackUp(int count);
+ bool Skip(int count);
+ int64 ByteCount() const;
+
+ private:
+ // Insures that buffer_ is not NULL.
+ void AllocateBufferIfNeeded();
+ // Frees the buffer and resets buffer_used_.
+ void FreeBuffer();
+
+ // The underlying copying stream.
+ CopyingInputStream* copying_stream_;
+ bool owns_copying_stream_;
+
+ // True if we have seen a permenant error from the underlying stream.
+ bool failed_;
+
+ // The current position of copying_stream_, relative to the point where
+ // we started reading.
+ int64 position_;
+
+ // Data is read into this buffer. It may be NULL if no buffer is currently
+ // in use. Otherwise, it points to an array of size buffer_size_.
+ google::protobuf::scoped_array<uint8> buffer_;
+ const int buffer_size_;
+
+ // Number of valid bytes currently in the buffer (i.e. the size last
+ // returned by Next()). 0 <= buffer_used_ <= buffer_size_.
+ int buffer_used_;
+
+ // Number of bytes in the buffer which were backed up over by a call to
+ // BackUp(). These need to be returned again.
+ // 0 <= backup_bytes_ <= buffer_used_
+ int backup_bytes_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CopyingInputStreamAdaptor);
+};
+
+// ===================================================================
+
+// A generic traditional output stream interface.
+//
+// Lots of traditional output streams (e.g. file descriptors, C stdio
+// streams, and C++ iostreams) expose an interface where every write
+// involves copying bytes from a buffer. If you want to take such an
+// interface and make a ZeroCopyOutputStream based on it, simply implement
+// CopyingOutputStream and then use CopyingOutputStreamAdaptor.
+//
+// CopyingOutputStream implementations should avoid buffering if possible.
+// CopyingOutputStreamAdaptor does its own buffering and will write data
+// in large blocks.
+class LIBPROTOBUF_EXPORT CopyingOutputStream {
+ public:
+ virtual ~CopyingOutputStream();
+
+ // Writes "size" bytes from the given buffer to the output. Returns true
+ // if successful, false on a write error.
+ virtual bool Write(const void* buffer, int size) = 0;
+};
+
+// A ZeroCopyOutputStream which writes to a CopyingOutputStream. This is
+// useful for implementing ZeroCopyOutputStreams that write to traditional
+// streams. Note that this class is not really zero-copy.
+//
+// If you want to write to file descriptors or C++ ostreams, this is
+// already implemented for you: use FileOutputStream or OstreamOutputStream
+// respectively.
+class LIBPROTOBUF_EXPORT CopyingOutputStreamAdaptor : public ZeroCopyOutputStream {
+ public:
+ // Creates a stream that writes to the given Unix file descriptor.
+ // If a block_size is given, it specifies the size of the buffers
+ // that should be returned by Next(). Otherwise, a reasonable default
+ // is used.
+ explicit CopyingOutputStreamAdaptor(CopyingOutputStream* copying_stream,
+ int block_size = -1);
+ ~CopyingOutputStreamAdaptor();
+
+ // Writes all pending data to the underlying stream. Returns false if a
+ // write error occurred on the underlying stream. (The underlying
+ // stream itself is not necessarily flushed.)
+ bool Flush();
+
+ // Call SetOwnsCopyingStream(true) to tell the CopyingOutputStreamAdaptor to
+ // delete the underlying CopyingOutputStream when it is destroyed.
+ void SetOwnsCopyingStream(bool value) { owns_copying_stream_ = value; }
+
+ // implements ZeroCopyOutputStream ---------------------------------
+ bool Next(void** data, int* size);
+ void BackUp(int count);
+ int64 ByteCount() const;
+
+ private:
+ // Write the current buffer, if it is present.
+ bool WriteBuffer();
+ // Insures that buffer_ is not NULL.
+ void AllocateBufferIfNeeded();
+ // Frees the buffer.
+ void FreeBuffer();
+
+ // The underlying copying stream.
+ CopyingOutputStream* copying_stream_;
+ bool owns_copying_stream_;
+
+ // True if we have seen a permenant error from the underlying stream.
+ bool failed_;
+
+ // The current position of copying_stream_, relative to the point where
+ // we started writing.
+ int64 position_;
+
+ // Data is written from this buffer. It may be NULL if no buffer is
+ // currently in use. Otherwise, it points to an array of size buffer_size_.
+ google::protobuf::scoped_array<uint8> buffer_;
+ const int buffer_size_;
+
+ // Number of valid bytes currently in the buffer (i.e. the size last
+ // returned by Next()). When BackUp() is called, we just reduce this.
+ // 0 <= buffer_used_ <= buffer_size_.
+ int buffer_used_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CopyingOutputStreamAdaptor);
+};
+
+// ===================================================================
+
+// mutable_string_data() and as_string_data() are workarounds to improve
+// the performance of writing new data to an existing string. Unfortunately
+// the methods provided by the string class are suboptimal, and using memcpy()
+// is mildly annoying because it requires its pointer args to be non-NULL even
+// if we ask it to copy 0 bytes. Furthermore, string_as_array() has the
+// property that it always returns NULL if its arg is the empty string, exactly
+// what we want to avoid if we're using it in conjunction with memcpy()!
+// With C++11, the desired memcpy() boils down to memcpy(..., &(*s)[0], size),
+// where s is a string*. Without C++11, &(*s)[0] is not guaranteed to be safe,
+// so we use string_as_array(), and live with the extra logic that tests whether
+// *s is empty.
+
+// Return a pointer to mutable characters underlying the given string. The
+// return value is valid until the next time the string is resized. We
+// trust the caller to treat the return value as an array of length s->size().
+inline char* mutable_string_data(string* s) {
+#ifdef LANG_CXX11
+ // This should be simpler & faster than string_as_array() because the latter
+ // is guaranteed to return NULL when *s is empty, so it has to check for that.
+ return &(*s)[0];
+#else
+ return string_as_array(s);
+#endif
+}
+
+// as_string_data(s) is equivalent to
+// ({ char* p = mutable_string_data(s); make_pair(p, p != NULL); })
+// Sometimes it's faster: in some scenarios p cannot be NULL, and then the
+// code can avoid that check.
+inline std::pair<char*, bool> as_string_data(string* s) {
+ char *p = mutable_string_data(s);
+#ifdef LANG_CXX11
+ return std::make_pair(p, true);
+#else
+ return make_pair(p, p != NULL);
+#endif
+}
+
+} // namespace io
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_IO_ZERO_COPY_STREAM_IMPL_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_unittest.cc
new file mode 100644
index 0000000000..a9db8872d4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/io/zero_copy_stream_unittest.cc
@@ -0,0 +1,1007 @@
+// 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.
+//
+// Testing strategy: For each type of I/O (array, string, file, etc.) we
+// create an output stream and write some data to it, then create a
+// corresponding input stream to read the same data back and expect it to
+// match. When the data is written, it is written in several small chunks
+// of varying sizes, with a BackUp() after each chunk. It is read back
+// similarly, but with chunks separated at different points. The whole
+// process is run with a variety of block sizes for both the input and
+// the output.
+//
+// TODO(kenton): Rewrite this test to bring it up to the standards of all
+// the other proto2 tests. May want to wait for gTest to implement
+// "parametized tests" so that one set of tests can be used on all the
+// implementations.
+
+
+#ifdef _MSC_VER
+#include <io.h>
+#else
+#include <unistd.h>
+#endif
+#include <stdlib.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <errno.h>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <sstream>
+
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+
+#if HAVE_ZLIB
+#include <google/protobuf/io/gzip_stream.h>
+#endif
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/testing/googletest.h>
+#include <google/protobuf/testing/file.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+namespace {
+
+#ifdef _WIN32
+#define pipe(fds) _pipe(fds, 4096, O_BINARY)
+#endif
+
+#ifndef O_BINARY
+#ifdef _O_BINARY
+#define O_BINARY _O_BINARY
+#else
+#define O_BINARY 0 // If this isn't defined, the platform doesn't need it.
+#endif
+#endif
+
+class IoTest : public testing::Test {
+ protected:
+ // Test helpers.
+
+ // Helper to write an array of data to an output stream.
+ bool WriteToOutput(ZeroCopyOutputStream* output, const void* data, int size);
+ // Helper to read a fixed-length array of data from an input stream.
+ int ReadFromInput(ZeroCopyInputStream* input, void* data, int size);
+ // Write a string to the output stream.
+ void WriteString(ZeroCopyOutputStream* output, const string& str);
+ // Read a number of bytes equal to the size of the given string and checks
+ // that it matches the string.
+ void ReadString(ZeroCopyInputStream* input, const string& str);
+ // Writes some text to the output stream in a particular order. Returns
+ // the number of bytes written, incase the caller needs that to set up an
+ // input stream.
+ int WriteStuff(ZeroCopyOutputStream* output);
+ // Reads text from an input stream and expects it to match what
+ // WriteStuff() writes.
+ void ReadStuff(ZeroCopyInputStream* input);
+
+ // Similar to WriteStuff, but performs more sophisticated testing.
+ int WriteStuffLarge(ZeroCopyOutputStream* output);
+ // Reads and tests a stream that should have been written to
+ // via WriteStuffLarge().
+ void ReadStuffLarge(ZeroCopyInputStream* input);
+
+#if HAVE_ZLIB
+ string Compress(const string& data, const GzipOutputStream::Options& options);
+ string Uncompress(const string& data);
+#endif
+
+ static const int kBlockSizes[];
+ static const int kBlockSizeCount;
+};
+
+const int IoTest::kBlockSizes[] = {-1, 1, 2, 5, 7, 10, 23, 64};
+const int IoTest::kBlockSizeCount = GOOGLE_ARRAYSIZE(IoTest::kBlockSizes);
+
+bool IoTest::WriteToOutput(ZeroCopyOutputStream* output,
+ const void* data, int size) {
+ const uint8* in = reinterpret_cast<const uint8*>(data);
+ int in_size = size;
+
+ void* out;
+ int out_size;
+
+ while (true) {
+ if (!output->Next(&out, &out_size)) {
+ return false;
+ }
+ EXPECT_GT(out_size, 0);
+
+ if (in_size <= out_size) {
+ memcpy(out, in, in_size);
+ output->BackUp(out_size - in_size);
+ return true;
+ }
+
+ memcpy(out, in, out_size);
+ in += out_size;
+ in_size -= out_size;
+ }
+}
+
+#define MAX_REPEATED_ZEROS 100
+
+int IoTest::ReadFromInput(ZeroCopyInputStream* input, void* data, int size) {
+ uint8* out = reinterpret_cast<uint8*>(data);
+ int out_size = size;
+
+ const void* in;
+ int in_size = 0;
+
+ int repeated_zeros = 0;
+
+ while (true) {
+ if (!input->Next(&in, &in_size)) {
+ return size - out_size;
+ }
+ EXPECT_GT(in_size, -1);
+ if (in_size == 0) {
+ repeated_zeros++;
+ } else {
+ repeated_zeros = 0;
+ }
+ EXPECT_LT(repeated_zeros, MAX_REPEATED_ZEROS);
+
+ if (out_size <= in_size) {
+ memcpy(out, in, out_size);
+ if (in_size > out_size) {
+ input->BackUp(in_size - out_size);
+ }
+ return size; // Copied all of it.
+ }
+
+ memcpy(out, in, in_size);
+ out += in_size;
+ out_size -= in_size;
+ }
+}
+
+void IoTest::WriteString(ZeroCopyOutputStream* output, const string& str) {
+ EXPECT_TRUE(WriteToOutput(output, str.c_str(), str.size()));
+}
+
+void IoTest::ReadString(ZeroCopyInputStream* input, const string& str) {
+ google::protobuf::scoped_array<char> buffer(new char[str.size() + 1]);
+ buffer[str.size()] = '\0';
+ EXPECT_EQ(ReadFromInput(input, buffer.get(), str.size()), str.size());
+ EXPECT_STREQ(str.c_str(), buffer.get());
+}
+
+int IoTest::WriteStuff(ZeroCopyOutputStream* output) {
+ WriteString(output, "Hello world!\n");
+ WriteString(output, "Some te");
+ WriteString(output, "xt. Blah blah.");
+ WriteString(output, "abcdefg");
+ WriteString(output, "01234567890123456789");
+ WriteString(output, "foobar");
+
+ EXPECT_EQ(output->ByteCount(), 68);
+
+ int result = output->ByteCount();
+ return result;
+}
+
+// Reads text from an input stream and expects it to match what WriteStuff()
+// writes.
+void IoTest::ReadStuff(ZeroCopyInputStream* input) {
+ ReadString(input, "Hello world!\n");
+ ReadString(input, "Some text. ");
+ ReadString(input, "Blah ");
+ ReadString(input, "blah.");
+ ReadString(input, "abcdefg");
+ EXPECT_TRUE(input->Skip(20));
+ ReadString(input, "foo");
+ ReadString(input, "bar");
+
+ EXPECT_EQ(input->ByteCount(), 68);
+
+ uint8 byte;
+ EXPECT_EQ(ReadFromInput(input, &byte, 1), 0);
+}
+
+int IoTest::WriteStuffLarge(ZeroCopyOutputStream* output) {
+ WriteString(output, "Hello world!\n");
+ WriteString(output, "Some te");
+ WriteString(output, "xt. Blah blah.");
+ WriteString(output, string(100000, 'x')); // A very long string
+ WriteString(output, string(100000, 'y')); // A very long string
+ WriteString(output, "01234567890123456789");
+
+ EXPECT_EQ(output->ByteCount(), 200055);
+
+ int result = output->ByteCount();
+ return result;
+}
+
+// Reads text from an input stream and expects it to match what WriteStuff()
+// writes.
+void IoTest::ReadStuffLarge(ZeroCopyInputStream* input) {
+ ReadString(input, "Hello world!\nSome text. ");
+ EXPECT_TRUE(input->Skip(5));
+ ReadString(input, "blah.");
+ EXPECT_TRUE(input->Skip(100000 - 10));
+ ReadString(input, string(10, 'x') + string(100000 - 20000, 'y'));
+ EXPECT_TRUE(input->Skip(20000 - 10));
+ ReadString(input, "yyyyyyyyyy01234567890123456789");
+
+ EXPECT_EQ(input->ByteCount(), 200055);
+
+ uint8 byte;
+ EXPECT_EQ(ReadFromInput(input, &byte, 1), 0);
+}
+
+// ===================================================================
+
+TEST_F(IoTest, ArrayIo) {
+ const int kBufferSize = 256;
+ uint8 buffer[kBufferSize];
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ int size;
+ {
+ ArrayOutputStream output(buffer, kBufferSize, kBlockSizes[i]);
+ size = WriteStuff(&output);
+ }
+ {
+ ArrayInputStream input(buffer, size, kBlockSizes[j]);
+ ReadStuff(&input);
+ }
+ }
+ }
+}
+
+TEST_F(IoTest, TwoSessionWrite) {
+ // Test that two concatenated write sessions read correctly
+
+ static const char* strA = "0123456789";
+ static const char* strB = "WhirledPeas";
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+ char* temp_buffer = new char[40];
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ ArrayOutputStream* output =
+ new ArrayOutputStream(buffer, kBufferSize, kBlockSizes[i]);
+ CodedOutputStream* coded_output = new CodedOutputStream(output);
+ coded_output->WriteVarint32(strlen(strA));
+ coded_output->WriteRaw(strA, strlen(strA));
+ delete coded_output; // flush
+ int64 pos = output->ByteCount();
+ delete output;
+ output = new ArrayOutputStream(
+ buffer + pos, kBufferSize - pos, kBlockSizes[i]);
+ coded_output = new CodedOutputStream(output);
+ coded_output->WriteVarint32(strlen(strB));
+ coded_output->WriteRaw(strB, strlen(strB));
+ delete coded_output; // flush
+ int64 size = pos + output->ByteCount();
+ delete output;
+
+ ArrayInputStream* input =
+ new ArrayInputStream(buffer, size, kBlockSizes[j]);
+ CodedInputStream* coded_input = new CodedInputStream(input);
+ uint32 insize;
+ EXPECT_TRUE(coded_input->ReadVarint32(&insize));
+ EXPECT_EQ(strlen(strA), insize);
+ EXPECT_TRUE(coded_input->ReadRaw(temp_buffer, insize));
+ EXPECT_EQ(0, memcmp(temp_buffer, strA, insize));
+
+ EXPECT_TRUE(coded_input->ReadVarint32(&insize));
+ EXPECT_EQ(strlen(strB), insize);
+ EXPECT_TRUE(coded_input->ReadRaw(temp_buffer, insize));
+ EXPECT_EQ(0, memcmp(temp_buffer, strB, insize));
+
+ delete coded_input;
+ delete input;
+ }
+ }
+
+ delete [] temp_buffer;
+ delete [] buffer;
+}
+
+#if HAVE_ZLIB
+TEST_F(IoTest, GzipIo) {
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ for (int z = 0; z < kBlockSizeCount; z++) {
+ int gzip_buffer_size = kBlockSizes[z];
+ int size;
+ {
+ ArrayOutputStream output(buffer, kBufferSize, kBlockSizes[i]);
+ GzipOutputStream::Options options;
+ options.format = GzipOutputStream::GZIP;
+ if (gzip_buffer_size != -1) {
+ options.buffer_size = gzip_buffer_size;
+ }
+ GzipOutputStream gzout(&output, options);
+ WriteStuff(&gzout);
+ gzout.Close();
+ size = output.ByteCount();
+ }
+ {
+ ArrayInputStream input(buffer, size, kBlockSizes[j]);
+ GzipInputStream gzin(
+ &input, GzipInputStream::GZIP, gzip_buffer_size);
+ ReadStuff(&gzin);
+ }
+ }
+ }
+ }
+ delete [] buffer;
+}
+
+TEST_F(IoTest, GzipIoWithFlush) {
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+ // We start with i = 4 as we want a block size > 6. With block size <= 6
+ // Flush() fills up the entire 2K buffer with flush markers and the test
+ // fails. See documentation for Flush() for more detail.
+ for (int i = 4; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ for (int z = 0; z < kBlockSizeCount; z++) {
+ int gzip_buffer_size = kBlockSizes[z];
+ int size;
+ {
+ ArrayOutputStream output(buffer, kBufferSize, kBlockSizes[i]);
+ GzipOutputStream::Options options;
+ options.format = GzipOutputStream::GZIP;
+ if (gzip_buffer_size != -1) {
+ options.buffer_size = gzip_buffer_size;
+ }
+ GzipOutputStream gzout(&output, options);
+ WriteStuff(&gzout);
+ EXPECT_TRUE(gzout.Flush());
+ gzout.Close();
+ size = output.ByteCount();
+ }
+ {
+ ArrayInputStream input(buffer, size, kBlockSizes[j]);
+ GzipInputStream gzin(
+ &input, GzipInputStream::GZIP, gzip_buffer_size);
+ ReadStuff(&gzin);
+ }
+ }
+ }
+ }
+ delete [] buffer;
+}
+
+TEST_F(IoTest, GzipIoContiguousFlushes) {
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+
+ int block_size = kBlockSizes[4];
+ int gzip_buffer_size = block_size;
+ int size;
+
+ ArrayOutputStream output(buffer, kBufferSize, block_size);
+ GzipOutputStream::Options options;
+ options.format = GzipOutputStream::GZIP;
+ if (gzip_buffer_size != -1) {
+ options.buffer_size = gzip_buffer_size;
+ }
+ GzipOutputStream gzout(&output, options);
+ WriteStuff(&gzout);
+ EXPECT_TRUE(gzout.Flush());
+ EXPECT_TRUE(gzout.Flush());
+ gzout.Close();
+ size = output.ByteCount();
+
+ ArrayInputStream input(buffer, size, block_size);
+ GzipInputStream gzin(
+ &input, GzipInputStream::GZIP, gzip_buffer_size);
+ ReadStuff(&gzin);
+
+ delete [] buffer;
+}
+
+TEST_F(IoTest, GzipIoReadAfterFlush) {
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+
+ int block_size = kBlockSizes[4];
+ int gzip_buffer_size = block_size;
+ int size;
+ ArrayOutputStream output(buffer, kBufferSize, block_size);
+ GzipOutputStream::Options options;
+ options.format = GzipOutputStream::GZIP;
+ if (gzip_buffer_size != -1) {
+ options.buffer_size = gzip_buffer_size;
+ }
+
+ GzipOutputStream gzout(&output, options);
+ WriteStuff(&gzout);
+ EXPECT_TRUE(gzout.Flush());
+ size = output.ByteCount();
+
+ ArrayInputStream input(buffer, size, block_size);
+ GzipInputStream gzin(
+ &input, GzipInputStream::GZIP, gzip_buffer_size);
+ ReadStuff(&gzin);
+
+ gzout.Close();
+
+ delete [] buffer;
+}
+
+TEST_F(IoTest, ZlibIo) {
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ for (int z = 0; z < kBlockSizeCount; z++) {
+ int gzip_buffer_size = kBlockSizes[z];
+ int size;
+ {
+ ArrayOutputStream output(buffer, kBufferSize, kBlockSizes[i]);
+ GzipOutputStream::Options options;
+ options.format = GzipOutputStream::ZLIB;
+ if (gzip_buffer_size != -1) {
+ options.buffer_size = gzip_buffer_size;
+ }
+ GzipOutputStream gzout(&output, options);
+ WriteStuff(&gzout);
+ gzout.Close();
+ size = output.ByteCount();
+ }
+ {
+ ArrayInputStream input(buffer, size, kBlockSizes[j]);
+ GzipInputStream gzin(
+ &input, GzipInputStream::ZLIB, gzip_buffer_size);
+ ReadStuff(&gzin);
+ }
+ }
+ }
+ }
+ delete [] buffer;
+}
+
+TEST_F(IoTest, ZlibIoInputAutodetect) {
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+ int size;
+ {
+ ArrayOutputStream output(buffer, kBufferSize);
+ GzipOutputStream::Options options;
+ options.format = GzipOutputStream::ZLIB;
+ GzipOutputStream gzout(&output, options);
+ WriteStuff(&gzout);
+ gzout.Close();
+ size = output.ByteCount();
+ }
+ {
+ ArrayInputStream input(buffer, size);
+ GzipInputStream gzin(&input, GzipInputStream::AUTO);
+ ReadStuff(&gzin);
+ }
+ {
+ ArrayOutputStream output(buffer, kBufferSize);
+ GzipOutputStream::Options options;
+ options.format = GzipOutputStream::GZIP;
+ GzipOutputStream gzout(&output, options);
+ WriteStuff(&gzout);
+ gzout.Close();
+ size = output.ByteCount();
+ }
+ {
+ ArrayInputStream input(buffer, size);
+ GzipInputStream gzin(&input, GzipInputStream::AUTO);
+ ReadStuff(&gzin);
+ }
+ delete [] buffer;
+}
+
+string IoTest::Compress(const string& data,
+ const GzipOutputStream::Options& options) {
+ string result;
+ {
+ StringOutputStream output(&result);
+ GzipOutputStream gzout(&output, options);
+ WriteToOutput(&gzout, data.data(), data.size());
+ }
+ return result;
+}
+
+string IoTest::Uncompress(const string& data) {
+ string result;
+ {
+ ArrayInputStream input(data.data(), data.size());
+ GzipInputStream gzin(&input);
+ const void* buffer;
+ int size;
+ while (gzin.Next(&buffer, &size)) {
+ result.append(reinterpret_cast<const char*>(buffer), size);
+ }
+ }
+ return result;
+}
+
+TEST_F(IoTest, CompressionOptions) {
+ // Some ad-hoc testing of compression options.
+
+ string golden;
+ GOOGLE_CHECK_OK(File::GetContents(
+ TestSourceDir() +
+ "/google/protobuf/testdata/golden_message",
+ &golden, true));
+
+ GzipOutputStream::Options options;
+ string gzip_compressed = Compress(golden, options);
+
+ options.compression_level = 0;
+ string not_compressed = Compress(golden, options);
+
+ // Try zlib compression for fun.
+ options = GzipOutputStream::Options();
+ options.format = GzipOutputStream::ZLIB;
+ string zlib_compressed = Compress(golden, options);
+
+ // Uncompressed should be bigger than the original since it should have some
+ // sort of header.
+ EXPECT_GT(not_compressed.size(), golden.size());
+
+ // Higher compression levels should result in smaller sizes.
+ EXPECT_LT(zlib_compressed.size(), not_compressed.size());
+
+ // ZLIB format should differ from GZIP format.
+ EXPECT_TRUE(zlib_compressed != gzip_compressed);
+
+ // Everything should decompress correctly.
+ EXPECT_TRUE(Uncompress(not_compressed) == golden);
+ EXPECT_TRUE(Uncompress(gzip_compressed) == golden);
+ EXPECT_TRUE(Uncompress(zlib_compressed) == golden);
+}
+
+TEST_F(IoTest, TwoSessionWriteGzip) {
+ // Test that two concatenated gzip streams can be read correctly
+
+ static const char* strA = "0123456789";
+ static const char* strB = "QuickBrownFox";
+ const int kBufferSize = 2*1024;
+ uint8* buffer = new uint8[kBufferSize];
+ char* temp_buffer = new char[40];
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ ArrayOutputStream* output =
+ new ArrayOutputStream(buffer, kBufferSize, kBlockSizes[i]);
+ GzipOutputStream* gzout = new GzipOutputStream(output);
+ CodedOutputStream* coded_output = new CodedOutputStream(gzout);
+ int32 outlen = strlen(strA) + 1;
+ coded_output->WriteVarint32(outlen);
+ coded_output->WriteRaw(strA, outlen);
+ delete coded_output; // flush
+ delete gzout; // flush
+ int64 pos = output->ByteCount();
+ delete output;
+ output = new ArrayOutputStream(
+ buffer + pos, kBufferSize - pos, kBlockSizes[i]);
+ gzout = new GzipOutputStream(output);
+ coded_output = new CodedOutputStream(gzout);
+ outlen = strlen(strB) + 1;
+ coded_output->WriteVarint32(outlen);
+ coded_output->WriteRaw(strB, outlen);
+ delete coded_output; // flush
+ delete gzout; // flush
+ int64 size = pos + output->ByteCount();
+ delete output;
+
+ ArrayInputStream* input =
+ new ArrayInputStream(buffer, size, kBlockSizes[j]);
+ GzipInputStream* gzin = new GzipInputStream(input);
+ CodedInputStream* coded_input = new CodedInputStream(gzin);
+ uint32 insize;
+ EXPECT_TRUE(coded_input->ReadVarint32(&insize));
+ EXPECT_EQ(strlen(strA) + 1, insize);
+ EXPECT_TRUE(coded_input->ReadRaw(temp_buffer, insize));
+ EXPECT_EQ(0, memcmp(temp_buffer, strA, insize))
+ << "strA=" << strA << " in=" << temp_buffer;
+
+ EXPECT_TRUE(coded_input->ReadVarint32(&insize));
+ EXPECT_EQ(strlen(strB) + 1, insize);
+ EXPECT_TRUE(coded_input->ReadRaw(temp_buffer, insize));
+ EXPECT_EQ(0, memcmp(temp_buffer, strB, insize))
+ << " out_block_size=" << kBlockSizes[i]
+ << " in_block_size=" << kBlockSizes[j]
+ << " pos=" << pos
+ << " size=" << size
+ << " strB=" << strB << " in=" << temp_buffer;
+
+ delete coded_input;
+ delete gzin;
+ delete input;
+ }
+ }
+
+ delete [] temp_buffer;
+ delete [] buffer;
+}
+
+TEST_F(IoTest, GzipInputByteCountAfterClosed) {
+ string golden = "abcdefghijklmnopqrstuvwxyz";
+ string compressed = Compress(golden, GzipOutputStream::Options());
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ ArrayInputStream arr_input(compressed.data(), compressed.size(),
+ kBlockSizes[i]);
+ GzipInputStream gz_input(&arr_input);
+ const void* buffer;
+ int size;
+ while (gz_input.Next(&buffer, &size)) {
+ EXPECT_LE(gz_input.ByteCount(), golden.size());
+ }
+ EXPECT_EQ(golden.size(), gz_input.ByteCount());
+ }
+}
+
+TEST_F(IoTest, GzipInputByteCountAfterClosedConcatenatedStreams) {
+ string golden1 = "abcdefghijklmnopqrstuvwxyz";
+ string golden2 = "the quick brown fox jumps over the lazy dog";
+ const size_t total_size = golden1.size() + golden2.size();
+ string compressed = Compress(golden1, GzipOutputStream::Options()) +
+ Compress(golden2, GzipOutputStream::Options());
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ ArrayInputStream arr_input(compressed.data(), compressed.size(),
+ kBlockSizes[i]);
+ GzipInputStream gz_input(&arr_input);
+ const void* buffer;
+ int size;
+ while (gz_input.Next(&buffer, &size)) {
+ EXPECT_LE(gz_input.ByteCount(), total_size);
+ }
+ EXPECT_EQ(total_size, gz_input.ByteCount());
+ }
+}
+#endif
+
+// There is no string input, only string output. Also, it doesn't support
+// explicit block sizes. So, we'll only run one test and we'll use
+// ArrayInput to read back the results.
+TEST_F(IoTest, StringIo) {
+ string str;
+ {
+ StringOutputStream output(&str);
+ WriteStuff(&output);
+ }
+ {
+ ArrayInputStream input(str.data(), str.size());
+ ReadStuff(&input);
+ }
+}
+
+
+// To test files, we create a temporary file, write, read, truncate, repeat.
+TEST_F(IoTest, FileIo) {
+ string filename = TestTempDir() + "/zero_copy_stream_test_file";
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ // Make a temporary file.
+ int file =
+ open(filename.c_str(), O_RDWR | O_CREAT | O_TRUNC | O_BINARY, 0777);
+ ASSERT_GE(file, 0);
+
+ {
+ FileOutputStream output(file, kBlockSizes[i]);
+ WriteStuff(&output);
+ EXPECT_EQ(0, output.GetErrno());
+ }
+
+ // Rewind.
+ ASSERT_NE(lseek(file, 0, SEEK_SET), (off_t)-1);
+
+ {
+ FileInputStream input(file, kBlockSizes[j]);
+ ReadStuff(&input);
+ EXPECT_EQ(0, input.GetErrno());
+ }
+
+ close(file);
+ }
+ }
+}
+
+#if HAVE_ZLIB
+TEST_F(IoTest, GzipFileIo) {
+ string filename = TestTempDir() + "/zero_copy_stream_test_file";
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ // Make a temporary file.
+ int file =
+ open(filename.c_str(), O_RDWR | O_CREAT | O_TRUNC | O_BINARY, 0777);
+ ASSERT_GE(file, 0);
+ {
+ FileOutputStream output(file, kBlockSizes[i]);
+ GzipOutputStream gzout(&output);
+ WriteStuffLarge(&gzout);
+ gzout.Close();
+ output.Flush();
+ EXPECT_EQ(0, output.GetErrno());
+ }
+
+ // Rewind.
+ ASSERT_NE(lseek(file, 0, SEEK_SET), (off_t)-1);
+
+ {
+ FileInputStream input(file, kBlockSizes[j]);
+ GzipInputStream gzin(&input);
+ ReadStuffLarge(&gzin);
+ EXPECT_EQ(0, input.GetErrno());
+ }
+
+ close(file);
+ }
+ }
+}
+#endif
+
+// MSVC raises various debugging exceptions if we try to use a file
+// descriptor of -1, defeating our tests below. This class will disable
+// these debug assertions while in scope.
+class MsvcDebugDisabler {
+ public:
+#if defined(_MSC_VER) && _MSC_VER >= 1400
+ MsvcDebugDisabler() {
+ old_handler_ = _set_invalid_parameter_handler(MyHandler);
+ old_mode_ = _CrtSetReportMode(_CRT_ASSERT, 0);
+ }
+ ~MsvcDebugDisabler() {
+ old_handler_ = _set_invalid_parameter_handler(old_handler_);
+ old_mode_ = _CrtSetReportMode(_CRT_ASSERT, old_mode_);
+ }
+
+ static void MyHandler(const wchar_t *expr,
+ const wchar_t *func,
+ const wchar_t *file,
+ unsigned int line,
+ uintptr_t pReserved) {
+ // do nothing
+ }
+
+ _invalid_parameter_handler old_handler_;
+ int old_mode_;
+#else
+ // Dummy constructor and destructor to ensure that GCC doesn't complain
+ // that debug_disabler is an unused variable.
+ MsvcDebugDisabler() {}
+ ~MsvcDebugDisabler() {}
+#endif
+};
+
+// Test that FileInputStreams report errors correctly.
+TEST_F(IoTest, FileReadError) {
+ MsvcDebugDisabler debug_disabler;
+
+ // -1 = invalid file descriptor.
+ FileInputStream input(-1);
+
+ const void* buffer;
+ int size;
+ EXPECT_FALSE(input.Next(&buffer, &size));
+ EXPECT_EQ(EBADF, input.GetErrno());
+}
+
+// Test that FileOutputStreams report errors correctly.
+TEST_F(IoTest, FileWriteError) {
+ MsvcDebugDisabler debug_disabler;
+
+ // -1 = invalid file descriptor.
+ FileOutputStream input(-1);
+
+ void* buffer;
+ int size;
+
+ // The first call to Next() succeeds because it doesn't have anything to
+ // write yet.
+ EXPECT_TRUE(input.Next(&buffer, &size));
+
+ // Second call fails.
+ EXPECT_FALSE(input.Next(&buffer, &size));
+
+ EXPECT_EQ(EBADF, input.GetErrno());
+}
+
+// Pipes are not seekable, so File{Input,Output}Stream ends up doing some
+// different things to handle them. We'll test by writing to a pipe and
+// reading back from it.
+TEST_F(IoTest, PipeIo) {
+ int files[2];
+
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ // Need to create a new pipe each time because ReadStuff() expects
+ // to see EOF at the end.
+ ASSERT_EQ(pipe(files), 0);
+
+ {
+ FileOutputStream output(files[1], kBlockSizes[i]);
+ WriteStuff(&output);
+ EXPECT_EQ(0, output.GetErrno());
+ }
+ close(files[1]); // Send EOF.
+
+ {
+ FileInputStream input(files[0], kBlockSizes[j]);
+ ReadStuff(&input);
+ EXPECT_EQ(0, input.GetErrno());
+ }
+ close(files[0]);
+ }
+ }
+}
+
+// Test using C++ iostreams.
+TEST_F(IoTest, IostreamIo) {
+ for (int i = 0; i < kBlockSizeCount; i++) {
+ for (int j = 0; j < kBlockSizeCount; j++) {
+ {
+ stringstream stream;
+
+ {
+ OstreamOutputStream output(&stream, kBlockSizes[i]);
+ WriteStuff(&output);
+ EXPECT_FALSE(stream.fail());
+ }
+
+ {
+ IstreamInputStream input(&stream, kBlockSizes[j]);
+ ReadStuff(&input);
+ EXPECT_TRUE(stream.eof());
+ }
+ }
+
+ {
+ stringstream stream;
+
+ {
+ OstreamOutputStream output(&stream, kBlockSizes[i]);
+ WriteStuffLarge(&output);
+ EXPECT_FALSE(stream.fail());
+ }
+
+ {
+ IstreamInputStream input(&stream, kBlockSizes[j]);
+ ReadStuffLarge(&input);
+ EXPECT_TRUE(stream.eof());
+ }
+ }
+ }
+ }
+}
+
+// To test ConcatenatingInputStream, we create several ArrayInputStreams
+// covering a buffer and then concatenate them.
+TEST_F(IoTest, ConcatenatingInputStream) {
+ const int kBufferSize = 256;
+ uint8 buffer[kBufferSize];
+
+ // Fill the buffer.
+ ArrayOutputStream output(buffer, kBufferSize);
+ WriteStuff(&output);
+
+ // Now split it up into multiple streams of varying sizes.
+ ASSERT_EQ(68, output.ByteCount()); // Test depends on this.
+ ArrayInputStream input1(buffer , 12);
+ ArrayInputStream input2(buffer + 12, 7);
+ ArrayInputStream input3(buffer + 19, 6);
+ ArrayInputStream input4(buffer + 25, 15);
+ ArrayInputStream input5(buffer + 40, 0);
+ // Note: We want to make sure we have a stream boundary somewhere between
+ // bytes 42 and 62, which is the range that it Skip()ed by ReadStuff(). This
+ // tests that a bug that existed in the original code for Skip() is fixed.
+ ArrayInputStream input6(buffer + 40, 10);
+ ArrayInputStream input7(buffer + 50, 18); // Total = 68 bytes.
+
+ ZeroCopyInputStream* streams[] =
+ {&input1, &input2, &input3, &input4, &input5, &input6, &input7};
+
+ // Create the concatenating stream and read.
+ ConcatenatingInputStream input(streams, GOOGLE_ARRAYSIZE(streams));
+ ReadStuff(&input);
+}
+
+// To test LimitingInputStream, we write our golden text to a buffer, then
+// create an ArrayInputStream that contains the whole buffer (not just the
+// bytes written), then use a LimitingInputStream to limit it just to the
+// bytes written.
+TEST_F(IoTest, LimitingInputStream) {
+ const int kBufferSize = 256;
+ uint8 buffer[kBufferSize];
+
+ // Fill the buffer.
+ ArrayOutputStream output(buffer, kBufferSize);
+ WriteStuff(&output);
+
+ // Set up input.
+ ArrayInputStream array_input(buffer, kBufferSize);
+ LimitingInputStream input(&array_input, output.ByteCount());
+
+ ReadStuff(&input);
+}
+
+// Checks that ByteCount works correctly for LimitingInputStreams where the
+// underlying stream has already been read.
+TEST_F(IoTest, LimitingInputStreamByteCount) {
+ const int kHalfBufferSize = 128;
+ const int kBufferSize = kHalfBufferSize * 2;
+ uint8 buffer[kBufferSize];
+
+ // Set up input. Only allow half to be read at once.
+ ArrayInputStream array_input(buffer, kBufferSize, kHalfBufferSize);
+ const void* data;
+ int size;
+ EXPECT_TRUE(array_input.Next(&data, &size));
+ EXPECT_EQ(kHalfBufferSize, array_input.ByteCount());
+ // kHalfBufferSize - 1 to test limiting logic as well.
+ LimitingInputStream input(&array_input, kHalfBufferSize - 1);
+ EXPECT_EQ(0, input.ByteCount());
+ EXPECT_TRUE(input.Next(&data, &size));
+ EXPECT_EQ(kHalfBufferSize - 1 , input.ByteCount());
+}
+
+// Check that a zero-size array doesn't confuse the code.
+TEST(ZeroSizeArray, Input) {
+ ArrayInputStream input(NULL, 0);
+ const void* data;
+ int size;
+ EXPECT_FALSE(input.Next(&data, &size));
+}
+
+TEST(ZeroSizeArray, Output) {
+ ArrayOutputStream output(NULL, 0);
+ void* data;
+ int size;
+ EXPECT_FALSE(output.Next(&data, &size));
+}
+
+} // namespace
+} // namespace io
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/lite_arena_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/lite_arena_unittest.cc
new file mode 100644
index 0000000000..f0bee880aa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/lite_arena_unittest.cc
@@ -0,0 +1,83 @@
+// 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.
+
+#include <google/protobuf/arena_test_util.h>
+#include <google/protobuf/map_lite_test_util.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+
+TEST(LiteArenaTest, MapNoHeapAllocation) {
+ // Allocate a large initial block to avoid mallocs during hooked test.
+ std::vector<char> arena_block(128 * 1024);
+ google::protobuf::ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ google::protobuf::Arena arena(options);
+ string data;
+ data.reserve(128 * 1024);
+
+ {
+ // TODO(teboring): Enable no heap check when ArenaStringPtr is used in
+ // Map.
+ // google::protobuf::internal::NoHeapChecker no_heap;
+
+ protobuf_unittest::TestArenaMapLite* from =
+ google::protobuf::Arena::CreateMessage<protobuf_unittest::TestArenaMapLite>(&arena);
+ google::protobuf::MapLiteTestUtil::SetArenaMapFields(from);
+ from->SerializeToString(&data);
+
+ protobuf_unittest::TestArenaMapLite* to =
+ google::protobuf::Arena::CreateMessage<protobuf_unittest::TestArenaMapLite>(&arena);
+ to->ParseFromString(data);
+ google::protobuf::MapLiteTestUtil::ExpectArenaMapFieldsSet(*to);
+ }
+}
+
+TEST(LiteArenaTest, UnknownFieldMemLeak) {
+ google::protobuf::Arena arena;
+ protobuf_unittest::ForeignMessageArenaLite* message =
+ google::protobuf::Arena::CreateMessage<protobuf_unittest::ForeignMessageArenaLite>(
+ &arena);
+ string data = "\012\000";
+ int original_capacity = data.capacity();
+ while (data.capacity() <= original_capacity) {
+ data.append("a");
+ }
+ data[1] = data.size() - 2;
+ message->ParseFromString(data);
+}
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/lite_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/lite_unittest.cc
new file mode 100644
index 0000000000..3ca3fbaf6e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/lite_unittest.cc
@@ -0,0 +1,718 @@
+// 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)
+
+#include <string>
+#include <iostream>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/arena_test_util.h>
+#include <google/protobuf/map_lite_unittest.pb.h>
+#include <google/protobuf/map_lite_test_util.h>
+#include <google/protobuf/test_util_lite.h>
+#include <google/protobuf/unittest_lite.pb.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/wire_format_lite.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/stubs/strutil.h>
+
+using namespace std;
+
+namespace {
+// Helper methods to test parsing merge behavior.
+void ExpectMessageMerged(const google::protobuf::unittest::TestAllTypesLite& message) {
+ GOOGLE_CHECK(message.optional_int32() == 3);
+ GOOGLE_CHECK(message.optional_int64() == 2);
+ GOOGLE_CHECK(message.optional_string() == "hello");
+}
+
+void AssignParsingMergeMessages(
+ google::protobuf::unittest::TestAllTypesLite* msg1,
+ google::protobuf::unittest::TestAllTypesLite* msg2,
+ google::protobuf::unittest::TestAllTypesLite* msg3) {
+ msg1->set_optional_int32(1);
+ msg2->set_optional_int64(2);
+ msg3->set_optional_int32(3);
+ msg3->set_optional_string("hello");
+}
+
+void SetAllTypesInEmptyMessageUnknownFields(
+ google::protobuf::unittest::TestEmptyMessageLite* empty_message) {
+ protobuf_unittest::TestAllTypesLite message;
+ google::protobuf::TestUtilLite::ExpectClear(message);
+ google::protobuf::TestUtilLite::SetAllFields(&message);
+ string data = message.SerializeAsString();
+ empty_message->ParseFromString(data);
+}
+
+void SetSomeTypesInEmptyMessageUnknownFields(
+ google::protobuf::unittest::TestEmptyMessageLite* empty_message) {
+ protobuf_unittest::TestAllTypesLite message;
+ google::protobuf::TestUtilLite::ExpectClear(message);
+ message.set_optional_int32(101);
+ message.set_optional_int64(102);
+ message.set_optional_uint32(103);
+ message.set_optional_uint64(104);
+ string data = message.SerializeAsString();
+ empty_message->ParseFromString(data);
+}
+
+} // namespace
+
+#define EXPECT_TRUE GOOGLE_CHECK
+#define ASSERT_TRUE GOOGLE_CHECK
+#define EXPECT_FALSE(COND) GOOGLE_CHECK(!(COND))
+#define EXPECT_EQ GOOGLE_CHECK_EQ
+#define ASSERT_EQ GOOGLE_CHECK_EQ
+
+int main(int argc, char* argv[]) {
+ string data, data2, packed_data;
+
+ {
+ protobuf_unittest::TestAllTypesLite message, message2, message3;
+ google::protobuf::TestUtilLite::ExpectClear(message);
+ google::protobuf::TestUtilLite::SetAllFields(&message);
+ message2.CopyFrom(message);
+ data = message.SerializeAsString();
+ message3.ParseFromString(data);
+ google::protobuf::TestUtilLite::ExpectAllFieldsSet(message);
+ google::protobuf::TestUtilLite::ExpectAllFieldsSet(message2);
+ google::protobuf::TestUtilLite::ExpectAllFieldsSet(message3);
+ google::protobuf::TestUtilLite::ModifyRepeatedFields(&message);
+ google::protobuf::TestUtilLite::ExpectRepeatedFieldsModified(message);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectClear(message);
+ }
+
+ {
+ protobuf_unittest::TestAllExtensionsLite message, message2, message3;
+ google::protobuf::TestUtilLite::ExpectExtensionsClear(message);
+ google::protobuf::TestUtilLite::SetAllExtensions(&message);
+ message2.CopyFrom(message);
+ string extensions_data = message.SerializeAsString();
+ message3.ParseFromString(extensions_data);
+ google::protobuf::TestUtilLite::ExpectAllExtensionsSet(message);
+ google::protobuf::TestUtilLite::ExpectAllExtensionsSet(message2);
+ google::protobuf::TestUtilLite::ExpectAllExtensionsSet(message3);
+ google::protobuf::TestUtilLite::ModifyRepeatedExtensions(&message);
+ google::protobuf::TestUtilLite::ExpectRepeatedExtensionsModified(message);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectExtensionsClear(message);
+ }
+
+ {
+ protobuf_unittest::TestPackedTypesLite message, message2, message3;
+ google::protobuf::TestUtilLite::ExpectPackedClear(message);
+ google::protobuf::TestUtilLite::SetPackedFields(&message);
+ message2.CopyFrom(message);
+ packed_data = message.SerializeAsString();
+ message3.ParseFromString(packed_data);
+ google::protobuf::TestUtilLite::ExpectPackedFieldsSet(message);
+ google::protobuf::TestUtilLite::ExpectPackedFieldsSet(message2);
+ google::protobuf::TestUtilLite::ExpectPackedFieldsSet(message3);
+ google::protobuf::TestUtilLite::ModifyPackedFields(&message);
+ google::protobuf::TestUtilLite::ExpectPackedFieldsModified(message);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectPackedClear(message);
+ }
+
+ {
+ protobuf_unittest::TestPackedExtensionsLite message, message2, message3;
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsClear(message);
+ google::protobuf::TestUtilLite::SetPackedExtensions(&message);
+ message2.CopyFrom(message);
+ string packed_extensions_data = message.SerializeAsString();
+ GOOGLE_CHECK(packed_extensions_data == packed_data);
+ message3.ParseFromString(packed_extensions_data);
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsSet(message);
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsSet(message2);
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsSet(message3);
+ google::protobuf::TestUtilLite::ModifyPackedExtensions(&message);
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsModified(message);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsClear(message);
+ }
+
+ {
+ // Test that if an optional or required message/group field appears multiple
+ // times in the input, they need to be merged.
+ google::protobuf::unittest::TestParsingMergeLite::RepeatedFieldsGenerator generator;
+ google::protobuf::unittest::TestAllTypesLite* msg1;
+ google::protobuf::unittest::TestAllTypesLite* msg2;
+ google::protobuf::unittest::TestAllTypesLite* msg3;
+
+#define ASSIGN_REPEATED_FIELD(FIELD) \
+ msg1 = generator.add_##FIELD(); \
+ msg2 = generator.add_##FIELD(); \
+ msg3 = generator.add_##FIELD(); \
+ AssignParsingMergeMessages(msg1, msg2, msg3)
+
+ ASSIGN_REPEATED_FIELD(field1);
+ ASSIGN_REPEATED_FIELD(field2);
+ ASSIGN_REPEATED_FIELD(field3);
+ ASSIGN_REPEATED_FIELD(ext1);
+ ASSIGN_REPEATED_FIELD(ext2);
+
+#undef ASSIGN_REPEATED_FIELD
+#define ASSIGN_REPEATED_GROUP(FIELD) \
+ msg1 = generator.add_##FIELD()->mutable_field1(); \
+ msg2 = generator.add_##FIELD()->mutable_field1(); \
+ msg3 = generator.add_##FIELD()->mutable_field1(); \
+ AssignParsingMergeMessages(msg1, msg2, msg3)
+
+ ASSIGN_REPEATED_GROUP(group1);
+ ASSIGN_REPEATED_GROUP(group2);
+
+#undef ASSIGN_REPEATED_GROUP
+
+ string buffer;
+ generator.SerializeToString(&buffer);
+ google::protobuf::unittest::TestParsingMergeLite parsing_merge;
+ parsing_merge.ParseFromString(buffer);
+
+ // Required and optional fields should be merged.
+ ExpectMessageMerged(parsing_merge.required_all_types());
+ ExpectMessageMerged(parsing_merge.optional_all_types());
+ ExpectMessageMerged(
+ parsing_merge.optionalgroup().optional_group_all_types());
+ ExpectMessageMerged(parsing_merge.GetExtension(
+ google::protobuf::unittest::TestParsingMergeLite::optional_ext));
+
+ // Repeated fields should not be merged.
+ GOOGLE_CHECK(parsing_merge.repeated_all_types_size() == 3);
+ GOOGLE_CHECK(parsing_merge.repeatedgroup_size() == 3);
+ GOOGLE_CHECK(parsing_merge.ExtensionSize(
+ google::protobuf::unittest::TestParsingMergeLite::repeated_ext) == 3);
+ }
+
+ // Test unknown fields support for lite messages.
+ {
+ protobuf_unittest::TestAllTypesLite message, message2;
+ protobuf_unittest::TestEmptyMessageLite empty_message;
+ google::protobuf::TestUtilLite::ExpectClear(message);
+ google::protobuf::TestUtilLite::SetAllFields(&message);
+ data = message.SerializeAsString();
+ empty_message.ParseFromString(data);
+ data.clear();
+ data = empty_message.SerializeAsString();
+ message2.ParseFromString(data);
+ data = message2.SerializeAsString();
+ google::protobuf::TestUtilLite::ExpectAllFieldsSet(message2);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectClear(message);
+ }
+
+ {
+ protobuf_unittest::TestAllExtensionsLite message, message2;
+ protobuf_unittest::TestEmptyMessageLite empty_message;
+ google::protobuf::TestUtilLite::ExpectExtensionsClear(message);
+ google::protobuf::TestUtilLite::SetAllExtensions(&message);
+ data = message.SerializeAsString();
+ empty_message.ParseFromString(data);
+ data.clear();
+ data = empty_message.SerializeAsString();
+ message2.ParseFromString(data);
+ data = message2.SerializeAsString();
+ google::protobuf::TestUtilLite::ExpectAllExtensionsSet(message2);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectExtensionsClear(message);
+ }
+
+ {
+ protobuf_unittest::TestPackedTypesLite message, message2;
+ protobuf_unittest::TestEmptyMessageLite empty_message;
+ google::protobuf::TestUtilLite::ExpectPackedClear(message);
+ google::protobuf::TestUtilLite::SetPackedFields(&message);
+ data = message.SerializeAsString();
+ empty_message.ParseFromString(data);
+ data.clear();
+ data = empty_message.SerializeAsString();
+ message2.ParseFromString(data);
+ data = message2.SerializeAsString();
+ google::protobuf::TestUtilLite::ExpectPackedFieldsSet(message2);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectPackedClear(message);
+ }
+
+ {
+ protobuf_unittest::TestPackedExtensionsLite message, message2;
+ protobuf_unittest::TestEmptyMessageLite empty_message;
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsClear(message);
+ google::protobuf::TestUtilLite::SetPackedExtensions(&message);
+ data = message.SerializeAsString();
+ empty_message.ParseFromString(data);
+ data.clear();
+ data = empty_message.SerializeAsString();
+ message2.ParseFromString(data);
+ data = message2.SerializeAsString();
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsSet(message2);
+ message.Clear();
+ google::protobuf::TestUtilLite::ExpectPackedExtensionsClear(message);
+ }
+
+ {
+ // Test Unknown fields swap
+ protobuf_unittest::TestEmptyMessageLite empty_message, empty_message2;
+ SetAllTypesInEmptyMessageUnknownFields(&empty_message);
+ SetSomeTypesInEmptyMessageUnknownFields(&empty_message2);
+ data = empty_message.SerializeAsString();
+ data2 = empty_message2.SerializeAsString();
+ empty_message.Swap(&empty_message2);
+ GOOGLE_CHECK_EQ(data, empty_message2.SerializeAsString());
+ GOOGLE_CHECK_EQ(data2, empty_message.SerializeAsString());
+ }
+
+ {
+ // Test unknown fields swap with self
+ protobuf_unittest::TestEmptyMessageLite empty_message;
+ SetAllTypesInEmptyMessageUnknownFields(&empty_message);
+ data = empty_message.SerializeAsString();
+ empty_message.Swap(&empty_message);
+ GOOGLE_CHECK_EQ(data, empty_message.SerializeAsString());
+ }
+
+ {
+ // Test MergeFrom with unknown fields
+ protobuf_unittest::TestAllTypesLite message, message2;
+ protobuf_unittest::TestEmptyMessageLite empty_message, empty_message2;
+ message.set_optional_int32(101);
+ message.add_repeated_int32(201);
+ message.set_optional_nested_enum(google::protobuf::unittest::TestAllTypesLite::BAZ);
+ message2.set_optional_int64(102);
+ message2.add_repeated_int64(202);
+ message2.set_optional_foreign_enum(google::protobuf::unittest::FOREIGN_LITE_BAZ);
+
+ data = message.SerializeAsString();
+ empty_message.ParseFromString(data);
+ data = message2.SerializeAsString();
+ empty_message2.ParseFromString(data);
+ message.MergeFrom(message2);
+ empty_message.MergeFrom(empty_message2);
+
+ data = empty_message.SerializeAsString();
+ message2.ParseFromString(data);
+ // We do not compare the serialized output of a normal message and a lite
+ // message because the order of fields do not match. We convert lite message
+ // back into normal message, then compare.
+ GOOGLE_CHECK_EQ(message.SerializeAsString(), message2.SerializeAsString());
+ }
+
+ {
+ // Test unknown enum value
+ protobuf_unittest::TestAllTypesLite message;
+ string buffer;
+ {
+ google::protobuf::io::StringOutputStream output_stream(&buffer);
+ google::protobuf::io::CodedOutputStream coded_output(&output_stream);
+ google::protobuf::internal::WireFormatLite::WriteTag(
+ protobuf_unittest::TestAllTypesLite::kOptionalNestedEnumFieldNumber,
+ google::protobuf::internal::WireFormatLite::WIRETYPE_VARINT, &coded_output);
+ coded_output.WriteVarint32(10);
+ google::protobuf::internal::WireFormatLite::WriteTag(
+ protobuf_unittest::TestAllTypesLite::kRepeatedNestedEnumFieldNumber,
+ google::protobuf::internal::WireFormatLite::WIRETYPE_VARINT, &coded_output);
+ coded_output.WriteVarint32(20);
+ }
+ message.ParseFromString(buffer);
+ data = message.SerializeAsString();
+ GOOGLE_CHECK_EQ(data, buffer);
+ }
+
+ {
+ // Test Clear with unknown fields
+ protobuf_unittest::TestEmptyMessageLite empty_message;
+ SetAllTypesInEmptyMessageUnknownFields(&empty_message);
+ empty_message.Clear();
+ GOOGLE_CHECK_EQ(0, empty_message.unknown_fields().size());
+ }
+
+ // Tests for map lite =============================================
+
+ {
+ // Accessors
+ protobuf_unittest::TestMapLite message;
+
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message);
+
+ google::protobuf::MapLiteTestUtil::ModifyMapFields(&message);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsModified(message);
+ }
+
+ {
+ // SetMapFieldsInitialized
+ protobuf_unittest::TestMapLite message;
+
+ google::protobuf::MapLiteTestUtil::SetMapFieldsInitialized(&message);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSetInitialized(message);
+ }
+
+ {
+ // Clear
+ protobuf_unittest::TestMapLite message;
+
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message);
+ message.Clear();
+ google::protobuf::MapLiteTestUtil::ExpectClear(message);
+ }
+
+ {
+ // ClearMessageMap
+ protobuf_unittest::TestMessageMapLite message;
+
+ // Creates a TestAllTypes with default value
+ google::protobuf::TestUtilLite::ExpectClear(
+ (*message.mutable_map_int32_message())[0]);
+ }
+
+ {
+ // CopyFrom
+ protobuf_unittest::TestMapLite message1, message2;
+
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+ message2.CopyFrom(message1);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+
+ // Copying from self should be a no-op.
+ message2.CopyFrom(message2);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+ }
+
+ {
+ // CopyFromMessageMap
+ protobuf_unittest::TestMessageMapLite message1, message2;
+
+ (*message1.mutable_map_int32_message())[0].add_repeated_int32(100);
+ (*message2.mutable_map_int32_message())[0].add_repeated_int32(101);
+
+ message1.CopyFrom(message2);
+
+ // Checks repeated field is overwritten.
+ EXPECT_EQ(1, message1.map_int32_message().at(0).repeated_int32_size());
+ EXPECT_EQ(101, message1.map_int32_message().at(0).repeated_int32(0));
+ }
+
+ {
+ // SwapWithEmpty
+ protobuf_unittest::TestMapLite message1, message2;
+
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message1);
+ google::protobuf::MapLiteTestUtil::ExpectClear(message2);
+
+ message1.Swap(&message2);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+ google::protobuf::MapLiteTestUtil::ExpectClear(message1);
+ }
+
+ {
+ // SwapWithSelf
+ protobuf_unittest::TestMapLite message;
+
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message);
+
+ message.Swap(&message);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message);
+ }
+
+ {
+ // SwapWithOther
+ protobuf_unittest::TestMapLite message1, message2;
+
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message2);
+ google::protobuf::MapLiteTestUtil::ModifyMapFields(&message2);
+
+ message1.Swap(&message2);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsModified(message1);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+ }
+
+ {
+ // CopyConstructor
+ protobuf_unittest::TestMapLite message1;
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+
+ protobuf_unittest::TestMapLite message2(message1);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+ }
+
+ {
+ // CopyAssignmentOperator
+ protobuf_unittest::TestMapLite message1;
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+
+ protobuf_unittest::TestMapLite message2;
+ message2 = message1;
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+
+ // Make sure that self-assignment does something sane.
+ message2.operator=(message2);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+ }
+
+ {
+ // NonEmptyMergeFrom
+ protobuf_unittest::TestMapLite message1, message2;
+
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+
+ // This field will test merging into an empty spot.
+ (*message2.mutable_map_int32_int32())[1] = 1;
+ message1.mutable_map_int32_int32()->erase(1);
+
+ // This tests overwriting.
+ (*message2.mutable_map_int32_double())[1] = 1;
+ (*message1.mutable_map_int32_double())[1] = 2;
+
+ message1.MergeFrom(message2);
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message1);
+ }
+
+ {
+ // MergeFromMessageMap
+ protobuf_unittest::TestMessageMapLite message1, message2;
+
+ (*message1.mutable_map_int32_message())[0].add_repeated_int32(100);
+ (*message2.mutable_map_int32_message())[0].add_repeated_int32(101);
+
+ message1.MergeFrom(message2);
+
+ // Checks repeated field is overwritten.
+ EXPECT_EQ(1, message1.map_int32_message().at(0).repeated_int32_size());
+ EXPECT_EQ(101, message1.map_int32_message().at(0).repeated_int32(0));
+ }
+
+ {
+ // Test the generated SerializeWithCachedSizesToArray()
+ protobuf_unittest::TestMapLite message1, message2;
+ string data;
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+ int size = message1.ByteSize();
+ data.resize(size);
+ ::google::protobuf::uint8* start = reinterpret_cast< ::google::protobuf::uint8*>(::google::protobuf::string_as_array(&data));
+ ::google::protobuf::uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+ }
+
+ {
+ // Test the generated SerializeWithCachedSizes()
+ protobuf_unittest::TestMapLite message1, message2;
+ google::protobuf::MapLiteTestUtil::SetMapFields(&message1);
+ int size = message1.ByteSize();
+ string data;
+ data.resize(size);
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ google::protobuf::io::ArrayOutputStream array_stream(
+ ::google::protobuf::string_as_array(&data), size, 1);
+ google::protobuf::io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+ EXPECT_TRUE(message2.ParseFromString(data));
+ google::protobuf::MapLiteTestUtil::ExpectMapFieldsSet(message2);
+ }
+
+
+ {
+ // Proto2UnknownEnum
+ protobuf_unittest::TestEnumMapPlusExtraLite from;
+ (*from.mutable_known_map_field())[0] =
+ protobuf_unittest::E_PROTO2_MAP_ENUM_FOO_LITE;
+ (*from.mutable_unknown_map_field())[0] =
+ protobuf_unittest::E_PROTO2_MAP_ENUM_EXTRA_LITE;
+ string data;
+ from.SerializeToString(&data);
+
+ protobuf_unittest::TestEnumMapLite to;
+ EXPECT_TRUE(to.ParseFromString(data));
+ EXPECT_EQ(0, to.unknown_map_field().size());
+ EXPECT_FALSE(to.mutable_unknown_fields()->empty());
+ EXPECT_EQ(1, to.known_map_field().size());
+ EXPECT_EQ(protobuf_unittest::PROTO2_MAP_ENUM_FOO_LITE,
+ to.known_map_field().at(0));
+
+ data.clear();
+ from.Clear();
+ to.SerializeToString(&data);
+ EXPECT_TRUE(from.ParseFromString(data));
+ EXPECT_EQ(1, from.known_map_field().size());
+ EXPECT_EQ(protobuf_unittest::E_PROTO2_MAP_ENUM_FOO_LITE,
+ from.known_map_field().at(0));
+ EXPECT_EQ(1, from.unknown_map_field().size());
+ EXPECT_EQ(protobuf_unittest::E_PROTO2_MAP_ENUM_EXTRA_LITE,
+ from.unknown_map_field().at(0));
+ }
+
+ {
+ // StandardWireFormat
+ protobuf_unittest::TestMapLite message;
+ string data = "\x0A\x04\x08\x01\x10\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(1));
+ }
+
+ {
+ // UnorderedWireFormat
+ protobuf_unittest::TestMapLite message;
+
+ // put value before key in wire format
+ string data = "\x0A\x04\x10\x01\x08\x02";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(2));
+ }
+
+ {
+ // DuplicatedKeyWireFormat
+ protobuf_unittest::TestMapLite message;
+
+ // Two key fields in wire format
+ string data = "\x0A\x06\x08\x01\x08\x02\x10\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(2));
+ }
+
+ {
+ // DuplicatedValueWireFormat
+ protobuf_unittest::TestMapLite message;
+
+ // Two value fields in wire format
+ string data = "\x0A\x06\x08\x01\x10\x01\x10\x02";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(2, message.map_int32_int32().at(1));
+ }
+
+ {
+ // MissedKeyWireFormat
+ protobuf_unittest::TestMapLite message;
+
+ // No key field in wire format
+ string data = "\x0A\x02\x10\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(0));
+ }
+
+ {
+ // MissedValueWireFormat
+ protobuf_unittest::TestMapLite message;
+
+ // No value field in wire format
+ string data = "\x0A\x02\x08\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(0, message.map_int32_int32().at(1));
+ }
+
+ {
+ // UnknownFieldWireFormat
+ protobuf_unittest::TestMapLite message;
+
+ // Unknown field in wire format
+ string data = "\x0A\x06\x08\x02\x10\x03\x18\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(3, message.map_int32_int32().at(2));
+ }
+
+ {
+ // CorruptedWireFormat
+ protobuf_unittest::TestMapLite message;
+
+ // corrupted data in wire format
+ string data = "\x0A\x06\x08\x02\x11\x03";
+
+ EXPECT_FALSE(message.ParseFromString(data));
+ }
+
+ {
+ // IsInitialized
+ protobuf_unittest::TestRequiredMessageMapLite map_message;
+
+ // Add an uninitialized message.
+ (*map_message.mutable_map_field())[0];
+ EXPECT_FALSE(map_message.IsInitialized());
+
+ // Initialize uninitialized message
+ (*map_message.mutable_map_field())[0].set_a(0);
+ (*map_message.mutable_map_field())[0].set_b(0);
+ (*map_message.mutable_map_field())[0].set_c(0);
+ EXPECT_TRUE(map_message.IsInitialized());
+ }
+
+ {
+ // Check that adding more values to enum does not corrupt message
+ // when passed through an old client.
+ protobuf_unittest::V2MessageLite v2_message;
+ v2_message.set_int_field(800);
+ // Set enum field to the value not understood by the old client.
+ v2_message.set_enum_field(protobuf_unittest::V2_SECOND);
+ string v2_bytes = v2_message.SerializeAsString();
+
+ protobuf_unittest::V1MessageLite v1_message;
+ v1_message.ParseFromString(v2_bytes);
+ EXPECT_TRUE(v1_message.IsInitialized());
+ EXPECT_EQ(v1_message.int_field(), v2_message.int_field());
+ // V1 client does not understand V2_SECOND value, so it discards it and
+ // uses default value instead.
+ EXPECT_EQ(v1_message.enum_field(), protobuf_unittest::V1_FIRST);
+
+ // However, when re-serialized, it should preserve enum value.
+ string v1_bytes = v1_message.SerializeAsString();
+
+ protobuf_unittest::V2MessageLite same_v2_message;
+ same_v2_message.ParseFromString(v1_bytes);
+
+ EXPECT_EQ(v2_message.int_field(), same_v2_message.int_field());
+ EXPECT_EQ(v2_message.enum_field(), same_v2_message.enum_field());
+ }
+
+ std::cout << "PASS" << std::endl;
+ return 0;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map.h b/third_party/protobuf/3.0.0/src/google/protobuf/map.h
new file mode 100644
index 0000000000..1b9aa70332
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map.h
@@ -0,0 +1,1742 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_H__
+#define GOOGLE_PROTOBUF_MAP_H__
+
+#include <google/protobuf/stubs/hash.h>
+#include <iterator>
+#include <limits> // To support Visual Studio 2008
+#include <set>
+#include <utility>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/generated_enum_util.h>
+#include <google/protobuf/map_type_handler.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/descriptor.h>
+#if __cpp_exceptions && LANG_CXX11
+#include <random>
+#endif
+
+namespace google {
+namespace protobuf {
+
+// The Map and MapIterator types are provided by this header file.
+// Please avoid using other types defined here, unless they are public
+// types within Map or MapIterator, such as Map::value_type.
+template <typename Key, typename T>
+class Map;
+
+class MapIterator;
+
+template <typename Enum> struct is_proto_enum;
+
+namespace internal {
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+class MapFieldLite;
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+class MapField;
+
+template <typename Key, typename T>
+class TypeDefinedMapFieldBase;
+
+class DynamicMapField;
+
+class GeneratedMessageReflection;
+} // namespace internal
+
+#define TYPE_CHECK(EXPECTEDTYPE, METHOD) \
+ if (type() != EXPECTEDTYPE) { \
+ GOOGLE_LOG(FATAL) \
+ << "Protocol Buffer map usage error:\n" \
+ << METHOD << " type does not match\n" \
+ << " Expected : " \
+ << FieldDescriptor::CppTypeName(EXPECTEDTYPE) << "\n" \
+ << " Actual : " \
+ << FieldDescriptor::CppTypeName(type()); \
+ }
+
+// MapKey is an union type for representing any possible
+// map key.
+class LIBPROTOBUF_EXPORT MapKey {
+ public:
+ MapKey() : type_(0) {
+ }
+ MapKey(const MapKey& other) : type_(0) {
+ CopyFrom(other);
+ }
+
+ ~MapKey() {
+ if (type_ == FieldDescriptor::CPPTYPE_STRING) {
+ delete val_.string_value_;
+ }
+ }
+
+ FieldDescriptor::CppType type() const {
+ if (type_ == 0) {
+ GOOGLE_LOG(FATAL)
+ << "Protocol Buffer map usage error:\n"
+ << "MapKey::type MapKey is not initialized. "
+ << "Call set methods to initialize MapKey.";
+ }
+ return (FieldDescriptor::CppType)type_;
+ }
+
+ void SetInt64Value(int64 value) {
+ SetType(FieldDescriptor::CPPTYPE_INT64);
+ val_.int64_value_ = value;
+ }
+ void SetUInt64Value(uint64 value) {
+ SetType(FieldDescriptor::CPPTYPE_UINT64);
+ val_.uint64_value_ = value;
+ }
+ void SetInt32Value(int32 value) {
+ SetType(FieldDescriptor::CPPTYPE_INT32);
+ val_.int32_value_ = value;
+ }
+ void SetUInt32Value(uint32 value) {
+ SetType(FieldDescriptor::CPPTYPE_UINT32);
+ val_.uint32_value_ = value;
+ }
+ void SetBoolValue(bool value) {
+ SetType(FieldDescriptor::CPPTYPE_BOOL);
+ val_.bool_value_ = value;
+ }
+ void SetStringValue(const string& val) {
+ SetType(FieldDescriptor::CPPTYPE_STRING);
+ *val_.string_value_ = val;
+ }
+
+ int64 GetInt64Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_INT64,
+ "MapKey::GetInt64Value");
+ return val_.int64_value_;
+ }
+ uint64 GetUInt64Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_UINT64,
+ "MapKey::GetUInt64Value");
+ return val_.uint64_value_;
+ }
+ int32 GetInt32Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_INT32,
+ "MapKey::GetInt32Value");
+ return val_.int32_value_;
+ }
+ uint32 GetUInt32Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_UINT32,
+ "MapKey::GetUInt32Value");
+ return val_.uint32_value_;
+ }
+ bool GetBoolValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_BOOL,
+ "MapKey::GetBoolValue");
+ return val_.bool_value_;
+ }
+ const string& GetStringValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_STRING,
+ "MapKey::GetStringValue");
+ return *val_.string_value_;
+ }
+
+ bool operator<(const MapKey& other) const {
+ if (type_ != other.type_) {
+ // We could define a total order that handles this case, but
+ // there currently no need. So, for now, fail.
+ GOOGLE_LOG(FATAL) << "Unsupported: type mismatch";
+ }
+ switch (type()) {
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ case FieldDescriptor::CPPTYPE_ENUM:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Unsupported";
+ return false;
+ case FieldDescriptor::CPPTYPE_STRING:
+ return *val_.string_value_ < *other.val_.string_value_;
+ case FieldDescriptor::CPPTYPE_INT64:
+ return val_.int64_value_ < other.val_.int64_value_;
+ case FieldDescriptor::CPPTYPE_INT32:
+ return val_.int32_value_ < other.val_.int32_value_;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return val_.uint64_value_ < other.val_.uint64_value_;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return val_.uint32_value_ < other.val_.uint32_value_;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return val_.bool_value_ < other.val_.bool_value_;
+ }
+ return false;
+ }
+
+ bool operator==(const MapKey& other) const {
+ if (type_ != other.type_) {
+ // To be consistent with operator<, we don't allow this either.
+ GOOGLE_LOG(FATAL) << "Unsupported: type mismatch";
+ }
+ switch (type()) {
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ case FieldDescriptor::CPPTYPE_ENUM:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Unsupported";
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ return *val_.string_value_ == *other.val_.string_value_;
+ case FieldDescriptor::CPPTYPE_INT64:
+ return val_.int64_value_ == other.val_.int64_value_;
+ case FieldDescriptor::CPPTYPE_INT32:
+ return val_.int32_value_ == other.val_.int32_value_;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return val_.uint64_value_ == other.val_.uint64_value_;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return val_.uint32_value_ == other.val_.uint32_value_;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return val_.bool_value_ == other.val_.bool_value_;
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return false;
+ }
+
+ void CopyFrom(const MapKey& other) {
+ SetType(other.type());
+ switch (type_) {
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ case FieldDescriptor::CPPTYPE_ENUM:
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Unsupported";
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ *val_.string_value_ = *other.val_.string_value_;
+ break;
+ case FieldDescriptor::CPPTYPE_INT64:
+ val_.int64_value_ = other.val_.int64_value_;
+ break;
+ case FieldDescriptor::CPPTYPE_INT32:
+ val_.int32_value_ = other.val_.int32_value_;
+ break;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ val_.uint64_value_ = other.val_.uint64_value_;
+ break;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ val_.uint32_value_ = other.val_.uint32_value_;
+ break;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ val_.bool_value_ = other.val_.bool_value_;
+ break;
+ }
+ }
+
+ private:
+ template <typename K, typename V>
+ friend class internal::TypeDefinedMapFieldBase;
+ friend class MapIterator;
+ friend class internal::DynamicMapField;
+
+ union KeyValue {
+ KeyValue() {}
+ string* string_value_;
+ int64 int64_value_;
+ int32 int32_value_;
+ uint64 uint64_value_;
+ uint32 uint32_value_;
+ bool bool_value_;
+ } val_;
+
+ void SetType(FieldDescriptor::CppType type) {
+ if (type_ == type) return;
+ if (type_ == FieldDescriptor::CPPTYPE_STRING) {
+ delete val_.string_value_;
+ }
+ type_ = type;
+ if (type_ == FieldDescriptor::CPPTYPE_STRING) {
+ val_.string_value_ = new string;
+ }
+ }
+
+ // type_ is 0 or a valid FieldDescriptor::CppType.
+ int type_;
+};
+
+// MapValueRef points to a map value.
+class LIBPROTOBUF_EXPORT MapValueRef {
+ public:
+ MapValueRef() : data_(NULL), type_(0) {}
+
+ void SetInt64Value(int64 value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_INT64,
+ "MapValueRef::SetInt64Value");
+ *reinterpret_cast<int64*>(data_) = value;
+ }
+ void SetUInt64Value(uint64 value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_UINT64,
+ "MapValueRef::SetUInt64Value");
+ *reinterpret_cast<uint64*>(data_) = value;
+ }
+ void SetInt32Value(int32 value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_INT32,
+ "MapValueRef::SetInt32Value");
+ *reinterpret_cast<int32*>(data_) = value;
+ }
+ void SetUInt32Value(uint32 value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_UINT32,
+ "MapValueRef::SetUInt32Value");
+ *reinterpret_cast<uint32*>(data_) = value;
+ }
+ void SetBoolValue(bool value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_BOOL,
+ "MapValueRef::SetBoolValue");
+ *reinterpret_cast<bool*>(data_) = value;
+ }
+ // TODO(jieluo) - Checks that enum is member.
+ void SetEnumValue(int value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_ENUM,
+ "MapValueRef::SetEnumValue");
+ *reinterpret_cast<int*>(data_) = value;
+ }
+ void SetStringValue(const string& value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_STRING,
+ "MapValueRef::SetStringValue");
+ *reinterpret_cast<string*>(data_) = value;
+ }
+ void SetFloatValue(float value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_FLOAT,
+ "MapValueRef::SetFloatValue");
+ *reinterpret_cast<float*>(data_) = value;
+ }
+ void SetDoubleValue(double value) {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_DOUBLE,
+ "MapValueRef::SetDoubleValue");
+ *reinterpret_cast<double*>(data_) = value;
+ }
+
+ int64 GetInt64Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_INT64,
+ "MapValueRef::GetInt64Value");
+ return *reinterpret_cast<int64*>(data_);
+ }
+ uint64 GetUInt64Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_UINT64,
+ "MapValueRef::GetUInt64Value");
+ return *reinterpret_cast<uint64*>(data_);
+ }
+ int32 GetInt32Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_INT32,
+ "MapValueRef::GetInt32Value");
+ return *reinterpret_cast<int32*>(data_);
+ }
+ uint32 GetUInt32Value() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_UINT32,
+ "MapValueRef::GetUInt32Value");
+ return *reinterpret_cast<uint32*>(data_);
+ }
+ bool GetBoolValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_BOOL,
+ "MapValueRef::GetBoolValue");
+ return *reinterpret_cast<bool*>(data_);
+ }
+ int GetEnumValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_ENUM,
+ "MapValueRef::GetEnumValue");
+ return *reinterpret_cast<int*>(data_);
+ }
+ const string& GetStringValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_STRING,
+ "MapValueRef::GetStringValue");
+ return *reinterpret_cast<string*>(data_);
+ }
+ float GetFloatValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_FLOAT,
+ "MapValueRef::GetFloatValue");
+ return *reinterpret_cast<float*>(data_);
+ }
+ double GetDoubleValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_DOUBLE,
+ "MapValueRef::GetDoubleValue");
+ return *reinterpret_cast<double*>(data_);
+ }
+
+ const Message& GetMessageValue() const {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_MESSAGE,
+ "MapValueRef::GetMessageValue");
+ return *reinterpret_cast<Message*>(data_);
+ }
+
+ Message* MutableMessageValue() {
+ TYPE_CHECK(FieldDescriptor::CPPTYPE_MESSAGE,
+ "MapValueRef::MutableMessageValue");
+ return reinterpret_cast<Message*>(data_);
+ }
+
+ private:
+ template <typename K, typename V,
+ internal::WireFormatLite::FieldType key_wire_type,
+ internal::WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+ friend class internal::MapField;
+ template <typename K, typename V>
+ friend class internal::TypeDefinedMapFieldBase;
+ friend class MapIterator;
+ friend class internal::GeneratedMessageReflection;
+ friend class internal::DynamicMapField;
+
+ void SetType(FieldDescriptor::CppType type) {
+ type_ = type;
+ }
+
+ FieldDescriptor::CppType type() const {
+ if (type_ == 0 || data_ == NULL) {
+ GOOGLE_LOG(FATAL)
+ << "Protocol Buffer map usage error:\n"
+ << "MapValueRef::type MapValueRef is not initialized.";
+ }
+ return (FieldDescriptor::CppType)type_;
+ }
+ void SetValue(const void* val) {
+ data_ = const_cast<void*>(val);
+ }
+ void CopyFrom(const MapValueRef& other) {
+ type_ = other.type_;
+ data_ = other.data_;
+ }
+ // Only used in DynamicMapField
+ void DeleteData() {
+ switch (type_) {
+#define HANDLE_TYPE(CPPTYPE, TYPE) \
+ case google::protobuf::FieldDescriptor::CPPTYPE_##CPPTYPE: { \
+ delete reinterpret_cast<TYPE*>(data_); \
+ break; \
+ }
+ HANDLE_TYPE(INT32, int32);
+ HANDLE_TYPE(INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE(FLOAT, float);
+ HANDLE_TYPE(BOOL, bool);
+ HANDLE_TYPE(STRING, string);
+ HANDLE_TYPE(ENUM, int32);
+ HANDLE_TYPE(MESSAGE, Message);
+#undef HANDLE_TYPE
+ }
+ }
+ // data_ point to a map value. MapValueRef does not
+ // own this value.
+ void* data_;
+ // type_ is 0 or a valid FieldDescriptor::CppType.
+ int type_;
+};
+
+#undef TYPE_CHECK
+
+// This is the class for google::protobuf::Map's internal value_type. Instead of using
+// std::pair as value_type, we use this class which provides us more control of
+// its process of construction and destruction.
+template <typename Key, typename T>
+class MapPair {
+ public:
+ typedef const Key first_type;
+ typedef T second_type;
+
+ MapPair(const Key& other_first, const T& other_second)
+ : first(other_first), second(other_second) {}
+ explicit MapPair(const Key& other_first) : first(other_first), second() {}
+ MapPair(const MapPair& other)
+ : first(other.first), second(other.second) {}
+
+ ~MapPair() {}
+
+ // Implicitly convertible to std::pair of compatible types.
+ template <typename T1, typename T2>
+ operator std::pair<T1, T2>() const {
+ return std::pair<T1, T2>(first, second);
+ }
+
+ const Key first;
+ T second;
+
+ private:
+ friend class ::google::protobuf::Arena;
+ friend class Map<Key, T>;
+};
+
+// google::protobuf::Map is an associative container type used to store protobuf map
+// fields. Each Map instance may or may not use a different hash function, a
+// different iteration order, and so on. E.g., please don't examine
+// implementation details to decide if the following would work:
+// Map<int, int> m0, m1;
+// m0[0] = m1[0] = m0[1] = m1[1] = 0;
+// assert(m0.begin()->first == m1.begin()->first); // Bug!
+//
+// Map's interface is similar to std::unordered_map, except that Map is not
+// designed to play well with exceptions.
+template <typename Key, typename T>
+class Map {
+ public:
+ typedef Key key_type;
+ typedef T mapped_type;
+ typedef MapPair<Key, T> value_type;
+
+ typedef value_type* pointer;
+ typedef const value_type* const_pointer;
+ typedef value_type& reference;
+ typedef const value_type& const_reference;
+
+ typedef size_t size_type;
+ typedef hash<Key> hasher;
+
+ explicit Map(bool old_style = true)
+ : arena_(NULL),
+ default_enum_value_(0),
+ old_style_(old_style) {
+ Init();
+ }
+ explicit Map(Arena* arena, bool old_style = true)
+ : arena_(arena),
+ default_enum_value_(0),
+ old_style_(old_style) {
+ Init();
+ }
+ Map(const Map& other)
+ : arena_(NULL),
+ default_enum_value_(other.default_enum_value_),
+ old_style_(other.old_style_) {
+ Init();
+ insert(other.begin(), other.end());
+ }
+ template <class InputIt>
+ Map(const InputIt& first, const InputIt& last, bool old_style = true)
+ : arena_(NULL),
+ default_enum_value_(0),
+ old_style_(old_style) {
+ Init();
+ insert(first, last);
+ }
+
+ ~Map() {
+ clear();
+ if (arena_ == NULL) {
+ if (old_style_)
+ delete deprecated_elements_;
+ else
+ delete elements_;
+ }
+ }
+
+ private:
+ void Init() {
+ if (old_style_)
+ deprecated_elements_ = Arena::Create<DeprecatedInnerMap>(
+ arena_, 0, hasher(), equal_to<Key>(),
+ MapAllocator<std::pair<const Key, MapPair<Key, T>*> >(arena_));
+ else
+ elements_ =
+ Arena::Create<InnerMap>(arena_, 0, hasher(), Allocator(arena_));
+ }
+
+ // re-implement std::allocator to use arena allocator for memory allocation.
+ // Used for google::protobuf::Map implementation. Users should not use this class
+ // directly.
+ template <typename U>
+ class MapAllocator {
+ public:
+ typedef U value_type;
+ typedef value_type* pointer;
+ typedef const value_type* const_pointer;
+ typedef value_type& reference;
+ typedef const value_type& const_reference;
+ typedef size_t size_type;
+ typedef ptrdiff_t difference_type;
+
+ MapAllocator() : arena_(NULL) {}
+ explicit MapAllocator(Arena* arena) : arena_(arena) {}
+ template <typename X>
+ MapAllocator(const MapAllocator<X>& allocator)
+ : arena_(allocator.arena()) {}
+
+ pointer allocate(size_type n, const_pointer hint = 0) {
+ // If arena is not given, malloc needs to be called which doesn't
+ // construct element object.
+ if (arena_ == NULL) {
+ return reinterpret_cast<pointer>(malloc(n * sizeof(value_type)));
+ } else {
+ return reinterpret_cast<pointer>(
+ Arena::CreateArray<uint8>(arena_, n * sizeof(value_type)));
+ }
+ }
+
+ void deallocate(pointer p, size_type n) {
+ if (arena_ == NULL) {
+ free(p);
+ }
+ }
+
+#if __cplusplus >= 201103L && !defined(GOOGLE_PROTOBUF_OS_APPLE) && \
+ !defined(GOOGLE_PROTOBUF_OS_NACL) && \
+ !defined(GOOGLE_PROTOBUF_OS_ANDROID) && \
+ !defined(GOOGLE_PROTOBUF_OS_EMSCRIPTEN)
+ template<class NodeType, class... Args>
+ void construct(NodeType* p, Args&&... args) {
+ // Clang 3.6 doesn't compile static casting to void* directly. (Issue
+ // #1266) According C++ standard 5.2.9/1: "The static_cast operator shall
+ // not cast away constness". So first the maybe const pointer is casted to
+ // const void* and after the const void* is const casted.
+ new (const_cast<void*>(static_cast<const void*>(p)))
+ NodeType(std::forward<Args>(args)...);
+ }
+
+ template<class NodeType>
+ void destroy(NodeType* p) {
+ p->~NodeType();
+ }
+#else
+ void construct(pointer p, const_reference t) { new (p) value_type(t); }
+
+ void destroy(pointer p) { p->~value_type(); }
+#endif
+
+ template <typename X>
+ struct rebind {
+ typedef MapAllocator<X> other;
+ };
+
+ template <typename X>
+ bool operator==(const MapAllocator<X>& other) const {
+ return arena_ == other.arena_;
+ }
+
+ template <typename X>
+ bool operator!=(const MapAllocator<X>& other) const {
+ return arena_ != other.arena_;
+ }
+
+ // To support Visual Studio 2008
+ size_type max_size() const {
+ return std::numeric_limits<size_type>::max();
+ }
+
+ // To support gcc-4.4, which does not properly
+ // support templated friend classes
+ Arena* arena() const {
+ return arena_;
+ }
+
+ private:
+ typedef void DestructorSkippable_;
+ Arena* const arena_;
+ };
+
+ // InnerMap's key type is Key and its value type is value_type*. We use a
+ // custom class here and for Node, below, to ensure that k_ is at offset 0,
+ // allowing safe conversion from pointer to Node to pointer to Key, and vice
+ // versa when appropriate.
+ class KeyValuePair {
+ public:
+ KeyValuePair(const Key& k, value_type* v) : k_(k), v_(v) {}
+
+ const Key& key() const { return k_; }
+ Key& key() { return k_; }
+ value_type* const value() const { return v_; }
+ value_type*& value() { return v_; }
+
+ private:
+ Key k_;
+ value_type* v_;
+ };
+
+ typedef MapAllocator<KeyValuePair> Allocator;
+
+ // InnerMap is a generic hash-based map. It doesn't contain any
+ // protocol-buffer-specific logic. It is a chaining hash map with the
+ // additional feature that some buckets can be converted to use an ordered
+ // container. This ensures O(lg n) bounds on find, insert, and erase, while
+ // avoiding the overheads of ordered containers most of the time.
+ //
+ // The implementation doesn't need the full generality of unordered_map,
+ // and it doesn't have it. More bells and whistles can be added as needed.
+ // Some implementation details:
+ // 1. The hash function has type hasher and the equality function
+ // equal_to<Key>. We inherit from hasher to save space
+ // (empty-base-class optimization).
+ // 2. The number of buckets is a power of two.
+ // 3. Buckets are converted to trees in pairs: if we convert bucket b then
+ // buckets b and b^1 will share a tree. Invariant: buckets b and b^1 have
+ // the same non-NULL value iff they are sharing a tree. (An alternative
+ // implementation strategy would be to have a tag bit per bucket.)
+ // 4. As is typical for hash_map and such, the Keys and Values are always
+ // stored in linked list nodes. Pointers to elements are never invalidated
+ // until the element is deleted.
+ // 5. The trees' payload type is pointer to linked-list node. Tree-converting
+ // a bucket doesn't copy Key-Value pairs.
+ // 6. Once we've tree-converted a bucket, it is never converted back. However,
+ // the items a tree contains may wind up assigned to trees or lists upon a
+ // rehash.
+ // 7. The code requires no C++ features from C++11 or later.
+ // 8. Mutations to a map do not invalidate the map's iterators, pointers to
+ // elements, or references to elements.
+ // 9. Except for erase(iterator), any non-const method can reorder iterators.
+ class InnerMap : private hasher {
+ public:
+ typedef value_type* Value;
+
+ InnerMap(size_type n, hasher h, Allocator alloc)
+ : hasher(h),
+ num_elements_(0),
+ seed_(Seed()),
+ table_(NULL),
+ alloc_(alloc) {
+ n = TableSize(n);
+ table_ = CreateEmptyTable(n);
+ num_buckets_ = index_of_first_non_null_ = n;
+ }
+
+ ~InnerMap() {
+ if (table_ != NULL) {
+ clear();
+ Dealloc<void*>(table_, num_buckets_);
+ }
+ }
+
+ private:
+ enum { kMinTableSize = 8 };
+
+ // Linked-list nodes, as one would expect for a chaining hash table.
+ struct Node {
+ KeyValuePair kv;
+ Node* next;
+ };
+
+ // This is safe only if the given pointer is known to point to a Key that is
+ // part of a Node.
+ static Node* NodePtrFromKeyPtr(Key* k) {
+ return reinterpret_cast<Node*>(k);
+ }
+
+ static Key* KeyPtrFromNodePtr(Node* node) { return &node->kv.key(); }
+
+ // Trees. The payload type is pointer to Key, so that we can query the tree
+ // with Keys that are not in any particular data structure. When we insert,
+ // though, the pointer is always pointing to a Key that is inside a Node.
+ struct KeyCompare {
+ bool operator()(const Key* n0, const Key* n1) const { return *n0 < *n1; }
+ };
+ typedef typename Allocator::template rebind<Key*>::other KeyPtrAllocator;
+ typedef std::set<Key*, KeyCompare, KeyPtrAllocator> Tree;
+
+ // iterator and const_iterator are instantiations of iterator_base.
+ template <typename KeyValueType>
+ class iterator_base {
+ public:
+ typedef KeyValueType& reference;
+ typedef KeyValueType* pointer;
+ typedef typename Tree::iterator TreeIterator;
+
+ // Invariants:
+ // node_ is always correct. This is handy because the most common
+ // operations are operator* and operator-> and they only use node_.
+ // When node_ is set to a non-NULL value, all the other non-const fields
+ // are updated to be correct also, but those fields can become stale
+ // if the underlying map is modified. When those fields are needed they
+ // are rechecked, and updated if necessary.
+ iterator_base() : node_(NULL) {}
+
+ explicit iterator_base(const InnerMap* m) : m_(m) {
+ SearchFrom(m->index_of_first_non_null_);
+ }
+
+ // Any iterator_base can convert to any other. This is overkill, and we
+ // rely on the enclosing class to use it wisely. The standard "iterator
+ // can convert to const_iterator" is OK but the reverse direction is not.
+ template <typename U>
+ explicit iterator_base(const iterator_base<U>& it)
+ : node_(it.node_),
+ m_(it.m_),
+ bucket_index_(it.bucket_index_),
+ tree_it_(it.tree_it_) {}
+
+ iterator_base(Node* n, const InnerMap* m, size_type index)
+ : node_(n),
+ m_(m),
+ bucket_index_(index) {}
+
+ iterator_base(TreeIterator tree_it, const InnerMap* m, size_type index)
+ : node_(NodePtrFromKeyPtr(*tree_it)),
+ m_(m),
+ bucket_index_(index),
+ tree_it_(tree_it) {
+ // Invariant: iterators that use tree_it_ have an even bucket_index_.
+ GOOGLE_DCHECK_EQ(bucket_index_ % 2, 0);
+ }
+
+ // Advance through buckets, looking for the first that isn't empty.
+ // If nothing non-empty is found then leave node_ == NULL.
+ void SearchFrom(size_type start_bucket) {
+ GOOGLE_DCHECK(m_->index_of_first_non_null_ == m_->num_buckets_ ||
+ m_->table_[m_->index_of_first_non_null_] != NULL);
+ node_ = NULL;
+ for (bucket_index_ = start_bucket; bucket_index_ < m_->num_buckets_;
+ bucket_index_++) {
+ if (m_->TableEntryIsNonEmptyList(bucket_index_)) {
+ node_ = static_cast<Node*>(m_->table_[bucket_index_]);
+ break;
+ } else if (m_->TableEntryIsTree(bucket_index_)) {
+ Tree* tree = static_cast<Tree*>(m_->table_[bucket_index_]);
+ GOOGLE_DCHECK(!tree->empty());
+ tree_it_ = tree->begin();
+ node_ = NodePtrFromKeyPtr(*tree_it_);
+ break;
+ }
+ }
+ }
+
+ reference operator*() const { return node_->kv; }
+ pointer operator->() const { return &(operator*()); }
+
+ friend bool operator==(const iterator_base& a, const iterator_base& b) {
+ return a.node_ == b.node_;
+ }
+ friend bool operator!=(const iterator_base& a, const iterator_base& b) {
+ return a.node_ != b.node_;
+ }
+
+ iterator_base& operator++() {
+ if (node_->next == NULL) {
+ const bool is_list = revalidate_if_necessary();
+ if (is_list) {
+ SearchFrom(bucket_index_ + 1);
+ } else {
+ GOOGLE_DCHECK_EQ(bucket_index_ & 1, 0);
+ Tree* tree = static_cast<Tree*>(m_->table_[bucket_index_]);
+ if (++tree_it_ == tree->end()) {
+ SearchFrom(bucket_index_ + 2);
+ } else {
+ node_ = NodePtrFromKeyPtr(*tree_it_);
+ }
+ }
+ } else {
+ node_ = node_->next;
+ }
+ return *this;
+ }
+
+ iterator_base operator++(int /* unused */) {
+ iterator_base tmp = *this;
+ ++*this;
+ return tmp;
+ }
+
+ // Assumes node_ and m_ are correct and non-NULL, but other fields may be
+ // stale. Fix them as needed. Then return true iff node_ points to a
+ // Node in a list.
+ bool revalidate_if_necessary() {
+ GOOGLE_DCHECK(node_ != NULL && m_ != NULL);
+ // Force bucket_index_ to be in range.
+ bucket_index_ &= (m_->num_buckets_ - 1);
+ // Common case: the bucket we think is relevant points to node_.
+ if (m_->table_[bucket_index_] == static_cast<void*>(node_))
+ return true;
+ // Less common: the bucket is a linked list with node_ somewhere in it,
+ // but not at the head.
+ if (m_->TableEntryIsNonEmptyList(bucket_index_)) {
+ Node* l = static_cast<Node*>(m_->table_[bucket_index_]);
+ while ((l = l->next) != NULL) {
+ if (l == node_) {
+ return true;
+ }
+ }
+ }
+ // Well, bucket_index_ still might be correct, but probably
+ // not. Revalidate just to be sure. This case is rare enough that we
+ // don't worry about potential optimizations, such as having a custom
+ // find-like method that compares Node* instead of const Key&.
+ iterator_base i(m_->find(*KeyPtrFromNodePtr(node_)));
+ bucket_index_ = i.bucket_index_;
+ tree_it_ = i.tree_it_;
+ return m_->TableEntryIsList(bucket_index_);
+ }
+
+ Node* node_;
+ const InnerMap* m_;
+ size_type bucket_index_;
+ TreeIterator tree_it_;
+ };
+
+ public:
+ typedef iterator_base<KeyValuePair> iterator;
+ typedef iterator_base<const KeyValuePair> const_iterator;
+
+ iterator begin() { return iterator(this); }
+ iterator end() { return iterator(); }
+ const_iterator begin() const { return const_iterator(this); }
+ const_iterator end() const { return const_iterator(); }
+
+ void clear() {
+ for (size_type b = 0; b < num_buckets_; b++) {
+ if (TableEntryIsNonEmptyList(b)) {
+ Node* node = static_cast<Node*>(table_[b]);
+ table_[b] = NULL;
+ do {
+ Node* next = node->next;
+ DestroyNode(node);
+ node = next;
+ } while (node != NULL);
+ } else if (TableEntryIsTree(b)) {
+ Tree* tree = static_cast<Tree*>(table_[b]);
+ GOOGLE_DCHECK(table_[b] == table_[b + 1] && (b & 1) == 0);
+ table_[b] = table_[b + 1] = NULL;
+ typename Tree::iterator tree_it = tree->begin();
+ do {
+ Node* node = NodePtrFromKeyPtr(*tree_it);
+ typename Tree::iterator next = tree_it;
+ ++next;
+ tree->erase(tree_it);
+ DestroyNode(node);
+ tree_it = next;
+ } while (tree_it != tree->end());
+ DestroyTree(tree);
+ b++;
+ }
+ }
+ num_elements_ = 0;
+ index_of_first_non_null_ = num_buckets_;
+ }
+
+ const hasher& hash_function() const { return *this; }
+
+ static size_type max_size() {
+ return static_cast<size_type>(1) << (sizeof(void**) >= 8 ? 60 : 28);
+ }
+ size_type size() const { return num_elements_; }
+ bool empty() const { return size() == 0; }
+
+ iterator find(const Key& k) { return iterator(FindHelper(k).first); }
+ const_iterator find(const Key& k) const { return FindHelper(k).first; }
+
+ // In traditional C++ style, this performs "insert if not present."
+ std::pair<iterator, bool> insert(const KeyValuePair& kv) {
+ std::pair<const_iterator, size_type> p = FindHelper(kv.key());
+ // Case 1: key was already present.
+ if (p.first.node_ != NULL)
+ return std::make_pair(iterator(p.first), false);
+ // Case 2: insert.
+ if (ResizeIfLoadIsOutOfRange(num_elements_ + 1)) {
+ p = FindHelper(kv.key());
+ }
+ const size_type b = p.second; // bucket number
+ Node* node = Alloc<Node>(1);
+ alloc_.construct(&node->kv, kv);
+ iterator result = InsertUnique(b, node);
+ ++num_elements_;
+ return std::make_pair(result, true);
+ }
+
+ // The same, but if an insertion is necessary then the value portion of the
+ // inserted key-value pair is left uninitialized.
+ std::pair<iterator, bool> insert(const Key& k) {
+ std::pair<const_iterator, size_type> p = FindHelper(k);
+ // Case 1: key was already present.
+ if (p.first.node_ != NULL)
+ return std::make_pair(iterator(p.first), false);
+ // Case 2: insert.
+ if (ResizeIfLoadIsOutOfRange(num_elements_ + 1)) {
+ p = FindHelper(k);
+ }
+ const size_type b = p.second; // bucket number
+ Node* node = Alloc<Node>(1);
+ typedef typename Allocator::template rebind<Key>::other KeyAllocator;
+ KeyAllocator(alloc_).construct(&node->kv.key(), k);
+ iterator result = InsertUnique(b, node);
+ ++num_elements_;
+ return std::make_pair(result, true);
+ }
+
+ Value& operator[](const Key& k) {
+ KeyValuePair kv(k, Value());
+ return insert(kv).first->value();
+ }
+
+ void erase(iterator it) {
+ GOOGLE_DCHECK_EQ(it.m_, this);
+ const bool is_list = it.revalidate_if_necessary();
+ size_type b = it.bucket_index_;
+ Node* const item = it.node_;
+ if (is_list) {
+ GOOGLE_DCHECK(TableEntryIsNonEmptyList(b));
+ Node* head = static_cast<Node*>(table_[b]);
+ head = EraseFromLinkedList(item, head);
+ table_[b] = static_cast<void*>(head);
+ } else {
+ GOOGLE_DCHECK(TableEntryIsTree(b));
+ Tree* tree = static_cast<Tree*>(table_[b]);
+ tree->erase(it.tree_it_);
+ if (tree->empty()) {
+ // Force b to be the minimum of b and b ^ 1. This is important
+ // only because we want index_of_first_non_null_ to be correct.
+ b &= ~static_cast<size_type>(1);
+ DestroyTree(tree);
+ table_[b] = table_[b + 1] = NULL;
+ }
+ }
+ DestroyNode(item);
+ --num_elements_;
+ if (GOOGLE_PREDICT_FALSE(b == index_of_first_non_null_)) {
+ while (index_of_first_non_null_ < num_buckets_ &&
+ table_[index_of_first_non_null_] == NULL) {
+ ++index_of_first_non_null_;
+ }
+ }
+ }
+
+ private:
+ std::pair<const_iterator, size_type> FindHelper(const Key& k) const {
+ size_type b = BucketNumber(k);
+ if (TableEntryIsNonEmptyList(b)) {
+ Node* node = static_cast<Node*>(table_[b]);
+ do {
+ if (IsMatch(*KeyPtrFromNodePtr(node), k)) {
+ return std::make_pair(const_iterator(node, this, b), b);
+ } else {
+ node = node->next;
+ }
+ } while (node != NULL);
+ } else if (TableEntryIsTree(b)) {
+ GOOGLE_DCHECK_EQ(table_[b], table_[b ^ 1]);
+ b &= ~static_cast<size_t>(1);
+ Tree* tree = static_cast<Tree*>(table_[b]);
+ Key* key = const_cast<Key*>(&k);
+ typename Tree::iterator tree_it = tree->find(key);
+ if (tree_it != tree->end()) {
+ return std::make_pair(const_iterator(tree_it, this, b), b);
+ }
+ }
+ return std::make_pair(end(), b);
+ }
+
+ // Insert the given Node in bucket b. If that would make bucket b too big,
+ // and bucket b is not a tree, create a tree for buckets b and b^1 to share.
+ // Requires count(*KeyPtrFromNodePtr(node)) == 0 and that b is the correct
+ // bucket. num_elements_ is not modified.
+ iterator InsertUnique(size_type b, Node* node) {
+ GOOGLE_DCHECK(index_of_first_non_null_ == num_buckets_ ||
+ table_[index_of_first_non_null_] != NULL);
+ // In practice, the code that led to this point may have already
+ // determined whether we are inserting into an empty list, a short list,
+ // or whatever. But it's probably cheap enough to recompute that here;
+ // it's likely that we're inserting into an empty or short list.
+ iterator result;
+ GOOGLE_DCHECK(find(*KeyPtrFromNodePtr(node)) == end());
+ if (TableEntryIsEmpty(b)) {
+ result = InsertUniqueInList(b, node);
+ } else if (TableEntryIsNonEmptyList(b)) {
+ if (GOOGLE_PREDICT_FALSE(TableEntryIsTooLong(b))) {
+ TreeConvert(b);
+ result = InsertUniqueInTree(b, node);
+ GOOGLE_DCHECK_EQ(result.bucket_index_, b & ~static_cast<size_type>(1));
+ } else {
+ // Insert into a pre-existing list. This case cannot modify
+ // index_of_first_non_null_, so we skip the code to update it.
+ return InsertUniqueInList(b, node);
+ }
+ } else {
+ // Insert into a pre-existing tree. This case cannot modify
+ // index_of_first_non_null_, so we skip the code to update it.
+ return InsertUniqueInTree(b, node);
+ }
+ index_of_first_non_null_ =
+ std::min(index_of_first_non_null_, result.bucket_index_);
+ return result;
+ }
+
+ // Helper for InsertUnique. Handles the case where bucket b is a
+ // not-too-long linked list.
+ iterator InsertUniqueInList(size_type b, Node* node) {
+ node->next = static_cast<Node*>(table_[b]);
+ table_[b] = static_cast<void*>(node);
+ return iterator(node, this, b);
+ }
+
+ // Helper for InsertUnique. Handles the case where bucket b points to a
+ // Tree.
+ iterator InsertUniqueInTree(size_type b, Node* node) {
+ GOOGLE_DCHECK_EQ(table_[b], table_[b ^ 1]);
+ // Maintain the invariant that node->next is NULL for all Nodes in Trees.
+ node->next = NULL;
+ return iterator(static_cast<Tree*>(table_[b])
+ ->insert(KeyPtrFromNodePtr(node))
+ .first,
+ this, b & ~static_cast<size_t>(1));
+ }
+
+ // Returns whether it did resize. Currently this is only used when
+ // num_elements_ increases, though it could be used in other situations.
+ // It checks for load too low as well as load too high: because any number
+ // of erases can occur between inserts, the load could be as low as 0 here.
+ // Resizing to a lower size is not always helpful, but failing to do so can
+ // destroy the expected big-O bounds for some operations. By having the
+ // policy that sometimes we resize down as well as up, clients can easily
+ // keep O(size()) = O(number of buckets) if they want that.
+ bool ResizeIfLoadIsOutOfRange(size_type new_size) {
+ const size_type kMaxMapLoadTimes16 = 12; // controls RAM vs CPU tradeoff
+ const size_type hi_cutoff = num_buckets_ * kMaxMapLoadTimes16 / 16;
+ const size_type lo_cutoff = hi_cutoff / 4;
+ // We don't care how many elements are in trees. If a lot are,
+ // we may resize even though there are many empty buckets. In
+ // practice, this seems fine.
+ if (GOOGLE_PREDICT_FALSE(new_size >= hi_cutoff)) {
+ if (num_buckets_ <= max_size() / 2) {
+ Resize(num_buckets_ * 2);
+ return true;
+ }
+ } else if (GOOGLE_PREDICT_FALSE(new_size <= lo_cutoff &&
+ num_buckets_ > kMinTableSize)) {
+ size_type lg2_of_size_reduction_factor = 1;
+ // It's possible we want to shrink a lot here... size() could even be 0.
+ // So, estimate how much to shrink by making sure we don't shrink so
+ // much that we would need to grow the table after a few inserts.
+ const size_type hypothetical_size = new_size * 5 / 4 + 1;
+ while ((hypothetical_size << lg2_of_size_reduction_factor) <
+ hi_cutoff) {
+ ++lg2_of_size_reduction_factor;
+ }
+ size_type new_num_buckets = std::max<size_type>(
+ kMinTableSize, num_buckets_ >> lg2_of_size_reduction_factor);
+ if (new_num_buckets != num_buckets_) {
+ Resize(new_num_buckets);
+ return true;
+ }
+ }
+ return false;
+ }
+
+ // Resize to the given number of buckets.
+ void Resize(size_t new_num_buckets) {
+ GOOGLE_DCHECK_GE(new_num_buckets, kMinTableSize);
+ void** const old_table = table_;
+ const size_type old_table_size = num_buckets_;
+ num_buckets_ = new_num_buckets;
+ table_ = CreateEmptyTable(num_buckets_);
+ const size_type start = index_of_first_non_null_;
+ index_of_first_non_null_ = num_buckets_;
+ for (size_type i = start; i < old_table_size; i++) {
+ if (TableEntryIsNonEmptyList(old_table, i)) {
+ TransferList(old_table, i);
+ } else if (TableEntryIsTree(old_table, i)) {
+ TransferTree(old_table, i++);
+ }
+ }
+ Dealloc<void*>(old_table, old_table_size);
+ }
+
+ void TransferList(void* const* table, size_type index) {
+ Node* node = static_cast<Node*>(table[index]);
+ do {
+ Node* next = node->next;
+ InsertUnique(BucketNumber(*KeyPtrFromNodePtr(node)), node);
+ node = next;
+ } while (node != NULL);
+ }
+
+ void TransferTree(void* const* table, size_type index) {
+ Tree* tree = static_cast<Tree*>(table[index]);
+ typename Tree::iterator tree_it = tree->begin();
+ do {
+ Node* node = NodePtrFromKeyPtr(*tree_it);
+ InsertUnique(BucketNumber(**tree_it), node);
+ } while (++tree_it != tree->end());
+ DestroyTree(tree);
+ }
+
+ Node* EraseFromLinkedList(Node* item, Node* head) {
+ if (head == item) {
+ return head->next;
+ } else {
+ head->next = EraseFromLinkedList(item, head->next);
+ return head;
+ }
+ }
+
+ bool TableEntryIsEmpty(size_type b) const {
+ return TableEntryIsEmpty(table_, b);
+ }
+ bool TableEntryIsNonEmptyList(size_type b) const {
+ return TableEntryIsNonEmptyList(table_, b);
+ }
+ bool TableEntryIsTree(size_type b) const {
+ return TableEntryIsTree(table_, b);
+ }
+ bool TableEntryIsList(size_type b) const {
+ return TableEntryIsList(table_, b);
+ }
+ static bool TableEntryIsEmpty(void* const* table, size_type b) {
+ return table[b] == NULL;
+ }
+ static bool TableEntryIsNonEmptyList(void* const* table, size_type b) {
+ return table[b] != NULL && table[b] != table[b ^ 1];
+ }
+ static bool TableEntryIsTree(void* const* table, size_type b) {
+ return !TableEntryIsEmpty(table, b) &&
+ !TableEntryIsNonEmptyList(table, b);
+ }
+ static bool TableEntryIsList(void* const* table, size_type b) {
+ return !TableEntryIsTree(table, b);
+ }
+
+ void TreeConvert(size_type b) {
+ GOOGLE_DCHECK(!TableEntryIsTree(b) && !TableEntryIsTree(b ^ 1));
+ typename Allocator::template rebind<Tree>::other tree_allocator(alloc_);
+ Tree* tree = tree_allocator.allocate(1);
+ // We want to use the three-arg form of construct, if it exists, but we
+ // create a temporary and use the two-arg construct that's known to exist.
+ // It's clunky, but the compiler should be able to generate more-or-less
+ // the same code.
+ tree_allocator.construct(tree,
+ Tree(KeyCompare(), KeyPtrAllocator(alloc_)));
+ // Now the tree is ready to use.
+ size_type count = CopyListToTree(b, tree) + CopyListToTree(b ^ 1, tree);
+ GOOGLE_DCHECK_EQ(count, tree->size());
+ table_[b] = table_[b ^ 1] = static_cast<void*>(tree);
+ }
+
+ // Copy a linked list in the given bucket to a tree.
+ // Returns the number of things it copied.
+ size_type CopyListToTree(size_type b, Tree* tree) {
+ size_type count = 0;
+ Node* node = static_cast<Node*>(table_[b]);
+ while (node != NULL) {
+ tree->insert(KeyPtrFromNodePtr(node));
+ ++count;
+ Node* next = node->next;
+ node->next = NULL;
+ node = next;
+ }
+ return count;
+ }
+
+ // Return whether table_[b] is a linked list that seems awfully long.
+ // Requires table_[b] to point to a non-empty linked list.
+ bool TableEntryIsTooLong(size_type b) {
+ const size_type kMaxLength = 8;
+ size_type count = 0;
+ Node* node = static_cast<Node*>(table_[b]);
+ do {
+ ++count;
+ node = node->next;
+ } while (node != NULL);
+ // Invariant: no linked list ever is more than kMaxLength in length.
+ GOOGLE_DCHECK_LE(count, kMaxLength);
+ return count >= kMaxLength;
+ }
+
+ size_type BucketNumber(const Key& k) const {
+ // We inherit from hasher, so one-arg operator() provides a hash function.
+ size_type h = (*const_cast<InnerMap*>(this))(k);
+ // To help prevent people from making assumptions about the hash function,
+ // we use the seed differently depending on NDEBUG. The default hash
+ // function, the seeding, etc., are all likely to change in the future.
+#ifndef NDEBUG
+ return (h * (seed_ | 1)) & (num_buckets_ - 1);
+#else
+ return (h + seed_) & (num_buckets_ - 1);
+#endif
+ }
+
+ bool IsMatch(const Key& k0, const Key& k1) const {
+ return std::equal_to<Key>()(k0, k1);
+ }
+
+ // Return a power of two no less than max(kMinTableSize, n).
+ // Assumes either n < kMinTableSize or n is a power of two.
+ size_type TableSize(size_type n) {
+ return n < kMinTableSize ? kMinTableSize : n;
+ }
+
+ // Use alloc_ to allocate an array of n objects of type U.
+ template <typename U>
+ U* Alloc(size_type n) {
+ typedef typename Allocator::template rebind<U>::other alloc_type;
+ return alloc_type(alloc_).allocate(n);
+ }
+
+ // Use alloc_ to deallocate an array of n objects of type U.
+ template <typename U>
+ void Dealloc(U* t, size_type n) {
+ typedef typename Allocator::template rebind<U>::other alloc_type;
+ alloc_type(alloc_).deallocate(t, n);
+ }
+
+ void DestroyNode(Node* node) {
+ alloc_.destroy(&node->kv);
+ Dealloc<Node>(node, 1);
+ }
+
+ void DestroyTree(Tree* tree) {
+ typename Allocator::template rebind<Tree>::other tree_allocator(alloc_);
+ tree_allocator.destroy(tree);
+ tree_allocator.deallocate(tree, 1);
+ }
+
+ void** CreateEmptyTable(size_type n) {
+ GOOGLE_DCHECK(n >= kMinTableSize);
+ GOOGLE_DCHECK_EQ(n & (n - 1), 0);
+ void** result = Alloc<void*>(n);
+ memset(result, 0, n * sizeof(result[0]));
+ return result;
+ }
+
+ // Return a randomish value.
+ size_type Seed() const {
+ // random_device can throw, so avoid it unless we are compiling with
+ // exceptions enabled.
+#if __cpp_exceptions && LANG_CXX11
+ try {
+ std::random_device rd;
+ std::knuth_b knuth(rd());
+ std::uniform_int_distribution<size_type> u;
+ return u(knuth);
+ } catch (...) { }
+#endif
+ size_type s = static_cast<size_type>(reinterpret_cast<uintptr_t>(this));
+#if defined(__x86_64__) && defined(__GNUC__)
+ uint32 hi, lo;
+ asm("rdtsc" : "=a" (lo), "=d" (hi));
+ s += ((static_cast<uint64>(hi) << 32) | lo);
+#endif
+ return s;
+ }
+
+ size_type num_elements_;
+ size_type num_buckets_;
+ size_type seed_;
+ size_type index_of_first_non_null_;
+ void** table_; // an array with num_buckets_ entries
+ Allocator alloc_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(InnerMap);
+ }; // end of class InnerMap
+
+ typedef hash_map<Key, value_type*, hash<Key>, equal_to<Key>,
+ MapAllocator<std::pair<const Key, MapPair<Key, T>*> > >
+ DeprecatedInnerMap;
+
+ public:
+ // Iterators
+ class iterator_base {
+ public:
+ // We support "old style" and "new style" iterators for now. This is
+ // temporary. Also, for "iterator()" we have an unknown category.
+ // TODO(gpike): get rid of this.
+ enum IteratorStyle { kUnknown, kOld, kNew };
+ explicit iterator_base(IteratorStyle style) : iterator_style_(style) {}
+
+ bool OldStyle() const {
+ GOOGLE_DCHECK_NE(iterator_style_, kUnknown);
+ return iterator_style_ == kOld;
+ }
+ bool UnknownStyle() const {
+ return iterator_style_ == kUnknown;
+ }
+ bool SameStyle(const iterator_base& other) const {
+ return iterator_style_ == other.iterator_style_;
+ }
+
+ private:
+ IteratorStyle iterator_style_;
+ };
+
+ class const_iterator
+ : private iterator_base,
+ public std::iterator<std::forward_iterator_tag, value_type, ptrdiff_t,
+ const value_type*, const value_type&> {
+ typedef typename InnerMap::const_iterator InnerIt;
+ typedef typename DeprecatedInnerMap::const_iterator DeprecatedInnerIt;
+
+ public:
+ const_iterator() : iterator_base(iterator_base::kUnknown) {}
+ explicit const_iterator(const DeprecatedInnerIt& dit)
+ : iterator_base(iterator_base::kOld), dit_(dit) {}
+ explicit const_iterator(const InnerIt& it)
+ : iterator_base(iterator_base::kNew), it_(it) {}
+
+ const_iterator(const const_iterator& other)
+ : iterator_base(other), it_(other.it_), dit_(other.dit_) {}
+
+ const_reference operator*() const {
+ return this->OldStyle() ? *dit_->second : *it_->value();
+ }
+ const_pointer operator->() const { return &(operator*()); }
+
+ const_iterator& operator++() {
+ if (this->OldStyle())
+ ++dit_;
+ else
+ ++it_;
+ return *this;
+ }
+ const_iterator operator++(int) {
+ return this->OldStyle() ? const_iterator(dit_++) : const_iterator(it_++);
+ }
+
+ friend bool operator==(const const_iterator& a, const const_iterator& b) {
+ if (!a.SameStyle(b)) return false;
+ if (a.UnknownStyle()) return true;
+ return a.OldStyle() ? (a.dit_ == b.dit_) : (a.it_ == b.it_);
+ }
+ friend bool operator!=(const const_iterator& a, const const_iterator& b) {
+ return !(a == b);
+ }
+
+ private:
+ InnerIt it_;
+ DeprecatedInnerIt dit_;
+ };
+
+ class iterator : private iterator_base,
+ public std::iterator<std::forward_iterator_tag, value_type> {
+ typedef typename InnerMap::iterator InnerIt;
+ typedef typename DeprecatedInnerMap::iterator DeprecatedInnerIt;
+
+ public:
+ iterator() : iterator_base(iterator_base::kUnknown) {}
+ explicit iterator(const DeprecatedInnerIt& dit)
+ : iterator_base(iterator_base::kOld), dit_(dit) {}
+ explicit iterator(const InnerIt& it)
+ : iterator_base(iterator_base::kNew), it_(it) {}
+
+ reference operator*() const {
+ return this->OldStyle() ? *dit_->second : *it_->value();
+ }
+ pointer operator->() const { return &(operator*()); }
+
+ iterator& operator++() {
+ if (this->OldStyle())
+ ++dit_;
+ else
+ ++it_;
+ return *this;
+ }
+ iterator operator++(int) {
+ return this->OldStyle() ? iterator(dit_++) : iterator(it_++);
+ }
+
+ // Allow implicit conversion to const_iterator.
+ operator const_iterator() const {
+ return this->OldStyle() ?
+ const_iterator(typename DeprecatedInnerMap::const_iterator(dit_)) :
+ const_iterator(typename InnerMap::const_iterator(it_));
+ }
+
+ friend bool operator==(const iterator& a, const iterator& b) {
+ if (!a.SameStyle(b)) return false;
+ if (a.UnknownStyle()) return true;
+ return a.OldStyle() ? a.dit_ == b.dit_ : a.it_ == b.it_;
+ }
+ friend bool operator!=(const iterator& a, const iterator& b) {
+ return !(a == b);
+ }
+
+ private:
+ friend class Map;
+
+ InnerIt it_;
+ DeprecatedInnerIt dit_;
+ };
+
+ iterator begin() {
+ return old_style_ ? iterator(deprecated_elements_->begin())
+ : iterator(elements_->begin());
+ }
+ iterator end() {
+ return old_style_ ? iterator(deprecated_elements_->end())
+ : iterator(elements_->end());
+ }
+ const_iterator begin() const {
+ return old_style_ ? const_iterator(deprecated_elements_->begin())
+ : const_iterator(iterator(elements_->begin()));
+ }
+ const_iterator end() const {
+ return old_style_ ? const_iterator(deprecated_elements_->end())
+ : const_iterator(iterator(elements_->end()));
+ }
+ const_iterator cbegin() const { return begin(); }
+ const_iterator cend() const { return end(); }
+
+ // Capacity
+ size_type size() const {
+ return old_style_ ? deprecated_elements_->size() : elements_->size();
+ }
+ bool empty() const { return size() == 0; }
+
+ // Element access
+ T& operator[](const key_type& key) {
+ value_type** value =
+ old_style_ ? &(*deprecated_elements_)[key] : &(*elements_)[key];
+ if (*value == NULL) {
+ *value = CreateValueTypeInternal(key);
+ internal::MapValueInitializer<google::protobuf::is_proto_enum<T>::value,
+ T>::Initialize((*value)->second,
+ default_enum_value_);
+ }
+ return (*value)->second;
+ }
+ const T& at(const key_type& key) const {
+ const_iterator it = find(key);
+ GOOGLE_CHECK(it != end());
+ return it->second;
+ }
+ T& at(const key_type& key) {
+ iterator it = find(key);
+ GOOGLE_CHECK(it != end());
+ return it->second;
+ }
+
+ // Lookup
+ size_type count(const key_type& key) const {
+ if (find(key) != end()) assert(key == find(key)->first);
+ return find(key) == end() ? 0 : 1;
+ }
+ const_iterator find(const key_type& key) const {
+ return old_style_ ? const_iterator(deprecated_elements_->find(key))
+ : const_iterator(iterator(elements_->find(key)));
+ }
+ iterator find(const key_type& key) {
+ return old_style_ ? iterator(deprecated_elements_->find(key))
+ : iterator(elements_->find(key));
+ }
+ std::pair<const_iterator, const_iterator> equal_range(
+ const key_type& key) const {
+ const_iterator it = find(key);
+ if (it == end()) {
+ return std::pair<const_iterator, const_iterator>(it, it);
+ } else {
+ const_iterator begin = it++;
+ return std::pair<const_iterator, const_iterator>(begin, it);
+ }
+ }
+ std::pair<iterator, iterator> equal_range(const key_type& key) {
+ iterator it = find(key);
+ if (it == end()) {
+ return std::pair<iterator, iterator>(it, it);
+ } else {
+ iterator begin = it++;
+ return std::pair<iterator, iterator>(begin, it);
+ }
+ }
+
+ // insert
+ std::pair<iterator, bool> insert(const value_type& value) {
+ if (old_style_) {
+ iterator it = find(value.first);
+ if (it != end()) {
+ return std::pair<iterator, bool>(it, false);
+ } else {
+ return std::pair<iterator, bool>(
+ iterator(deprecated_elements_->insert(std::pair<Key, value_type*>(
+ value.first, CreateValueTypeInternal(value))).first), true);
+ }
+ } else {
+ std::pair<typename InnerMap::iterator, bool> p =
+ elements_->insert(value.first);
+ if (p.second) {
+ p.first->value() = CreateValueTypeInternal(value);
+ }
+ return std::pair<iterator, bool>(iterator(p.first), p.second);
+ }
+ }
+ template <class InputIt>
+ void insert(InputIt first, InputIt last) {
+ for (InputIt it = first; it != last; ++it) {
+ iterator exist_it = find(it->first);
+ if (exist_it == end()) {
+ operator[](it->first) = it->second;
+ }
+ }
+ }
+
+ // Erase and clear
+ size_type erase(const key_type& key) {
+ iterator it = find(key);
+ if (it == end()) {
+ return 0;
+ } else {
+ erase(it);
+ return 1;
+ }
+ }
+ iterator erase(iterator pos) {
+ if (arena_ == NULL) delete pos.operator->();
+ iterator i = pos++;
+ if (old_style_)
+ deprecated_elements_->erase(i.dit_);
+ else
+ elements_->erase(i.it_);
+ return pos;
+ }
+ void erase(iterator first, iterator last) {
+ while (first != last) {
+ first = erase(first);
+ }
+ }
+ void clear() { erase(begin(), end()); }
+
+ // Assign
+ Map& operator=(const Map& other) {
+ if (this != &other) {
+ clear();
+ insert(other.begin(), other.end());
+ }
+ return *this;
+ }
+
+ void swap(Map& other) {
+ if (arena_ == other.arena_ && old_style_ == other.old_style_) {
+ std::swap(default_enum_value_, other.default_enum_value_);
+ if (old_style_) {
+ std::swap(deprecated_elements_, other.deprecated_elements_);
+ } else {
+ std::swap(elements_, other.elements_);
+ }
+ } else {
+ // TODO(zuguang): optimize this. The temporary copy can be allocated
+ // in the same arena as the other message, and the "other = copy" can
+ // be replaced with the fast-path swap above.
+ Map copy = *this;
+ *this = other;
+ other = copy;
+ }
+ }
+
+ // Access to hasher. Currently this returns a copy, but it may
+ // be modified to return a const reference in the future.
+ hasher hash_function() const {
+ return old_style_ ? deprecated_elements_->hash_function()
+ : elements_->hash_function();
+ }
+
+ private:
+ // Set default enum value only for proto2 map field whose value is enum type.
+ void SetDefaultEnumValue(int default_enum_value) {
+ default_enum_value_ = default_enum_value;
+ }
+
+ value_type* CreateValueTypeInternal(const Key& key) {
+ if (arena_ == NULL) {
+ return new value_type(key);
+ } else {
+ value_type* value = reinterpret_cast<value_type*>(
+ Arena::CreateArray<uint8>(arena_, sizeof(value_type)));
+ Arena::CreateInArenaStorage(const_cast<Key*>(&value->first), arena_);
+ Arena::CreateInArenaStorage(&value->second, arena_);
+ const_cast<Key&>(value->first) = key;
+ return value;
+ }
+ }
+
+ value_type* CreateValueTypeInternal(const value_type& value) {
+ if (arena_ == NULL) {
+ return new value_type(value);
+ } else {
+ value_type* p = reinterpret_cast<value_type*>(
+ Arena::CreateArray<uint8>(arena_, sizeof(value_type)));
+ Arena::CreateInArenaStorage(const_cast<Key*>(&p->first), arena_);
+ Arena::CreateInArenaStorage(&p->second, arena_);
+ const_cast<Key&>(p->first) = value.first;
+ p->second = value.second;
+ return p;
+ }
+ }
+
+ Arena* arena_;
+ int default_enum_value_;
+ // The following is a tagged union because we support two map styles
+ // for now.
+ // TODO(gpike): get rid of the old style.
+ const bool old_style_;
+ union {
+ InnerMap* elements_;
+ DeprecatedInnerMap* deprecated_elements_;
+ };
+
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ template <typename K, typename V,
+ internal::WireFormatLite::FieldType key_wire_type,
+ internal::WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+ friend class internal::MapFieldLite;
+};
+
+} // namespace protobuf
+} // namespace google
+
+GOOGLE_PROTOBUF_HASH_NAMESPACE_DECLARATION_START
+template<>
+struct hash<google::protobuf::MapKey> {
+ size_t
+ operator()(const google::protobuf::MapKey& map_key) const {
+ switch (map_key.type()) {
+ case google::protobuf::FieldDescriptor::CPPTYPE_DOUBLE:
+ case google::protobuf::FieldDescriptor::CPPTYPE_FLOAT:
+ case google::protobuf::FieldDescriptor::CPPTYPE_ENUM:
+ case google::protobuf::FieldDescriptor::CPPTYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Unsupported";
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_STRING:
+ return hash<string>()(map_key.GetStringValue());
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT64:
+ return hash< ::google::protobuf::int64>()(map_key.GetInt64Value());
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT32:
+ return hash< ::google::protobuf::int32>()(map_key.GetInt32Value());
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT64:
+ return hash< ::google::protobuf::uint64>()(map_key.GetUInt64Value());
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT32:
+ return hash< ::google::protobuf::uint32>()(map_key.GetUInt32Value());
+ case google::protobuf::FieldDescriptor::CPPTYPE_BOOL:
+ return hash<bool>()(map_key.GetBoolValue());
+ }
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ return 0;
+ }
+ bool
+ operator()(const google::protobuf::MapKey& map_key1,
+ const google::protobuf::MapKey& map_key2) const {
+ return map_key1 < map_key2;
+ }
+};
+GOOGLE_PROTOBUF_HASH_NAMESPACE_DECLARATION_END
+
+#endif // GOOGLE_PROTOBUF_MAP_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_entry.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_entry.h
new file mode 100644
index 0000000000..e87eda6498
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_entry.h
@@ -0,0 +1,310 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_ENTRY_H__
+#define GOOGLE_PROTOBUF_MAP_ENTRY_H__
+
+#include <google/protobuf/generated_message_reflection.h>
+#include <google/protobuf/map_entry_lite.h>
+#include <google/protobuf/map_type_handler.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/reflection_ops.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+
+namespace google {
+namespace protobuf {
+class Arena;
+namespace internal {
+template <typename Key, typename Value,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+class MapField;
+}
+}
+
+namespace protobuf {
+namespace internal {
+
+// Register all MapEntry default instances so we can delete them in
+// ShutdownProtobufLibrary().
+void LIBPROTOBUF_EXPORT RegisterMapEntryDefaultInstance(
+ MessageLite* default_instance);
+
+// This is the common base class for MapEntry. It is used by MapFieldBase in
+// reflection api, in which the static type of key and value is unknown.
+class LIBPROTOBUF_EXPORT MapEntryBase : public Message {
+ public:
+ ::google::protobuf::Metadata GetMetadata() const {
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = descriptor_;
+ metadata.reflection = reflection_;
+ return metadata;
+ }
+
+ protected:
+ MapEntryBase() : descriptor_(NULL), reflection_(NULL) { }
+ virtual ~MapEntryBase() {}
+
+ const Descriptor* descriptor_;
+ const Reflection* reflection_;
+};
+
+// MapEntry is the returned google::protobuf::Message when calling AddMessage of
+// google::protobuf::Reflection. In order to let it work with generated message
+// reflection, its in-memory type is the same as generated message with the same
+// fields. However, in order to decide the in-memory type of key/value, we need
+// to know both their cpp type in generated api and proto type. In
+// implementation, all in-memory types have related wire format functions to
+// support except ArenaStringPtr. Therefore, we need to define another type with
+// supporting wire format functions. Since this type is only used as return type
+// of MapEntry accessors, it's named MapEntry accessor type.
+//
+// cpp type: the type visible to users in public API.
+// proto type: WireFormatLite::FieldType of the field.
+// in-memory type: type of the data member used to stored this field.
+// MapEntry accessor type: type used in MapEntry getters/mutators to access the
+// field.
+//
+// cpp type | proto type | in-memory type | MapEntry accessor type
+// int32 TYPE_INT32 int32 int32
+// int32 TYPE_FIXED32 int32 int32
+// string TYPE_STRING ArenaStringPtr string
+// FooEnum TYPE_ENUM int int
+// FooMessage TYPE_MESSAGE FooMessage* FooMessage
+//
+// The in-memory types of primitive types can be inferred from its proto type,
+// while we need to explicitly specify the cpp type if proto type is
+// TYPE_MESSAGE to infer the in-memory type. Moreover, default_enum_value is
+// used to initialize enum field in proto2.
+template <typename Key, typename Value,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+class MapEntry : public MapEntryBase {
+ // Provide utilities to parse/serialize key/value. Provide utilities to
+ // manipulate internal stored type.
+ typedef MapTypeHandler<kKeyFieldType, Key> KeyTypeHandler;
+ typedef MapTypeHandler<kValueFieldType, Value> ValueTypeHandler;
+
+ // Enum type cannot be used for MapTypeHandler::Read. Define a type
+ // which will replace Enum with int.
+ typedef typename KeyTypeHandler::MapEntryAccessorType KeyMapEntryAccessorType;
+ typedef typename ValueTypeHandler::MapEntryAccessorType
+ ValueMapEntryAccessorType;
+
+ // Abbreviation for MapEntry
+ typedef typename google::protobuf::internal::MapEntry<
+ Key, Value, kKeyFieldType, kValueFieldType, default_enum_value> EntryType;
+
+ // Abbreviation for MapEntryLite
+ typedef typename google::protobuf::internal::MapEntryLite<
+ Key, Value, kKeyFieldType, kValueFieldType, default_enum_value>
+ EntryLiteType;
+
+ public:
+ ~MapEntry() {
+ if (this == default_instance_) {
+ delete reflection_;
+ }
+ }
+
+ // accessors ======================================================
+
+ virtual inline const KeyMapEntryAccessorType& key() const {
+ return entry_lite_.key();
+ }
+ inline KeyMapEntryAccessorType* mutable_key() {
+ return entry_lite_.mutable_key();
+ }
+ virtual inline const ValueMapEntryAccessorType& value() const {
+ return entry_lite_.value();
+ }
+ inline ValueMapEntryAccessorType* mutable_value() {
+ return entry_lite_.mutable_value();
+ }
+
+ // implements Message =============================================
+
+ bool MergePartialFromCodedStream(::google::protobuf::io::CodedInputStream* input) {
+ return entry_lite_.MergePartialFromCodedStream(input);
+ }
+
+ int ByteSize() const {
+ return entry_lite_.ByteSize();
+ }
+
+ void SerializeWithCachedSizes(::google::protobuf::io::CodedOutputStream* output) const {
+ entry_lite_.SerializeWithCachedSizes(output);
+ }
+
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(bool deterministic,
+ ::google::protobuf::uint8* output) const {
+ return entry_lite_.InternalSerializeWithCachedSizesToArray(deterministic,
+ output);
+ }
+
+ int GetCachedSize() const {
+ return entry_lite_.GetCachedSize();
+ }
+
+ bool IsInitialized() const {
+ return entry_lite_.IsInitialized();
+ }
+
+ Message* New() const {
+ MapEntry* entry = new MapEntry;
+ entry->descriptor_ = descriptor_;
+ entry->reflection_ = reflection_;
+ entry->set_default_instance(default_instance_);
+ return entry;
+ }
+
+ Message* New(Arena* arena) const {
+ MapEntry* entry = Arena::CreateMessage<MapEntry>(arena);
+ entry->descriptor_ = descriptor_;
+ entry->reflection_ = reflection_;
+ entry->set_default_instance(default_instance_);
+ return entry;
+ }
+
+ int SpaceUsed() const {
+ int size = sizeof(MapEntry);
+ size += entry_lite_.SpaceUsed();
+ return size;
+ }
+
+ void CopyFrom(const ::google::protobuf::Message& from) {
+ Clear();
+ MergeFrom(from);
+ }
+
+ void MergeFrom(const ::google::protobuf::Message& from) {
+ GOOGLE_CHECK_NE(&from, this);
+ const MapEntry* source = dynamic_cast_if_available<const MapEntry*>(&from);
+ if (source == NULL) {
+ ReflectionOps::Merge(from, this);
+ } else {
+ MergeFrom(*source);
+ }
+ }
+
+ void CopyFrom(const MapEntry& from) {
+ Clear();
+ MergeFrom(from);
+ }
+
+ void MergeFrom(const MapEntry& from) {
+ entry_lite_.MergeFrom(from.entry_lite_);
+ }
+
+ void Clear() {
+ entry_lite_.Clear();
+ }
+
+ void InitAsDefaultInstance() {
+ entry_lite_.InitAsDefaultInstance();
+ }
+
+ Arena* GetArena() const {
+ return entry_lite_.GetArena();
+ }
+
+ // Create default MapEntry instance for given descriptor. Descriptor has to be
+ // given when creating default MapEntry instance because different map field
+ // may have the same type and MapEntry class. The given descriptor is needed
+ // to distinguish instances of the same MapEntry class.
+ static MapEntry* CreateDefaultInstance(const Descriptor* descriptor) {
+ MapEntry* entry = new MapEntry;
+ const Reflection* reflection = new GeneratedMessageReflection(
+ descriptor, entry, offsets_,
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MapEntry, entry_lite_._has_bits_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MapEntry, _unknown_fields_), -1,
+ DescriptorPool::generated_pool(),
+ ::google::protobuf::MessageFactory::generated_factory(),
+ sizeof(MapEntry),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MapEntry, _internal_metadata_));
+ entry->descriptor_ = descriptor;
+ entry->reflection_ = reflection;
+ entry->set_default_instance(entry);
+ entry->InitAsDefaultInstance();
+ RegisterMapEntryDefaultInstance(entry);
+ return entry;
+ }
+
+ private:
+ MapEntry()
+ : _internal_metadata_(NULL), default_instance_(NULL), entry_lite_() {}
+
+ explicit MapEntry(Arena* arena)
+ : _internal_metadata_(arena),
+ default_instance_(NULL),
+ entry_lite_(arena) {}
+
+ inline Arena* GetArenaNoVirtual() const {
+ return entry_lite_.GetArenaNoVirtual();
+ }
+
+ void set_default_instance(MapEntry* default_instance) {
+ default_instance_ = default_instance;
+ entry_lite_.set_default_instance(&default_instance->entry_lite_);
+ }
+
+ static int offsets_[2];
+ UnknownFieldSet _unknown_fields_;
+ InternalMetadataWithArena _internal_metadata_;
+ MapEntry* default_instance_;
+ EntryLiteType entry_lite_;
+
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ template <typename K, typename V, WireFormatLite::FieldType k_wire_type,
+ WireFormatLite::FieldType, int default_enum>
+ friend class internal::MapField;
+ friend class internal::GeneratedMessageReflection;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MapEntry);
+};
+
+template <typename Key, typename Value, WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType, int default_enum_value>
+int MapEntry<Key, Value, kKeyFieldType, kValueFieldType,
+ default_enum_value>::offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MapEntry, entry_lite_.key_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(MapEntry, entry_lite_.value_),
+};
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_ENTRY_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_entry_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_entry_lite.h
new file mode 100644
index 0000000000..4dedfd5702
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_entry_lite.h
@@ -0,0 +1,568 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_ENTRY_LITE_H__
+#define GOOGLE_PROTOBUF_MAP_ENTRY_LITE_H__
+
+#include <assert.h>
+#include <google/protobuf/map_type_handler.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+
+namespace google {
+namespace protobuf {
+class Arena;
+namespace internal {
+template <typename Key, typename Value,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+class MapEntry;
+template <typename Key, typename Value,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+class MapFieldLite;
+} // namespace internal
+} // namespace protobuf
+
+namespace protobuf {
+namespace internal {
+
+// MoveHelper::Move is used to set *dest. It copies *src, or moves it (in
+// the C++11 sense), or swaps it. *src is left in a sane state for
+// subsequent destruction, but shouldn't be used for anything.
+template <bool is_enum, bool is_message, bool is_stringlike, typename T>
+struct MoveHelper { // primitives
+ static void Move(T* src, T* dest) { *dest = *src; }
+};
+
+template <bool is_message, bool is_stringlike, typename T>
+struct MoveHelper<true, is_message, is_stringlike, T> { // enums
+ static void Move(T* src, T* dest) { *dest = *src; }
+ // T is an enum here, so allow conversions to and from int.
+ static void Move(T* src, int* dest) { *dest = static_cast<int>(*src); }
+ static void Move(int* src, T* dest) { *dest = static_cast<T>(*src); }
+};
+
+template <bool is_stringlike, typename T>
+struct MoveHelper<false, true, is_stringlike, T> { // messages
+ static void Move(T* src, T* dest) { dest->Swap(src); }
+};
+
+template <typename T>
+struct MoveHelper<false, false, true, T> { // strings and similar
+ static void Move(T* src, T* dest) {
+#if __cplusplus >= 201103L
+ *dest = std::move(*src);
+#else
+ dest->swap(*src);
+#endif
+ }
+};
+
+// MapEntryLite is used to implement parsing and serialization of map for lite
+// runtime.
+template <typename Key, typename Value,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+class MapEntryLite : public MessageLite {
+ // Provide utilities to parse/serialize key/value. Provide utilities to
+ // manipulate internal stored type.
+ typedef MapTypeHandler<kKeyFieldType, Key> KeyTypeHandler;
+ typedef MapTypeHandler<kValueFieldType, Value> ValueTypeHandler;
+
+ // Define internal memory layout. Strings and messages are stored as
+ // pointers, while other types are stored as values.
+ typedef typename KeyTypeHandler::TypeOnMemory KeyOnMemory;
+ typedef typename ValueTypeHandler::TypeOnMemory ValueOnMemory;
+
+ // Enum type cannot be used for MapTypeHandler::Read. Define a type
+ // which will replace Enum with int.
+ typedef typename KeyTypeHandler::MapEntryAccessorType KeyMapEntryAccessorType;
+ typedef typename ValueTypeHandler::MapEntryAccessorType
+ ValueMapEntryAccessorType;
+
+ // Constants for field number.
+ static const int kKeyFieldNumber = 1;
+ static const int kValueFieldNumber = 2;
+
+ // Constants for field tag.
+ static const uint8 kKeyTag = GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(
+ kKeyFieldNumber, KeyTypeHandler::kWireType);
+ static const uint8 kValueTag = GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(
+ kValueFieldNumber, ValueTypeHandler::kWireType);
+ static const int kTagSize = 1;
+
+ public:
+ ~MapEntryLite() {
+ if (this != default_instance_) {
+ if (GetArenaNoVirtual() != NULL) return;
+ KeyTypeHandler::DeleteNoArena(key_);
+ ValueTypeHandler::DeleteNoArena(value_);
+ }
+ }
+
+ // accessors ======================================================
+
+ virtual inline const KeyMapEntryAccessorType& key() const {
+ return KeyTypeHandler::GetExternalReference(key_);
+ }
+ virtual inline const ValueMapEntryAccessorType& value() const {
+ GOOGLE_CHECK(default_instance_ != NULL);
+ return ValueTypeHandler::DefaultIfNotInitialized(value_,
+ default_instance_->value_);
+ }
+ inline KeyMapEntryAccessorType* mutable_key() {
+ set_has_key();
+ return KeyTypeHandler::EnsureMutable(&key_, GetArenaNoVirtual());
+ }
+ inline ValueMapEntryAccessorType* mutable_value() {
+ set_has_value();
+ return ValueTypeHandler::EnsureMutable(&value_, GetArenaNoVirtual());
+ }
+
+ // implements MessageLite =========================================
+
+ // MapEntryLite is for implementation only and this function isn't called
+ // anywhere. Just provide a fake implementation here for MessageLite.
+ string GetTypeName() const { return ""; }
+
+ void CheckTypeAndMergeFrom(const MessageLite& other) {
+ MergeFrom(*::google::protobuf::down_cast<const MapEntryLite*>(&other));
+ }
+
+ bool MergePartialFromCodedStream(::google::protobuf::io::CodedInputStream* input) {
+ uint32 tag;
+
+ for (;;) {
+ // 1) corrupted data: return false;
+ // 2) unknown field: skip without putting into unknown field set;
+ // 3) unknown enum value: keep it in parsing. In proto2, caller should
+ // check the value and put this entry into containing message's unknown
+ // field set if the value is an unknown enum. In proto3, caller doesn't
+ // need to care whether the value is unknown enum;
+ // 4) missing key/value: missed key/value will have default value. caller
+ // should take this entry as if key/value is set to default value.
+ tag = input->ReadTag();
+ switch (tag) {
+ case kKeyTag:
+ if (!KeyTypeHandler::Read(input, mutable_key())) {
+ return false;
+ }
+ set_has_key();
+ if (!input->ExpectTag(kValueTag)) break;
+ GOOGLE_FALLTHROUGH_INTENDED;
+
+ case kValueTag:
+ if (!ValueTypeHandler::Read(input, mutable_value())) {
+ return false;
+ }
+ set_has_value();
+ if (input->ExpectAtEnd()) return true;
+ break;
+
+ default:
+ if (tag == 0 ||
+ WireFormatLite::GetTagWireType(tag) ==
+ WireFormatLite::WIRETYPE_END_GROUP) {
+ return true;
+ }
+ if (!WireFormatLite::SkipField(input, tag)) return false;
+ break;
+ }
+ }
+ }
+
+ int ByteSize() const {
+ int size = 0;
+ size += has_key() ? kTagSize + KeyTypeHandler::ByteSize(key()) : 0;
+ size += has_value() ? kTagSize + ValueTypeHandler::ByteSize(value()) : 0;
+ return size;
+ }
+
+ void SerializeWithCachedSizes(::google::protobuf::io::CodedOutputStream* output) const {
+ KeyTypeHandler::Write(kKeyFieldNumber, key(), output);
+ ValueTypeHandler::Write(kValueFieldNumber, value(), output);
+ }
+
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(bool deterministic,
+ ::google::protobuf::uint8* output) const {
+ output = KeyTypeHandler::InternalWriteToArray(kKeyFieldNumber, key(),
+ deterministic, output);
+ output = ValueTypeHandler::InternalWriteToArray(kValueFieldNumber, value(),
+ deterministic, output);
+ return output;
+ }
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+
+ int GetCachedSize() const {
+ int size = 0;
+ size += has_key()
+ ? kTagSize + KeyTypeHandler::GetCachedSize(key())
+ : 0;
+ size += has_value()
+ ? kTagSize + ValueTypeHandler::GetCachedSize(
+ value())
+ : 0;
+ return size;
+ }
+
+ bool IsInitialized() const { return ValueTypeHandler::IsInitialized(value_); }
+
+ MessageLite* New() const {
+ MapEntryLite* entry = new MapEntryLite;
+ entry->default_instance_ = default_instance_;
+ return entry;
+ }
+
+ MessageLite* New(Arena* arena) const {
+ MapEntryLite* entry = Arena::CreateMessage<MapEntryLite>(arena);
+ entry->default_instance_ = default_instance_;
+ return entry;
+ }
+
+ int SpaceUsed() const {
+ int size = sizeof(MapEntryLite);
+ size += KeyTypeHandler::SpaceUsedInMapEntry(key_);
+ size += ValueTypeHandler::SpaceUsedInMapEntry(value_);
+ return size;
+ }
+
+ void MergeFrom(const MapEntryLite& from) {
+ if (from._has_bits_[0]) {
+ if (from.has_key()) {
+ KeyTypeHandler::EnsureMutable(&key_, GetArenaNoVirtual());
+ KeyTypeHandler::Merge(from.key(), &key_, GetArenaNoVirtual());
+ set_has_key();
+ }
+ if (from.has_value()) {
+ ValueTypeHandler::EnsureMutable(&value_, GetArenaNoVirtual());
+ ValueTypeHandler::Merge(from.value(), &value_, GetArenaNoVirtual());
+ set_has_value();
+ }
+ }
+ }
+
+ void Clear() {
+ KeyTypeHandler::Clear(&key_, GetArenaNoVirtual());
+ ValueTypeHandler::ClearMaybeByDefaultEnum(
+ &value_, GetArenaNoVirtual(), default_enum_value);
+ clear_has_key();
+ clear_has_value();
+ }
+
+ void InitAsDefaultInstance() {
+ KeyTypeHandler::AssignDefaultValue(&key_);
+ ValueTypeHandler::AssignDefaultValue(&value_);
+ }
+
+ Arena* GetArena() const {
+ return GetArenaNoVirtual();
+ }
+
+ // Create a MapEntryLite for given key and value from google::protobuf::Map in
+ // serialization. This function is only called when value is enum. Enum is
+ // treated differently because its type in MapEntry is int and its type in
+ // google::protobuf::Map is enum. We cannot create a reference to int from an enum.
+ static MapEntryLite* EnumWrap(const Key& key, const Value value,
+ Arena* arena) {
+ return Arena::CreateMessage<MapEnumEntryWrapper<
+ Key, Value, kKeyFieldType, kValueFieldType, default_enum_value> >(
+ arena, key, value);
+ }
+
+ // Like above, but for all the other types. This avoids value copy to create
+ // MapEntryLite from google::protobuf::Map in serialization.
+ static MapEntryLite* Wrap(const Key& key, const Value& value, Arena* arena) {
+ return Arena::CreateMessage<MapEntryWrapper<Key, Value, kKeyFieldType,
+ kValueFieldType,
+ default_enum_value> >(
+ arena, key, value);
+ }
+
+ // Parsing using MergePartialFromCodedStream, above, is not as
+ // efficient as it could be. This helper class provides a speedier way.
+ template <typename MapField, typename Map>
+ class Parser {
+ public:
+ explicit Parser(MapField* mf) : mf_(mf), map_(mf->MutableMap()) {}
+
+ // This does what the typical MergePartialFromCodedStream() is expected to
+ // do, with the additional side-effect that if successful (i.e., if true is
+ // going to be its return value) it inserts the key-value pair into map_.
+ bool MergePartialFromCodedStream(::google::protobuf::io::CodedInputStream* input) {
+ // Look for the expected thing: a key and then a value. If it fails,
+ // invoke the enclosing class's MergePartialFromCodedStream, or return
+ // false if that would be pointless.
+ if (input->ExpectTag(kKeyTag)) {
+ if (!KeyTypeHandler::Read(input, &key_)) {
+ return false;
+ }
+ // Peek at the next byte to see if it is kValueTag. If not, bail out.
+ const void* data;
+ int size;
+ input->GetDirectBufferPointerInline(&data, &size);
+ // We could use memcmp here, but we don't bother. The tag is one byte.
+ assert(kTagSize == 1);
+ if (size > 0 && *reinterpret_cast<const char*>(data) == kValueTag) {
+ typename Map::size_type size = map_->size();
+ value_ptr_ = &(*map_)[key_];
+ if (GOOGLE_PREDICT_TRUE(size != map_->size())) {
+ // We created a new key-value pair. Fill in the value.
+ typedef
+ typename MapIf<ValueTypeHandler::kIsEnum, int*, Value*>::type T;
+ input->Skip(kTagSize); // Skip kValueTag.
+ if (!ValueTypeHandler::Read(input,
+ reinterpret_cast<T>(value_ptr_))) {
+ map_->erase(key_); // Failure! Undo insertion.
+ return false;
+ }
+ if (input->ExpectAtEnd()) return true;
+ return ReadBeyondKeyValuePair(input);
+ }
+ }
+ } else {
+ key_ = Key();
+ }
+
+ entry_.reset(mf_->NewEntry());
+ *entry_->mutable_key() = key_;
+ if (!entry_->MergePartialFromCodedStream(input)) return false;
+ return UseKeyAndValueFromEntry();
+ }
+
+ const Key& key() const { return key_; }
+ const Value& value() const { return *value_ptr_; }
+
+ private:
+ bool UseKeyAndValueFromEntry() GOOGLE_ATTRIBUTE_COLD {
+ // Update key_ in case we need it later (because key() is called).
+ // This is potentially inefficient, especially if the key is
+ // expensive to copy (e.g., a long string), but this is a cold
+ // path, so it's not a big deal.
+ key_ = entry_->key();
+ value_ptr_ = &(*map_)[key_];
+ MoveHelper<ValueTypeHandler::kIsEnum,
+ ValueTypeHandler::kIsMessage,
+ ValueTypeHandler::kWireType ==
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ Value>::Move(entry_->mutable_value(), value_ptr_);
+ if (entry_->GetArena() != NULL) entry_.release();
+ return true;
+ }
+
+ // After reading a key and value successfully, and inserting that data
+ // into map_, we are not at the end of the input. This is unusual, but
+ // allowed by the spec.
+ bool ReadBeyondKeyValuePair(::google::protobuf::io::CodedInputStream* input)
+ GOOGLE_ATTRIBUTE_COLD {
+ typedef MoveHelper<KeyTypeHandler::kIsEnum,
+ KeyTypeHandler::kIsMessage,
+ KeyTypeHandler::kWireType ==
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ Key> KeyMover;
+ typedef MoveHelper<ValueTypeHandler::kIsEnum,
+ ValueTypeHandler::kIsMessage,
+ ValueTypeHandler::kWireType ==
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ Value> ValueMover;
+ entry_.reset(mf_->NewEntry());
+ ValueMover::Move(value_ptr_, entry_->mutable_value());
+ map_->erase(key_);
+ KeyMover::Move(&key_, entry_->mutable_key());
+ if (!entry_->MergePartialFromCodedStream(input)) return false;
+ return UseKeyAndValueFromEntry();
+ }
+
+ MapField* const mf_;
+ Map* const map_;
+ Key key_;
+ Value* value_ptr_;
+ // On the fast path entry_ is not used.
+ google::protobuf::scoped_ptr<MapEntryLite> entry_;
+ };
+
+ protected:
+ void set_has_key() { _has_bits_[0] |= 0x00000001u; }
+ bool has_key() const { return (_has_bits_[0] & 0x00000001u) != 0; }
+ void clear_has_key() { _has_bits_[0] &= ~0x00000001u; }
+ void set_has_value() { _has_bits_[0] |= 0x00000002u; }
+ bool has_value() const { return (_has_bits_[0] & 0x00000002u) != 0; }
+ void clear_has_value() { _has_bits_[0] &= ~0x00000002u; }
+
+ private:
+ // Serializing a generated message containing map field involves serializing
+ // key-value pairs from google::protobuf::Map. The wire format of each key-value pair
+ // after serialization should be the same as that of a MapEntry message
+ // containing the same key and value inside it. However, google::protobuf::Map doesn't
+ // store key and value as MapEntry message, which disables us to use existing
+ // code to serialize message. In order to use existing code to serialize
+ // message, we need to construct a MapEntry from key-value pair. But it
+ // involves copy of key and value to construct a MapEntry. In order to avoid
+ // this copy in constructing a MapEntry, we need the following class which
+ // only takes references of given key and value.
+ template <typename K, typename V, WireFormatLite::FieldType k_wire_type,
+ WireFormatLite::FieldType v_wire_type, int default_enum>
+ class MapEntryWrapper
+ : public MapEntryLite<K, V, k_wire_type, v_wire_type, default_enum> {
+ typedef MapEntryLite<K, V, k_wire_type, v_wire_type, default_enum> Base;
+ typedef typename Base::KeyMapEntryAccessorType KeyMapEntryAccessorType;
+ typedef typename Base::ValueMapEntryAccessorType ValueMapEntryAccessorType;
+
+ public:
+ MapEntryWrapper(Arena* arena, const K& key, const V& value)
+ : MapEntryLite<K, V, k_wire_type, v_wire_type, default_enum>(arena),
+ key_(key),
+ value_(value) {
+ Base::set_has_key();
+ Base::set_has_value();
+ }
+ inline const KeyMapEntryAccessorType& key() const { return key_; }
+ inline const ValueMapEntryAccessorType& value() const { return value_; }
+
+ private:
+ const Key& key_;
+ const Value& value_;
+
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ };
+
+ // Like above, but for enum value only, which stores value instead of
+ // reference of value field inside. This is needed because the type of value
+ // field in constructor is an enum, while we need to store it as an int. If we
+ // initialize a reference to int with a reference to enum, compiler will
+ // generate a temporary int from enum and initialize the reference to int with
+ // the temporary.
+ template <typename K, typename V, WireFormatLite::FieldType k_wire_type,
+ WireFormatLite::FieldType v_wire_type, int default_enum>
+ class MapEnumEntryWrapper
+ : public MapEntryLite<K, V, k_wire_type, v_wire_type, default_enum> {
+ typedef MapEntryLite<K, V, k_wire_type, v_wire_type, default_enum> Base;
+ typedef typename Base::KeyMapEntryAccessorType KeyMapEntryAccessorType;
+ typedef typename Base::ValueMapEntryAccessorType ValueMapEntryAccessorType;
+
+ public:
+ MapEnumEntryWrapper(Arena* arena, const K& key, const V& value)
+ : MapEntryLite<K, V, k_wire_type, v_wire_type, default_enum>(arena),
+ key_(key),
+ value_(value) {
+ Base::set_has_key();
+ Base::set_has_value();
+ }
+ inline const KeyMapEntryAccessorType& key() const { return key_; }
+ inline const ValueMapEntryAccessorType& value() const { return value_; }
+
+ private:
+ const KeyMapEntryAccessorType& key_;
+ const ValueMapEntryAccessorType value_;
+
+ friend class google::protobuf::Arena;
+ typedef void DestructorSkippable_;
+ };
+
+ MapEntryLite() : default_instance_(NULL), arena_(NULL) {
+ KeyTypeHandler::Initialize(&key_, NULL);
+ ValueTypeHandler::InitializeMaybeByDefaultEnum(
+ &value_, default_enum_value, NULL);
+ _has_bits_[0] = 0;
+ }
+
+ explicit MapEntryLite(Arena* arena)
+ : default_instance_(NULL), arena_(arena) {
+ KeyTypeHandler::Initialize(&key_, arena);
+ ValueTypeHandler::InitializeMaybeByDefaultEnum(
+ &value_, default_enum_value, arena);
+ _has_bits_[0] = 0;
+ }
+
+ inline Arena* GetArenaNoVirtual() const {
+ return arena_;
+ }
+
+ void set_default_instance(MapEntryLite* default_instance) {
+ default_instance_ = default_instance;
+ }
+
+ MapEntryLite* default_instance_;
+
+ KeyOnMemory key_;
+ ValueOnMemory value_;
+ Arena* arena_;
+ uint32 _has_bits_[1];
+
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ template <typename K, typename V, WireFormatLite::FieldType,
+ WireFormatLite::FieldType, int>
+ friend class internal::MapEntry;
+ template <typename K, typename V, WireFormatLite::FieldType,
+ WireFormatLite::FieldType, int>
+ friend class internal::MapFieldLite;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MapEntryLite);
+};
+
+// Helpers for deterministic serialization =============================
+
+// This struct can be used with any generic sorting algorithm. If the Key
+// type is relatively small and easy to copy then copying Keys into an
+// array of SortItems can be beneficial. Then all the data the sorting
+// algorithm needs to touch is in that one array.
+template <typename Key, typename PtrToKeyValuePair> struct SortItem {
+ SortItem() {}
+ explicit SortItem(PtrToKeyValuePair p) : first(p->first), second(p) {}
+
+ Key first;
+ PtrToKeyValuePair second;
+};
+
+template <typename T> struct CompareByFirstField {
+ bool operator()(const T& a, const T& b) const {
+ return a.first < b.first;
+ }
+};
+
+template <typename T> struct CompareByDerefFirst {
+ bool operator()(const T& a, const T& b) const {
+ return a->first < b->first;
+ }
+};
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_ENTRY_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/map_field.cc
new file mode 100644
index 0000000000..49f918181f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_field.cc
@@ -0,0 +1,471 @@
+// 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.
+
+#include <google/protobuf/map_field.h>
+#include <google/protobuf/map_field_inl.h>
+
+#include <vector>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+ProtobufOnceType map_entry_default_instances_once_;
+Mutex* map_entry_default_instances_mutex_;
+vector<MessageLite*>* map_entry_default_instances_;
+
+void DeleteMapEntryDefaultInstances() {
+ for (int i = 0; i < map_entry_default_instances_->size(); ++i) {
+ delete map_entry_default_instances_->at(i);
+ }
+ delete map_entry_default_instances_mutex_;
+ delete map_entry_default_instances_;
+}
+
+void InitMapEntryDefaultInstances() {
+ map_entry_default_instances_mutex_ = new Mutex();
+ map_entry_default_instances_ = new vector<MessageLite*>();
+ OnShutdown(&DeleteMapEntryDefaultInstances);
+}
+
+void RegisterMapEntryDefaultInstance(MessageLite* default_instance) {
+ ::google::protobuf::GoogleOnceInit(&map_entry_default_instances_once_,
+ &InitMapEntryDefaultInstances);
+ MutexLock lock(map_entry_default_instances_mutex_);
+ map_entry_default_instances_->push_back(default_instance);
+}
+
+MapFieldBase::~MapFieldBase() {
+ if (repeated_field_ != NULL && arena_ == NULL) delete repeated_field_;
+}
+
+const RepeatedPtrFieldBase& MapFieldBase::GetRepeatedField() const {
+ SyncRepeatedFieldWithMap();
+ return *repeated_field_;
+}
+
+RepeatedPtrFieldBase* MapFieldBase::MutableRepeatedField() {
+ SyncRepeatedFieldWithMap();
+ SetRepeatedDirty();
+ return repeated_field_;
+}
+
+int MapFieldBase::SpaceUsedExcludingSelf() const {
+ mutex_.Lock();
+ int size = SpaceUsedExcludingSelfNoLock();
+ mutex_.Unlock();
+ return size;
+}
+
+int MapFieldBase::SpaceUsedExcludingSelfNoLock() const {
+ if (repeated_field_ != NULL) {
+ return repeated_field_->SpaceUsedExcludingSelf();
+ } else {
+ return 0;
+ }
+}
+
+void MapFieldBase::InitMetadataOnce() const {
+ GOOGLE_CHECK(entry_descriptor_ != NULL);
+ GOOGLE_CHECK(assign_descriptor_callback_ != NULL);
+ (*assign_descriptor_callback_)();
+}
+
+void MapFieldBase::SetMapDirty() { state_ = STATE_MODIFIED_MAP; }
+
+void MapFieldBase::SetRepeatedDirty() { state_ = STATE_MODIFIED_REPEATED; }
+
+void* MapFieldBase::MutableRepeatedPtrField() const { return repeated_field_; }
+
+void MapFieldBase::SyncRepeatedFieldWithMap() const {
+ // "Acquire" insures the operation after SyncRepeatedFieldWithMap won't get
+ // executed before state_ is checked.
+ Atomic32 state = google::protobuf::internal::Acquire_Load(&state_);
+ if (state == STATE_MODIFIED_MAP) {
+ mutex_.Lock();
+ // Double check state, because another thread may have seen the same state
+ // and done the synchronization before the current thread.
+ if (state_ == STATE_MODIFIED_MAP) {
+ SyncRepeatedFieldWithMapNoLock();
+ // "Release" insures state_ can only be changed "after"
+ // SyncRepeatedFieldWithMapNoLock is finished.
+ google::protobuf::internal::Release_Store(&state_, CLEAN);
+ }
+ mutex_.Unlock();
+ }
+}
+
+void MapFieldBase::SyncRepeatedFieldWithMapNoLock() const {
+ if (repeated_field_ == NULL) {
+ repeated_field_ = Arena::CreateMessage<RepeatedPtrField<Message> >(arena_);
+ }
+}
+
+void MapFieldBase::SyncMapWithRepeatedField() const {
+ // "Acquire" insures the operation after SyncMapWithRepeatedField won't get
+ // executed before state_ is checked.
+ Atomic32 state = google::protobuf::internal::Acquire_Load(&state_);
+ if (state == STATE_MODIFIED_REPEATED) {
+ mutex_.Lock();
+ // Double check state, because another thread may have seen the same state
+ // and done the synchronization before the current thread.
+ if (state_ == STATE_MODIFIED_REPEATED) {
+ SyncMapWithRepeatedFieldNoLock();
+ // "Release" insures state_ can only be changed "after"
+ // SyncRepeatedFieldWithMapNoLock is finished.
+ google::protobuf::internal::Release_Store(&state_, CLEAN);
+ }
+ mutex_.Unlock();
+ }
+}
+
+// ------------------DynamicMapField------------------
+DynamicMapField::DynamicMapField(const Message* default_entry)
+ : default_entry_(default_entry) {
+}
+
+DynamicMapField::DynamicMapField(const Message* default_entry,
+ Arena* arena)
+ : TypeDefinedMapFieldBase<MapKey, MapValueRef>(arena),
+ default_entry_(default_entry) {
+}
+
+DynamicMapField::~DynamicMapField() {
+ // DynamicMapField owns map values. Need to delete them before clearing
+ // the map.
+ for (Map<MapKey, MapValueRef>::iterator iter = map_.begin();
+ iter != map_.end(); ++iter) {
+ iter->second.DeleteData();
+ }
+ map_.clear();
+}
+
+int DynamicMapField::size() const {
+ return GetMap().size();
+}
+
+bool DynamicMapField::ContainsMapKey(
+ const MapKey& map_key) const {
+ const Map<MapKey, MapValueRef>& map = GetMap();
+ Map<MapKey, MapValueRef>::const_iterator iter = map.find(map_key);
+ return iter != map.end();
+}
+
+bool DynamicMapField::InsertOrLookupMapValue(
+ const MapKey& map_key, MapValueRef* val) {
+ // Always use mutable map because users may change the map value by
+ // MapValueRef.
+ Map<MapKey, MapValueRef>* map = MutableMap();
+ Map<MapKey, MapValueRef>::iterator iter = map->find(map_key);
+ if (iter == map->end()) {
+ // Insert
+ MapValueRef& map_val = (*map)[map_key];
+ const FieldDescriptor* val_des =
+ default_entry_->GetDescriptor()->FindFieldByName("value");
+ map_val.SetType(val_des->cpp_type());
+ // Allocate memory for the inserted MapValueRef, and initialize to
+ // default value.
+ switch (val_des->cpp_type()) {
+#define HANDLE_TYPE(CPPTYPE, TYPE) \
+ case google::protobuf::FieldDescriptor::CPPTYPE_##CPPTYPE: { \
+ TYPE * value = new TYPE(); \
+ map_val.SetValue(value); \
+ break; \
+ }
+ HANDLE_TYPE(INT32, int32);
+ HANDLE_TYPE(INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE(FLOAT, float);
+ HANDLE_TYPE(BOOL, bool);
+ HANDLE_TYPE(STRING, string);
+ HANDLE_TYPE(ENUM, int32);
+#undef HANDLE_TYPE
+ case google::protobuf::FieldDescriptor::CPPTYPE_MESSAGE: {
+ const Message& message = default_entry_->GetReflection()->GetMessage(
+ *default_entry_, val_des);
+ Message* value = message.New();
+ map_val.SetValue(value);
+ break;
+ }
+ }
+ val->CopyFrom(map_val);
+ return true;
+ }
+ // map_key is already in the map. Make sure (*map)[map_key] is not called.
+ // [] may reorder the map and iterators.
+ val->CopyFrom(iter->second);
+ return false;
+}
+
+bool DynamicMapField::DeleteMapValue(const MapKey& map_key) {
+ MapFieldBase::SyncMapWithRepeatedField();
+ Map<MapKey, MapValueRef>::iterator iter = map_.find(map_key);
+ if (iter == map_.end()) {
+ return false;
+ }
+ // Set map dirty only if the delete is successful.
+ MapFieldBase::SetMapDirty();
+ iter->second.DeleteData();
+ map_.erase(iter);
+ return true;
+}
+
+const Map<MapKey, MapValueRef>& DynamicMapField::GetMap() const {
+ MapFieldBase::SyncMapWithRepeatedField();
+ return map_;
+}
+
+Map<MapKey, MapValueRef>* DynamicMapField::MutableMap() {
+ MapFieldBase::SyncMapWithRepeatedField();
+ MapFieldBase::SetMapDirty();
+ return &map_;
+}
+
+void DynamicMapField::SetMapIteratorValue(MapIterator* map_iter) const {
+ Map<MapKey, MapValueRef>::const_iterator iter =
+ TypeDefinedMapFieldBase<MapKey, MapValueRef>::InternalGetIterator(
+ map_iter);
+ if (iter == map_.end()) return;
+ map_iter->key_.CopyFrom(iter->first);
+ map_iter->value_.CopyFrom(iter->second);
+}
+
+void DynamicMapField::SyncRepeatedFieldWithMapNoLock() const {
+ const Reflection* reflection = default_entry_->GetReflection();
+ const FieldDescriptor* key_des =
+ default_entry_->GetDescriptor()->FindFieldByName("key");
+ const FieldDescriptor* val_des =
+ default_entry_->GetDescriptor()->FindFieldByName("value");
+ if (MapFieldBase::repeated_field_ == NULL) {
+ if (MapFieldBase::arena_ == NULL) {
+ MapFieldBase::repeated_field_ = new RepeatedPtrField<Message>();
+ } else {
+ MapFieldBase::repeated_field_ =
+ Arena::CreateMessage<RepeatedPtrField<Message> >(
+ MapFieldBase::arena_);
+ }
+ }
+
+ MapFieldBase::repeated_field_->Clear();
+
+ for (Map<MapKey, MapValueRef>::const_iterator it = map_.begin();
+ it != map_.end(); ++it) {
+ Message* new_entry = default_entry_->New();
+ MapFieldBase::repeated_field_->AddAllocated(new_entry);
+ const MapKey& map_key = it->first;
+ switch (key_des->cpp_type()) {
+ case google::protobuf::FieldDescriptor::CPPTYPE_STRING:
+ reflection->SetString(new_entry, key_des, map_key.GetStringValue());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT64:
+ reflection->SetInt64(new_entry, key_des, map_key.GetInt64Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT32:
+ reflection->SetInt32(new_entry, key_des, map_key.GetInt32Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT64:
+ reflection->SetUInt64(new_entry, key_des, map_key.GetUInt64Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT32:
+ reflection->SetUInt32(new_entry, key_des, map_key.GetUInt32Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_BOOL:
+ reflection->SetBool(new_entry, key_des, map_key.GetBoolValue());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_DOUBLE:
+ case google::protobuf::FieldDescriptor::CPPTYPE_FLOAT:
+ case google::protobuf::FieldDescriptor::CPPTYPE_ENUM:
+ case google::protobuf::FieldDescriptor::CPPTYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ break;
+ }
+ const MapValueRef& map_val = it->second;
+ switch (val_des->cpp_type()) {
+ case google::protobuf::FieldDescriptor::CPPTYPE_STRING:
+ reflection->SetString(new_entry, val_des, map_val.GetStringValue());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT64:
+ reflection->SetInt64(new_entry, val_des, map_val.GetInt64Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT32:
+ reflection->SetInt32(new_entry, val_des, map_val.GetInt32Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT64:
+ reflection->SetUInt64(new_entry, val_des, map_val.GetUInt64Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT32:
+ reflection->SetUInt32(new_entry, val_des, map_val.GetUInt32Value());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_BOOL:
+ reflection->SetBool(new_entry, val_des, map_val.GetBoolValue());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_DOUBLE:
+ reflection->SetDouble(new_entry, val_des, map_val.GetDoubleValue());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_FLOAT:
+ reflection->SetFloat(new_entry, val_des, map_val.GetFloatValue());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_ENUM:
+ reflection->SetEnumValue(new_entry, val_des, map_val.GetEnumValue());
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_MESSAGE: {
+ const Message& message = map_val.GetMessageValue();
+ reflection->MutableMessage(new_entry, val_des)->CopyFrom(message);
+ break;
+ }
+ }
+ }
+}
+
+void DynamicMapField::SyncMapWithRepeatedFieldNoLock() const {
+ Map<MapKey, MapValueRef>* map = &const_cast<DynamicMapField*>(this)->map_;
+ const Reflection* reflection = default_entry_->GetReflection();
+ const FieldDescriptor* key_des =
+ default_entry_->GetDescriptor()->FindFieldByName("key");
+ const FieldDescriptor* val_des =
+ default_entry_->GetDescriptor()->FindFieldByName("value");
+ // DynamicMapField owns map values. Need to delete them before clearing
+ // the map.
+ for (Map<MapKey, MapValueRef>::iterator iter = map->begin();
+ iter != map->end(); ++iter) {
+ iter->second.DeleteData();
+ }
+ map->clear();
+ for (RepeatedPtrField<Message>::iterator it =
+ MapFieldBase::repeated_field_->begin();
+ it != MapFieldBase::repeated_field_->end(); ++it) {
+ MapKey map_key;
+ switch (key_des->cpp_type()) {
+ case google::protobuf::FieldDescriptor::CPPTYPE_STRING:
+ map_key.SetStringValue(reflection->GetString(*it, key_des));
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT64:
+ map_key.SetInt64Value(reflection->GetInt64(*it, key_des));
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_INT32:
+ map_key.SetInt32Value(reflection->GetInt32(*it, key_des));
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT64:
+ map_key.SetUInt64Value(reflection->GetUInt64(*it, key_des));
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_UINT32:
+ map_key.SetUInt32Value(reflection->GetUInt32(*it, key_des));
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_BOOL:
+ map_key.SetBoolValue(reflection->GetBool(*it, key_des));
+ break;
+ case google::protobuf::FieldDescriptor::CPPTYPE_DOUBLE:
+ case google::protobuf::FieldDescriptor::CPPTYPE_FLOAT:
+ case google::protobuf::FieldDescriptor::CPPTYPE_ENUM:
+ case google::protobuf::FieldDescriptor::CPPTYPE_MESSAGE:
+ GOOGLE_LOG(FATAL) << "Can't get here.";
+ break;
+ }
+ MapValueRef& map_val = (*map)[map_key];
+ map_val.SetType(val_des->cpp_type());
+ switch (val_des->cpp_type()) {
+#define HANDLE_TYPE(CPPTYPE, TYPE, METHOD) \
+ case google::protobuf::FieldDescriptor::CPPTYPE_##CPPTYPE: { \
+ TYPE * value = new TYPE; \
+ *value = reflection->Get##METHOD(*it, val_des); \
+ map_val.SetValue(value); \
+ break; \
+ }
+ HANDLE_TYPE(INT32, int32, Int32);
+ HANDLE_TYPE(INT64, int64, Int64);
+ HANDLE_TYPE(UINT32, uint32, UInt32);
+ HANDLE_TYPE(UINT64, uint64, UInt64);
+ HANDLE_TYPE(DOUBLE, double, Double);
+ HANDLE_TYPE(FLOAT, float, Float);
+ HANDLE_TYPE(BOOL, bool, Bool);
+ HANDLE_TYPE(STRING, string, String);
+ HANDLE_TYPE(ENUM, int32, EnumValue);
+#undef HANDLE_TYPE
+ case google::protobuf::FieldDescriptor::CPPTYPE_MESSAGE: {
+ const Message& message = reflection->GetMessage(*it, val_des);
+ Message* value = message.New();
+ value->CopyFrom(message);
+ map_val.SetValue(value);
+ break;
+ }
+ }
+ }
+}
+
+int DynamicMapField::SpaceUsedExcludingSelfNoLock() const {
+ int size = 0;
+ if (MapFieldBase::repeated_field_ != NULL) {
+ size += MapFieldBase::repeated_field_->SpaceUsedExcludingSelf();
+ }
+ size += sizeof(map_);
+ int map_size = map_.size();
+ if (map_size) {
+ Map<MapKey, MapValueRef>::const_iterator it = map_.begin();
+ size += sizeof(it->first) * map_size;
+ size += sizeof(it->second) * map_size;
+ // If key is string, add the allocated space.
+ if (it->first.type() == google::protobuf::FieldDescriptor::CPPTYPE_STRING) {
+ size += sizeof(string) * map_size;
+ }
+ // Add the allocated space in MapValueRef.
+ switch (it->second.type()) {
+#define HANDLE_TYPE(CPPTYPE, TYPE) \
+ case google::protobuf::FieldDescriptor::CPPTYPE_##CPPTYPE: { \
+ size += sizeof(TYPE) * map_size; \
+ break; \
+ }
+ HANDLE_TYPE(INT32, int32);
+ HANDLE_TYPE(INT64, int64);
+ HANDLE_TYPE(UINT32, uint32);
+ HANDLE_TYPE(UINT64, uint64);
+ HANDLE_TYPE(DOUBLE, double);
+ HANDLE_TYPE(FLOAT, float);
+ HANDLE_TYPE(BOOL, bool);
+ HANDLE_TYPE(STRING, string);
+ HANDLE_TYPE(ENUM, int32);
+#undef HANDLE_TYPE
+ case google::protobuf::FieldDescriptor::CPPTYPE_MESSAGE: {
+ while (it != map_.end()) {
+ const Message& message = it->second.GetMessageValue();
+ size += message.GetReflection()->SpaceUsed(message);
+ ++it;
+ }
+ break;
+ }
+ }
+ }
+ return size;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_field.h
new file mode 100644
index 0000000000..d6af8532d2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_field.h
@@ -0,0 +1,397 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_FIELD_H__
+#define GOOGLE_PROTOBUF_MAP_FIELD_H__
+
+#include <google/protobuf/stubs/atomicops.h>
+#include <google/protobuf/stubs/mutex.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/generated_message_reflection.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/map_entry.h>
+#include <google/protobuf/map_field_lite.h>
+#include <google/protobuf/map_type_handler.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/unknown_field_set.h>
+
+
+namespace google {
+namespace protobuf {
+class DynamicMessage;
+class MapKey;
+namespace internal {
+
+class ContendedMapCleanTest;
+class GeneratedMessageReflection;
+class MapFieldAccessor;
+
+// This class provides access to map field using reflection, which is the same
+// as those provided for RepeatedPtrField<Message>. It is used for internal
+// reflection implentation only. Users should never use this directly.
+class LIBPROTOBUF_EXPORT MapFieldBase {
+ public:
+ MapFieldBase()
+ : arena_(NULL),
+ repeated_field_(NULL),
+ entry_descriptor_(NULL),
+ assign_descriptor_callback_(NULL),
+ state_(STATE_MODIFIED_MAP) {}
+ explicit MapFieldBase(Arena* arena)
+ : arena_(arena),
+ repeated_field_(NULL),
+ entry_descriptor_(NULL),
+ assign_descriptor_callback_(NULL),
+ state_(STATE_MODIFIED_MAP) {
+ // Mutex's destructor needs to be called explicitly to release resources
+ // acquired in its constructor.
+ arena->OwnDestructor(&mutex_);
+ }
+ virtual ~MapFieldBase();
+
+ // Returns reference to internal repeated field. Data written using
+ // google::protobuf::Map's api prior to calling this function is guarantted to be
+ // included in repeated field.
+ const RepeatedPtrFieldBase& GetRepeatedField() const;
+
+ // Like above. Returns mutable pointer to the internal repeated field.
+ RepeatedPtrFieldBase* MutableRepeatedField();
+
+ // Pure virtual map APIs for Map Reflection.
+ virtual bool ContainsMapKey(const MapKey& map_key) const = 0;
+ virtual bool InsertOrLookupMapValue(
+ const MapKey& map_key, MapValueRef* val) = 0;
+ virtual bool DeleteMapValue(const MapKey& map_key) = 0;
+ virtual bool EqualIterator(const MapIterator& a,
+ const MapIterator& b) const = 0;
+ virtual void MapBegin(MapIterator* map_iter) const = 0;
+ virtual void MapEnd(MapIterator* map_iter) const = 0;
+ // Sync Map with repeated field and returns the size of map.
+ virtual int size() const = 0;
+
+ // Returns the number of bytes used by the repeated field, excluding
+ // sizeof(*this)
+ int SpaceUsedExcludingSelf() const;
+
+ protected:
+ // Gets the size of space used by map field.
+ virtual int SpaceUsedExcludingSelfNoLock() const;
+
+ // Synchronizes the content in Map to RepeatedPtrField if there is any change
+ // to Map after last synchronization.
+ void SyncRepeatedFieldWithMap() const;
+ virtual void SyncRepeatedFieldWithMapNoLock() const;
+
+ // Synchronizes the content in RepeatedPtrField to Map if there is any change
+ // to RepeatedPtrField after last synchronization.
+ void SyncMapWithRepeatedField() const;
+ virtual void SyncMapWithRepeatedFieldNoLock() const {}
+
+ // Tells MapFieldBase that there is new change to Map.
+ void SetMapDirty();
+
+ // Tells MapFieldBase that there is new change to RepeatedPTrField.
+ void SetRepeatedDirty();
+
+ // Provides derived class the access to repeated field.
+ void* MutableRepeatedPtrField() const;
+
+ // Creates descriptor for only one time.
+ void InitMetadataOnce() const;
+
+ enum State {
+ STATE_MODIFIED_MAP = 0, // map has newly added data that has not been
+ // synchronized to repeated field
+ STATE_MODIFIED_REPEATED = 1, // repeated field has newly added data that
+ // has not been synchronized to map
+ CLEAN = 2, // data in map and repeated field are same
+ };
+
+ Arena* arena_;
+ mutable RepeatedPtrField<Message>* repeated_field_;
+ // MapEntry can only be created from MapField. To create MapEntry, MapField
+ // needs to know its descriptor, because MapEntry is not generated class which
+ // cannot initialize its own descriptor by calling generated
+ // descriptor-assign-function. Thus, we need to register a callback to
+ // initialize MapEntry's descriptor.
+ const Descriptor** entry_descriptor_;
+ void (*assign_descriptor_callback_)();
+
+ mutable Mutex mutex_; // The thread to synchronize map and repeated field
+ // needs to get lock first;
+ mutable volatile Atomic32 state_; // 0: STATE_MODIFIED_MAP
+ // 1: STATE_MODIFIED_REPEATED
+ // 2: CLEAN
+
+ private:
+ friend class ContendedMapCleanTest;
+ friend class GeneratedMessageReflection;
+ friend class MapFieldAccessor;
+ friend class ::google::protobuf::DynamicMessage;
+
+ // Virtual helper methods for MapIterator. MapIterator doesn't have the
+ // type helper for key and value. Call these help methods to deal with
+ // different types. Real helper methods are implemented in
+ // TypeDefinedMapFieldBase.
+ friend class ::google::protobuf::MapIterator;
+ // Allocate map<...>::iterator for MapIterator.
+ virtual void InitializeIterator(MapIterator* map_iter) const = 0;
+
+ // DeleteIterator() is called by the destructor of MapIterator only.
+ // It deletes map<...>::iterator for MapIterator.
+ virtual void DeleteIterator(MapIterator* map_iter) const = 0;
+
+ // Copy the map<...>::iterator from other_iterator to
+ // this_iterator.
+ virtual void CopyIterator(MapIterator* this_iterator,
+ const MapIterator& other_iterator) const = 0;
+
+ // IncreaseIterator() is called by operator++() of MapIterator only.
+ // It implements the ++ operator of MapIterator.
+ virtual void IncreaseIterator(MapIterator* map_iter) const = 0;
+};
+
+// This class provides common Map Reflection implementations for generated
+// message and dynamic message.
+template<typename Key, typename T>
+class TypeDefinedMapFieldBase : public MapFieldBase {
+ public:
+ TypeDefinedMapFieldBase() {}
+ explicit TypeDefinedMapFieldBase(Arena* arena) : MapFieldBase(arena) {}
+ ~TypeDefinedMapFieldBase() {}
+ void MapBegin(MapIterator* map_iter) const;
+ void MapEnd(MapIterator* map_iter) const;
+ bool EqualIterator(const MapIterator& a, const MapIterator& b) const;
+
+ virtual const Map<Key, T>& GetMap() const = 0;
+ virtual Map<Key, T>* MutableMap() = 0;
+
+ protected:
+ typename Map<Key, T>::const_iterator& InternalGetIterator(
+ const MapIterator* map_iter) const;
+
+ private:
+ void InitializeIterator(MapIterator* map_iter) const;
+ void DeleteIterator(MapIterator* map_iter) const;
+ void CopyIterator(MapIterator* this_iteratorm,
+ const MapIterator& that_iterator) const;
+ void IncreaseIterator(MapIterator* map_iter) const;
+
+ virtual void SetMapIteratorValue(MapIterator* map_iter) const = 0;
+};
+
+// This class provides access to map field using generated api. It is used for
+// internal generated message implentation only. Users should never use this
+// directly.
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value = 0>
+class MapField : public TypeDefinedMapFieldBase<Key, T>,
+ public MapFieldLite<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value> {
+ // Provide utilities to parse/serialize key/value. Provide utilities to
+ // manipulate internal stored type.
+ typedef MapTypeHandler<kKeyFieldType, Key> KeyTypeHandler;
+ typedef MapTypeHandler<kValueFieldType, T> ValueTypeHandler;
+
+ // Define message type for internal repeated field.
+ typedef MapEntry<Key, T, kKeyFieldType, kValueFieldType, default_enum_value>
+ EntryType;
+ typedef MapEntryLite<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value> EntryLiteType;
+
+ // Define abbreviation for parent MapFieldLite
+ typedef MapFieldLite<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value> MapFieldLiteType;
+
+ // Enum needs to be handled differently from other types because it has
+ // different exposed type in google::protobuf::Map's api and repeated field's api. For
+ // details see the comment in the implementation of
+ // SyncMapWithRepeatedFieldNoLock.
+ static const bool kIsValueEnum = ValueTypeHandler::kIsEnum;
+ typedef typename MapIf<kIsValueEnum, T, const T&>::type CastValueType;
+
+ public:
+ MapField();
+ explicit MapField(Arena* arena);
+ // MapField doesn't own the default_entry, which means default_entry must
+ // outlive the lifetime of MapField.
+ MapField(const Message* default_entry);
+ // For tests only.
+ MapField(Arena* arena, const Message* default_entry);
+ ~MapField();
+
+ // Implement MapFieldBase
+ bool ContainsMapKey(const MapKey& map_key) const;
+ bool InsertOrLookupMapValue(const MapKey& map_key, MapValueRef* val);
+ bool DeleteMapValue(const MapKey& map_key);
+
+ // Accessors
+ const Map<Key, T>& GetMap() const;
+ Map<Key, T>* MutableMap();
+
+ // Convenient methods for generated message implementation.
+ int size() const;
+ void Clear();
+ void MergeFrom(const MapFieldLiteType& other);
+ void Swap(MapFieldLiteType* other);
+
+ // Allocates metadata only if this MapField is part of a generated message.
+ void SetEntryDescriptor(const Descriptor** descriptor);
+ void SetAssignDescriptorCallback(void (*callback)());
+
+ private:
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+
+ // MapField needs MapEntry's default instance to create new MapEntry.
+ void InitDefaultEntryOnce() const;
+
+ // Manually set default entry instance. For test only.
+ void SetDefaultEntryOnce(const EntryType* default_entry) const;
+
+ // Convenient methods to get internal google::protobuf::Map
+ const Map<Key, T>& GetInternalMap() const;
+ Map<Key, T>* MutableInternalMap();
+
+ // Implements MapFieldBase
+ void SyncRepeatedFieldWithMapNoLock() const;
+ void SyncMapWithRepeatedFieldNoLock() const;
+ int SpaceUsedExcludingSelfNoLock() const;
+
+ void SetMapIteratorValue(MapIterator* map_iter) const;
+
+ mutable const EntryType* default_entry_;
+
+ friend class ::google::protobuf::Arena;
+};
+
+class LIBPROTOBUF_EXPORT DynamicMapField: public TypeDefinedMapFieldBase<MapKey, MapValueRef> {
+ public:
+ explicit DynamicMapField(const Message* default_entry);
+ DynamicMapField(const Message* default_entry, Arena* arena);
+ ~DynamicMapField();
+
+ // Implement MapFieldBase
+ bool ContainsMapKey(const MapKey& map_key) const;
+ bool InsertOrLookupMapValue(const MapKey& map_key, MapValueRef* val);
+ bool DeleteMapValue(const MapKey& map_key);
+
+ const Map<MapKey, MapValueRef>& GetMap() const;
+ Map<MapKey, MapValueRef>* MutableMap();
+
+ int size() const;
+
+ private:
+ Map<MapKey, MapValueRef> map_;
+ const Message* default_entry_;
+
+ // Implements MapFieldBase
+ void SyncRepeatedFieldWithMapNoLock() const;
+ void SyncMapWithRepeatedFieldNoLock() const;
+ int SpaceUsedExcludingSelfNoLock() const;
+ void SetMapIteratorValue(MapIterator* map_iter) const;
+};
+
+} // namespace internal
+
+class LIBPROTOBUF_EXPORT MapIterator {
+ public:
+ MapIterator(Message* message, const FieldDescriptor* field) {
+ const Reflection* reflection = message->GetReflection();
+ map_ = reflection->MapData(message, field);
+ key_.SetType(field->message_type()->FindFieldByName("key")->cpp_type());
+ value_.SetType(field->message_type()->FindFieldByName("value")->cpp_type());
+ map_->InitializeIterator(this);
+ }
+ MapIterator(const MapIterator& other) {
+ map_ = other.map_;
+ map_->InitializeIterator(this);
+ map_->CopyIterator(this, other);
+ }
+ ~MapIterator() {
+ map_->DeleteIterator(this);
+ }
+ friend bool operator==(const MapIterator& a, const MapIterator& b) {
+ return a.map_->EqualIterator(a, b);
+ }
+ friend bool operator!=(const MapIterator& a, const MapIterator& b) {
+ return !a.map_->EqualIterator(a, b);
+ }
+ MapIterator& operator++() {
+ map_->IncreaseIterator(this);
+ return *this;
+ }
+ MapIterator operator++(int) {
+ // iter_ is copied from Map<...>::iterator, no need to
+ // copy from its self again. Use the same implementation
+ // with operator++()
+ map_->IncreaseIterator(this);
+ return *this;
+ }
+ const MapKey& GetKey() {
+ return key_;
+ }
+ const MapValueRef& GetValueRef() {
+ return value_;
+ }
+ MapValueRef* MutableValueRef() {
+ map_->SetMapDirty();
+ return &value_;
+ }
+
+ private:
+ template <typename Key, typename T>
+ friend class internal::TypeDefinedMapFieldBase;
+ friend class internal::DynamicMapField;
+ template <typename Key, typename T,
+ internal::WireFormatLite::FieldType kKeyFieldType,
+ internal::WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+ friend class internal::MapField;
+
+ // reinterpret_cast from heap-allocated Map<...>::iterator*. MapIterator owns
+ // the iterator. It is allocated by MapField<...>::InitializeIterator() called
+ // in constructor and deleted by MapField<...>::DeleteIterator() called in
+ // destructor.
+ void* iter_;
+ // Point to a MapField to call helper methods implemented in MapField.
+ // MapIterator does not own this object.
+ internal::MapFieldBase* map_;
+ MapKey key_;
+ MapValueRef value_;
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_field_inl.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_field_inl.h
new file mode 100644
index 0000000000..01c9b89aab
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_field_inl.h
@@ -0,0 +1,489 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_FIELD_INL_H__
+#define GOOGLE_PROTOBUF_MAP_FIELD_INL_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/map.h>
+#include <google/protobuf/map_field.h>
+#include <google/protobuf/map_type_handler.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+// UnwrapMapKey template
+template<typename T>
+T UnwrapMapKey(const MapKey& map_key);
+template<>
+inline int32 UnwrapMapKey<int32>(const MapKey& map_key) {
+ return map_key.GetInt32Value();
+}
+template<>
+inline uint32 UnwrapMapKey<uint32>(const MapKey& map_key) {
+ return map_key.GetUInt32Value();
+}
+template<>
+inline int64 UnwrapMapKey<int64>(const MapKey& map_key) {
+ return map_key.GetInt64Value();
+}
+template<>
+inline uint64 UnwrapMapKey<uint64>(const MapKey& map_key) {
+ return map_key.GetUInt64Value();
+}
+template<>
+inline bool UnwrapMapKey<bool>(const MapKey& map_key) {
+ return map_key.GetBoolValue();
+}
+template<>
+inline string UnwrapMapKey<string>(const MapKey& map_key) {
+ return map_key.GetStringValue();
+}
+
+// SetMapKey template
+template<typename T>
+inline void SetMapKey(MapKey* map_key, const T& value);
+template<>
+inline void SetMapKey<int32>(MapKey* map_key, const int32& value) {
+ map_key->SetInt32Value(value);
+}
+template<>
+inline void SetMapKey<uint32>(MapKey* map_key, const uint32& value) {
+ map_key->SetUInt32Value(value);
+}
+template<>
+inline void SetMapKey<int64>(MapKey* map_key, const int64& value) {
+ map_key->SetInt64Value(value);
+}
+template<>
+inline void SetMapKey<uint64>(MapKey* map_key, const uint64& value) {
+ map_key->SetUInt64Value(value);
+}
+template<>
+inline void SetMapKey<bool>(MapKey* map_key, const bool& value) {
+ map_key->SetBoolValue(value);
+}
+template<>
+inline void SetMapKey<string>(MapKey* map_key, const string& value) {
+ map_key->SetStringValue(value);
+}
+
+// ------------------------TypeDefinedMapFieldBase---------------
+template <typename Key, typename T>
+typename Map<Key, T>::const_iterator&
+TypeDefinedMapFieldBase<Key, T>::InternalGetIterator(
+ const MapIterator* map_iter) const {
+ return *reinterpret_cast<typename Map<Key, T>::const_iterator *>(
+ map_iter->iter_);
+}
+
+template <typename Key, typename T>
+void TypeDefinedMapFieldBase<Key, T>::MapBegin(MapIterator* map_iter) const {
+ InternalGetIterator(map_iter) = GetMap().begin();
+ SetMapIteratorValue(map_iter);
+}
+
+template <typename Key, typename T>
+void TypeDefinedMapFieldBase<Key, T>::MapEnd(MapIterator* map_iter) const {
+ InternalGetIterator(map_iter) = GetMap().end();
+}
+
+template <typename Key, typename T>
+bool TypeDefinedMapFieldBase<Key, T>::EqualIterator(const MapIterator& a,
+ const MapIterator& b)
+ const {
+ return InternalGetIterator(&a) == InternalGetIterator(&b);
+}
+
+template <typename Key, typename T>
+void TypeDefinedMapFieldBase<Key, T>::IncreaseIterator(MapIterator* map_iter)
+ const {
+ ++InternalGetIterator(map_iter);
+ SetMapIteratorValue(map_iter);
+}
+
+template <typename Key, typename T>
+void TypeDefinedMapFieldBase<Key, T>::InitializeIterator(
+ MapIterator* map_iter) const {
+ map_iter->iter_ = new typename Map<Key, T>::const_iterator;
+ GOOGLE_CHECK(map_iter->iter_ != NULL);
+}
+
+template <typename Key, typename T>
+void TypeDefinedMapFieldBase<Key, T>::DeleteIterator(MapIterator* map_iter)
+ const {
+ delete reinterpret_cast<typename Map<Key, T>::const_iterator *>(
+ map_iter->iter_);
+}
+
+template <typename Key, typename T>
+void TypeDefinedMapFieldBase<Key, T>::CopyIterator(
+ MapIterator* this_iter,
+ const MapIterator& that_iter) const {
+ InternalGetIterator(this_iter) = InternalGetIterator(&that_iter);
+ this_iter->key_.SetType(that_iter.key_.type());
+ // MapValueRef::type() fails when containing data is null. However, if
+ // this_iter points to MapEnd, data can be null.
+ this_iter->value_.SetType(
+ static_cast<FieldDescriptor::CppType>(that_iter.value_.type_));
+ SetMapIteratorValue(this_iter);
+}
+
+// ----------------------------------------------------------------------
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+MapField<Key, T, kKeyFieldType, kValueFieldType, default_enum_value>::MapField()
+ : default_entry_(NULL) {}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+MapField<Key, T, kKeyFieldType, kValueFieldType, default_enum_value>::MapField(
+ Arena* arena)
+ : TypeDefinedMapFieldBase<Key, T>(arena),
+ MapFieldLite<Key, T, kKeyFieldType, kValueFieldType, default_enum_value>(
+ arena),
+ default_entry_(NULL) {}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+MapField<Key, T, kKeyFieldType, kValueFieldType, default_enum_value>::MapField(
+ const Message* default_entry)
+ : default_entry_(down_cast<const EntryType*>(default_entry)) {}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+MapField<Key, T, kKeyFieldType, kValueFieldType, default_enum_value>::MapField(
+ Arena* arena, const Message* default_entry)
+ : TypeDefinedMapFieldBase<Key, T>(arena),
+ MapFieldLite<Key, T, kKeyFieldType, kValueFieldType, default_enum_value>(
+ arena),
+ default_entry_(down_cast<const EntryType*>(default_entry)) {}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::~MapField() {}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+int
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::size() const {
+ MapFieldBase::SyncMapWithRepeatedField();
+ return MapFieldLiteType::GetInternalMap().size();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::Clear() {
+ MapFieldBase::SyncMapWithRepeatedField();
+ MapFieldLiteType::MutableInternalMap()->clear();
+ MapFieldBase::SetMapDirty();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::SetMapIteratorValue(
+ MapIterator* map_iter) const {
+ const Map<Key, T>& map = GetMap();
+ typename Map<Key, T>::const_iterator iter =
+ TypeDefinedMapFieldBase<Key, T>::InternalGetIterator(map_iter);
+ if (iter == map.end()) return;
+ SetMapKey(&map_iter->key_, iter->first);
+ map_iter->value_.SetValue(&iter->second);
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+bool MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::ContainsMapKey(
+ const MapKey& map_key) const {
+ const Map<Key, T>& map = GetMap();
+ const Key& key = UnwrapMapKey<Key>(map_key);
+ typename Map<Key, T>::const_iterator iter = map.find(key);
+ return iter != map.end();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+bool MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::InsertOrLookupMapValue(
+ const MapKey& map_key,
+ MapValueRef* val) {
+ // Always use mutable map because users may change the map value by
+ // MapValueRef.
+ Map<Key, T>* map = MutableMap();
+ const Key& key = UnwrapMapKey<Key>(map_key);
+ typename Map<Key, T>::iterator iter = map->find(key);
+ if (map->end() == iter) {
+ val->SetValue(&((*map)[key]));
+ return true;
+ }
+ // Key is already in the map. Make sure (*map)[key] is not called.
+ // [] may reorder the map and iterators.
+ val->SetValue(&(iter->second));
+ return false;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+bool MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::DeleteMapValue(
+ const MapKey& map_key) {
+ const Key& key = UnwrapMapKey<Key>(map_key);
+ return MutableMap()->erase(key);
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+const Map<Key, T>&
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::GetMap() const {
+ MapFieldBase::SyncMapWithRepeatedField();
+ return MapFieldLiteType::GetInternalMap();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+Map<Key, T>*
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::MutableMap() {
+ MapFieldBase::SyncMapWithRepeatedField();
+ Map<Key, T>* result = MapFieldLiteType::MutableInternalMap();
+ MapFieldBase::SetMapDirty();
+ return result;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::MergeFrom(
+ const MapFieldLiteType& other) {
+ const MapField& down_other = down_cast<const MapField&>(other);
+ MapFieldBase::SyncMapWithRepeatedField();
+ down_other.SyncMapWithRepeatedField();
+ MapFieldLiteType::MergeFrom(other);
+ MapFieldBase::SetMapDirty();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::Swap(
+ MapFieldLiteType* other) {
+ MapField* down_other = down_cast<MapField*>(other);
+ std::swap(MapFieldBase::repeated_field_, down_other->repeated_field_);
+ MapFieldLiteType::Swap(other);
+ std::swap(MapFieldBase::state_, down_other->state_);
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::SetEntryDescriptor(
+ const Descriptor** descriptor) {
+ MapFieldBase::entry_descriptor_ = descriptor;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::SetAssignDescriptorCallback(void (*callback)()) {
+ MapFieldBase::assign_descriptor_callback_ = callback;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+const Map<Key, T>&
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::GetInternalMap() const {
+ return MapFieldLiteType::GetInternalMap();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+Map<Key, T>*
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::MutableInternalMap() {
+ return MapFieldLiteType::MutableInternalMap();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::SyncRepeatedFieldWithMapNoLock() const {
+ if (MapFieldBase::repeated_field_ == NULL) {
+ if (MapFieldBase::arena_ == NULL) {
+ MapFieldBase::repeated_field_ = new RepeatedPtrField<Message>();
+ } else {
+ MapFieldBase::repeated_field_ =
+ Arena::CreateMessage<RepeatedPtrField<Message> >(
+ MapFieldBase::arena_);
+ }
+ }
+ const Map<Key, T>& map = GetInternalMap();
+ RepeatedPtrField<EntryType>* repeated_field =
+ reinterpret_cast<RepeatedPtrField<EntryType>*>(
+ MapFieldBase::repeated_field_);
+
+ repeated_field->Clear();
+
+ for (typename Map<Key, T>::const_iterator it = map.begin();
+ it != map.end(); ++it) {
+ InitDefaultEntryOnce();
+ GOOGLE_CHECK(default_entry_ != NULL);
+ EntryType* new_entry =
+ down_cast<EntryType*>(default_entry_->New(MapFieldBase::arena_));
+ repeated_field->AddAllocated(new_entry);
+ (*new_entry->mutable_key()) = it->first;
+ (*new_entry->mutable_value()) = it->second;
+ }
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::SyncMapWithRepeatedFieldNoLock() const {
+ Map<Key, T>* map = const_cast<MapField*>(this)->MutableInternalMap();
+ RepeatedPtrField<EntryType>* repeated_field =
+ reinterpret_cast<RepeatedPtrField<EntryType>*>(
+ MapFieldBase::repeated_field_);
+ GOOGLE_CHECK(MapFieldBase::repeated_field_ != NULL);
+ map->clear();
+ for (typename RepeatedPtrField<EntryType>::iterator it =
+ repeated_field->begin(); it != repeated_field->end(); ++it) {
+ // Cast is needed because Map's api and internal storage is different when
+ // value is enum. For enum, we cannot cast an int to enum. Thus, we have to
+ // copy value. For other types, they have same exposed api type and internal
+ // stored type. We should not introduce value copy for them. We achieve this
+ // by casting to value for enum while casting to reference for other types.
+ (*map)[it->key()] = static_cast<CastValueType>(it->value());
+ }
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+int
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::SpaceUsedExcludingSelfNoLock() const {
+ int size = 0;
+ if (MapFieldBase::repeated_field_ != NULL) {
+ size += MapFieldBase::repeated_field_->SpaceUsedExcludingSelf();
+ }
+ Map<Key, T>* map = const_cast<MapField*>(this)->MutableInternalMap();
+ size += sizeof(*map);
+ for (typename Map<Key, T>::iterator it = map->begin();
+ it != map->end(); ++it) {
+ size += KeyTypeHandler::SpaceUsedInMap(it->first);
+ size += ValueTypeHandler::SpaceUsedInMap(it->second);
+ }
+ return size;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType kKeyFieldType,
+ WireFormatLite::FieldType kValueFieldType,
+ int default_enum_value>
+void
+MapField<Key, T, kKeyFieldType, kValueFieldType,
+ default_enum_value>::InitDefaultEntryOnce()
+ const {
+ if (default_entry_ == NULL) {
+ MapFieldBase::InitMetadataOnce();
+ GOOGLE_CHECK(*MapFieldBase::entry_descriptor_ != NULL);
+ default_entry_ = down_cast<const EntryType*>(
+ MessageFactory::generated_factory()->GetPrototype(
+ *MapFieldBase::entry_descriptor_));
+ }
+}
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_FIELD_INL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_field_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_field_lite.h
new file mode 100644
index 0000000000..a9f30f593c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_field_lite.h
@@ -0,0 +1,278 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_FIELD_LITE_H__
+#define GOOGLE_PROTOBUF_MAP_FIELD_LITE_H__
+
+#include <google/protobuf/map.h>
+#include <google/protobuf/map_entry_lite.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// This class provides access to map field using generated api. It is used for
+// internal generated message implentation only. Users should never use this
+// directly.
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value = 0>
+class MapFieldLite {
+ // Define message type for internal repeated field.
+ typedef MapEntryLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value> EntryType;
+
+ public:
+ MapFieldLite();
+ explicit MapFieldLite(Arena* arena);
+ virtual ~MapFieldLite();
+
+ // Accessors
+ virtual const Map<Key, T>& GetMap() const;
+ virtual Map<Key, T>* MutableMap();
+
+ // Convenient methods for generated message implementation.
+ virtual int size() const;
+ virtual void Clear();
+ virtual void MergeFrom(const MapFieldLite& other);
+ virtual void Swap(MapFieldLite* other);
+
+ // Set default enum value only for proto2 map field whose value is enum type.
+ void SetDefaultEnumValue();
+
+ // Used in the implementation of parsing. Caller should take the ownership.
+ EntryType* NewEntry() const;
+ // Used in the implementation of serializing enum value type. Caller should
+ // take the ownership.
+ EntryType* NewEnumEntryWrapper(const Key& key, const T t) const;
+ // Used in the implementation of serializing other value types. Caller should
+ // take the ownership.
+ EntryType* NewEntryWrapper(const Key& key, const T& t) const;
+
+ protected:
+ // Convenient methods to get internal google::protobuf::Map
+ virtual const Map<Key, T>& GetInternalMap() const;
+ virtual Map<Key, T>* MutableInternalMap();
+
+ private:
+ typedef void DestructorSkippable_;
+
+ Arena* arena_;
+ Map<Key, T>* map_;
+
+ friend class ::google::protobuf::Arena;
+};
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::MapFieldLite()
+ : arena_(NULL) {
+ map_ = new Map<Key, T>;
+ SetDefaultEnumValue();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::MapFieldLite(Arena* arena)
+ : arena_(arena) {
+ map_ = Arena::CreateMessage<Map<Key, T> >(arena);
+ SetDefaultEnumValue();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::~MapFieldLite() {
+ delete map_;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+const Map<Key, T>&
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::GetMap() const {
+ return *map_;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+Map<Key, T>*
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::MutableMap() {
+ return map_;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+int
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::size() const {
+ return map_->size();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+void
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::Clear() {
+ map_->clear();
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+void
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::MergeFrom(
+ const MapFieldLite& other) {
+ for (typename Map<Key, T>::const_iterator it = other.map_->begin();
+ it != other.map_->end(); ++it) {
+ (*map_)[it->first] = it->second;
+ }
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+void
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::Swap(
+ MapFieldLite* other) {
+ std::swap(map_, other->map_);
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+void
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::SetDefaultEnumValue() {
+ MutableInternalMap()->SetDefaultEnumValue(default_enum_value);
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+const Map<Key, T>&
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::GetInternalMap() const {
+ return *map_;
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+Map<Key, T>*
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::MutableInternalMap() {
+ return map_;
+}
+
+#define EntryType \
+ MapEntryLite<Key, T, key_wire_type, value_wire_type, default_enum_value>
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+EntryType*
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::NewEntry() const {
+ if (arena_ == NULL) {
+ return new EntryType();
+ } else {
+ return Arena::CreateMessage<EntryType>(arena_);
+ }
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+EntryType*
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::NewEnumEntryWrapper(const Key& key,
+ const T t) const {
+ return EntryType::EnumWrap(key, t, arena_);
+}
+
+template <typename Key, typename T,
+ WireFormatLite::FieldType key_wire_type,
+ WireFormatLite::FieldType value_wire_type,
+ int default_enum_value>
+EntryType*
+MapFieldLite<Key, T, key_wire_type, value_wire_type,
+ default_enum_value>::NewEntryWrapper(const Key& key,
+ const T& t) const {
+ return EntryType::Wrap(key, t, arena_);
+}
+
+#undef EntryType
+
+// True if IsInitialized() is true for value field in all elements of t. T is
+// expected to be message. It's useful to have this helper here to keep the
+// protobuf compiler from ever having to emit loops in IsInitialized() methods.
+// We want the C++ compiler to inline this or not as it sees fit.
+template <typename Key, typename T>
+bool AllAreInitialized(const Map<Key, T>& t) {
+ for (typename Map<Key, T>::const_iterator it = t.begin(); it != t.end();
+ ++it) {
+ if (!it->second.IsInitialized()) return false;
+ }
+ return true;
+}
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_FIELD_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_field_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/map_field_test.cc
new file mode 100644
index 0000000000..dd5061c498
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_field_test.cc
@@ -0,0 +1,494 @@
+// 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.
+
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/map.h>
+#include <google/protobuf/arena_test_util.h>
+#include <google/protobuf/map_unittest.pb.h>
+#include <google/protobuf/map_test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/map_field_inl.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <gtest/gtest.h>
+namespace google {
+
+namespace protobuf {
+
+namespace internal {
+
+using unittest::TestAllTypes;
+
+class MapFieldBaseStub : public MapFieldBase {
+ public:
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ MapFieldBaseStub() {}
+ explicit MapFieldBaseStub(Arena* arena) : MapFieldBase(arena) {}
+ void SyncRepeatedFieldWithMap() const {
+ MapFieldBase::SyncRepeatedFieldWithMap();
+ }
+ void SyncMapWithRepeatedField() const {
+ MapFieldBase::SyncMapWithRepeatedField();
+ }
+ // Get underlined repeated field without synchronizing map.
+ RepeatedPtrField<Message>* InternalRepeatedField() {
+ return repeated_field_;
+ }
+ bool IsMapClean() { return state_ != 0; }
+ bool IsRepeatedClean() { return state_ != 1; }
+ void SetMapDirty() { state_ = 0; }
+ void SetRepeatedDirty() { state_ = 1; }
+ bool ContainsMapKey(const MapKey& map_key) const {
+ return false;
+ }
+ bool InsertOrLookupMapValue(const MapKey& map_key, MapValueRef* val) {
+ return false;
+ }
+ bool DeleteMapValue(const MapKey& map_key) {
+ return false;
+ }
+ bool EqualIterator(const MapIterator& a, const MapIterator& b) const {
+ return false;
+ }
+ int size() const { return 0; }
+ void MapBegin(MapIterator* map_iter) const {}
+ void MapEnd(MapIterator* map_iter) const {}
+ void InitializeIterator(MapIterator* map_iter) const {}
+ void DeleteIterator(MapIterator* map_iter) const {}
+ void CopyIterator(MapIterator* this_iterator,
+ const MapIterator& other_iterator) const {}
+ void IncreaseIterator(MapIterator* map_iter) const {}
+ void SetDefaultMessageEntry(const Message* message) const {}
+ const Message* GetDefaultMessageEntry() const { return NULL; }
+};
+
+class MapFieldBasePrimitiveTest : public ::testing::Test {
+ protected:
+ typedef MapField<int32, int32, WireFormatLite::TYPE_INT32,
+ WireFormatLite::TYPE_INT32, false> MapFieldType;
+
+ MapFieldBasePrimitiveTest() {
+ // Get descriptors
+ map_descriptor_ = unittest::TestMap::descriptor()
+ ->FindFieldByName("map_int32_int32")
+ ->message_type();
+ key_descriptor_ = map_descriptor_->FindFieldByName("key");
+ value_descriptor_ = map_descriptor_->FindFieldByName("value");
+
+ // Build map field
+ default_entry_ =
+ MessageFactory::generated_factory()->GetPrototype(map_descriptor_);
+ map_field_.reset(new MapFieldType(default_entry_));
+ map_field_base_ = map_field_.get();
+ map_ = map_field_->MutableMap();
+ initial_value_map_[0] = 100;
+ initial_value_map_[1] = 101;
+ map_->insert(initial_value_map_.begin(), initial_value_map_.end());
+ EXPECT_EQ(2, map_->size());
+ }
+
+ google::protobuf::scoped_ptr<MapFieldType> map_field_;
+ MapFieldBase* map_field_base_;
+ Map<int32, int32>* map_;
+ const Descriptor* map_descriptor_;
+ const FieldDescriptor* key_descriptor_;
+ const FieldDescriptor* value_descriptor_;
+ const Message* default_entry_;
+ std::map<int32, int32> initial_value_map_; // copy of initial values inserted
+};
+
+TEST_F(MapFieldBasePrimitiveTest, SpaceUsedExcludingSelf) {
+ EXPECT_LT(0, map_field_base_->SpaceUsedExcludingSelf());
+}
+
+TEST_F(MapFieldBasePrimitiveTest, GetRepeatedField) {
+ const RepeatedPtrField<Message>& repeated =
+ reinterpret_cast<const RepeatedPtrField<Message>&>(
+ map_field_base_->GetRepeatedField());
+ EXPECT_EQ(2, repeated.size());
+ for (int i = 0; i < repeated.size(); i++) {
+ const Message& message = repeated.Get(i);
+ int key = message.GetReflection()->GetInt32(message, key_descriptor_);
+ int value = message.GetReflection()->GetInt32(message, value_descriptor_);
+ EXPECT_EQ(value, initial_value_map_[key]);
+ }
+}
+
+TEST_F(MapFieldBasePrimitiveTest, MutableRepeatedField) {
+ RepeatedPtrField<Message>* repeated =
+ reinterpret_cast<RepeatedPtrField<Message>*>(
+ map_field_base_->MutableRepeatedField());
+ EXPECT_EQ(2, repeated->size());
+ for (int i = 0; i < repeated->size(); i++) {
+ const Message& message = repeated->Get(i);
+ int key = message.GetReflection()->GetInt32(message, key_descriptor_);
+ int value = message.GetReflection()->GetInt32(message, value_descriptor_);
+ EXPECT_EQ(value, initial_value_map_[key]);
+ }
+}
+
+TEST_F(MapFieldBasePrimitiveTest, Arena) {
+ // Allocate a large initial block to avoid mallocs during hooked test.
+ std::vector<char> arena_block(128 * 1024);
+ ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena(options);
+
+ {
+ // TODO(liujisi): Re-write the test to ensure the memory for the map and
+ // repeated fields are allocated from arenas.
+ // NoHeapChecker no_heap;
+
+ MapFieldType* map_field =
+ Arena::CreateMessage<MapFieldType>(&arena, default_entry_);
+
+ // Set content in map
+ (*map_field->MutableMap())[100] = 101;
+
+ // Trigger conversion to repeated field.
+ map_field->GetRepeatedField();
+ }
+
+ {
+ // TODO(liujisi): Re-write the test to ensure the memory for the map and
+ // repeated fields are allocated from arenas.
+ // NoHeapChecker no_heap;
+
+ MapFieldBaseStub* map_field =
+ Arena::CreateMessage<MapFieldBaseStub>(&arena);
+
+ // Trigger conversion to repeated field.
+ EXPECT_TRUE(map_field->MutableRepeatedField() != NULL);
+ }
+}
+
+namespace {
+enum State { CLEAN, MAP_DIRTY, REPEATED_DIRTY };
+} // anonymous namespace
+
+class MapFieldStateTest
+ : public testing::TestWithParam<State> {
+ public:
+ protected:
+ typedef MapField<int32, int32, WireFormatLite::TYPE_INT32,
+ WireFormatLite::TYPE_INT32, false> MapFieldType;
+ typedef MapFieldLite<int32, int32, WireFormatLite::TYPE_INT32,
+ WireFormatLite::TYPE_INT32, false> MapFieldLiteType;
+ MapFieldStateTest() : state_(GetParam()) {
+ // Build map field
+ const Descriptor* map_descriptor =
+ unittest::TestMap::descriptor()
+ ->FindFieldByName("map_int32_int32")
+ ->message_type();
+ default_entry_ =
+ MessageFactory::generated_factory()->GetPrototype(map_descriptor);
+ map_field_.reset(new MapFieldType(default_entry_));
+ map_field_base_ = map_field_.get();
+
+ Expect(map_field_.get(), MAP_DIRTY, 0, 0, true);
+ switch (state_) {
+ case CLEAN:
+ AddOneStillClean(map_field_.get());
+ break;
+ case MAP_DIRTY:
+ MakeMapDirty(map_field_.get());
+ break;
+ case REPEATED_DIRTY:
+ MakeRepeatedDirty(map_field_.get());
+ break;
+ default:
+ break;
+ }
+ }
+
+ void AddOneStillClean(MapFieldType* map_field) {
+ MapFieldBase* map_field_base = map_field;
+ Map<int32, int32>* map = map_field->MutableMap();
+ (*map)[0] = 0;
+ map_field_base->GetRepeatedField();
+ Expect(map_field, CLEAN, 1, 1, false);
+ }
+
+ void MakeMapDirty(MapFieldType* map_field) {
+ Map<int32, int32>* map = map_field->MutableMap();
+ (*map)[0] = 0;
+ Expect(map_field, MAP_DIRTY, 1, 0, true);
+ }
+
+ void MakeRepeatedDirty(MapFieldType* map_field) {
+ MakeMapDirty(map_field);
+ MapFieldBase* map_field_base = map_field;
+ map_field_base->MutableRepeatedField();
+ Map<int32, int32>* map = implicit_cast<MapFieldLiteType*>(map_field)
+ ->MapFieldLiteType::MutableMap();
+ map->clear();
+
+ Expect(map_field, REPEATED_DIRTY, 0, 1, false);
+ }
+
+ void Expect(MapFieldType* map_field, State state, int map_size,
+ int repeated_size, bool is_repeated_null) {
+ MapFieldBase* map_field_base = map_field;
+ MapFieldBaseStub* stub =
+ reinterpret_cast<MapFieldBaseStub*>(map_field_base);
+
+ Map<int32, int32>* map = implicit_cast<MapFieldLiteType*>(map_field)
+ ->MapFieldLiteType::MutableMap();
+ RepeatedPtrField<Message>* repeated_field = stub->InternalRepeatedField();
+
+ switch (state) {
+ case MAP_DIRTY:
+ EXPECT_FALSE(stub->IsMapClean());
+ EXPECT_TRUE(stub->IsRepeatedClean());
+ break;
+ case REPEATED_DIRTY:
+ EXPECT_TRUE(stub->IsMapClean());
+ EXPECT_FALSE(stub->IsRepeatedClean());
+ break;
+ case CLEAN:
+ EXPECT_TRUE(stub->IsMapClean());
+ EXPECT_TRUE(stub->IsRepeatedClean());
+ break;
+ default:
+ FAIL();
+ }
+
+ EXPECT_EQ(map_size, map->size());
+ if (is_repeated_null) {
+ EXPECT_TRUE(repeated_field == NULL);
+ } else {
+ EXPECT_EQ(repeated_size, repeated_field->size());
+ }
+ }
+
+ google::protobuf::scoped_ptr<MapFieldType> map_field_;
+ MapFieldBase* map_field_base_;
+ State state_;
+ const Message* default_entry_;
+};
+
+INSTANTIATE_TEST_CASE_P(MapFieldStateTestInstance, MapFieldStateTest,
+ ::testing::Values(CLEAN, MAP_DIRTY, REPEATED_DIRTY));
+
+TEST_P(MapFieldStateTest, GetMap) {
+ map_field_->GetMap();
+ if (state_ != MAP_DIRTY) {
+ Expect(map_field_.get(), CLEAN, 1, 1, false);
+ } else {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 0, true);
+ }
+}
+
+TEST_P(MapFieldStateTest, MutableMap) {
+ map_field_->MutableMap();
+ if (state_ != MAP_DIRTY) {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 1, false);
+ } else {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 0, true);
+ }
+}
+
+TEST_P(MapFieldStateTest, MergeFromClean) {
+ MapFieldType other(default_entry_);
+ AddOneStillClean(&other);
+
+ map_field_->MergeFrom(other);
+
+ if (state_ != MAP_DIRTY) {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 1, false);
+ } else {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 0, true);
+ }
+
+ Expect(&other, CLEAN, 1, 1, false);
+}
+
+TEST_P(MapFieldStateTest, MergeFromMapDirty) {
+ MapFieldType other(default_entry_);
+ MakeMapDirty(&other);
+
+ map_field_->MergeFrom(other);
+
+ if (state_ != MAP_DIRTY) {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 1, false);
+ } else {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 0, true);
+ }
+
+ Expect(&other, MAP_DIRTY, 1, 0, true);
+}
+
+TEST_P(MapFieldStateTest, MergeFromRepeatedDirty) {
+ MapFieldType other(default_entry_);
+ MakeRepeatedDirty(&other);
+
+ map_field_->MergeFrom(other);
+
+ if (state_ != MAP_DIRTY) {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 1, false);
+ } else {
+ Expect(map_field_.get(), MAP_DIRTY, 1, 0, true);
+ }
+
+ Expect(&other, CLEAN, 1, 1, false);
+}
+
+TEST_P(MapFieldStateTest, SwapClean) {
+ MapFieldType other(default_entry_);
+ AddOneStillClean(&other);
+
+ map_field_->Swap(&other);
+
+ Expect(map_field_.get(), CLEAN, 1, 1, false);
+
+ switch (state_) {
+ case CLEAN:
+ Expect(&other, CLEAN, 1, 1, false);
+ break;
+ case MAP_DIRTY:
+ Expect(&other, MAP_DIRTY, 1, 0, true);
+ break;
+ case REPEATED_DIRTY:
+ Expect(&other, REPEATED_DIRTY, 0, 1, false);
+ break;
+ default:
+ break;
+ }
+}
+
+TEST_P(MapFieldStateTest, SwapMapDirty) {
+ MapFieldType other(default_entry_);
+ MakeMapDirty(&other);
+
+ map_field_->Swap(&other);
+
+ Expect(map_field_.get(), MAP_DIRTY, 1, 0, true);
+
+ switch (state_) {
+ case CLEAN:
+ Expect(&other, CLEAN, 1, 1, false);
+ break;
+ case MAP_DIRTY:
+ Expect(&other, MAP_DIRTY, 1, 0, true);
+ break;
+ case REPEATED_DIRTY:
+ Expect(&other, REPEATED_DIRTY, 0, 1, false);
+ break;
+ default:
+ break;
+ }
+}
+
+TEST_P(MapFieldStateTest, SwapRepeatedDirty) {
+ MapFieldType other(default_entry_);
+ MakeRepeatedDirty(&other);
+
+ map_field_->Swap(&other);
+
+ Expect(map_field_.get(), REPEATED_DIRTY, 0, 1, false);
+
+ switch (state_) {
+ case CLEAN:
+ Expect(&other, CLEAN, 1, 1, false);
+ break;
+ case MAP_DIRTY:
+ Expect(&other, MAP_DIRTY, 1, 0, true);
+ break;
+ case REPEATED_DIRTY:
+ Expect(&other, REPEATED_DIRTY, 0, 1, false);
+ break;
+ default:
+ break;
+ }
+}
+
+TEST_P(MapFieldStateTest, Clear) {
+ map_field_->Clear();
+
+ if (state_ != MAP_DIRTY) {
+ Expect(map_field_.get(), MAP_DIRTY, 0, 1, false);
+ } else {
+ Expect(map_field_.get(), MAP_DIRTY, 0, 0, true);
+ }
+}
+
+TEST_P(MapFieldStateTest, SpaceUsedExcludingSelf) {
+ map_field_base_->SpaceUsedExcludingSelf();
+
+ switch (state_) {
+ case CLEAN:
+ Expect(map_field_.get(), CLEAN, 1, 1, false);
+ break;
+ case MAP_DIRTY:
+ Expect(map_field_.get(), MAP_DIRTY, 1, 0, true);
+ break;
+ case REPEATED_DIRTY:
+ Expect(map_field_.get(), REPEATED_DIRTY, 0, 1, false);
+ break;
+ default:
+ break;
+ }
+}
+
+TEST_P(MapFieldStateTest, GetMapField) {
+ map_field_base_->GetRepeatedField();
+
+ if (state_ != REPEATED_DIRTY) {
+ Expect(map_field_.get(), CLEAN, 1, 1, false);
+ } else {
+ Expect(map_field_.get(), REPEATED_DIRTY, 0, 1, false);
+ }
+}
+
+TEST_P(MapFieldStateTest, MutableMapField) {
+ map_field_base_->MutableRepeatedField();
+
+ if (state_ != REPEATED_DIRTY) {
+ Expect(map_field_.get(), REPEATED_DIRTY, 1, 1, false);
+ } else {
+ Expect(map_field_.get(), REPEATED_DIRTY, 0, 1, false);
+ }
+}
+
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.cc
new file mode 100644
index 0000000000..b65b4d6301
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.cc
@@ -0,0 +1,93 @@
+// 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.
+
+#include <google/protobuf/map_lite_test_util.h>
+#include <google/protobuf/map_lite_unittest.pb.h>
+#include <google/protobuf/map_test_util_impl.h>
+
+namespace google {
+namespace protobuf {
+
+void MapLiteTestUtil::SetMapFields(unittest::TestMapLite* message) {
+ MapTestUtilImpl::SetMapFields<unittest::MapEnumLite,
+ unittest::MAP_ENUM_BAR_LITE,
+ unittest::MAP_ENUM_BAZ_LITE>(message);
+}
+
+void MapLiteTestUtil::SetArenaMapFields(unittest::TestArenaMapLite* message) {
+ MapTestUtilImpl::SetArenaMapFields<unittest::MapEnumLite,
+ unittest::MAP_ENUM_BAR_LITE,
+ unittest::MAP_ENUM_BAZ_LITE>(message);
+}
+
+void MapLiteTestUtil::SetMapFieldsInitialized(unittest::TestMapLite* message) {
+ MapTestUtilImpl::SetMapFieldsInitialized(message);
+}
+
+void MapLiteTestUtil::ModifyMapFields(unittest::TestMapLite* message) {
+ MapTestUtilImpl::ModifyMapFields<unittest::MapEnumLite,
+ unittest::MAP_ENUM_FOO_LITE>(message);
+}
+
+void MapLiteTestUtil::ExpectClear(const unittest::TestMapLite& message) {
+ MapTestUtilImpl::ExpectClear(message);
+}
+
+void MapLiteTestUtil::ExpectMapFieldsSet(const unittest::TestMapLite& message) {
+ MapTestUtilImpl::ExpectMapFieldsSet<unittest::MapEnumLite,
+ unittest::MAP_ENUM_BAR_LITE,
+ unittest::MAP_ENUM_BAZ_LITE>(message);
+}
+
+void MapLiteTestUtil::ExpectArenaMapFieldsSet(
+ const unittest::TestArenaMapLite& message) {
+ MapTestUtilImpl::ExpectArenaMapFieldsSet<unittest::MapEnumLite,
+ unittest::MAP_ENUM_BAR_LITE,
+ unittest::MAP_ENUM_BAZ_LITE>(
+ message);
+}
+
+void MapLiteTestUtil::ExpectMapFieldsSetInitialized(
+ const unittest::TestMapLite& message) {
+ MapTestUtilImpl::ExpectMapFieldsSetInitialized<unittest::MapEnumLite,
+ unittest::MAP_ENUM_FOO_LITE>(
+ message);
+}
+
+void MapLiteTestUtil::ExpectMapFieldsModified(
+ const unittest::TestMapLite& message) {
+ MapTestUtilImpl::ExpectMapFieldsModified<unittest::MapEnumLite,
+ unittest::MAP_ENUM_BAR_LITE,
+ unittest::MAP_ENUM_FOO_LITE>(
+ message);
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.h
new file mode 100644
index 0000000000..66dedde5db
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_test_util.h
@@ -0,0 +1,80 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_LITE_TEST_UTIL_H__
+#define GOOGLE_PROTOBUF_MAP_LITE_TEST_UTIL_H__
+
+#include <google/protobuf/map_lite_unittest.pb.h>
+
+namespace google {
+namespace protobuf {
+
+class MapLiteTestUtil {
+ public:
+ // Set every field in the TestMapLite message to a unique value.
+ static void SetMapFields(protobuf_unittest::TestMapLite* message);
+
+ // Set every field in the TestArenaMapLite message to a unique value.
+ static void SetArenaMapFields(protobuf_unittest::TestArenaMapLite* message);
+
+ // Set every field in the message to a default value.
+ static void SetMapFieldsInitialized(protobuf_unittest::TestMapLite* message);
+
+ // Modify all the map fields of the message (which should already have been
+ // initialized with SetMapFields()).
+ static void ModifyMapFields(protobuf_unittest::TestMapLite* message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFields() is called.
+ static void ExpectMapFieldsSet(const protobuf_unittest::TestMapLite& message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFields() is called for TestArenaMapLite.
+ static void ExpectArenaMapFieldsSet(
+ const protobuf_unittest::TestArenaMapLite& message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFieldsInitialized() is called.
+ static void ExpectMapFieldsSetInitialized(
+ const protobuf_unittest::TestMapLite& message);
+
+ // Expect that the message is modified as would be expected from
+ // ModifyMapFields().
+ static void ExpectMapFieldsModified(
+ const protobuf_unittest::TestMapLite& message);
+
+ // Check that all fields are empty.
+ static void ExpectClear(const protobuf_unittest::TestMapLite& message);
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_LITE_TEST_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_unittest.proto b/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_unittest.proto
new file mode 100644
index 0000000000..0135fff305
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_lite_unittest.proto
@@ -0,0 +1,130 @@
+// 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.
+
+syntax = "proto2";
+
+option cc_enable_arenas = true;
+option optimize_for = LITE_RUNTIME;
+
+import "google/protobuf/unittest_lite.proto";
+import "google/protobuf/unittest_no_arena_lite.proto";
+
+package protobuf_unittest;
+
+message TestMapLite {
+ map<int32 , int32 > map_int32_int32 = 1;
+ map<int64 , int64 > map_int64_int64 = 2;
+ map<uint32 , uint32 > map_uint32_uint32 = 3;
+ map<uint64 , uint64 > map_uint64_uint64 = 4;
+ map<sint32 , sint32 > map_sint32_sint32 = 5;
+ map<sint64 , sint64 > map_sint64_sint64 = 6;
+ map<fixed32 , fixed32 > map_fixed32_fixed32 = 7;
+ map<fixed64 , fixed64 > map_fixed64_fixed64 = 8;
+ map<sfixed32, sfixed32> map_sfixed32_sfixed32 = 9;
+ map<sfixed64, sfixed64> map_sfixed64_sfixed64 = 10;
+ map<int32 , float > map_int32_float = 11;
+ map<int32 , double > map_int32_double = 12;
+ map<bool , bool > map_bool_bool = 13;
+ map<string , string > map_string_string = 14;
+ map<int32 , bytes > map_int32_bytes = 15;
+ map<int32 , MapEnumLite> map_int32_enum = 16;
+ map<int32 , ForeignMessageLite> map_int32_foreign_message = 17;
+ map<int32, int32> teboring = 18;
+}
+
+message TestArenaMapLite {
+ map<int32 , int32 > map_int32_int32 = 1;
+ map<int64 , int64 > map_int64_int64 = 2;
+ map<uint32 , uint32 > map_uint32_uint32 = 3;
+ map<uint64 , uint64 > map_uint64_uint64 = 4;
+ map<sint32 , sint32 > map_sint32_sint32 = 5;
+ map<sint64 , sint64 > map_sint64_sint64 = 6;
+ map<fixed32 , fixed32 > map_fixed32_fixed32 = 7;
+ map<fixed64 , fixed64 > map_fixed64_fixed64 = 8;
+ map<sfixed32, sfixed32> map_sfixed32_sfixed32 = 9;
+ map<sfixed64, sfixed64> map_sfixed64_sfixed64 = 10;
+ map<int32 , float > map_int32_float = 11;
+ map<int32 , double > map_int32_double = 12;
+ map<bool , bool > map_bool_bool = 13;
+ map<string , string > map_string_string = 14;
+ map<int32 , bytes > map_int32_bytes = 15;
+ map<int32 , MapEnumLite> map_int32_enum = 16;
+ map<int32 , ForeignMessageArenaLite> map_int32_foreign_message = 17;
+ map<int32, .protobuf_unittest_no_arena.ForeignMessageLite>
+ map_int32_foreign_message_no_arena = 18;
+}
+
+// Test embedded message with required fields
+message TestRequiredMessageMapLite {
+ map<int32, TestRequiredLite> map_field = 1;
+}
+
+message TestEnumMapLite {
+ map<int32, Proto2MapEnumLite> known_map_field = 101;
+ map<int32, Proto2MapEnumLite> unknown_map_field = 102;
+}
+
+message TestEnumMapPlusExtraLite {
+ map<int32, Proto2MapEnumPlusExtraLite> known_map_field = 101;
+ map<int32, Proto2MapEnumPlusExtraLite> unknown_map_field = 102;
+}
+
+message TestMessageMapLite {
+ map<int32, TestAllTypesLite> map_int32_message = 1;
+}
+
+enum Proto2MapEnumLite {
+ PROTO2_MAP_ENUM_FOO_LITE = 0;
+ PROTO2_MAP_ENUM_BAR_LITE = 1;
+ PROTO2_MAP_ENUM_BAZ_LITE = 2;
+}
+
+enum Proto2MapEnumPlusExtraLite {
+ E_PROTO2_MAP_ENUM_FOO_LITE = 0;
+ E_PROTO2_MAP_ENUM_BAR_LITE = 1;
+ E_PROTO2_MAP_ENUM_BAZ_LITE = 2;
+ E_PROTO2_MAP_ENUM_EXTRA_LITE = 3;
+}
+
+enum MapEnumLite {
+ MAP_ENUM_FOO_LITE = 0;
+ MAP_ENUM_BAR_LITE = 1;
+ MAP_ENUM_BAZ_LITE = 2;
+}
+
+message TestRequiredLite {
+ required int32 a = 1;
+ required int32 b = 2;
+ required int32 c = 3;
+}
+
+message ForeignMessageArenaLite {
+ optional int32 c = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_proto2_unittest.proto b/third_party/protobuf/3.0.0/src/google/protobuf/map_proto2_unittest.proto
new file mode 100644
index 0000000000..ddc2a58247
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_proto2_unittest.proto
@@ -0,0 +1,86 @@
+// 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.
+
+syntax = "proto2";
+
+
+import "google/protobuf/unittest_import.proto";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In map_test_util.h we do "using namespace unittest = protobuf_unittest".
+package protobuf_unittest;
+
+enum Proto2MapEnum {
+ PROTO2_MAP_ENUM_FOO = 0;
+ PROTO2_MAP_ENUM_BAR = 1;
+ PROTO2_MAP_ENUM_BAZ = 2;
+}
+
+enum Proto2MapEnumPlusExtra {
+ E_PROTO2_MAP_ENUM_FOO = 0;
+ E_PROTO2_MAP_ENUM_BAR = 1;
+ E_PROTO2_MAP_ENUM_BAZ = 2;
+ E_PROTO2_MAP_ENUM_EXTRA = 3;
+}
+
+message TestEnumMap {
+ map<int32, Proto2MapEnum> known_map_field = 101;
+ map<int32, Proto2MapEnum> unknown_map_field = 102;
+}
+
+message TestEnumMapPlusExtra {
+ map<int32, Proto2MapEnumPlusExtra> known_map_field = 101;
+ map<int32, Proto2MapEnumPlusExtra> unknown_map_field = 102;
+}
+
+message TestImportEnumMap {
+ map<int32, protobuf_unittest_import.ImportEnumForMap> import_enum_amp = 1;
+}
+
+message TestIntIntMap {
+ map<int32, int32> m = 1;
+}
+
+// Test all key types: string, plus the non-floating-point scalars.
+message TestMaps {
+ map<int32, TestIntIntMap> m_int32 = 1;
+ map<int64, TestIntIntMap> m_int64 = 2;
+ map<uint32, TestIntIntMap> m_uint32 = 3;
+ map<uint64, TestIntIntMap> m_uint64 = 4;
+ map<sint32, TestIntIntMap> m_sint32 = 5;
+ map<sint64, TestIntIntMap> m_sint64 = 6;
+ map<fixed32, TestIntIntMap> m_fixed32 = 7;
+ map<fixed64, TestIntIntMap> m_fixed64 = 8;
+ map<sfixed32, TestIntIntMap> m_sfixed32 = 9;
+ map<sfixed64, TestIntIntMap> m_sfixed64 = 10;
+ map<bool, TestIntIntMap> m_bool = 11;
+ map<string, TestIntIntMap> m_string = 12;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/map_test.cc
new file mode 100644
index 0000000000..03954e75f1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_test.cc
@@ -0,0 +1,3067 @@
+// 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.
+
+// A hack to include windows.h first, which ensures the GetMessage macro can
+// be undefined when we include <google/protobuf/stubs/common.h>
+#if defined(_WIN32)
+#define _WINSOCKAPI_ // to avoid re-definition in WinSock2.h
+#define NOMINMAX // to avoid defining min/max macros
+#include <windows.h>
+#endif // _WIN32
+
+#include <algorithm>
+#include <google/protobuf/stubs/hash.h>
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <set>
+#include <sstream>
+#include <vector>
+
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/arena_test_util.h>
+#include <google/protobuf/map_proto2_unittest.pb.h>
+#include <google/protobuf/map_unittest.pb.h>
+#include <google/protobuf/map_test_util.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor_database.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/map.h>
+#include <google/protobuf/map_field_inl.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/reflection.h>
+#include <google/protobuf/reflection_ops.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/util/time_util.h>
+#include <google/protobuf/util/message_differencer.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <gmock/gmock.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+
+using google::protobuf::unittest::ForeignMessage;
+using google::protobuf::unittest::TestAllTypes;
+using google::protobuf::unittest::TestMap;
+using google::protobuf::unittest::TestRecursiveMapMessage;
+
+namespace protobuf {
+namespace internal {
+
+// Map API Test =====================================================
+
+// Parameterized tests on whether to use old style maps.
+class MapImplTest : public testing::TestWithParam<bool> {
+ protected:
+ MapImplTest()
+ : map_ptr_(new Map<int32, int32>(GetParam())),
+ map_(*map_ptr_),
+ const_map_(*map_ptr_) {
+ EXPECT_TRUE(map_.empty());
+ EXPECT_EQ(0, map_.size());
+ }
+ ~MapImplTest() {}
+
+ void ExpectSingleElement(int32 key, int32 value) {
+ EXPECT_FALSE(map_.empty());
+ EXPECT_EQ(1, map_.size());
+ ExpectElement(key, value);
+ }
+
+ void ExpectElements(const std::map<int32, int32>& map) {
+ EXPECT_FALSE(map_.empty());
+ EXPECT_EQ(map.size(), map_.size());
+ for (std::map<int32, int32>::const_iterator it = map.begin();
+ it != map.end(); ++it) {
+ ExpectElement(it->first, it->second);
+ }
+ }
+
+ void ExpectElement(int32 key, int32 value) {
+ // Test map size is correct.
+ EXPECT_EQ(value, map_[key]);
+ EXPECT_EQ(1, map_.count(key));
+
+ // Check mutable at and find work correctly.
+ EXPECT_EQ(value, map_.at(key));
+ Map<int32, int32>::iterator it = map_.find(key);
+
+ // interator dereferenceable
+ EXPECT_EQ(key, (*it).first);
+ EXPECT_EQ(value, (*it).second);
+ EXPECT_EQ(key, it->first);
+ EXPECT_EQ(value, it->second);
+
+ // iterator mutable
+ ((*it).second) = value + 1;
+ EXPECT_EQ(value + 1, map_[key]);
+ ((*it).second) = value;
+ EXPECT_EQ(value, map_[key]);
+
+ it->second = value + 1;
+ EXPECT_EQ(value + 1, map_[key]);
+ it->second = value;
+ EXPECT_EQ(value, map_[key]);
+
+ // copy constructor
+ Map<int32, int32>::iterator it_copy = it;
+ EXPECT_EQ(key, it_copy->first);
+ EXPECT_EQ(value, it_copy->second);
+
+ // Immutable API ================================================
+
+ // Check immutable at and find work correctly.
+ EXPECT_EQ(value, const_map_.at(key));
+ Map<int32, int32>::const_iterator const_it = const_map_.find(key);
+
+ // interator dereferenceable
+ EXPECT_EQ(key, (*const_it).first);
+ EXPECT_EQ(value, (*const_it).second);
+ EXPECT_EQ(key, const_it->first);
+ EXPECT_EQ(value, const_it->second);
+
+ // copy constructor
+ Map<int32, int32>::const_iterator const_it_copy = const_it;
+ EXPECT_EQ(key, const_it_copy->first);
+ EXPECT_EQ(value, const_it_copy->second);
+ }
+
+ google::protobuf::scoped_ptr<Map<int32, int32> > map_ptr_;
+ Map<int32, int32>& map_;
+ const Map<int32, int32>& const_map_;
+};
+
+TEST_P(MapImplTest, OperatorBracket) {
+ int32 key = 0;
+ int32 value1 = 100;
+ int32 value2 = 101;
+
+ EXPECT_EQ(0, map_[key]);
+
+ map_[key] = value1;
+ ExpectSingleElement(key, value1);
+
+ map_[key] = value2;
+ ExpectSingleElement(key, value2);
+}
+
+TEST_P(MapImplTest, OperatorBracketNonExist) {
+ int32 key = 0;
+ int32 default_value = 0;
+
+ EXPECT_EQ(default_value, map_[key]);
+ ExpectSingleElement(key, default_value);
+}
+
+TEST_P(MapImplTest, MutableAt) {
+ int32 key = 0;
+ int32 value1 = 100;
+ int32 value2 = 101;
+
+ map_[key] = value1;
+ ExpectSingleElement(key, value1);
+
+ map_.at(key) = value2;
+ ExpectSingleElement(key, value2);
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+
+TEST_P(MapImplTest, MutableAtNonExistDeathTest) {
+ EXPECT_DEATH(map_.at(0), "");
+}
+
+TEST_P(MapImplTest, ImmutableAtNonExistDeathTest) {
+ EXPECT_DEATH(const_map_.at(0), "");
+}
+
+TEST_P(MapImplTest, UsageErrors) {
+ MapKey key;
+ key.SetInt64Value(1);
+ EXPECT_DEATH(key.GetUInt64Value(),
+ "Protocol Buffer map usage error:\n"
+ "MapKey::GetUInt64Value type does not match\n"
+ " Expected : uint64\n"
+ " Actual : int64");
+
+ MapValueRef value;
+ EXPECT_DEATH(value.SetFloatValue(0.1),
+ "Protocol Buffer map usage error:\n"
+ "MapValueRef::type MapValueRef is not initialized.");
+}
+
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST_P(MapImplTest, CountNonExist) {
+ EXPECT_EQ(0, map_.count(0));
+}
+
+TEST_P(MapImplTest, MutableFindNonExist) {
+ EXPECT_TRUE(map_.end() == map_.find(0));
+}
+
+TEST_P(MapImplTest, ImmutableFindNonExist) {
+ EXPECT_TRUE(const_map_.end() == const_map_.find(0));
+}
+
+TEST_P(MapImplTest, ConstEnd) {
+ EXPECT_TRUE(const_map_.end() == const_map_.cend());
+}
+
+TEST_P(MapImplTest, GetReferenceFromIterator) {
+ for (int i = 0; i < 10; i++) {
+ map_[i] = i;
+ }
+
+ for (Map<int32, int32>::const_iterator it = map_.cbegin();
+ it != map_.cend();) {
+ Map<int32, int32>::const_reference entry = *it++;
+ EXPECT_EQ(entry.first, entry.second);
+ }
+
+ for (Map<int32, int32>::const_iterator it = const_map_.begin();
+ it != const_map_.end();) {
+ Map<int32, int32>::const_reference entry = *it++;
+ EXPECT_EQ(entry.first, entry.second);
+ }
+
+ for (Map<int32, int32>::iterator it = map_.begin(); it != map_.end();) {
+ Map<int32, int32>::reference entry = *it++;
+ EXPECT_EQ(entry.first + 1, ++entry.second);
+ }
+}
+
+TEST_P(MapImplTest, IteratorBasic) {
+ map_[0] = 0;
+
+ // Default constructible (per forward iterator requirements).
+ Map<int, int>::const_iterator cit;
+ Map<int, int>::iterator it;
+
+ it = map_.begin();
+ cit = it; // Converts to const_iterator
+
+ // Can compare between them.
+ EXPECT_TRUE(it == cit);
+ EXPECT_FALSE(cit != it);
+
+ // Pre increment.
+ EXPECT_FALSE(it == ++cit);
+
+ // Post increment.
+ EXPECT_FALSE(it++ == cit);
+ EXPECT_TRUE(it == cit);
+}
+
+template <typename Iterator>
+static int64 median(Iterator i0, Iterator i1) {
+ vector<int64> v(i0, i1);
+ std::nth_element(v.begin(), v.begin() + v.size() / 2, v.end());
+ return v[v.size() / 2];
+}
+
+static int64 Now() {
+ return google::protobuf::util::TimeUtil::TimestampToNanoseconds(
+ google::protobuf::util::TimeUtil::GetCurrentTime());
+}
+
+// Arbitrary odd integers for creating test data.
+static int k0 = 812398771;
+static int k1 = 1312938717;
+static int k2 = 1321555333;
+
+// A naive begin() implementation will cause begin() to get slower and slower
+// if one erases elements at the "front" of the hash map, and we'd like to
+// avoid that, as std::unordered_map does.
+TEST_P(MapImplTest, BeginIsFast) {
+ // Disable this test for both new and old implementations.
+ if (/*GetParam()*/true) return;
+ Map<int32, int32> map(false); // This test uses new-style maps only.
+ const int kTestSize = 250000;
+ // Create a random-looking map of size n. Use non-negative integer keys.
+ uint32 frog = 123983;
+ int last_key = 0;
+ int counter = 0;
+ while (map.size() < kTestSize) {
+ frog *= static_cast<uint32>(k0);
+ frog ^= frog >> 17;
+ frog += counter++;
+ last_key =
+ static_cast<int>(frog) >= 0 ? static_cast<int>(frog) : last_key ^ 1;
+ GOOGLE_DCHECK_GE(last_key, 0);
+ map[last_key] = last_key ^ 1;
+ }
+ vector<int64> times;
+ // We're going to do map.erase(map.begin()) over and over again. But,
+ // just in case one iteration is fast compared to the granularity of
+ // our time keeping, we measure kChunkSize iterations per outer-loop iter.
+ const int kChunkSize = 1000;
+ GOOGLE_CHECK_EQ(kTestSize % kChunkSize, 0);
+ do {
+ const int64 start = Now();
+ for (int i = 0; i < kChunkSize; i++) {
+ map.erase(map.begin());
+ }
+ const int64 end = Now();
+ if (end > start) {
+ times.push_back(end - start);
+ }
+ } while (!map.empty());
+ if (times.size() < .99 * kTestSize / kChunkSize) {
+ GOOGLE_LOG(WARNING) << "Now() isn't helping us measure time";
+ return;
+ }
+ int64 x0 = median(times.begin(), times.begin() + 9);
+ int64 x1 = median(times.begin() + times.size() - 9, times.end());
+ GOOGLE_LOG(INFO) << "x0=" << x0 << ", x1=" << x1;
+ // x1 will greatly exceed x0 if the code we just executed took O(n^2) time.
+ // And we'll probably time out and never get here. So, this test is
+ // intentionally loose: we check that x0 and x1 are within a factor of 8.
+ EXPECT_GE(x1, x0 / 8);
+ EXPECT_GE(x0, x1 / 8);
+}
+
+// Try to create kTestSize keys that will land in just a few buckets, and
+// time the insertions, to get a rough estimate of whether an O(n^2) worst case
+// was triggered. This test is a hacky, but probably better than nothing.
+TEST_P(MapImplTest, HashFlood) {
+ const int kTestSize = 1024; // must be a power of 2
+ std::set<int> s;
+ for (int i = 0; s.size() < kTestSize; i++) {
+ if ((map_.hash_function()(i) & (kTestSize - 1)) < 3) {
+ s.insert(i);
+ }
+ }
+ // Create hash table with kTestSize entries that hash flood a table with
+ // 1024 (or 512 or 2048 or ...) entries. This assumes that map_ uses powers
+ // of 2 for table sizes, and that it's sufficient to "flood" with respect to
+ // the low bits of the output of map_.hash_function().
+ vector<int64> times;
+ std::set<int>::iterator it = s.begin();
+ int count = 0;
+ do {
+ const int64 start = Now();
+ map_[*it] = 0;
+ const int64 end = Now();
+ if (end > start) {
+ times.push_back(end - start);
+ }
+ ++count;
+ ++it;
+ } while (it != s.end());
+ if (times.size() < .99 * count) return;
+ int64 x0 = median(times.begin(), times.begin() + 9);
+ int64 x1 = median(times.begin() + times.size() - 9, times.end());
+ // x1 will greatly exceed x0 if the code we just executed took O(n^2) time.
+ // But we want to allow O(n log n). A factor of 20 should be generous enough.
+ EXPECT_LE(x1, x0 * 20);
+}
+
+template <typename T, typename U>
+static void TestValidityForAllKeysExcept(int key_to_avoid,
+ const T& check_map,
+ const U& map) {
+ typedef typename U::value_type value_type; // a key-value pair
+ for (typename U::const_iterator it = map.begin(); it != map.end(); ++it) {
+ const int key = it->first;
+ if (key == key_to_avoid) continue;
+ // All iterators relevant to this key, whether old (from check_map) or new,
+ // must point to the same memory. So, test pointer equality here.
+ const value_type* check_val = &*check_map.find(key)->second;
+ EXPECT_EQ(check_val, &*it);
+ EXPECT_EQ(check_val, &*map.find(key));
+ }
+}
+
+// EXPECT i0 and i1 to be the same. Advancing them should have the same effect,
+// too.
+template <typename Iter>
+static void TestEqualIterators(Iter i0, Iter i1, Iter end) {
+ const int kMaxAdvance = 10;
+ for (int i = 0; i < kMaxAdvance; i++) {
+ EXPECT_EQ(i0 == end, i1 == end);
+ if (i0 == end) return;
+ EXPECT_EQ(&*i0, &*i1) << "iter " << i;
+ ++i0;
+ ++i1;
+ }
+}
+
+template <typename IteratorType>
+static void TestOldVersusNewIterator(int skip, Map<int, int>* m) {
+ const int initial_size = m->size();
+ IteratorType it = m->begin();
+ for (int i = 0; i < skip && it != m->end(); it++, i++) {}
+ if (it == m->end()) return;
+ const IteratorType old = it;
+ GOOGLE_LOG(INFO) << "skip=" << skip << ", old->first=" << old->first;
+ const int target_size =
+ initial_size < 100 ? initial_size * 5 : initial_size * 5 / 4;
+ for (int i = 0; m->size() <= target_size; i++) {
+ (*m)[i] = 0;
+ }
+ // Iterator 'old' should still work just fine despite the growth of *m.
+ const IteratorType after_growth = m->find(old->first);
+ TestEqualIterators<IteratorType>(old, after_growth, m->end());
+
+ // Now shrink the number of elements. Do this with a mix of erases and
+ // inserts to increase the chance that the hashtable will resize to a lower
+ // number of buckets. (But, in any case, the test is still useful.)
+ for (int i = 0; i < 2 * (target_size - initial_size); i++) {
+ if (i != old->first) {
+ m->erase(i);
+ }
+ if (((i ^ m->begin()->first) & 15) == 0) {
+ (*m)[i * 342] = i;
+ }
+ }
+ // Now, the table has grown and shrunk; test again.
+ TestEqualIterators<IteratorType>(old, m->find(old->first), m->end());
+ TestEqualIterators<IteratorType>(old, after_growth, m->end());
+}
+
+// Create and test an n-element Map, with emphasis on iterator correctness.
+static void StressTestIterators(int n, bool test_old_style_proto2_maps) {
+ GOOGLE_LOG(INFO) << "StressTestIterators " << n;
+ GOOGLE_CHECK_GT(n, 0);
+ // Create a random-looking map of size n. Use non-negative integer keys.
+ Map<int, int> m(test_old_style_proto2_maps);
+ uint32 frog = 123987 + n;
+ int last_key = 0;
+ int counter = 0;
+ while (m.size() < n) {
+ frog *= static_cast<uint32>(k0);
+ frog ^= frog >> 17;
+ frog += counter++;
+ last_key =
+ static_cast<int>(frog) >= 0 ? static_cast<int>(frog) : last_key ^ 1;
+ GOOGLE_DCHECK_GE(last_key, 0);
+ m[last_key] = last_key ^ 1;
+ }
+ // Test it.
+ ASSERT_EQ(n, m.size());
+ // Create maps of pointers and iterators.
+ // These should remain valid even if we modify m.
+ hash_map<int, Map<int, int>::value_type*> mp(n);
+ hash_map<int, Map<int, int>::iterator> mi(n);
+ for (Map<int, int>::iterator it = m.begin(); it != m.end(); ++it) {
+ mp[it->first] = &*it;
+ mi[it->first] = it;
+ }
+ ASSERT_EQ(m.size(), mi.size());
+ ASSERT_EQ(m.size(), mp.size());
+ m.erase(last_key);
+ ASSERT_EQ(n - 1, m.size());
+ TestValidityForAllKeysExcept(last_key, mp, m);
+ TestValidityForAllKeysExcept(last_key, mi, m);
+
+ m[last_key] = 0;
+ ASSERT_EQ(n, m.size());
+ // Test old iterator vs new iterator, with table modification in between.
+ TestOldVersusNewIterator<Map<int, int>::const_iterator>(n % 3, &m);
+ TestOldVersusNewIterator<Map<int, int>::iterator>(n % (1 + (n / 40)), &m);
+ // Finally, ensure erase(iterator) doesn't reorder anything, because that is
+ // what its documentation says.
+ m[last_key] = m[last_key ^ 999] = 0;
+ vector<Map<int, int>::iterator> v;
+ v.reserve(m.size());
+ int position_of_last_key = 0;
+ for (Map<int, int>::iterator it = m.begin(); it != m.end(); ++it) {
+ if (it->first == last_key) {
+ position_of_last_key = v.size();
+ }
+ v.push_back(it);
+ }
+ ASSERT_EQ(m.size(), v.size());
+ const Map<int, int>::iterator erase_result = m.erase(m.find(last_key));
+ int index = 0;
+ for (Map<int, int>::iterator it = m.begin(); it != m.end(); ++it, ++index) {
+ if (index == position_of_last_key) {
+ EXPECT_EQ(&*erase_result, &*v[++index]);
+ }
+ ASSERT_EQ(&*it, &*v[index]);
+ }
+}
+
+TEST_P(MapImplTest, IteratorInvalidation) {
+ // As multiple underlying hash_map implementations do not follow the
+ // validation requirement, the test is disabled for old-style maps.
+ if (GetParam()) return;
+ // Create a set of pseudo-random sizes to test.
+#ifndef NDEBUG
+ const int kMaxSizeToTest = 100 * 1000;
+#else
+ const int kMaxSizeToTest = 1000 * 1000;
+#endif
+ std::set<int> s;
+ int n = kMaxSizeToTest;
+ int frog = k1 + n;
+ while (n > 1 && s.size() < 25) {
+ s.insert(n);
+ n = static_cast<int>(n * 100 / (101.0 + (frog & 63)));
+ frog *= k2;
+ frog ^= frog >> 17;
+ }
+ // Ensure we test a few small sizes.
+ s.insert(1);
+ s.insert(2);
+ s.insert(3);
+ // Now, the real work.
+ for (std::set<int>::iterator i = s.begin(); i != s.end(); ++i) {
+ StressTestIterators(*i, GetParam());
+ }
+}
+
+// Test that erase() revalidates iterators.
+TEST_P(MapImplTest, EraseRevalidates) {
+ // As multiple underlying hash_map implementations do not follow the
+ // validation requirement, the test is disabled for old-style maps.
+ if (GetParam()) return;
+ map_[3] = map_[13] = map_[20] = 0;
+ const int initial_size = map_.size();
+ EXPECT_EQ(3, initial_size);
+ vector<Map<int, int>::iterator> v;
+ for (Map<int, int>::iterator it = map_.begin(); it != map_.end(); ++it) {
+ v.push_back(it);
+ }
+ EXPECT_EQ(initial_size, v.size());
+ for (int i = 0; map_.size() <= initial_size * 20; i++) {
+ map_[i] = 0;
+ }
+ const int larger_size = map_.size();
+ // We've greatly increased the size of the map, so it is highly likely that
+ // the following will corrupt m if erase() doesn't properly revalidate
+ // iterators passed to it. Finishing this routine without crashing indicates
+ // success.
+ for (int i = 0; i < v.size(); i++) {
+ map_.erase(v[i]);
+ }
+ EXPECT_EQ(larger_size - v.size(), map_.size());
+}
+
+template <typename T>
+bool IsConstHelper(T& /*t*/) { // NOLINT. We want to catch non-const refs here.
+ return false;
+}
+template <typename T>
+bool IsConstHelper(const T& /*t*/) {
+ return true;
+}
+
+TEST_P(MapImplTest, IteratorConstness) {
+ map_[0] = 0;
+ EXPECT_TRUE(IsConstHelper(*map_.cbegin()));
+ EXPECT_TRUE(IsConstHelper(*const_map_.begin()));
+ EXPECT_FALSE(IsConstHelper(*map_.begin()));
+}
+
+bool IsForwardIteratorHelper(std::forward_iterator_tag /*tag*/) { return true; }
+template <typename T>
+bool IsForwardIteratorHelper(T /*t*/) {
+ return false;
+}
+
+TEST_P(MapImplTest, IteratorCategory) {
+ EXPECT_TRUE(IsForwardIteratorHelper(
+ std::iterator_traits<Map<int, int>::iterator>::iterator_category()));
+ EXPECT_TRUE(IsForwardIteratorHelper(std::iterator_traits<
+ Map<int, int>::const_iterator>::iterator_category()));
+}
+
+TEST_P(MapImplTest, InsertSingle) {
+ int32 key = 0;
+ int32 value1 = 100;
+ int32 value2 = 101;
+
+ // Insert a non-existed key.
+ std::pair<Map<int32, int32>::iterator, bool> result1 =
+ map_.insert(Map<int32, int32>::value_type(key, value1));
+ ExpectSingleElement(key, value1);
+
+ Map<int32, int32>::iterator it1 = result1.first;
+ EXPECT_EQ(key, it1->first);
+ EXPECT_EQ(value1, it1->second);
+ EXPECT_TRUE(result1.second);
+
+ // Insert an existed key.
+ std::pair<Map<int32, int32>::iterator, bool> result2 =
+ map_.insert(Map<int32, int32>::value_type(key, value2));
+ ExpectSingleElement(key, value1);
+
+ Map<int32, int32>::iterator it2 = result2.first;
+ EXPECT_TRUE(it1 == it2);
+ EXPECT_FALSE(result2.second);
+}
+
+TEST_P(MapImplTest, InsertByIterator) {
+ int32 key1 = 0;
+ int32 key2 = 1;
+ int32 value1a = 100;
+ int32 value1b = 101;
+ int32 value2a = 200;
+ int32 value2b = 201;
+
+ std::map<int32, int32> map1;
+ map1[key1] = value1a;
+ map1[key2] = value2a;
+
+ map_.insert(map1.begin(), map1.end());
+ ExpectElements(map1);
+
+ std::map<int32, int32> map2;
+ map2[key1] = value1b;
+ map2[key2] = value2b;
+
+ map_.insert(map2.begin(), map2.end());
+ ExpectElements(map1);
+}
+
+TEST_P(MapImplTest, EraseSingleByKey) {
+ int32 key = 0;
+ int32 value = 100;
+
+ map_[key] = value;
+ ExpectSingleElement(key, value);
+
+ // Erase an existing key.
+ EXPECT_EQ(1, map_.erase(key));
+ EXPECT_TRUE(map_.empty());
+ EXPECT_EQ(0, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(key));
+ EXPECT_TRUE(map_.begin() == map_.end());
+
+ // Erase a non-existing key.
+ EXPECT_EQ(0, map_.erase(key));
+}
+
+TEST_P(MapImplTest, EraseMutipleByKey) {
+ // erase in one specific order to trigger corner cases
+ for (int i = 0; i < 5; i++) {
+ map_[i] = i;
+ }
+
+ map_.erase(0);
+ EXPECT_EQ(4, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(0));
+
+ map_.erase(1);
+ EXPECT_EQ(3, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(1));
+
+ map_.erase(3);
+ EXPECT_EQ(2, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(3));
+
+ map_.erase(4);
+ EXPECT_EQ(1, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(4));
+
+ map_.erase(2);
+ EXPECT_EQ(0, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(2));
+}
+
+TEST_P(MapImplTest, EraseSingleByIterator) {
+ int32 key = 0;
+ int32 value = 100;
+
+ map_[key] = value;
+ ExpectSingleElement(key, value);
+
+ Map<int32, int32>::iterator it = map_.find(key);
+ map_.erase(it);
+ EXPECT_TRUE(map_.empty());
+ EXPECT_EQ(0, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(key));
+ EXPECT_TRUE(map_.begin() == map_.end());
+}
+
+TEST_P(MapImplTest, ValidIteratorAfterErase) {
+ for (int i = 0; i < 10; i++) {
+ map_[i] = i;
+ }
+
+ int count = 0;
+
+ for (Map<int32, int32>::iterator it = map_.begin(); it != map_.end();) {
+ count++;
+ if (it->first % 2 == 1) {
+ map_.erase(it++);
+ } else {
+ ++it;
+ }
+ }
+
+ EXPECT_EQ(10, count);
+ EXPECT_EQ(5, map_.size());
+}
+
+TEST_P(MapImplTest, EraseByIterator) {
+ int32 key1 = 0;
+ int32 key2 = 1;
+ int32 value1 = 100;
+ int32 value2 = 101;
+
+ std::map<int32, int32> map;
+ map[key1] = value1;
+ map[key2] = value2;
+
+ map_.insert(map.begin(), map.end());
+ ExpectElements(map);
+
+ map_.erase(map_.begin(), map_.end());
+ EXPECT_TRUE(map_.empty());
+ EXPECT_EQ(0, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(key1));
+ EXPECT_TRUE(map_.end() == map_.find(key2));
+ EXPECT_TRUE(map_.begin() == map_.end());
+}
+
+TEST_P(MapImplTest, Clear) {
+ int32 key = 0;
+ int32 value = 100;
+
+ map_[key] = value;
+ ExpectSingleElement(key, value);
+
+ map_.clear();
+
+ EXPECT_TRUE(map_.empty());
+ EXPECT_EQ(0, map_.size());
+ EXPECT_TRUE(map_.end() == map_.find(key));
+ EXPECT_TRUE(map_.begin() == map_.end());
+}
+
+static void CopyConstructorHelper(Arena* arena, Map<int32, int32>* m) {
+ int32 key1 = 0;
+ int32 key2 = 1;
+ int32 value1 = 100;
+ int32 value2 = 101;
+
+ std::map<int32, int32> map;
+ map[key1] = value1;
+ map[key2] = value2;
+
+ m->insert(map.begin(), map.end());
+
+ Map<int32, int32> other(*m);
+
+ EXPECT_EQ(2, other.size());
+ EXPECT_EQ(value1, other.at(key1));
+ EXPECT_EQ(value2, other.at(key2));
+}
+
+TEST_P(MapImplTest, CopyConstructorWithArena) {
+ Arena a;
+ CopyConstructorHelper(&a, &map_);
+}
+
+TEST_P(MapImplTest, CopyConstructorWithoutArena) {
+ CopyConstructorHelper(NULL, &map_);
+}
+
+TEST_P(MapImplTest, IterConstructor) {
+ int32 key1 = 0;
+ int32 key2 = 1;
+ int32 value1 = 100;
+ int32 value2 = 101;
+
+ std::map<int32, int32> map;
+ map[key1] = value1;
+ map[key2] = value2;
+
+ Map<int32, int32> new_map(map.begin(), map.end(),
+ GetParam());
+
+ EXPECT_EQ(2, new_map.size());
+ EXPECT_EQ(value1, new_map.at(key1));
+ EXPECT_EQ(value2, new_map.at(key2));
+}
+
+TEST_P(MapImplTest, Assigner) {
+ int32 key1 = 0;
+ int32 key2 = 1;
+ int32 value1 = 100;
+ int32 value2 = 101;
+
+ std::map<int32, int32> map;
+ map[key1] = value1;
+ map[key2] = value2;
+
+ map_.insert(map.begin(), map.end());
+
+ Map<int32, int32> other(GetParam());
+ int32 key_other = 123;
+ int32 value_other = 321;
+ other[key_other] = value_other;
+ EXPECT_EQ(1, other.size());
+
+ other = map_;
+
+ EXPECT_EQ(2, other.size());
+ EXPECT_EQ(value1, other.at(key1));
+ EXPECT_EQ(value2, other.at(key2));
+ EXPECT_TRUE(other.find(key_other) == other.end());
+
+ // Self assign
+ other = other;
+ EXPECT_EQ(2, other.size());
+ EXPECT_EQ(value1, other.at(key1));
+ EXPECT_EQ(value2, other.at(key2));
+
+ // Try assignment to a map with a different choice of "style."
+ Map<int32, int32> m(!GetParam());
+ m = other;
+ EXPECT_EQ(2, m.size());
+ EXPECT_EQ(value1, m.at(key1));
+ EXPECT_EQ(value2, m.at(key2));
+}
+
+TEST_P(MapImplTest, Rehash) {
+ const int test_size = 50;
+ std::map<int32, int32> reference_map;
+ for (int i = 0; i < test_size; i++) {
+ reference_map[i] = i;
+ }
+ for (int i = 0; i < test_size; i++) {
+ map_[i] = reference_map[i];
+ EXPECT_EQ(reference_map[i], map_[i]);
+ }
+ for (int i = 0; i < test_size; i++) {
+ map_.erase(i);
+ EXPECT_TRUE(map_.end() == map_.find(i));
+ }
+ EXPECT_TRUE(map_.empty());
+}
+
+TEST_P(MapImplTest, EqualRange) {
+ int key = 100, key_missing = 101;
+ map_[key] = 100;
+
+ std::pair<google::protobuf::Map<int32, int32>::iterator,
+ google::protobuf::Map<int32, int32>::iterator> range = map_.equal_range(key);
+ EXPECT_TRUE(map_.find(key) == range.first);
+ EXPECT_TRUE(++map_.find(key) == range.second);
+
+ range = map_.equal_range(key_missing);
+ EXPECT_TRUE(map_.end() == range.first);
+ EXPECT_TRUE(map_.end() == range.second);
+
+ std::pair<google::protobuf::Map<int32, int32>::const_iterator,
+ google::protobuf::Map<int32, int32>::const_iterator> const_range =
+ const_map_.equal_range(key);
+ EXPECT_TRUE(const_map_.find(key) == const_range.first);
+ EXPECT_TRUE(++const_map_.find(key) == const_range.second);
+
+ const_range = const_map_.equal_range(key_missing);
+ EXPECT_TRUE(const_map_.end() == const_range.first);
+ EXPECT_TRUE(const_map_.end() == const_range.second);
+}
+
+TEST_P(MapImplTest, ConvertToStdMap) {
+ map_[100] = 101;
+ std::map<int32, int32> std_map(map_.begin(), map_.end());
+ EXPECT_EQ(1, std_map.size());
+ EXPECT_EQ(101, std_map[100]);
+}
+
+TEST_P(MapImplTest, ConvertToStdVectorOfPairs) {
+ map_[100] = 101;
+ std::vector<std::pair<int32, int32> > std_vec(map_.begin(), map_.end());
+ EXPECT_EQ(1, std_vec.size());
+ EXPECT_EQ(100, std_vec[0].first);
+ EXPECT_EQ(101, std_vec[0].second);
+}
+
+TEST_P(MapImplTest, SwapSameStyle) {
+ Map<int32, int32> another(GetParam()); // same old_style_ value
+ map_[9398] = 41999;
+ another[9398] = 41999;
+ another[8070] = 42056;
+ another.swap(map_);
+ EXPECT_THAT(another, testing::UnorderedElementsAre(
+ testing::Pair(9398, 41999)));
+ EXPECT_THAT(map_, testing::UnorderedElementsAre(
+ testing::Pair(8070, 42056),
+ testing::Pair(9398, 41999)));
+}
+
+TEST_P(MapImplTest, SwapDifferentStyle) {
+ Map<int32, int32> another(!GetParam()); // different old_style_ value
+ map_[9398] = 41999;
+ another[9398] = 41999;
+ another[8070] = 42056;
+ another.swap(map_);
+ EXPECT_THAT(another, testing::UnorderedElementsAre(
+ testing::Pair(9398, 41999)));
+ EXPECT_THAT(map_, testing::UnorderedElementsAre(
+ testing::Pair(8070, 42056),
+ testing::Pair(9398, 41999)));
+}
+
+TEST_P(MapImplTest, SwapArena) {
+ Arena arena1, arena2;
+ Map<int32, int32> m1(&arena1, false);
+ Map<int32, int32> m2(&arena2, false);
+ map_[9398] = 41999;
+ m1[9398] = 41999;
+ m1[8070] = 42056;
+ m2[10244] = 10247;
+ m2[8070] = 42056;
+ m1.swap(map_);
+ EXPECT_THAT(m1, testing::UnorderedElementsAre(
+ testing::Pair(9398, 41999)));
+ EXPECT_THAT(map_, testing::UnorderedElementsAre(
+ testing::Pair(8070, 42056),
+ testing::Pair(9398, 41999)));
+ m2.swap(m1);
+ EXPECT_THAT(m1, testing::UnorderedElementsAre(
+ testing::Pair(8070, 42056),
+ testing::Pair(10244, 10247)));
+ EXPECT_THAT(m2, testing::UnorderedElementsAre(
+ testing::Pair(9398, 41999)));
+}
+
+INSTANTIATE_TEST_CASE_P(BoolSequence, MapImplTest, testing::Bool());
+
+// Map Field Reflection Test ========================================
+
+static int Func(int i, int j) {
+ return i * j;
+}
+
+static string StrFunc(int i, int j) {
+ string str;
+ SStringPrintf(&str, "%d", Func(i, j));
+ return str;
+}
+
+static int Int(const string& value) {
+ int result = 0;
+ std::istringstream(value) >> result;
+ return result;
+}
+
+class MapFieldReflectionTest : public testing::Test {
+ protected:
+ typedef FieldDescriptor FD;
+};
+
+TEST_F(MapFieldReflectionTest, RegularFields) {
+ TestMap message;
+ const Reflection* refl = message.GetReflection();
+ const Descriptor* desc = message.GetDescriptor();
+
+ Map<int32, int32>* map_int32_int32 = message.mutable_map_int32_int32();
+ Map<int32, double>* map_int32_double = message.mutable_map_int32_double();
+ Map<string, string>* map_string_string = message.mutable_map_string_string();
+ Map<int32, ForeignMessage>* map_int32_foreign_message =
+ message.mutable_map_int32_foreign_message();
+
+ for (int i = 0; i < 10; ++i) {
+ (*map_int32_int32)[i] = Func(i, 1);
+ (*map_int32_double)[i] = Func(i, 2);
+ (*map_string_string)[StrFunc(i, 1)] = StrFunc(i, 5);
+ (*map_int32_foreign_message)[i].set_c(Func(i, 6));
+ }
+
+ // Get FieldDescriptors for all the fields of interest.
+ const FieldDescriptor* fd_map_int32_int32 =
+ desc->FindFieldByName("map_int32_int32");
+ const FieldDescriptor* fd_map_int32_double =
+ desc->FindFieldByName("map_int32_double");
+ const FieldDescriptor* fd_map_string_string =
+ desc->FindFieldByName("map_string_string");
+ const FieldDescriptor* fd_map_int32_foreign_message =
+ desc->FindFieldByName("map_int32_foreign_message");
+
+ const FieldDescriptor* fd_map_int32_in32_key =
+ fd_map_int32_int32->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_int32_in32_value =
+ fd_map_int32_int32->message_type()->FindFieldByName("value");
+ const FieldDescriptor* fd_map_int32_double_key =
+ fd_map_int32_double->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_int32_double_value =
+ fd_map_int32_double->message_type()->FindFieldByName("value");
+ const FieldDescriptor* fd_map_string_string_key =
+ fd_map_string_string->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_string_string_value =
+ fd_map_string_string->message_type()->FindFieldByName("value");
+ const FieldDescriptor* fd_map_int32_foreign_message_key =
+ fd_map_int32_foreign_message->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_int32_foreign_message_value =
+ fd_map_int32_foreign_message->message_type()->FindFieldByName("value");
+
+ // Get RepeatedPtrField objects for all fields of interest.
+ const RepeatedPtrField<Message>& mf_int32_int32 =
+ refl->GetRepeatedPtrField<Message>(message, fd_map_int32_int32);
+ const RepeatedPtrField<Message>& mf_int32_double =
+ refl->GetRepeatedPtrField<Message>(message, fd_map_int32_double);
+ const RepeatedPtrField<Message>& mf_string_string =
+ refl->GetRepeatedPtrField<Message>(message, fd_map_string_string);
+ const RepeatedPtrField<Message>&
+ mf_int32_foreign_message =
+ refl->GetRepeatedPtrField<Message>(
+ message, fd_map_int32_foreign_message);
+
+ // Get mutable RepeatedPtrField objects for all fields of interest.
+ RepeatedPtrField<Message>* mmf_int32_int32 =
+ refl->MutableRepeatedPtrField<Message>(&message, fd_map_int32_int32);
+ RepeatedPtrField<Message>* mmf_int32_double =
+ refl->MutableRepeatedPtrField<Message>(&message, fd_map_int32_double);
+ RepeatedPtrField<Message>* mmf_string_string =
+ refl->MutableRepeatedPtrField<Message>(&message, fd_map_string_string);
+ RepeatedPtrField<Message>* mmf_int32_foreign_message =
+ refl->MutableRepeatedPtrField<Message>(
+ &message, fd_map_int32_foreign_message);
+
+ // Make sure we can do gets through the RepeatedPtrField objects.
+ for (int i = 0; i < 10; ++i) {
+ {
+ // Check gets through const objects.
+ const Message& message_int32_int32 = mf_int32_int32.Get(i);
+ int32 key_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_key);
+ int32 value_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_value);
+ EXPECT_EQ(value_int32_int32, Func(key_int32_int32, 1));
+
+ const Message& message_int32_double = mf_int32_double.Get(i);
+ int32 key_int32_double = message_int32_double.GetReflection()->GetInt32(
+ message_int32_double, fd_map_int32_double_key);
+ double value_int32_double =
+ message_int32_double.GetReflection()->GetDouble(
+ message_int32_double, fd_map_int32_double_value);
+ EXPECT_EQ(value_int32_double, Func(key_int32_double, 2));
+
+ const Message& message_string_string = mf_string_string.Get(i);
+ string key_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_key);
+ string value_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_value);
+ EXPECT_EQ(value_string_string, StrFunc(Int(key_string_string), 5));
+
+ const Message& message_int32_message = mf_int32_foreign_message.Get(i);
+ int32 key_int32_message = message_int32_message.GetReflection()->GetInt32(
+ message_int32_message, fd_map_int32_foreign_message_key);
+ const ForeignMessage& value_int32_message =
+ down_cast<const ForeignMessage&>(
+ message_int32_message.GetReflection()
+ ->GetMessage(message_int32_message,
+ fd_map_int32_foreign_message_value));
+ EXPECT_EQ(value_int32_message.c(), Func(key_int32_message, 6));
+ }
+
+ {
+ // Check gets through mutable objects.
+ const Message& message_int32_int32 = mmf_int32_int32->Get(i);
+ int32 key_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_key);
+ int32 value_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_value);
+ EXPECT_EQ(value_int32_int32, Func(key_int32_int32, 1));
+
+ const Message& message_int32_double = mmf_int32_double->Get(i);
+ int32 key_int32_double = message_int32_double.GetReflection()->GetInt32(
+ message_int32_double, fd_map_int32_double_key);
+ double value_int32_double =
+ message_int32_double.GetReflection()->GetDouble(
+ message_int32_double, fd_map_int32_double_value);
+ EXPECT_EQ(value_int32_double, Func(key_int32_double, 2));
+
+ const Message& message_string_string = mmf_string_string->Get(i);
+ string key_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_key);
+ string value_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_value);
+ EXPECT_EQ(value_string_string, StrFunc(Int(key_string_string), 5));
+
+ const Message& message_int32_message = mmf_int32_foreign_message->Get(i);
+ int32 key_int32_message = message_int32_message.GetReflection()->GetInt32(
+ message_int32_message, fd_map_int32_foreign_message_key);
+ const ForeignMessage& value_int32_message =
+ down_cast<const ForeignMessage&>(
+ message_int32_message.GetReflection()
+ ->GetMessage(message_int32_message,
+ fd_map_int32_foreign_message_value));
+ EXPECT_EQ(value_int32_message.c(), Func(key_int32_message, 6));
+ }
+ }
+
+ // Do sets through the RepeatedPtrField objects.
+ for (int i = 0; i < 10; i++) {
+ {
+ Message* message_int32_int32 = mmf_int32_int32->Mutable(i);
+ int32 key_int32_int32 = message_int32_int32->GetReflection()->GetInt32(
+ *message_int32_int32, fd_map_int32_in32_key);
+ message_int32_int32->GetReflection()->SetInt32(message_int32_int32,
+ fd_map_int32_in32_value,
+ Func(key_int32_int32, -1));
+
+ Message* message_int32_double = mmf_int32_double->Mutable(i);
+ int32 key_int32_double = message_int32_double->GetReflection()->GetInt32(
+ *message_int32_double, fd_map_int32_double_key);
+ message_int32_double->GetReflection()->SetDouble(
+ message_int32_double, fd_map_int32_double_value,
+ Func(key_int32_double, -2));
+
+ Message* message_string_string = mmf_string_string->Mutable(i);
+ string key_string_string =
+ message_string_string->GetReflection()->GetString(
+ *message_string_string, fd_map_string_string_key);
+ message_string_string->GetReflection()->SetString(
+ message_string_string, fd_map_string_string_value,
+ StrFunc(Int(key_string_string), -5));
+
+ Message* message_int32_message = mmf_int32_foreign_message->Mutable(i);
+ int32 key_int32_message =
+ message_int32_message->GetReflection()->GetInt32(
+ *message_int32_message, fd_map_int32_foreign_message_key);
+ ForeignMessage* value_int32_message = down_cast<ForeignMessage*>(
+ message_int32_message->GetReflection()
+ ->MutableMessage(message_int32_message,
+ fd_map_int32_foreign_message_value));
+ value_int32_message->set_c(Func(key_int32_message, -6));
+ }
+ }
+
+ // Check gets through mutable objects.
+ for (int i = 0; i < 10; i++) {
+ EXPECT_EQ(Func(i, -1), message.map_int32_int32().at(i));
+ EXPECT_EQ(Func(i, -2), message.map_int32_double().at(i));
+ EXPECT_EQ(StrFunc(i, -5), message.map_string_string().at(StrFunc(i, 1)));
+ EXPECT_EQ(Func(i, -6), message.map_int32_foreign_message().at(i).c());
+ }
+}
+
+TEST_F(MapFieldReflectionTest, RepeatedFieldRefForRegularFields) {
+ TestMap message;
+ const Reflection* refl = message.GetReflection();
+ const Descriptor* desc = message.GetDescriptor();
+
+ Map<int32, int32>* map_int32_int32 = message.mutable_map_int32_int32();
+ Map<int32, double>* map_int32_double = message.mutable_map_int32_double();
+ Map<string, string>* map_string_string = message.mutable_map_string_string();
+ Map<int32, ForeignMessage>* map_int32_foreign_message =
+ message.mutable_map_int32_foreign_message();
+
+ for (int i = 0; i < 10; ++i) {
+ (*map_int32_int32)[i] = Func(i, 1);
+ (*map_int32_double)[i] = Func(i, 2);
+ (*map_string_string)[StrFunc(i, 1)] = StrFunc(i, 5);
+ (*map_int32_foreign_message)[i].set_c(Func(i, 6));
+ }
+
+ // Get FieldDescriptors for all the fields of interest.
+ const FieldDescriptor* fd_map_int32_int32 =
+ desc->FindFieldByName("map_int32_int32");
+ const FieldDescriptor* fd_map_int32_double =
+ desc->FindFieldByName("map_int32_double");
+ const FieldDescriptor* fd_map_string_string =
+ desc->FindFieldByName("map_string_string");
+ const FieldDescriptor* fd_map_int32_foreign_message =
+ desc->FindFieldByName("map_int32_foreign_message");
+
+ const FieldDescriptor* fd_map_int32_in32_key =
+ fd_map_int32_int32->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_int32_in32_value =
+ fd_map_int32_int32->message_type()->FindFieldByName("value");
+ const FieldDescriptor* fd_map_int32_double_key =
+ fd_map_int32_double->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_int32_double_value =
+ fd_map_int32_double->message_type()->FindFieldByName("value");
+ const FieldDescriptor* fd_map_string_string_key =
+ fd_map_string_string->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_string_string_value =
+ fd_map_string_string->message_type()->FindFieldByName("value");
+ const FieldDescriptor* fd_map_int32_foreign_message_key =
+ fd_map_int32_foreign_message->message_type()->FindFieldByName("key");
+ const FieldDescriptor* fd_map_int32_foreign_message_value =
+ fd_map_int32_foreign_message->message_type()->FindFieldByName("value");
+
+ // Get RepeatedFieldRef objects for all fields of interest.
+ const RepeatedFieldRef<Message> mf_int32_int32 =
+ refl->GetRepeatedFieldRef<Message>(message, fd_map_int32_int32);
+ const RepeatedFieldRef<Message> mf_int32_double =
+ refl->GetRepeatedFieldRef<Message>(message, fd_map_int32_double);
+ const RepeatedFieldRef<Message> mf_string_string =
+ refl->GetRepeatedFieldRef<Message>(message, fd_map_string_string);
+ const RepeatedFieldRef<Message> mf_int32_foreign_message =
+ refl->GetRepeatedFieldRef<Message>(message, fd_map_int32_foreign_message);
+
+ // Get mutable RepeatedFieldRef objects for all fields of interest.
+ const MutableRepeatedFieldRef<Message> mmf_int32_int32 =
+ refl->GetMutableRepeatedFieldRef<Message>(&message, fd_map_int32_int32);
+ const MutableRepeatedFieldRef<Message> mmf_int32_double =
+ refl->GetMutableRepeatedFieldRef<Message>(&message, fd_map_int32_double);
+ const MutableRepeatedFieldRef<Message> mmf_string_string =
+ refl->GetMutableRepeatedFieldRef<Message>(&message, fd_map_string_string);
+ const MutableRepeatedFieldRef<Message>
+ mmf_int32_foreign_message =
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &message, fd_map_int32_foreign_message);
+
+ // Get entry default instances
+ google::protobuf::scoped_ptr<Message> entry_int32_int32(
+ MessageFactory::generated_factory()
+ ->GetPrototype(fd_map_int32_int32->message_type())
+ ->New());
+ google::protobuf::scoped_ptr<Message> entry_int32_double(
+ MessageFactory::generated_factory()
+ ->GetPrototype(fd_map_int32_double->message_type())
+ ->New());
+ google::protobuf::scoped_ptr<Message> entry_string_string(
+ MessageFactory::generated_factory()
+ ->GetPrototype(fd_map_string_string->message_type())
+ ->New());
+ google::protobuf::scoped_ptr<Message> entry_int32_foreign_message(
+ MessageFactory::generated_factory()
+ ->GetPrototype(fd_map_int32_foreign_message->message_type())
+ ->New());
+
+ EXPECT_EQ(10, mf_int32_int32.size());
+ EXPECT_EQ(10, mmf_int32_int32.size());
+ EXPECT_EQ(10, mf_int32_double.size());
+ EXPECT_EQ(10, mmf_int32_double.size());
+ EXPECT_EQ(10, mf_string_string.size());
+ EXPECT_EQ(10, mmf_string_string.size());
+ EXPECT_EQ(10, mf_int32_foreign_message.size());
+ EXPECT_EQ(10, mmf_int32_foreign_message.size());
+
+ EXPECT_FALSE(mf_int32_int32.empty());
+ EXPECT_FALSE(mmf_int32_int32.empty());
+ EXPECT_FALSE(mf_int32_double.empty());
+ EXPECT_FALSE(mmf_int32_double.empty());
+ EXPECT_FALSE(mf_string_string.empty());
+ EXPECT_FALSE(mmf_string_string.empty());
+ EXPECT_FALSE(mf_int32_foreign_message.empty());
+ EXPECT_FALSE(mmf_int32_foreign_message.empty());
+
+ // Make sure we can do gets through the RepeatedFieldRef objects.
+ for (int i = 0; i < 10; ++i) {
+ {
+ // Check gets through const objects.
+ const Message& message_int32_int32 =
+ mf_int32_int32.Get(i, entry_int32_int32.get());
+ int32 key_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_key);
+ int32 value_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_value);
+ EXPECT_EQ(value_int32_int32, Func(key_int32_int32, 1));
+
+ const Message& message_int32_double =
+ mf_int32_double.Get(i, entry_int32_double.get());
+ int32 key_int32_double = message_int32_double.GetReflection()->GetInt32(
+ message_int32_double, fd_map_int32_double_key);
+ double value_int32_double =
+ message_int32_double.GetReflection()->GetDouble(
+ message_int32_double, fd_map_int32_double_value);
+ EXPECT_EQ(value_int32_double, Func(key_int32_double, 2));
+
+ const Message& message_string_string =
+ mf_string_string.Get(i, entry_string_string.get());
+ string key_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_key);
+ string value_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_value);
+ EXPECT_EQ(value_string_string, StrFunc(Int(key_string_string), 5));
+
+ const Message& message_int32_message =
+ mf_int32_foreign_message.Get(i, entry_int32_foreign_message.get());
+ int32 key_int32_message = message_int32_message.GetReflection()->GetInt32(
+ message_int32_message, fd_map_int32_foreign_message_key);
+ const ForeignMessage& value_int32_message =
+ down_cast<const ForeignMessage&>(
+ message_int32_message.GetReflection()
+ ->GetMessage(message_int32_message,
+ fd_map_int32_foreign_message_value));
+ EXPECT_EQ(value_int32_message.c(), Func(key_int32_message, 6));
+ }
+
+ {
+ // Check gets through mutable objects.
+ const Message& message_int32_int32 =
+ mmf_int32_int32.Get(i, entry_int32_int32.get());
+ int32 key_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_key);
+ int32 value_int32_int32 = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_value);
+ EXPECT_EQ(value_int32_int32, Func(key_int32_int32, 1));
+
+ const Message& message_int32_double =
+ mmf_int32_double.Get(i, entry_int32_double.get());
+ int32 key_int32_double = message_int32_double.GetReflection()->GetInt32(
+ message_int32_double, fd_map_int32_double_key);
+ double value_int32_double =
+ message_int32_double.GetReflection()->GetDouble(
+ message_int32_double, fd_map_int32_double_value);
+ EXPECT_EQ(value_int32_double, Func(key_int32_double, 2));
+
+ const Message& message_string_string =
+ mmf_string_string.Get(i, entry_string_string.get());
+ string key_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_key);
+ string value_string_string =
+ message_string_string.GetReflection()->GetString(
+ message_string_string, fd_map_string_string_value);
+ EXPECT_EQ(value_string_string, StrFunc(Int(key_string_string), 5));
+
+ const Message& message_int32_message =
+ mmf_int32_foreign_message.Get(i, entry_int32_foreign_message.get());
+ int32 key_int32_message = message_int32_message.GetReflection()->GetInt32(
+ message_int32_message, fd_map_int32_foreign_message_key);
+ const ForeignMessage& value_int32_message =
+ down_cast<const ForeignMessage&>(
+ message_int32_message.GetReflection()
+ ->GetMessage(message_int32_message,
+ fd_map_int32_foreign_message_value));
+ EXPECT_EQ(value_int32_message.c(), Func(key_int32_message, 6));
+ }
+ }
+
+ // Make sure we can do sets through the RepeatedFieldRef objects.
+ for (int i = 0; i < 10; i++) {
+ const Message& message_int32_int32 =
+ mmf_int32_int32.Get(i, entry_int32_int32.get());
+ int key = message_int32_int32.GetReflection()->GetInt32(
+ message_int32_int32, fd_map_int32_in32_key);
+
+ entry_int32_int32->GetReflection()->SetInt32(
+ entry_int32_int32.get(), fd_map_int32_int32->message_type()->field(0),
+ key);
+ entry_int32_int32->GetReflection()->SetInt32(
+ entry_int32_int32.get(), fd_map_int32_int32->message_type()->field(1),
+ Func(key, -1));
+ entry_int32_double->GetReflection()->SetInt32(
+ entry_int32_double.get(), fd_map_int32_double->message_type()->field(0),
+ key);
+ entry_int32_double->GetReflection()->SetDouble(
+ entry_int32_double.get(), fd_map_int32_double->message_type()->field(1),
+ Func(key, -2));
+ entry_string_string->GetReflection()->SetString(
+ entry_string_string.get(),
+ fd_map_string_string->message_type()->field(0), StrFunc(key, 1));
+ entry_string_string->GetReflection()->SetString(
+ entry_string_string.get(),
+ fd_map_string_string->message_type()->field(1), StrFunc(key, -5));
+ entry_int32_foreign_message->GetReflection()->SetInt32(
+ entry_int32_foreign_message.get(),
+ fd_map_int32_foreign_message->message_type()->field(0), key);
+ Message* value_message =
+ entry_int32_foreign_message->GetReflection()->MutableMessage(
+ entry_int32_foreign_message.get(),
+ fd_map_int32_foreign_message->message_type()->field(1));
+ value_message->GetReflection()->SetInt32(
+ value_message, value_message->GetDescriptor()->FindFieldByName("c"),
+ Func(key, -6));
+
+ mmf_int32_int32.Set(i, *entry_int32_int32);
+ mmf_int32_double.Set(i, *entry_int32_double);
+ mmf_string_string.Set(i, *entry_string_string);
+ mmf_int32_foreign_message.Set(i, *entry_int32_foreign_message);
+ }
+
+ for (int i = 0; i < 10; i++) {
+ EXPECT_EQ(Func(i, -1), message.map_int32_int32().at(i));
+ EXPECT_EQ(Func(i, -2), message.map_int32_double().at(i));
+ EXPECT_EQ(StrFunc(i, -5), message.map_string_string().at(StrFunc(i, 1)));
+ EXPECT_EQ(Func(i, -6), message.map_int32_foreign_message().at(i).c());
+ }
+
+ // Test iterators.
+ {
+ int index = 0;
+ hash_map<int32, int32> result;
+ for (RepeatedFieldRef<Message>::iterator it = mf_int32_int32.begin();
+ it != mf_int32_int32.end(); ++it) {
+ const Message& message = *it;
+ int32 key =
+ message.GetReflection()->GetInt32(message, fd_map_int32_in32_key);
+ int32 value =
+ message.GetReflection()->GetInt32(message, fd_map_int32_in32_value);
+ result[key] = value;
+ ++index;
+ }
+ EXPECT_EQ(10, index);
+ for (hash_map<int32, int32>::const_iterator it = result.begin();
+ it != result.end(); ++it) {
+ EXPECT_EQ(message.map_int32_int32().at(it->first), it->second);
+ }
+ }
+
+ {
+ int index = 0;
+ hash_map<int32, double> result;
+ for (RepeatedFieldRef<Message>::iterator it = mf_int32_double.begin();
+ it != mf_int32_double.end(); ++it) {
+ const Message& message = *it;
+ int32 key =
+ message.GetReflection()->GetInt32(message, fd_map_int32_double_key);
+ double value = message.GetReflection()->GetDouble(
+ message, fd_map_int32_double_value);
+ result[key] = value;
+ ++index;
+ }
+ EXPECT_EQ(10, index);
+ for (hash_map<int32, double>::const_iterator it = result.begin();
+ it != result.end(); ++it) {
+ EXPECT_EQ(message.map_int32_double().at(it->first), it->second);
+ }
+ }
+
+ {
+ int index = 0;
+ hash_map<string, string> result;
+ for (RepeatedFieldRef<Message>::iterator it = mf_string_string.begin();
+ it != mf_string_string.end(); ++it) {
+ const Message& message = *it;
+ string key =
+ message.GetReflection()->GetString(message, fd_map_string_string_key);
+ string value = message.GetReflection()->GetString(
+ message, fd_map_string_string_value);
+ result[key] = value;
+ ++index;
+ }
+ EXPECT_EQ(10, index);
+ for (hash_map<string, string>::const_iterator it = result.begin();
+ it != result.end(); ++it) {
+ EXPECT_EQ(message.map_string_string().at(it->first), it->second);
+ }
+ }
+
+ {
+ int index = 0;
+ std::map<int32, ForeignMessage> result;
+ for (RepeatedFieldRef<Message>::iterator it =
+ mf_int32_foreign_message.begin();
+ it != mf_int32_foreign_message.end(); ++it) {
+ const Message& message = *it;
+ int32 key = message.GetReflection()->GetInt32(
+ message, fd_map_int32_foreign_message_key);
+ const ForeignMessage& sub_message = down_cast<const ForeignMessage&>(
+ message.GetReflection()
+ ->GetMessage(message, fd_map_int32_foreign_message_value));
+ result[key].MergeFrom(sub_message);
+ ++index;
+ }
+ EXPECT_EQ(10, index);
+ for (std::map<int32, ForeignMessage>::const_iterator it = result.begin();
+ it != result.end(); ++it) {
+ EXPECT_EQ(message.map_int32_foreign_message().at(it->first).c(),
+ it->second.c());
+ }
+ }
+
+ // Test MutableRepeatedFieldRef::Add()
+ entry_int32_int32->GetReflection()->SetInt32(
+ entry_int32_int32.get(), fd_map_int32_int32->message_type()->field(0),
+ 4321);
+ entry_int32_int32->GetReflection()->SetInt32(
+ entry_int32_int32.get(), fd_map_int32_int32->message_type()->field(1),
+ 1234);
+ mmf_int32_int32.Add(*entry_int32_int32);
+ EXPECT_EQ(1234, message.map_int32_int32().at(4321));
+
+ entry_int32_double->GetReflection()->SetInt32(
+ entry_int32_double.get(), fd_map_int32_double->message_type()->field(0),
+ 4321);
+ entry_int32_double->GetReflection()->SetDouble(
+ entry_int32_double.get(), fd_map_int32_double->message_type()->field(1),
+ 1234.0);
+ mmf_int32_double.Add(*entry_int32_double);
+ EXPECT_EQ(1234.0, message.map_int32_double().at(4321));
+
+ entry_string_string->GetReflection()->SetString(
+ entry_string_string.get(),
+ fd_map_string_string->message_type()->field(0), "4321");
+ entry_string_string->GetReflection()->SetString(
+ entry_string_string.get(), fd_map_string_string->message_type()->field(1),
+ "1234");
+ mmf_string_string.Add(*entry_string_string);
+ EXPECT_EQ("1234", message.map_string_string().at("4321"));
+
+ entry_int32_foreign_message->GetReflection()->SetInt32(
+ entry_int32_foreign_message.get(),
+ fd_map_int32_foreign_message->message_type()->field(0), 4321);
+ Message* value_message =
+ entry_int32_foreign_message->GetReflection()->MutableMessage(
+ entry_int32_foreign_message.get(),
+ fd_map_int32_foreign_message->message_type()->field(1));
+ ForeignMessage foreign_message;
+ foreign_message.set_c(1234);
+ value_message->CopyFrom(foreign_message);
+
+ mmf_int32_foreign_message.Add(*entry_int32_foreign_message);
+ EXPECT_EQ(1234, message.map_int32_foreign_message().at(4321).c());
+
+ // Test Reflection::AddAllocatedMessage
+ Message* free_entry_string_string = MessageFactory::generated_factory()
+ ->GetPrototype(fd_map_string_string->message_type())
+ ->New();
+ entry_string_string->GetReflection()->SetString(
+ free_entry_string_string,
+ fd_map_string_string->message_type()->field(0), "4321");
+ entry_string_string->GetReflection()->SetString(
+ free_entry_string_string, fd_map_string_string->message_type()->field(1),
+ "1234");
+ refl->AddAllocatedMessage(&message, fd_map_string_string,
+ free_entry_string_string);
+
+ // Test MutableRepeatedFieldRef::RemoveLast()
+ mmf_int32_int32.RemoveLast();
+ mmf_int32_double.RemoveLast();
+ mmf_string_string.RemoveLast();
+ mmf_int32_foreign_message.RemoveLast();
+ EXPECT_EQ(10, message.map_int32_int32().size());
+ EXPECT_EQ(10, message.map_int32_double().size());
+ EXPECT_EQ(11, message.map_string_string().size());
+ EXPECT_EQ(10, message.map_int32_foreign_message().size());
+
+ // Test MutableRepeatedFieldRef::SwapElements()
+ {
+ const Message& message0a = mmf_int32_int32.Get(0, entry_int32_int32.get());
+ int32 int32_value0a =
+ message0a.GetReflection()->GetInt32(message0a, fd_map_int32_in32_value);
+ const Message& message9a = mmf_int32_int32.Get(9, entry_int32_int32.get());
+ int32 int32_value9a =
+ message9a.GetReflection()->GetInt32(message9a, fd_map_int32_in32_value);
+
+ mmf_int32_int32.SwapElements(0, 9);
+
+ const Message& message0b = mmf_int32_int32.Get(0, entry_int32_int32.get());
+ int32 int32_value0b =
+ message0b.GetReflection()->GetInt32(message0b, fd_map_int32_in32_value);
+ const Message& message9b = mmf_int32_int32.Get(9, entry_int32_int32.get());
+ int32 int32_value9b =
+ message9b.GetReflection()->GetInt32(message9b, fd_map_int32_in32_value);
+
+ EXPECT_EQ(int32_value9a, int32_value0b);
+ EXPECT_EQ(int32_value0a, int32_value9b);
+ }
+
+ {
+ const Message& message0a =
+ mmf_int32_double.Get(0, entry_int32_double.get());
+ double double_value0a = message0a.GetReflection()->GetDouble(
+ message0a, fd_map_int32_double_value);
+ const Message& message9a =
+ mmf_int32_double.Get(9, entry_int32_double.get());
+ double double_value9a = message9a.GetReflection()->GetDouble(
+ message9a, fd_map_int32_double_value);
+
+ mmf_int32_double.SwapElements(0, 9);
+
+ const Message& message0b =
+ mmf_int32_double.Get(0, entry_int32_double.get());
+ double double_value0b = message0b.GetReflection()->GetDouble(
+ message0b, fd_map_int32_double_value);
+ const Message& message9b =
+ mmf_int32_double.Get(9, entry_int32_double.get());
+ double double_value9b = message9b.GetReflection()->GetDouble(
+ message9b, fd_map_int32_double_value);
+
+ EXPECT_EQ(double_value9a, double_value0b);
+ EXPECT_EQ(double_value0a, double_value9b);
+ }
+
+ {
+ const Message& message0a =
+ mmf_string_string.Get(0, entry_string_string.get());
+ string string_value0a = message0a.GetReflection()->GetString(
+ message0a, fd_map_string_string_value);
+ const Message& message9a =
+ mmf_string_string.Get(9, entry_string_string.get());
+ string string_value9a = message9a.GetReflection()->GetString(
+ message9a, fd_map_string_string_value);
+
+ mmf_string_string.SwapElements(0, 9);
+
+ const Message& message0b =
+ mmf_string_string.Get(0, entry_string_string.get());
+ string string_value0b = message0b.GetReflection()->GetString(
+ message0b, fd_map_string_string_value);
+ const Message& message9b =
+ mmf_string_string.Get(9, entry_string_string.get());
+ string string_value9b = message9b.GetReflection()->GetString(
+ message9b, fd_map_string_string_value);
+
+ EXPECT_EQ(string_value9a, string_value0b);
+ EXPECT_EQ(string_value0a, string_value9b);
+ }
+
+ {
+ const Message& message0a =
+ mmf_int32_foreign_message.Get(0, entry_int32_foreign_message.get());
+ const ForeignMessage& sub_message0a = down_cast<const ForeignMessage&>(
+ message0a.GetReflection()
+ ->GetMessage(message0a, fd_map_int32_foreign_message_value));
+ int32 int32_value0a = sub_message0a.c();
+ const Message& message9a =
+ mmf_int32_foreign_message.Get(9, entry_int32_foreign_message.get());
+ const ForeignMessage& sub_message9a = down_cast<const ForeignMessage&>(
+ message9a.GetReflection()
+ ->GetMessage(message9a, fd_map_int32_foreign_message_value));
+ int32 int32_value9a = sub_message9a.c();
+
+ mmf_int32_foreign_message.SwapElements(0, 9);
+
+ const Message& message0b =
+ mmf_int32_foreign_message.Get(0, entry_int32_foreign_message.get());
+ const ForeignMessage& sub_message0b = down_cast<const ForeignMessage&>(
+ message0b.GetReflection()
+ ->GetMessage(message0b, fd_map_int32_foreign_message_value));
+ int32 int32_value0b = sub_message0b.c();
+ const Message& message9b =
+ mmf_int32_foreign_message.Get(9, entry_int32_foreign_message.get());
+ const ForeignMessage& sub_message9b = down_cast<const ForeignMessage&>(
+ message9b.GetReflection()
+ ->GetMessage(message9b, fd_map_int32_foreign_message_value));
+ int32 int32_value9b = sub_message9b.c();
+
+ EXPECT_EQ(int32_value9a, int32_value0b);
+ EXPECT_EQ(int32_value0a, int32_value9b);
+ }
+}
+
+TEST_F(MapFieldReflectionTest, RepeatedFieldRefMergeFromAndSwap) {
+ // Set-up message content.
+ TestMap m0, m1, m2;
+ for (int i = 0; i < 10; ++i) {
+ (*m0.mutable_map_int32_int32())[i] = Func(i, 1);
+ (*m0.mutable_map_int32_double())[i] = Func(i, 2);
+ (*m0.mutable_map_string_string())[StrFunc(i, 1)] = StrFunc(i, 5);
+ (*m0.mutable_map_int32_foreign_message())[i].set_c(Func(i, 6));
+ (*m1.mutable_map_int32_int32())[i + 10] = Func(i, 11);
+ (*m1.mutable_map_int32_double())[i + 10] = Func(i, 12);
+ (*m1.mutable_map_string_string())[StrFunc(i + 10, 1)] = StrFunc(i, 15);
+ (*m1.mutable_map_int32_foreign_message())[i + 10].set_c(Func(i, 16));
+ (*m2.mutable_map_int32_int32())[i + 20] = Func(i, 21);
+ (*m2.mutable_map_int32_double())[i + 20] = Func(i, 22);
+ (*m2.mutable_map_string_string())[StrFunc(i + 20, 1)] = StrFunc(i, 25);
+ (*m2.mutable_map_int32_foreign_message())[i + 20].set_c(Func(i, 26));
+ }
+
+ const Reflection* refl = m0.GetReflection();
+ const Descriptor* desc = m0.GetDescriptor();
+
+ // Get FieldDescriptors for all the fields of interest.
+ const FieldDescriptor* fd_map_int32_int32 =
+ desc->FindFieldByName("map_int32_int32");
+ const FieldDescriptor* fd_map_int32_double =
+ desc->FindFieldByName("map_int32_double");
+ const FieldDescriptor* fd_map_string_string =
+ desc->FindFieldByName("map_string_string");
+ const FieldDescriptor* fd_map_int32_foreign_message =
+ desc->FindFieldByName("map_int32_foreign_message");
+
+ // Get MutableRepeatedFieldRef objects for all fields of interest.
+ const MutableRepeatedFieldRef<Message> mmf_int32_int32 =
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m0, fd_map_int32_int32);
+ const MutableRepeatedFieldRef<Message> mmf_int32_double =
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m0, fd_map_int32_double);
+ const MutableRepeatedFieldRef<Message> mmf_string_string =
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m0, fd_map_string_string);
+ const MutableRepeatedFieldRef<Message>
+ mmf_int32_foreign_message =
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m0, fd_map_int32_foreign_message);
+
+ // Test MutableRepeatedRef::CopyFrom
+ mmf_int32_int32.CopyFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m1, fd_map_int32_int32));
+ mmf_int32_double.CopyFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m1, fd_map_int32_double));
+ mmf_string_string.CopyFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m1, fd_map_string_string));
+ mmf_int32_foreign_message.CopyFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m1, fd_map_int32_foreign_message));
+
+ for (int i = 0; i < 10; ++i) {
+ EXPECT_EQ(Func(i, 11), m0.map_int32_int32().at(i + 10));
+ EXPECT_EQ(Func(i, 12), m0.map_int32_double().at(i + 10));
+ EXPECT_EQ(StrFunc(i, 15), m0.map_string_string().at(StrFunc(i + 10, 1)));
+ EXPECT_EQ(Func(i, 16), m0.map_int32_foreign_message().at(i + 10).c());
+ }
+
+ // Test MutableRepeatedRef::MergeFrom
+ mmf_int32_int32.MergeFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m2, fd_map_int32_int32));
+ mmf_int32_double.MergeFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m2, fd_map_int32_double));
+ mmf_string_string.MergeFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m2, fd_map_string_string));
+ mmf_int32_foreign_message.MergeFrom(
+ refl->GetRepeatedFieldRef<Message>(
+ m2, fd_map_int32_foreign_message));
+ for (int i = 0; i < 10; ++i) {
+ EXPECT_EQ(Func(i, 21), m0.map_int32_int32().at(i + 20));
+ EXPECT_EQ(Func(i, 22), m0.map_int32_double().at(i + 20));
+ EXPECT_EQ(StrFunc(i, 25), m0.map_string_string().at(StrFunc(i + 20, 1)));
+ EXPECT_EQ(Func(i, 26), m0.map_int32_foreign_message().at(i + 20).c());
+ }
+
+ // Test MutableRepeatedRef::Swap
+ // Swap between m0 and m2.
+ mmf_int32_int32.Swap(
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m2, fd_map_int32_int32));
+ mmf_int32_double.Swap(
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m2, fd_map_int32_double));
+ mmf_string_string.Swap(
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m2, fd_map_string_string));
+ mmf_int32_foreign_message.Swap(
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &m2, fd_map_int32_foreign_message));
+ for (int i = 0; i < 10; ++i) {
+ // Check the content of m0.
+ EXPECT_EQ(Func(i, 21), m0.map_int32_int32().at(i + 20));
+ EXPECT_EQ(Func(i, 22), m0.map_int32_double().at(i + 20));
+ EXPECT_EQ(StrFunc(i, 25), m0.map_string_string().at(StrFunc(i + 20, 1)));
+ EXPECT_EQ(Func(i, 26), m0.map_int32_foreign_message().at(i + 20).c());
+
+ // Check the content of m2.
+ EXPECT_EQ(Func(i, 11), m2.map_int32_int32().at(i + 10));
+ EXPECT_EQ(Func(i, 12), m2.map_int32_double().at(i + 10));
+ EXPECT_EQ(StrFunc(i, 15), m2.map_string_string().at(StrFunc(i + 10, 1)));
+ EXPECT_EQ(Func(i, 16), m2.map_int32_foreign_message().at(i + 10).c());
+ EXPECT_EQ(Func(i, 21), m2.map_int32_int32().at(i + 20));
+ EXPECT_EQ(Func(i, 22), m2.map_int32_double().at(i + 20));
+ EXPECT_EQ(StrFunc(i, 25), m2.map_string_string().at(StrFunc(i + 20, 1)));
+ EXPECT_EQ(Func(i, 26), m2.map_int32_foreign_message().at(i + 20).c());
+ }
+
+ // TODO(teboring): add test for duplicated key
+}
+
+// Generated Message Test ===========================================
+
+TEST(GeneratedMapFieldTest, Accessors) {
+ unittest::TestMap message;
+
+ MapTestUtil::SetMapFields(&message);
+ MapTestUtil::ExpectMapFieldsSet(message);
+
+ MapTestUtil::ModifyMapFields(&message);
+ MapTestUtil::ExpectMapFieldsModified(message);
+}
+
+TEST(GeneratedMapFieldTest, SetMapFieldsInitialized) {
+ unittest::TestMap message;
+
+ MapTestUtil::SetMapFieldsInitialized(&message);
+ MapTestUtil::ExpectMapFieldsSetInitialized(message);
+}
+
+TEST(GeneratedMapFieldTest, Proto2SetMapFieldsInitialized) {
+ unittest::TestEnumMap message;
+ EXPECT_EQ(unittest::PROTO2_MAP_ENUM_FOO,
+ (*message.mutable_known_map_field())[0]);
+}
+
+TEST(GeneratedMapFieldTest, Clear) {
+ unittest::TestMap message;
+
+ MapTestUtil::SetMapFields(&message);
+ message.Clear();
+ MapTestUtil::ExpectClear(message);
+}
+
+TEST(GeneratedMapFieldTest, ClearMessageMap) {
+ unittest::TestMessageMap message;
+
+ // Creates a TestAllTypes with default value
+ TestUtil::ExpectClear((*message.mutable_map_int32_message())[0]);
+}
+
+TEST(GeneratedMapFieldTest, CopyFrom) {
+ unittest::TestMap message1, message2;
+
+ MapTestUtil::SetMapFields(&message1);
+ message2.CopyFrom(message1);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+
+ // Copying from self should be a no-op.
+ message2.CopyFrom(message2);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(GeneratedMapFieldTest, CopyFromMessageMap) {
+ unittest::TestMessageMap message1, message2;
+
+ (*message1.mutable_map_int32_message())[0].add_repeated_int32(100);
+ (*message2.mutable_map_int32_message())[0].add_repeated_int32(101);
+
+ message1.CopyFrom(message2);
+
+ // Checks repeated field is overwritten.
+ EXPECT_EQ(1, message1.map_int32_message().at(0).repeated_int32_size());
+ EXPECT_EQ(101, message1.map_int32_message().at(0).repeated_int32(0));
+}
+
+TEST(GeneratedMapFieldTest, SwapWithEmpty) {
+ unittest::TestMap message1, message2;
+
+ MapTestUtil::SetMapFields(&message1);
+ MapTestUtil::ExpectMapFieldsSet(message1);
+ MapTestUtil::ExpectClear(message2);
+
+ message1.Swap(&message2);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+ MapTestUtil::ExpectClear(message1);
+}
+
+TEST(GeneratedMapFieldTest, SwapWithSelf) {
+ unittest::TestMap message;
+
+ MapTestUtil::SetMapFields(&message);
+ MapTestUtil::ExpectMapFieldsSet(message);
+
+ message.Swap(&message);
+ MapTestUtil::ExpectMapFieldsSet(message);
+}
+
+TEST(GeneratedMapFieldTest, SwapWithOther) {
+ unittest::TestMap message1, message2;
+
+ MapTestUtil::SetMapFields(&message1);
+ MapTestUtil::SetMapFields(&message2);
+ MapTestUtil::ModifyMapFields(&message2);
+
+ message1.Swap(&message2);
+ MapTestUtil::ExpectMapFieldsModified(message1);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(GeneratedMapFieldTest, CopyConstructor) {
+ unittest::TestMap message1;
+ MapTestUtil::SetMapFields(&message1);
+
+ unittest::TestMap message2(message1);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(GeneratedMapFieldTest, CopyAssignmentOperator) {
+ unittest::TestMap message1;
+ MapTestUtil::SetMapFields(&message1);
+
+ unittest::TestMap message2;
+ message2 = message1;
+ MapTestUtil::ExpectMapFieldsSet(message2);
+
+ // Make sure that self-assignment does something sane.
+ message2.operator=(message2);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+#if !defined(PROTOBUF_TEST_NO_DESCRIPTORS) || \
+ !defined(GOOGLE_PROTOBUF_NO_RTTI)
+TEST(GeneratedMapFieldTest, UpcastCopyFrom) {
+ // Test the CopyFrom method that takes in the generic const Message&
+ // parameter.
+ unittest::TestMap message1, message2;
+
+ MapTestUtil::SetMapFields(&message1);
+
+ const Message* source = implicit_cast<const Message*>(&message1);
+ message2.CopyFrom(*source);
+
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+#endif
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+
+TEST(GeneratedMapFieldTest, CopyFromDynamicMessage) {
+ // Test copying from a DynamicMessage, which must fall back to using
+ // reflection.
+ unittest::TestMap message2;
+
+ // Construct a new version of the dynamic message via the factory.
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> message1;
+ message1.reset(
+ factory.GetPrototype(unittest::TestMap::descriptor())->New());
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.SetMapFieldsViaReflection(message1.get());
+ reflection_tester.ExpectMapFieldsSetViaReflection(*message1);
+ reflection_tester.ExpectMapFieldsSetViaReflectionIterator(message1.get());
+ message2.CopyFrom(*message1);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(GeneratedMapFieldTest, CopyFromDynamicMessageMapReflection) {
+ unittest::TestMap message2;
+
+ // Construct a new version of the dynamic message via the factory.
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> message1;
+ message1.reset(
+ factory.GetPrototype(unittest::TestMap::descriptor())->New());
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.SetMapFieldsViaMapReflection(message1.get());
+ reflection_tester.ExpectMapFieldsSetViaReflection(*message1);
+ reflection_tester.ExpectMapFieldsSetViaReflectionIterator(message1.get());
+ message2.CopyFrom(*message1);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(GeneratedMapFieldTest, DynamicMessageCopyFrom) {
+ // Test copying to a DynamicMessage, which must fall back to using reflection.
+ unittest::TestMap message2;
+ MapTestUtil::SetMapFields(&message2);
+
+ // Construct a new version of the dynamic message via the factory.
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> message1;
+ message1.reset(
+ factory.GetPrototype(unittest::TestMap::descriptor())->New());
+
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ message1->MergeFrom(message2);
+ reflection_tester.ExpectMapFieldsSetViaReflection(*message1);
+ reflection_tester.ExpectMapFieldsSetViaReflectionIterator(message1.get());
+}
+
+TEST(GeneratedMapFieldTest, DynamicMessageCopyFromMapReflection) {
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ unittest::TestMap message2;
+ reflection_tester.SetMapFieldsViaMapReflection(&message2);
+
+ // Construct a dynamic message via the factory.
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> message1;
+ message1.reset(
+ factory.GetPrototype(unittest::TestMap::descriptor())->New());
+
+ message1->MergeFrom(message2);
+ reflection_tester.ExpectMapFieldsSetViaReflectionIterator(message1.get());
+ reflection_tester.ExpectMapFieldsSetViaReflection(*message1);
+}
+
+TEST(GeneratedMapFieldTest, SyncDynamicMapWithRepeatedField) {
+ // Construct a dynamic message via the factory.
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> message;
+ message.reset(
+ factory.GetPrototype(unittest::TestMap::descriptor())->New());
+ reflection_tester.SetMapFieldsViaReflection(message.get());
+ reflection_tester.ExpectMapFieldsSetViaReflectionIterator(message.get());
+ reflection_tester.ExpectMapFieldsSetViaReflection(*message);
+}
+
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+
+TEST(GeneratedMapFieldTest, NonEmptyMergeFrom) {
+ unittest::TestMap message1, message2;
+
+ MapTestUtil::SetMapFields(&message1);
+
+ // This field will test merging into an empty spot.
+ (*message2.mutable_map_int32_int32())[1] = 1;
+ message1.mutable_map_int32_int32()->erase(1);
+
+ // This tests overwriting.
+ (*message2.mutable_map_int32_double())[1] = 1;
+ (*message1.mutable_map_int32_double())[1] = 2;
+
+ message1.MergeFrom(message2);
+ MapTestUtil::ExpectMapFieldsSet(message1);
+}
+
+TEST(GeneratedMapFieldTest, MergeFromMessageMap) {
+ unittest::TestMessageMap message1, message2;
+
+ (*message1.mutable_map_int32_message())[0].add_repeated_int32(100);
+ (*message2.mutable_map_int32_message())[0].add_repeated_int32(101);
+
+ message1.MergeFrom(message2);
+
+ // Checks repeated field is overwritten.
+ EXPECT_EQ(1, message1.map_int32_message().at(0).repeated_int32_size());
+ EXPECT_EQ(101, message1.map_int32_message().at(0).repeated_int32(0));
+}
+
+// Test the generated SerializeWithCachedSizesToArray()
+TEST(GeneratedMapFieldTest, SerializationToArray) {
+ unittest::TestMap message1, message2;
+ string data;
+ MapTestUtil::SetMapFields(&message1);
+ int size = message1.ByteSize();
+ data.resize(size);
+ uint8* start = reinterpret_cast<uint8*>(string_as_array(&data));
+ uint8* end = message1.SerializeWithCachedSizesToArray(start);
+ EXPECT_EQ(size, end - start);
+ EXPECT_TRUE(message2.ParseFromString(data));
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+// Test the generated SerializeWithCachedSizes()
+TEST(GeneratedMapFieldTest, SerializationToStream) {
+ unittest::TestMap message1, message2;
+ MapTestUtil::SetMapFields(&message1);
+ int size = message1.ByteSize();
+ string data;
+ data.resize(size);
+ {
+ // Allow the output stream to buffer only one byte at a time.
+ io::ArrayOutputStream array_stream(string_as_array(&data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message1.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ }
+ EXPECT_TRUE(message2.ParseFromString(data));
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+
+TEST(GeneratedMapFieldTest, SameTypeMaps) {
+ const Descriptor* map1 = unittest::TestSameTypeMap::descriptor()
+ ->FindFieldByName("map1")
+ ->message_type();
+ const Descriptor* map2 = unittest::TestSameTypeMap::descriptor()
+ ->FindFieldByName("map2")
+ ->message_type();
+
+ const Message* map1_entry =
+ MessageFactory::generated_factory()->GetPrototype(map1);
+ const Message* map2_entry =
+ MessageFactory::generated_factory()->GetPrototype(map2);
+
+ EXPECT_EQ(map1, map1_entry->GetDescriptor());
+ EXPECT_EQ(map2, map2_entry->GetDescriptor());
+}
+
+TEST(GeneratedMapFieldTest, Proto2UnknownEnum) {
+ unittest::TestEnumMapPlusExtra from;
+ (*from.mutable_known_map_field())[0] = unittest::E_PROTO2_MAP_ENUM_FOO;
+ (*from.mutable_unknown_map_field())[0] = unittest::E_PROTO2_MAP_ENUM_EXTRA;
+ string data;
+ from.SerializeToString(&data);
+
+ unittest::TestEnumMap to;
+ EXPECT_TRUE(to.ParseFromString(data));
+ EXPECT_EQ(0, to.unknown_map_field().size());
+ const UnknownFieldSet& unknown_field_set =
+ to.GetReflection()->GetUnknownFields(to);
+ EXPECT_EQ(1, unknown_field_set.field_count());
+ EXPECT_EQ(1, to.known_map_field().size());
+ EXPECT_EQ(unittest::PROTO2_MAP_ENUM_FOO, to.known_map_field().at(0));
+
+ data.clear();
+ from.Clear();
+ to.SerializeToString(&data);
+ EXPECT_TRUE(from.ParseFromString(data));
+ EXPECT_EQ(0, from.GetReflection()->GetUnknownFields(from).field_count());
+ EXPECT_EQ(1, from.known_map_field().size());
+ EXPECT_EQ(unittest::E_PROTO2_MAP_ENUM_FOO, from.known_map_field().at(0));
+ EXPECT_EQ(1, from.unknown_map_field().size());
+ EXPECT_EQ(unittest::E_PROTO2_MAP_ENUM_EXTRA, from.unknown_map_field().at(0));
+}
+
+TEST(GeneratedMapFieldTest, StandardWireFormat) {
+ unittest::TestMap message;
+ string data = "\x0A\x04\x08\x01\x10\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(1));
+}
+
+TEST(GeneratedMapFieldTest, UnorderedWireFormat) {
+ unittest::TestMap message;
+
+ // put value before key in wire format
+ string data = "\x0A\x04\x10\x01\x08\x02";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(2));
+}
+
+TEST(GeneratedMapFieldTest, DuplicatedKeyWireFormat) {
+ unittest::TestMap message;
+
+ // Two key fields in wire format
+ string data = "\x0A\x06\x08\x01\x08\x02\x10\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(2));
+
+ // A similar test, but with a map from int to a message type.
+ // Again, we want to be sure that the "second one wins" when
+ // there are two separate entries with the same key.
+ const int key = 99;
+ unittest::TestRequiredMessageMap map_message;
+ unittest::TestRequired with_dummy4;
+ with_dummy4.set_a(0);
+ with_dummy4.set_b(0);
+ with_dummy4.set_c(0);
+ with_dummy4.set_dummy4(11);
+ (*map_message.mutable_map_field())[key] = with_dummy4;
+ string s = map_message.SerializeAsString();
+ unittest::TestRequired with_dummy5;
+ with_dummy5.set_a(0);
+ with_dummy5.set_b(0);
+ with_dummy5.set_c(0);
+ with_dummy5.set_dummy5(12);
+ (*map_message.mutable_map_field())[key] = with_dummy5;
+ string both = s + map_message.SerializeAsString();
+ // We don't expect a merge now. The "second one wins."
+ ASSERT_TRUE(map_message.ParseFromString(both));
+ ASSERT_EQ(1, map_message.map_field().size());
+ ASSERT_EQ(1, map_message.map_field().count(key));
+ EXPECT_EQ(0, map_message.map_field().find(key)->second.a());
+ EXPECT_EQ(0, map_message.map_field().find(key)->second.b());
+ EXPECT_EQ(0, map_message.map_field().find(key)->second.c());
+ EXPECT_FALSE(map_message.map_field().find(key)->second.has_dummy4());
+ ASSERT_TRUE(map_message.map_field().find(key)->second.has_dummy5());
+ EXPECT_EQ(12, map_message.map_field().find(key)->second.dummy5());
+}
+
+// Exhaustive combinations of keys, values, and junk in any order.
+// This re-tests some of the things tested above, but if it fails
+// it's more work to determine what went wrong, so it isn't necessarily
+// bad that we have the simpler tests too.
+TEST(GeneratedMapFieldTest, KeysValuesUnknownsWireFormat) {
+ unittest::TestMap message;
+ const int kMaxNumKeysAndValuesAndJunk = 4;
+ const char kKeyTag = 0x08;
+ const char kValueTag = 0x10;
+ const char kJunkTag = 0x20;
+ for (int items = 0; items <= kMaxNumKeysAndValuesAndJunk; items++) {
+ string data = "\x0A";
+ // Encode length of what will follow.
+ data.push_back(items * 2);
+ static const int kBitsOfIPerItem = 4;
+ static const int mask = (1 << kBitsOfIPerItem) - 1;
+ // Each iteration of the following is a test. It uses i as bit vector
+ // encoding the keys and values to put in the wire format.
+ for (int i = 0; i < (1 << (items * kBitsOfIPerItem)); i++) {
+ string wire_format = data;
+ int expected_key = 0;
+ int expected_value = 0;
+ for (int k = i, j = 0; j < items; j++, k >>= kBitsOfIPerItem) {
+ bool is_key = k & 0x1;
+ bool is_value = !is_key && (k & 0x2);
+ wire_format.push_back(is_key ? kKeyTag :
+ is_value ? kValueTag : kJunkTag);
+ char c = static_cast<char>(k & mask) >> 2; // One char after the tag.
+ wire_format.push_back(c);
+ if (is_key) expected_key = static_cast<int>(c);
+ if (is_value) expected_value = static_cast<int>(c);
+ ASSERT_TRUE(message.ParseFromString(wire_format));
+ ASSERT_EQ(1, message.map_int32_int32().size());
+ ASSERT_EQ(expected_key, message.map_int32_int32().begin()->first);
+ ASSERT_EQ(expected_value, message.map_int32_int32().begin()->second);
+ }
+ }
+ }
+}
+
+TEST(GeneratedMapFieldTest, DuplicatedValueWireFormat) {
+ unittest::TestMap message;
+
+ // Two value fields in wire format
+ string data = "\x0A\x06\x08\x01\x10\x01\x10\x02";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(2, message.map_int32_int32().at(1));
+}
+
+TEST(GeneratedMapFieldTest, MissedKeyWireFormat) {
+ unittest::TestMap message;
+
+ // No key field in wire format
+ string data = "\x0A\x02\x10\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int32_int32().at(0));
+}
+
+TEST(GeneratedMapFieldTest, MissedValueWireFormat) {
+ unittest::TestMap message;
+
+ // No value field in wire format
+ string data = "\x0A\x02\x08\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(0, message.map_int32_int32().at(1));
+}
+
+TEST(GeneratedMapFieldTest, MissedValueTextFormat) {
+ unittest::TestMap message;
+
+ // No value field in text format
+ string text =
+ "map_int32_foreign_message {\n"
+ " key: 1234567890\n"
+ "}";
+
+ EXPECT_TRUE(google::protobuf::TextFormat::ParseFromString(text, &message));
+ EXPECT_EQ(1, message.map_int32_foreign_message().size());
+ EXPECT_EQ(11, message.ByteSize());
+}
+
+TEST(GeneratedMapFieldTest, UnknownFieldWireFormat) {
+ unittest::TestMap message;
+
+ // Unknown field in wire format
+ string data = "\x0A\x06\x08\x02\x10\x03\x18\x01";
+
+ EXPECT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(3, message.map_int32_int32().at(2));
+}
+
+TEST(GeneratedMapFieldTest, CorruptedWireFormat) {
+ unittest::TestMap message;
+
+ // corrupted data in wire format
+ string data = "\x0A\x06\x08\x02\x11\x03";
+
+ EXPECT_FALSE(message.ParseFromString(data));
+}
+
+TEST(GeneratedMapFieldTest, IsInitialized) {
+ unittest::TestRequiredMessageMap map_message;
+
+ // Add an uninitialized message.
+ (*map_message.mutable_map_field())[0];
+ EXPECT_FALSE(map_message.IsInitialized());
+
+ // Initialize uninitialized message
+ (*map_message.mutable_map_field())[0].set_a(0);
+ (*map_message.mutable_map_field())[0].set_b(0);
+ (*map_message.mutable_map_field())[0].set_c(0);
+ EXPECT_TRUE(map_message.IsInitialized());
+}
+
+TEST(GeneratedMapFieldTest, MessagesMustMerge) {
+ unittest::TestRequiredMessageMap map_message;
+ unittest::TestRequired with_dummy4;
+ with_dummy4.set_a(97);
+ with_dummy4.set_b(0);
+ with_dummy4.set_c(0);
+ with_dummy4.set_dummy4(98);
+
+ EXPECT_TRUE(with_dummy4.IsInitialized());
+ (*map_message.mutable_map_field())[0] = with_dummy4;
+ EXPECT_TRUE(map_message.IsInitialized());
+ string s = map_message.SerializeAsString();
+
+ // Modify s so that there are two values in the entry for key 0.
+ // The first will have no value for c. The second will have no value for a.
+ // Those are required fields. Also, make some other little changes, to
+ // ensure we are merging the two values (because they're messages).
+ ASSERT_EQ(s.size() - 2, s[1]); // encoding of the length of what follows
+ string encoded_val(s.data() + 4, s.data() + s.size());
+ // In s, change the encoding of c to an encoding of dummy32.
+ s[s.size() - 3] -= 8;
+ // Make encoded_val slightly different from what's in s.
+ encoded_val[encoded_val.size() - 1] += 33; // Encode c = 33.
+ for (int i = 0; i < encoded_val.size(); i++) {
+ if (encoded_val[i] == 97) {
+ // Encode b = 91 instead of a = 97. But this won't matter, because
+ // we also encode b = 0 right after this. The point is to leave out
+ // a required field, and make sure the parser doesn't complain, because
+ // every required field is set after the merge of the two values.
+ encoded_val[i - 1] += 16;
+ encoded_val[i] = 91;
+ } else if (encoded_val[i] == 98) {
+ // Encode dummy5 = 99 instead of dummy4 = 98.
+ encoded_val[i - 1] += 8; // The tag for dummy5 is 8 more.
+ encoded_val[i]++;
+ break;
+ }
+ }
+
+ s += encoded_val; // Add the second message.
+ s[1] += encoded_val.size(); // Adjust encoded size.
+
+ // Test key then value then value.
+ int key = 0;
+ ASSERT_TRUE(map_message.ParseFromString(s));
+ ASSERT_EQ(1, map_message.map_field().size());
+ ASSERT_EQ(1, map_message.map_field().count(key));
+ EXPECT_EQ(97, map_message.map_field().find(key)->second.a());
+ EXPECT_EQ(0, map_message.map_field().find(key)->second.b());
+ EXPECT_EQ(33, map_message.map_field().find(key)->second.c());
+ EXPECT_EQ(98, map_message.map_field().find(key)->second.dummy4());
+ EXPECT_EQ(99, map_message.map_field().find(key)->second.dummy5());
+
+ // Test key then value then value then key.
+ s.push_back(s[2]); // Copy the key's tag.
+ key = 19;
+ s.push_back(key); // Second key is 19 instead of 0.
+ s[1] += 2; // Adjust encoded size.
+ ASSERT_TRUE(map_message.ParseFromString(s));
+ ASSERT_EQ(1, map_message.map_field().size());
+ ASSERT_EQ(1, map_message.map_field().count(key));
+ EXPECT_EQ(97, map_message.map_field().find(key)->second.a());
+ EXPECT_EQ(0, map_message.map_field().find(key)->second.b());
+ EXPECT_EQ(33, map_message.map_field().find(key)->second.c());
+ EXPECT_EQ(98, map_message.map_field().find(key)->second.dummy4());
+ EXPECT_EQ(99, map_message.map_field().find(key)->second.dummy5());
+}
+
+// Generated Message Reflection Test ================================
+
+TEST(GeneratedMapFieldReflectionTest, SpaceUsed) {
+ unittest::TestMap message;
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.SetMapFieldsViaReflection(&message);
+
+ EXPECT_LT(0, message.GetReflection()->SpaceUsed(message));
+}
+
+TEST(GeneratedMapFieldReflectionTest, Accessors) {
+ // Set every field to a unique value then go back and check all those
+ // values.
+ unittest::TestMap message;
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.SetMapFieldsViaReflection(&message);
+ MapTestUtil::ExpectMapFieldsSet(message);
+ reflection_tester.ExpectMapFieldsSetViaReflection(message);
+ reflection_tester.ExpectMapFieldsSetViaReflectionIterator(&message);
+
+ reflection_tester.ModifyMapFieldsViaReflection(&message);
+ MapTestUtil::ExpectMapFieldsModified(message);
+}
+
+TEST(GeneratedMapFieldReflectionTest, Swap) {
+ unittest::TestMap message1;
+ unittest::TestMap message2;
+
+ MapTestUtil::SetMapFields(&message1);
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+
+ MapTestUtil::ExpectClear(message1);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(GeneratedMapFieldReflectionTest, SwapWithBothSet) {
+ unittest::TestMap message1;
+ unittest::TestMap message2;
+
+ MapTestUtil::SetMapFields(&message1);
+ MapTestUtil::SetMapFields(&message2);
+ MapTestUtil::ModifyMapFields(&message2);
+
+ const Reflection* reflection = message1.GetReflection();
+ reflection->Swap(&message1, &message2);
+
+ MapTestUtil::ExpectMapFieldsModified(message1);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(GeneratedMapFieldReflectionTest, SwapFields) {
+ unittest::TestMap message1;
+ unittest::TestMap message2;
+
+ MapTestUtil::SetMapFields(&message2);
+
+ vector<const FieldDescriptor*> fields;
+ const Reflection* reflection = message1.GetReflection();
+ reflection->ListFields(message2, &fields);
+ reflection->SwapFields(&message1, &message2, fields);
+
+ MapTestUtil::ExpectMapFieldsSet(message1);
+ MapTestUtil::ExpectClear(message2);
+}
+
+TEST(GeneratedMapFieldReflectionTest, ClearField) {
+ unittest::TestMap message;
+ MapTestUtil::SetMapFields(&message);
+ MapTestUtil::ExpectMapFieldsSet(message);
+
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.ClearMapFieldsViaReflection(&message);
+ reflection_tester.ExpectClearViaReflection(message);
+ reflection_tester.ExpectClearViaReflectionIterator(&message);
+}
+
+TEST(GeneratedMapFieldReflectionTest, RemoveLast) {
+ unittest::TestMap message;
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+
+ MapTestUtil::SetMapFields(&message);
+ MapTestUtil::ExpectMapsSize(message, 2);
+ std::vector<const Message*> expected_entries =
+ MapTestUtil::GetMapEntries(message, 0);
+
+ reflection_tester.RemoveLastMapsViaReflection(&message);
+
+ MapTestUtil::ExpectMapsSize(message, 1);
+ std::vector<const Message*> remained_entries =
+ MapTestUtil::GetMapEntries(message, 0);
+ EXPECT_TRUE(expected_entries == remained_entries);
+}
+
+TEST(GeneratedMapFieldReflectionTest, ReleaseLast) {
+ unittest::TestMap message;
+ const Descriptor* descriptor = message.GetDescriptor();
+ MapReflectionTester reflection_tester(descriptor);
+
+ MapTestUtil::SetMapFields(&message);
+
+ MapTestUtil::ExpectMapsSize(message, 2);
+
+ reflection_tester.ReleaseLastMapsViaReflection(&message);
+
+ MapTestUtil::ExpectMapsSize(message, 1);
+
+ // Now test that we actually release the right message.
+ message.Clear();
+ MapTestUtil::SetMapFields(&message);
+
+ MapTestUtil::ExpectMapsSize(message, 2);
+ std::vector<const Message*> expect_last =
+ MapTestUtil::GetMapEntries(message, 1);
+ std::vector<const Message*> release_last =
+ MapTestUtil::GetMapEntriesFromRelease(&message);
+ MapTestUtil::ExpectMapsSize(message, 1);
+ EXPECT_TRUE(expect_last == release_last);
+ for (std::vector<const Message*>::iterator it = release_last.begin();
+ it != release_last.end(); ++it) {
+ delete *it;
+ }
+}
+
+TEST(GeneratedMapFieldReflectionTest, SwapElements) {
+ unittest::TestMap message;
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+
+ MapTestUtil::SetMapFields(&message);
+
+ // Get pointers of map entries at their original position
+ std::vector<const Message*> entries0 = MapTestUtil::GetMapEntries(message, 0);
+ std::vector<const Message*> entries1 = MapTestUtil::GetMapEntries(message, 1);
+
+ // Swap the first time.
+ reflection_tester.SwapMapsViaReflection(&message);
+
+ // Get pointer of map entry after swap once.
+ std::vector<const Message*> entries0_once =
+ MapTestUtil::GetMapEntries(message, 0);
+ std::vector<const Message*> entries1_once =
+ MapTestUtil::GetMapEntries(message, 1);
+
+ // Test map entries are swapped.
+ MapTestUtil::ExpectMapsSize(message, 2);
+ EXPECT_TRUE(entries0 == entries1_once);
+ EXPECT_TRUE(entries1 == entries0_once);
+
+ // Swap the second time.
+ reflection_tester.SwapMapsViaReflection(&message);
+
+ // Get pointer of map entry after swap once.
+ std::vector<const Message*> entries0_twice =
+ MapTestUtil::GetMapEntries(message, 0);
+ std::vector<const Message*> entries1_twice =
+ MapTestUtil::GetMapEntries(message, 1);
+
+ // Test map entries are swapped back.
+ MapTestUtil::ExpectMapsSize(message, 2);
+ EXPECT_TRUE(entries0 == entries0_twice);
+ EXPECT_TRUE(entries1 == entries1_twice);
+}
+
+TEST(GeneratedMapFieldReflectionTest, MutableUnknownFields) {
+ unittest::TestMap message;
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.MutableUnknownFieldsOfMapFieldsViaReflection(&message);
+}
+
+TEST(GeneratedMapFieldReflectionTest, EmbedProto2Message) {
+ unittest::TestMessageMap message;
+
+ const FieldDescriptor* map_field =
+ unittest::TestMessageMap::descriptor()->FindFieldByName(
+ "map_int32_message");
+ const FieldDescriptor* value =
+ map_field->message_type()->FindFieldByName("value");
+
+ Message* entry_message =
+ message.GetReflection()->AddMessage(&message, map_field);
+ EXPECT_EQ(
+ &entry_message->GetReflection()->GetMessage(*entry_message, value),
+ reinterpret_cast<const Message*>(&TestAllTypes::default_instance()));
+
+ Message* proto2_message =
+ entry_message->GetReflection()->MutableMessage(entry_message, value);
+ EXPECT_EQ(unittest::TestAllTypes::descriptor(),
+ proto2_message->GetDescriptor());
+ ASSERT_EQ(1, message.map_int32_message().size());
+}
+
+TEST(GeneratedMapFieldReflectionTest, MergeFromClearMapEntry) {
+ unittest::TestMap message;
+ const FieldDescriptor* map_field =
+ unittest::TestMap::descriptor()->FindFieldByName("map_int32_int32");
+ const FieldDescriptor* key =
+ map_field->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value =
+ map_field->message_type()->FindFieldByName("value");
+
+ Message* entry_message1 =
+ message.GetReflection()->AddMessage(&message, map_field);
+ EXPECT_FALSE(entry_message1->GetReflection()->HasField(*entry_message1, key));
+ EXPECT_FALSE(
+ entry_message1->GetReflection()->HasField(*entry_message1, value));
+
+ Message* entry_message2 =
+ message.GetReflection()->AddMessage(&message, map_field);
+ EXPECT_FALSE(entry_message2->GetReflection()->HasField(*entry_message2, key));
+ EXPECT_FALSE(
+ entry_message2->GetReflection()->HasField(*entry_message2, value));
+
+ entry_message1->MergeFrom(*entry_message2);
+ EXPECT_FALSE(entry_message1->GetReflection()->HasField(*entry_message1, key));
+ EXPECT_FALSE(
+ entry_message1->GetReflection()->HasField(*entry_message1, value));
+}
+
+TEST(GeneratedMapFieldReflectionTest, MapEntryClear) {
+ unittest::TestMap message;
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.MutableUnknownFieldsOfMapFieldsViaReflection(&message);
+}
+
+TEST(GeneratedMapFieldReflectionTest, Proto2MapEntryClear) {
+ unittest::TestEnumMap message;
+ const Descriptor* descriptor = message.GetDescriptor();
+ const FieldDescriptor* field_descriptor =
+ descriptor->FindFieldByName("known_map_field");
+ const FieldDescriptor* value_descriptor =
+ field_descriptor->message_type()->FindFieldByName("value");
+ Message* sub_message =
+ message.GetReflection()->AddMessage(&message, field_descriptor);
+ EXPECT_EQ(0, sub_message->GetReflection()->GetEnumValue(*sub_message,
+ value_descriptor));
+}
+
+// Map Reflection API Test =========================================
+
+TEST(GeneratedMapFieldReflectionTest, SetViaMapReflection) {
+ unittest::TestMap message;
+ MapReflectionTester reflection_tester(
+ unittest::TestMap::descriptor());
+ reflection_tester.SetMapFieldsViaMapReflection(&message);
+ reflection_tester.ExpectMapFieldsSetViaReflection(message);
+ reflection_tester.ExpectMapFieldsSetViaReflectionIterator(&message);
+}
+
+// Dynamic Message Test =============================================
+
+class MapFieldInDynamicMessageTest : public testing::Test {
+ protected:
+ const DescriptorPool* pool_;
+ DynamicMessageFactory factory_;
+ const Descriptor* map_descriptor_;
+ const Descriptor* recursive_map_descriptor_;
+ const Message* map_prototype_;
+
+ MapFieldInDynamicMessageTest()
+ : pool_(DescriptorPool::generated_pool()), factory_(pool_) {}
+
+ virtual void SetUp() {
+ map_descriptor_ =
+ pool_->FindMessageTypeByName("protobuf_unittest.TestMap");
+ recursive_map_descriptor_ =
+ pool_->FindMessageTypeByName("protobuf_unittest.TestRecursiveMapMessage");
+ ASSERT_TRUE(map_descriptor_ != NULL);
+ ASSERT_TRUE(recursive_map_descriptor_ != NULL);
+ map_prototype_ = factory_.GetPrototype(map_descriptor_);
+ }
+};
+
+TEST_F(MapFieldInDynamicMessageTest, MapIndependentOffsets) {
+ // Check that all fields have independent offsets by setting each
+ // one to a unique value then checking that they all still have those
+ // unique values (i.e. they don't stomp each other).
+ google::protobuf::scoped_ptr<Message> message(map_prototype_->New());
+ MapReflectionTester reflection_tester(map_descriptor_);
+
+ reflection_tester.SetMapFieldsViaReflection(message.get());
+ reflection_tester.ExpectMapFieldsSetViaReflection(*message);
+}
+
+TEST_F(MapFieldInDynamicMessageTest, DynamicMapReflection) {
+ // Check that map fields work properly.
+ google::protobuf::scoped_ptr<Message> message(map_prototype_->New());
+
+ // Check set functions.
+ MapReflectionTester reflection_tester(map_descriptor_);
+ reflection_tester.SetMapFieldsViaMapReflection(message.get());
+ reflection_tester.ExpectMapFieldsSetViaReflection(*message);
+}
+
+TEST_F(MapFieldInDynamicMessageTest, MapSpaceUsed) {
+ // Test that SpaceUsed() works properly
+
+ // Since we share the implementation with generated messages, we don't need
+ // to test very much here. Just make sure it appears to be working.
+
+ google::protobuf::scoped_ptr<Message> message(map_prototype_->New());
+ MapReflectionTester reflection_tester(map_descriptor_);
+
+ int initial_space_used = message->SpaceUsed();
+
+ reflection_tester.SetMapFieldsViaReflection(message.get());
+ EXPECT_LT(initial_space_used, message->SpaceUsed());
+}
+
+TEST_F(MapFieldInDynamicMessageTest, RecursiveMap) {
+ TestRecursiveMapMessage from;
+ (*from.mutable_a())[""];
+ string data = from.SerializeAsString();
+ google::protobuf::scoped_ptr<Message> to(
+ factory_.GetPrototype(recursive_map_descriptor_)->New());
+ ASSERT_TRUE(to->ParseFromString(data));
+}
+
+// ReflectionOps Test ===============================================
+
+TEST(ReflectionOpsForMapFieldTest, MapSanityCheck) {
+ unittest::TestMap message;
+
+ MapTestUtil::SetMapFields(&message);
+ MapTestUtil::ExpectMapFieldsSet(message);
+}
+
+TEST(ReflectionOpsForMapFieldTest, MapCopy) {
+ unittest::TestMap message, message2;
+
+ MapTestUtil::SetMapFields(&message);
+
+ ReflectionOps::Copy(message, &message2);
+
+ MapTestUtil::ExpectMapFieldsSet(message2);
+
+ // Copying from self should be a no-op.
+ ReflectionOps::Copy(message2, &message2);
+ MapTestUtil::ExpectMapFieldsSet(message2);
+}
+
+TEST(ReflectionOpsForMapFieldTest, MergeMap) {
+ // Note: Copy is implemented in terms of Merge() so technically the Copy
+ // test already tested most of this.
+
+ unittest::TestMap message, message2;
+
+ MapTestUtil::SetMapFields(&message);
+
+ ReflectionOps::Merge(message2, &message);
+
+ MapTestUtil::ExpectMapFieldsSet(message);
+}
+
+TEST(ReflectionOpsForMapFieldTest, ClearMap) {
+ unittest::TestMap message;
+
+ MapTestUtil::SetMapFields(&message);
+
+ ReflectionOps::Clear(&message);
+
+ MapTestUtil::ExpectClear(message);
+}
+
+TEST(ReflectionOpsForMapFieldTest, MapDiscardUnknownFields) {
+ unittest::TestMap message;
+ MapTestUtil::SetMapFields(&message);
+
+ // Set some unknown fields in message.
+ message.GetReflection()->MutableUnknownFields(&message)->
+ AddVarint(123456, 654321);
+
+ // Discard them.
+ ReflectionOps::DiscardUnknownFields(&message);
+ MapTestUtil::ExpectMapFieldsSet(message);
+
+ EXPECT_EQ(0, message.GetReflection()->
+ GetUnknownFields(message).field_count());
+}
+
+// Wire Format Test =================================================
+
+TEST(WireFormatForMapFieldTest, ParseMap) {
+ unittest::TestMap source, dest;
+ string data;
+
+ // Serialize using the generated code.
+ MapTestUtil::SetMapFields(&source);
+ source.SerializeToString(&data);
+
+ // Parse using WireFormat.
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ MapTestUtil::ExpectMapFieldsSet(dest);
+}
+
+TEST(WireFormatForMapFieldTest, MapByteSize) {
+ unittest::TestMap message;
+ MapTestUtil::SetMapFields(&message);
+
+ EXPECT_EQ(message.ByteSize(), WireFormat::ByteSize(message));
+ message.Clear();
+ EXPECT_EQ(0, message.ByteSize());
+ EXPECT_EQ(0, WireFormat::ByteSize(message));
+}
+
+TEST(WireFormatForMapFieldTest, SerializeMap) {
+ unittest::TestMap message;
+ string generated_data;
+ string dynamic_data;
+
+ MapTestUtil::SetMapFields(&message);
+
+ // Serialize using the generated code.
+ {
+ message.ByteSize();
+ io::StringOutputStream raw_output(&generated_data);
+ io::CodedOutputStream output(&raw_output);
+ message.SerializeWithCachedSizes(&output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Serialize using WireFormat.
+ {
+ io::StringOutputStream raw_output(&dynamic_data);
+ io::CodedOutputStream output(&raw_output);
+ int size = WireFormat::ByteSize(message);
+ WireFormat::SerializeWithCachedSizes(message, size, &output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Should be the same.
+ // Don't use EXPECT_EQ here because we're comparing raw binary data and
+ // we really don't want it dumped to stdout on failure.
+ EXPECT_TRUE(dynamic_data == generated_data);
+}
+
+TEST(WireFormatForMapFieldTest, MapParseHelpers) {
+ string data;
+
+ {
+ // Set up.
+ protobuf_unittest::TestMap message;
+ MapTestUtil::SetMapFields(&message);
+ message.SerializeToString(&data);
+ }
+
+ {
+ // Test ParseFromString.
+ protobuf_unittest::TestMap message;
+ EXPECT_TRUE(message.ParseFromString(data));
+ MapTestUtil::ExpectMapFieldsSet(message);
+ }
+
+ {
+ // Test ParseFromIstream.
+ protobuf_unittest::TestMap message;
+ stringstream stream(data);
+ EXPECT_TRUE(message.ParseFromIstream(&stream));
+ EXPECT_TRUE(stream.eof());
+ MapTestUtil::ExpectMapFieldsSet(message);
+ }
+
+ {
+ // Test ParseFromBoundedZeroCopyStream.
+ string data_with_junk(data);
+ data_with_junk.append("some junk on the end");
+ io::ArrayInputStream stream(data_with_junk.data(), data_with_junk.size());
+ protobuf_unittest::TestMap message;
+ EXPECT_TRUE(message.ParseFromBoundedZeroCopyStream(&stream, data.size()));
+ MapTestUtil::ExpectMapFieldsSet(message);
+ }
+
+ {
+ // Test that ParseFromBoundedZeroCopyStream fails (but doesn't crash) if
+ // EOF is reached before the expected number of bytes.
+ io::ArrayInputStream stream(data.data(), data.size());
+ protobuf_unittest::TestAllTypes message;
+ EXPECT_FALSE(
+ message.ParseFromBoundedZeroCopyStream(&stream, data.size() + 1));
+ }
+}
+
+// Deterministic Serialization Test ==========================================
+
+template <typename T>
+static string DeterministicSerialization(const T& t) {
+ const int size = t.ByteSize();
+ string result(size, '\0');
+ io::ArrayOutputStream array_stream(string_as_array(&result), size);
+ io::CodedOutputStream output_stream(&array_stream);
+ output_stream.SetSerializationDeterministic(true);
+ t.SerializeWithCachedSizes(&output_stream);
+ EXPECT_FALSE(output_stream.HadError());
+ EXPECT_EQ(size, output_stream.ByteCount());
+ return result;
+}
+
+// Helper to test the serialization of the first arg against a golden file.
+static void TestDeterministicSerialization(const protobuf_unittest::TestMaps& t,
+ const string& filename) {
+ string expected;
+ GOOGLE_CHECK_OK(File::GetContents(
+ TestSourceDir() + "/google/protobuf/testdata/" + filename,
+ &expected, true));
+ const string actual = DeterministicSerialization(t);
+ EXPECT_EQ(expected, actual);
+ protobuf_unittest::TestMaps u;
+ EXPECT_TRUE(u.ParseFromString(actual));
+ EXPECT_TRUE(google::protobuf::util::MessageDifferencer::Equals(u, t));
+}
+
+// Helper for MapSerializationTest. Return a 7-bit ASCII string.
+static string ConstructKey(uint64 n) {
+ string s(n % static_cast<uint64>(9), '\0');
+ if (s.empty()) {
+ return StrCat(n);
+ } else {
+ while (n != 0) {
+ s[n % s.size()] = (n >> 10) & 0x7f;
+ n /= 888;
+ }
+ return s;
+ }
+}
+
+TEST(MapSerializationTest, Deterministic) {
+ const int kIters = 25;
+ protobuf_unittest::TestMaps t;
+ protobuf_unittest::TestIntIntMap inner;
+ (*inner.mutable_m())[0] = (*inner.mutable_m())[10] =
+ (*inner.mutable_m())[-200] = 0;
+ uint64 frog = 9;
+ const uint64 multiplier = 0xa29cd16f;
+ for (int i = 0; i < kIters; i++) {
+ const int32 i32 = static_cast<int32>(frog & 0xffffffff);
+ const uint32 u32 = static_cast<uint32>(i32) * 91919;
+ const int64 i64 = static_cast<int64>(frog);
+ const uint64 u64 = frog * static_cast<uint64>(187321);
+ const bool b = i32 > 0;
+ const string s = ConstructKey(frog);
+ (*inner.mutable_m())[i] = i32;
+ (*t.mutable_m_int32())[i32] = (*t.mutable_m_sint32())[i32] =
+ (*t.mutable_m_sfixed32())[i32] = inner;
+ (*t.mutable_m_uint32())[u32] = (*t.mutable_m_fixed32())[u32] = inner;
+ (*t.mutable_m_int64())[i64] = (*t.mutable_m_sint64())[i64] =
+ (*t.mutable_m_sfixed64())[i64] = inner;
+ (*t.mutable_m_uint64())[u64] = (*t.mutable_m_fixed64())[u64] = inner;
+ (*t.mutable_m_bool())[b] = inner;
+ (*t.mutable_m_string())[s] = inner;
+ (*t.mutable_m_string())[s + string(1 << (u32 % static_cast<uint32>(9)),
+ b)] = inner;
+ inner.mutable_m()->erase(i);
+ frog = frog * multiplier + i;
+ frog ^= (frog >> 41);
+ }
+ TestDeterministicSerialization(t, "golden_message_maps");
+}
+
+// Text Format Test =================================================
+
+TEST(TextFormatMapTest, SerializeAndParse) {
+ unittest::TestMap source;
+ unittest::TestMap dest;
+ MapTestUtil::SetMapFields(&source);
+ string output;
+
+ // Test compact ASCII
+ TextFormat::Printer printer;
+ printer.PrintToString(source, &output);
+ TextFormat::Parser parser;
+ EXPECT_TRUE(parser.ParseFromString(output, &dest));
+ MapTestUtil::ExpectMapFieldsSet(dest);
+}
+
+TEST(TextFormatMapTest, Sorted) {
+ unittest::TestMap message;
+ MapReflectionTester tester(message.GetDescriptor());
+ tester.SetMapFieldsViaReflection(&message);
+
+ string expected_text;
+ GOOGLE_CHECK_OK(File::GetContents(
+ TestSourceDir() +
+ "/google/protobuf/"
+ "testdata/map_test_data.txt",
+ &expected_text, true));
+
+ EXPECT_EQ(message.DebugString(), expected_text);
+
+ // Test again on the reverse order.
+ unittest::TestMap message2;
+ tester.SetMapFieldsViaReflection(&message2);
+ tester.SwapMapsViaReflection(&message2);
+ EXPECT_EQ(message2.DebugString(), expected_text);
+}
+
+
+// arena support =================================================
+TEST(ArenaTest, ParsingAndSerializingNoHeapAllocation) {
+ // Allocate a large initial block to avoid mallocs during hooked test.
+ std::vector<char> arena_block(128 * 1024);
+ ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena(options);
+ string data;
+ data.reserve(128 * 1024);
+
+ {
+ // TODO(teboring): Enable no heap check when ArenaStringPtr is used in map.
+ // NoHeapChecker no_heap;
+
+ unittest::TestArenaMap* from =
+ Arena::CreateMessage<unittest::TestArenaMap>(&arena);
+ MapTestUtil::SetArenaMapFields(from);
+ from->SerializeToString(&data);
+
+ unittest::TestArenaMap* to =
+ Arena::CreateMessage<unittest::TestArenaMap>(&arena);
+ to->ParseFromString(data);
+ MapTestUtil::ExpectArenaMapFieldsSet(*to);
+ }
+}
+
+// Use text format parsing and serializing to test reflection api.
+TEST(ArenaTest, RelfectionInTextFormat) {
+ Arena arena;
+ string data;
+
+ TextFormat::Printer printer;
+ TextFormat::Parser parser;
+
+ unittest::TestArenaMap* from =
+ Arena::CreateMessage<unittest::TestArenaMap>(&arena);
+ unittest::TestArenaMap* to =
+ Arena::CreateMessage<unittest::TestArenaMap>(&arena);
+
+ MapTestUtil::SetArenaMapFields(from);
+ printer.PrintToString(*from, &data);
+
+ EXPECT_TRUE(parser.ParseFromString(data, to));
+ MapTestUtil::ExpectArenaMapFieldsSet(*to);
+}
+
+// Make sure the memory allocated for string in map is deallocated.
+TEST(ArenaTest, StringMapNoLeak) {
+ Arena arena;
+ unittest::TestArenaMap* message =
+ Arena::CreateMessage<unittest::TestArenaMap>(&arena);
+ string data;
+ // String with length less than 16 will not be allocated from heap.
+ int original_capacity = data.capacity();
+ while (data.capacity() <= original_capacity) {
+ data.append("a");
+ }
+ (*message->mutable_map_string_string())[data] = data;
+ // We rely on heap checkers to detect memory leak for us.
+ ASSERT_FALSE(message == NULL);
+}
+
+TEST(ArenaTest, IsInitialized) {
+ // Allocate a large initial polluted block.
+ std::vector<char> arena_block(128 * 1024);
+ std::fill(arena_block.begin(), arena_block.end(), '\xff');
+
+ ArenaOptions options;
+ options.initial_block = &arena_block[0];
+ options.initial_block_size = arena_block.size();
+ Arena arena(options);
+
+ unittest::TestArenaMap* message =
+ Arena::CreateMessage<unittest::TestArenaMap>(&arena);
+ EXPECT_EQ(0, (*message->mutable_map_int32_int32())[0]);
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.cc
new file mode 100644
index 0000000000..ae094647bb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.cc
@@ -0,0 +1,1801 @@
+// 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.
+
+#include <google/protobuf/map_test_util.h>
+#include <google/protobuf/map_test_util_impl.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+
+namespace google {
+namespace protobuf {
+
+void MapTestUtil::SetMapFields(unittest::TestMap* message) {
+ MapTestUtilImpl::SetMapFields<unittest::MapEnum, unittest::MAP_ENUM_BAR,
+ unittest::MAP_ENUM_BAZ>(message);
+}
+
+void MapTestUtil::SetArenaMapFields(unittest::TestArenaMap* message) {
+ MapTestUtilImpl::SetArenaMapFields<unittest::MapEnum, unittest::MAP_ENUM_BAR,
+ unittest::MAP_ENUM_BAZ>(message);
+}
+
+void MapTestUtil::SetMapFieldsInitialized(unittest::TestMap* message) {
+ MapTestUtilImpl::SetMapFieldsInitialized(message);
+}
+
+void MapTestUtil::ModifyMapFields(unittest::TestMap* message) {
+ MapTestUtilImpl::ModifyMapFields<unittest::MapEnum, unittest::MAP_ENUM_FOO>(
+ message);
+}
+
+void MapTestUtil::ExpectClear(const unittest::TestMap& message) {
+ MapTestUtilImpl::ExpectClear(message);
+}
+
+void MapTestUtil::ExpectMapFieldsSet(const unittest::TestMap& message) {
+ MapTestUtilImpl::ExpectMapFieldsSet<unittest::MapEnum, unittest::MAP_ENUM_BAR,
+ unittest::MAP_ENUM_BAZ>(message);
+}
+
+void MapTestUtil::ExpectArenaMapFieldsSet(
+ const unittest::TestArenaMap& message) {
+ MapTestUtilImpl::ExpectArenaMapFieldsSet<
+ unittest::MapEnum, unittest::MAP_ENUM_BAR, unittest::MAP_ENUM_BAZ>(
+ message);
+}
+
+void MapTestUtil::ExpectMapFieldsSetInitialized(
+ const unittest::TestMap& message) {
+ MapTestUtilImpl::ExpectMapFieldsSetInitialized<unittest::MapEnum,
+ unittest::MAP_ENUM_FOO>(
+ message);
+}
+
+void MapTestUtil::ExpectMapFieldsModified(
+ const unittest::TestMap& message) {
+ MapTestUtilImpl::ExpectMapFieldsModified<
+ unittest::MapEnum, unittest::MAP_ENUM_BAR, unittest::MAP_ENUM_FOO>(
+ message);
+}
+
+void MapTestUtil::ExpectMapsSize(
+ const unittest::TestMap& message, int size) {
+ const Descriptor* descriptor = message.GetDescriptor();
+
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_int32_int32")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_int64_int64")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_uint32_uint32")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_uint64_uint64")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_sint32_sint32")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_sint64_sint64")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_fixed32_fixed32")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_fixed64_fixed64")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_sfixed32_sfixed32")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_sfixed64_sfixed64")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_int32_float")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_int32_double")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_bool_bool")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_string_string")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_int32_bytes")));
+ EXPECT_EQ(size, message.GetReflection()->FieldSize(
+ message, descriptor->FindFieldByName("map_int32_foreign_message")));
+}
+
+std::vector<const Message*> MapTestUtil::GetMapEntries(
+ const unittest::TestMap& message, int index) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ std::vector<const Message*> result;
+
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_int32_int32"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_int64_int64"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_uint32_uint32"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_uint64_uint64"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_sint32_sint32"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_sint64_sint64"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_fixed32_fixed32"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_fixed64_fixed64"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_sfixed32_sfixed32"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_sfixed64_sfixed64"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_int32_float"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_int32_double"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_bool_bool"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_string_string"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_int32_bytes"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_int32_enum"), index));
+ result.push_back(&message.GetReflection()->GetRepeatedMessage(
+ message, descriptor->FindFieldByName("map_int32_foreign_message"), index));
+
+ return result;
+}
+
+std::vector<const Message*> MapTestUtil::GetMapEntriesFromRelease(
+ unittest::TestMap* message) {
+ const Descriptor* descriptor = message->GetDescriptor();
+ std::vector<const Message*> result;
+
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_int32_int32")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_int64_int64")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_uint32_uint32")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_uint64_uint64")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_sint32_sint32")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_sint64_sint64")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_fixed32_fixed32")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_fixed64_fixed64")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_sfixed32_sfixed32")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_sfixed64_sfixed64")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_int32_float")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_int32_double")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_bool_bool")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_string_string")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_int32_bytes")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_int32_enum")));
+ result.push_back(message->GetReflection()->ReleaseLast(
+ message, descriptor->FindFieldByName("map_int32_foreign_message")));
+
+ return result;
+}
+
+MapReflectionTester::MapReflectionTester(
+ const Descriptor* base_descriptor)
+ : base_descriptor_(base_descriptor) {
+ const DescriptorPool* pool = base_descriptor->file()->pool();
+
+ map_enum_foo_ = pool->FindEnumValueByName("protobuf_unittest.MAP_ENUM_FOO");
+ map_enum_bar_ = pool->FindEnumValueByName("protobuf_unittest.MAP_ENUM_BAR");
+ map_enum_baz_ = pool->FindEnumValueByName("protobuf_unittest.MAP_ENUM_BAZ");
+
+ foreign_c_ = pool->FindFieldByName(
+ "protobuf_unittest.ForeignMessage.c");
+ map_int32_int32_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32Int32Entry.key");
+ map_int32_int32_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32Int32Entry.value");
+ map_int64_int64_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt64Int64Entry.key");
+ map_int64_int64_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt64Int64Entry.value");
+ map_uint32_uint32_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapUint32Uint32Entry.key");
+ map_uint32_uint32_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapUint32Uint32Entry.value");
+ map_uint64_uint64_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapUint64Uint64Entry.key");
+ map_uint64_uint64_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapUint64Uint64Entry.value");
+ map_sint32_sint32_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSint32Sint32Entry.key");
+ map_sint32_sint32_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSint32Sint32Entry.value");
+ map_sint64_sint64_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSint64Sint64Entry.key");
+ map_sint64_sint64_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSint64Sint64Entry.value");
+ map_fixed32_fixed32_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapFixed32Fixed32Entry.key");
+ map_fixed32_fixed32_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapFixed32Fixed32Entry.value");
+ map_fixed64_fixed64_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapFixed64Fixed64Entry.key");
+ map_fixed64_fixed64_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapFixed64Fixed64Entry.value");
+ map_sfixed32_sfixed32_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSfixed32Sfixed32Entry.key");
+ map_sfixed32_sfixed32_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSfixed32Sfixed32Entry.value");
+ map_sfixed64_sfixed64_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSfixed64Sfixed64Entry.key");
+ map_sfixed64_sfixed64_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapSfixed64Sfixed64Entry.value");
+ map_int32_float_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32FloatEntry.key");
+ map_int32_float_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32FloatEntry.value");
+ map_int32_double_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32DoubleEntry.key");
+ map_int32_double_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32DoubleEntry.value");
+ map_bool_bool_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapBoolBoolEntry.key");
+ map_bool_bool_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapBoolBoolEntry.value");
+ map_string_string_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapStringStringEntry.key");
+ map_string_string_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapStringStringEntry.value");
+ map_int32_bytes_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32BytesEntry.key");
+ map_int32_bytes_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32BytesEntry.value");
+ map_int32_enum_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32EnumEntry.key");
+ map_int32_enum_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32EnumEntry.value");
+ map_int32_foreign_message_key_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32ForeignMessageEntry.key");
+ map_int32_foreign_message_val_ = pool->FindFieldByName(
+ "protobuf_unittest.TestMap.MapInt32ForeignMessageEntry.value");
+
+ EXPECT_FALSE(map_enum_foo_ == NULL);
+ EXPECT_FALSE(map_enum_bar_ == NULL);
+ EXPECT_FALSE(map_enum_baz_ == NULL);
+ EXPECT_FALSE(map_int32_int32_key_ == NULL);
+ EXPECT_FALSE(map_int32_int32_val_ == NULL);
+ EXPECT_FALSE(map_int64_int64_key_ == NULL);
+ EXPECT_FALSE(map_int64_int64_val_ == NULL);
+ EXPECT_FALSE(map_uint32_uint32_key_ == NULL);
+ EXPECT_FALSE(map_uint32_uint32_val_ == NULL);
+ EXPECT_FALSE(map_uint64_uint64_key_ == NULL);
+ EXPECT_FALSE(map_uint64_uint64_val_ == NULL);
+ EXPECT_FALSE(map_sint32_sint32_key_ == NULL);
+ EXPECT_FALSE(map_sint32_sint32_val_ == NULL);
+ EXPECT_FALSE(map_sint64_sint64_key_ == NULL);
+ EXPECT_FALSE(map_sint64_sint64_val_ == NULL);
+ EXPECT_FALSE(map_fixed32_fixed32_key_ == NULL);
+ EXPECT_FALSE(map_fixed32_fixed32_val_ == NULL);
+ EXPECT_FALSE(map_fixed64_fixed64_key_ == NULL);
+ EXPECT_FALSE(map_fixed64_fixed64_val_ == NULL);
+ EXPECT_FALSE(map_sfixed32_sfixed32_key_ == NULL);
+ EXPECT_FALSE(map_sfixed32_sfixed32_val_ == NULL);
+ EXPECT_FALSE(map_sfixed64_sfixed64_key_ == NULL);
+ EXPECT_FALSE(map_sfixed64_sfixed64_val_ == NULL);
+ EXPECT_FALSE(map_int32_float_key_ == NULL);
+ EXPECT_FALSE(map_int32_float_val_ == NULL);
+ EXPECT_FALSE(map_int32_double_key_ == NULL);
+ EXPECT_FALSE(map_int32_double_val_ == NULL);
+ EXPECT_FALSE(map_bool_bool_key_ == NULL);
+ EXPECT_FALSE(map_bool_bool_val_ == NULL);
+ EXPECT_FALSE(map_string_string_key_ == NULL);
+ EXPECT_FALSE(map_string_string_val_ == NULL);
+ EXPECT_FALSE(map_int32_bytes_key_ == NULL);
+ EXPECT_FALSE(map_int32_bytes_val_ == NULL);
+ EXPECT_FALSE(map_int32_enum_key_ == NULL);
+ EXPECT_FALSE(map_int32_enum_val_ == NULL);
+ EXPECT_FALSE(map_int32_foreign_message_key_ == NULL);
+ EXPECT_FALSE(map_int32_foreign_message_val_ == NULL);
+}
+
+// Shorthand to get a FieldDescriptor for a field of unittest::TestMap.
+const FieldDescriptor* MapReflectionTester::F(const string& name) {
+ const FieldDescriptor* result = NULL;
+ result = base_descriptor_->FindFieldByName(name);
+ GOOGLE_CHECK(result != NULL);
+ return result;
+}
+
+void MapReflectionTester::SetMapFieldsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ Message* sub_message = NULL;
+ Message* sub_foreign_message = NULL;
+
+ // Add first element.
+ sub_message = reflection->AddMessage(message, F("map_int32_int32"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_int32_key_, 0);
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_int32_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_int64_int64"));
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_int64_int64_key_, 0);
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_int64_int64_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_uint32_uint32"));
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_uint32_uint32_key_, 0);
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_uint32_uint32_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_uint64_uint64"));
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_uint64_uint64_key_, 0);
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_uint64_uint64_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_sint32_sint32"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sint32_sint32_key_, 0);
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sint32_sint32_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_sint64_sint64"));
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sint64_sint64_key_, 0);
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sint64_sint64_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_fixed32_fixed32"));
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_fixed32_fixed32_key_, 0);
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_fixed32_fixed32_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_fixed64_fixed64"));
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_fixed64_fixed64_key_, 0);
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_fixed64_fixed64_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_sfixed32_sfixed32"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sfixed32_sfixed32_key_, 0);
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sfixed32_sfixed32_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_sfixed64_sfixed64"));
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sfixed64_sfixed64_key_, 0);
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sfixed64_sfixed64_val_, 0);
+
+ sub_message = reflection->AddMessage(message, F("map_int32_float"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_float_key_, 0);
+ sub_message->GetReflection()
+ ->SetFloat(sub_message, map_int32_float_val_, 0.0);
+
+ sub_message = reflection->AddMessage(message, F("map_int32_double"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_double_key_, 0);
+ sub_message->GetReflection()
+ ->SetDouble(sub_message, map_int32_double_val_, 0.0);
+
+ sub_message = reflection->AddMessage(message, F("map_bool_bool"));
+ sub_message->GetReflection()
+ ->SetBool(sub_message, map_bool_bool_key_, false);
+ sub_message->GetReflection()
+ ->SetBool(sub_message, map_bool_bool_val_, false);
+
+ sub_message = reflection->AddMessage(message, F("map_string_string"));
+ sub_message->GetReflection()
+ ->SetString(sub_message, map_string_string_key_, "0");
+ sub_message->GetReflection()
+ ->SetString(sub_message, map_string_string_val_, "0");
+
+ sub_message = reflection->AddMessage(message, F("map_int32_bytes"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_bytes_key_, 0);
+ sub_message->GetReflection()
+ ->SetString(sub_message, map_int32_bytes_val_, "0");
+
+ sub_message = reflection->AddMessage(message, F("map_int32_enum"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_enum_key_, 0);
+ sub_message->GetReflection()
+ ->SetEnum(sub_message, map_int32_enum_val_, map_enum_bar_);
+
+ sub_message = reflection
+ ->AddMessage(message, F("map_int32_foreign_message"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_foreign_message_key_, 0);
+ sub_foreign_message = sub_message->GetReflection()->
+ MutableMessage(sub_message, map_int32_foreign_message_val_, NULL);
+ sub_foreign_message->GetReflection()->
+ SetInt32(sub_foreign_message, foreign_c_, 0);
+
+ // Add second element
+ sub_message = reflection->AddMessage(message, F("map_int32_int32"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_int32_key_, 1);
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_int32_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_int64_int64"));
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_int64_int64_key_, 1);
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_int64_int64_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_uint32_uint32"));
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_uint32_uint32_key_, 1);
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_uint32_uint32_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_uint64_uint64"));
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_uint64_uint64_key_, 1);
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_uint64_uint64_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_sint32_sint32"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sint32_sint32_key_, 1);
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sint32_sint32_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_sint64_sint64"));
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sint64_sint64_key_, 1);
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sint64_sint64_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_fixed32_fixed32"));
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_fixed32_fixed32_key_, 1);
+ sub_message->GetReflection()
+ ->SetUInt32(sub_message, map_fixed32_fixed32_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_fixed64_fixed64"));
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_fixed64_fixed64_key_, 1);
+ sub_message->GetReflection()
+ ->SetUInt64(sub_message, map_fixed64_fixed64_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_sfixed32_sfixed32"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sfixed32_sfixed32_key_, 1);
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_sfixed32_sfixed32_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_sfixed64_sfixed64"));
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sfixed64_sfixed64_key_, 1);
+ sub_message->GetReflection()
+ ->SetInt64(sub_message, map_sfixed64_sfixed64_val_, 1);
+
+ sub_message = reflection->AddMessage(message, F("map_int32_float"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_float_key_, 1);
+ sub_message->GetReflection()
+ ->SetFloat(sub_message, map_int32_float_val_, 1.0);
+
+ sub_message = reflection->AddMessage(message, F("map_int32_double"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_double_key_, 1);
+ sub_message->GetReflection()
+ ->SetDouble(sub_message, map_int32_double_val_, 1.0);
+
+ sub_message = reflection->AddMessage(message, F("map_bool_bool"));
+ sub_message->GetReflection()
+ ->SetBool(sub_message, map_bool_bool_key_, true);
+ sub_message->GetReflection()
+ ->SetBool(sub_message, map_bool_bool_val_, true);
+
+ sub_message = reflection->AddMessage(message, F("map_string_string"));
+ sub_message->GetReflection()
+ ->SetString(sub_message, map_string_string_key_, "1");
+ sub_message->GetReflection()
+ ->SetString(sub_message, map_string_string_val_, "1");
+
+ sub_message = reflection->AddMessage(message, F("map_int32_bytes"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_bytes_key_, 1);
+ sub_message->GetReflection()
+ ->SetString(sub_message, map_int32_bytes_val_, "1");
+
+ sub_message = reflection->AddMessage(message, F("map_int32_enum"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_enum_key_, 1);
+ sub_message->GetReflection()
+ ->SetEnum(sub_message, map_int32_enum_val_, map_enum_baz_);
+
+ sub_message = reflection
+ ->AddMessage(message, F("map_int32_foreign_message"));
+ sub_message->GetReflection()
+ ->SetInt32(sub_message, map_int32_foreign_message_key_, 1);
+ sub_foreign_message = sub_message->GetReflection()->
+ MutableMessage(sub_message, map_int32_foreign_message_val_, NULL);
+ sub_foreign_message->GetReflection()->
+ SetInt32(sub_foreign_message, foreign_c_, 1);
+}
+
+void MapReflectionTester::SetMapFieldsViaMapReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ Message* sub_foreign_message = NULL;
+ MapValueRef map_val;
+
+ // Add first element.
+ MapKey map_key;
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_int32"), map_key, &map_val));
+ map_val.SetInt32Value(0);
+
+ map_key.SetInt64Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int64_int64"), map_key, &map_val));
+ map_val.SetInt64Value(0);
+
+ map_key.SetUInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_uint32_uint32"), map_key, &map_val));
+ map_val.SetUInt32Value(0);
+
+ map_key.SetUInt64Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_uint64_uint64"), map_key, &map_val));
+ map_val.SetUInt64Value(0);
+
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_sint32_sint32"), map_key, &map_val));
+ map_val.SetInt32Value(0);
+
+ map_key.SetInt64Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_sint64_sint64"), map_key, &map_val));
+ map_val.SetInt64Value(0);
+
+ map_key.SetUInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_fixed32_fixed32"), map_key, &map_val));
+ map_val.SetUInt32Value(0);
+
+ map_key.SetUInt64Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_fixed64_fixed64"), map_key, &map_val));
+ map_val.SetUInt64Value(0);
+
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_sfixed32_sfixed32"), map_key, &map_val));
+ map_val.SetInt32Value(0);
+
+ map_key.SetInt64Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_sfixed64_sfixed64"), map_key, &map_val));
+ map_val.SetInt64Value(0);
+
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_float"), map_key, &map_val));
+ map_val.SetFloatValue(0.0);
+
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_double"), map_key, &map_val));
+ map_val.SetDoubleValue(0.0);
+
+ map_key.SetBoolValue(false);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_bool_bool"), map_key, &map_val));
+ map_val.SetBoolValue(false);
+
+ map_key.SetStringValue("0");
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_string_string"), map_key, &map_val));
+ map_val.SetStringValue("0");
+
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_bytes"), map_key, &map_val));
+ map_val.SetStringValue("0");
+
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_enum"), map_key, &map_val));
+ map_val.SetEnumValue(map_enum_bar_->number());
+
+ map_key.SetInt32Value(0);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_foreign_message"), map_key, &map_val));
+ sub_foreign_message = map_val.MutableMessageValue();
+ sub_foreign_message->GetReflection()->SetInt32(
+ sub_foreign_message, foreign_c_, 0);
+
+ // Add second element
+ map_key.SetInt32Value(1);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_int32"), map_key, &map_val));
+ map_val.SetInt32Value(1);
+ EXPECT_FALSE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_int32"), map_key, &map_val));
+
+ map_key.SetInt64Value(1);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int64_int64"), map_key, &map_val));
+ map_val.SetInt64Value(1);
+ EXPECT_FALSE(reflection->InsertOrLookupMapValue(
+ message, F("map_int64_int64"), map_key, &map_val));
+
+ map_key.SetUInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_uint32_uint32"), map_key, &map_val);
+ map_val.SetUInt32Value(1);
+
+ map_key.SetUInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_uint64_uint64"), map_key, &map_val);
+ map_val.SetUInt64Value(1);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sint32_sint32"), map_key, &map_val);
+ map_val.SetInt32Value(1);
+
+ map_key.SetInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sint64_sint64"), map_key, &map_val);
+ map_val.SetInt64Value(1);
+
+ map_key.SetUInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_fixed32_fixed32"), map_key, &map_val);
+ map_val.SetUInt32Value(1);
+
+ map_key.SetUInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_fixed64_fixed64"), map_key, &map_val);
+ map_val.SetUInt64Value(1);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sfixed32_sfixed32"), map_key, &map_val);
+ map_val.SetInt32Value(1);
+
+ map_key.SetInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sfixed64_sfixed64"), map_key, &map_val);
+ map_val.SetInt64Value(1);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_float"), map_key, &map_val);
+ map_val.SetFloatValue(1.0);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_double"), map_key, &map_val);
+ map_val.SetDoubleValue(1.0);
+
+ map_key.SetBoolValue(true);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_bool_bool"), map_key, &map_val);
+ map_val.SetBoolValue(true);
+
+ map_key.SetStringValue("1");
+ reflection->InsertOrLookupMapValue(
+ message, F("map_string_string"), map_key, &map_val);
+ map_val.SetStringValue("1");
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_bytes"), map_key, &map_val);
+ map_val.SetStringValue("1");
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_enum"), map_key, &map_val);
+ map_val.SetEnumValue(map_enum_baz_->number());
+
+ map_key.SetInt32Value(1);
+ EXPECT_TRUE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_foreign_message"), map_key, &map_val));
+ sub_foreign_message = map_val.MutableMessageValue();
+ sub_foreign_message->GetReflection()->SetInt32(
+ sub_foreign_message, foreign_c_, 1);
+}
+
+void MapReflectionTester::ClearMapFieldsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ reflection->ClearField(message, F("map_int32_int32"));
+ reflection->ClearField(message, F("map_int64_int64"));
+ reflection->ClearField(message, F("map_uint32_uint32"));
+ reflection->ClearField(message, F("map_uint64_uint64"));
+ reflection->ClearField(message, F("map_sint32_sint32"));
+ reflection->ClearField(message, F("map_sint64_sint64"));
+ reflection->ClearField(message, F("map_fixed32_fixed32"));
+ reflection->ClearField(message, F("map_fixed64_fixed64"));
+ reflection->ClearField(message, F("map_sfixed32_sfixed32"));
+ reflection->ClearField(message, F("map_sfixed64_sfixed64"));
+ reflection->ClearField(message, F("map_int32_float"));
+ reflection->ClearField(message, F("map_int32_double"));
+ reflection->ClearField(message, F("map_bool_bool"));
+ reflection->ClearField(message, F("map_string_string"));
+ reflection->ClearField(message, F("map_int32_bytes"));
+ reflection->ClearField(message, F("map_int32_enum"));
+ reflection->ClearField(message, F("map_int32_foreign_message"));
+}
+
+void MapReflectionTester::ModifyMapFieldsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ MapValueRef map_val;
+ Message* sub_foreign_message;
+
+ // Modify the second element
+ MapKey map_key;
+ map_key.SetInt32Value(1);
+ EXPECT_FALSE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_int32"), map_key, &map_val));
+ map_val.SetInt32Value(2);
+
+ map_key.SetInt64Value(1);
+ EXPECT_FALSE(reflection->InsertOrLookupMapValue(
+ message, F("map_int64_int64"), map_key, &map_val));
+ map_val.SetInt64Value(2);
+
+ map_key.SetUInt32Value(1);
+ EXPECT_FALSE(reflection->InsertOrLookupMapValue(
+ message, F("map_uint32_uint32"), map_key, &map_val));
+ map_val.SetUInt32Value(2);
+
+ map_key.SetUInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_uint64_uint64"), map_key, &map_val);
+ map_val.SetUInt64Value(2);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sint32_sint32"), map_key, &map_val);
+ map_val.SetInt32Value(2);
+
+ map_key.SetInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sint64_sint64"), map_key, &map_val);
+ map_val.SetInt64Value(2);
+
+ map_key.SetUInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_fixed32_fixed32"), map_key, &map_val);
+ map_val.SetUInt32Value(2);
+
+ map_key.SetUInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_fixed64_fixed64"), map_key, &map_val);
+ map_val.SetUInt64Value(2);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sfixed32_sfixed32"), map_key, &map_val);
+ map_val.SetInt32Value(2);
+
+ map_key.SetInt64Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_sfixed64_sfixed64"), map_key, &map_val);
+ map_val.SetInt64Value(2);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_float"), map_key, &map_val);
+ map_val.SetFloatValue(2.0);
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_double"), map_key, &map_val);
+ map_val.SetDoubleValue(2.0);
+
+ map_key.SetBoolValue(true);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_bool_bool"), map_key, &map_val);
+ map_val.SetBoolValue(false);
+
+ map_key.SetStringValue("1");
+ reflection->InsertOrLookupMapValue(
+ message, F("map_string_string"), map_key, &map_val);
+ map_val.SetStringValue("2");
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_bytes"), map_key, &map_val);
+ map_val.SetStringValue("2");
+
+ map_key.SetInt32Value(1);
+ reflection->InsertOrLookupMapValue(
+ message, F("map_int32_enum"), map_key, &map_val);
+ map_val.SetEnumValue(map_enum_foo_->number());
+
+ map_key.SetInt32Value(1);
+ EXPECT_FALSE(reflection->InsertOrLookupMapValue(
+ message, F("map_int32_foreign_message"), map_key, &map_val));
+ sub_foreign_message = map_val.MutableMessageValue();
+ sub_foreign_message->GetReflection()->SetInt32(
+ sub_foreign_message, foreign_c_, 2);
+}
+
+void MapReflectionTester::RemoveLastMapsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ vector<const FieldDescriptor*> output;
+ reflection->ListFields(*message, &output);
+ for (int i = 0; i < output.size(); ++i) {
+ const FieldDescriptor* field = output[i];
+ if (!field->is_repeated()) continue;
+ reflection->RemoveLast(message, field);
+ }
+}
+
+void MapReflectionTester::ReleaseLastMapsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ vector<const FieldDescriptor*> output;
+ reflection->ListFields(*message, &output);
+ for (int i = 0; i < output.size(); ++i) {
+ const FieldDescriptor* field = output[i];
+ if (!field->is_repeated()) continue;
+ if (field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) continue;
+
+ Message* released = reflection->ReleaseLast(message, field);
+ ASSERT_TRUE(released != NULL) << "ReleaseLast returned NULL for: "
+ << field->name();
+ delete released;
+ }
+}
+
+void MapReflectionTester::SwapMapsViaReflection(Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ vector<const FieldDescriptor*> output;
+ reflection->ListFields(*message, &output);
+ for (int i = 0; i < output.size(); ++i) {
+ const FieldDescriptor* field = output[i];
+ if (!field->is_repeated()) continue;
+ reflection->SwapElements(message, field, 0, 1);
+ }
+}
+
+void MapReflectionTester::
+ MutableUnknownFieldsOfMapFieldsViaReflection(Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ Message* sub_message = NULL;
+
+ sub_message = reflection->AddMessage(message, F("map_int32_int32"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_int64_int64"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_uint32_uint32"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_uint64_uint64"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_sint32_sint32"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_sint64_sint64"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_fixed32_fixed32"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_fixed64_fixed64"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_sfixed32_sfixed32"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_sfixed64_sfixed64"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_int32_float"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_int32_double"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_bool_bool"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_string_string"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_int32_bytes"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_int32_enum"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+ sub_message = reflection->AddMessage(message, F("map_int32_foreign_message"));
+ EXPECT_TRUE(sub_message->GetReflection()->MutableUnknownFields(sub_message) !=
+ NULL);
+}
+
+void MapReflectionTester::ExpectMapFieldsSetViaReflection(
+ const Message& message) {
+ string scratch;
+ const Reflection* reflection = message.GetReflection();
+ const Message* sub_message;
+ MapKey map_key;
+
+ // -----------------------------------------------------------------
+
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_int32_int32")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_int64_int64")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_uint32_uint32")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_uint64_uint64")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_sint32_sint32")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_sint64_sint64")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_fixed32_fixed32")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_fixed64_fixed64")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_sfixed32_sfixed32")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_sfixed64_sfixed64")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_int32_float")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_int32_double")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_bool_bool")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_string_string")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_int32_bytes")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_int32_enum")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("map_int32_foreign_message")));
+
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ // Check with RepeatedField Reflection
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_int32_int32"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_int32_int32_key_);
+ int32 val = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_int32_int32_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_TRUE(reflection->ContainsMapKey(
+ message, F("map_int32_int32"), map_key));
+ }
+ }
+ {
+ std::map<int64, int64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ // Check with RepeatedField Reflection
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_int64_int64"), i);
+ int64 key = sub_message->GetReflection()->GetInt64(
+ *sub_message, map_int64_int64_key_);
+ int64 val = sub_message->GetReflection()->GetInt64(
+ *sub_message, map_int64_int64_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt64Value(key);
+ EXPECT_TRUE(reflection->ContainsMapKey(
+ message, F("map_int64_int64"), map_key));
+ }
+ }
+ {
+ std::map<uint32, uint32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ // Check with RepeatedField Reflection
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_uint32_uint32"), i);
+ uint32 key = sub_message->GetReflection()->GetUInt32(
+ *sub_message, map_uint32_uint32_key_);
+ uint32 val = sub_message->GetReflection()->GetUInt32(
+ *sub_message, map_uint32_uint32_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetUInt32Value(key);
+ EXPECT_TRUE(reflection->ContainsMapKey(
+ message, F("map_uint32_uint32"), map_key));
+ }
+ }
+ {
+ std::map<uint64, uint64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_uint64_uint64"), i);
+ uint64 key = sub_message->GetReflection()->GetUInt64(
+ *sub_message, map_uint64_uint64_key_);
+ uint64 val = sub_message->GetReflection()->GetUInt64(
+ *sub_message, map_uint64_uint64_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetUInt64Value(key);
+ EXPECT_TRUE(reflection->ContainsMapKey(
+ message, F("map_uint64_uint64"), map_key));
+ }
+ }
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_sint32_sint32"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_sint32_sint32_key_);
+ int32 val = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_sint32_sint32_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_sint32_sint32"), map_key));
+ }
+ }
+ {
+ std::map<int64, int64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_sint64_sint64"), i);
+ int64 key = sub_message->GetReflection()->GetInt64(
+ *sub_message, map_sint64_sint64_key_);
+ int64 val = sub_message->GetReflection()->GetInt64(
+ *sub_message, map_sint64_sint64_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt64Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_sint64_sint64"), map_key));
+ }
+ }
+ {
+ std::map<uint32, uint32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_fixed32_fixed32"), i);
+ uint32 key = sub_message->GetReflection()->GetUInt32(
+ *sub_message, map_fixed32_fixed32_key_);
+ uint32 val = sub_message->GetReflection()->GetUInt32(
+ *sub_message, map_fixed32_fixed32_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetUInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_fixed32_fixed32"), map_key));
+ }
+ }
+ {
+ std::map<uint64, uint64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_fixed64_fixed64"), i);
+ uint64 key = sub_message->GetReflection()->GetUInt64(
+ *sub_message, map_fixed64_fixed64_key_);
+ uint64 val = sub_message->GetReflection()->GetUInt64(
+ *sub_message, map_fixed64_fixed64_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetUInt64Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_fixed64_fixed64"), map_key));
+ }
+ }
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message = &reflection->GetRepeatedMessage(
+ message, F("map_sfixed32_sfixed32"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_sfixed32_sfixed32_key_);
+ int32 val = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_sfixed32_sfixed32_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_sfixed32_sfixed32"), map_key));
+ }
+ }
+ {
+ std::map<int64, int64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message = &reflection->GetRepeatedMessage(
+ message, F("map_sfixed64_sfixed64"), i);
+ int64 key = sub_message->GetReflection()->GetInt64(
+ *sub_message, map_sfixed64_sfixed64_key_);
+ int64 val = sub_message->GetReflection()->GetInt64(
+ *sub_message, map_sfixed64_sfixed64_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt64Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_sfixed64_sfixed64"), map_key));
+ }
+ }
+ {
+ std::map<int32, float> map;
+ map[0] = 0.0;
+ map[1] = 1.0;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_int32_float"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_int32_float_key_);
+ float val = sub_message->GetReflection()->GetFloat(
+ *sub_message, map_int32_float_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_int32_float"), map_key));
+ }
+ }
+ {
+ std::map<int32, double> map;
+ map[0] = 0.0;
+ map[1] = 1.0;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_int32_double"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_int32_double_key_);
+ double val = sub_message->GetReflection()->GetDouble(
+ *sub_message, map_int32_double_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_int32_double"), map_key));
+ }
+ }
+ {
+ std::map<bool, bool> map;
+ map[false] = false;
+ map[true] = true;
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_bool_bool"), i);
+ bool key = sub_message->GetReflection()->GetBool(
+ *sub_message, map_bool_bool_key_);
+ bool val = sub_message->GetReflection()->GetBool(
+ *sub_message, map_bool_bool_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetBoolValue(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_bool_bool"), map_key));
+ }
+ }
+ {
+ std::map<string, string> map;
+ map["0"] = "0";
+ map["1"] = "1";
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_string_string"), i);
+ string key = sub_message->GetReflection()->GetString(
+ *sub_message, map_string_string_key_);
+ string val = sub_message->GetReflection()->GetString(
+ *sub_message, map_string_string_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetStringValue(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_string_string"), map_key));
+ }
+ }
+ {
+ std::map<int32, string> map;
+ map[0] = "0";
+ map[1] = "1";
+ for (int i = 0; i < 2; i++) {
+ sub_message =
+ &reflection->GetRepeatedMessage(message, F("map_int32_bytes"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_int32_bytes_key_);
+ string val = sub_message->GetReflection()->GetString(
+ *sub_message, map_int32_bytes_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_int32_bytes"), map_key));
+ }
+ }
+ {
+ std::map<int32, const EnumValueDescriptor*> map;
+ map[0] = map_enum_bar_;
+ map[1] = map_enum_baz_;
+ for (int i = 0; i < 2; i++) {
+ sub_message = &reflection->GetRepeatedMessage(
+ message, F("map_int32_enum"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_int32_enum_key_);
+ const EnumValueDescriptor* val = sub_message->GetReflection()->GetEnum(
+ *sub_message, map_int32_enum_val_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_int32_enum"), map_key));
+ }
+ }
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (int i = 0; i < 2; i++) {
+ sub_message = &reflection->GetRepeatedMessage(
+ message, F("map_int32_foreign_message"), i);
+ int32 key = sub_message->GetReflection()->GetInt32(
+ *sub_message, map_int32_foreign_message_key_);
+ const Message& foreign_message = sub_message->GetReflection()->GetMessage(
+ *sub_message, map_int32_foreign_message_val_);
+ int32 val = foreign_message.GetReflection()->GetInt32(
+ foreign_message, foreign_c_);
+ EXPECT_EQ(map[key], val);
+ // Check with Map Reflection
+ map_key.SetInt32Value(key);
+ EXPECT_EQ(true, reflection->ContainsMapKey(
+ message, F("map_int32_foreign_message"), map_key));
+ }
+ }
+}
+
+void MapReflectionTester::ExpectMapFieldsSetViaReflectionIterator(
+ Message* message) {
+ string scratch;
+ string serialized;
+ const Reflection* reflection = message->GetReflection();
+
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_int32_int32")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_int64_int64")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_uint32_uint32")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_uint64_uint64")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_sint32_sint32")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_sint64_sint64")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_fixed32_fixed32")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_fixed64_fixed64")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_sfixed32_sfixed32")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_sfixed64_sfixed64")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_int32_float")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_int32_double")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_bool_bool")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_string_string")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_int32_bytes")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_int32_enum")));
+ ASSERT_EQ(2, reflection->FieldSize(*message, F("map_int32_foreign_message")));
+
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ int size = 0;
+ for (MapIterator iter = reflection->MapBegin(message, F("map_int32_int32"));
+ iter != reflection->MapEnd(message, F("map_int32_int32"));
+ ++iter, ++size) {
+ // Check const methods do not invalidate map.
+ message->DebugString();
+ message->ShortDebugString();
+ message->SerializeToString(&serialized);
+ message->SpaceUsed();
+ message->ByteSize();
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()],
+ iter.GetValueRef().GetInt32Value());
+ }
+ EXPECT_EQ(size, 2);
+ }
+ {
+ std::map<int64, int64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(message, F("map_int64_int64"));
+ iter != reflection->MapEnd(message, F("map_int64_int64")); ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt64Value()],
+ iter.GetValueRef().GetInt64Value());
+ }
+ }
+ {
+ std::map<uint32, uint32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_uint32_uint32"));
+ iter != reflection->MapEnd(message, F("map_uint32_uint32"));
+ ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetUInt32Value()],
+ iter.GetValueRef().GetUInt32Value());
+ }
+ }
+ {
+ std::map<uint64, uint64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_uint64_uint64"));
+ iter != reflection->MapEnd(message, F("map_uint64_uint64"));
+ ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetUInt64Value()],
+ iter.GetValueRef().GetUInt64Value());
+ }
+ }
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_sint32_sint32"));
+ iter != reflection->MapEnd(message, F("map_sint32_sint32"));
+ ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()],
+ iter.GetValueRef().GetInt32Value());
+ }
+ }
+ {
+ std::map<int64, int64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_sint64_sint64"));
+ iter != reflection->MapEnd(message, F("map_sint64_sint64")); ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt64Value()],
+ iter.GetValueRef().GetInt64Value());
+ }
+ }
+ {
+ std::map<uint32, uint32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_fixed32_fixed32"));
+ iter != reflection->MapEnd(message, F("map_fixed32_fixed32"));
+ ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetUInt32Value()],
+ iter.GetValueRef().GetUInt32Value());
+ }
+ }
+ {
+ std::map<uint64, uint64> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_fixed64_fixed64"));
+ iter != reflection->MapEnd(message, F("map_fixed64_fixed64"));
+ ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetUInt64Value()],
+ iter.GetValueRef().GetUInt64Value());
+ }
+ }
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_sfixed32_sfixed32"));
+ iter != reflection->MapEnd(message, F("map_sfixed32_sfixed32"));
+ ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()],
+ iter.GetValueRef().GetInt32Value());
+ }
+ }
+ {
+ std::map<int32, float> map;
+ map[0] = 0.0;
+ map[1] = 1.0;
+ for (MapIterator iter = reflection->MapBegin(message, F("map_int32_float"));
+ iter != reflection->MapEnd(message, F("map_int32_float")); ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()],
+ iter.GetValueRef().GetFloatValue());
+ }
+ }
+ {
+ std::map<int32, double> map;
+ map[0] = 0.0;
+ map[1] = 1.0;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_int32_double"));
+ iter != reflection->MapEnd(message, F("map_int32_double")); ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()],
+ iter.GetValueRef().GetDoubleValue());
+ }
+ }
+ {
+ std::map<bool, bool> map;
+ map[false] = false;
+ map[true] = true;
+ for (MapIterator iter = reflection->MapBegin(message, F("map_bool_bool"));
+ iter != reflection->MapEnd(message, F("map_bool_bool")); ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetBoolValue()],
+ iter.GetValueRef().GetBoolValue());
+ }
+ }
+ {
+ std::map<string, string> map;
+ map["0"] = "0";
+ map["1"] = "1";
+ int size = 0;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_string_string"));
+ iter != reflection->MapEnd(message, F("map_string_string"));
+ ++iter, ++size) {
+ // Check const methods do not invalidate map.
+ message->DebugString();
+ message->ShortDebugString();
+ message->SerializeToString(&serialized);
+ message->SpaceUsed();
+ message->ByteSize();
+ EXPECT_EQ(map[iter.GetKey().GetStringValue()],
+ iter.GetValueRef().GetStringValue());
+ }
+ EXPECT_EQ(size, 2);
+ }
+ {
+ std::map<int32, string> map;
+ map[0] = "0";
+ map[1] = "1";
+ for (MapIterator iter = reflection->MapBegin(message, F("map_int32_bytes"));
+ iter != reflection->MapEnd(message, F("map_int32_bytes")); ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()],
+ iter.GetValueRef().GetStringValue());
+ }
+ }
+ {
+ std::map<int32, const EnumValueDescriptor*> map;
+ map[0] = map_enum_bar_;
+ map[1] = map_enum_baz_;
+ for (MapIterator iter = reflection->MapBegin(message, F("map_int32_enum"));
+ iter != reflection->MapEnd(message, F("map_int32_enum")); ++iter) {
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()]->number(),
+ iter.GetValueRef().GetEnumValue());
+ }
+ }
+ {
+ std::map<int32, int32> map;
+ map[0] = 0;
+ map[1] = 1;
+ int size = 0;
+ for (MapIterator iter = reflection->MapBegin(
+ message, F("map_int32_foreign_message"));
+ iter != reflection->MapEnd(message, F("map_int32_foreign_message"));
+ ++iter, ++size) {
+ // Check const methods do not invalidate map.
+ message->DebugString();
+ message->ShortDebugString();
+ message->SerializeToString(&serialized);
+ message->SpaceUsed();
+ message->ByteSize();
+ const Message& sub_message = iter.GetValueRef().GetMessageValue();
+ EXPECT_EQ(map[iter.GetKey().GetInt32Value()],
+ sub_message.GetReflection()->GetInt32(sub_message, foreign_c_));
+ }
+ EXPECT_EQ(size, 2);
+ }
+}
+
+void MapReflectionTester::ExpectClearViaReflection(
+ const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+ // Map fields are empty.
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_int32_int32")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_int64_int64")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_uint32_uint32")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_uint64_uint64")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_sint32_sint32")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_sint64_sint64")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_fixed32_fixed32")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_fixed64_fixed64")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_sfixed32_sfixed32")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_sfixed64_sfixed64")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_int32_float")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_int32_double")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_bool_bool")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_string_string")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_int32_bytes")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_int32_enum")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("map_int32_foreign_message")));
+}
+
+void MapReflectionTester::ExpectClearViaReflectionIterator(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_int32_int32")) ==
+ reflection->MapEnd(message, F("map_int32_int32")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_int64_int64")) ==
+ reflection->MapEnd(message, F("map_int64_int64")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_uint32_uint32")) ==
+ reflection->MapEnd(message, F("map_uint32_uint32")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_uint64_uint64")) ==
+ reflection->MapEnd(message, F("map_uint64_uint64")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_sint32_sint32")) ==
+ reflection->MapEnd(message, F("map_sint32_sint32")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_sint64_sint64")) ==
+ reflection->MapEnd(message, F("map_sint64_sint64")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_fixed32_fixed32")) ==
+ reflection->MapEnd(message, F("map_fixed32_fixed32")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_fixed64_fixed64")) ==
+ reflection->MapEnd(message, F("map_fixed64_fixed64")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_sfixed32_sfixed32")) ==
+ reflection->MapEnd(message, F("map_sfixed32_sfixed32")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_sfixed64_sfixed64")) ==
+ reflection->MapEnd(message, F("map_sfixed64_sfixed64")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_int32_float")) ==
+ reflection->MapEnd(message, F("map_int32_float")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_int32_double")) ==
+ reflection->MapEnd(message, F("map_int32_double")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_bool_bool")) ==
+ reflection->MapEnd(message, F("map_bool_bool")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_string_string")) ==
+ reflection->MapEnd(message, F("map_string_string")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_int32_bytes")) ==
+ reflection->MapEnd(message, F("map_int32_bytes")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_int32_enum")) ==
+ reflection->MapEnd(message, F("map_int32_enum")));
+ EXPECT_TRUE(reflection->MapBegin(message, F("map_int32_foreign_message")) ==
+ reflection->MapEnd(message, F("map_int32_foreign_message")));
+}
+
+void MapReflectionTester::ExpectMapEntryClearViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ const Message* sub_message;
+
+ {
+ const FieldDescriptor* descriptor = F("map_int32_int32");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_int32_int32"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_int64_int64");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_int64_int64"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt64(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt64(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_uint32_uint32");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_uint32_uint32"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt32(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_uint64_uint64");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_uint64_uint64"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt64(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt64(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_sint32_sint32");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_sint32_sint32"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_sint64_sint64");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_sint64_sint64"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt64(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt64(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_fixed32_fixed32");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_fixed32_fixed32"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt32(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_fixed64_fixed64");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_fixed64_fixed64"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt64(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetUInt64(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_sfixed32_sfixed32");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_sfixed32_sfixed32"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_sfixed64_sfixed64");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_sfixed64_sfixed64"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt64(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt64(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_int32_float");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_int32_float"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetFloat(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_int32_double");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_int32_double"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetDouble(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_bool_bool");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_bool_bool"));
+ EXPECT_EQ(false, sub_message->GetReflection()->GetBool(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(false, sub_message->GetReflection()->GetBool(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_string_string");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_string_string"));
+ EXPECT_EQ("", sub_message->GetReflection()->GetString(*sub_message,
+ key_descriptor));
+ EXPECT_EQ("", sub_message->GetReflection()->GetString(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_int32_bytes");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_int32_bytes"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ("", sub_message->GetReflection()->GetString(*sub_message,
+ value_descriptor));
+ }
+ {
+ const FieldDescriptor* descriptor = F("map_int32_enum");
+ const FieldDescriptor* key_descriptor =
+ descriptor->message_type()->FindFieldByName("key");
+ const FieldDescriptor* value_descriptor =
+ descriptor->message_type()->FindFieldByName("value");
+ sub_message = reflection->AddMessage(message, F("map_int32_enum"));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message,
+ key_descriptor));
+ EXPECT_EQ(0, sub_message->GetReflection()
+ ->GetEnum(*sub_message, value_descriptor)
+ ->number());
+ }
+ // Map using message as value has been tested in other place. Thus, we don't
+ // test it here.
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.h
new file mode 100644
index 0000000000..deaf0f4f4b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util.h
@@ -0,0 +1,159 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_TEST_UTIL_H__
+#define GOOGLE_PROTOBUF_MAP_TEST_UTIL_H__
+
+#include <google/protobuf/map_unittest.pb.h>
+
+namespace google {
+namespace protobuf {
+
+namespace unittest = ::protobuf_unittest;
+
+class MapTestUtil {
+ public:
+ // Set every field in the TestMap message to a unique value.
+ static void SetMapFields(unittest::TestMap* message);
+
+ // Set every field in the TestArenaMap message to a unique value.
+ static void SetArenaMapFields(unittest::TestArenaMap* message);
+
+ // Set every field in the message to a default value.
+ static void SetMapFieldsInitialized(unittest::TestMap* message);
+
+ // Modify all the map fields of the message (which should already have been
+ // initialized with SetMapFields()).
+ static void ModifyMapFields(unittest::TestMap* message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFields() is called.
+ static void ExpectMapFieldsSet(const unittest::TestMap& message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFields() is called for TestArenaMap.
+ static void ExpectArenaMapFieldsSet(const unittest::TestArenaMap& message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFieldsInitialized() is called.
+ static void ExpectMapFieldsSetInitialized(
+ const unittest::TestMap& message);
+
+ // Expect that the message is modified as would be expected from
+ // ModifyMapFields().
+ static void ExpectMapFieldsModified(const unittest::TestMap& message);
+
+ // Check that all fields are empty.
+ static void ExpectClear(const unittest::TestMap& message);
+
+ // Check that all map fields have the given size.
+ static void ExpectMapsSize(const unittest::TestMap& message, int size);
+
+ // Get pointers of map entries at given index.
+ static std::vector<const Message*> GetMapEntries(
+ const unittest::TestMap& message, int index);
+
+ // Get pointers of map entries from release.
+ static std::vector<const Message*> GetMapEntriesFromRelease(
+ unittest::TestMap* message);
+};
+
+// Like above, but use the reflection interface.
+class MapReflectionTester {
+ public:
+ // base_descriptor must be a descriptor for TestMap, which is used for
+ // MapReflectionTester to fetch the FieldDescriptors needed to use the
+ // reflection interface.
+ explicit MapReflectionTester(const Descriptor* base_descriptor);
+
+ void SetMapFieldsViaReflection(Message* message);
+ void SetMapFieldsViaMapReflection(Message* message);
+ void ClearMapFieldsViaReflection(Message* message);
+ void ModifyMapFieldsViaReflection(Message* message);
+ void RemoveLastMapsViaReflection(Message* message);
+ void ReleaseLastMapsViaReflection(Message* message);
+ void SwapMapsViaReflection(Message* message);
+ void MutableUnknownFieldsOfMapFieldsViaReflection(Message* message);
+ void ExpectMapFieldsSetViaReflection(const Message& message);
+ void ExpectMapFieldsSetViaReflectionIterator(Message* message);
+ void ExpectClearViaReflection(const Message& message);
+ void ExpectClearViaReflectionIterator(Message* message);
+ void ExpectMapEntryClearViaReflection(Message* message);
+
+ private:
+ const FieldDescriptor* F(const string& name);
+
+ const Descriptor* base_descriptor_;
+
+ const EnumValueDescriptor* map_enum_bar_;
+ const EnumValueDescriptor* map_enum_baz_;
+ const EnumValueDescriptor* map_enum_foo_;
+
+ const FieldDescriptor* foreign_c_;
+ const FieldDescriptor* map_int32_int32_key_;
+ const FieldDescriptor* map_int32_int32_val_;
+ const FieldDescriptor* map_int64_int64_key_;
+ const FieldDescriptor* map_int64_int64_val_;
+ const FieldDescriptor* map_uint32_uint32_key_;
+ const FieldDescriptor* map_uint32_uint32_val_;
+ const FieldDescriptor* map_uint64_uint64_key_;
+ const FieldDescriptor* map_uint64_uint64_val_;
+ const FieldDescriptor* map_sint32_sint32_key_;
+ const FieldDescriptor* map_sint32_sint32_val_;
+ const FieldDescriptor* map_sint64_sint64_key_;
+ const FieldDescriptor* map_sint64_sint64_val_;
+ const FieldDescriptor* map_fixed32_fixed32_key_;
+ const FieldDescriptor* map_fixed32_fixed32_val_;
+ const FieldDescriptor* map_fixed64_fixed64_key_;
+ const FieldDescriptor* map_fixed64_fixed64_val_;
+ const FieldDescriptor* map_sfixed32_sfixed32_key_;
+ const FieldDescriptor* map_sfixed32_sfixed32_val_;
+ const FieldDescriptor* map_sfixed64_sfixed64_key_;
+ const FieldDescriptor* map_sfixed64_sfixed64_val_;
+ const FieldDescriptor* map_int32_float_key_;
+ const FieldDescriptor* map_int32_float_val_;
+ const FieldDescriptor* map_int32_double_key_;
+ const FieldDescriptor* map_int32_double_val_;
+ const FieldDescriptor* map_bool_bool_key_;
+ const FieldDescriptor* map_bool_bool_val_;
+ const FieldDescriptor* map_string_string_key_;
+ const FieldDescriptor* map_string_string_val_;
+ const FieldDescriptor* map_int32_bytes_key_;
+ const FieldDescriptor* map_int32_bytes_val_;
+ const FieldDescriptor* map_int32_enum_key_;
+ const FieldDescriptor* map_int32_enum_val_;
+ const FieldDescriptor* map_int32_foreign_message_key_;
+ const FieldDescriptor* map_int32_foreign_message_val_;
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_TEST_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util_impl.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util_impl.h
new file mode 100644
index 0000000000..b3ba4e0699
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_test_util_impl.h
@@ -0,0 +1,490 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MAP_TEST_UTIL_IMPL_H__
+#define GOOGLE_PROTOBUF_MAP_TEST_UTIL_IMPL_H__
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+
+
+#define EXPECT_TRUE GOOGLE_CHECK
+#define ASSERT_TRUE GOOGLE_CHECK
+#define EXPECT_FALSE(COND) GOOGLE_CHECK(!(COND))
+#define EXPECT_EQ GOOGLE_CHECK_EQ
+#define ASSERT_EQ GOOGLE_CHECK_EQ
+
+namespace google {
+namespace protobuf_unittest {} // forward declaration
+
+namespace protobuf {
+
+namespace unittest = ::protobuf_unittest;
+
+class MapTestUtilImpl {
+ public:
+ // Set every field in the TestMap message to a unique value.
+ template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+ static void SetMapFields(MapMessage* message);
+
+ // Set every field in the TestArenaMap message to a unique value.
+ template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+ static void SetArenaMapFields(MapMessage* message);
+
+ // Set every field in the message to a default value.
+ template <typename MapMessage>
+ static void SetMapFieldsInitialized(MapMessage* message);
+
+ // Modify all the map fields of the message (which should already have been
+ // initialized with SetMapFields()).
+ template <typename EnumType, EnumType enum_value, typename MapMessage>
+ static void ModifyMapFields(MapMessage* message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFields() is called.
+ template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+ static void ExpectMapFieldsSet(const MapMessage& message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFields() is called for TestArenaMap.
+ template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+ static void ExpectArenaMapFieldsSet(const MapMessage& message);
+
+ // Check that all fields have the values that they should have after
+ // SetMapFieldsInitialized() is called.
+ template <typename EnumType, EnumType enum_value, typename MapMessage>
+ static void ExpectMapFieldsSetInitialized(const MapMessage& message);
+
+ // Expect that the message is modified as would be expected from
+ // ModifyMapFields().
+ template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+ static void ExpectMapFieldsModified(const MapMessage& message);
+
+ // Check that all fields are empty.
+ template <typename MapMessage>
+ static void ExpectClear(const MapMessage& message);
+
+ // // Check that all map fields have the given size.
+ // template <typename MapMessage>
+ // static void ExpectMapsSize(const MapMessage& message, int size);
+
+ // // Get pointers of map entries at given index.
+ // static std::vector<const Message*> GetMapEntries(
+ // const MapMessage& message, int index);
+
+ // // Get pointers of map entries from release.
+ // static std::vector<const Message*> GetMapEntriesFromRelease(
+ // MapMessage* message);
+};
+
+template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+void MapTestUtilImpl::SetMapFields(MapMessage* message) {
+ // Add first element.
+ (*message->mutable_map_int32_int32())[0] = 0;
+ (*message->mutable_map_int64_int64())[0] = 0;
+ (*message->mutable_map_uint32_uint32())[0] = 0;
+ (*message->mutable_map_uint64_uint64())[0] = 0;
+ (*message->mutable_map_sint32_sint32())[0] = 0;
+ (*message->mutable_map_sint64_sint64())[0] = 0;
+ (*message->mutable_map_fixed32_fixed32())[0] = 0;
+ (*message->mutable_map_fixed64_fixed64())[0] = 0;
+ (*message->mutable_map_sfixed32_sfixed32())[0] = 0;
+ (*message->mutable_map_sfixed64_sfixed64())[0] = 0;
+ (*message->mutable_map_int32_float())[0] = 0.0;
+ (*message->mutable_map_int32_double())[0] = 0.0;
+ (*message->mutable_map_bool_bool())[0] = false;
+ (*message->mutable_map_string_string())["0"] = "0";
+ (*message->mutable_map_int32_bytes())[0] = "0";
+ (*message->mutable_map_int32_enum())[0] = enum_value0;
+ (*message->mutable_map_int32_foreign_message())[0].set_c(0);
+
+ // Add second element
+ (*message->mutable_map_int32_int32())[1] = 1;
+ (*message->mutable_map_int64_int64())[1] = 1;
+ (*message->mutable_map_uint32_uint32())[1] = 1;
+ (*message->mutable_map_uint64_uint64())[1] = 1;
+ (*message->mutable_map_sint32_sint32())[1] = 1;
+ (*message->mutable_map_sint64_sint64())[1] = 1;
+ (*message->mutable_map_fixed32_fixed32())[1] = 1;
+ (*message->mutable_map_fixed64_fixed64())[1] = 1;
+ (*message->mutable_map_sfixed32_sfixed32())[1] = 1;
+ (*message->mutable_map_sfixed64_sfixed64())[1] = 1;
+ (*message->mutable_map_int32_float())[1] = 1.0;
+ (*message->mutable_map_int32_double())[1] = 1.0;
+ (*message->mutable_map_bool_bool())[1] = true;
+ (*message->mutable_map_string_string())["1"] = "1";
+ (*message->mutable_map_int32_bytes())[1] = "1";
+ (*message->mutable_map_int32_enum())[1] = enum_value1;
+ (*message->mutable_map_int32_foreign_message())[1].set_c(1);
+}
+
+template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+void MapTestUtilImpl::SetArenaMapFields(MapMessage* message) {
+ // Add first element.
+ (*message->mutable_map_int32_int32())[0] = 0;
+ (*message->mutable_map_int64_int64())[0] = 0;
+ (*message->mutable_map_uint32_uint32())[0] = 0;
+ (*message->mutable_map_uint64_uint64())[0] = 0;
+ (*message->mutable_map_sint32_sint32())[0] = 0;
+ (*message->mutable_map_sint64_sint64())[0] = 0;
+ (*message->mutable_map_fixed32_fixed32())[0] = 0;
+ (*message->mutable_map_fixed64_fixed64())[0] = 0;
+ (*message->mutable_map_sfixed32_sfixed32())[0] = 0;
+ (*message->mutable_map_sfixed64_sfixed64())[0] = 0;
+ (*message->mutable_map_int32_float())[0] = 0.0;
+ (*message->mutable_map_int32_double())[0] = 0.0;
+ (*message->mutable_map_bool_bool())[0] = false;
+ (*message->mutable_map_string_string())["0"] = "0";
+ (*message->mutable_map_int32_bytes())[0] = "0";
+ (*message->mutable_map_int32_enum())[0] = enum_value0;
+ (*message->mutable_map_int32_foreign_message())[0].set_c(0);
+ (*message->mutable_map_int32_foreign_message_no_arena())[0].set_c(0);
+
+ // Add second element
+ (*message->mutable_map_int32_int32())[1] = 1;
+ (*message->mutable_map_int64_int64())[1] = 1;
+ (*message->mutable_map_uint32_uint32())[1] = 1;
+ (*message->mutable_map_uint64_uint64())[1] = 1;
+ (*message->mutable_map_sint32_sint32())[1] = 1;
+ (*message->mutable_map_sint64_sint64())[1] = 1;
+ (*message->mutable_map_fixed32_fixed32())[1] = 1;
+ (*message->mutable_map_fixed64_fixed64())[1] = 1;
+ (*message->mutable_map_sfixed32_sfixed32())[1] = 1;
+ (*message->mutable_map_sfixed64_sfixed64())[1] = 1;
+ (*message->mutable_map_int32_float())[1] = 1.0;
+ (*message->mutable_map_int32_double())[1] = 1.0;
+ (*message->mutable_map_bool_bool())[1] = true;
+ (*message->mutable_map_string_string())["1"] = "1";
+ (*message->mutable_map_int32_bytes())[1] = "1";
+ (*message->mutable_map_int32_enum())[1] = enum_value1;
+ (*message->mutable_map_int32_foreign_message())[1].set_c(1);
+ (*message->mutable_map_int32_foreign_message_no_arena())[1].set_c(1);
+}
+
+template <typename MapMessage>
+void MapTestUtilImpl::SetMapFieldsInitialized(MapMessage* message) {
+ // Add first element using bracket operator, which should assign default
+ // value automatically.
+ (*message->mutable_map_int32_int32())[0];
+ (*message->mutable_map_int64_int64())[0];
+ (*message->mutable_map_uint32_uint32())[0];
+ (*message->mutable_map_uint64_uint64())[0];
+ (*message->mutable_map_sint32_sint32())[0];
+ (*message->mutable_map_sint64_sint64())[0];
+ (*message->mutable_map_fixed32_fixed32())[0];
+ (*message->mutable_map_fixed64_fixed64())[0];
+ (*message->mutable_map_sfixed32_sfixed32())[0];
+ (*message->mutable_map_sfixed64_sfixed64())[0];
+ (*message->mutable_map_int32_float())[0];
+ (*message->mutable_map_int32_double())[0];
+ (*message->mutable_map_bool_bool())[0];
+ (*message->mutable_map_string_string())["0"];
+ (*message->mutable_map_int32_bytes())[0];
+ (*message->mutable_map_int32_enum())[0];
+ (*message->mutable_map_int32_foreign_message())[0];
+}
+
+template <typename EnumType, EnumType enum_value, typename MapMessage>
+void MapTestUtilImpl::ModifyMapFields(MapMessage* message) {
+ (*message->mutable_map_int32_int32())[1] = 2;
+ (*message->mutable_map_int64_int64())[1] = 2;
+ (*message->mutable_map_uint32_uint32())[1] = 2;
+ (*message->mutable_map_uint64_uint64())[1] = 2;
+ (*message->mutable_map_sint32_sint32())[1] = 2;
+ (*message->mutable_map_sint64_sint64())[1] = 2;
+ (*message->mutable_map_fixed32_fixed32())[1] = 2;
+ (*message->mutable_map_fixed64_fixed64())[1] = 2;
+ (*message->mutable_map_sfixed32_sfixed32())[1] = 2;
+ (*message->mutable_map_sfixed64_sfixed64())[1] = 2;
+ (*message->mutable_map_int32_float())[1] = 2.0;
+ (*message->mutable_map_int32_double())[1] = 2.0;
+ (*message->mutable_map_bool_bool())[1] = false;
+ (*message->mutable_map_string_string())["1"] = "2";
+ (*message->mutable_map_int32_bytes())[1] = "2";
+ (*message->mutable_map_int32_enum())[1] = enum_value;
+ (*message->mutable_map_int32_foreign_message())[1].set_c(2);
+}
+
+template <typename MapMessage>
+void MapTestUtilImpl::ExpectClear(const MapMessage& message) {
+ EXPECT_EQ(0, message.map_int32_int32().size());
+ EXPECT_EQ(0, message.map_int64_int64().size());
+ EXPECT_EQ(0, message.map_uint32_uint32().size());
+ EXPECT_EQ(0, message.map_uint64_uint64().size());
+ EXPECT_EQ(0, message.map_sint32_sint32().size());
+ EXPECT_EQ(0, message.map_sint64_sint64().size());
+ EXPECT_EQ(0, message.map_fixed32_fixed32().size());
+ EXPECT_EQ(0, message.map_fixed64_fixed64().size());
+ EXPECT_EQ(0, message.map_sfixed32_sfixed32().size());
+ EXPECT_EQ(0, message.map_sfixed64_sfixed64().size());
+ EXPECT_EQ(0, message.map_int32_float().size());
+ EXPECT_EQ(0, message.map_int32_double().size());
+ EXPECT_EQ(0, message.map_bool_bool().size());
+ EXPECT_EQ(0, message.map_string_string().size());
+ EXPECT_EQ(0, message.map_int32_bytes().size());
+ EXPECT_EQ(0, message.map_int32_enum().size());
+ EXPECT_EQ(0, message.map_int32_foreign_message().size());
+}
+
+
+
+template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+void MapTestUtilImpl::ExpectMapFieldsSet(const MapMessage& message) {
+ EXPECT_EQ(2, message.map_int32_int32().size());
+ EXPECT_EQ(2, message.map_int64_int64().size());
+ EXPECT_EQ(2, message.map_uint32_uint32().size());
+ EXPECT_EQ(2, message.map_uint64_uint64().size());
+ EXPECT_EQ(2, message.map_sint32_sint32().size());
+ EXPECT_EQ(2, message.map_sint64_sint64().size());
+ EXPECT_EQ(2, message.map_fixed32_fixed32().size());
+ EXPECT_EQ(2, message.map_fixed64_fixed64().size());
+ EXPECT_EQ(2, message.map_sfixed32_sfixed32().size());
+ EXPECT_EQ(2, message.map_sfixed64_sfixed64().size());
+ EXPECT_EQ(2, message.map_int32_float().size());
+ EXPECT_EQ(2, message.map_int32_double().size());
+ EXPECT_EQ(2, message.map_bool_bool().size());
+ EXPECT_EQ(2, message.map_string_string().size());
+ EXPECT_EQ(2, message.map_int32_bytes().size());
+ EXPECT_EQ(2, message.map_int32_enum().size());
+ EXPECT_EQ(2, message.map_int32_foreign_message().size());
+
+ EXPECT_EQ(0, message.map_int32_int32().at(0));
+ EXPECT_EQ(0, message.map_int64_int64().at(0));
+ EXPECT_EQ(0, message.map_uint32_uint32().at(0));
+ EXPECT_EQ(0, message.map_uint64_uint64().at(0));
+ EXPECT_EQ(0, message.map_sint32_sint32().at(0));
+ EXPECT_EQ(0, message.map_sint64_sint64().at(0));
+ EXPECT_EQ(0, message.map_fixed32_fixed32().at(0));
+ EXPECT_EQ(0, message.map_fixed64_fixed64().at(0));
+ EXPECT_EQ(0, message.map_sfixed32_sfixed32().at(0));
+ EXPECT_EQ(0, message.map_sfixed64_sfixed64().at(0));
+ EXPECT_EQ(0, message.map_int32_float().at(0));
+ EXPECT_EQ(0, message.map_int32_double().at(0));
+ EXPECT_EQ(false, message.map_bool_bool().at(0));
+ EXPECT_EQ("0", message.map_string_string().at("0"));
+ EXPECT_EQ("0", message.map_int32_bytes().at(0));
+ EXPECT_EQ(enum_value0, message.map_int32_enum().at(0));
+ EXPECT_EQ(0, message.map_int32_foreign_message().at(0).c());
+
+ EXPECT_EQ(1, message.map_int32_int32().at(1));
+ EXPECT_EQ(1, message.map_int64_int64().at(1));
+ EXPECT_EQ(1, message.map_uint32_uint32().at(1));
+ EXPECT_EQ(1, message.map_uint64_uint64().at(1));
+ EXPECT_EQ(1, message.map_sint32_sint32().at(1));
+ EXPECT_EQ(1, message.map_sint64_sint64().at(1));
+ EXPECT_EQ(1, message.map_fixed32_fixed32().at(1));
+ EXPECT_EQ(1, message.map_fixed64_fixed64().at(1));
+ EXPECT_EQ(1, message.map_sfixed32_sfixed32().at(1));
+ EXPECT_EQ(1, message.map_sfixed64_sfixed64().at(1));
+ EXPECT_EQ(1, message.map_int32_float().at(1));
+ EXPECT_EQ(1, message.map_int32_double().at(1));
+ EXPECT_EQ(true, message.map_bool_bool().at(1));
+ EXPECT_EQ("1", message.map_string_string().at("1"));
+ EXPECT_EQ("1", message.map_int32_bytes().at(1));
+ EXPECT_EQ(enum_value1, message.map_int32_enum().at(1));
+ EXPECT_EQ(1, message.map_int32_foreign_message().at(1).c());
+}
+
+template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+void MapTestUtilImpl::ExpectArenaMapFieldsSet(const MapMessage& message) {
+ EXPECT_EQ(2, message.map_int32_int32().size());
+ EXPECT_EQ(2, message.map_int64_int64().size());
+ EXPECT_EQ(2, message.map_uint32_uint32().size());
+ EXPECT_EQ(2, message.map_uint64_uint64().size());
+ EXPECT_EQ(2, message.map_sint32_sint32().size());
+ EXPECT_EQ(2, message.map_sint64_sint64().size());
+ EXPECT_EQ(2, message.map_fixed32_fixed32().size());
+ EXPECT_EQ(2, message.map_fixed64_fixed64().size());
+ EXPECT_EQ(2, message.map_sfixed32_sfixed32().size());
+ EXPECT_EQ(2, message.map_sfixed64_sfixed64().size());
+ EXPECT_EQ(2, message.map_int32_float().size());
+ EXPECT_EQ(2, message.map_int32_double().size());
+ EXPECT_EQ(2, message.map_bool_bool().size());
+ EXPECT_EQ(2, message.map_string_string().size());
+ EXPECT_EQ(2, message.map_int32_bytes().size());
+ EXPECT_EQ(2, message.map_int32_enum().size());
+ EXPECT_EQ(2, message.map_int32_foreign_message().size());
+ EXPECT_EQ(2, message.map_int32_foreign_message_no_arena().size());
+
+ EXPECT_EQ(0, message.map_int32_int32().at(0));
+ EXPECT_EQ(0, message.map_int64_int64().at(0));
+ EXPECT_EQ(0, message.map_uint32_uint32().at(0));
+ EXPECT_EQ(0, message.map_uint64_uint64().at(0));
+ EXPECT_EQ(0, message.map_sint32_sint32().at(0));
+ EXPECT_EQ(0, message.map_sint64_sint64().at(0));
+ EXPECT_EQ(0, message.map_fixed32_fixed32().at(0));
+ EXPECT_EQ(0, message.map_fixed64_fixed64().at(0));
+ EXPECT_EQ(0, message.map_sfixed32_sfixed32().at(0));
+ EXPECT_EQ(0, message.map_sfixed64_sfixed64().at(0));
+ EXPECT_EQ(0, message.map_int32_float().at(0));
+ EXPECT_EQ(0, message.map_int32_double().at(0));
+ EXPECT_EQ(false, message.map_bool_bool().at(0));
+ EXPECT_EQ("0", message.map_string_string().at("0"));
+ EXPECT_EQ("0", message.map_int32_bytes().at(0));
+ EXPECT_EQ(enum_value0, message.map_int32_enum().at(0));
+ EXPECT_EQ(0, message.map_int32_foreign_message().at(0).c());
+ EXPECT_EQ(0, message.map_int32_foreign_message_no_arena().at(0).c());
+
+ EXPECT_EQ(1, message.map_int32_int32().at(1));
+ EXPECT_EQ(1, message.map_int64_int64().at(1));
+ EXPECT_EQ(1, message.map_uint32_uint32().at(1));
+ EXPECT_EQ(1, message.map_uint64_uint64().at(1));
+ EXPECT_EQ(1, message.map_sint32_sint32().at(1));
+ EXPECT_EQ(1, message.map_sint64_sint64().at(1));
+ EXPECT_EQ(1, message.map_fixed32_fixed32().at(1));
+ EXPECT_EQ(1, message.map_fixed64_fixed64().at(1));
+ EXPECT_EQ(1, message.map_sfixed32_sfixed32().at(1));
+ EXPECT_EQ(1, message.map_sfixed64_sfixed64().at(1));
+ EXPECT_EQ(1, message.map_int32_float().at(1));
+ EXPECT_EQ(1, message.map_int32_double().at(1));
+ EXPECT_EQ(true, message.map_bool_bool().at(1));
+ EXPECT_EQ("1", message.map_string_string().at("1"));
+ EXPECT_EQ("1", message.map_int32_bytes().at(1));
+ EXPECT_EQ(enum_value1, message.map_int32_enum().at(1));
+ EXPECT_EQ(1, message.map_int32_foreign_message().at(1).c());
+ EXPECT_EQ(1, message.map_int32_foreign_message_no_arena().at(1).c());
+}
+
+template <typename EnumType, EnumType enum_value, typename MapMessage>
+void MapTestUtilImpl::ExpectMapFieldsSetInitialized(
+ const MapMessage& message) {
+ EXPECT_EQ(1, message.map_int32_int32().size());
+ EXPECT_EQ(1, message.map_int64_int64().size());
+ EXPECT_EQ(1, message.map_uint32_uint32().size());
+ EXPECT_EQ(1, message.map_uint64_uint64().size());
+ EXPECT_EQ(1, message.map_sint32_sint32().size());
+ EXPECT_EQ(1, message.map_sint64_sint64().size());
+ EXPECT_EQ(1, message.map_fixed32_fixed32().size());
+ EXPECT_EQ(1, message.map_fixed64_fixed64().size());
+ EXPECT_EQ(1, message.map_sfixed32_sfixed32().size());
+ EXPECT_EQ(1, message.map_sfixed64_sfixed64().size());
+ EXPECT_EQ(1, message.map_int32_float().size());
+ EXPECT_EQ(1, message.map_int32_double().size());
+ EXPECT_EQ(1, message.map_bool_bool().size());
+ EXPECT_EQ(1, message.map_string_string().size());
+ EXPECT_EQ(1, message.map_int32_bytes().size());
+ EXPECT_EQ(1, message.map_int32_enum().size());
+ EXPECT_EQ(1, message.map_int32_foreign_message().size());
+
+ EXPECT_EQ(0, message.map_int32_int32().at(0));
+ EXPECT_EQ(0, message.map_int64_int64().at(0));
+ EXPECT_EQ(0, message.map_uint32_uint32().at(0));
+ EXPECT_EQ(0, message.map_uint64_uint64().at(0));
+ EXPECT_EQ(0, message.map_sint32_sint32().at(0));
+ EXPECT_EQ(0, message.map_sint64_sint64().at(0));
+ EXPECT_EQ(0, message.map_fixed32_fixed32().at(0));
+ EXPECT_EQ(0, message.map_fixed64_fixed64().at(0));
+ EXPECT_EQ(0, message.map_sfixed32_sfixed32().at(0));
+ EXPECT_EQ(0, message.map_sfixed64_sfixed64().at(0));
+ EXPECT_EQ(0, message.map_int32_float().at(0));
+ EXPECT_EQ(0, message.map_int32_double().at(0));
+ EXPECT_EQ(false, message.map_bool_bool().at(0));
+ EXPECT_EQ("", message.map_string_string().at("0"));
+ EXPECT_EQ("", message.map_int32_bytes().at(0));
+ EXPECT_EQ(enum_value, message.map_int32_enum().at(0));
+ EXPECT_EQ(0, message.map_int32_foreign_message().at(0).ByteSize());
+}
+
+template <typename EnumType, EnumType enum_value0,
+ EnumType enum_value1, typename MapMessage>
+void MapTestUtilImpl::ExpectMapFieldsModified(
+ const MapMessage& message) {
+ // ModifyMapFields only sets the second element of each field. In addition to
+ // verifying this, we also verify that the first element and size were *not*
+ // modified.
+ EXPECT_EQ(2, message.map_int32_int32().size());
+ EXPECT_EQ(2, message.map_int64_int64().size());
+ EXPECT_EQ(2, message.map_uint32_uint32().size());
+ EXPECT_EQ(2, message.map_uint64_uint64().size());
+ EXPECT_EQ(2, message.map_sint32_sint32().size());
+ EXPECT_EQ(2, message.map_sint64_sint64().size());
+ EXPECT_EQ(2, message.map_fixed32_fixed32().size());
+ EXPECT_EQ(2, message.map_fixed64_fixed64().size());
+ EXPECT_EQ(2, message.map_sfixed32_sfixed32().size());
+ EXPECT_EQ(2, message.map_sfixed64_sfixed64().size());
+ EXPECT_EQ(2, message.map_int32_float().size());
+ EXPECT_EQ(2, message.map_int32_double().size());
+ EXPECT_EQ(2, message.map_bool_bool().size());
+ EXPECT_EQ(2, message.map_string_string().size());
+ EXPECT_EQ(2, message.map_int32_bytes().size());
+ EXPECT_EQ(2, message.map_int32_enum().size());
+ EXPECT_EQ(2, message.map_int32_foreign_message().size());
+
+ EXPECT_EQ(0, message.map_int32_int32().at(0));
+ EXPECT_EQ(0, message.map_int64_int64().at(0));
+ EXPECT_EQ(0, message.map_uint32_uint32().at(0));
+ EXPECT_EQ(0, message.map_uint64_uint64().at(0));
+ EXPECT_EQ(0, message.map_sint32_sint32().at(0));
+ EXPECT_EQ(0, message.map_sint64_sint64().at(0));
+ EXPECT_EQ(0, message.map_fixed32_fixed32().at(0));
+ EXPECT_EQ(0, message.map_fixed64_fixed64().at(0));
+ EXPECT_EQ(0, message.map_sfixed32_sfixed32().at(0));
+ EXPECT_EQ(0, message.map_sfixed64_sfixed64().at(0));
+ EXPECT_EQ(0, message.map_int32_float().at(0));
+ EXPECT_EQ(0, message.map_int32_double().at(0));
+ EXPECT_EQ(false, message.map_bool_bool().at(0));
+ EXPECT_EQ("0", message.map_string_string().at("0"));
+ EXPECT_EQ("0", message.map_int32_bytes().at(0));
+ EXPECT_EQ(enum_value0, message.map_int32_enum().at(0));
+ EXPECT_EQ(0, message.map_int32_foreign_message().at(0).c());
+
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(2, message.map_int32_int32().at(1));
+ EXPECT_EQ(2, message.map_int64_int64().at(1));
+ EXPECT_EQ(2, message.map_uint32_uint32().at(1));
+ EXPECT_EQ(2, message.map_uint64_uint64().at(1));
+ EXPECT_EQ(2, message.map_sint32_sint32().at(1));
+ EXPECT_EQ(2, message.map_sint64_sint64().at(1));
+ EXPECT_EQ(2, message.map_fixed32_fixed32().at(1));
+ EXPECT_EQ(2, message.map_fixed64_fixed64().at(1));
+ EXPECT_EQ(2, message.map_sfixed32_sfixed32().at(1));
+ EXPECT_EQ(2, message.map_sfixed64_sfixed64().at(1));
+ EXPECT_EQ(2, message.map_int32_float().at(1));
+ EXPECT_EQ(2, message.map_int32_double().at(1));
+ EXPECT_EQ(false, message.map_bool_bool().at(1));
+ EXPECT_EQ("2", message.map_string_string().at("1"));
+ EXPECT_EQ("2", message.map_int32_bytes().at(1));
+ EXPECT_EQ(enum_value1, message.map_int32_enum().at(1));
+ EXPECT_EQ(2, message.map_int32_foreign_message().at(1).c());
+}
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MAP_TEST_UTIL_IMPL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_type_handler.h b/third_party/protobuf/3.0.0/src/google/protobuf/map_type_handler.h
new file mode 100644
index 0000000000..685a770fb9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_type_handler.h
@@ -0,0 +1,743 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_TYPE_HANDLER_H__
+#define GOOGLE_PROTOBUF_TYPE_HANDLER_H__
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Used for compile time type selection. MapIf::type will be TrueType if Flag is
+// true and FalseType otherwise.
+template<bool Flag, typename TrueType, typename FalseType>
+struct MapIf;
+
+template<typename TrueType, typename FalseType>
+struct MapIf<true, TrueType, FalseType> {
+ typedef TrueType type;
+};
+
+template<typename TrueType, typename FalseType>
+struct MapIf<false, TrueType, FalseType> {
+ typedef FalseType type;
+};
+
+// In proto2 Map, enum needs to be initialized to given default value, while
+// other types' default value can be inferred from the type.
+template <bool IsEnum, typename Type>
+class MapValueInitializer {
+ public:
+ static inline void Initialize(Type& type, int default_enum_value);
+};
+
+template <typename Type>
+class MapValueInitializer<true, Type> {
+ public:
+ static inline void Initialize(Type& value, int default_enum_value) {
+ value = static_cast<Type>(default_enum_value);
+ }
+};
+
+template <typename Type>
+class MapValueInitializer<false, Type> {
+ public:
+ static inline void Initialize(Type& value, int default_enum_value) {}
+};
+
+template <typename Type, bool is_arena_constructable>
+class MapArenaMessageCreator {
+ public:
+ // Use arena to create message if Type is arena constructable. Otherwise,
+ // create the message on heap.
+ static inline Type* CreateMessage(Arena* arena);
+};
+template <typename Type>
+class MapArenaMessageCreator<Type, true> {
+ public:
+ static inline Type* CreateMessage(Arena* arena) {
+ return Arena::CreateMessage<Type>(arena);
+ }
+};
+template <typename Type>
+class MapArenaMessageCreator<Type, false> {
+ public:
+ static inline Type* CreateMessage(Arena* arena) {
+ return Arena::Create<Type>(arena);
+ }
+};
+
+// Define constants for given wire field type
+template <WireFormatLite::FieldType field_type, typename Type>
+class MapWireFieldTypeTraits {};
+
+#define TYPE_TRAITS(FieldType, CType, WireFormatType, IsMessage, IsEnum) \
+ template <typename Type> \
+ class MapWireFieldTypeTraits<WireFormatLite::TYPE_##FieldType, Type> { \
+ public: \
+ static const bool kIsMessage = IsMessage; \
+ static const bool kIsEnum = IsEnum; \
+ typedef typename MapIf<kIsMessage, Type*, CType>::type TypeOnMemory; \
+ typedef typename MapIf<kIsEnum, int, Type>::type MapEntryAccessorType; \
+ static const WireFormatLite::WireType kWireType = \
+ WireFormatLite::WIRETYPE_##WireFormatType; \
+ };
+
+TYPE_TRAITS(MESSAGE , Type, LENGTH_DELIMITED, true, false)
+TYPE_TRAITS(STRING , ArenaStringPtr, LENGTH_DELIMITED, false, false)
+TYPE_TRAITS(BYTES , ArenaStringPtr , LENGTH_DELIMITED, false, false)
+TYPE_TRAITS(INT64 , int64 , VARINT , false, false)
+TYPE_TRAITS(UINT64 , uint64 , VARINT , false, false)
+TYPE_TRAITS(INT32 , int32 , VARINT , false, false)
+TYPE_TRAITS(UINT32 , uint32 , VARINT , false, false)
+TYPE_TRAITS(SINT64 , int64 , VARINT , false, false)
+TYPE_TRAITS(SINT32 , int32 , VARINT , false, false)
+TYPE_TRAITS(ENUM , int , VARINT , false, true )
+TYPE_TRAITS(DOUBLE , double , FIXED64, false, false)
+TYPE_TRAITS(FLOAT , float , FIXED32, false, false)
+TYPE_TRAITS(FIXED64 , uint64 , FIXED64, false, false)
+TYPE_TRAITS(FIXED32 , uint32 , FIXED32, false, false)
+TYPE_TRAITS(SFIXED64, int64 , FIXED64, false, false)
+TYPE_TRAITS(SFIXED32, int32 , FIXED32, false, false)
+TYPE_TRAITS(BOOL , bool , VARINT , false, false)
+
+#undef TYPE_TRAITS
+
+template <WireFormatLite::FieldType field_type, typename Type>
+class MapTypeHandler {};
+
+template <typename Type>
+class MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type> {
+ public:
+ // Enum type cannot be used for MapTypeHandler::Read. Define a type which will
+ // replace Enum with int.
+ typedef typename MapWireFieldTypeTraits<WireFormatLite::TYPE_MESSAGE,
+ Type>::MapEntryAccessorType MapEntryAccessorType;
+ // Internal stored type in MapEntryLite for given wire field type.
+ typedef typename MapWireFieldTypeTraits<WireFormatLite::TYPE_MESSAGE,
+ Type>::TypeOnMemory TypeOnMemory;
+ // Corresponding wire type for field type.
+ static const WireFormatLite::WireType kWireType =
+ MapWireFieldTypeTraits<WireFormatLite::TYPE_MESSAGE, Type>::kWireType;
+ // Whether wire type is for message.
+ static const bool kIsMessage =
+ MapWireFieldTypeTraits<WireFormatLite::TYPE_MESSAGE, Type>::kIsMessage;
+ // Whether wire type is for enum.
+ static const bool kIsEnum =
+ MapWireFieldTypeTraits<WireFormatLite::TYPE_MESSAGE, Type>::kIsEnum;
+
+ // Functions used in parsing and serialization. ===================
+ static inline int ByteSize(const MapEntryAccessorType& value);
+ static inline int GetCachedSize(const MapEntryAccessorType& value);
+ static inline bool Read(io::CodedInputStream* input,
+ MapEntryAccessorType* value);
+ static inline void Write(int field, const MapEntryAccessorType& value,
+ io::CodedOutputStream* output);
+ static inline uint8* InternalWriteToArray(int field,
+ const MapEntryAccessorType& value,
+ bool deterministic, uint8* target);
+ static inline uint8* WriteToArray(int field,
+ const MapEntryAccessorType& value,
+ uint8* target);
+
+ // Functions to manipulate data on memory. ========================
+ static inline const Type& GetExternalReference(const Type* value);
+ static inline void DeleteNoArena(const Type* x);
+ static inline void Merge(const Type& from, Type** to, Arena* arena);
+ static inline void Clear(Type** value, Arena* arena);
+ static inline void ClearMaybeByDefaultEnum(Type** value, Arena* arena,
+ int default_enum_value);
+ static inline void Initialize(Type** x, Arena* arena);
+
+ static inline void InitializeMaybeByDefaultEnum(Type** x,
+ int default_enum_value,
+ Arena* arena);
+ static inline Type* EnsureMutable(Type** value, Arena* arena);
+ // SpaceUsedInMapEntry: Return bytes used by value in MapEntry, excluding
+ // those already calculate in sizeof(MapField).
+ static inline int SpaceUsedInMapEntry(const Type* value);
+ // Return bytes used by value in Map.
+ static inline int SpaceUsedInMap(const Type& value);
+ // Assign default value to given instance.
+ static inline void AssignDefaultValue(Type** value);
+ // Return default instance if value is not initialized when calling const
+ // reference accessor.
+ static inline const Type& DefaultIfNotInitialized(
+ const Type* value, const Type* default_value);
+ // Check if all required fields have values set.
+ static inline bool IsInitialized(Type* value);
+};
+
+#define MAP_HANDLER(FieldType) \
+ template <typename Type> \
+ class MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type> { \
+ public: \
+ typedef typename MapWireFieldTypeTraits<WireFormatLite::TYPE_##FieldType, \
+ Type>::MapEntryAccessorType \
+ MapEntryAccessorType; \
+ typedef typename MapWireFieldTypeTraits<WireFormatLite::TYPE_##FieldType, \
+ Type>::TypeOnMemory TypeOnMemory; \
+ static const WireFormatLite::WireType kWireType = \
+ MapWireFieldTypeTraits<WireFormatLite::TYPE_##FieldType, \
+ Type>::kWireType; \
+ static const bool kIsMessage = \
+ MapWireFieldTypeTraits<WireFormatLite::TYPE_##FieldType, \
+ Type>::kIsMessage; \
+ static const bool kIsEnum = \
+ MapWireFieldTypeTraits<WireFormatLite::TYPE_##FieldType, \
+ Type>::kIsEnum; \
+ static inline int ByteSize(const MapEntryAccessorType& value); \
+ static inline int GetCachedSize(const MapEntryAccessorType& value); \
+ static inline bool Read(io::CodedInputStream* input, \
+ MapEntryAccessorType* value); \
+ static inline void Write(int field, const MapEntryAccessorType& value, \
+ io::CodedOutputStream* output); \
+ static inline uint8* InternalWriteToArray( \
+ int field, \
+ const MapEntryAccessorType& value, \
+ bool deterministic, \
+ uint8* target); \
+ static inline uint8* WriteToArray(int field, \
+ const MapEntryAccessorType& value, \
+ uint8* target) { \
+ return InternalWriteToArray(field, value, false, target); \
+ } \
+ static inline const MapEntryAccessorType& GetExternalReference( \
+ const TypeOnMemory& value); \
+ static inline void DeleteNoArena(const TypeOnMemory& x); \
+ static inline void Merge(const MapEntryAccessorType& from, \
+ TypeOnMemory* to, Arena* arena); \
+ static inline void Clear(TypeOnMemory* value, Arena* arena); \
+ static inline void ClearMaybeByDefaultEnum(TypeOnMemory* value, \
+ Arena* arena, \
+ int default_enum); \
+ static inline int SpaceUsedInMapEntry(const TypeOnMemory& value); \
+ static inline int SpaceUsedInMap(const TypeOnMemory& value); \
+ static inline int SpaceUsedInMap(const string& value); \
+ static inline void AssignDefaultValue(TypeOnMemory* value); \
+ static inline const MapEntryAccessorType& DefaultIfNotInitialized( \
+ const TypeOnMemory& value, const TypeOnMemory& default_value); \
+ static inline bool IsInitialized(const TypeOnMemory& value); \
+ static void DeleteNoArena(TypeOnMemory& value); \
+ static inline void Initialize(TypeOnMemory* value, Arena* arena); \
+ static inline void InitializeMaybeByDefaultEnum(TypeOnMemory* value, \
+ int default_enum_value, \
+ Arena* arena); \
+ static inline MapEntryAccessorType* EnsureMutable(TypeOnMemory* value, \
+ Arena* arena); \
+ };
+MAP_HANDLER(STRING)
+MAP_HANDLER(BYTES)
+MAP_HANDLER(INT64)
+MAP_HANDLER(UINT64)
+MAP_HANDLER(INT32)
+MAP_HANDLER(UINT32)
+MAP_HANDLER(SINT64)
+MAP_HANDLER(SINT32)
+MAP_HANDLER(ENUM)
+MAP_HANDLER(DOUBLE)
+MAP_HANDLER(FLOAT)
+MAP_HANDLER(FIXED64)
+MAP_HANDLER(FIXED32)
+MAP_HANDLER(SFIXED64)
+MAP_HANDLER(SFIXED32)
+MAP_HANDLER(BOOL)
+#undef MAP_HANDLER
+
+template <typename Type>
+inline int
+MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::ByteSize(
+ const MapEntryAccessorType& value) {
+ return WireFormatLite::MessageSizeNoVirtual(value);
+}
+
+#define GOOGLE_PROTOBUF_BYTE_SIZE(FieldType, DeclaredType) \
+ template <typename Type> \
+ inline int MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::ByteSize( \
+ const MapEntryAccessorType& value) { \
+ return WireFormatLite::DeclaredType##Size(value); \
+ }
+
+GOOGLE_PROTOBUF_BYTE_SIZE(STRING, String)
+GOOGLE_PROTOBUF_BYTE_SIZE(BYTES , Bytes)
+GOOGLE_PROTOBUF_BYTE_SIZE(INT64 , Int64)
+GOOGLE_PROTOBUF_BYTE_SIZE(UINT64, UInt64)
+GOOGLE_PROTOBUF_BYTE_SIZE(INT32 , Int32)
+GOOGLE_PROTOBUF_BYTE_SIZE(UINT32, UInt32)
+GOOGLE_PROTOBUF_BYTE_SIZE(SINT64, SInt64)
+GOOGLE_PROTOBUF_BYTE_SIZE(SINT32, SInt32)
+GOOGLE_PROTOBUF_BYTE_SIZE(ENUM , Enum)
+
+#undef GOOGLE_PROTOBUF_BYTE_SIZE
+
+#define FIXED_BYTE_SIZE(FieldType, DeclaredType) \
+ template <typename Type> \
+ inline int MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::ByteSize( \
+ const MapEntryAccessorType& value) { \
+ return WireFormatLite::k##DeclaredType##Size; \
+ }
+
+FIXED_BYTE_SIZE(DOUBLE , Double)
+FIXED_BYTE_SIZE(FLOAT , Float)
+FIXED_BYTE_SIZE(FIXED64 , Fixed64)
+FIXED_BYTE_SIZE(FIXED32 , Fixed32)
+FIXED_BYTE_SIZE(SFIXED64, SFixed64)
+FIXED_BYTE_SIZE(SFIXED32, SFixed32)
+FIXED_BYTE_SIZE(BOOL , Bool)
+
+#undef FIXED_BYTE_SIZE
+
+template <typename Type>
+inline int
+MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::GetCachedSize(
+ const MapEntryAccessorType& value) {
+ return WireFormatLite::LengthDelimitedSize(value.GetCachedSize());
+}
+
+#define GET_CACHED_SIZE(FieldType, DeclaredType) \
+ template <typename Type> \
+ inline int \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::GetCachedSize( \
+ const MapEntryAccessorType& value) { \
+ return WireFormatLite::DeclaredType##Size(value); \
+ }
+
+GET_CACHED_SIZE(STRING, String)
+GET_CACHED_SIZE(BYTES , Bytes)
+GET_CACHED_SIZE(INT64 , Int64)
+GET_CACHED_SIZE(UINT64, UInt64)
+GET_CACHED_SIZE(INT32 , Int32)
+GET_CACHED_SIZE(UINT32, UInt32)
+GET_CACHED_SIZE(SINT64, SInt64)
+GET_CACHED_SIZE(SINT32, SInt32)
+GET_CACHED_SIZE(ENUM , Enum)
+
+#undef GET_CACHED_SIZE
+
+#define GET_FIXED_CACHED_SIZE(FieldType, DeclaredType) \
+ template <typename Type> \
+ inline int \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::GetCachedSize( \
+ const MapEntryAccessorType& value) { \
+ return WireFormatLite::k##DeclaredType##Size; \
+ }
+
+GET_FIXED_CACHED_SIZE(DOUBLE , Double)
+GET_FIXED_CACHED_SIZE(FLOAT , Float)
+GET_FIXED_CACHED_SIZE(FIXED64 , Fixed64)
+GET_FIXED_CACHED_SIZE(FIXED32 , Fixed32)
+GET_FIXED_CACHED_SIZE(SFIXED64, SFixed64)
+GET_FIXED_CACHED_SIZE(SFIXED32, SFixed32)
+GET_FIXED_CACHED_SIZE(BOOL , Bool)
+
+#undef GET_FIXED_CACHED_SIZE
+
+template <typename Type>
+inline void MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::Write(
+ int field, const MapEntryAccessorType& value,
+ io::CodedOutputStream* output) {
+ WireFormatLite::WriteMessageMaybeToArray(field, value, output);
+}
+
+template <typename Type>
+inline uint8*
+MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::InternalWriteToArray(
+ int field, const MapEntryAccessorType& value, bool deterministic,
+ uint8* target) {
+ return WireFormatLite::InternalWriteMessageToArray(field, value,
+ deterministic, target);
+}
+
+#define WRITE_METHOD(FieldType, DeclaredType) \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Write( \
+ int field, const MapEntryAccessorType& value, \
+ io::CodedOutputStream* output) { \
+ return WireFormatLite::Write##DeclaredType(field, value, output); \
+ } \
+ template <typename Type> \
+ inline uint8* \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::InternalWriteToArray( \
+ int field, const MapEntryAccessorType& value, bool, uint8* target) { \
+ return WireFormatLite::Write##DeclaredType##ToArray(field, value, target); \
+ }
+
+WRITE_METHOD(STRING , String)
+WRITE_METHOD(BYTES , Bytes)
+WRITE_METHOD(INT64 , Int64)
+WRITE_METHOD(UINT64 , UInt64)
+WRITE_METHOD(INT32 , Int32)
+WRITE_METHOD(UINT32 , UInt32)
+WRITE_METHOD(SINT64 , SInt64)
+WRITE_METHOD(SINT32 , SInt32)
+WRITE_METHOD(ENUM , Enum)
+WRITE_METHOD(DOUBLE , Double)
+WRITE_METHOD(FLOAT , Float)
+WRITE_METHOD(FIXED64 , Fixed64)
+WRITE_METHOD(FIXED32 , Fixed32)
+WRITE_METHOD(SFIXED64, SFixed64)
+WRITE_METHOD(SFIXED32, SFixed32)
+WRITE_METHOD(BOOL , Bool)
+
+#undef WRITE_METHOD
+
+template <typename Type>
+inline bool MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::Read(
+ io::CodedInputStream* input, MapEntryAccessorType* value) {
+ return WireFormatLite::ReadMessageNoVirtual(input, value);
+}
+
+template <typename Type>
+inline bool MapTypeHandler<WireFormatLite::TYPE_STRING, Type>::Read(
+ io::CodedInputStream* input, MapEntryAccessorType* value) {
+ return WireFormatLite::ReadString(input, value);
+}
+
+template <typename Type>
+inline bool MapTypeHandler<WireFormatLite::TYPE_BYTES, Type>::Read(
+ io::CodedInputStream* input, MapEntryAccessorType* value) {
+ return WireFormatLite::ReadBytes(input, value);
+}
+
+#define READ_METHOD(FieldType) \
+ template <typename Type> \
+ inline bool MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Read( \
+ io::CodedInputStream* input, MapEntryAccessorType* value) { \
+ return WireFormatLite::ReadPrimitive<TypeOnMemory, \
+ WireFormatLite::TYPE_##FieldType>( \
+ input, value); \
+ }
+
+READ_METHOD(INT64)
+READ_METHOD(UINT64)
+READ_METHOD(INT32)
+READ_METHOD(UINT32)
+READ_METHOD(SINT64)
+READ_METHOD(SINT32)
+READ_METHOD(ENUM)
+READ_METHOD(DOUBLE)
+READ_METHOD(FLOAT)
+READ_METHOD(FIXED64)
+READ_METHOD(FIXED32)
+READ_METHOD(SFIXED64)
+READ_METHOD(SFIXED32)
+READ_METHOD(BOOL)
+
+#undef READ_METHOD
+
+// Definition for message handler
+
+template <typename Type>
+inline const Type&
+MapTypeHandler<WireFormatLite::TYPE_MESSAGE,
+ Type>::GetExternalReference(const Type* value) {
+ return *value;
+}
+
+template <typename Type>
+inline int
+MapTypeHandler<WireFormatLite::TYPE_MESSAGE,
+ Type>::SpaceUsedInMapEntry(const Type* value) {
+ return value->SpaceUsed();
+}
+
+template <typename Type>
+int MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::SpaceUsedInMap(
+ const Type& value) {
+ return value.SpaceUsed();
+}
+
+template <typename Type>
+inline void MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::Clear(
+ Type** value, Arena* arena) {
+ if (*value != NULL) (*value)->Clear();
+}
+template <typename Type>
+inline void
+MapTypeHandler<WireFormatLite::TYPE_MESSAGE,
+ Type>::ClearMaybeByDefaultEnum(Type** value,
+ Arena* arena,
+ int default_enum_value) {
+ if (*value != NULL) (*value)->Clear();
+}
+template <typename Type>
+inline void MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::Merge(
+ const Type& from, Type** to, Arena* arena) {
+ (*to)->MergeFrom(from);
+}
+
+template <typename Type>
+void MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::DeleteNoArena(
+ const Type* ptr) {
+ delete ptr;
+}
+
+template <typename Type>
+inline void MapTypeHandler<WireFormatLite::TYPE_MESSAGE,
+ Type>::AssignDefaultValue(Type** value) {
+ *value = const_cast<Type*>(&Type::default_instance());
+}
+
+template <typename Type>
+inline void MapTypeHandler<WireFormatLite::TYPE_MESSAGE,
+ Type>::Initialize(Type** x,
+ Arena* arena) {
+ *x = NULL;
+}
+
+template <typename Type>
+inline void MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::
+ InitializeMaybeByDefaultEnum(Type** x, int default_enum_value,
+ Arena* arena) {
+ *x = NULL;
+}
+
+template <typename Type>
+inline Type* MapTypeHandler<WireFormatLite::TYPE_MESSAGE,
+ Type>::EnsureMutable(Type** value,
+ Arena* arena) {
+ if (*value == NULL) {
+ *value =
+ MapArenaMessageCreator<Type, Arena::is_arena_constructable<Type>::
+ type::value>::CreateMessage(arena);
+ }
+ return *value;
+}
+
+template <typename Type>
+inline const Type& MapTypeHandler<WireFormatLite::TYPE_MESSAGE, Type>::
+ DefaultIfNotInitialized(const Type* value, const Type* default_value) {
+ return value != NULL ? *value : *default_value;
+}
+
+template <typename Type>
+inline bool MapTypeHandler<WireFormatLite::TYPE_MESSAGE,
+ Type>::IsInitialized(Type* value) {
+ return value->IsInitialized();
+}
+
+// Definition for string/bytes handler
+
+#define STRING_OR_BYTES_HANDLER_FUNCTIONS(FieldType) \
+ template <typename Type> \
+ inline const typename MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::MapEntryAccessorType& \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::GetExternalReference(const TypeOnMemory& value) { \
+ return value.Get(&::google::protobuf::internal::GetEmptyStringAlreadyInited()); \
+ } \
+ template <typename Type> \
+ inline int \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::SpaceUsedInMapEntry( \
+ const TypeOnMemory& value) { \
+ return sizeof(value); \
+ } \
+ template <typename Type> \
+ inline int MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::SpaceUsedInMap(const TypeOnMemory& value) { \
+ return sizeof(value); \
+ } \
+ template <typename Type> \
+ inline int MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::SpaceUsedInMap(const string& value) { \
+ return sizeof(value); \
+ } \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Clear( \
+ TypeOnMemory* value, Arena* arena) { \
+ value->ClearToEmpty(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), \
+ arena); \
+ } \
+ template <typename Type> \
+ inline void \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::ClearMaybeByDefaultEnum(TypeOnMemory* value, \
+ Arena* arena, \
+ int default_enum) { \
+ Clear(value, arena); \
+ } \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Merge( \
+ const MapEntryAccessorType& from, TypeOnMemory* to, Arena* arena) { \
+ to->Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from, arena); \
+ } \
+ template <typename Type> \
+ void MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::DeleteNoArena( \
+ TypeOnMemory& value) { \
+ value.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited()); \
+ } \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::AssignDefaultValue(TypeOnMemory* value) {} \
+ template <typename Type> \
+ inline void \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Initialize( \
+ TypeOnMemory* value, Arena* arena) { \
+ value->UnsafeSetDefault( \
+ &::google::protobuf::internal::GetEmptyStringAlreadyInited()); \
+ } \
+ template <typename Type> \
+ inline void \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::InitializeMaybeByDefaultEnum(TypeOnMemory* value, \
+ int default_enum_value, \
+ Arena* arena) { \
+ Initialize(value, arena); \
+ } \
+ template <typename Type> \
+ inline typename MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::MapEntryAccessorType* \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::EnsureMutable( \
+ TypeOnMemory* value, Arena* arena) { \
+ return value->Mutable(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), \
+ arena); \
+ } \
+ template <typename Type> \
+ inline const typename MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::MapEntryAccessorType& \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::DefaultIfNotInitialized(const TypeOnMemory& value, \
+ const TypeOnMemory& \
+ default_value) { \
+ return value.Get(&::google::protobuf::internal::GetEmptyStringAlreadyInited()); \
+ } \
+ template <typename Type> \
+ inline bool MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::IsInitialized(const TypeOnMemory& value) { \
+ return true; \
+ }
+STRING_OR_BYTES_HANDLER_FUNCTIONS(STRING)
+STRING_OR_BYTES_HANDLER_FUNCTIONS(BYTES)
+#undef STRING_OR_BYTES_HANDLER_FUNCTIONS
+
+#define PRIMITIVE_HANDLER_FUNCTIONS(FieldType) \
+ template <typename Type> \
+ inline const typename MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::MapEntryAccessorType& \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::GetExternalReference(const TypeOnMemory& value) { \
+ return value; \
+ } \
+ template <typename Type> \
+ inline int \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::SpaceUsedInMapEntry( \
+ const TypeOnMemory& value) { \
+ return 0; \
+ } \
+ template <typename Type> \
+ inline int MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::SpaceUsedInMap(const TypeOnMemory& value) { \
+ return sizeof(Type); \
+ } \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Clear( \
+ TypeOnMemory* value, Arena* arena) { \
+ *value = 0; \
+ } \
+ template <typename Type> \
+ inline void \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::ClearMaybeByDefaultEnum(TypeOnMemory* value, \
+ Arena* arena, \
+ int default_enum_value) { \
+ *value = static_cast<TypeOnMemory>(default_enum_value); \
+ } \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Merge( \
+ const MapEntryAccessorType& from, TypeOnMemory* to, Arena* arena) { \
+ *to = from; \
+ } \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::DeleteNoArena(TypeOnMemory& x) {} \
+ template <typename Type> \
+ inline void MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::AssignDefaultValue(TypeOnMemory* value) {} \
+ template <typename Type> \
+ inline void \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::Initialize( \
+ TypeOnMemory* value, Arena* arena) { \
+ *value = 0; \
+ } \
+ template <typename Type> \
+ inline void \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::InitializeMaybeByDefaultEnum(TypeOnMemory* value, \
+ int default_enum_value, \
+ Arena* arena) { \
+ *value = static_cast<TypeOnMemory>(default_enum_value); \
+ } \
+ template <typename Type> \
+ inline typename MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::MapEntryAccessorType* \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, Type>::EnsureMutable( \
+ TypeOnMemory* value, Arena* arena) { \
+ return value; \
+ } \
+ template <typename Type> \
+ inline const typename MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::MapEntryAccessorType& \
+ MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::DefaultIfNotInitialized(const TypeOnMemory& value, \
+ const TypeOnMemory& \
+ default_value) { \
+ return value; \
+ } \
+ template <typename Type> \
+ inline bool MapTypeHandler<WireFormatLite::TYPE_##FieldType, \
+ Type>::IsInitialized(const TypeOnMemory& value) { \
+ return true; \
+ }
+PRIMITIVE_HANDLER_FUNCTIONS(INT64)
+PRIMITIVE_HANDLER_FUNCTIONS(UINT64)
+PRIMITIVE_HANDLER_FUNCTIONS(INT32)
+PRIMITIVE_HANDLER_FUNCTIONS(UINT32)
+PRIMITIVE_HANDLER_FUNCTIONS(SINT64)
+PRIMITIVE_HANDLER_FUNCTIONS(SINT32)
+PRIMITIVE_HANDLER_FUNCTIONS(ENUM)
+PRIMITIVE_HANDLER_FUNCTIONS(DOUBLE)
+PRIMITIVE_HANDLER_FUNCTIONS(FLOAT)
+PRIMITIVE_HANDLER_FUNCTIONS(FIXED64)
+PRIMITIVE_HANDLER_FUNCTIONS(FIXED32)
+PRIMITIVE_HANDLER_FUNCTIONS(SFIXED64)
+PRIMITIVE_HANDLER_FUNCTIONS(SFIXED32)
+PRIMITIVE_HANDLER_FUNCTIONS(BOOL)
+#undef PRIMITIVE_HANDLER_FUNCTIONS
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_TYPE_HANDLER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_unittest.proto b/third_party/protobuf/3.0.0/src/google/protobuf/map_unittest.proto
new file mode 100644
index 0000000000..c6154f040a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_unittest.proto
@@ -0,0 +1,129 @@
+// 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.
+
+syntax = "proto3";
+
+option cc_enable_arenas = true;
+
+import "google/protobuf/unittest.proto";
+import "google/protobuf/unittest_no_arena.proto";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In map_test_util.h we do "using namespace unittest = protobuf_unittest".
+package protobuf_unittest;
+
+// Tests maps.
+message TestMap {
+ map<int32 , int32 > map_int32_int32 = 1;
+ map<int64 , int64 > map_int64_int64 = 2;
+ map<uint32 , uint32 > map_uint32_uint32 = 3;
+ map<uint64 , uint64 > map_uint64_uint64 = 4;
+ map<sint32 , sint32 > map_sint32_sint32 = 5;
+ map<sint64 , sint64 > map_sint64_sint64 = 6;
+ map<fixed32 , fixed32 > map_fixed32_fixed32 = 7;
+ map<fixed64 , fixed64 > map_fixed64_fixed64 = 8;
+ map<sfixed32, sfixed32> map_sfixed32_sfixed32 = 9;
+ map<sfixed64, sfixed64> map_sfixed64_sfixed64 = 10;
+ map<int32 , float > map_int32_float = 11;
+ map<int32 , double > map_int32_double = 12;
+ map<bool , bool > map_bool_bool = 13;
+ map<string , string > map_string_string = 14;
+ map<int32 , bytes > map_int32_bytes = 15;
+ map<int32 , MapEnum > map_int32_enum = 16;
+ map<int32 , ForeignMessage> map_int32_foreign_message = 17;
+ map<string , ForeignMessage> map_string_foreign_message = 18;
+}
+
+message TestMapSubmessage {
+ TestMap test_map = 1;
+}
+
+message TestMessageMap {
+ map<int32, TestAllTypes> map_int32_message = 1;
+}
+
+// Two map fields share the same entry default instance.
+message TestSameTypeMap {
+ map<int32, int32> map1 = 1;
+ map<int32, int32> map2 = 2;
+}
+
+
+enum MapEnum {
+ MAP_ENUM_FOO = 0;
+ MAP_ENUM_BAR = 1;
+ MAP_ENUM_BAZ = 2;
+}
+
+// Test embedded message with required fields
+message TestRequiredMessageMap {
+ map<int32, TestRequired> map_field = 1;
+}
+
+message TestArenaMap {
+ map<int32 , int32 > map_int32_int32 = 1;
+ map<int64 , int64 > map_int64_int64 = 2;
+ map<uint32 , uint32 > map_uint32_uint32 = 3;
+ map<uint64 , uint64 > map_uint64_uint64 = 4;
+ map<sint32 , sint32 > map_sint32_sint32 = 5;
+ map<sint64 , sint64 > map_sint64_sint64 = 6;
+ map<fixed32 , fixed32 > map_fixed32_fixed32 = 7;
+ map<fixed64 , fixed64 > map_fixed64_fixed64 = 8;
+ map<sfixed32, sfixed32> map_sfixed32_sfixed32 = 9;
+ map<sfixed64, sfixed64> map_sfixed64_sfixed64 = 10;
+ map<int32 , float > map_int32_float = 11;
+ map<int32 , double > map_int32_double = 12;
+ map<bool , bool > map_bool_bool = 13;
+ map<string , string > map_string_string = 14;
+ map<int32 , bytes > map_int32_bytes = 15;
+ map<int32 , MapEnum > map_int32_enum = 16;
+ map<int32 , ForeignMessage> map_int32_foreign_message = 17;
+ map<int32, .protobuf_unittest_no_arena.ForeignMessage>
+ map_int32_foreign_message_no_arena = 18;
+}
+
+// Previously, message containing enum called Type cannot be used as value of
+// map field.
+message MessageContainingEnumCalledType {
+ enum Type {
+ TYPE_FOO = 0;
+ }
+ map<string, MessageContainingEnumCalledType> type = 1;
+}
+
+// Previously, message cannot contain map field called "entry".
+message MessageContainingMapCalledEntry {
+ map<int32, int32> entry = 1;
+}
+
+message TestRecursiveMapMessage {
+ map<string, TestRecursiveMapMessage> a = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/map_unittest_proto3.proto b/third_party/protobuf/3.0.0/src/google/protobuf/map_unittest_proto3.proto
new file mode 100644
index 0000000000..16be277304
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/map_unittest_proto3.proto
@@ -0,0 +1,120 @@
+// 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.
+
+// This file is mostly equivalent to map_unittest.proto, but imports
+// unittest_proto3.proto instead of unittest.proto, so that it only
+// uses proto3 messages. This makes it suitable for testing
+// implementations which only support proto3.
+// The TestRequiredMessageMap message has been removed as there are no
+// required fields in proto3.
+syntax = "proto3";
+
+option cc_enable_arenas = true;
+option csharp_namespace = "Google.Protobuf.TestProtos";
+
+import "google/protobuf/unittest_proto3.proto";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In map_test_util.h we do "using namespace unittest = protobuf_unittest".
+package protobuf_unittest;
+
+// Tests maps.
+message TestMap {
+ map<int32 , int32 > map_int32_int32 = 1;
+ map<int64 , int64 > map_int64_int64 = 2;
+ map<uint32 , uint32 > map_uint32_uint32 = 3;
+ map<uint64 , uint64 > map_uint64_uint64 = 4;
+ map<sint32 , sint32 > map_sint32_sint32 = 5;
+ map<sint64 , sint64 > map_sint64_sint64 = 6;
+ map<fixed32 , fixed32 > map_fixed32_fixed32 = 7;
+ map<fixed64 , fixed64 > map_fixed64_fixed64 = 8;
+ map<sfixed32, sfixed32> map_sfixed32_sfixed32 = 9;
+ map<sfixed64, sfixed64> map_sfixed64_sfixed64 = 10;
+ map<int32 , float > map_int32_float = 11;
+ map<int32 , double > map_int32_double = 12;
+ map<bool , bool > map_bool_bool = 13;
+ map<string , string > map_string_string = 14;
+ map<int32 , bytes > map_int32_bytes = 15;
+ map<int32 , MapEnum > map_int32_enum = 16;
+ map<int32 , ForeignMessage> map_int32_foreign_message = 17;
+}
+
+message TestMapSubmessage {
+ TestMap test_map = 1;
+}
+
+message TestMessageMap {
+ map<int32, TestAllTypes> map_int32_message = 1;
+}
+
+// Two map fields share the same entry default instance.
+message TestSameTypeMap {
+ map<int32, int32> map1 = 1;
+ map<int32, int32> map2 = 2;
+}
+
+enum MapEnum {
+ MAP_ENUM_FOO = 0;
+ MAP_ENUM_BAR = 1;
+ MAP_ENUM_BAZ = 2;
+}
+
+message TestArenaMap {
+ map<int32 , int32 > map_int32_int32 = 1;
+ map<int64 , int64 > map_int64_int64 = 2;
+ map<uint32 , uint32 > map_uint32_uint32 = 3;
+ map<uint64 , uint64 > map_uint64_uint64 = 4;
+ map<sint32 , sint32 > map_sint32_sint32 = 5;
+ map<sint64 , sint64 > map_sint64_sint64 = 6;
+ map<fixed32 , fixed32 > map_fixed32_fixed32 = 7;
+ map<fixed64 , fixed64 > map_fixed64_fixed64 = 8;
+ map<sfixed32, sfixed32> map_sfixed32_sfixed32 = 9;
+ map<sfixed64, sfixed64> map_sfixed64_sfixed64 = 10;
+ map<int32 , float > map_int32_float = 11;
+ map<int32 , double > map_int32_double = 12;
+ map<bool , bool > map_bool_bool = 13;
+ map<int32 , MapEnum > map_int32_enum = 14;
+ map<int32 , ForeignMessage> map_int32_foreign_message = 15;
+}
+
+// Previously, message containing enum called Type cannot be used as value of
+// map field.
+message MessageContainingEnumCalledType {
+ enum Type {
+ TYPE_FOO = 0;
+ }
+ map<int32, MessageContainingEnumCalledType> type = 1;
+}
+
+// Previously, message cannot contain map field called "entry".
+message MessageContainingMapCalledEntry {
+ map<int32, int32> entry = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/message.cc b/third_party/protobuf/3.0.0/src/google/protobuf/message.cc
new file mode 100644
index 0000000000..f18077dd20
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/message.cc
@@ -0,0 +1,515 @@
+// 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.
+
+#include <iostream>
+#include <stack>
+#include <google/protobuf/stubs/hash.h>
+
+#include <google/protobuf/message.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/mutex.h>
+#include <google/protobuf/stubs/once.h>
+#include <google/protobuf/reflection_internal.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/map_field.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/reflection_ops.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/singleton.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+
+using internal::WireFormat;
+using internal::ReflectionOps;
+
+void Message::MergeFrom(const Message& from) {
+ const Descriptor* descriptor = GetDescriptor();
+ GOOGLE_CHECK_EQ(from.GetDescriptor(), descriptor)
+ << ": Tried to merge from a message with a different type. "
+ "to: " << descriptor->full_name() << ", "
+ "from: " << from.GetDescriptor()->full_name();
+ ReflectionOps::Merge(from, this);
+}
+
+void Message::CheckTypeAndMergeFrom(const MessageLite& other) {
+ MergeFrom(*down_cast<const Message*>(&other));
+}
+
+void Message::CopyFrom(const Message& from) {
+ const Descriptor* descriptor = GetDescriptor();
+ GOOGLE_CHECK_EQ(from.GetDescriptor(), descriptor)
+ << ": Tried to copy from a message with a different type. "
+ "to: " << descriptor->full_name() << ", "
+ "from: " << from.GetDescriptor()->full_name();
+ ReflectionOps::Copy(from, this);
+}
+
+string Message::GetTypeName() const {
+ return GetDescriptor()->full_name();
+}
+
+void Message::Clear() {
+ ReflectionOps::Clear(this);
+}
+
+bool Message::IsInitialized() const {
+ return ReflectionOps::IsInitialized(*this);
+}
+
+void Message::FindInitializationErrors(vector<string>* errors) const {
+ return ReflectionOps::FindInitializationErrors(*this, "", errors);
+}
+
+string Message::InitializationErrorString() const {
+ vector<string> errors;
+ FindInitializationErrors(&errors);
+ return Join(errors, ", ");
+}
+
+void Message::CheckInitialized() const {
+ GOOGLE_CHECK(IsInitialized())
+ << "Message of type \"" << GetDescriptor()->full_name()
+ << "\" is missing required fields: " << InitializationErrorString();
+}
+
+void Message::DiscardUnknownFields() {
+ return ReflectionOps::DiscardUnknownFields(this);
+}
+
+bool Message::MergePartialFromCodedStream(io::CodedInputStream* input) {
+ return WireFormat::ParseAndMergePartial(input, this);
+}
+
+bool Message::ParseFromFileDescriptor(int file_descriptor) {
+ io::FileInputStream input(file_descriptor);
+ return ParseFromZeroCopyStream(&input) && input.GetErrno() == 0;
+}
+
+bool Message::ParsePartialFromFileDescriptor(int file_descriptor) {
+ io::FileInputStream input(file_descriptor);
+ return ParsePartialFromZeroCopyStream(&input) && input.GetErrno() == 0;
+}
+
+bool Message::ParseFromIstream(istream* input) {
+ io::IstreamInputStream zero_copy_input(input);
+ return ParseFromZeroCopyStream(&zero_copy_input) && input->eof();
+}
+
+bool Message::ParsePartialFromIstream(istream* input) {
+ io::IstreamInputStream zero_copy_input(input);
+ return ParsePartialFromZeroCopyStream(&zero_copy_input) && input->eof();
+}
+
+
+void Message::SerializeWithCachedSizes(
+ io::CodedOutputStream* output) const {
+ WireFormat::SerializeWithCachedSizes(*this, GetCachedSize(), output);
+}
+
+int Message::ByteSize() const {
+ int size = WireFormat::ByteSize(*this);
+ SetCachedSize(size);
+ return size;
+}
+
+void Message::SetCachedSize(int /* size */) const {
+ GOOGLE_LOG(FATAL) << "Message class \"" << GetDescriptor()->full_name()
+ << "\" implements neither SetCachedSize() nor ByteSize(). "
+ "Must implement one or the other.";
+}
+
+int Message::SpaceUsed() const {
+ return GetReflection()->SpaceUsed(*this);
+}
+
+bool Message::SerializeToFileDescriptor(int file_descriptor) const {
+ io::FileOutputStream output(file_descriptor);
+ return SerializeToZeroCopyStream(&output);
+}
+
+bool Message::SerializePartialToFileDescriptor(int file_descriptor) const {
+ io::FileOutputStream output(file_descriptor);
+ return SerializePartialToZeroCopyStream(&output);
+}
+
+bool Message::SerializeToOstream(ostream* output) const {
+ {
+ io::OstreamOutputStream zero_copy_output(output);
+ if (!SerializeToZeroCopyStream(&zero_copy_output)) return false;
+ }
+ return output->good();
+}
+
+bool Message::SerializePartialToOstream(ostream* output) const {
+ io::OstreamOutputStream zero_copy_output(output);
+ return SerializePartialToZeroCopyStream(&zero_copy_output);
+}
+
+
+// =============================================================================
+// Reflection and associated Template Specializations
+
+Reflection::~Reflection() {}
+
+#define HANDLE_TYPE(TYPE, CPPTYPE, CTYPE) \
+template<> \
+const RepeatedField<TYPE>& Reflection::GetRepeatedField<TYPE>( \
+ const Message& message, const FieldDescriptor* field) const { \
+ return *static_cast<RepeatedField<TYPE>* >( \
+ MutableRawRepeatedField(const_cast<Message*>(&message), \
+ field, CPPTYPE, CTYPE, NULL)); \
+} \
+ \
+template<> \
+RepeatedField<TYPE>* Reflection::MutableRepeatedField<TYPE>( \
+ Message* message, const FieldDescriptor* field) const { \
+ return static_cast<RepeatedField<TYPE>* >( \
+ MutableRawRepeatedField(message, field, CPPTYPE, CTYPE, NULL)); \
+}
+
+HANDLE_TYPE(int32, FieldDescriptor::CPPTYPE_INT32, -1);
+HANDLE_TYPE(int64, FieldDescriptor::CPPTYPE_INT64, -1);
+HANDLE_TYPE(uint32, FieldDescriptor::CPPTYPE_UINT32, -1);
+HANDLE_TYPE(uint64, FieldDescriptor::CPPTYPE_UINT64, -1);
+HANDLE_TYPE(float, FieldDescriptor::CPPTYPE_FLOAT, -1);
+HANDLE_TYPE(double, FieldDescriptor::CPPTYPE_DOUBLE, -1);
+HANDLE_TYPE(bool, FieldDescriptor::CPPTYPE_BOOL, -1);
+
+
+#undef HANDLE_TYPE
+
+void* Reflection::MutableRawRepeatedString(
+ Message* message, const FieldDescriptor* field, bool is_string) const {
+ return MutableRawRepeatedField(message, field,
+ FieldDescriptor::CPPTYPE_STRING, FieldOptions::STRING, NULL);
+}
+
+
+// Default EnumValue API implementations. Real reflection implementations should
+// override these. However, there are several legacy implementations that do
+// not, and cannot easily be changed at the same time as the Reflection API, so
+// we provide these for now.
+// TODO: Remove these once all Reflection implementations are updated.
+int Reflection::GetEnumValue(const Message& message,
+ const FieldDescriptor* field) const {
+ GOOGLE_LOG(FATAL) << "Unimplemented EnumValue API.";
+ return 0;
+}
+void Reflection::SetEnumValue(Message* message,
+ const FieldDescriptor* field,
+ int value) const {
+ GOOGLE_LOG(FATAL) << "Unimplemented EnumValue API.";
+}
+int Reflection::GetRepeatedEnumValue(
+ const Message& message,
+ const FieldDescriptor* field, int index) const {
+ GOOGLE_LOG(FATAL) << "Unimplemented EnumValue API.";
+ return 0;
+}
+void Reflection::SetRepeatedEnumValue(Message* message,
+ const FieldDescriptor* field, int index,
+ int value) const {
+ GOOGLE_LOG(FATAL) << "Unimplemented EnumValue API.";
+}
+void Reflection::AddEnumValue(Message* message,
+ const FieldDescriptor* field,
+ int value) const {
+ GOOGLE_LOG(FATAL) << "Unimplemented EnumValue API.";
+}
+
+MapIterator Reflection::MapBegin(
+ Message* message,
+ const FieldDescriptor* field) const {
+ GOOGLE_LOG(FATAL) << "Unimplemented Map Reflection API.";
+ MapIterator iter(message, field);
+ return iter;
+}
+
+MapIterator Reflection::MapEnd(
+ Message* message,
+ const FieldDescriptor* field) const {
+ GOOGLE_LOG(FATAL) << "Unimplemented Map Reflection API.";
+ MapIterator iter(message, field);
+ return iter;
+}
+
+// =============================================================================
+// MessageFactory
+
+MessageFactory::~MessageFactory() {}
+
+namespace {
+
+class GeneratedMessageFactory : public MessageFactory {
+ public:
+ GeneratedMessageFactory();
+ ~GeneratedMessageFactory();
+
+ static GeneratedMessageFactory* singleton();
+
+ typedef void RegistrationFunc(const string&);
+ void RegisterFile(const char* file, RegistrationFunc* registration_func);
+ void RegisterType(const Descriptor* descriptor, const Message* prototype);
+
+ // implements MessageFactory ---------------------------------------
+ const Message* GetPrototype(const Descriptor* type);
+
+ private:
+ // Only written at static init time, so does not require locking.
+ hash_map<const char*, RegistrationFunc*,
+ hash<const char*>, streq> file_map_;
+
+ // Initialized lazily, so requires locking.
+ Mutex mutex_;
+ hash_map<const Descriptor*, const Message*> type_map_;
+};
+
+GeneratedMessageFactory* generated_message_factory_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(generated_message_factory_once_init_);
+
+void ShutdownGeneratedMessageFactory() {
+ delete generated_message_factory_;
+}
+
+void InitGeneratedMessageFactory() {
+ generated_message_factory_ = new GeneratedMessageFactory;
+ internal::OnShutdown(&ShutdownGeneratedMessageFactory);
+}
+
+GeneratedMessageFactory::GeneratedMessageFactory() {}
+GeneratedMessageFactory::~GeneratedMessageFactory() {}
+
+GeneratedMessageFactory* GeneratedMessageFactory::singleton() {
+ ::google::protobuf::GoogleOnceInit(&generated_message_factory_once_init_,
+ &InitGeneratedMessageFactory);
+ return generated_message_factory_;
+}
+
+void GeneratedMessageFactory::RegisterFile(
+ const char* file, RegistrationFunc* registration_func) {
+ if (!InsertIfNotPresent(&file_map_, file, registration_func)) {
+ GOOGLE_LOG(FATAL) << "File is already registered: " << file;
+ }
+}
+
+void GeneratedMessageFactory::RegisterType(const Descriptor* descriptor,
+ const Message* prototype) {
+ GOOGLE_DCHECK_EQ(descriptor->file()->pool(), DescriptorPool::generated_pool())
+ << "Tried to register a non-generated type with the generated "
+ "type registry.";
+
+ // This should only be called as a result of calling a file registration
+ // function during GetPrototype(), in which case we already have locked
+ // the mutex.
+ mutex_.AssertHeld();
+ if (!InsertIfNotPresent(&type_map_, descriptor, prototype)) {
+ GOOGLE_LOG(DFATAL) << "Type is already registered: " << descriptor->full_name();
+ }
+}
+
+
+const Message* GeneratedMessageFactory::GetPrototype(const Descriptor* type) {
+ {
+ ReaderMutexLock lock(&mutex_);
+ const Message* result = FindPtrOrNull(type_map_, type);
+ if (result != NULL) return result;
+ }
+
+ // If the type is not in the generated pool, then we can't possibly handle
+ // it.
+ if (type->file()->pool() != DescriptorPool::generated_pool()) return NULL;
+
+ // Apparently the file hasn't been registered yet. Let's do that now.
+ RegistrationFunc* registration_func =
+ FindPtrOrNull(file_map_, type->file()->name().c_str());
+ if (registration_func == NULL) {
+ GOOGLE_LOG(DFATAL) << "File appears to be in generated pool but wasn't "
+ "registered: " << type->file()->name();
+ return NULL;
+ }
+
+ WriterMutexLock lock(&mutex_);
+
+ // Check if another thread preempted us.
+ const Message* result = FindPtrOrNull(type_map_, type);
+ if (result == NULL) {
+ // Nope. OK, register everything.
+ registration_func(type->file()->name());
+ // Should be here now.
+ result = FindPtrOrNull(type_map_, type);
+ }
+
+ if (result == NULL) {
+ GOOGLE_LOG(DFATAL) << "Type appears to be in generated pool but wasn't "
+ << "registered: " << type->full_name();
+ }
+
+ return result;
+}
+
+} // namespace
+
+MessageFactory* MessageFactory::generated_factory() {
+ return GeneratedMessageFactory::singleton();
+}
+
+void MessageFactory::InternalRegisterGeneratedFile(
+ const char* filename, void (*register_messages)(const string&)) {
+ GeneratedMessageFactory::singleton()->RegisterFile(filename,
+ register_messages);
+}
+
+void MessageFactory::InternalRegisterGeneratedMessage(
+ const Descriptor* descriptor, const Message* prototype) {
+ GeneratedMessageFactory::singleton()->RegisterType(descriptor, prototype);
+}
+
+
+MessageFactory* Reflection::GetMessageFactory() const {
+ GOOGLE_LOG(FATAL) << "Not implemented.";
+ return NULL;
+}
+
+void* Reflection::RepeatedFieldData(
+ Message* message, const FieldDescriptor* field,
+ FieldDescriptor::CppType cpp_type,
+ const Descriptor* message_type) const {
+ GOOGLE_LOG(FATAL) << "Not implemented.";
+ return NULL;
+}
+
+namespace internal {
+RepeatedFieldAccessor::~RepeatedFieldAccessor() {
+}
+} // namespace internal
+
+const internal::RepeatedFieldAccessor* Reflection::RepeatedFieldAccessor(
+ const FieldDescriptor* field) const {
+ GOOGLE_CHECK(field->is_repeated());
+ switch (field->cpp_type()) {
+#define HANDLE_PRIMITIVE_TYPE(TYPE, type) \
+ case FieldDescriptor::CPPTYPE_ ## TYPE: \
+ return internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<type> >::get();
+ HANDLE_PRIMITIVE_TYPE(INT32, int32)
+ HANDLE_PRIMITIVE_TYPE(UINT32, uint32)
+ HANDLE_PRIMITIVE_TYPE(INT64, int64)
+ HANDLE_PRIMITIVE_TYPE(UINT64, uint64)
+ HANDLE_PRIMITIVE_TYPE(FLOAT, float)
+ HANDLE_PRIMITIVE_TYPE(DOUBLE, double)
+ HANDLE_PRIMITIVE_TYPE(BOOL, bool)
+ HANDLE_PRIMITIVE_TYPE(ENUM, int32)
+#undef HANDLE_PRIMITIVE_TYPE
+ case FieldDescriptor::CPPTYPE_STRING:
+ switch (field->options().ctype()) {
+ default:
+ case FieldOptions::STRING:
+ return internal::Singleton<internal::RepeatedPtrFieldStringAccessor>::get();
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ if (field->is_map()) {
+ return internal::Singleton<internal::MapFieldAccessor>::get();
+ } else {
+ return internal::Singleton<internal::RepeatedPtrFieldMessageAccessor>::get();
+ }
+ }
+ GOOGLE_LOG(FATAL) << "Should not reach here.";
+ return NULL;
+}
+
+namespace internal {
+namespace {
+void ShutdownRepeatedFieldAccessor() {
+ internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<int32> >::ShutDown();
+ internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<uint32> >::ShutDown();
+ internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<int64> >::ShutDown();
+ internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<uint64> >::ShutDown();
+ internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<float> >::ShutDown();
+ internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<double> >::ShutDown();
+ internal::Singleton<internal::RepeatedFieldPrimitiveAccessor<bool> >::ShutDown();
+ internal::Singleton<internal::RepeatedPtrFieldStringAccessor>::ShutDown();
+ internal::Singleton<internal::RepeatedPtrFieldMessageAccessor>::ShutDown();
+ internal::Singleton<internal::MapFieldAccessor>::ShutDown();
+}
+
+struct ShutdownRepeatedFieldRegister {
+ ShutdownRepeatedFieldRegister() {
+ OnShutdown(&ShutdownRepeatedFieldAccessor);
+ }
+} shutdown_;
+
+} // namespace
+} // namespace internal
+
+namespace internal {
+template<>
+#if defined(_MSC_VER) && (_MSC_VER >= 1900)
+// Note: force noinline to workaround MSVC 2015 compiler bug, issue #240
+GOOGLE_ATTRIBUTE_NOINLINE
+#endif
+Message* GenericTypeHandler<Message>::NewFromPrototype(
+ const Message* prototype, google::protobuf::Arena* arena) {
+ return prototype->New(arena);
+}
+template<>
+#if defined(_MSC_VER) && (_MSC_VER >= 1900)
+// Note: force noinline to workaround MSVC 2015 compiler bug, issue #240
+GOOGLE_ATTRIBUTE_NOINLINE
+#endif
+google::protobuf::Arena* GenericTypeHandler<Message>::GetArena(
+ Message* value) {
+ return value->GetArena();
+}
+template<>
+#if defined(_MSC_VER) && (_MSC_VER >= 1900)
+// Note: force noinline to workaround MSVC 2015 compiler bug, issue #240
+GOOGLE_ATTRIBUTE_NOINLINE
+#endif
+void* GenericTypeHandler<Message>::GetMaybeArenaPointer(
+ Message* value) {
+ return value->GetMaybeArenaPointer();
+}
+} // namespace internal
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/message.h b/third_party/protobuf/3.0.0/src/google/protobuf/message.h
new file mode 100644
index 0000000000..9705e97e43
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/message.h
@@ -0,0 +1,1150 @@
+// 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.
+//
+// Defines Message, the abstract interface implemented by non-lite
+// protocol message objects. Although it's possible to implement this
+// interface manually, most users will use the protocol compiler to
+// generate implementations.
+//
+// Example usage:
+//
+// Say you have a message defined as:
+//
+// message Foo {
+// optional string text = 1;
+// repeated int32 numbers = 2;
+// }
+//
+// Then, if you used the protocol compiler to generate a class from the above
+// definition, you could use it like so:
+//
+// string data; // Will store a serialized version of the message.
+//
+// {
+// // Create a message and serialize it.
+// Foo foo;
+// foo.set_text("Hello World!");
+// foo.add_numbers(1);
+// foo.add_numbers(5);
+// foo.add_numbers(42);
+//
+// foo.SerializeToString(&data);
+// }
+//
+// {
+// // Parse the serialized message and check that it contains the
+// // correct data.
+// Foo foo;
+// foo.ParseFromString(data);
+//
+// assert(foo.text() == "Hello World!");
+// assert(foo.numbers_size() == 3);
+// assert(foo.numbers(0) == 1);
+// assert(foo.numbers(1) == 5);
+// assert(foo.numbers(2) == 42);
+// }
+//
+// {
+// // Same as the last block, but do it dynamically via the Message
+// // reflection interface.
+// Message* foo = new Foo;
+// const Descriptor* descriptor = foo->GetDescriptor();
+//
+// // Get the descriptors for the fields we're interested in and verify
+// // their types.
+// const FieldDescriptor* text_field = descriptor->FindFieldByName("text");
+// assert(text_field != NULL);
+// assert(text_field->type() == FieldDescriptor::TYPE_STRING);
+// assert(text_field->label() == FieldDescriptor::LABEL_OPTIONAL);
+// const FieldDescriptor* numbers_field = descriptor->
+// FindFieldByName("numbers");
+// assert(numbers_field != NULL);
+// assert(numbers_field->type() == FieldDescriptor::TYPE_INT32);
+// assert(numbers_field->label() == FieldDescriptor::LABEL_REPEATED);
+//
+// // Parse the message.
+// foo->ParseFromString(data);
+//
+// // Use the reflection interface to examine the contents.
+// const Reflection* reflection = foo->GetReflection();
+// assert(reflection->GetString(*foo, text_field) == "Hello World!");
+// assert(reflection->FieldSize(*foo, numbers_field) == 3);
+// assert(reflection->GetRepeatedInt32(*foo, numbers_field, 0) == 1);
+// assert(reflection->GetRepeatedInt32(*foo, numbers_field, 1) == 5);
+// assert(reflection->GetRepeatedInt32(*foo, numbers_field, 2) == 42);
+//
+// delete foo;
+// }
+
+#ifndef GOOGLE_PROTOBUF_MESSAGE_H__
+#define GOOGLE_PROTOBUF_MESSAGE_H__
+
+#include <iosfwd>
+#include <string>
+#include <google/protobuf/stubs/type_traits.h>
+#include <vector>
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/message_lite.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+
+
+#define GOOGLE_PROTOBUF_HAS_ONEOF
+#define GOOGLE_PROTOBUF_HAS_ARENAS
+
+namespace google {
+namespace protobuf {
+
+// Defined in this file.
+class Message;
+class Reflection;
+class MessageFactory;
+
+// Defined in other files.
+class MapKey;
+class MapValueRef;
+class MapIterator;
+class MapReflectionTester;
+
+namespace internal {
+class MapFieldBase;
+}
+class UnknownFieldSet; // unknown_field_set.h
+namespace io {
+class ZeroCopyInputStream; // zero_copy_stream.h
+class ZeroCopyOutputStream; // zero_copy_stream.h
+class CodedInputStream; // coded_stream.h
+class CodedOutputStream; // coded_stream.h
+}
+namespace python {
+class MapReflectionFriend; // scalar_map_container.h
+}
+
+
+template<typename T>
+class RepeatedField; // repeated_field.h
+
+template<typename T>
+class RepeatedPtrField; // repeated_field.h
+
+// A container to hold message metadata.
+struct Metadata {
+ const Descriptor* descriptor;
+ const Reflection* reflection;
+};
+
+// Abstract interface for protocol messages.
+//
+// See also MessageLite, which contains most every-day operations. Message
+// adds descriptors and reflection on top of that.
+//
+// The methods of this class that are virtual but not pure-virtual have
+// default implementations based on reflection. Message classes which are
+// optimized for speed will want to override these with faster implementations,
+// but classes optimized for code size may be happy with keeping them. See
+// the optimize_for option in descriptor.proto.
+class LIBPROTOBUF_EXPORT Message : public MessageLite {
+ public:
+ inline Message() {}
+ virtual ~Message() {}
+
+ // Basic Operations ------------------------------------------------
+
+ // Construct a new instance of the same type. Ownership is passed to the
+ // caller. (This is also defined in MessageLite, but is defined again here
+ // for return-type covariance.)
+ virtual Message* New() const = 0;
+
+ // Construct a new instance on the arena. Ownership is passed to the caller
+ // if arena is a NULL. Default implementation allows for API compatibility
+ // during the Arena transition.
+ virtual Message* New(::google::protobuf::Arena* arena) const {
+ Message* message = New();
+ if (arena != NULL) {
+ arena->Own(message);
+ }
+ return message;
+ }
+
+ // Make this message into a copy of the given message. The given message
+ // must have the same descriptor, but need not necessarily be the same class.
+ // By default this is just implemented as "Clear(); MergeFrom(from);".
+ virtual void CopyFrom(const Message& from);
+
+ // Merge the fields from the given message into this message. Singular
+ // fields will be overwritten, if specified in from, except for embedded
+ // messages which will be merged. Repeated fields will be concatenated.
+ // The given message must be of the same type as this message (i.e. the
+ // exact same class).
+ virtual void MergeFrom(const Message& from);
+
+ // Verifies that IsInitialized() returns true. GOOGLE_CHECK-fails otherwise, with
+ // a nice error message.
+ void CheckInitialized() const;
+
+ // Slowly build a list of all required fields that are not set.
+ // This is much, much slower than IsInitialized() as it is implemented
+ // purely via reflection. Generally, you should not call this unless you
+ // have already determined that an error exists by calling IsInitialized().
+ void FindInitializationErrors(std::vector<string>* errors) const;
+
+ // Like FindInitializationErrors, but joins all the strings, delimited by
+ // commas, and returns them.
+ string InitializationErrorString() const;
+
+ // Clears all unknown fields from this message and all embedded messages.
+ // Normally, if unknown tag numbers are encountered when parsing a message,
+ // the tag and value are stored in the message's UnknownFieldSet and
+ // then written back out when the message is serialized. This allows servers
+ // which simply route messages to other servers to pass through messages
+ // that have new field definitions which they don't yet know about. However,
+ // this behavior can have security implications. To avoid it, call this
+ // method after parsing.
+ //
+ // See Reflection::GetUnknownFields() for more on unknown fields.
+ virtual void DiscardUnknownFields();
+
+ // Computes (an estimate of) the total number of bytes currently used for
+ // storing the message in memory. The default implementation calls the
+ // Reflection object's SpaceUsed() method.
+ //
+ // SpaceUsed() is noticeably slower than ByteSize(), as it is implemented
+ // using reflection (rather than the generated code implementation for
+ // ByteSize()). Like ByteSize(), its CPU time is linear in the number of
+ // fields defined for the proto.
+ virtual int SpaceUsed() const;
+
+ // Debugging & Testing----------------------------------------------
+
+ // Generates a human readable form of this message, useful for debugging
+ // and other purposes.
+ string DebugString() const;
+ // Like DebugString(), but with less whitespace.
+ string ShortDebugString() const;
+ // Like DebugString(), but do not escape UTF-8 byte sequences.
+ string Utf8DebugString() const;
+ // Convenience function useful in GDB. Prints DebugString() to stdout.
+ void PrintDebugString() const;
+
+ // Heavy I/O -------------------------------------------------------
+ // Additional parsing and serialization methods not implemented by
+ // MessageLite because they are not supported by the lite library.
+
+ // Parse a protocol buffer from a file descriptor. If successful, the entire
+ // input will be consumed.
+ bool ParseFromFileDescriptor(int file_descriptor);
+ // Like ParseFromFileDescriptor(), but accepts messages that are missing
+ // required fields.
+ bool ParsePartialFromFileDescriptor(int file_descriptor);
+ // Parse a protocol buffer from a C++ istream. If successful, the entire
+ // input will be consumed.
+ bool ParseFromIstream(istream* input);
+ // Like ParseFromIstream(), but accepts messages that are missing
+ // required fields.
+ bool ParsePartialFromIstream(istream* input);
+
+ // Serialize the message and write it to the given file descriptor. All
+ // required fields must be set.
+ bool SerializeToFileDescriptor(int file_descriptor) const;
+ // Like SerializeToFileDescriptor(), but allows missing required fields.
+ bool SerializePartialToFileDescriptor(int file_descriptor) const;
+ // Serialize the message and write it to the given C++ ostream. All
+ // required fields must be set.
+ bool SerializeToOstream(ostream* output) const;
+ // Like SerializeToOstream(), but allows missing required fields.
+ bool SerializePartialToOstream(ostream* output) const;
+
+
+ // Reflection-based methods ----------------------------------------
+ // These methods are pure-virtual in MessageLite, but Message provides
+ // reflection-based default implementations.
+
+ virtual string GetTypeName() const;
+ virtual void Clear();
+ virtual bool IsInitialized() const;
+ virtual void CheckTypeAndMergeFrom(const MessageLite& other);
+ virtual bool MergePartialFromCodedStream(io::CodedInputStream* input);
+ virtual int ByteSize() const;
+ virtual void SerializeWithCachedSizes(io::CodedOutputStream* output) const;
+
+ private:
+ // This is called only by the default implementation of ByteSize(), to
+ // update the cached size. If you override ByteSize(), you do not need
+ // to override this. If you do not override ByteSize(), you MUST override
+ // this; the default implementation will crash.
+ //
+ // The method is private because subclasses should never call it; only
+ // override it. Yes, C++ lets you do that. Crazy, huh?
+ virtual void SetCachedSize(int size) const;
+
+ public:
+
+ // Introspection ---------------------------------------------------
+
+ // Typedef for backwards-compatibility.
+ typedef google::protobuf::Reflection Reflection;
+
+ // Get a Descriptor for this message's type. This describes what
+ // fields the message contains, the types of those fields, etc.
+ const Descriptor* GetDescriptor() const { return GetMetadata().descriptor; }
+
+ // Get the Reflection interface for this Message, which can be used to
+ // read and modify the fields of the Message dynamically (in other words,
+ // without knowing the message type at compile time). This object remains
+ // property of the Message.
+ //
+ // This method remains virtual in case a subclass does not implement
+ // reflection and wants to override the default behavior.
+ virtual const Reflection* GetReflection() const {
+ return GetMetadata().reflection;
+ }
+
+ protected:
+ // Get a struct containing the metadata for the Message. Most subclasses only
+ // need to implement this method, rather than the GetDescriptor() and
+ // GetReflection() wrappers.
+ virtual Metadata GetMetadata() const = 0;
+
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Message);
+};
+
+namespace internal {
+// Forward-declare interfaces used to implement RepeatedFieldRef.
+// These are protobuf internals that users shouldn't care about.
+class RepeatedFieldAccessor;
+} // namespace internal
+
+// Forward-declare RepeatedFieldRef templates. The second type parameter is
+// used for SFINAE tricks. Users should ignore it.
+template<typename T, typename Enable = void>
+class RepeatedFieldRef;
+
+template<typename T, typename Enable = void>
+class MutableRepeatedFieldRef;
+
+// This interface contains methods that can be used to dynamically access
+// and modify the fields of a protocol message. Their semantics are
+// similar to the accessors the protocol compiler generates.
+//
+// To get the Reflection for a given Message, call Message::GetReflection().
+//
+// This interface is separate from Message only for efficiency reasons;
+// the vast majority of implementations of Message will share the same
+// implementation of Reflection (GeneratedMessageReflection,
+// defined in generated_message.h), and all Messages of a particular class
+// should share the same Reflection object (though you should not rely on
+// the latter fact).
+//
+// There are several ways that these methods can be used incorrectly. For
+// example, any of the following conditions will lead to undefined
+// results (probably assertion failures):
+// - The FieldDescriptor is not a field of this message type.
+// - The method called is not appropriate for the field's type. For
+// each field type in FieldDescriptor::TYPE_*, there is only one
+// Get*() method, one Set*() method, and one Add*() method that is
+// valid for that type. It should be obvious which (except maybe
+// for TYPE_BYTES, which are represented using strings in C++).
+// - A Get*() or Set*() method for singular fields is called on a repeated
+// field.
+// - GetRepeated*(), SetRepeated*(), or Add*() is called on a non-repeated
+// field.
+// - The Message object passed to any method is not of the right type for
+// this Reflection object (i.e. message.GetReflection() != reflection).
+//
+// You might wonder why there is not any abstract representation for a field
+// of arbitrary type. E.g., why isn't there just a "GetField()" method that
+// returns "const Field&", where "Field" is some class with accessors like
+// "GetInt32Value()". The problem is that someone would have to deal with
+// allocating these Field objects. For generated message classes, having to
+// allocate space for an additional object to wrap every field would at least
+// double the message's memory footprint, probably worse. Allocating the
+// objects on-demand, on the other hand, would be expensive and prone to
+// memory leaks. So, instead we ended up with this flat interface.
+//
+// TODO(kenton): Create a utility class which callers can use to read and
+// write fields from a Reflection without paying attention to the type.
+class LIBPROTOBUF_EXPORT Reflection {
+ public:
+ inline Reflection() {}
+ virtual ~Reflection();
+
+ // Get the UnknownFieldSet for the message. This contains fields which
+ // were seen when the Message was parsed but were not recognized according
+ // to the Message's definition. For proto3 protos, this method will always
+ // return an empty UnknownFieldSet.
+ virtual const UnknownFieldSet& GetUnknownFields(
+ const Message& message) const = 0;
+ // Get a mutable pointer to the UnknownFieldSet for the message. This
+ // contains fields which were seen when the Message was parsed but were not
+ // recognized according to the Message's definition. For proto3 protos, this
+ // method will return a valid mutable UnknownFieldSet pointer but modifying
+ // it won't affect the serialized bytes of the message.
+ virtual UnknownFieldSet* MutableUnknownFields(Message* message) const = 0;
+
+ // Estimate the amount of memory used by the message object.
+ virtual int SpaceUsed(const Message& message) const = 0;
+
+ // Check if the given non-repeated field is set.
+ virtual bool HasField(const Message& message,
+ const FieldDescriptor* field) const = 0;
+
+ // Get the number of elements of a repeated field.
+ virtual int FieldSize(const Message& message,
+ const FieldDescriptor* field) const = 0;
+
+ // Clear the value of a field, so that HasField() returns false or
+ // FieldSize() returns zero.
+ virtual void ClearField(Message* message,
+ const FieldDescriptor* field) const = 0;
+
+ // Check if the oneof is set. Returns true if any field in oneof
+ // is set, false otherwise.
+ // TODO(jieluo) - make it pure virtual after updating all
+ // the subclasses.
+ virtual bool HasOneof(const Message& /*message*/,
+ const OneofDescriptor* /*oneof_descriptor*/) const {
+ return false;
+ }
+
+ virtual void ClearOneof(Message* /*message*/,
+ const OneofDescriptor* /*oneof_descriptor*/) const {}
+
+ // Returns the field descriptor if the oneof is set. NULL otherwise.
+ // TODO(jieluo) - make it pure virtual.
+ virtual const FieldDescriptor* GetOneofFieldDescriptor(
+ const Message& /*message*/,
+ const OneofDescriptor* /*oneof_descriptor*/) const {
+ return NULL;
+ }
+
+ // Removes the last element of a repeated field.
+ // We don't provide a way to remove any element other than the last
+ // because it invites inefficient use, such as O(n^2) filtering loops
+ // that should have been O(n). If you want to remove an element other
+ // than the last, the best way to do it is to re-arrange the elements
+ // (using Swap()) so that the one you want removed is at the end, then
+ // call RemoveLast().
+ virtual void RemoveLast(Message* message,
+ const FieldDescriptor* field) const = 0;
+ // Removes the last element of a repeated message field, and returns the
+ // pointer to the caller. Caller takes ownership of the returned pointer.
+ virtual Message* ReleaseLast(Message* message,
+ const FieldDescriptor* field) const = 0;
+
+ // Swap the complete contents of two messages.
+ virtual void Swap(Message* message1, Message* message2) const = 0;
+
+ // Swap fields listed in fields vector of two messages.
+ virtual void SwapFields(Message* message1,
+ Message* message2,
+ const std::vector<const FieldDescriptor*>& fields)
+ const = 0;
+
+ // Swap two elements of a repeated field.
+ virtual void SwapElements(Message* message,
+ const FieldDescriptor* field,
+ int index1,
+ int index2) const = 0;
+
+ // List all fields of the message which are currently set. This includes
+ // extensions. Singular fields will only be listed if HasField(field) would
+ // return true and repeated fields will only be listed if FieldSize(field)
+ // would return non-zero. Fields (both normal fields and extension fields)
+ // will be listed ordered by field number.
+ virtual void ListFields(
+ const Message& message,
+ std::vector<const FieldDescriptor*>* output) const = 0;
+
+ // Singular field getters ------------------------------------------
+ // These get the value of a non-repeated field. They return the default
+ // value for fields that aren't set.
+
+ virtual int32 GetInt32 (const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual int64 GetInt64 (const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual uint32 GetUInt32(const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual uint64 GetUInt64(const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual float GetFloat (const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual double GetDouble(const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual bool GetBool (const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual string GetString(const Message& message,
+ const FieldDescriptor* field) const = 0;
+ virtual const EnumValueDescriptor* GetEnum(
+ const Message& message, const FieldDescriptor* field) const = 0;
+
+ // GetEnumValue() returns an enum field's value as an integer rather than
+ // an EnumValueDescriptor*. If the integer value does not correspond to a
+ // known value descriptor, a new value descriptor is created. (Such a value
+ // will only be present when the new unknown-enum-value semantics are enabled
+ // for a message.)
+ virtual int GetEnumValue(
+ const Message& message, const FieldDescriptor* field) const;
+
+ // See MutableMessage() for the meaning of the "factory" parameter.
+ virtual const Message& GetMessage(const Message& message,
+ const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const = 0;
+
+ // Get a string value without copying, if possible.
+ //
+ // GetString() necessarily returns a copy of the string. This can be
+ // inefficient when the string is already stored in a string object in the
+ // underlying message. GetStringReference() will return a reference to the
+ // underlying string in this case. Otherwise, it will copy the string into
+ // *scratch and return that.
+ //
+ // Note: It is perfectly reasonable and useful to write code like:
+ // str = reflection->GetStringReference(field, &str);
+ // This line would ensure that only one copy of the string is made
+ // regardless of the field's underlying representation. When initializing
+ // a newly-constructed string, though, it's just as fast and more readable
+ // to use code like:
+ // string str = reflection->GetString(message, field);
+ virtual const string& GetStringReference(const Message& message,
+ const FieldDescriptor* field,
+ string* scratch) const = 0;
+
+
+ // Singular field mutators -----------------------------------------
+ // These mutate the value of a non-repeated field.
+
+ virtual void SetInt32 (Message* message,
+ const FieldDescriptor* field, int32 value) const = 0;
+ virtual void SetInt64 (Message* message,
+ const FieldDescriptor* field, int64 value) const = 0;
+ virtual void SetUInt32(Message* message,
+ const FieldDescriptor* field, uint32 value) const = 0;
+ virtual void SetUInt64(Message* message,
+ const FieldDescriptor* field, uint64 value) const = 0;
+ virtual void SetFloat (Message* message,
+ const FieldDescriptor* field, float value) const = 0;
+ virtual void SetDouble(Message* message,
+ const FieldDescriptor* field, double value) const = 0;
+ virtual void SetBool (Message* message,
+ const FieldDescriptor* field, bool value) const = 0;
+ virtual void SetString(Message* message,
+ const FieldDescriptor* field,
+ const string& value) const = 0;
+ virtual void SetEnum (Message* message,
+ const FieldDescriptor* field,
+ const EnumValueDescriptor* value) const = 0;
+ // Set an enum field's value with an integer rather than EnumValueDescriptor.
+ // If the value does not correspond to a known enum value, either behavior is
+ // undefined (for proto2 messages), or the value is accepted silently for
+ // messages with new unknown-enum-value semantics.
+ virtual void SetEnumValue(Message* message,
+ const FieldDescriptor* field,
+ int value) const;
+
+ // Get a mutable pointer to a field with a message type. If a MessageFactory
+ // is provided, it will be used to construct instances of the sub-message;
+ // otherwise, the default factory is used. If the field is an extension that
+ // does not live in the same pool as the containing message's descriptor (e.g.
+ // it lives in an overlay pool), then a MessageFactory must be provided.
+ // If you have no idea what that meant, then you probably don't need to worry
+ // about it (don't provide a MessageFactory). WARNING: If the
+ // FieldDescriptor is for a compiled-in extension, then
+ // factory->GetPrototype(field->message_type()) MUST return an instance of
+ // the compiled-in class for this type, NOT DynamicMessage.
+ virtual Message* MutableMessage(Message* message,
+ const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const = 0;
+ // Replaces the message specified by 'field' with the already-allocated object
+ // sub_message, passing ownership to the message. If the field contained a
+ // message, that message is deleted. If sub_message is NULL, the field is
+ // cleared.
+ virtual void SetAllocatedMessage(Message* message,
+ Message* sub_message,
+ const FieldDescriptor* field) const = 0;
+ // Releases the message specified by 'field' and returns the pointer,
+ // ReleaseMessage() will return the message the message object if it exists.
+ // Otherwise, it may or may not return NULL. In any case, if the return value
+ // is non-NULL, the caller takes ownership of the pointer.
+ // If the field existed (HasField() is true), then the returned pointer will
+ // be the same as the pointer returned by MutableMessage().
+ // This function has the same effect as ClearField().
+ virtual Message* ReleaseMessage(Message* message,
+ const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const = 0;
+
+
+ // Repeated field getters ------------------------------------------
+ // These get the value of one element of a repeated field.
+
+ virtual int32 GetRepeatedInt32 (const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual int64 GetRepeatedInt64 (const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual uint32 GetRepeatedUInt32(const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual uint64 GetRepeatedUInt64(const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual float GetRepeatedFloat (const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual double GetRepeatedDouble(const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual bool GetRepeatedBool (const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual string GetRepeatedString(const Message& message,
+ const FieldDescriptor* field,
+ int index) const = 0;
+ virtual const EnumValueDescriptor* GetRepeatedEnum(
+ const Message& message,
+ const FieldDescriptor* field, int index) const = 0;
+ // GetRepeatedEnumValue() returns an enum field's value as an integer rather
+ // than an EnumValueDescriptor*. If the integer value does not correspond to a
+ // known value descriptor, a new value descriptor is created. (Such a value
+ // will only be present when the new unknown-enum-value semantics are enabled
+ // for a message.)
+ virtual int GetRepeatedEnumValue(
+ const Message& message,
+ const FieldDescriptor* field, int index) const;
+ virtual const Message& GetRepeatedMessage(
+ const Message& message,
+ const FieldDescriptor* field, int index) const = 0;
+
+ // See GetStringReference(), above.
+ virtual const string& GetRepeatedStringReference(
+ const Message& message, const FieldDescriptor* field,
+ int index, string* scratch) const = 0;
+
+
+ // Repeated field mutators -----------------------------------------
+ // These mutate the value of one element of a repeated field.
+
+ virtual void SetRepeatedInt32 (Message* message,
+ const FieldDescriptor* field,
+ int index, int32 value) const = 0;
+ virtual void SetRepeatedInt64 (Message* message,
+ const FieldDescriptor* field,
+ int index, int64 value) const = 0;
+ virtual void SetRepeatedUInt32(Message* message,
+ const FieldDescriptor* field,
+ int index, uint32 value) const = 0;
+ virtual void SetRepeatedUInt64(Message* message,
+ const FieldDescriptor* field,
+ int index, uint64 value) const = 0;
+ virtual void SetRepeatedFloat (Message* message,
+ const FieldDescriptor* field,
+ int index, float value) const = 0;
+ virtual void SetRepeatedDouble(Message* message,
+ const FieldDescriptor* field,
+ int index, double value) const = 0;
+ virtual void SetRepeatedBool (Message* message,
+ const FieldDescriptor* field,
+ int index, bool value) const = 0;
+ virtual void SetRepeatedString(Message* message,
+ const FieldDescriptor* field,
+ int index, const string& value) const = 0;
+ virtual void SetRepeatedEnum(Message* message,
+ const FieldDescriptor* field, int index,
+ const EnumValueDescriptor* value) const = 0;
+ // Set an enum field's value with an integer rather than EnumValueDescriptor.
+ // If the value does not correspond to a known enum value, either behavior is
+ // undefined (for proto2 messages), or the value is accepted silently for
+ // messages with new unknown-enum-value semantics.
+ virtual void SetRepeatedEnumValue(Message* message,
+ const FieldDescriptor* field, int index,
+ int value) const;
+ // Get a mutable pointer to an element of a repeated field with a message
+ // type.
+ virtual Message* MutableRepeatedMessage(
+ Message* message, const FieldDescriptor* field, int index) const = 0;
+
+
+ // Repeated field adders -------------------------------------------
+ // These add an element to a repeated field.
+
+ virtual void AddInt32 (Message* message,
+ const FieldDescriptor* field, int32 value) const = 0;
+ virtual void AddInt64 (Message* message,
+ const FieldDescriptor* field, int64 value) const = 0;
+ virtual void AddUInt32(Message* message,
+ const FieldDescriptor* field, uint32 value) const = 0;
+ virtual void AddUInt64(Message* message,
+ const FieldDescriptor* field, uint64 value) const = 0;
+ virtual void AddFloat (Message* message,
+ const FieldDescriptor* field, float value) const = 0;
+ virtual void AddDouble(Message* message,
+ const FieldDescriptor* field, double value) const = 0;
+ virtual void AddBool (Message* message,
+ const FieldDescriptor* field, bool value) const = 0;
+ virtual void AddString(Message* message,
+ const FieldDescriptor* field,
+ const string& value) const = 0;
+ virtual void AddEnum (Message* message,
+ const FieldDescriptor* field,
+ const EnumValueDescriptor* value) const = 0;
+ // Set an enum field's value with an integer rather than EnumValueDescriptor.
+ // If the value does not correspond to a known enum value, either behavior is
+ // undefined (for proto2 messages), or the value is accepted silently for
+ // messages with new unknown-enum-value semantics.
+ virtual void AddEnumValue(Message* message,
+ const FieldDescriptor* field,
+ int value) const;
+ // See MutableMessage() for comments on the "factory" parameter.
+ virtual Message* AddMessage(Message* message,
+ const FieldDescriptor* field,
+ MessageFactory* factory = NULL) const = 0;
+
+ // Appends an already-allocated object 'new_entry' to the repeated field
+ // specifyed by 'field' passing ownership to the message.
+ // TODO(tmarek): Make virtual after all subclasses have been
+ // updated.
+ virtual void AddAllocatedMessage(Message* /* message */,
+ const FieldDescriptor* /*field */,
+ Message* /* new_entry */) const {}
+
+
+ // Get a RepeatedFieldRef object that can be used to read the underlying
+ // repeated field. The type parameter T must be set according to the
+ // field's cpp type. The following table shows the mapping from cpp type
+ // to acceptable T.
+ //
+ // field->cpp_type() T
+ // CPPTYPE_INT32 int32
+ // CPPTYPE_UINT32 uint32
+ // CPPTYPE_INT64 int64
+ // CPPTYPE_UINT64 uint64
+ // CPPTYPE_DOUBLE double
+ // CPPTYPE_FLOAT float
+ // CPPTYPE_BOOL bool
+ // CPPTYPE_ENUM generated enum type or int32
+ // CPPTYPE_STRING string
+ // CPPTYPE_MESSAGE generated message type or google::protobuf::Message
+ //
+ // A RepeatedFieldRef object can be copied and the resulted object will point
+ // to the same repeated field in the same message. The object can be used as
+ // long as the message is not destroyed.
+ //
+ // Note that to use this method users need to include the header file
+ // "google/protobuf/reflection.h" (which defines the RepeatedFieldRef
+ // class templates).
+ template<typename T>
+ RepeatedFieldRef<T> GetRepeatedFieldRef(
+ const Message& message, const FieldDescriptor* field) const;
+
+ // Like GetRepeatedFieldRef() but return an object that can also be used
+ // manipulate the underlying repeated field.
+ template<typename T>
+ MutableRepeatedFieldRef<T> GetMutableRepeatedFieldRef(
+ Message* message, const FieldDescriptor* field) const;
+
+ // DEPRECATED. Please use Get(Mutable)RepeatedFieldRef() for repeated field
+ // access. The following repeated field accesors will be removed in the
+ // future.
+ //
+ // Repeated field accessors -------------------------------------------------
+ // The methods above, e.g. GetRepeatedInt32(msg, fd, index), provide singular
+ // access to the data in a RepeatedField. The methods below provide aggregate
+ // access by exposing the RepeatedField object itself with the Message.
+ // Applying these templates to inappropriate types will lead to an undefined
+ // reference at link time (e.g. GetRepeatedField<***double>), or possibly a
+ // template matching error at compile time (e.g. GetRepeatedPtrField<File>).
+ //
+ // Usage example: my_doubs = refl->GetRepeatedField<double>(msg, fd);
+
+ // DEPRECATED. Please use GetRepeatedFieldRef().
+ //
+ // for T = Cord and all protobuf scalar types except enums.
+ template<typename T>
+ const RepeatedField<T>& GetRepeatedField(
+ const Message&, const FieldDescriptor*) const;
+
+ // DEPRECATED. Please use GetMutableRepeatedFieldRef().
+ //
+ // for T = Cord and all protobuf scalar types except enums.
+ template<typename T>
+ RepeatedField<T>* MutableRepeatedField(
+ Message*, const FieldDescriptor*) const;
+
+ // DEPRECATED. Please use GetRepeatedFieldRef().
+ //
+ // for T = string, google::protobuf::internal::StringPieceField
+ // google::protobuf::Message & descendants.
+ template<typename T>
+ const RepeatedPtrField<T>& GetRepeatedPtrField(
+ const Message&, const FieldDescriptor*) const;
+
+ // DEPRECATED. Please use GetMutableRepeatedFieldRef().
+ //
+ // for T = string, google::protobuf::internal::StringPieceField
+ // google::protobuf::Message & descendants.
+ template<typename T>
+ RepeatedPtrField<T>* MutableRepeatedPtrField(
+ Message*, const FieldDescriptor*) const;
+
+ // Extensions ----------------------------------------------------------------
+
+ // Try to find an extension of this message type by fully-qualified field
+ // name. Returns NULL if no extension is known for this name or number.
+ virtual const FieldDescriptor* FindKnownExtensionByName(
+ const string& name) const = 0;
+
+ // Try to find an extension of this message type by field number.
+ // Returns NULL if no extension is known for this name or number.
+ virtual const FieldDescriptor* FindKnownExtensionByNumber(
+ int number) const = 0;
+
+ // Feature Flags -------------------------------------------------------------
+
+ // Does this message support storing arbitrary integer values in enum fields?
+ // If |true|, GetEnumValue/SetEnumValue and associated repeated-field versions
+ // take arbitrary integer values, and the legacy GetEnum() getter will
+ // dynamically create an EnumValueDescriptor for any integer value without
+ // one. If |false|, setting an unknown enum value via the integer-based
+ // setters results in undefined behavior (in practice, GOOGLE_DCHECK-fails).
+ //
+ // Generic code that uses reflection to handle messages with enum fields
+ // should check this flag before using the integer-based setter, and either
+ // downgrade to a compatible value or use the UnknownFieldSet if not. For
+ // example:
+ //
+ // int new_value = GetValueFromApplicationLogic();
+ // if (reflection->SupportsUnknownEnumValues()) {
+ // reflection->SetEnumValue(message, field, new_value);
+ // } else {
+ // if (field_descriptor->enum_type()->
+ // FindValueByNumver(new_value) != NULL) {
+ // reflection->SetEnumValue(message, field, new_value);
+ // } else if (emit_unknown_enum_values) {
+ // reflection->MutableUnknownFields(message)->AddVarint(
+ // field->number(),
+ // new_value);
+ // } else {
+ // // convert value to a compatible/default value.
+ // new_value = CompatibleDowngrade(new_value);
+ // reflection->SetEnumValue(message, field, new_value);
+ // }
+ // }
+ virtual bool SupportsUnknownEnumValues() const { return false; }
+
+ // Returns the MessageFactory associated with this message. This can be
+ // useful for determining if a message is a generated message or not, for
+ // example:
+ //
+ // if (message->GetReflection()->GetMessageFactory() ==
+ // google::protobuf::MessageFactory::generated_factory()) {
+ // // This is a generated message.
+ // }
+ //
+ // It can also be used to create more messages of this type, though
+ // Message::New() is an easier way to accomplish this.
+ virtual MessageFactory* GetMessageFactory() const;
+
+ // ---------------------------------------------------------------------------
+
+ protected:
+ // Obtain a pointer to a Repeated Field Structure and do some type checking:
+ // on field->cpp_type(),
+ // on field->field_option().ctype() (if ctype >= 0)
+ // of field->message_type() (if message_type != NULL).
+ // We use 2 routine rather than 4 (const vs mutable) x (scalar vs pointer).
+ virtual void* MutableRawRepeatedField(
+ Message* message, const FieldDescriptor* field, FieldDescriptor::CppType,
+ int ctype, const Descriptor* message_type) const = 0;
+
+ // TODO(jieluo) - make it pure virtual after updating all the subclasses.
+ virtual const void* GetRawRepeatedField(
+ const Message& message, const FieldDescriptor* field,
+ FieldDescriptor::CppType cpptype, int ctype,
+ const Descriptor* message_type) const {
+ return MutableRawRepeatedField(
+ const_cast<Message*>(&message), field, cpptype, ctype, message_type);
+ }
+
+ // The following methods are used to implement (Mutable)RepeatedFieldRef.
+ // A Ref object will store a raw pointer to the repeated field data (obtained
+ // from RepeatedFieldData()) and a pointer to a Accessor (obtained from
+ // RepeatedFieldAccessor) which will be used to access the raw data.
+ //
+ // TODO(xiaofeng): Make these methods pure-virtual.
+
+ // Returns a raw pointer to the repeated field
+ //
+ // "cpp_type" and "message_type" are decuded from the type parameter T passed
+ // to Get(Mutable)RepeatedFieldRef. If T is a generated message type,
+ // "message_type" should be set to its descriptor. Otherwise "message_type"
+ // should be set to NULL. Implementations of this method should check whether
+ // "cpp_type"/"message_type" is consistent with the actual type of the field.
+ // We use 1 routine rather than 2 (const vs mutable) because it is protected
+ // and it doesn't change the message.
+ virtual void* RepeatedFieldData(
+ Message* message, const FieldDescriptor* field,
+ FieldDescriptor::CppType cpp_type,
+ const Descriptor* message_type) const;
+
+ // The returned pointer should point to a singleton instance which implements
+ // the RepeatedFieldAccessor interface.
+ virtual const internal::RepeatedFieldAccessor* RepeatedFieldAccessor(
+ const FieldDescriptor* field) const;
+
+ private:
+ template<typename T, typename Enable>
+ friend class RepeatedFieldRef;
+ template<typename T, typename Enable>
+ friend class MutableRepeatedFieldRef;
+ friend class ::google::protobuf::python::MapReflectionFriend;
+
+ // Special version for specialized implementations of string. We can't call
+ // MutableRawRepeatedField directly here because we don't have access to
+ // FieldOptions::* which are defined in descriptor.pb.h. Including that
+ // file here is not possible because it would cause a circular include cycle.
+ // We use 1 routine rather than 2 (const vs mutable) because it is private
+ // and mutable a repeated string field doesn't change the message.
+ void* MutableRawRepeatedString(
+ Message* message, const FieldDescriptor* field, bool is_string) const;
+
+ friend class MapReflectionTester;
+ // TODO(jieluo) - make the map APIs pure virtual after updating
+ // all the subclasses.
+ // Returns true if key is in map. Returns false if key is not in map field.
+ virtual bool ContainsMapKey(const Message& /* message*/,
+ const FieldDescriptor* /* field */,
+ const MapKey& /* key */) const {
+ return false;
+ }
+
+ // If key is in map field: Saves the value pointer to val and returns
+ // false. If key in not in map field: Insert the key into map, saves
+ // value pointer to val and retuns true.
+ virtual bool InsertOrLookupMapValue(Message* /* message */,
+ const FieldDescriptor* /* field */,
+ const MapKey& /* key */,
+ MapValueRef* /* val */) const {
+ return false;
+ }
+
+ // Delete and returns true if key is in the map field. Returns false
+ // otherwise.
+ virtual bool DeleteMapValue(Message* /* mesage */,
+ const FieldDescriptor* /* field */,
+ const MapKey& /* key */) const {
+ return false;
+ }
+
+ // Returns a MapIterator referring to the first element in the map field.
+ // If the map field is empty, this function returns the same as
+ // reflection::MapEnd. Mutation to the field may invalidate the iterator.
+ virtual MapIterator MapBegin(
+ Message* message,
+ const FieldDescriptor* field) const;
+
+ // Returns a MapIterator referring to the theoretical element that would
+ // follow the last element in the map field. It does not point to any
+ // real element. Mutation to the field may invalidate the iterator.
+ virtual MapIterator MapEnd(
+ Message* message,
+ const FieldDescriptor* field) const;
+
+ // Get the number of <key, value> pair of a map field. The result may be
+ // different from FieldSize which can have duplicate keys.
+ virtual int MapSize(const Message& /* message */,
+ const FieldDescriptor* /* field */) const {
+ return 0;
+ }
+
+ // Help method for MapIterator.
+ friend class MapIterator;
+ virtual internal::MapFieldBase* MapData(
+ Message* /* message */, const FieldDescriptor* /* field */) const {
+ return NULL;
+ }
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Reflection);
+};
+
+// Abstract interface for a factory for message objects.
+class LIBPROTOBUF_EXPORT MessageFactory {
+ public:
+ inline MessageFactory() {}
+ virtual ~MessageFactory();
+
+ // Given a Descriptor, gets or constructs the default (prototype) Message
+ // of that type. You can then call that message's New() method to construct
+ // a mutable message of that type.
+ //
+ // Calling this method twice with the same Descriptor returns the same
+ // object. The returned object remains property of the factory. Also, any
+ // objects created by calling the prototype's New() method share some data
+ // with the prototype, so these must be destroyed before the MessageFactory
+ // is destroyed.
+ //
+ // The given descriptor must outlive the returned message, and hence must
+ // outlive the MessageFactory.
+ //
+ // Some implementations do not support all types. GetPrototype() will
+ // return NULL if the descriptor passed in is not supported.
+ //
+ // This method may or may not be thread-safe depending on the implementation.
+ // Each implementation should document its own degree thread-safety.
+ virtual const Message* GetPrototype(const Descriptor* type) = 0;
+
+ // Gets a MessageFactory which supports all generated, compiled-in messages.
+ // In other words, for any compiled-in type FooMessage, the following is true:
+ // MessageFactory::generated_factory()->GetPrototype(
+ // FooMessage::descriptor()) == FooMessage::default_instance()
+ // This factory supports all types which are found in
+ // DescriptorPool::generated_pool(). If given a descriptor from any other
+ // pool, GetPrototype() will return NULL. (You can also check if a
+ // descriptor is for a generated message by checking if
+ // descriptor->file()->pool() == DescriptorPool::generated_pool().)
+ //
+ // This factory is 100% thread-safe; calling GetPrototype() does not modify
+ // any shared data.
+ //
+ // This factory is a singleton. The caller must not delete the object.
+ static MessageFactory* generated_factory();
+
+ // For internal use only: Registers a .proto file at static initialization
+ // time, to be placed in generated_factory. The first time GetPrototype()
+ // is called with a descriptor from this file, |register_messages| will be
+ // called, with the file name as the parameter. It must call
+ // InternalRegisterGeneratedMessage() (below) to register each message type
+ // in the file. This strange mechanism is necessary because descriptors are
+ // built lazily, so we can't register types by their descriptor until we
+ // know that the descriptor exists. |filename| must be a permanent string.
+ static void InternalRegisterGeneratedFile(
+ const char* filename, void (*register_messages)(const string&));
+
+ // For internal use only: Registers a message type. Called only by the
+ // functions which are registered with InternalRegisterGeneratedFile(),
+ // above.
+ static void InternalRegisterGeneratedMessage(const Descriptor* descriptor,
+ const Message* prototype);
+
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageFactory);
+};
+
+#define DECLARE_GET_REPEATED_FIELD(TYPE) \
+template<> \
+LIBPROTOBUF_EXPORT \
+const RepeatedField<TYPE>& Reflection::GetRepeatedField<TYPE>( \
+ const Message& message, const FieldDescriptor* field) const; \
+ \
+template<> \
+LIBPROTOBUF_EXPORT \
+RepeatedField<TYPE>* Reflection::MutableRepeatedField<TYPE>( \
+ Message* message, const FieldDescriptor* field) const;
+
+DECLARE_GET_REPEATED_FIELD(int32)
+DECLARE_GET_REPEATED_FIELD(int64)
+DECLARE_GET_REPEATED_FIELD(uint32)
+DECLARE_GET_REPEATED_FIELD(uint64)
+DECLARE_GET_REPEATED_FIELD(float)
+DECLARE_GET_REPEATED_FIELD(double)
+DECLARE_GET_REPEATED_FIELD(bool)
+
+#undef DECLARE_GET_REPEATED_FIELD
+
+// =============================================================================
+// Implementation details for {Get,Mutable}RawRepeatedPtrField. We provide
+// specializations for <string>, <StringPieceField> and <Message> and handle
+// everything else with the default template which will match any type having
+// a method with signature "static const google::protobuf::Descriptor* descriptor()".
+// Such a type presumably is a descendant of google::protobuf::Message.
+
+template<>
+inline const RepeatedPtrField<string>& Reflection::GetRepeatedPtrField<string>(
+ const Message& message, const FieldDescriptor* field) const {
+ return *static_cast<RepeatedPtrField<string>* >(
+ MutableRawRepeatedString(const_cast<Message*>(&message), field, true));
+}
+
+template<>
+inline RepeatedPtrField<string>* Reflection::MutableRepeatedPtrField<string>(
+ Message* message, const FieldDescriptor* field) const {
+ return static_cast<RepeatedPtrField<string>* >(
+ MutableRawRepeatedString(message, field, true));
+}
+
+
+// -----
+
+template<>
+inline const RepeatedPtrField<Message>& Reflection::GetRepeatedPtrField(
+ const Message& message, const FieldDescriptor* field) const {
+ return *static_cast<const RepeatedPtrField<Message>* >(
+ GetRawRepeatedField(message, field, FieldDescriptor::CPPTYPE_MESSAGE,
+ -1, NULL));
+}
+
+template<>
+inline RepeatedPtrField<Message>* Reflection::MutableRepeatedPtrField(
+ Message* message, const FieldDescriptor* field) const {
+ return static_cast<RepeatedPtrField<Message>* >(
+ MutableRawRepeatedField(message, field,
+ FieldDescriptor::CPPTYPE_MESSAGE, -1,
+ NULL));
+}
+
+template<typename PB>
+inline const RepeatedPtrField<PB>& Reflection::GetRepeatedPtrField(
+ const Message& message, const FieldDescriptor* field) const {
+ return *static_cast<const RepeatedPtrField<PB>* >(
+ GetRawRepeatedField(message, field, FieldDescriptor::CPPTYPE_MESSAGE,
+ -1, PB::default_instance().GetDescriptor()));
+}
+
+template<typename PB>
+inline RepeatedPtrField<PB>* Reflection::MutableRepeatedPtrField(
+ Message* message, const FieldDescriptor* field) const {
+ return static_cast<RepeatedPtrField<PB>* >(
+ MutableRawRepeatedField(message, field,
+ FieldDescriptor::CPPTYPE_MESSAGE, -1,
+ PB::default_instance().GetDescriptor()));
+}
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MESSAGE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/message_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/message_lite.cc
new file mode 100644
index 0000000000..ba56db952d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/message_lite.cc
@@ -0,0 +1,371 @@
+// 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.
+
+// Authors: wink@google.com (Wink Saville),
+// kenton@google.com (Kenton Varda)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <google/protobuf/message_lite.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/repeated_field.h>
+#include <string>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+
+string MessageLite::InitializationErrorString() const {
+ return "(cannot determine missing fields for lite message)";
+}
+
+namespace {
+
+// When serializing, we first compute the byte size, then serialize the message.
+// If serialization produces a different number of bytes than expected, we
+// call this function, which crashes. The problem could be due to a bug in the
+// protobuf implementation but is more likely caused by concurrent modification
+// of the message. This function attempts to distinguish between the two and
+// provide a useful error message.
+void ByteSizeConsistencyError(int byte_size_before_serialization,
+ int byte_size_after_serialization,
+ int bytes_produced_by_serialization,
+ const MessageLite& message) {
+ GOOGLE_CHECK_EQ(byte_size_before_serialization, byte_size_after_serialization)
+ << message.GetTypeName()
+ << " was modified concurrently during serialization.";
+ GOOGLE_CHECK_EQ(bytes_produced_by_serialization, byte_size_before_serialization)
+ << "Byte size calculation and serialization were inconsistent. This "
+ "may indicate a bug in protocol buffers or it may be caused by "
+ "concurrent modification of " << message.GetTypeName() << ".";
+ GOOGLE_LOG(FATAL) << "This shouldn't be called if all the sizes are equal.";
+}
+
+string InitializationErrorMessage(const char* action,
+ const MessageLite& message) {
+ // Note: We want to avoid depending on strutil in the lite library, otherwise
+ // we'd use:
+ //
+ // return strings::Substitute(
+ // "Can't $0 message of type \"$1\" because it is missing required "
+ // "fields: $2",
+ // action, message.GetTypeName(),
+ // message.InitializationErrorString());
+
+ string result;
+ result += "Can't ";
+ result += action;
+ result += " message of type \"";
+ result += message.GetTypeName();
+ result += "\" because it is missing required fields: ";
+ result += message.InitializationErrorString();
+ return result;
+}
+
+// Several of the Parse methods below just do one thing and then call another
+// method. In a naive implementation, we might have ParseFromString() call
+// ParseFromArray() which would call ParseFromZeroCopyStream() which would call
+// ParseFromCodedStream() which would call MergeFromCodedStream() which would
+// call MergePartialFromCodedStream(). However, when parsing very small
+// messages, every function call introduces significant overhead. To avoid
+// this without reproducing code, we use these forced-inline helpers.
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool InlineMergeFromCodedStream(
+ io::CodedInputStream* input, MessageLite* message);
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool InlineParseFromCodedStream(
+ io::CodedInputStream* input, MessageLite* message);
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool InlineParsePartialFromCodedStream(
+ io::CodedInputStream* input, MessageLite* message);
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool InlineParseFromArray(
+ const void* data, int size, MessageLite* message);
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool InlineParsePartialFromArray(
+ const void* data, int size, MessageLite* message);
+
+inline bool InlineMergeFromCodedStream(io::CodedInputStream* input,
+ MessageLite* message) {
+ if (!message->MergePartialFromCodedStream(input)) return false;
+ if (!message->IsInitialized()) {
+ GOOGLE_LOG(ERROR) << InitializationErrorMessage("parse", *message);
+ return false;
+ }
+ return true;
+}
+
+inline bool InlineParseFromCodedStream(io::CodedInputStream* input,
+ MessageLite* message) {
+ message->Clear();
+ return InlineMergeFromCodedStream(input, message);
+}
+
+inline bool InlineParsePartialFromCodedStream(io::CodedInputStream* input,
+ MessageLite* message) {
+ message->Clear();
+ return message->MergePartialFromCodedStream(input);
+}
+
+inline bool InlineParseFromArray(
+ const void* data, int size, MessageLite* message) {
+ io::CodedInputStream input(reinterpret_cast<const uint8*>(data), size);
+ return InlineParseFromCodedStream(&input, message) &&
+ input.ConsumedEntireMessage();
+}
+
+inline bool InlineParsePartialFromArray(
+ const void* data, int size, MessageLite* message) {
+ io::CodedInputStream input(reinterpret_cast<const uint8*>(data), size);
+ return InlineParsePartialFromCodedStream(&input, message) &&
+ input.ConsumedEntireMessage();
+}
+
+} // namespace
+
+
+MessageLite* MessageLite::New(::google::protobuf::Arena* arena) const {
+ MessageLite* message = New();
+ if (arena != NULL) {
+ arena->Own(message);
+ }
+ return message;
+}
+
+bool MessageLite::MergeFromCodedStream(io::CodedInputStream* input) {
+ return InlineMergeFromCodedStream(input, this);
+}
+
+bool MessageLite::ParseFromCodedStream(io::CodedInputStream* input) {
+ return InlineParseFromCodedStream(input, this);
+}
+
+bool MessageLite::ParsePartialFromCodedStream(io::CodedInputStream* input) {
+ return InlineParsePartialFromCodedStream(input, this);
+}
+
+bool MessageLite::ParseFromZeroCopyStream(io::ZeroCopyInputStream* input) {
+ io::CodedInputStream decoder(input);
+ return ParseFromCodedStream(&decoder) && decoder.ConsumedEntireMessage();
+}
+
+bool MessageLite::ParsePartialFromZeroCopyStream(
+ io::ZeroCopyInputStream* input) {
+ io::CodedInputStream decoder(input);
+ return ParsePartialFromCodedStream(&decoder) &&
+ decoder.ConsumedEntireMessage();
+}
+
+bool MessageLite::ParseFromBoundedZeroCopyStream(
+ io::ZeroCopyInputStream* input, int size) {
+ io::CodedInputStream decoder(input);
+ decoder.PushLimit(size);
+ return ParseFromCodedStream(&decoder) &&
+ decoder.ConsumedEntireMessage() &&
+ decoder.BytesUntilLimit() == 0;
+}
+
+bool MessageLite::ParsePartialFromBoundedZeroCopyStream(
+ io::ZeroCopyInputStream* input, int size) {
+ io::CodedInputStream decoder(input);
+ decoder.PushLimit(size);
+ return ParsePartialFromCodedStream(&decoder) &&
+ decoder.ConsumedEntireMessage() &&
+ decoder.BytesUntilLimit() == 0;
+}
+
+bool MessageLite::ParseFromString(const string& data) {
+ return InlineParseFromArray(data.data(), data.size(), this);
+}
+
+bool MessageLite::ParsePartialFromString(const string& data) {
+ return InlineParsePartialFromArray(data.data(), data.size(), this);
+}
+
+bool MessageLite::ParseFromArray(const void* data, int size) {
+ return InlineParseFromArray(data, size, this);
+}
+
+bool MessageLite::ParsePartialFromArray(const void* data, int size) {
+ return InlineParsePartialFromArray(data, size, this);
+}
+
+
+// ===================================================================
+
+uint8* MessageLite::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, uint8* target) const {
+ // We only optimize this when using optimize_for = SPEED. In other cases
+ // we just use the CodedOutputStream path.
+ int size = GetCachedSize();
+ io::ArrayOutputStream out(target, size);
+ io::CodedOutputStream coded_out(&out);
+ SerializeWithCachedSizes(&coded_out);
+ GOOGLE_CHECK(!coded_out.HadError());
+ return target + size;
+}
+
+bool MessageLite::SerializeToCodedStream(io::CodedOutputStream* output) const {
+ GOOGLE_DCHECK(IsInitialized()) << InitializationErrorMessage("serialize", *this);
+ return SerializePartialToCodedStream(output);
+}
+
+bool MessageLite::SerializePartialToCodedStream(
+ io::CodedOutputStream* output) const {
+ const int size = ByteSize(); // Force size to be cached.
+ if (size < 0) {
+ // Messages >2G cannot be serialized due to overflow computing ByteSize.
+ GOOGLE_LOG(ERROR) << "Error computing ByteSize (possible overflow?).";
+ return false;
+ }
+
+ uint8* buffer = output->GetDirectBufferForNBytesAndAdvance(size);
+ if (buffer != NULL) {
+ uint8* end = SerializeWithCachedSizesToArray(buffer);
+ if (end - buffer != size) {
+ ByteSizeConsistencyError(size, ByteSize(), end - buffer, *this);
+ }
+ return true;
+ } else {
+ int original_byte_count = output->ByteCount();
+ SerializeWithCachedSizes(output);
+ if (output->HadError()) {
+ return false;
+ }
+ int final_byte_count = output->ByteCount();
+
+ if (final_byte_count - original_byte_count != size) {
+ ByteSizeConsistencyError(size, ByteSize(),
+ final_byte_count - original_byte_count, *this);
+ }
+
+ return true;
+ }
+}
+
+bool MessageLite::SerializeToZeroCopyStream(
+ io::ZeroCopyOutputStream* output) const {
+ io::CodedOutputStream encoder(output);
+ return SerializeToCodedStream(&encoder);
+}
+
+bool MessageLite::SerializePartialToZeroCopyStream(
+ io::ZeroCopyOutputStream* output) const {
+ io::CodedOutputStream encoder(output);
+ return SerializePartialToCodedStream(&encoder);
+}
+
+bool MessageLite::AppendToString(string* output) const {
+ GOOGLE_DCHECK(IsInitialized()) << InitializationErrorMessage("serialize", *this);
+ return AppendPartialToString(output);
+}
+
+bool MessageLite::AppendPartialToString(string* output) const {
+ int old_size = output->size();
+ int byte_size = ByteSize();
+ if (byte_size < 0) {
+ // Messages >2G cannot be serialized due to overflow computing ByteSize.
+ GOOGLE_LOG(ERROR) << "Error computing ByteSize (possible overflow?).";
+ return false;
+ }
+
+ STLStringResizeUninitialized(output, old_size + byte_size);
+ uint8* start =
+ reinterpret_cast<uint8*>(io::mutable_string_data(output) + old_size);
+ uint8* end = SerializeWithCachedSizesToArray(start);
+ if (end - start != byte_size) {
+ ByteSizeConsistencyError(byte_size, ByteSize(), end - start, *this);
+ }
+ return true;
+}
+
+bool MessageLite::SerializeToString(string* output) const {
+ output->clear();
+ return AppendToString(output);
+}
+
+bool MessageLite::SerializePartialToString(string* output) const {
+ output->clear();
+ return AppendPartialToString(output);
+}
+
+bool MessageLite::SerializeToArray(void* data, int size) const {
+ GOOGLE_DCHECK(IsInitialized()) << InitializationErrorMessage("serialize", *this);
+ return SerializePartialToArray(data, size);
+}
+
+bool MessageLite::SerializePartialToArray(void* data, int size) const {
+ int byte_size = ByteSize();
+ if (size < byte_size) return false;
+ uint8* start = reinterpret_cast<uint8*>(data);
+ uint8* end = SerializeWithCachedSizesToArray(start);
+ if (end - start != byte_size) {
+ ByteSizeConsistencyError(byte_size, ByteSize(), end - start, *this);
+ }
+ return true;
+}
+
+string MessageLite::SerializeAsString() const {
+ // If the compiler implements the (Named) Return Value Optimization,
+ // the local variable 'output' will not actually reside on the stack
+ // of this function, but will be overlaid with the object that the
+ // caller supplied for the return value to be constructed in.
+ string output;
+ if (!AppendToString(&output))
+ output.clear();
+ return output;
+}
+
+string MessageLite::SerializePartialAsString() const {
+ string output;
+ if (!AppendPartialToString(&output))
+ output.clear();
+ return output;
+}
+
+namespace internal {
+template<>
+MessageLite* GenericTypeHandler<MessageLite>::NewFromPrototype(
+ const MessageLite* prototype, google::protobuf::Arena* arena) {
+ return prototype->New(arena);
+}
+template <>
+void GenericTypeHandler<MessageLite>::Merge(const MessageLite& from,
+ MessageLite* to) {
+ to->CheckTypeAndMergeFrom(from);
+}
+template<>
+void GenericTypeHandler<string>::Merge(const string& from,
+ string* to) {
+ *to = from;
+}
+} // namespace internal
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/message_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/message_lite.h
new file mode 100644
index 0000000000..2bdfe49614
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/message_lite.h
@@ -0,0 +1,296 @@
+// 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.
+
+// Authors: wink@google.com (Wink Saville),
+// kenton@google.com (Kenton Varda)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// Defines MessageLite, the abstract interface implemented by all (lite
+// and non-lite) protocol message objects.
+
+#ifndef GOOGLE_PROTOBUF_MESSAGE_LITE_H__
+#define GOOGLE_PROTOBUF_MESSAGE_LITE_H__
+
+#include <google/protobuf/stubs/common.h>
+
+
+namespace google {
+namespace protobuf {
+ class Arena;
+namespace io {
+ class CodedInputStream;
+ class CodedOutputStream;
+ class ZeroCopyInputStream;
+ class ZeroCopyOutputStream;
+}
+namespace internal {
+ class WireFormatLite;
+}
+
+// Interface to light weight protocol messages.
+//
+// This interface is implemented by all protocol message objects. Non-lite
+// messages additionally implement the Message interface, which is a
+// subclass of MessageLite. Use MessageLite instead when you only need
+// the subset of features which it supports -- namely, nothing that uses
+// descriptors or reflection. You can instruct the protocol compiler
+// to generate classes which implement only MessageLite, not the full
+// Message interface, by adding the following line to the .proto file:
+//
+// option optimize_for = LITE_RUNTIME;
+//
+// This is particularly useful on resource-constrained systems where
+// the full protocol buffers runtime library is too big.
+//
+// Note that on non-constrained systems (e.g. servers) when you need
+// to link in lots of protocol definitions, a better way to reduce
+// total code footprint is to use optimize_for = CODE_SIZE. This
+// will make the generated code smaller while still supporting all the
+// same features (at the expense of speed). optimize_for = LITE_RUNTIME
+// is best when you only have a small number of message types linked
+// into your binary, in which case the size of the protocol buffers
+// runtime itself is the biggest problem.
+class LIBPROTOBUF_EXPORT MessageLite {
+ public:
+ inline MessageLite() {}
+ virtual ~MessageLite() {}
+
+ // Basic Operations ------------------------------------------------
+
+ // Get the name of this message type, e.g. "foo.bar.BazProto".
+ virtual string GetTypeName() const = 0;
+
+ // Construct a new instance of the same type. Ownership is passed to the
+ // caller.
+ virtual MessageLite* New() const = 0;
+
+ // Construct a new instance on the arena. Ownership is passed to the caller
+ // if arena is a NULL. Default implementation for backwards compatibility.
+ virtual MessageLite* New(::google::protobuf::Arena* arena) const;
+
+ // Get the arena, if any, associated with this message. Virtual method
+ // required for generic operations but most arena-related operations should
+ // use the GetArenaNoVirtual() generated-code method. Default implementation
+ // to reduce code size by avoiding the need for per-type implementations when
+ // types do not implement arena support.
+ virtual ::google::protobuf::Arena* GetArena() const { return NULL; }
+
+ // Get a pointer that may be equal to this message's arena, or may not be. If
+ // the value returned by this method is equal to some arena pointer, then this
+ // message is on that arena; however, if this message is on some arena, this
+ // method may or may not return that arena's pointer. As a tradeoff, this
+ // method may be more efficient than GetArena(). The intent is to allow
+ // underlying representations that use e.g. tagged pointers to sometimes store
+ // the arena pointer directly, and sometimes in a more indirect way, and allow
+ // a fastpath comparison against the arena pointer when it's easy to obtain.
+ virtual void* GetMaybeArenaPointer() const { return GetArena(); }
+
+ // Clear all fields of the message and set them to their default values.
+ // Clear() avoids freeing memory, assuming that any memory allocated
+ // to hold parts of the message will be needed again to hold the next
+ // message. If you actually want to free the memory used by a Message,
+ // you must delete it.
+ virtual void Clear() = 0;
+
+ // Quickly check if all required fields have values set.
+ virtual bool IsInitialized() const = 0;
+
+ // This is not implemented for Lite messages -- it just returns "(cannot
+ // determine missing fields for lite message)". However, it is implemented
+ // for full messages. See message.h.
+ virtual string InitializationErrorString() const;
+
+ // If |other| is the exact same class as this, calls MergeFrom(). Otherwise,
+ // results are undefined (probably crash).
+ virtual void CheckTypeAndMergeFrom(const MessageLite& other) = 0;
+
+ // Parsing ---------------------------------------------------------
+ // Methods for parsing in protocol buffer format. Most of these are
+ // just simple wrappers around MergeFromCodedStream(). Clear() will be called
+ // before merging the input.
+
+ // Fill the message with a protocol buffer parsed from the given input stream.
+ // Returns false on a read error or if the input is in the wrong format. A
+ // successful return does not indicate the entire input is consumed, ensure
+ // you call ConsumedEntireMessage() to check that if applicable.
+ bool ParseFromCodedStream(io::CodedInputStream* input);
+ // Like ParseFromCodedStream(), but accepts messages that are missing
+ // required fields.
+ bool ParsePartialFromCodedStream(io::CodedInputStream* input);
+ // Read a protocol buffer from the given zero-copy input stream. If
+ // successful, the entire input will be consumed.
+ bool ParseFromZeroCopyStream(io::ZeroCopyInputStream* input);
+ // Like ParseFromZeroCopyStream(), but accepts messages that are missing
+ // required fields.
+ bool ParsePartialFromZeroCopyStream(io::ZeroCopyInputStream* input);
+ // Read a protocol buffer from the given zero-copy input stream, expecting
+ // the message to be exactly "size" bytes long. If successful, exactly
+ // this many bytes will have been consumed from the input.
+ bool ParseFromBoundedZeroCopyStream(io::ZeroCopyInputStream* input, int size);
+ // Like ParseFromBoundedZeroCopyStream(), but accepts messages that are
+ // missing required fields.
+ bool ParsePartialFromBoundedZeroCopyStream(io::ZeroCopyInputStream* input,
+ int size);
+ // Parses a protocol buffer contained in a string. Returns true on success.
+ // This function takes a string in the (non-human-readable) binary wire
+ // format, matching the encoding output by MessageLite::SerializeToString().
+ // If you'd like to convert a human-readable string into a protocol buffer
+ // object, see google::protobuf::TextFormat::ParseFromString().
+ bool ParseFromString(const string& data);
+ // Like ParseFromString(), but accepts messages that are missing
+ // required fields.
+ bool ParsePartialFromString(const string& data);
+ // Parse a protocol buffer contained in an array of bytes.
+ bool ParseFromArray(const void* data, int size);
+ // Like ParseFromArray(), but accepts messages that are missing
+ // required fields.
+ bool ParsePartialFromArray(const void* data, int size);
+
+
+ // Reads a protocol buffer from the stream and merges it into this
+ // Message. Singular fields read from the input overwrite what is
+ // already in the Message and repeated fields are appended to those
+ // already present.
+ //
+ // It is the responsibility of the caller to call input->LastTagWas()
+ // (for groups) or input->ConsumedEntireMessage() (for non-groups) after
+ // this returns to verify that the message's end was delimited correctly.
+ //
+ // ParsefromCodedStream() is implemented as Clear() followed by
+ // MergeFromCodedStream().
+ bool MergeFromCodedStream(io::CodedInputStream* input);
+
+ // Like MergeFromCodedStream(), but succeeds even if required fields are
+ // missing in the input.
+ //
+ // MergeFromCodedStream() is just implemented as MergePartialFromCodedStream()
+ // followed by IsInitialized().
+ virtual bool MergePartialFromCodedStream(io::CodedInputStream* input) = 0;
+
+
+ // Serialization ---------------------------------------------------
+ // Methods for serializing in protocol buffer format. Most of these
+ // are just simple wrappers around ByteSize() and SerializeWithCachedSizes().
+
+ // Write a protocol buffer of this message to the given output. Returns
+ // false on a write error. If the message is missing required fields,
+ // this may GOOGLE_CHECK-fail.
+ bool SerializeToCodedStream(io::CodedOutputStream* output) const;
+ // Like SerializeToCodedStream(), but allows missing required fields.
+ bool SerializePartialToCodedStream(io::CodedOutputStream* output) const;
+ // Write the message to the given zero-copy output stream. All required
+ // fields must be set.
+ bool SerializeToZeroCopyStream(io::ZeroCopyOutputStream* output) const;
+ // Like SerializeToZeroCopyStream(), but allows missing required fields.
+ bool SerializePartialToZeroCopyStream(io::ZeroCopyOutputStream* output) const;
+ // Serialize the message and store it in the given string. All required
+ // fields must be set.
+ bool SerializeToString(string* output) const;
+ // Like SerializeToString(), but allows missing required fields.
+ bool SerializePartialToString(string* output) const;
+ // Serialize the message and store it in the given byte array. All required
+ // fields must be set.
+ bool SerializeToArray(void* data, int size) const;
+ // Like SerializeToArray(), but allows missing required fields.
+ bool SerializePartialToArray(void* data, int size) const;
+
+ // Make a string encoding the message. Is equivalent to calling
+ // SerializeToString() on a string and using that. Returns the empty
+ // string if SerializeToString() would have returned an error.
+ // Note: If you intend to generate many such strings, you may
+ // reduce heap fragmentation by instead re-using the same string
+ // object with calls to SerializeToString().
+ string SerializeAsString() const;
+ // Like SerializeAsString(), but allows missing required fields.
+ string SerializePartialAsString() const;
+
+ // Like SerializeToString(), but appends to the data to the string's existing
+ // contents. All required fields must be set.
+ bool AppendToString(string* output) const;
+ // Like AppendToString(), but allows missing required fields.
+ bool AppendPartialToString(string* output) const;
+
+ // Computes the serialized size of the message. This recursively calls
+ // ByteSize() on all embedded messages. If a subclass does not override
+ // this, it MUST override SetCachedSize().
+ //
+ // ByteSize() is generally linear in the number of fields defined for the
+ // proto.
+ virtual int ByteSize() const = 0;
+
+ // Serializes the message without recomputing the size. The message must
+ // not have changed since the last call to ByteSize(); if it has, the results
+ // are undefined.
+ virtual void SerializeWithCachedSizes(
+ io::CodedOutputStream* output) const = 0;
+
+ // A version of SerializeWithCachedSizesToArray, below, that does
+ // not guarantee deterministic serialization.
+ virtual uint8* SerializeWithCachedSizesToArray(uint8* target) const {
+ return InternalSerializeWithCachedSizesToArray(false, target);
+ }
+
+ // Returns the result of the last call to ByteSize(). An embedded message's
+ // size is needed both to serialize it (because embedded messages are
+ // length-delimited) and to compute the outer message's size. Caching
+ // the size avoids computing it multiple times.
+ //
+ // ByteSize() does not automatically use the cached size when available
+ // because this would require invalidating it every time the message was
+ // modified, which would be too hard and expensive. (E.g. if a deeply-nested
+ // sub-message is changed, all of its parents' cached sizes would need to be
+ // invalidated, which is too much work for an otherwise inlined setter
+ // method.)
+ virtual int GetCachedSize() const = 0;
+
+ // Functions below here are not part of the public interface. It isn't
+ // enforced, but they should be treated as private, and will be private
+ // at some future time. Unfortunately the implementation of the "friend"
+ // keyword in GCC is broken at the moment, but we expect it will be fixed.
+
+ // Like SerializeWithCachedSizes, but writes directly to *target, returning
+ // a pointer to the byte immediately after the last byte written. "target"
+ // must point at a byte array of at least ByteSize() bytes. If deterministic
+ // is true then we use deterministic serialization, e.g., map keys are sorted.
+ // FOR INTERNAL USE ONLY!
+ virtual uint8* InternalSerializeWithCachedSizesToArray(bool deterministic,
+ uint8* target) const;
+
+ private:
+ friend class internal::WireFormatLite;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageLite);
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_MESSAGE_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/message_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/message_unittest.cc
new file mode 100644
index 0000000000..d668a1a6bb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/message_unittest.cc
@@ -0,0 +1,471 @@
+// 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.
+
+#include <google/protobuf/message.h>
+
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#ifdef _MSC_VER
+#include <io.h>
+#else
+#include <unistd.h>
+#endif
+#include <sstream>
+#include <fstream>
+
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/generated_message_reflection.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+#ifndef O_BINARY
+#ifdef _O_BINARY
+#define O_BINARY _O_BINARY
+#else
+#define O_BINARY 0 // If this isn't defined, the platform doesn't need it.
+#endif
+#endif
+
+TEST(MessageTest, SerializeHelpers) {
+ // TODO(kenton): Test more helpers? They're all two-liners so it seems
+ // like a waste of time.
+
+ protobuf_unittest::TestAllTypes message;
+ TestUtil::SetAllFields(&message);
+ stringstream stream;
+
+ string str1("foo");
+ string str2("bar");
+
+ EXPECT_TRUE(message.SerializeToString(&str1));
+ EXPECT_TRUE(message.AppendToString(&str2));
+ EXPECT_TRUE(message.SerializeToOstream(&stream));
+
+ EXPECT_EQ(str1.size() + 3, str2.size());
+ EXPECT_EQ("bar", str2.substr(0, 3));
+ // Don't use EXPECT_EQ because we don't want to dump raw binary data to
+ // stdout.
+ EXPECT_TRUE(str2.substr(3) == str1);
+
+ // GCC gives some sort of error if we try to just do stream.str() == str1.
+ string temp = stream.str();
+ EXPECT_TRUE(temp == str1);
+
+ EXPECT_TRUE(message.SerializeAsString() == str1);
+
+}
+
+TEST(MessageTest, SerializeToBrokenOstream) {
+ ofstream out;
+ protobuf_unittest::TestAllTypes message;
+ message.set_optional_int32(123);
+
+ EXPECT_FALSE(message.SerializeToOstream(&out));
+}
+
+TEST(MessageTest, ParseFromFileDescriptor) {
+ string filename = TestSourceDir() +
+ "/google/protobuf/testdata/golden_message";
+ int file = open(filename.c_str(), O_RDONLY | O_BINARY);
+
+ unittest::TestAllTypes message;
+ EXPECT_TRUE(message.ParseFromFileDescriptor(file));
+ TestUtil::ExpectAllFieldsSet(message);
+
+ EXPECT_GE(close(file), 0);
+}
+
+TEST(MessageTest, ParsePackedFromFileDescriptor) {
+ string filename =
+ TestSourceDir() +
+ "/google/protobuf/testdata/golden_packed_fields_message";
+ int file = open(filename.c_str(), O_RDONLY | O_BINARY);
+
+ unittest::TestPackedTypes message;
+ EXPECT_TRUE(message.ParseFromFileDescriptor(file));
+ TestUtil::ExpectPackedFieldsSet(message);
+
+ EXPECT_GE(close(file), 0);
+}
+
+TEST(MessageTest, ParseHelpers) {
+ // TODO(kenton): Test more helpers? They're all two-liners so it seems
+ // like a waste of time.
+ string data;
+
+ {
+ // Set up.
+ protobuf_unittest::TestAllTypes message;
+ TestUtil::SetAllFields(&message);
+ message.SerializeToString(&data);
+ }
+
+ {
+ // Test ParseFromString.
+ protobuf_unittest::TestAllTypes message;
+ EXPECT_TRUE(message.ParseFromString(data));
+ TestUtil::ExpectAllFieldsSet(message);
+ }
+
+ {
+ // Test ParseFromIstream.
+ protobuf_unittest::TestAllTypes message;
+ stringstream stream(data);
+ EXPECT_TRUE(message.ParseFromIstream(&stream));
+ EXPECT_TRUE(stream.eof());
+ TestUtil::ExpectAllFieldsSet(message);
+ }
+
+ {
+ // Test ParseFromBoundedZeroCopyStream.
+ string data_with_junk(data);
+ data_with_junk.append("some junk on the end");
+ io::ArrayInputStream stream(data_with_junk.data(), data_with_junk.size());
+ protobuf_unittest::TestAllTypes message;
+ EXPECT_TRUE(message.ParseFromBoundedZeroCopyStream(&stream, data.size()));
+ TestUtil::ExpectAllFieldsSet(message);
+ }
+
+ {
+ // Test that ParseFromBoundedZeroCopyStream fails (but doesn't crash) if
+ // EOF is reached before the expected number of bytes.
+ io::ArrayInputStream stream(data.data(), data.size());
+ protobuf_unittest::TestAllTypes message;
+ EXPECT_FALSE(
+ message.ParseFromBoundedZeroCopyStream(&stream, data.size() + 1));
+ }
+}
+
+TEST(MessageTest, ParseFailsIfNotInitialized) {
+ unittest::TestRequired message;
+ vector<string> errors;
+
+ {
+ ScopedMemoryLog log;
+ EXPECT_FALSE(message.ParseFromString(""));
+ errors = log.GetMessages(ERROR);
+ }
+
+ ASSERT_EQ(1, errors.size());
+ EXPECT_EQ("Can't parse message of type \"protobuf_unittest.TestRequired\" "
+ "because it is missing required fields: a, b, c",
+ errors[0]);
+}
+
+TEST(MessageTest, BypassInitializationCheckOnParse) {
+ unittest::TestRequired message;
+ io::ArrayInputStream raw_input(NULL, 0);
+ io::CodedInputStream input(&raw_input);
+ EXPECT_TRUE(message.MergePartialFromCodedStream(&input));
+}
+
+TEST(MessageTest, InitializationErrorString) {
+ unittest::TestRequired message;
+ EXPECT_EQ("a, b, c", message.InitializationErrorString());
+}
+
+TEST(MessageTest, DynamicCastToGenerated) {
+ unittest::TestAllTypes test_all_types;
+
+ google::protobuf::Message* test_all_types_pointer = &test_all_types;
+ EXPECT_EQ(&test_all_types,
+ google::protobuf::internal::DynamicCastToGenerated<unittest::TestAllTypes>(
+ test_all_types_pointer));
+ EXPECT_EQ(NULL,
+ google::protobuf::internal::DynamicCastToGenerated<unittest::TestRequired>(
+ test_all_types_pointer));
+
+ const google::protobuf::Message* test_all_types_pointer_const = &test_all_types;
+ EXPECT_EQ(
+ &test_all_types,
+ google::protobuf::internal::DynamicCastToGenerated<const unittest::TestAllTypes>(
+ test_all_types_pointer_const));
+ EXPECT_EQ(
+ NULL,
+ google::protobuf::internal::DynamicCastToGenerated<const unittest::TestRequired>(
+ test_all_types_pointer_const));
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST // death tests do not work on Windows yet.
+
+TEST(MessageTest, SerializeFailsIfNotInitialized) {
+ unittest::TestRequired message;
+ string data;
+ EXPECT_DEBUG_DEATH(EXPECT_TRUE(message.SerializeToString(&data)),
+ "Can't serialize message of type \"protobuf_unittest.TestRequired\" because "
+ "it is missing required fields: a, b, c");
+}
+
+TEST(MessageTest, CheckInitialized) {
+ unittest::TestRequired message;
+ EXPECT_DEATH(message.CheckInitialized(),
+ "Message of type \"protobuf_unittest.TestRequired\" is missing required "
+ "fields: a, b, c");
+}
+
+TEST(MessageTest, CheckOverflow) {
+ unittest::TestAllTypes message;
+ // Create a message with size just over 2GB. This triggers integer overflow
+ // when computing message size.
+ const string data(1024, 'x');
+ Cord one_megabyte;
+ for (int i = 0; i < 1024; i++) {
+ one_megabyte.Append(data);
+ }
+
+ for (int i = 0; i < 2 * 1024 + 1; ++i) {
+ message.add_repeated_cord()->CopyFrom(one_megabyte);
+ }
+
+ Cord serialized;
+ EXPECT_FALSE(message.AppendToCord(&serialized));
+}
+
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+namespace {
+
+class NegativeByteSize : public unittest::TestRequired {
+ public:
+ virtual int ByteSize() const { return -1; }
+};
+
+} // namespace
+
+TEST(MessageTest, SerializationFailsOnNegativeByteSize) {
+ NegativeByteSize message;
+ string string_output;
+ EXPECT_FALSE(message.AppendPartialToString(&string_output));
+
+ io::ArrayOutputStream coded_raw_output(NULL, 100);
+ io::CodedOutputStream coded_output(&coded_raw_output);
+ EXPECT_FALSE(message.SerializePartialToCodedStream(&coded_output));
+}
+
+TEST(MessageTest, BypassInitializationCheckOnSerialize) {
+ unittest::TestRequired message;
+ io::ArrayOutputStream raw_output(NULL, 0);
+ io::CodedOutputStream output(&raw_output);
+ EXPECT_TRUE(message.SerializePartialToCodedStream(&output));
+}
+
+TEST(MessageTest, FindInitializationErrors) {
+ unittest::TestRequired message;
+ vector<string> errors;
+ message.FindInitializationErrors(&errors);
+ ASSERT_EQ(3, errors.size());
+ EXPECT_EQ("a", errors[0]);
+ EXPECT_EQ("b", errors[1]);
+ EXPECT_EQ("c", errors[2]);
+}
+
+TEST(MessageTest, ParseFailsOnInvalidMessageEnd) {
+ unittest::TestAllTypes message;
+
+ // Control case.
+ EXPECT_TRUE(message.ParseFromArray("", 0));
+
+ // The byte is a valid varint, but not a valid tag (zero).
+ EXPECT_FALSE(message.ParseFromArray("\0", 1));
+
+ // The byte is a malformed varint.
+ EXPECT_FALSE(message.ParseFromArray("\200", 1));
+
+ // The byte is an endgroup tag, but we aren't parsing a group.
+ EXPECT_FALSE(message.ParseFromArray("\014", 1));
+}
+
+namespace {
+
+void ExpectMessageMerged(const unittest::TestAllTypes& message) {
+ EXPECT_EQ(3, message.optional_int32());
+ EXPECT_EQ(2, message.optional_int64());
+ EXPECT_EQ("hello", message.optional_string());
+}
+
+void AssignParsingMergeMessages(
+ unittest::TestAllTypes* msg1,
+ unittest::TestAllTypes* msg2,
+ unittest::TestAllTypes* msg3) {
+ msg1->set_optional_int32(1);
+ msg2->set_optional_int64(2);
+ msg3->set_optional_int32(3);
+ msg3->set_optional_string("hello");
+}
+
+} // namespace
+
+// Test that if an optional or required message/group field appears multiple
+// times in the input, they need to be merged.
+TEST(MessageTest, ParsingMerge) {
+ unittest::TestParsingMerge::RepeatedFieldsGenerator generator;
+ unittest::TestAllTypes* msg1;
+ unittest::TestAllTypes* msg2;
+ unittest::TestAllTypes* msg3;
+
+#define ASSIGN_REPEATED_FIELD(FIELD) \
+ msg1 = generator.add_##FIELD(); \
+ msg2 = generator.add_##FIELD(); \
+ msg3 = generator.add_##FIELD(); \
+ AssignParsingMergeMessages(msg1, msg2, msg3)
+
+ ASSIGN_REPEATED_FIELD(field1);
+ ASSIGN_REPEATED_FIELD(field2);
+ ASSIGN_REPEATED_FIELD(field3);
+ ASSIGN_REPEATED_FIELD(ext1);
+ ASSIGN_REPEATED_FIELD(ext2);
+
+#undef ASSIGN_REPEATED_FIELD
+#define ASSIGN_REPEATED_GROUP(FIELD) \
+ msg1 = generator.add_##FIELD()->mutable_field1(); \
+ msg2 = generator.add_##FIELD()->mutable_field1(); \
+ msg3 = generator.add_##FIELD()->mutable_field1(); \
+ AssignParsingMergeMessages(msg1, msg2, msg3)
+
+ ASSIGN_REPEATED_GROUP(group1);
+ ASSIGN_REPEATED_GROUP(group2);
+
+#undef ASSIGN_REPEATED_GROUP
+
+ string buffer;
+ generator.SerializeToString(&buffer);
+ unittest::TestParsingMerge parsing_merge;
+ parsing_merge.ParseFromString(buffer);
+
+ // Required and optional fields should be merged.
+ ExpectMessageMerged(parsing_merge.required_all_types());
+ ExpectMessageMerged(parsing_merge.optional_all_types());
+ ExpectMessageMerged(
+ parsing_merge.optionalgroup().optional_group_all_types());
+ ExpectMessageMerged(
+ parsing_merge.GetExtension(unittest::TestParsingMerge::optional_ext));
+
+ // Repeated fields should not be merged.
+ EXPECT_EQ(3, parsing_merge.repeated_all_types_size());
+ EXPECT_EQ(3, parsing_merge.repeatedgroup_size());
+ EXPECT_EQ(3, parsing_merge.ExtensionSize(
+ unittest::TestParsingMerge::repeated_ext));
+}
+
+TEST(MessageTest, MergeFrom) {
+ unittest::TestAllTypes source;
+ unittest::TestAllTypes dest;
+
+ // Optional fields
+ source.set_optional_int32(1); // only source
+ source.set_optional_int64(2); // both source and dest
+ dest.set_optional_int64(3);
+ dest.set_optional_uint32(4); // only dest
+
+ // Optional fields with defaults
+ source.set_default_int32(13); // only source
+ source.set_default_int64(14); // both source and dest
+ dest.set_default_int64(15);
+ dest.set_default_uint32(16); // only dest
+
+ // Repeated fields
+ source.add_repeated_int32(5); // only source
+ source.add_repeated_int32(6);
+ source.add_repeated_int64(7); // both source and dest
+ source.add_repeated_int64(8);
+ dest.add_repeated_int64(9);
+ dest.add_repeated_int64(10);
+ dest.add_repeated_uint32(11); // only dest
+ dest.add_repeated_uint32(12);
+
+ dest.MergeFrom(source);
+
+ // Optional fields: source overwrites dest if source is specified
+ EXPECT_EQ(1, dest.optional_int32()); // only source: use source
+ EXPECT_EQ(2, dest.optional_int64()); // source and dest: use source
+ EXPECT_EQ(4, dest.optional_uint32()); // only dest: use dest
+ EXPECT_EQ(0, dest.optional_uint64()); // neither: use default
+
+ // Optional fields with defaults
+ EXPECT_EQ(13, dest.default_int32()); // only source: use source
+ EXPECT_EQ(14, dest.default_int64()); // source and dest: use source
+ EXPECT_EQ(16, dest.default_uint32()); // only dest: use dest
+ EXPECT_EQ(44, dest.default_uint64()); // neither: use default
+
+ // Repeated fields: concatenate source onto the end of dest
+ ASSERT_EQ(2, dest.repeated_int32_size());
+ EXPECT_EQ(5, dest.repeated_int32(0));
+ EXPECT_EQ(6, dest.repeated_int32(1));
+ ASSERT_EQ(4, dest.repeated_int64_size());
+ EXPECT_EQ(9, dest.repeated_int64(0));
+ EXPECT_EQ(10, dest.repeated_int64(1));
+ EXPECT_EQ(7, dest.repeated_int64(2));
+ EXPECT_EQ(8, dest.repeated_int64(3));
+ ASSERT_EQ(2, dest.repeated_uint32_size());
+ EXPECT_EQ(11, dest.repeated_uint32(0));
+ EXPECT_EQ(12, dest.repeated_uint32(1));
+ ASSERT_EQ(0, dest.repeated_uint64_size());
+}
+
+TEST(MessageFactoryTest, GeneratedFactoryLookup) {
+ EXPECT_EQ(
+ MessageFactory::generated_factory()->GetPrototype(
+ protobuf_unittest::TestAllTypes::descriptor()),
+ &protobuf_unittest::TestAllTypes::default_instance());
+}
+
+TEST(MessageFactoryTest, GeneratedFactoryUnknownType) {
+ // Construct a new descriptor.
+ DescriptorPool pool;
+ FileDescriptorProto file;
+ file.set_name("foo.proto");
+ file.add_message_type()->set_name("Foo");
+ const Descriptor* descriptor = pool.BuildFile(file)->message_type(0);
+
+ // Trying to construct it should return NULL.
+ EXPECT_TRUE(
+ MessageFactory::generated_factory()->GetPrototype(descriptor) == NULL);
+}
+
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/metadata.h b/third_party/protobuf/3.0.0/src/google/protobuf/metadata.h
new file mode 100644
index 0000000000..fdee150b44
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/metadata.h
@@ -0,0 +1,163 @@
+// 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.
+
+// This header file defines an internal class that encapsulates internal message
+// metadata (Unknown-field set, Arena pointer, ...) and allows its
+// representation to be made more space-efficient via various optimizations.
+//
+// Note that this is distinct from google::protobuf::Metadata, which encapsulates
+// Descriptor and Reflection pointers.
+
+#ifndef GOOGLE_PROTOBUF_METADATA_H__
+#define GOOGLE_PROTOBUF_METADATA_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/unknown_field_set.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// This is the representation for messages that support arena allocation. It
+// uses a tagged pointer to either store the Arena pointer, if there are no
+// unknown fields, or a pointer to a block of memory with both the Arena pointer
+// and the UnknownFieldSet, if there are unknown fields. This optimization
+// allows for "zero-overhead" storage of the Arena pointer, relative to the
+// above baseline implementation.
+//
+// The tagged pointer uses the LSB to disambiguate cases, and uses bit 0 == 0 to
+// indicate an arena pointer and bit 0 == 1 to indicate a UFS+Arena-container
+// pointer.
+class LIBPROTOBUF_EXPORT InternalMetadataWithArena {
+ public:
+ InternalMetadataWithArena() : ptr_(NULL) {}
+ explicit InternalMetadataWithArena(Arena* arena)
+ : ptr_ (arena) {}
+
+ ~InternalMetadataWithArena() {
+ if (have_unknown_fields() && arena() == NULL) {
+ delete PtrValue<Container>();
+ }
+ ptr_ = NULL;
+ }
+
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE const UnknownFieldSet& unknown_fields() const {
+ if (GOOGLE_PREDICT_FALSE(have_unknown_fields())) {
+ return PtrValue<Container>()->unknown_fields_;
+ } else {
+ return *UnknownFieldSet::default_instance();
+ }
+ }
+
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE UnknownFieldSet* mutable_unknown_fields() {
+ if (GOOGLE_PREDICT_TRUE(have_unknown_fields())) {
+ return &PtrValue<Container>()->unknown_fields_;
+ } else {
+ return mutable_unknown_fields_slow();
+ }
+ }
+
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE Arena* arena() const {
+ if (GOOGLE_PREDICT_FALSE(have_unknown_fields())) {
+ return PtrValue<Container>()->arena_;
+ } else {
+ return PtrValue<Arena>();
+ }
+ }
+
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE bool have_unknown_fields() const {
+ return PtrTag() == kTagContainer;
+ }
+
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE void Swap(InternalMetadataWithArena* other) {
+ // Semantics here are that we swap only the unknown fields, not the arena
+ // pointer. We cannot simply swap ptr_ with other->ptr_ because we need to
+ // maintain our own arena ptr. Also, our ptr_ and other's ptr_ may be in
+ // different states (direct arena pointer vs. container with UFS) so we
+ // cannot simply swap ptr_ and then restore the arena pointers. We reuse
+ // UFS's swap implementation instead.
+ if (have_unknown_fields() || other->have_unknown_fields()) {
+ mutable_unknown_fields()->Swap(other->mutable_unknown_fields());
+ }
+ }
+
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE void* raw_arena_ptr() const {
+ return ptr_;
+ }
+
+ private:
+ void* ptr_;
+
+ // Tagged pointer implementation.
+ enum {
+ // ptr_ is an Arena*.
+ kTagArena = 0,
+ // ptr_ is a Container*.
+ kTagContainer = 1,
+ };
+ static const intptr_t kPtrTagMask = 1;
+ static const intptr_t kPtrValueMask = ~kPtrTagMask;
+
+ // Accessors for pointer tag and pointer value.
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE int PtrTag() const {
+ return reinterpret_cast<intptr_t>(ptr_) & kPtrTagMask;
+ }
+
+ template<typename T> T* PtrValue() const {
+ return reinterpret_cast<T*>(
+ reinterpret_cast<intptr_t>(ptr_) & kPtrValueMask);
+ }
+
+ // If ptr_'s tag is kTagContainer, it points to an instance of this struct.
+ struct Container {
+ UnknownFieldSet unknown_fields_;
+ Arena* arena_;
+ };
+
+ GOOGLE_ATTRIBUTE_NOINLINE UnknownFieldSet* mutable_unknown_fields_slow() {
+ Arena* my_arena = arena();
+ Container* container = Arena::Create<Container>(my_arena);
+ ptr_ = reinterpret_cast<void*>(
+ reinterpret_cast<intptr_t>(container) | kTagContainer);
+ container->arena_ = my_arena;
+ return &(container->unknown_fields_);
+ }
+};
+
+// Temporary compatibility typedef. Remove once this is released in components
+// and upb CL is submitted.
+typedef InternalMetadataWithArena InternalMetadata;
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_METADATA_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/no_field_presence_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/no_field_presence_test.cc
new file mode 100644
index 0000000000..bc41beec81
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/no_field_presence_test.cc
@@ -0,0 +1,577 @@
+// 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.
+
+#include <string>
+
+#include <google/protobuf/unittest_no_field_presence.pb.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+
+// Helper: checks that all fields have default (zero/empty) values.
+void CheckDefaultValues(
+ const proto2_nofieldpresence_unittest::TestAllTypes& m) {
+ EXPECT_EQ(0, m.optional_int32());
+ EXPECT_EQ(0, m.optional_int64());
+ EXPECT_EQ(0, m.optional_uint32());
+ EXPECT_EQ(0, m.optional_uint64());
+ EXPECT_EQ(0, m.optional_sint32());
+ EXPECT_EQ(0, m.optional_sint64());
+ EXPECT_EQ(0, m.optional_fixed32());
+ EXPECT_EQ(0, m.optional_fixed64());
+ EXPECT_EQ(0, m.optional_sfixed32());
+ EXPECT_EQ(0, m.optional_sfixed64());
+ EXPECT_EQ(0, m.optional_float());
+ EXPECT_EQ(0, m.optional_double());
+ EXPECT_EQ(false, m.optional_bool());
+ EXPECT_EQ(0, m.optional_string().size());
+ EXPECT_EQ(0, m.optional_bytes().size());
+
+ EXPECT_EQ(false, m.has_optional_nested_message());
+ // accessor for message fields returns default instance when not present
+ EXPECT_EQ(0, m.optional_nested_message().bb());
+ EXPECT_EQ(false, m.has_optional_proto2_message());
+ // Embedded proto2 messages still have proto2 semantics, e.g. non-zero default
+ // values. Here the submessage is not present but its accessor returns the
+ // default instance.
+ EXPECT_EQ(41, m.optional_proto2_message().default_int32());
+ EXPECT_EQ(false, m.has_optional_foreign_message());
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes_NestedEnum_FOO,
+ m.optional_nested_enum());
+ EXPECT_EQ(proto2_nofieldpresence_unittest::FOREIGN_FOO,
+ m.optional_foreign_enum());
+
+
+ EXPECT_EQ(0, m.repeated_int32_size());
+ EXPECT_EQ(0, m.repeated_int64_size());
+ EXPECT_EQ(0, m.repeated_uint32_size());
+ EXPECT_EQ(0, m.repeated_uint64_size());
+ EXPECT_EQ(0, m.repeated_sint32_size());
+ EXPECT_EQ(0, m.repeated_sint64_size());
+ EXPECT_EQ(0, m.repeated_fixed32_size());
+ EXPECT_EQ(0, m.repeated_fixed64_size());
+ EXPECT_EQ(0, m.repeated_sfixed32_size());
+ EXPECT_EQ(0, m.repeated_sfixed64_size());
+ EXPECT_EQ(0, m.repeated_float_size());
+ EXPECT_EQ(0, m.repeated_double_size());
+ EXPECT_EQ(0, m.repeated_bool_size());
+ EXPECT_EQ(0, m.repeated_string_size());
+ EXPECT_EQ(0, m.repeated_bytes_size());
+ EXPECT_EQ(0, m.repeated_nested_message_size());
+ EXPECT_EQ(0, m.repeated_foreign_message_size());
+ EXPECT_EQ(0, m.repeated_proto2_message_size());
+ EXPECT_EQ(0, m.repeated_nested_enum_size());
+ EXPECT_EQ(0, m.repeated_foreign_enum_size());
+ EXPECT_EQ(0, m.repeated_lazy_message_size());
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes::ONEOF_FIELD_NOT_SET,
+ m.oneof_field_case());
+}
+
+void FillValues(proto2_nofieldpresence_unittest::TestAllTypes* m) {
+ m->set_optional_int32(100);
+ m->set_optional_int64(101);
+ m->set_optional_uint32(102);
+ m->set_optional_uint64(103);
+ m->set_optional_sint32(104);
+ m->set_optional_sint64(105);
+ m->set_optional_fixed32(106);
+ m->set_optional_fixed64(107);
+ m->set_optional_sfixed32(108);
+ m->set_optional_sfixed64(109);
+ m->set_optional_float(110.0);
+ m->set_optional_double(111.0);
+ m->set_optional_bool(true);
+ m->set_optional_string("asdf");
+ m->set_optional_bytes("jkl;");
+ m->mutable_optional_nested_message()->set_bb(42);
+ m->mutable_optional_foreign_message()->set_c(43);
+ m->mutable_optional_proto2_message()->set_optional_int32(44);
+ m->set_optional_nested_enum(
+ proto2_nofieldpresence_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->set_optional_foreign_enum(
+ proto2_nofieldpresence_unittest::FOREIGN_BAZ);
+ m->mutable_optional_lazy_message()->set_bb(45);
+ m->add_repeated_int32(100);
+ m->add_repeated_int64(101);
+ m->add_repeated_uint32(102);
+ m->add_repeated_uint64(103);
+ m->add_repeated_sint32(104);
+ m->add_repeated_sint64(105);
+ m->add_repeated_fixed32(106);
+ m->add_repeated_fixed64(107);
+ m->add_repeated_sfixed32(108);
+ m->add_repeated_sfixed64(109);
+ m->add_repeated_float(110.0);
+ m->add_repeated_double(111.0);
+ m->add_repeated_bool(true);
+ m->add_repeated_string("asdf");
+ m->add_repeated_bytes("jkl;");
+ m->add_repeated_nested_message()->set_bb(46);
+ m->add_repeated_foreign_message()->set_c(47);
+ m->add_repeated_proto2_message()->set_optional_int32(48);
+ m->add_repeated_nested_enum(
+ proto2_nofieldpresence_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->add_repeated_foreign_enum(
+ proto2_nofieldpresence_unittest::FOREIGN_BAZ);
+ m->add_repeated_lazy_message()->set_bb(49);
+
+ m->set_oneof_uint32(1);
+ m->mutable_oneof_nested_message()->set_bb(50);
+ m->set_oneof_string("test"); // only this one remains set
+}
+
+void CheckNonDefaultValues(
+const proto2_nofieldpresence_unittest::TestAllTypes& m) {
+ EXPECT_EQ(100, m.optional_int32());
+ EXPECT_EQ(101, m.optional_int64());
+ EXPECT_EQ(102, m.optional_uint32());
+ EXPECT_EQ(103, m.optional_uint64());
+ EXPECT_EQ(104, m.optional_sint32());
+ EXPECT_EQ(105, m.optional_sint64());
+ EXPECT_EQ(106, m.optional_fixed32());
+ EXPECT_EQ(107, m.optional_fixed64());
+ EXPECT_EQ(108, m.optional_sfixed32());
+ EXPECT_EQ(109, m.optional_sfixed64());
+ EXPECT_EQ(110.0, m.optional_float());
+ EXPECT_EQ(111.0, m.optional_double());
+ EXPECT_EQ(true, m.optional_bool());
+ EXPECT_EQ("asdf", m.optional_string());
+ EXPECT_EQ("jkl;", m.optional_bytes());
+ EXPECT_EQ(true, m.has_optional_nested_message());
+ EXPECT_EQ(42, m.optional_nested_message().bb());
+ EXPECT_EQ(true, m.has_optional_foreign_message());
+ EXPECT_EQ(43, m.optional_foreign_message().c());
+ EXPECT_EQ(true, m.has_optional_proto2_message());
+ EXPECT_EQ(44, m.optional_proto2_message().optional_int32());
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.optional_nested_enum());
+ EXPECT_EQ(proto2_nofieldpresence_unittest::FOREIGN_BAZ,
+ m.optional_foreign_enum());
+ EXPECT_EQ(true, m.has_optional_lazy_message());
+ EXPECT_EQ(45, m.optional_lazy_message().bb());
+
+ EXPECT_EQ(1, m.repeated_int32_size());
+ EXPECT_EQ(100, m.repeated_int32(0));
+ EXPECT_EQ(1, m.repeated_int64_size());
+ EXPECT_EQ(101, m.repeated_int64(0));
+ EXPECT_EQ(1, m.repeated_uint32_size());
+ EXPECT_EQ(102, m.repeated_uint32(0));
+ EXPECT_EQ(1, m.repeated_uint64_size());
+ EXPECT_EQ(103, m.repeated_uint64(0));
+ EXPECT_EQ(1, m.repeated_sint32_size());
+ EXPECT_EQ(104, m.repeated_sint32(0));
+ EXPECT_EQ(1, m.repeated_sint64_size());
+ EXPECT_EQ(105, m.repeated_sint64(0));
+ EXPECT_EQ(1, m.repeated_fixed32_size());
+ EXPECT_EQ(106, m.repeated_fixed32(0));
+ EXPECT_EQ(1, m.repeated_fixed64_size());
+ EXPECT_EQ(107, m.repeated_fixed64(0));
+ EXPECT_EQ(1, m.repeated_sfixed32_size());
+ EXPECT_EQ(108, m.repeated_sfixed32(0));
+ EXPECT_EQ(1, m.repeated_sfixed64_size());
+ EXPECT_EQ(109, m.repeated_sfixed64(0));
+ EXPECT_EQ(1, m.repeated_float_size());
+ EXPECT_EQ(110.0, m.repeated_float(0));
+ EXPECT_EQ(1, m.repeated_double_size());
+ EXPECT_EQ(111.0, m.repeated_double(0));
+ EXPECT_EQ(1, m.repeated_bool_size());
+ EXPECT_EQ(true, m.repeated_bool(0));
+ EXPECT_EQ(1, m.repeated_string_size());
+ EXPECT_EQ("asdf", m.repeated_string(0));
+ EXPECT_EQ(1, m.repeated_bytes_size());
+ EXPECT_EQ("jkl;", m.repeated_bytes(0));
+ EXPECT_EQ(1, m.repeated_nested_message_size());
+ EXPECT_EQ(46, m.repeated_nested_message(0).bb());
+ EXPECT_EQ(1, m.repeated_foreign_message_size());
+ EXPECT_EQ(47, m.repeated_foreign_message(0).c());
+ EXPECT_EQ(1, m.repeated_proto2_message_size());
+ EXPECT_EQ(48, m.repeated_proto2_message(0).optional_int32());
+ EXPECT_EQ(1, m.repeated_nested_enum_size());
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.repeated_nested_enum(0));
+ EXPECT_EQ(1, m.repeated_foreign_enum_size());
+ EXPECT_EQ(proto2_nofieldpresence_unittest::FOREIGN_BAZ,
+ m.repeated_foreign_enum(0));
+ EXPECT_EQ(1, m.repeated_lazy_message_size());
+ EXPECT_EQ(49, m.repeated_lazy_message(0).bb());
+
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes::kOneofString,
+ m.oneof_field_case());
+ EXPECT_EQ("test", m.oneof_string());
+}
+
+TEST(NoFieldPresenceTest, BasicMessageTest) {
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+ // Check default values, fill all fields, check values. We just want to
+ // exercise the basic getters/setter paths here to make sure no
+ // field-presence-related changes broke these.
+ CheckDefaultValues(message);
+ FillValues(&message);
+ CheckNonDefaultValues(message);
+
+ // Clear() should be equivalent to getting a freshly-constructed message.
+ message.Clear();
+ CheckDefaultValues(message);
+}
+
+TEST(NoFieldPresenceTest, MessageFieldPresenceTest) {
+ // check that presence still works properly for message fields.
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+ EXPECT_EQ(false, message.has_optional_nested_message());
+ // Getter should fetch default instance, and not cause the field to become
+ // present.
+ EXPECT_EQ(0, message.optional_nested_message().bb());
+ EXPECT_EQ(false, message.has_optional_nested_message());
+ message.mutable_optional_nested_message()->set_bb(42);
+ EXPECT_EQ(true, message.has_optional_nested_message());
+ message.clear_optional_nested_message();
+ EXPECT_EQ(false, message.has_optional_nested_message());
+
+ // Likewise for a lazy message field.
+ EXPECT_EQ(false, message.has_optional_lazy_message());
+ // Getter should fetch default instance, and not cause the field to become
+ // present.
+ EXPECT_EQ(0, message.optional_lazy_message().bb());
+ EXPECT_EQ(false, message.has_optional_lazy_message());
+ message.mutable_optional_lazy_message()->set_bb(42);
+ EXPECT_EQ(true, message.has_optional_lazy_message());
+ message.clear_optional_lazy_message();
+ EXPECT_EQ(false, message.has_optional_lazy_message());
+
+ // Test field presence of a message field on the default instance.
+ EXPECT_EQ(false, proto2_nofieldpresence_unittest::TestAllTypes::
+ default_instance().has_optional_nested_message());
+}
+
+TEST(NoFieldPresenceTest, ReflectionHasFieldTest) {
+ // check that HasField reports true on all scalar fields. Check that it
+ // behaves properly for message fields.
+
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+ const google::protobuf::Reflection* r = message.GetReflection();
+ const google::protobuf::Descriptor* desc = message.GetDescriptor();
+
+ // Check initial state: scalars not present (due to need to be consistent with
+ // MergeFrom()), message fields not present, oneofs not present.
+ for (int i = 0; i < desc->field_count(); i++) {
+ const google::protobuf::FieldDescriptor* field = desc->field(i);
+ if (field->is_repeated()) continue;
+ EXPECT_EQ(false, r->HasField(message, field));
+ }
+
+ // Test field presence of a message field on the default instance.
+ const google::protobuf::FieldDescriptor* msg_field =
+ desc->FindFieldByName("optional_nested_message");
+ EXPECT_EQ(false, r->HasField(
+ proto2_nofieldpresence_unittest::TestAllTypes::
+ default_instance(), msg_field));
+
+ // Fill all fields, expect everything to report true (check oneofs below).
+ FillValues(&message);
+ for (int i = 0; i < desc->field_count(); i++) {
+ const google::protobuf::FieldDescriptor* field = desc->field(i);
+ if (field->is_repeated() || field->containing_oneof()) {
+ continue;
+ }
+ if (field->options().ctype() != google::protobuf::FieldOptions::STRING) {
+ continue;
+ }
+ EXPECT_EQ(true, r->HasField(message, field));
+ }
+
+ message.Clear();
+
+ // Check zero/empty-means-not-present semantics.
+ const google::protobuf::FieldDescriptor* field_int32 = desc->FindFieldByName(
+ "optional_int32");
+ const google::protobuf::FieldDescriptor* field_double = desc->FindFieldByName(
+ "optional_double");
+ const google::protobuf::FieldDescriptor* field_string = desc->FindFieldByName(
+ "optional_string");
+
+ EXPECT_EQ(false, r->HasField(message, field_int32));
+ EXPECT_EQ(false, r->HasField(message, field_double));
+ EXPECT_EQ(false, r->HasField(message, field_string));
+
+ message.set_optional_int32(42);
+ EXPECT_EQ(true, r->HasField(message, field_int32));
+ message.set_optional_int32(0);
+ EXPECT_EQ(false, r->HasField(message, field_int32));
+
+ message.set_optional_double(42.0);
+ EXPECT_EQ(true, r->HasField(message, field_double));
+ message.set_optional_double(0.0);
+ EXPECT_EQ(false, r->HasField(message, field_double));
+
+ message.set_optional_string("test");
+ EXPECT_EQ(true, r->HasField(message, field_string));
+ message.set_optional_string("");
+ EXPECT_EQ(false, r->HasField(message, field_string));
+}
+
+TEST(NoFieldPresenceTest, ReflectionClearFieldTest) {
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+
+ const google::protobuf::Reflection* r = message.GetReflection();
+ const google::protobuf::Descriptor* desc = message.GetDescriptor();
+
+ const google::protobuf::FieldDescriptor* field_int32 = desc->FindFieldByName(
+ "optional_int32");
+ const google::protobuf::FieldDescriptor* field_double = desc->FindFieldByName(
+ "optional_double");
+ const google::protobuf::FieldDescriptor* field_string = desc->FindFieldByName(
+ "optional_string");
+ const google::protobuf::FieldDescriptor* field_message = desc->FindFieldByName(
+ "optional_nested_message");
+ const google::protobuf::FieldDescriptor* field_lazy = desc->FindFieldByName(
+ "optional_lazy_message");
+
+ message.set_optional_int32(42);
+ r->ClearField(&message, field_int32);
+ EXPECT_EQ(0, message.optional_int32());
+
+ message.set_optional_double(42.0);
+ r->ClearField(&message, field_double);
+ EXPECT_EQ(0.0, message.optional_double());
+
+ message.set_optional_string("test");
+ r->ClearField(&message, field_string);
+ EXPECT_EQ("", message.optional_string());
+
+ message.mutable_optional_nested_message()->set_bb(1234);
+ r->ClearField(&message, field_message);
+ EXPECT_FALSE(message.has_optional_nested_message());
+ EXPECT_EQ(0, message.optional_nested_message().bb());
+
+ message.mutable_optional_lazy_message()->set_bb(42);
+ r->ClearField(&message, field_lazy);
+ EXPECT_FALSE(message.has_optional_lazy_message());
+ EXPECT_EQ(0, message.optional_lazy_message().bb());
+}
+
+TEST(NoFieldPresenceTest, HasFieldOneofsTest) {
+ // check that HasField behaves properly for oneofs.
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+
+ const google::protobuf::Reflection* r = message.GetReflection();
+ const google::protobuf::Descriptor* desc = message.GetDescriptor();
+ const google::protobuf::FieldDescriptor* desc_oneof_uint32 =
+ desc->FindFieldByName("oneof_uint32");
+ const google::protobuf::FieldDescriptor* desc_oneof_nested_message =
+ desc->FindFieldByName("oneof_nested_message");
+ const google::protobuf::FieldDescriptor* desc_oneof_string =
+ desc->FindFieldByName("oneof_string");
+ GOOGLE_CHECK_NOTNULL(desc_oneof_uint32);
+ GOOGLE_CHECK_NOTNULL(desc_oneof_nested_message);
+ GOOGLE_CHECK_NOTNULL(desc_oneof_string);
+
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_uint32));
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_nested_message));
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_string));
+
+ message.set_oneof_string("test");
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_uint32));
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_nested_message));
+ EXPECT_EQ(true, r->HasField(message, desc_oneof_string));
+ message.mutable_oneof_nested_message()->set_bb(42);
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_uint32));
+ EXPECT_EQ(true, r->HasField(message, desc_oneof_nested_message));
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_string));
+
+ message.Clear();
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_uint32));
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_nested_message));
+ EXPECT_EQ(false, r->HasField(message, desc_oneof_string));
+}
+
+TEST(NoFieldPresenceTest, DontSerializeDefaultValuesTest) {
+ // check that serialized data contains only non-zero numeric fields/non-empty
+ // string/byte fields.
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+ string output;
+
+ // All default values -> no output.
+ message.SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+
+ // Zero values -> still no output.
+ message.set_optional_int32(0);
+ message.set_optional_int64(0);
+ message.set_optional_uint32(0);
+ message.set_optional_uint64(0);
+ message.set_optional_sint32(0);
+ message.set_optional_sint64(0);
+ message.set_optional_fixed32(0);
+ message.set_optional_fixed64(0);
+ message.set_optional_sfixed32(0);
+ message.set_optional_sfixed64(0);
+ message.set_optional_float(0);
+ message.set_optional_double(0);
+ message.set_optional_bool(0);
+ message.set_optional_string("");
+ message.set_optional_bytes("");
+ message.set_optional_nested_enum(
+ proto2_nofieldpresence_unittest::TestAllTypes_NestedEnum_FOO); // first enum entry
+ message.set_optional_foreign_enum(
+ proto2_nofieldpresence_unittest::FOREIGN_FOO); // first enum entry
+
+ message.SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+
+ message.set_optional_int32(1);
+ message.SerializeToString(&output);
+ EXPECT_EQ(2, output.size());
+ EXPECT_EQ("\x08\x01", output);
+
+ message.set_optional_int32(0);
+ message.SerializeToString(&output);
+ EXPECT_EQ(0, output.size());
+}
+
+TEST(NoFieldPresenceTest, MergeFromIfNonzeroTest) {
+ // check that MergeFrom copies if nonzero/nondefault only.
+ proto2_nofieldpresence_unittest::TestAllTypes source;
+ proto2_nofieldpresence_unittest::TestAllTypes dest;
+
+ dest.set_optional_int32(42);
+ dest.set_optional_string("test");
+ source.set_optional_int32(0);
+ source.set_optional_string("");
+ // MergeFrom() copies only if present in serialization, i.e., non-zero.
+ dest.MergeFrom(source);
+ EXPECT_EQ(42, dest.optional_int32());
+ EXPECT_EQ("test", dest.optional_string());
+
+ source.set_optional_int32(84);
+ source.set_optional_string("test2");
+ dest.MergeFrom(source);
+ EXPECT_EQ(84, dest.optional_int32());
+ EXPECT_EQ("test2", dest.optional_string());
+}
+
+TEST(NoFieldPresenceTest, IsInitializedTest) {
+ // Check that IsInitialized works properly.
+ proto2_nofieldpresence_unittest::TestProto2Required message;
+
+ EXPECT_EQ(true, message.IsInitialized());
+ message.mutable_proto2()->set_a(1);
+ EXPECT_EQ(false, message.IsInitialized());
+ message.mutable_proto2()->set_b(1);
+ EXPECT_EQ(false, message.IsInitialized());
+ message.mutable_proto2()->set_c(1);
+ EXPECT_EQ(true, message.IsInitialized());
+}
+
+TEST(NoFieldPresenceTest, LazyMessageFieldHasBit) {
+ // Check that has-bit interaction with lazy message works (has-bit before and
+ // after lazy decode).
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+ const google::protobuf::Reflection* r = message.GetReflection();
+ const google::protobuf::Descriptor* desc = message.GetDescriptor();
+ const google::protobuf::FieldDescriptor* field = desc->FindFieldByName(
+ "optional_lazy_message");
+ GOOGLE_CHECK_NOTNULL(field);
+
+ EXPECT_EQ(false, message.has_optional_lazy_message());
+ EXPECT_EQ(false, r->HasField(message, field));
+
+ message.mutable_optional_lazy_message()->set_bb(42);
+ EXPECT_EQ(true, message.has_optional_lazy_message());
+ EXPECT_EQ(true, r->HasField(message, field));
+
+ // Serialize and parse with a new message object so that lazy field on new
+ // object is in unparsed state.
+ string output;
+ message.SerializeToString(&output);
+ proto2_nofieldpresence_unittest::TestAllTypes message2;
+ message2.ParseFromString(output);
+
+ EXPECT_EQ(true, message2.has_optional_lazy_message());
+ EXPECT_EQ(true, r->HasField(message2, field));
+
+ // Access field to force lazy parse.
+ EXPECT_EQ(42, message.optional_lazy_message().bb());
+ EXPECT_EQ(true, message2.has_optional_lazy_message());
+ EXPECT_EQ(true, r->HasField(message2, field));
+}
+
+TEST(NoFieldPresenceTest, OneofPresence) {
+ proto2_nofieldpresence_unittest::TestAllTypes message;
+ // oneof fields still have field presence -- ensure that this goes on the wire
+ // even though its value is the empty string.
+ message.set_oneof_string("");
+ string serialized;
+ message.SerializeToString(&serialized);
+ // Tag: 113 --> tag is (113 << 3) | 2 (length delimited) = 906
+ // varint: 0x8a 0x07
+ // Length: 0x00
+ EXPECT_EQ(3, serialized.size());
+ EXPECT_EQ(static_cast<char>(0x8a), serialized.at(0));
+ EXPECT_EQ(static_cast<char>(0x07), serialized.at(1));
+ EXPECT_EQ(static_cast<char>(0x00), serialized.at(2));
+
+ message.Clear();
+ EXPECT_TRUE(message.ParseFromString(serialized));
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes::kOneofString,
+ message.oneof_field_case());
+
+ // Also test int32 and enum fields.
+ message.Clear();
+ message.set_oneof_uint32(0); // would not go on wire if ordinary field.
+ message.SerializeToString(&serialized);
+ EXPECT_EQ(3, serialized.size());
+ EXPECT_TRUE(message.ParseFromString(serialized));
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes::kOneofUint32,
+ message.oneof_field_case());
+
+ message.Clear();
+ message.set_oneof_enum(proto2_nofieldpresence_unittest::
+ TestAllTypes_NestedEnum_FOO); // default value.
+ message.SerializeToString(&serialized);
+ EXPECT_EQ(3, serialized.size());
+ EXPECT_TRUE(message.ParseFromString(serialized));
+ EXPECT_EQ(proto2_nofieldpresence_unittest::TestAllTypes::kOneofEnum,
+ message.oneof_field_case());
+
+ message.Clear();
+ message.set_oneof_string("test");
+ message.clear_oneof_string();
+ EXPECT_EQ(0, message.ByteSize());
+}
+
+} // namespace
+} // namespace protobuf
+
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/package_info.h b/third_party/protobuf/3.0.0/src/google/protobuf/package_info.h
new file mode 100644
index 0000000000..935e96396d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/package_info.h
@@ -0,0 +1,64 @@
+// 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 exists solely to document the google::protobuf namespace.
+// It is not compiled into anything, but it may be read by an automated
+// documentation generator.
+
+namespace google {
+
+// Core components of the Protocol Buffers runtime library.
+//
+// The files in this package represent the core of the Protocol Buffer
+// system. All of them are part of the libprotobuf library.
+//
+// A note on thread-safety:
+//
+// Thread-safety in the Protocol Buffer library follows a simple rule:
+// unless explicitly noted otherwise, it is always safe to use an object
+// from multiple threads simultaneously as long as the object is declared
+// const in all threads (or, it is only used in ways that would be allowed
+// if it were declared const). However, if an object is accessed in one
+// thread in a way that would not be allowed if it were const, then it is
+// not safe to access that object in any other thread simultaneously.
+//
+// Put simply, read-only access to an object can happen in multiple threads
+// simultaneously, but write access can only happen in a single thread at
+// a time.
+//
+// The implementation does contain some "const" methods which actually modify
+// the object behind the scenes -- e.g., to cache results -- but in these cases
+// mutex locking is used to make the access thread-safe.
+namespace protobuf {}
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/preserve_unknown_enum_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/preserve_unknown_enum_test.cc
new file mode 100644
index 0000000000..1673e8afae
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/preserve_unknown_enum_test.cc
@@ -0,0 +1,289 @@
+// 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.
+
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_preserve_unknown_enum.pb.h>
+#include <google/protobuf/unittest_preserve_unknown_enum2.pb.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/descriptor.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+
+void FillMessage(
+ proto3_preserve_unknown_enum_unittest::MyMessagePlusExtra* message) {
+ message->set_e(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA);
+ message->add_repeated_e(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA);
+ message->add_repeated_packed_e(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA);
+ message->add_repeated_packed_unexpected_e(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA);
+ message->set_oneof_e_1(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA);
+}
+
+void CheckMessage(
+ const proto3_preserve_unknown_enum_unittest::MyMessagePlusExtra& message) {
+ EXPECT_EQ(proto3_preserve_unknown_enum_unittest::E_EXTRA,
+ message.e());
+ EXPECT_EQ(1, message.repeated_e_size());
+ EXPECT_EQ(proto3_preserve_unknown_enum_unittest::E_EXTRA,
+ message.repeated_e(0));
+ EXPECT_EQ(1, message.repeated_packed_e_size());
+ EXPECT_EQ(proto3_preserve_unknown_enum_unittest::E_EXTRA,
+ message.repeated_packed_e(0));
+ EXPECT_EQ(1, message.repeated_packed_unexpected_e_size());
+ EXPECT_EQ(proto3_preserve_unknown_enum_unittest::E_EXTRA,
+ message.repeated_packed_unexpected_e(0));
+ EXPECT_EQ(proto3_preserve_unknown_enum_unittest::E_EXTRA,
+ message.oneof_e_1());
+}
+
+void CheckMessage(
+ const proto3_preserve_unknown_enum_unittest::MyMessage& message) {
+ EXPECT_EQ(static_cast<int>(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA),
+ static_cast<int>(message.e()));
+ EXPECT_EQ(1, message.repeated_e_size());
+ EXPECT_EQ(static_cast<int>(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA),
+ static_cast<int>(message.repeated_e(0)));
+ EXPECT_EQ(1, message.repeated_packed_e_size());
+ EXPECT_EQ(static_cast<int>(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA),
+ static_cast<int>(message.repeated_packed_e(0)));
+ EXPECT_EQ(1, message.repeated_packed_unexpected_e_size());
+ EXPECT_EQ(static_cast<int>(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA),
+ static_cast<int>(message.repeated_packed_unexpected_e(0)));
+ EXPECT_EQ(static_cast<int>(
+ proto3_preserve_unknown_enum_unittest::E_EXTRA),
+ static_cast<int>(message.oneof_e_1()));
+}
+
+} // anonymous namespace
+
+// Test that parsing preserves an unknown value in the enum field and does not
+// punt it to the UnknownFieldSet.
+TEST(PreserveUnknownEnumTest, PreserveParseAndSerialize) {
+ proto3_preserve_unknown_enum_unittest::MyMessagePlusExtra orig_message;
+ FillMessage(&orig_message);
+ string serialized;
+ orig_message.SerializeToString(&serialized);
+
+ proto3_preserve_unknown_enum_unittest::MyMessage message;
+ EXPECT_EQ(true, message.ParseFromString(serialized));
+ CheckMessage(message);
+
+ serialized.clear();
+ message.SerializeToString(&serialized);
+ EXPECT_EQ(true, orig_message.ParseFromString(serialized));
+ CheckMessage(orig_message);
+}
+
+// Test that reflection based implementation also keeps unknown enum values and
+// doesn't put them into UnknownFieldSet.
+TEST(PreserveUnknownEnumTest, PreserveParseAndSerializeDynamicMessage) {
+ proto3_preserve_unknown_enum_unittest::MyMessagePlusExtra orig_message;
+ FillMessage(&orig_message);
+ string serialized = orig_message.SerializeAsString();
+
+ google::protobuf::DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<google::protobuf::Message> message(factory.GetPrototype(
+ proto3_preserve_unknown_enum_unittest::MyMessage::descriptor())->New());
+ EXPECT_EQ(true, message->ParseFromString(serialized));
+ message->DiscardUnknownFields();
+
+ serialized = message->SerializeAsString();
+ EXPECT_EQ(true, orig_message.ParseFromString(serialized));
+ CheckMessage(orig_message);
+}
+
+// Test that for proto2 messages, unknown values are in unknown fields.
+TEST(PreserveUnknownEnumTest, Proto2HidesUnknownValues) {
+ proto3_preserve_unknown_enum_unittest::MyMessagePlusExtra orig_message;
+ FillMessage(&orig_message);
+
+ string serialized;
+ orig_message.SerializeToString(&serialized);
+
+ proto2_preserve_unknown_enum_unittest::MyMessage message;
+ EXPECT_EQ(true, message.ParseFromString(serialized));
+ // The intermediate message has everything in its "unknown fields".
+ proto2_preserve_unknown_enum_unittest::MyMessage message2 = message;
+ message2.DiscardUnknownFields();
+ EXPECT_EQ(0, message2.ByteSize());
+
+ // But when we pass it to the correct structure, all values are there.
+ serialized.clear();
+ message.SerializeToString(&serialized);
+ EXPECT_EQ(true, orig_message.ParseFromString(serialized));
+ CheckMessage(orig_message);
+}
+
+// Same as before, for a dynamic message.
+TEST(PreserveUnknownEnumTest, DynamicProto2HidesUnknownValues) {
+ proto3_preserve_unknown_enum_unittest::MyMessagePlusExtra orig_message;
+ FillMessage(&orig_message);
+
+ string serialized;
+ orig_message.SerializeToString(&serialized);
+
+ google::protobuf::DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<google::protobuf::Message> message(factory.GetPrototype(
+ proto2_preserve_unknown_enum_unittest::MyMessage::descriptor())->New());
+ EXPECT_EQ(true, message->ParseFromString(serialized));
+ // The intermediate message has everything in its "unknown fields".
+ proto2_preserve_unknown_enum_unittest::MyMessage message2;
+ message2.CopyFrom(*message);
+ message2.DiscardUnknownFields();
+ EXPECT_EQ(0, message2.ByteSize());
+
+ // But when we pass it to the correct structure, all values are there.
+ serialized.clear();
+ message->SerializeToString(&serialized);
+ EXPECT_EQ(true, orig_message.ParseFromString(serialized));
+ CheckMessage(orig_message);
+}
+
+// Test that reflection provides EnumValueDescriptors for unknown values.
+TEST(PreserveUnknownEnumTest, DynamicEnumValueDescriptors) {
+ proto3_preserve_unknown_enum_unittest::MyMessagePlusExtra orig_message;
+ FillMessage(&orig_message);
+ string serialized;
+ orig_message.SerializeToString(&serialized);
+
+ proto3_preserve_unknown_enum_unittest::MyMessage message;
+ EXPECT_EQ(true, message.ParseFromString(serialized));
+ CheckMessage(message);
+
+ const google::protobuf::Reflection* r = message.GetReflection();
+ const google::protobuf::Descriptor* d = message.GetDescriptor();
+ const google::protobuf::FieldDescriptor* field = d->FindFieldByName("e");
+
+ // This should dynamically create an EnumValueDescriptor.
+ const google::protobuf::EnumValueDescriptor* enum_value = r->GetEnum(message, field);
+ EXPECT_EQ(enum_value->number(),
+ static_cast<int>(proto3_preserve_unknown_enum_unittest::E_EXTRA));
+
+ // Fetching value for a second time should return the same pointer.
+ const google::protobuf::EnumValueDescriptor* enum_value_second =
+ r->GetEnum(message, field);
+ EXPECT_EQ(enum_value, enum_value_second);
+
+ // Check the repeated case too.
+ const google::protobuf::FieldDescriptor* repeated_field =
+ d->FindFieldByName("repeated_e");
+ enum_value = r->GetRepeatedEnum(message, repeated_field, 0);
+ EXPECT_EQ(enum_value->number(),
+ static_cast<int>(proto3_preserve_unknown_enum_unittest::E_EXTRA));
+ // Should reuse the same EnumValueDescriptor, even for a different field.
+ EXPECT_EQ(enum_value, enum_value_second);
+
+ // We should be able to use the returned value descriptor to set a value on
+ // another message.
+ google::protobuf::Message* m = message.New();
+ r->SetEnum(m, field, enum_value);
+ EXPECT_EQ(enum_value, r->GetEnum(*m, field));
+ delete m;
+}
+
+// Test that the new integer-based enum reflection API works.
+TEST(PreserveUnknownEnumTest, IntegerEnumReflectionAPI) {
+ proto3_preserve_unknown_enum_unittest::MyMessage message;
+ const google::protobuf::Reflection* r = message.GetReflection();
+ const google::protobuf::Descriptor* d = message.GetDescriptor();
+
+ const google::protobuf::FieldDescriptor* singular_field = d->FindFieldByName("e");
+ const google::protobuf::FieldDescriptor* repeated_field =
+ d->FindFieldByName("repeated_e");
+
+ r->SetEnumValue(&message, singular_field, 42);
+ EXPECT_EQ(42, r->GetEnumValue(message, singular_field));
+ r->AddEnumValue(&message, repeated_field, 42);
+ r->AddEnumValue(&message, repeated_field, 42);
+ EXPECT_EQ(42, r->GetRepeatedEnumValue(message, repeated_field, 0));
+ r->SetRepeatedEnumValue(&message, repeated_field, 1, 84);
+ EXPECT_EQ(84, r->GetRepeatedEnumValue(message, repeated_field, 1));
+ const google::protobuf::EnumValueDescriptor* enum_value = r->GetEnum(message,
+ singular_field);
+ EXPECT_EQ(42, enum_value->number());
+}
+
+// Test that the EnumValue API works properly for proto2 messages as well.
+TEST(PreserveUnknownEnumTest, Proto2CatchesUnknownValues) {
+ protobuf_unittest::TestAllTypes message; // proto2 message
+ const google::protobuf::Reflection* r = message.GetReflection();
+ const google::protobuf::Descriptor* d = message.GetDescriptor();
+ const google::protobuf::FieldDescriptor* repeated_field =
+ d->FindFieldByName("repeated_nested_enum");
+ // Add one element to the repeated field so that we can test
+ // SetRepeatedEnumValue.
+ const google::protobuf::EnumValueDescriptor* enum_value =
+ repeated_field->enum_type()->FindValueByName("BAR");
+ EXPECT_TRUE(enum_value != NULL);
+ r->AddEnum(&message, repeated_field, enum_value);
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+ const google::protobuf::FieldDescriptor* singular_field =
+ d->FindFieldByName("optional_nested_enum");
+ // Enum-field integer-based setters GOOGLE_DCHECK-fail on invalid values, in order to
+ // remain consistent with proto2 generated code.
+ EXPECT_DEBUG_DEATH({
+ r->SetEnumValue(&message, singular_field, 4242);
+ r->GetEnum(message, singular_field)->number();
+ }, "SetEnumValue accepts only valid integer values");
+ EXPECT_DEBUG_DEATH({
+ r->SetRepeatedEnumValue(&message, repeated_field, 0, 4242);
+ r->GetRepeatedEnum(message, repeated_field, 0);
+ }, "SetRepeatedEnumValue accepts only valid integer values");
+ EXPECT_DEBUG_DEATH({
+ r->AddEnumValue(&message, repeated_field, 4242);
+ r->GetRepeatedEnum(message, repeated_field, 1);
+ }, "AddEnumValue accepts only valid integer values");
+#endif // PROTOBUF_HAS_DEATH_TEST
+}
+
+TEST(PreserveUnknownEnumTest, SupportsUnknownEnumValuesAPI) {
+ protobuf_unittest::TestAllTypes proto2_message;
+ proto3_preserve_unknown_enum_unittest::MyMessage new_message;
+
+ const google::protobuf::Reflection* proto2_reflection = proto2_message.GetReflection();
+ const google::protobuf::Reflection* new_reflection = new_message.GetReflection();
+
+ EXPECT_FALSE(proto2_reflection->SupportsUnknownEnumValues());
+ EXPECT_TRUE(new_reflection->SupportsUnknownEnumValues());
+}
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_lite_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_lite_unittest.cc
new file mode 100644
index 0000000000..0f18c027e8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_lite_unittest.cc
@@ -0,0 +1,164 @@
+// 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.
+
+#include <string>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_proto3_arena_lite.pb.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+using proto3_arena_lite_unittest::TestAllTypes;
+
+namespace protobuf {
+namespace {
+// We selectively set/check a few representative fields rather than all fields
+// as this test is only expected to cover the basics of arena support.
+void SetAllFields(TestAllTypes* m) {
+ m->set_optional_int32(100);
+ m->set_optional_string("asdf");
+ m->set_optional_bytes("jkl;");
+ m->mutable_optional_nested_message()->set_bb(42);
+ m->mutable_optional_foreign_message()->set_c(43);
+ m->set_optional_nested_enum(
+ proto3_arena_lite_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->set_optional_foreign_enum(
+ proto3_arena_lite_unittest::FOREIGN_BAZ);
+ m->mutable_optional_lazy_message()->set_bb(45);
+ m->add_repeated_int32(100);
+ m->add_repeated_string("asdf");
+ m->add_repeated_bytes("jkl;");
+ m->add_repeated_nested_message()->set_bb(46);
+ m->add_repeated_foreign_message()->set_c(47);
+ m->add_repeated_nested_enum(
+ proto3_arena_lite_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->add_repeated_foreign_enum(
+ proto3_arena_lite_unittest::FOREIGN_BAZ);
+ m->add_repeated_lazy_message()->set_bb(49);
+
+ m->set_oneof_uint32(1);
+ m->mutable_oneof_nested_message()->set_bb(50);
+ m->set_oneof_string("test"); // only this one remains set
+}
+
+void ExpectAllFieldsSet(const TestAllTypes& m) {
+ EXPECT_EQ(100, m.optional_int32());
+ EXPECT_EQ("asdf", m.optional_string());
+ EXPECT_EQ("jkl;", m.optional_bytes());
+ EXPECT_EQ(true, m.has_optional_nested_message());
+ EXPECT_EQ(42, m.optional_nested_message().bb());
+ EXPECT_EQ(true, m.has_optional_foreign_message());
+ EXPECT_EQ(43, m.optional_foreign_message().c());
+ EXPECT_EQ(proto3_arena_lite_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.optional_nested_enum());
+ EXPECT_EQ(proto3_arena_lite_unittest::FOREIGN_BAZ,
+ m.optional_foreign_enum());
+ EXPECT_EQ(true, m.has_optional_lazy_message());
+ EXPECT_EQ(45, m.optional_lazy_message().bb());
+
+ EXPECT_EQ(1, m.repeated_int32_size());
+ EXPECT_EQ(100, m.repeated_int32(0));
+ EXPECT_EQ(1, m.repeated_string_size());
+ EXPECT_EQ("asdf", m.repeated_string(0));
+ EXPECT_EQ(1, m.repeated_bytes_size());
+ EXPECT_EQ("jkl;", m.repeated_bytes(0));
+ EXPECT_EQ(1, m.repeated_nested_message_size());
+ EXPECT_EQ(46, m.repeated_nested_message(0).bb());
+ EXPECT_EQ(1, m.repeated_foreign_message_size());
+ EXPECT_EQ(47, m.repeated_foreign_message(0).c());
+ EXPECT_EQ(1, m.repeated_nested_enum_size());
+ EXPECT_EQ(proto3_arena_lite_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.repeated_nested_enum(0));
+ EXPECT_EQ(1, m.repeated_foreign_enum_size());
+ EXPECT_EQ(proto3_arena_lite_unittest::FOREIGN_BAZ,
+ m.repeated_foreign_enum(0));
+ EXPECT_EQ(1, m.repeated_lazy_message_size());
+ EXPECT_EQ(49, m.repeated_lazy_message(0).bb());
+
+ EXPECT_EQ(proto3_arena_lite_unittest::TestAllTypes::kOneofString,
+ m.oneof_field_case());
+ EXPECT_EQ("test", m.oneof_string());
+}
+
+// In this file we only test some basic functionalities of arena support in
+// proto3 and expect the arena support to be fully tested in proto2 unittests
+// because proto3 shares most code with proto2.
+
+TEST(Proto3ArenaLiteTest, Parsing) {
+ TestAllTypes original;
+ SetAllFields(&original);
+
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->ParseFromString(original.SerializeAsString());
+ ExpectAllFieldsSet(*arena_message);
+}
+
+TEST(Proto3ArenaLiteTest, Swap) {
+ Arena arena1;
+ Arena arena2;
+
+ // Test Swap().
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ TestAllTypes* arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ arena1_message->Swap(arena2_message);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(&arena2, arena2_message->GetArena());
+}
+
+TEST(Proto3ArenaLiteTest, SetAllocatedMessage) {
+ Arena arena;
+ TestAllTypes *arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ TestAllTypes::NestedMessage* nested = new TestAllTypes::NestedMessage;
+ nested->set_bb(118);
+ arena_message->set_allocated_optional_nested_message(nested);
+ EXPECT_EQ(118, arena_message->optional_nested_message().bb());
+}
+
+TEST(Proto3ArenaLiteTest, ReleaseMessage) {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->mutable_optional_nested_message()->set_bb(118);
+ google::protobuf::scoped_ptr<TestAllTypes::NestedMessage> nested(
+ arena_message->release_optional_nested_message());
+ EXPECT_EQ(118, nested->bb());
+}
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_unittest.cc
new file mode 100644
index 0000000000..2838e0fc64
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/proto3_arena_unittest.cc
@@ -0,0 +1,209 @@
+// 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.
+
+#include <string>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_proto3_arena.pb.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+using proto3_arena_unittest::TestAllTypes;
+
+namespace protobuf {
+namespace {
+// We selectively set/check a few representative fields rather than all fields
+// as this test is only expected to cover the basics of arena support.
+void SetAllFields(TestAllTypes* m) {
+ m->set_optional_int32(100);
+ m->set_optional_string("asdf");
+ m->set_optional_bytes("jkl;");
+ m->mutable_optional_nested_message()->set_bb(42);
+ m->mutable_optional_foreign_message()->set_c(43);
+ m->set_optional_nested_enum(
+ proto3_arena_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->set_optional_foreign_enum(
+ proto3_arena_unittest::FOREIGN_BAZ);
+ m->mutable_optional_lazy_message()->set_bb(45);
+ m->add_repeated_int32(100);
+ m->add_repeated_string("asdf");
+ m->add_repeated_bytes("jkl;");
+ m->add_repeated_nested_message()->set_bb(46);
+ m->add_repeated_foreign_message()->set_c(47);
+ m->add_repeated_nested_enum(
+ proto3_arena_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->add_repeated_foreign_enum(
+ proto3_arena_unittest::FOREIGN_BAZ);
+ m->add_repeated_lazy_message()->set_bb(49);
+
+ m->set_oneof_uint32(1);
+ m->mutable_oneof_nested_message()->set_bb(50);
+ m->set_oneof_string("test"); // only this one remains set
+}
+
+void ExpectAllFieldsSet(const TestAllTypes& m) {
+ EXPECT_EQ(100, m.optional_int32());
+ EXPECT_EQ("asdf", m.optional_string());
+ EXPECT_EQ("jkl;", m.optional_bytes());
+ EXPECT_EQ(true, m.has_optional_nested_message());
+ EXPECT_EQ(42, m.optional_nested_message().bb());
+ EXPECT_EQ(true, m.has_optional_foreign_message());
+ EXPECT_EQ(43, m.optional_foreign_message().c());
+ EXPECT_EQ(proto3_arena_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.optional_nested_enum());
+ EXPECT_EQ(proto3_arena_unittest::FOREIGN_BAZ,
+ m.optional_foreign_enum());
+ EXPECT_EQ(true, m.has_optional_lazy_message());
+ EXPECT_EQ(45, m.optional_lazy_message().bb());
+
+ EXPECT_EQ(1, m.repeated_int32_size());
+ EXPECT_EQ(100, m.repeated_int32(0));
+ EXPECT_EQ(1, m.repeated_string_size());
+ EXPECT_EQ("asdf", m.repeated_string(0));
+ EXPECT_EQ(1, m.repeated_bytes_size());
+ EXPECT_EQ("jkl;", m.repeated_bytes(0));
+ EXPECT_EQ(1, m.repeated_nested_message_size());
+ EXPECT_EQ(46, m.repeated_nested_message(0).bb());
+ EXPECT_EQ(1, m.repeated_foreign_message_size());
+ EXPECT_EQ(47, m.repeated_foreign_message(0).c());
+ EXPECT_EQ(1, m.repeated_nested_enum_size());
+ EXPECT_EQ(proto3_arena_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.repeated_nested_enum(0));
+ EXPECT_EQ(1, m.repeated_foreign_enum_size());
+ EXPECT_EQ(proto3_arena_unittest::FOREIGN_BAZ,
+ m.repeated_foreign_enum(0));
+ EXPECT_EQ(1, m.repeated_lazy_message_size());
+ EXPECT_EQ(49, m.repeated_lazy_message(0).bb());
+
+ EXPECT_EQ(proto3_arena_unittest::TestAllTypes::kOneofString,
+ m.oneof_field_case());
+ EXPECT_EQ("test", m.oneof_string());
+}
+
+// In this file we only test some basic functionalities of arena support in
+// proto3 and expect the arena support to be fully tested in proto2 unittests
+// because proto3 shares most code with proto2.
+
+TEST(Proto3ArenaTest, Parsing) {
+ TestAllTypes original;
+ SetAllFields(&original);
+
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->ParseFromString(original.SerializeAsString());
+ ExpectAllFieldsSet(*arena_message);
+}
+
+TEST(Proto3ArenaTest, UnknownFields) {
+ TestAllTypes original;
+ SetAllFields(&original);
+
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->ParseFromString(original.SerializeAsString());
+ ExpectAllFieldsSet(*arena_message);
+
+ // In proto3 we can still get a pointer to the UnknownFieldSet through
+ // reflection API.
+ UnknownFieldSet* unknown_fields =
+ arena_message->GetReflection()->MutableUnknownFields(arena_message);
+ // We can modify this UnknownFieldSet.
+ unknown_fields->AddVarint(1, 2);
+ // But the change will never will serialized back.
+ ASSERT_EQ(original.ByteSize(), arena_message->ByteSize());
+ ASSERT_TRUE(
+ arena_message->GetReflection()->GetUnknownFields(*arena_message).empty());
+}
+
+TEST(Proto3ArenaTest, Swap) {
+ Arena arena1;
+ Arena arena2;
+
+ // Test Swap().
+ TestAllTypes* arena1_message = Arena::CreateMessage<TestAllTypes>(&arena1);
+ TestAllTypes* arena2_message = Arena::CreateMessage<TestAllTypes>(&arena2);
+ arena1_message->Swap(arena2_message);
+ EXPECT_EQ(&arena1, arena1_message->GetArena());
+ EXPECT_EQ(&arena2, arena2_message->GetArena());
+}
+
+TEST(Proto3ArenaTest, SetAllocatedMessage) {
+ Arena arena;
+ TestAllTypes *arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ TestAllTypes::NestedMessage* nested = new TestAllTypes::NestedMessage;
+ nested->set_bb(118);
+ arena_message->set_allocated_optional_nested_message(nested);
+ EXPECT_EQ(118, arena_message->optional_nested_message().bb());
+}
+
+TEST(Proto3ArenaTest, ReleaseMessage) {
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->mutable_optional_nested_message()->set_bb(118);
+ google::protobuf::scoped_ptr<TestAllTypes::NestedMessage> nested(
+ arena_message->release_optional_nested_message());
+ EXPECT_EQ(118, nested->bb());
+}
+
+TEST(Proto3ArenaTest, MessageFieldClear) {
+ // GitHub issue #310: https://github.com/google/protobuf/issues/310
+ Arena arena;
+ TestAllTypes* arena_message = Arena::CreateMessage<TestAllTypes>(&arena);
+ arena_message->mutable_optional_nested_message()->set_bb(118);
+ // This should not crash, but prior to the bugfix, it tried to use `operator
+ // delete` the nested message (which is on the arena):
+ arena_message->Clear();
+}
+
+TEST(Proto3ArenaTest, MessageFieldClearViaReflection) {
+ Arena arena;
+ TestAllTypes* message = Arena::CreateMessage<TestAllTypes>(&arena);
+ const Reflection* r = message->GetReflection();
+ const Descriptor* d = message->GetDescriptor();
+ const FieldDescriptor* msg_field = d->FindFieldByName(
+ "optional_nested_message");
+
+ message->mutable_optional_nested_message()->set_bb(1);
+ r->ClearField(message, msg_field);
+ EXPECT_FALSE(message->has_optional_nested_message());
+ EXPECT_EQ(0, message->optional_nested_message().bb());
+}
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/proto3_lite_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/proto3_lite_unittest.cc
new file mode 100644
index 0000000000..2e2beea909
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/proto3_lite_unittest.cc
@@ -0,0 +1,145 @@
+// 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.
+
+#include <string>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_proto3_lite.pb.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+using proto3_lite_unittest::TestAllTypes;
+
+namespace protobuf {
+namespace {
+// We selectively set/check a few representative fields rather than all fields
+// as this test is only expected to cover the basics of lite support.
+void SetAllFields(TestAllTypes* m) {
+ m->set_optional_int32(100);
+ m->set_optional_string("asdf");
+ m->set_optional_bytes("jkl;");
+ m->mutable_optional_nested_message()->set_bb(42);
+ m->mutable_optional_foreign_message()->set_c(43);
+ m->set_optional_nested_enum(
+ proto3_lite_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->set_optional_foreign_enum(
+ proto3_lite_unittest::FOREIGN_BAZ);
+ m->mutable_optional_lazy_message()->set_bb(45);
+ m->add_repeated_int32(100);
+ m->add_repeated_string("asdf");
+ m->add_repeated_bytes("jkl;");
+ m->add_repeated_nested_message()->set_bb(46);
+ m->add_repeated_foreign_message()->set_c(47);
+ m->add_repeated_nested_enum(
+ proto3_lite_unittest::TestAllTypes_NestedEnum_BAZ);
+ m->add_repeated_foreign_enum(
+ proto3_lite_unittest::FOREIGN_BAZ);
+ m->add_repeated_lazy_message()->set_bb(49);
+
+ m->set_oneof_uint32(1);
+ m->mutable_oneof_nested_message()->set_bb(50);
+ m->set_oneof_string("test"); // only this one remains set
+}
+
+void ExpectAllFieldsSet(const TestAllTypes& m) {
+ EXPECT_EQ(100, m.optional_int32());
+ EXPECT_EQ("asdf", m.optional_string());
+ EXPECT_EQ("jkl;", m.optional_bytes());
+ EXPECT_EQ(true, m.has_optional_nested_message());
+ EXPECT_EQ(42, m.optional_nested_message().bb());
+ EXPECT_EQ(true, m.has_optional_foreign_message());
+ EXPECT_EQ(43, m.optional_foreign_message().c());
+ EXPECT_EQ(proto3_lite_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.optional_nested_enum());
+ EXPECT_EQ(proto3_lite_unittest::FOREIGN_BAZ,
+ m.optional_foreign_enum());
+ EXPECT_EQ(true, m.has_optional_lazy_message());
+ EXPECT_EQ(45, m.optional_lazy_message().bb());
+
+ EXPECT_EQ(1, m.repeated_int32_size());
+ EXPECT_EQ(100, m.repeated_int32(0));
+ EXPECT_EQ(1, m.repeated_string_size());
+ EXPECT_EQ("asdf", m.repeated_string(0));
+ EXPECT_EQ(1, m.repeated_bytes_size());
+ EXPECT_EQ("jkl;", m.repeated_bytes(0));
+ EXPECT_EQ(1, m.repeated_nested_message_size());
+ EXPECT_EQ(46, m.repeated_nested_message(0).bb());
+ EXPECT_EQ(1, m.repeated_foreign_message_size());
+ EXPECT_EQ(47, m.repeated_foreign_message(0).c());
+ EXPECT_EQ(1, m.repeated_nested_enum_size());
+ EXPECT_EQ(proto3_lite_unittest::TestAllTypes_NestedEnum_BAZ,
+ m.repeated_nested_enum(0));
+ EXPECT_EQ(1, m.repeated_foreign_enum_size());
+ EXPECT_EQ(proto3_lite_unittest::FOREIGN_BAZ,
+ m.repeated_foreign_enum(0));
+ EXPECT_EQ(1, m.repeated_lazy_message_size());
+ EXPECT_EQ(49, m.repeated_lazy_message(0).bb());
+
+ EXPECT_EQ(proto3_lite_unittest::TestAllTypes::kOneofString,
+ m.oneof_field_case());
+ EXPECT_EQ("test", m.oneof_string());
+}
+
+// In this file we only test some basic functionalities of in proto3 and expect
+// the rest is fully tested in proto2 unittests because proto3 shares most code
+// with proto2.
+
+TEST(Proto3LiteTest, Parsing) {
+ TestAllTypes original;
+ SetAllFields(&original);
+
+ TestAllTypes msg;
+ msg.ParseFromString(original.SerializeAsString());
+ ExpectAllFieldsSet(msg);
+}
+
+TEST(Proto3LiteTest, Swap) {
+ // Test Swap().
+ TestAllTypes msg1;
+ TestAllTypes msg2;
+ msg1.set_optional_string("123");
+ msg2.set_optional_string("3456");
+ msg1.Swap(&msg2);
+ EXPECT_EQ("3456", msg1.optional_string());
+ EXPECT_EQ("123", msg2.optional_string());
+ EXPECT_EQ(msg1.ByteSize(), msg2.ByteSize() + 1);
+}
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/reflection.h b/third_party/protobuf/3.0.0/src/google/protobuf/reflection.h
new file mode 100755
index 0000000000..2391f45389
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/reflection.h
@@ -0,0 +1,600 @@
+// 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.
+
+// This header defines the RepeatedFieldRef class template used to access
+// repeated fields with protobuf reflection API.
+#ifndef GOOGLE_PROTOBUF_REFLECTION_H__
+#define GOOGLE_PROTOBUF_REFLECTION_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/message.h>
+#include <google/protobuf/generated_enum_util.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+template<typename T, typename Enable = void>
+struct RefTypeTraits;
+} // namespace internal
+
+template<typename T>
+RepeatedFieldRef<T> Reflection::GetRepeatedFieldRef(
+ const Message& message, const FieldDescriptor* field) const {
+ return RepeatedFieldRef<T>(message, field);
+}
+
+template<typename T>
+MutableRepeatedFieldRef<T> Reflection::GetMutableRepeatedFieldRef(
+ Message* message, const FieldDescriptor* field) const {
+ return MutableRepeatedFieldRef<T>(message, field);
+}
+
+// RepeatedFieldRef definition for non-message types.
+template<typename T>
+class RepeatedFieldRef<
+ T, typename internal::enable_if<!internal::is_base_of<Message, T>::value>::type> {
+ typedef typename internal::RefTypeTraits<T>::iterator IteratorType;
+ typedef typename internal::RefTypeTraits<T>::AccessorType AccessorType;
+
+ public:
+ bool empty() const {
+ return accessor_->IsEmpty(data_);
+ }
+ int size() const {
+ return accessor_->Size(data_);
+ }
+ T Get(int index) const {
+ return accessor_->template Get<T>(data_, index);
+ }
+
+ typedef IteratorType iterator;
+ typedef IteratorType const_iterator;
+ iterator begin() const {
+ return iterator(data_, accessor_, true);
+ }
+ iterator end() const {
+ return iterator(data_, accessor_, false);
+ }
+
+ private:
+ friend class Reflection;
+ RepeatedFieldRef(
+ const Message& message,
+ const FieldDescriptor* field) {
+ const Reflection* reflection = message.GetReflection();
+ data_ = reflection->RepeatedFieldData(
+ const_cast<Message*>(&message), field,
+ internal::RefTypeTraits<T>::cpp_type, NULL);
+ accessor_ = reflection->RepeatedFieldAccessor(field);
+ }
+
+ const void* data_;
+ const AccessorType* accessor_;
+};
+
+// MutableRepeatedFieldRef definition for non-message types.
+template<typename T>
+class MutableRepeatedFieldRef<
+ T, typename internal::enable_if<!internal::is_base_of<Message, T>::value>::type> {
+ typedef typename internal::RefTypeTraits<T>::AccessorType AccessorType;
+
+ public:
+ bool empty() const {
+ return accessor_->IsEmpty(data_);
+ }
+ int size() const {
+ return accessor_->Size(data_);
+ }
+ T Get(int index) const {
+ return accessor_->template Get<T>(data_, index);
+ }
+
+ void Set(int index, const T& value) const {
+ accessor_->template Set<T>(data_, index, value);
+ }
+ void Add(const T& value) const {
+ accessor_->template Add<T>(data_, value);
+ }
+ void RemoveLast() const {
+ accessor_->RemoveLast(data_);
+ }
+ void SwapElements(int index1, int index2) const {
+ accessor_->SwapElements(data_, index1, index2);
+ }
+ void Clear() const {
+ accessor_->Clear(data_);
+ }
+
+ void Swap(const MutableRepeatedFieldRef& other) const {
+ accessor_->Swap(data_, other.accessor_, other.data_);
+ }
+
+ template<typename Container>
+ void MergeFrom(const Container& container) const {
+ typedef typename Container::const_iterator Iterator;
+ for (Iterator it = container.begin(); it != container.end(); ++it) {
+ Add(*it);
+ }
+ }
+ template<typename Container>
+ void CopyFrom(const Container& container) const {
+ Clear();
+ MergeFrom(container);
+ }
+
+ private:
+ friend class Reflection;
+ MutableRepeatedFieldRef(
+ Message* message,
+ const FieldDescriptor* field) {
+ const Reflection* reflection = message->GetReflection();
+ data_ = reflection->RepeatedFieldData(
+ message, field, internal::RefTypeTraits<T>::cpp_type, NULL);
+ accessor_ = reflection->RepeatedFieldAccessor(field);
+ }
+
+ void* data_;
+ const AccessorType* accessor_;
+};
+
+// RepeatedFieldRef definition for message types.
+template<typename T>
+class RepeatedFieldRef<
+ T, typename internal::enable_if<internal::is_base_of<Message, T>::value>::type> {
+ typedef typename internal::RefTypeTraits<T>::iterator IteratorType;
+ typedef typename internal::RefTypeTraits<T>::AccessorType AccessorType;
+
+ public:
+ bool empty() const {
+ return accessor_->IsEmpty(data_);
+ }
+ int size() const {
+ return accessor_->Size(data_);
+ }
+ // This method returns a reference to the underlying message object if it
+ // exists. If a message object doesn't exist (e.g., data stored in serialized
+ // form), scratch_space will be filled with the data and a reference to it
+ // will be returned.
+ //
+ // Example:
+ // RepeatedFieldRef<Message> h = ...
+ // unique_ptr<Message> scratch_space(h.NewMessage());
+ // const Message& item = h.Get(index, scratch_space.get());
+ const T& Get(int index, T* scratch_space) const {
+ return *static_cast<const T*>(accessor_->Get(data_, index, scratch_space));
+ }
+ // Create a new message of the same type as the messages stored in this
+ // repeated field. Caller takes ownership of the returned object.
+ T* NewMessage() const {
+ return static_cast<T*>(default_instance_->New());
+ }
+
+ typedef IteratorType iterator;
+ typedef IteratorType const_iterator;
+ iterator begin() const {
+ return iterator(data_, accessor_, true, NewMessage());
+ }
+ iterator end() const {
+ return iterator(data_, accessor_, false, NewMessage());
+ }
+
+ private:
+ friend class Reflection;
+ RepeatedFieldRef(
+ const Message& message,
+ const FieldDescriptor* field) {
+ const Reflection* reflection = message.GetReflection();
+ data_ = reflection->RepeatedFieldData(
+ const_cast<Message*>(&message), field,
+ internal::RefTypeTraits<T>::cpp_type,
+ internal::RefTypeTraits<T>::GetMessageFieldDescriptor());
+ accessor_ = reflection->RepeatedFieldAccessor(field);
+ default_instance_ =
+ reflection->GetMessageFactory()->GetPrototype(field->message_type());
+ }
+
+ const void* data_;
+ const AccessorType* accessor_;
+ const Message* default_instance_;
+};
+
+// MutableRepeatedFieldRef definition for message types.
+template<typename T>
+class MutableRepeatedFieldRef<
+ T, typename internal::enable_if<internal::is_base_of<Message, T>::value>::type> {
+ typedef typename internal::RefTypeTraits<T>::AccessorType AccessorType;
+
+ public:
+ bool empty() const {
+ return accessor_->IsEmpty(data_);
+ }
+ int size() const {
+ return accessor_->Size(data_);
+ }
+ // See comments for RepeatedFieldRef<Message>::Get()
+ const T& Get(int index, T* scratch_space) const {
+ return *static_cast<const T*>(accessor_->Get(data_, index, scratch_space));
+ }
+ // Create a new message of the same type as the messages stored in this
+ // repeated field. Caller takes ownership of the returned object.
+ T* NewMessage() const {
+ return static_cast<T*>(default_instance_->New());
+ }
+
+ void Set(int index, const T& value) const {
+ accessor_->Set(data_, index, &value);
+ }
+ void Add(const T& value) const {
+ accessor_->Add(data_, &value);
+ }
+ void RemoveLast() const {
+ accessor_->RemoveLast(data_);
+ }
+ void SwapElements(int index1, int index2) const {
+ accessor_->SwapElements(data_, index1, index2);
+ }
+ void Clear() const {
+ accessor_->Clear(data_);
+ }
+
+ void Swap(const MutableRepeatedFieldRef& other) const {
+ accessor_->Swap(data_, other.accessor_, other.data_);
+ }
+
+ template<typename Container>
+ void MergeFrom(const Container& container) const {
+ typedef typename Container::const_iterator Iterator;
+ for (Iterator it = container.begin(); it != container.end(); ++it) {
+ Add(*it);
+ }
+ }
+ template<typename Container>
+ void CopyFrom(const Container& container) const {
+ Clear();
+ MergeFrom(container);
+ }
+
+ private:
+ friend class Reflection;
+ MutableRepeatedFieldRef(
+ Message* message,
+ const FieldDescriptor* field) {
+ const Reflection* reflection = message->GetReflection();
+ data_ = reflection->RepeatedFieldData(
+ message, field, internal::RefTypeTraits<T>::cpp_type,
+ internal::RefTypeTraits<T>::GetMessageFieldDescriptor());
+ accessor_ = reflection->RepeatedFieldAccessor(field);
+ default_instance_ =
+ reflection->GetMessageFactory()->GetPrototype(field->message_type());
+ }
+
+ void* data_;
+ const AccessorType* accessor_;
+ const Message* default_instance_;
+};
+
+namespace internal {
+// Interfaces used to implement reflection RepeatedFieldRef API.
+// Reflection::GetRepeatedAccessor() should return a pointer to an singleton
+// object that implements the below interface.
+//
+// This interface passes/returns values using void pointers. The actual type
+// of the value depends on the field's cpp_type. Following is a mapping from
+// cpp_type to the type that should be used in this interface:
+//
+// field->cpp_type() T Actual type of void*
+// CPPTYPE_INT32 int32 int32
+// CPPTYPE_UINT32 uint32 uint32
+// CPPTYPE_INT64 int64 int64
+// CPPTYPE_UINT64 uint64 uint64
+// CPPTYPE_DOUBLE double double
+// CPPTYPE_FLOAT float float
+// CPPTYPE_BOOL bool bool
+// CPPTYPE_ENUM generated enum type int32
+// CPPTYPE_STRING string string
+// CPPTYPE_MESSAGE generated message type google::protobuf::Message
+// or google::protobuf::Message
+//
+// Note that for enums we use int32 in the interface.
+//
+// You can map from T to the actual type using RefTypeTraits:
+// typedef RefTypeTraits<T>::AccessorValueType ActualType;
+class LIBPROTOBUF_EXPORT RepeatedFieldAccessor {
+ public:
+ // Typedefs for clarity.
+ typedef void Field;
+ typedef void Value;
+ typedef void Iterator;
+
+ virtual ~RepeatedFieldAccessor();
+ virtual bool IsEmpty(const Field* data) const = 0;
+ virtual int Size(const Field* data) const = 0;
+ // Depends on the underlying representation of the repeated field, this
+ // method can return a pointer to the underlying object if such an object
+ // exists, or fill the data into scratch_space and return scratch_space.
+ // Callers of this method must ensure scratch_space is a valid pointer
+ // to a mutable object of the correct type.
+ virtual const Value* Get(
+ const Field* data, int index, Value* scratch_space) const = 0;
+
+ virtual void Clear(Field* data) const = 0;
+ virtual void Set(Field* data, int index, const Value* value) const = 0;
+ virtual void Add(Field* data, const Value* value) const = 0;
+ virtual void RemoveLast(Field* data) const = 0;
+ virtual void SwapElements(Field* data, int index1, int index2) const = 0;
+ virtual void Swap(Field* data, const RepeatedFieldAccessor* other_mutator,
+ Field* other_data) const = 0;
+
+ // Create an iterator that points at the beginning of the repeated field.
+ virtual Iterator* BeginIterator(const Field* data) const = 0;
+ // Create an iterator that points at the end of the repeated field.
+ virtual Iterator* EndIterator(const Field* data) const = 0;
+ // Make a copy of an iterator and return the new copy.
+ virtual Iterator* CopyIterator(const Field* data,
+ const Iterator* iterator) const = 0;
+ // Move an iterator to point to the next element.
+ virtual Iterator* AdvanceIterator(const Field* data,
+ Iterator* iterator) const = 0;
+ // Compare whether two iterators point to the same element.
+ virtual bool EqualsIterator(const Field* data, const Iterator* a,
+ const Iterator* b) const = 0;
+ // Delete an iterator created by BeginIterator(), EndIterator() and
+ // CopyIterator().
+ virtual void DeleteIterator(const Field* data, Iterator* iterator) const = 0;
+ // Like Get() but for iterators.
+ virtual const Value* GetIteratorValue(const Field* data,
+ const Iterator* iterator,
+ Value* scratch_space) const = 0;
+
+ // Templated methods that make using this interface easier for non-message
+ // types.
+ template<typename T>
+ T Get(const Field* data, int index) const {
+ typedef typename RefTypeTraits<T>::AccessorValueType ActualType;
+ ActualType scratch_space;
+ return static_cast<T>(
+ *reinterpret_cast<const ActualType*>(
+ Get(data, index, static_cast<Value*>(&scratch_space))));
+ }
+
+ template<typename T, typename ValueType>
+ void Set(Field* data, int index, const ValueType& value) const {
+ typedef typename RefTypeTraits<T>::AccessorValueType ActualType;
+ // In this RepeatedFieldAccessor interface we pass/return data using
+ // raw pointers. Type of the data these raw pointers point to should
+ // be ActualType. Here we have a ValueType object and want a ActualType
+ // pointer. We can't cast a ValueType pointer to an ActualType pointer
+ // directly because their type might be different (for enums ValueType
+ // may be a generated enum type while ActualType is int32). To be safe
+ // we make a copy to get a temporary ActualType object and use it.
+ ActualType tmp = static_cast<ActualType>(value);
+ Set(data, index, static_cast<const Value*>(&tmp));
+ }
+
+ template<typename T, typename ValueType>
+ void Add(Field* data, const ValueType& value) const {
+ typedef typename RefTypeTraits<T>::AccessorValueType ActualType;
+ // In this RepeatedFieldAccessor interface we pass/return data using
+ // raw pointers. Type of the data these raw pointers point to should
+ // be ActualType. Here we have a ValueType object and want a ActualType
+ // pointer. We can't cast a ValueType pointer to an ActualType pointer
+ // directly because their type might be different (for enums ValueType
+ // may be a generated enum type while ActualType is int32). To be safe
+ // we make a copy to get a temporary ActualType object and use it.
+ ActualType tmp = static_cast<ActualType>(value);
+ Add(data, static_cast<const Value*>(&tmp));
+ }
+};
+
+// Implement (Mutable)RepeatedFieldRef::iterator
+template<typename T>
+class RepeatedFieldRefIterator
+ : public std::iterator<std::forward_iterator_tag, T> {
+ typedef typename RefTypeTraits<T>::AccessorValueType AccessorValueType;
+ typedef typename RefTypeTraits<T>::IteratorValueType IteratorValueType;
+ typedef typename RefTypeTraits<T>::IteratorPointerType IteratorPointerType;
+
+ public:
+ // Constructor for non-message fields.
+ RepeatedFieldRefIterator(const void* data,
+ const RepeatedFieldAccessor* accessor,
+ bool begin)
+ : data_(data), accessor_(accessor),
+ iterator_(begin ? accessor->BeginIterator(data) :
+ accessor->EndIterator(data)),
+ scratch_space_(new AccessorValueType) {
+ }
+ // Constructor for message fields.
+ RepeatedFieldRefIterator(const void* data,
+ const RepeatedFieldAccessor* accessor,
+ bool begin,
+ AccessorValueType* scratch_space)
+ : data_(data), accessor_(accessor),
+ iterator_(begin ? accessor->BeginIterator(data) :
+ accessor->EndIterator(data)),
+ scratch_space_(scratch_space) {
+ }
+ ~RepeatedFieldRefIterator() {
+ accessor_->DeleteIterator(data_, iterator_);
+ }
+ RepeatedFieldRefIterator operator++(int) {
+ RepeatedFieldRefIterator tmp(*this);
+ iterator_ = accessor_->AdvanceIterator(data_, iterator_);
+ return tmp;
+ }
+ RepeatedFieldRefIterator& operator++() {
+ iterator_ = accessor_->AdvanceIterator(data_, iterator_);
+ return *this;
+ }
+ IteratorValueType operator*() const {
+ return static_cast<IteratorValueType>(
+ *static_cast<const AccessorValueType*>(
+ accessor_->GetIteratorValue(
+ data_, iterator_, scratch_space_.get())));
+ }
+ IteratorPointerType operator->() const {
+ return static_cast<IteratorPointerType>(
+ accessor_->GetIteratorValue(
+ data_, iterator_, scratch_space_.get()));
+ }
+ bool operator!=(const RepeatedFieldRefIterator& other) const {
+ assert(data_ == other.data_);
+ assert(accessor_ == other.accessor_);
+ return !accessor_->EqualsIterator(data_, iterator_, other.iterator_);
+ }
+ bool operator==(const RepeatedFieldRefIterator& other) const {
+ return !this->operator!=(other);
+ }
+
+ RepeatedFieldRefIterator(const RepeatedFieldRefIterator& other)
+ : data_(other.data_), accessor_(other.accessor_),
+ iterator_(accessor_->CopyIterator(data_, other.iterator_)) {
+ }
+ RepeatedFieldRefIterator& operator=(const RepeatedFieldRefIterator& other) {
+ if (this != &other) {
+ accessor_->DeleteIterator(data_, iterator_);
+ data_ = other.data_;
+ accessor_ = other.accessor_;
+ iterator_ = accessor_->CopyIterator(data_, other.iterator_);
+ }
+ return *this;
+ }
+
+ protected:
+ const void* data_;
+ const RepeatedFieldAccessor* accessor_;
+ void* iterator_;
+ google::protobuf::scoped_ptr<AccessorValueType> scratch_space_;
+};
+
+// TypeTraits that maps the type parameter T of RepeatedFieldRef or
+// MutableRepeatedFieldRef to corresponding iterator type,
+// RepeatedFieldAccessor type, etc.
+template<typename T>
+struct PrimitiveTraits {
+ static const bool is_primitive = false;
+};
+#define DEFINE_PRIMITIVE(TYPE, type) \
+ template<> struct PrimitiveTraits<type> { \
+ static const bool is_primitive = true; \
+ static const FieldDescriptor::CppType cpp_type = \
+ FieldDescriptor::CPPTYPE_ ## TYPE; \
+ };
+DEFINE_PRIMITIVE(INT32, int32)
+DEFINE_PRIMITIVE(UINT32, uint32)
+DEFINE_PRIMITIVE(INT64, int64)
+DEFINE_PRIMITIVE(UINT64, uint64)
+DEFINE_PRIMITIVE(FLOAT, float)
+DEFINE_PRIMITIVE(DOUBLE, double)
+DEFINE_PRIMITIVE(BOOL, bool)
+#undef DEFINE_PRIMITIVE
+
+template<typename T>
+struct RefTypeTraits<
+ T, typename internal::enable_if<PrimitiveTraits<T>::is_primitive>::type> {
+ typedef RepeatedFieldRefIterator<T> iterator;
+ typedef RepeatedFieldAccessor AccessorType;
+ typedef T AccessorValueType;
+ typedef T IteratorValueType;
+ typedef T* IteratorPointerType;
+ static const FieldDescriptor::CppType cpp_type =
+ PrimitiveTraits<T>::cpp_type;
+ static const Descriptor* GetMessageFieldDescriptor() {
+ return NULL;
+ }
+};
+
+template<typename T>
+struct RefTypeTraits<
+ T, typename internal::enable_if<is_proto_enum<T>::value>::type> {
+ typedef RepeatedFieldRefIterator<T> iterator;
+ typedef RepeatedFieldAccessor AccessorType;
+ // We use int32 for repeated enums in RepeatedFieldAccessor.
+ typedef int32 AccessorValueType;
+ typedef T IteratorValueType;
+ typedef int32* IteratorPointerType;
+ static const FieldDescriptor::CppType cpp_type =
+ FieldDescriptor::CPPTYPE_ENUM;
+ static const Descriptor* GetMessageFieldDescriptor() {
+ return NULL;
+ }
+};
+
+template<typename T>
+struct RefTypeTraits<
+ T, typename internal::enable_if< ::google::protobuf::internal::is_same<string, T>::value>::type> {
+ typedef RepeatedFieldRefIterator<T> iterator;
+ typedef RepeatedFieldAccessor AccessorType;
+ typedef string AccessorValueType;
+ typedef string IteratorValueType;
+ typedef string* IteratorPointerType;
+ static const FieldDescriptor::CppType cpp_type =
+ FieldDescriptor::CPPTYPE_STRING;
+ static const Descriptor* GetMessageFieldDescriptor() {
+ return NULL;
+ }
+};
+
+template<typename T>
+struct MessageDescriptorGetter {
+ static const Descriptor* get() {
+ return T::default_instance().GetDescriptor();
+ }
+};
+template<>
+struct MessageDescriptorGetter<Message> {
+ static const Descriptor* get() {
+ return NULL;
+ }
+};
+
+template<typename T>
+struct RefTypeTraits<
+ T, typename internal::enable_if<internal::is_base_of<Message, T>::value>::type> {
+ typedef RepeatedFieldRefIterator<T> iterator;
+ typedef RepeatedFieldAccessor AccessorType;
+ typedef Message AccessorValueType;
+ typedef const T& IteratorValueType;
+ typedef const T* IteratorPointerType;
+ static const FieldDescriptor::CppType cpp_type =
+ FieldDescriptor::CPPTYPE_MESSAGE;
+ static const Descriptor* GetMessageFieldDescriptor() {
+ return MessageDescriptorGetter<T>::get();
+ }
+};
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_REFLECTION_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/reflection_internal.h b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_internal.h
new file mode 100644
index 0000000000..fcb424715c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_internal.h
@@ -0,0 +1,378 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_REFLECTION_INTERNAL_H__
+#define GOOGLE_PROTOBUF_REFLECTION_INTERNAL_H__
+
+#include <google/protobuf/map_field.h>
+#include <google/protobuf/reflection.h>
+#include <google/protobuf/repeated_field.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+// A base class for RepeatedFieldAccessor implementations that can support
+// random-access efficiently. All iterator methods delegates the work to
+// corresponding random-access methods.
+class RandomAccessRepeatedFieldAccessor : public RepeatedFieldAccessor {
+ public:
+ virtual ~RandomAccessRepeatedFieldAccessor() {}
+
+ virtual Iterator* BeginIterator(const Field* data) const {
+ return PositionToIterator(0);
+ }
+ virtual Iterator* EndIterator(const Field* data) const {
+ return PositionToIterator(this->Size(data));
+ }
+ virtual Iterator* CopyIterator(const Field* data,
+ const Iterator* iterator) const {
+ return const_cast<Iterator*>(iterator);
+ }
+ virtual Iterator* AdvanceIterator(const Field* data,
+ Iterator* iterator) const {
+ return PositionToIterator(IteratorToPosition(iterator) + 1);
+ }
+ virtual bool EqualsIterator(const Field* data,
+ const Iterator* a,
+ const Iterator* b) const {
+ return a == b;
+ }
+ virtual void DeleteIterator(const Field* data, Iterator* iterator) const {
+ }
+ virtual const Value* GetIteratorValue(const Field* data,
+ const Iterator* iterator,
+ Value* scratch_space) const {
+ return Get(data, static_cast<int>(IteratorToPosition(iterator)),
+ scratch_space);
+ }
+
+ private:
+ static intptr_t IteratorToPosition(const Iterator* iterator) {
+ return reinterpret_cast<intptr_t>(iterator);
+ }
+ static Iterator* PositionToIterator(intptr_t position) {
+ return reinterpret_cast<Iterator*>(position);
+ }
+};
+
+// Base class for RepeatedFieldAccessor implementations that manipulates
+// RepeatedField<T>.
+template<typename T>
+class RepeatedFieldWrapper : public RandomAccessRepeatedFieldAccessor {
+ public:
+ RepeatedFieldWrapper() {}
+ virtual ~RepeatedFieldWrapper() {}
+ virtual bool IsEmpty(const Field* data) const {
+ return GetRepeatedField(data)->empty();
+ }
+ virtual int Size(const Field* data) const {
+ return GetRepeatedField(data)->size();
+ }
+ virtual const Value* Get(const Field* data, int index,
+ Value* scratch_space) const {
+ return ConvertFromT(GetRepeatedField(data)->Get(index), scratch_space);
+ }
+ virtual void Clear(Field* data) const {
+ MutableRepeatedField(data)->Clear();
+ }
+ virtual void Set(Field* data, int index, const Value* value) const {
+ MutableRepeatedField(data)->Set(index, ConvertToT(value));
+ }
+ virtual void Add(Field* data, const Value* value) const {
+ MutableRepeatedField(data)->Add(ConvertToT(value));
+ }
+ virtual void RemoveLast(Field* data) const {
+ MutableRepeatedField(data)->RemoveLast();
+ }
+ virtual void SwapElements(Field* data, int index1, int index2) const {
+ MutableRepeatedField(data)->SwapElements(index1, index2);
+ }
+
+ protected:
+ typedef RepeatedField<T> RepeatedFieldType;
+ static const RepeatedFieldType* GetRepeatedField(const Field* data) {
+ return reinterpret_cast<const RepeatedFieldType*>(data);
+ }
+ static RepeatedFieldType* MutableRepeatedField(Field* data) {
+ return reinterpret_cast<RepeatedFieldType*>(data);
+ }
+
+ // Convert an object recevied by this accessor to an object to be stored in
+ // the underlying RepeatedField.
+ virtual T ConvertToT(const Value* value) const = 0;
+
+ // Convert an object stored in RepeatedPtrField to an object that will be
+ // returned by this accessor. If the two objects have the same type (true
+ // for string fields with ctype=STRING), a pointer to the source object can
+ // be returned directly. Otherwise, data should be copied from value to
+ // scratch_space and scratch_space should be returned.
+ virtual const Value* ConvertFromT(const T& value,
+ Value* scratch_space) const = 0;
+};
+
+// Base class for RepeatedFieldAccessor implementations that manipulates
+// RepeatedPtrField<T>.
+template<typename T>
+class RepeatedPtrFieldWrapper : public RandomAccessRepeatedFieldAccessor {
+ public:
+ RepeatedPtrFieldWrapper() {}
+ virtual ~RepeatedPtrFieldWrapper() {}
+ virtual bool IsEmpty(const Field* data) const {
+ return GetRepeatedField(data)->empty();
+ }
+ virtual int Size(const Field* data) const {
+ return GetRepeatedField(data)->size();
+ }
+ virtual const Value* Get(const Field* data, int index,
+ Value* scratch_space) const {
+ return ConvertFromT(GetRepeatedField(data)->Get(index), scratch_space);
+ }
+ virtual void Clear(Field* data) const {
+ MutableRepeatedField(data)->Clear();
+ }
+ virtual void Set(Field* data, int index, const Value* value) const {
+ ConvertToT(value, MutableRepeatedField(data)->Mutable(index));
+ }
+ virtual void Add(Field* data, const Value* value) const {
+ T* allocated = New(value);
+ ConvertToT(value, allocated);
+ MutableRepeatedField(data)->AddAllocated(allocated);
+ }
+ virtual void RemoveLast(Field* data) const {
+ MutableRepeatedField(data)->RemoveLast();
+ }
+ virtual void SwapElements(Field* data, int index1, int index2) const {
+ MutableRepeatedField(data)->SwapElements(index1, index2);
+ }
+
+ protected:
+ typedef RepeatedPtrField<T> RepeatedFieldType;
+ static const RepeatedFieldType* GetRepeatedField(const Field* data) {
+ return reinterpret_cast<const RepeatedFieldType*>(data);
+ }
+ static RepeatedFieldType* MutableRepeatedField(Field* data) {
+ return reinterpret_cast<RepeatedFieldType*>(data);
+ }
+
+ // Create a new T instance. For repeated message fields, T can be specified
+ // as google::protobuf::Message so we can't use "new T()" directly. In that case, value
+ // should be a message of the same type (it's ensured by the caller) and a
+ // new message object will be created using it.
+ virtual T* New(const Value* value) const = 0;
+
+ // Convert an object received by this accessor to an object that will be
+ // stored in the underlying RepeatedPtrField.
+ virtual void ConvertToT(const Value* value, T* result) const = 0;
+
+ // Convert an object stored in RepeatedPtrField to an object that will be
+ // returned by this accessor. If the two objects have the same type (true
+ // for string fields with ctype=STRING), a pointer to the source object can
+ // be returned directly. Otherwise, data should be copied from value to
+ // scratch_space and scratch_space should be returned.
+ virtual const Value* ConvertFromT(const T& value,
+ Value* scratch_space) const = 0;
+};
+
+// An implementation of RandomAccessRepeatedFieldAccessor that manipulates
+// MapFieldBase.
+class MapFieldAccessor : public RandomAccessRepeatedFieldAccessor {
+ public:
+ MapFieldAccessor() {}
+ virtual ~MapFieldAccessor() {}
+ virtual bool IsEmpty(const Field* data) const {
+ return GetRepeatedField(data)->empty();
+ }
+ virtual int Size(const Field* data) const {
+ return GetRepeatedField(data)->size();
+ }
+ virtual const Value* Get(const Field* data, int index,
+ Value* scratch_space) const {
+ return ConvertFromEntry(GetRepeatedField(data)->Get(index), scratch_space);
+ }
+ virtual void Clear(Field* data) const {
+ MutableRepeatedField(data)->Clear();
+ }
+ virtual void Set(Field* data, int index, const Value* value) const {
+ ConvertToEntry(value, MutableRepeatedField(data)->Mutable(index));
+ }
+ virtual void Add(Field* data, const Value* value) const {
+ Message* allocated = New(value);
+ ConvertToEntry(value, allocated);
+ MutableRepeatedField(data)->AddAllocated(allocated);
+ }
+ virtual void RemoveLast(Field* data) const {
+ MutableRepeatedField(data)->RemoveLast();
+ }
+ virtual void SwapElements(Field* data, int index1, int index2) const {
+ MutableRepeatedField(data)->SwapElements(index1, index2);
+ }
+ virtual void Swap(
+ Field* data,
+ const internal::RepeatedFieldAccessor* other_mutator,
+ Field* other_data) const {
+ GOOGLE_CHECK(this == other_mutator);
+ MutableRepeatedField(data)->Swap(MutableRepeatedField(other_data));
+ }
+
+ protected:
+ typedef RepeatedPtrField<Message> RepeatedFieldType;
+ static const RepeatedFieldType* GetRepeatedField(const Field* data) {
+ return reinterpret_cast<const RepeatedFieldType*>(
+ (&reinterpret_cast<const MapFieldBase*>(data)->GetRepeatedField()));
+ }
+ static RepeatedFieldType* MutableRepeatedField(Field* data) {
+ return reinterpret_cast<RepeatedFieldType*>(
+ reinterpret_cast<MapFieldBase*>(data)->MutableRepeatedField());
+ }
+ virtual Message* New(const Value* value) const {
+ return static_cast<const Message*>(value)->New();
+ }
+ // Convert an object received by this accessor to an MapEntry message to be
+ // stored in the underlying MapFieldBase.
+ virtual void ConvertToEntry(const Value* value, Message* result) const {
+ result->CopyFrom(*static_cast<const Message*>(value));
+ }
+ // Convert a MapEntry message stored in the underlying MapFieldBase to an
+ // object that will be returned by this accessor.
+ virtual const Value* ConvertFromEntry(const Message& value,
+ Value* scratch_space) const {
+ return static_cast<const Value*>(&value);
+ }
+};
+
+// Default implementations of RepeatedFieldAccessor for primitive types.
+template<typename T>
+class RepeatedFieldPrimitiveAccessor : public RepeatedFieldWrapper<T> {
+ typedef void Field;
+ typedef void Value;
+ using RepeatedFieldWrapper<T>::MutableRepeatedField;
+
+ public:
+ RepeatedFieldPrimitiveAccessor() {}
+ virtual ~RepeatedFieldPrimitiveAccessor() {}
+ virtual void Swap(
+ Field* data,
+ const internal::RepeatedFieldAccessor* other_mutator,
+ Field* other_data) const {
+ // Currently RepeatedFieldPrimitiveAccessor is the only implementation of
+ // RepeatedFieldAccessor for primitive types. As we are using singletons
+ // for these accessors, here "other_mutator" must be "this".
+ GOOGLE_CHECK(this == other_mutator);
+ MutableRepeatedField(data)->Swap(MutableRepeatedField(other_data));
+ }
+
+ protected:
+ virtual T ConvertToT(const Value* value) const {
+ return *static_cast<const T*>(value);
+ }
+ virtual const Value* ConvertFromT(const T& value,
+ Value* scratch_space) const {
+ return static_cast<const Value*>(&value);
+ }
+};
+
+// Default implementation of RepeatedFieldAccessor for string fields with
+// ctype=STRING.
+class RepeatedPtrFieldStringAccessor : public RepeatedPtrFieldWrapper<string> {
+ typedef void Field;
+ typedef void Value;
+ using RepeatedFieldAccessor::Add;
+
+ public:
+ RepeatedPtrFieldStringAccessor() {}
+ virtual ~RepeatedPtrFieldStringAccessor() {}
+ virtual void Swap(
+ Field* data,
+ const internal::RepeatedFieldAccessor* other_mutator,
+ Field* other_data) const {
+ if (this == other_mutator) {
+ MutableRepeatedField(data)->Swap(MutableRepeatedField(other_data));
+ } else {
+ RepeatedPtrField<string> tmp;
+ tmp.Swap(MutableRepeatedField(data));
+ int other_size = other_mutator->Size(other_data);
+ for (int i = 0; i < other_size; ++i) {
+ Add<string>(data, other_mutator->Get<string>(other_data, i));
+ }
+ int size = Size(data);
+ other_mutator->Clear(other_data);
+ for (int i = 0; i < size; ++i) {
+ other_mutator->Add<string>(other_data, tmp.Get(i));
+ }
+ }
+ }
+
+ protected:
+ virtual string* New(const Value*) const {
+ return new string();
+ }
+ virtual void ConvertToT(const Value* value, string* result) const {
+ *result = *static_cast<const string*>(value);
+ }
+ virtual const Value* ConvertFromT(const string& value,
+ Value* scratch_space) const {
+ return static_cast<const Value*>(&value);
+ }
+};
+
+
+class RepeatedPtrFieldMessageAccessor
+ : public RepeatedPtrFieldWrapper<Message> {
+ typedef void Field;
+ typedef void Value;
+
+ public:
+ RepeatedPtrFieldMessageAccessor() {}
+ virtual ~RepeatedPtrFieldMessageAccessor() {}
+ virtual void Swap(
+ Field* data,
+ const internal::RepeatedFieldAccessor* other_mutator,
+ Field* other_data) const {
+ GOOGLE_CHECK(this == other_mutator);
+ MutableRepeatedField(data)->Swap(MutableRepeatedField(other_data));
+ }
+
+ protected:
+ virtual Message* New(const Value* value) const {
+ return static_cast<const Message*>(value)->New();
+ }
+ virtual void ConvertToT(const Value* value, Message* result) const {
+ result->CopyFrom(*static_cast<const Message*>(value));
+ }
+ virtual const Value* ConvertFromT(const Message& value,
+ Value* scratch_space) const {
+ return static_cast<const Value*>(&value);
+ }
+};
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_REFLECTION_INTERNAL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.cc b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.cc
new file mode 100644
index 0000000000..4629dec251
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.cc
@@ -0,0 +1,269 @@
+// 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.
+
+#include <string>
+#include <vector>
+
+#include <google/protobuf/reflection_ops.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+void ReflectionOps::Copy(const Message& from, Message* to) {
+ if (&from == to) return;
+ Clear(to);
+ Merge(from, to);
+}
+
+void ReflectionOps::Merge(const Message& from, Message* to) {
+ GOOGLE_CHECK_NE(&from, to);
+
+ const Descriptor* descriptor = from.GetDescriptor();
+ GOOGLE_CHECK_EQ(to->GetDescriptor(), descriptor)
+ << "Tried to merge messages of different types "
+ << "(merge " << descriptor->full_name()
+ << " to " << to->GetDescriptor()->full_name() << ")";
+
+ const Reflection* from_reflection = from.GetReflection();
+ const Reflection* to_reflection = to->GetReflection();
+
+ vector<const FieldDescriptor*> fields;
+ from_reflection->ListFields(from, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ const FieldDescriptor* field = fields[i];
+
+ if (field->is_repeated()) {
+ int count = from_reflection->FieldSize(from, field);
+ for (int j = 0; j < count; j++) {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(CPPTYPE, METHOD) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ to_reflection->Add##METHOD(to, field, \
+ from_reflection->GetRepeated##METHOD(from, field, j)); \
+ break;
+
+ HANDLE_TYPE(INT32 , Int32 );
+ HANDLE_TYPE(INT64 , Int64 );
+ HANDLE_TYPE(UINT32, UInt32);
+ HANDLE_TYPE(UINT64, UInt64);
+ HANDLE_TYPE(FLOAT , Float );
+ HANDLE_TYPE(DOUBLE, Double);
+ HANDLE_TYPE(BOOL , Bool );
+ HANDLE_TYPE(STRING, String);
+ HANDLE_TYPE(ENUM , Enum );
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ to_reflection->AddMessage(to, field)->MergeFrom(
+ from_reflection->GetRepeatedMessage(from, field, j));
+ break;
+ }
+ }
+ } else {
+ switch (field->cpp_type()) {
+#define HANDLE_TYPE(CPPTYPE, METHOD) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ to_reflection->Set##METHOD(to, field, \
+ from_reflection->Get##METHOD(from, field)); \
+ break;
+
+ HANDLE_TYPE(INT32 , Int32 );
+ HANDLE_TYPE(INT64 , Int64 );
+ HANDLE_TYPE(UINT32, UInt32);
+ HANDLE_TYPE(UINT64, UInt64);
+ HANDLE_TYPE(FLOAT , Float );
+ HANDLE_TYPE(DOUBLE, Double);
+ HANDLE_TYPE(BOOL , Bool );
+ HANDLE_TYPE(STRING, String);
+ HANDLE_TYPE(ENUM , Enum );
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ to_reflection->MutableMessage(to, field)->MergeFrom(
+ from_reflection->GetMessage(from, field));
+ break;
+ }
+ }
+ }
+
+ to_reflection->MutableUnknownFields(to)->MergeFrom(
+ from_reflection->GetUnknownFields(from));
+}
+
+void ReflectionOps::Clear(Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(*message, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ reflection->ClearField(message, fields[i]);
+ }
+
+ reflection->MutableUnknownFields(message)->Clear();
+}
+
+bool ReflectionOps::IsInitialized(const Message& message) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ const Reflection* reflection = message.GetReflection();
+
+ // Check required fields of this message.
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ if (descriptor->field(i)->is_required()) {
+ if (!reflection->HasField(message, descriptor->field(i))) {
+ return false;
+ }
+ }
+ }
+
+ // Check that sub-messages are initialized.
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ const FieldDescriptor* field = fields[i];
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+
+ if (field->is_repeated()) {
+ int size = reflection->FieldSize(message, field);
+
+ for (int j = 0; j < size; j++) {
+ if (!reflection->GetRepeatedMessage(message, field, j)
+ .IsInitialized()) {
+ return false;
+ }
+ }
+ } else {
+ if (!reflection->GetMessage(message, field).IsInitialized()) {
+ return false;
+ }
+ }
+ }
+ }
+
+ return true;
+}
+
+void ReflectionOps::DiscardUnknownFields(Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ reflection->MutableUnknownFields(message)->Clear();
+
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(*message, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ const FieldDescriptor* field = fields[i];
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ if (field->is_repeated()) {
+ int size = reflection->FieldSize(*message, field);
+ for (int j = 0; j < size; j++) {
+ reflection->MutableRepeatedMessage(message, field, j)
+ ->DiscardUnknownFields();
+ }
+ } else {
+ reflection->MutableMessage(message, field)->DiscardUnknownFields();
+ }
+ }
+ }
+}
+
+static string SubMessagePrefix(const string& prefix,
+ const FieldDescriptor* field,
+ int index) {
+ string result(prefix);
+ if (field->is_extension()) {
+ result.append("(");
+ result.append(field->full_name());
+ result.append(")");
+ } else {
+ result.append(field->name());
+ }
+ if (index != -1) {
+ result.append("[");
+ result.append(SimpleItoa(index));
+ result.append("]");
+ }
+ result.append(".");
+ return result;
+}
+
+void ReflectionOps::FindInitializationErrors(
+ const Message& message,
+ const string& prefix,
+ vector<string>* errors) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ const Reflection* reflection = message.GetReflection();
+
+ // Check required fields of this message.
+ for (int i = 0; i < descriptor->field_count(); i++) {
+ if (descriptor->field(i)->is_required()) {
+ if (!reflection->HasField(message, descriptor->field(i))) {
+ errors->push_back(prefix + descriptor->field(i)->name());
+ }
+ }
+ }
+
+ // Check sub-messages.
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ const FieldDescriptor* field = fields[i];
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+
+ if (field->is_repeated()) {
+ int size = reflection->FieldSize(message, field);
+
+ for (int j = 0; j < size; j++) {
+ const Message& sub_message =
+ reflection->GetRepeatedMessage(message, field, j);
+ FindInitializationErrors(sub_message,
+ SubMessagePrefix(prefix, field, j),
+ errors);
+ }
+ } else {
+ const Message& sub_message = reflection->GetMessage(message, field);
+ FindInitializationErrors(sub_message,
+ SubMessagePrefix(prefix, field, -1),
+ errors);
+ }
+ }
+ }
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.h b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.h
new file mode 100644
index 0000000000..4775911e84
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops.h
@@ -0,0 +1,81 @@
+// 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 header is logically internal, but is made public because it is used
+// from protocol-compiler-generated code, which may reside in other components.
+
+#ifndef GOOGLE_PROTOBUF_REFLECTION_OPS_H__
+#define GOOGLE_PROTOBUF_REFLECTION_OPS_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/message.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Basic operations that can be performed using reflection.
+// These can be used as a cheap way to implement the corresponding
+// methods of the Message interface, though they are likely to be
+// slower than implementations tailored for the specific message type.
+//
+// This class should stay limited to operations needed to implement
+// the Message interface.
+//
+// This class is really a namespace that contains only static methods.
+class LIBPROTOBUF_EXPORT ReflectionOps {
+ public:
+ static void Copy(const Message& from, Message* to);
+ static void Merge(const Message& from, Message* to);
+ static void Clear(Message* message);
+ static bool IsInitialized(const Message& message);
+ static void DiscardUnknownFields(Message* message);
+
+ // Finds all unset required fields in the message and adds their full
+ // paths (e.g. "foo.bar[5].baz") to *names. "prefix" will be attached to
+ // the front of each name.
+ static void FindInitializationErrors(const Message& message,
+ const string& prefix,
+ vector<string>* errors);
+
+ private:
+ // All methods are static. No need to construct.
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ReflectionOps);
+};
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_REFLECTION_OPS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops_unittest.cc
new file mode 100644
index 0000000000..88d6bfb610
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/reflection_ops_unittest.cc
@@ -0,0 +1,476 @@
+// 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.
+
+#include <google/protobuf/reflection_ops.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/test_util.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+namespace {
+
+TEST(ReflectionOpsTest, SanityCheck) {
+ unittest::TestAllTypes message;
+
+ TestUtil::SetAllFields(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+}
+
+TEST(ReflectionOpsTest, Copy) {
+ unittest::TestAllTypes message, message2;
+
+ TestUtil::SetAllFields(&message);
+
+ ReflectionOps::Copy(message, &message2);
+
+ TestUtil::ExpectAllFieldsSet(message2);
+
+ // Copying from self should be a no-op.
+ ReflectionOps::Copy(message2, &message2);
+ TestUtil::ExpectAllFieldsSet(message2);
+}
+
+TEST(ReflectionOpsTest, CopyExtensions) {
+ unittest::TestAllExtensions message, message2;
+
+ TestUtil::SetAllExtensions(&message);
+
+ ReflectionOps::Copy(message, &message2);
+
+ TestUtil::ExpectAllExtensionsSet(message2);
+}
+
+TEST(ReflectionOpsTest, CopyOneof) {
+ unittest::TestOneof2 message, message2;
+ TestUtil::SetOneof1(&message);
+ ReflectionOps::Copy(message, &message2);
+ TestUtil::ExpectOneofSet1(message2);
+
+ TestUtil::SetOneof2(&message);
+ TestUtil::ExpectOneofSet2(message);
+ ReflectionOps::Copy(message, &message2);
+ TestUtil::ExpectOneofSet2(message2);
+}
+
+TEST(ReflectionOpsTest, Merge) {
+ // Note: Copy is implemented in terms of Merge() so technically the Copy
+ // test already tested most of this.
+
+ unittest::TestAllTypes message, message2;
+
+ TestUtil::SetAllFields(&message);
+
+ // This field will test merging into an empty spot.
+ message2.set_optional_int32(message.optional_int32());
+ message.clear_optional_int32();
+
+ // This tests overwriting.
+ message2.set_optional_string(message.optional_string());
+ message.set_optional_string("something else");
+
+ // This tests concatenating.
+ message2.add_repeated_int32(message.repeated_int32(1));
+ int32 i = message.repeated_int32(0);
+ message.clear_repeated_int32();
+ message.add_repeated_int32(i);
+
+ ReflectionOps::Merge(message2, &message);
+
+ TestUtil::ExpectAllFieldsSet(message);
+}
+
+TEST(ReflectionOpsTest, MergeExtensions) {
+ // Note: Copy is implemented in terms of Merge() so technically the Copy
+ // test already tested most of this.
+
+ unittest::TestAllExtensions message, message2;
+
+ TestUtil::SetAllExtensions(&message);
+
+ // This field will test merging into an empty spot.
+ message2.SetExtension(unittest::optional_int32_extension,
+ message.GetExtension(unittest::optional_int32_extension));
+ message.ClearExtension(unittest::optional_int32_extension);
+
+ // This tests overwriting.
+ message2.SetExtension(unittest::optional_string_extension,
+ message.GetExtension(unittest::optional_string_extension));
+ message.SetExtension(unittest::optional_string_extension, "something else");
+
+ // This tests concatenating.
+ message2.AddExtension(unittest::repeated_int32_extension,
+ message.GetExtension(unittest::repeated_int32_extension, 1));
+ int32 i = message.GetExtension(unittest::repeated_int32_extension, 0);
+ message.ClearExtension(unittest::repeated_int32_extension);
+ message.AddExtension(unittest::repeated_int32_extension, i);
+
+ ReflectionOps::Merge(message2, &message);
+
+ TestUtil::ExpectAllExtensionsSet(message);
+}
+
+TEST(ReflectionOpsTest, MergeUnknown) {
+ // Test that the messages' UnknownFieldSets are correctly merged.
+ unittest::TestEmptyMessage message1, message2;
+ message1.mutable_unknown_fields()->AddVarint(1234, 1);
+ message2.mutable_unknown_fields()->AddVarint(1234, 2);
+
+ ReflectionOps::Merge(message2, &message1);
+
+ ASSERT_EQ(2, message1.unknown_fields().field_count());
+ ASSERT_EQ(UnknownField::TYPE_VARINT,
+ message1.unknown_fields().field(0).type());
+ EXPECT_EQ(1, message1.unknown_fields().field(0).varint());
+ ASSERT_EQ(UnknownField::TYPE_VARINT,
+ message1.unknown_fields().field(1).type());
+ EXPECT_EQ(2, message1.unknown_fields().field(1).varint());
+}
+
+TEST(ReflectionOpsTest, MergeOneof) {
+ unittest::TestOneof2 message1, message2;
+ TestUtil::SetOneof1(&message1);
+
+ // Merge to empty message
+ ReflectionOps::Merge(message1, &message2);
+ TestUtil::ExpectOneofSet1(message2);
+
+ // Merge with the same oneof fields
+ ReflectionOps::Merge(message1, &message2);
+ TestUtil::ExpectOneofSet1(message2);
+
+ // Merge with different oneof fields
+ TestUtil::SetOneof2(&message1);
+ ReflectionOps::Merge(message1, &message2);
+ TestUtil::ExpectOneofSet2(message2);
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+
+TEST(ReflectionOpsTest, MergeFromSelf) {
+ // Note: Copy is implemented in terms of Merge() so technically the Copy
+ // test already tested most of this.
+
+ unittest::TestAllTypes message;
+
+ EXPECT_DEATH(
+ ReflectionOps::Merge(message, &message),
+ "&from");
+}
+
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST(ReflectionOpsTest, Clear) {
+ unittest::TestAllTypes message;
+
+ TestUtil::SetAllFields(&message);
+
+ ReflectionOps::Clear(&message);
+
+ TestUtil::ExpectClear(message);
+
+ // Check that getting embedded messages returns the objects created during
+ // SetAllFields() rather than default instances.
+ EXPECT_NE(&unittest::TestAllTypes::OptionalGroup::default_instance(),
+ &message.optionalgroup());
+ EXPECT_NE(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &message.optional_nested_message());
+ EXPECT_NE(&unittest::ForeignMessage::default_instance(),
+ &message.optional_foreign_message());
+ EXPECT_NE(&unittest_import::ImportMessage::default_instance(),
+ &message.optional_import_message());
+}
+
+TEST(ReflectionOpsTest, ClearExtensions) {
+ unittest::TestAllExtensions message;
+
+ TestUtil::SetAllExtensions(&message);
+
+ ReflectionOps::Clear(&message);
+
+ TestUtil::ExpectExtensionsClear(message);
+
+ // Check that getting embedded messages returns the objects created during
+ // SetAllExtensions() rather than default instances.
+ EXPECT_NE(&unittest::OptionalGroup_extension::default_instance(),
+ &message.GetExtension(unittest::optionalgroup_extension));
+ EXPECT_NE(&unittest::TestAllTypes::NestedMessage::default_instance(),
+ &message.GetExtension(unittest::optional_nested_message_extension));
+ EXPECT_NE(&unittest::ForeignMessage::default_instance(),
+ &message.GetExtension(
+ unittest::optional_foreign_message_extension));
+ EXPECT_NE(&unittest_import::ImportMessage::default_instance(),
+ &message.GetExtension(unittest::optional_import_message_extension));
+}
+
+TEST(ReflectionOpsTest, ClearUnknown) {
+ // Test that the message's UnknownFieldSet is correctly cleared.
+ unittest::TestEmptyMessage message;
+ message.mutable_unknown_fields()->AddVarint(1234, 1);
+
+ ReflectionOps::Clear(&message);
+
+ EXPECT_EQ(0, message.unknown_fields().field_count());
+}
+
+TEST(ReflectionOpsTest, ClearOneof) {
+ unittest::TestOneof2 message;
+
+ TestUtil::ExpectOneofClear(message);
+ TestUtil::SetOneof1(&message);
+ TestUtil::ExpectOneofSet1(message);
+ ReflectionOps::Clear(&message);
+ TestUtil::ExpectOneofClear(message);
+
+ TestUtil::SetOneof1(&message);
+ TestUtil::ExpectOneofSet1(message);
+ TestUtil::SetOneof2(&message);
+ TestUtil::ExpectOneofSet2(message);
+ ReflectionOps::Clear(&message);
+ TestUtil::ExpectOneofClear(message);
+}
+
+TEST(ReflectionOpsTest, DiscardUnknownFields) {
+ unittest::TestAllTypes message;
+ TestUtil::SetAllFields(&message);
+
+ // Set some unknown fields in message.
+ message.mutable_unknown_fields()
+ ->AddVarint(123456, 654321);
+ message.mutable_optional_nested_message()
+ ->mutable_unknown_fields()
+ ->AddVarint(123456, 654321);
+ message.mutable_repeated_nested_message(0)
+ ->mutable_unknown_fields()
+ ->AddVarint(123456, 654321);
+
+ EXPECT_EQ(1, message.unknown_fields().field_count());
+ EXPECT_EQ(1, message.optional_nested_message()
+ .unknown_fields().field_count());
+ EXPECT_EQ(1, message.repeated_nested_message(0)
+ .unknown_fields().field_count());
+
+ // Discard them.
+ ReflectionOps::DiscardUnknownFields(&message);
+ TestUtil::ExpectAllFieldsSet(message);
+
+ EXPECT_EQ(0, message.unknown_fields().field_count());
+ EXPECT_EQ(0, message.optional_nested_message()
+ .unknown_fields().field_count());
+ EXPECT_EQ(0, message.repeated_nested_message(0)
+ .unknown_fields().field_count());
+}
+
+TEST(ReflectionOpsTest, DiscardUnknownExtensions) {
+ unittest::TestAllExtensions message;
+ TestUtil::SetAllExtensions(&message);
+
+ // Set some unknown fields.
+ message.mutable_unknown_fields()
+ ->AddVarint(123456, 654321);
+ message.MutableExtension(unittest::optional_nested_message_extension)
+ ->mutable_unknown_fields()
+ ->AddVarint(123456, 654321);
+ message.MutableExtension(unittest::repeated_nested_message_extension, 0)
+ ->mutable_unknown_fields()
+ ->AddVarint(123456, 654321);
+
+ EXPECT_EQ(1, message.unknown_fields().field_count());
+ EXPECT_EQ(1,
+ message.GetExtension(unittest::optional_nested_message_extension)
+ .unknown_fields().field_count());
+ EXPECT_EQ(1,
+ message.GetExtension(unittest::repeated_nested_message_extension, 0)
+ .unknown_fields().field_count());
+
+ // Discard them.
+ ReflectionOps::DiscardUnknownFields(&message);
+ TestUtil::ExpectAllExtensionsSet(message);
+
+ EXPECT_EQ(0, message.unknown_fields().field_count());
+ EXPECT_EQ(0,
+ message.GetExtension(unittest::optional_nested_message_extension)
+ .unknown_fields().field_count());
+ EXPECT_EQ(0,
+ message.GetExtension(unittest::repeated_nested_message_extension, 0)
+ .unknown_fields().field_count());
+}
+
+TEST(ReflectionOpsTest, IsInitialized) {
+ unittest::TestRequired message;
+
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+ message.set_a(1);
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+ message.set_b(2);
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+ message.set_c(3);
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+}
+
+TEST(ReflectionOpsTest, ForeignIsInitialized) {
+ unittest::TestRequiredForeign message;
+
+ // Starts out initialized because the foreign message is itself an optional
+ // field.
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+
+ // Once we create that field, the message is no longer initialized.
+ message.mutable_optional_message();
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+
+ // Initialize it. Now we're initialized.
+ message.mutable_optional_message()->set_a(1);
+ message.mutable_optional_message()->set_b(2);
+ message.mutable_optional_message()->set_c(3);
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+
+ // Add a repeated version of the message. No longer initialized.
+ unittest::TestRequired* sub_message = message.add_repeated_message();
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+
+ // Initialize that repeated version.
+ sub_message->set_a(1);
+ sub_message->set_b(2);
+ sub_message->set_c(3);
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+}
+
+TEST(ReflectionOpsTest, ExtensionIsInitialized) {
+ unittest::TestAllExtensions message;
+
+ // Starts out initialized because the foreign message is itself an optional
+ // field.
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+
+ // Once we create that field, the message is no longer initialized.
+ message.MutableExtension(unittest::TestRequired::single);
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+
+ // Initialize it. Now we're initialized.
+ message.MutableExtension(unittest::TestRequired::single)->set_a(1);
+ message.MutableExtension(unittest::TestRequired::single)->set_b(2);
+ message.MutableExtension(unittest::TestRequired::single)->set_c(3);
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+
+ // Add a repeated version of the message. No longer initialized.
+ message.AddExtension(unittest::TestRequired::multi);
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+
+ // Initialize that repeated version.
+ message.MutableExtension(unittest::TestRequired::multi, 0)->set_a(1);
+ message.MutableExtension(unittest::TestRequired::multi, 0)->set_b(2);
+ message.MutableExtension(unittest::TestRequired::multi, 0)->set_c(3);
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+}
+
+TEST(ReflectionOpsTest, OneofIsInitialized) {
+ unittest::TestRequiredOneof message;
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+
+ message.mutable_foo_message();
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+
+ message.set_foo_int(1);
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+
+ message.mutable_foo_message();
+ EXPECT_FALSE(ReflectionOps::IsInitialized(message));
+ message.mutable_foo_message()->set_required_double(0.1);
+ EXPECT_TRUE(ReflectionOps::IsInitialized(message));
+}
+
+static string FindInitializationErrors(const Message& message) {
+ vector<string> errors;
+ ReflectionOps::FindInitializationErrors(message, "", &errors);
+ return Join(errors, ",");
+}
+
+TEST(ReflectionOpsTest, FindInitializationErrors) {
+ unittest::TestRequired message;
+ EXPECT_EQ("a,b,c", FindInitializationErrors(message));
+}
+
+TEST(ReflectionOpsTest, FindForeignInitializationErrors) {
+ unittest::TestRequiredForeign message;
+ message.mutable_optional_message();
+ message.add_repeated_message();
+ message.add_repeated_message();
+ EXPECT_EQ("optional_message.a,"
+ "optional_message.b,"
+ "optional_message.c,"
+ "repeated_message[0].a,"
+ "repeated_message[0].b,"
+ "repeated_message[0].c,"
+ "repeated_message[1].a,"
+ "repeated_message[1].b,"
+ "repeated_message[1].c",
+ FindInitializationErrors(message));
+}
+
+TEST(ReflectionOpsTest, FindExtensionInitializationErrors) {
+ unittest::TestAllExtensions message;
+ message.MutableExtension(unittest::TestRequired::single);
+ message.AddExtension(unittest::TestRequired::multi);
+ message.AddExtension(unittest::TestRequired::multi);
+ EXPECT_EQ("(protobuf_unittest.TestRequired.single).a,"
+ "(protobuf_unittest.TestRequired.single).b,"
+ "(protobuf_unittest.TestRequired.single).c,"
+ "(protobuf_unittest.TestRequired.multi)[0].a,"
+ "(protobuf_unittest.TestRequired.multi)[0].b,"
+ "(protobuf_unittest.TestRequired.multi)[0].c,"
+ "(protobuf_unittest.TestRequired.multi)[1].a,"
+ "(protobuf_unittest.TestRequired.multi)[1].b,"
+ "(protobuf_unittest.TestRequired.multi)[1].c",
+ FindInitializationErrors(message));
+}
+
+TEST(ReflectionOpsTest, FindOneofInitializationErrors) {
+ unittest::TestRequiredOneof message;
+ message.mutable_foo_message();
+ EXPECT_EQ("foo_message.required_double",
+ FindInitializationErrors(message));
+}
+
+} // namespace
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.cc b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.cc
new file mode 100644
index 0000000000..77004f59af
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.cc
@@ -0,0 +1,102 @@
+// 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.
+
+#include <algorithm>
+
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+namespace internal {
+
+void** RepeatedPtrFieldBase::InternalExtend(int extend_amount) {
+ int new_size = current_size_ + extend_amount;
+ if (total_size_ >= new_size) {
+ // N.B.: rep_ is non-NULL because extend_amount is always > 0, hence
+ // total_size must be non-zero since it is lower-bounded by new_size.
+ return &rep_->elements[current_size_];
+ }
+ Rep* old_rep = rep_;
+ Arena* arena = GetArenaNoVirtual();
+ new_size = std::max(kMinRepeatedFieldAllocationSize,
+ std::max(total_size_ * 2, new_size));
+ GOOGLE_CHECK_LE(new_size,
+ (std::numeric_limits<size_t>::max() - kRepHeaderSize) /
+ sizeof(old_rep->elements[0]))
+ << "Requested size is too large to fit into size_t.";
+ if (arena == NULL) {
+ rep_ = reinterpret_cast<Rep*>(
+ new char[kRepHeaderSize + sizeof(old_rep->elements[0]) * new_size]);
+ } else {
+ rep_ = reinterpret_cast<Rep*>(
+ ::google::protobuf::Arena::CreateArray<char>(arena,
+ kRepHeaderSize + sizeof(old_rep->elements[0]) * new_size));
+ }
+ total_size_ = new_size;
+ if (old_rep && old_rep->allocated_size > 0) {
+ memcpy(rep_->elements, old_rep->elements,
+ old_rep->allocated_size * sizeof(rep_->elements[0]));
+ rep_->allocated_size = old_rep->allocated_size;
+ } else {
+ rep_->allocated_size = 0;
+ }
+ if (arena == NULL) {
+ delete [] reinterpret_cast<char*>(old_rep);
+ }
+ return &rep_->elements[current_size_];
+}
+
+void RepeatedPtrFieldBase::Reserve(int new_size) {
+ if (new_size > current_size_) {
+ InternalExtend(new_size - current_size_);
+ }
+}
+
+void RepeatedPtrFieldBase::CloseGap(int start, int num) {
+ if (rep_ == NULL) return;
+ // Close up a gap of "num" elements starting at offset "start".
+ for (int i = start + num; i < rep_->allocated_size; ++i)
+ rep_->elements[i - num] = rep_->elements[i];
+ current_size_ -= num;
+ rep_->allocated_size -= num;
+}
+
+} // namespace internal
+
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.h b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.h
new file mode 100644
index 0000000000..bc5675554d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field.h
@@ -0,0 +1,2481 @@
+// 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.
+//
+// RepeatedField and RepeatedPtrField are used by generated protocol message
+// classes to manipulate repeated fields. These classes are very similar to
+// STL's vector, but include a number of optimizations found to be useful
+// specifically in the case of Protocol Buffers. RepeatedPtrField is
+// particularly different from STL vector as it manages ownership of the
+// pointers that it contains.
+//
+// Typically, clients should not need to access RepeatedField objects directly,
+// but should instead use the accessor functions generated automatically by the
+// protocol compiler.
+
+#ifndef GOOGLE_PROTOBUF_REPEATED_FIELD_H__
+#define GOOGLE_PROTOBUF_REPEATED_FIELD_H__
+
+#ifdef _MSC_VER
+// This is required for min/max on VS2013 only.
+#include <algorithm>
+#endif
+
+#include <string>
+#include <iterator>
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/type_traits.h>
+#include <google/protobuf/arena.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/message_lite.h>
+
+namespace google {
+
+namespace upb {
+namespace google_opensource {
+class GMR_Handlers;
+} // namespace google_opensource
+} // namespace upb
+
+namespace protobuf {
+
+class Message;
+
+namespace internal {
+
+static const int kMinRepeatedFieldAllocationSize = 4;
+
+// A utility function for logging that doesn't need any template types.
+void LogIndexOutOfBounds(int index, int size);
+
+template <typename Iter>
+inline int CalculateReserve(Iter begin, Iter end, std::forward_iterator_tag) {
+ return std::distance(begin, end);
+}
+
+template <typename Iter>
+inline int CalculateReserve(Iter /*begin*/, Iter /*end*/,
+ std::input_iterator_tag /*unused*/) {
+ return -1;
+}
+
+template <typename Iter>
+inline int CalculateReserve(Iter begin, Iter end) {
+ typedef typename std::iterator_traits<Iter>::iterator_category Category;
+ return CalculateReserve(begin, end, Category());
+}
+} // namespace internal
+
+
+// RepeatedField is used to represent repeated fields of a primitive type (in
+// other words, everything except strings and nested Messages). Most users will
+// not ever use a RepeatedField directly; they will use the get-by-index,
+// set-by-index, and add accessors that are generated for all repeated fields.
+template <typename Element>
+class RepeatedField {
+ public:
+ RepeatedField();
+ explicit RepeatedField(Arena* arena);
+ RepeatedField(const RepeatedField& other);
+ template <typename Iter>
+ RepeatedField(Iter begin, const Iter& end);
+ ~RepeatedField();
+
+ RepeatedField& operator=(const RepeatedField& other);
+
+ bool empty() const;
+ int size() const;
+
+ const Element& Get(int index) const;
+ Element* Mutable(int index);
+ void Set(int index, const Element& value);
+ void Add(const Element& value);
+ Element* Add();
+ // Remove the last element in the array.
+ void RemoveLast();
+
+ // Extract elements with indices in "[start .. start+num-1]".
+ // Copy them into "elements[0 .. num-1]" if "elements" is not NULL.
+ // Caution: implementation also moves elements with indices [start+num ..].
+ // Calling this routine inside a loop can cause quadratic behavior.
+ void ExtractSubrange(int start, int num, Element* elements);
+
+ void Clear();
+ void MergeFrom(const RepeatedField& other);
+ void CopyFrom(const RepeatedField& other);
+
+ // Reserve space to expand the field to at least the given size. If the
+ // array is grown, it will always be at least doubled in size.
+ void Reserve(int new_size);
+
+ // Resize the RepeatedField to a new, smaller size. This is O(1).
+ void Truncate(int new_size);
+
+ void AddAlreadyReserved(const Element& value);
+ Element* AddAlreadyReserved();
+ int Capacity() const;
+
+ // Like STL resize. Uses value to fill appended elements.
+ // Like Truncate() if new_size <= size(), otherwise this is
+ // O(new_size - size()).
+ void Resize(int new_size, const Element& value);
+
+ // Gets the underlying array. This pointer is possibly invalidated by
+ // any add or remove operation.
+ Element* mutable_data();
+ const Element* data() const;
+
+ // Swap entire contents with "other". If they are separate arenas then, copies
+ // data between each other.
+ void Swap(RepeatedField* other);
+
+ // Swap entire contents with "other". Should be called only if the caller can
+ // guarantee that both repeated fields are on the same arena or are on the
+ // heap. Swapping between different arenas is disallowed and caught by a
+ // GOOGLE_DCHECK (see API docs for details).
+ void UnsafeArenaSwap(RepeatedField* other);
+
+ // Swap two elements.
+ void SwapElements(int index1, int index2);
+
+ // STL-like iterator support
+ typedef Element* iterator;
+ typedef const Element* const_iterator;
+ typedef Element value_type;
+ typedef value_type& reference;
+ typedef const value_type& const_reference;
+ typedef value_type* pointer;
+ typedef const value_type* const_pointer;
+ typedef int size_type;
+ typedef ptrdiff_t difference_type;
+
+ iterator begin();
+ const_iterator begin() const;
+ const_iterator cbegin() const;
+ iterator end();
+ const_iterator end() const;
+ const_iterator cend() const;
+
+ // Reverse iterator support
+ typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
+ typedef std::reverse_iterator<iterator> reverse_iterator;
+ reverse_iterator rbegin() {
+ return reverse_iterator(end());
+ }
+ const_reverse_iterator rbegin() const {
+ return const_reverse_iterator(end());
+ }
+ reverse_iterator rend() {
+ return reverse_iterator(begin());
+ }
+ const_reverse_iterator rend() const {
+ return const_reverse_iterator(begin());
+ }
+
+ // Returns the number of bytes used by the repeated field, excluding
+ // sizeof(*this)
+ int SpaceUsedExcludingSelf() const;
+
+ // Removes the element referenced by position.
+ //
+ // Returns an iterator to the element immediately following the removed
+ // element.
+ //
+ // Invalidates all iterators at or after the removed element, including end().
+ iterator erase(const_iterator position);
+
+ // Removes the elements in the range [first, last).
+ //
+ // Returns an iterator to the element immediately following the removed range.
+ //
+ // Invalidates all iterators at or after the removed range, including end().
+ iterator erase(const_iterator first, const_iterator last);
+
+ // Get the Arena on which this RepeatedField stores its elements.
+ ::google::protobuf::Arena* GetArena() const {
+ return GetArenaNoVirtual();
+ }
+
+ private:
+ static const int kInitialSize = 0;
+ // A note on the representation here (see also comment below for
+ // RepeatedPtrFieldBase's struct Rep):
+ //
+ // We maintain the same sizeof(RepeatedField) as before we added arena support
+ // so that we do not degrade performance by bloating memory usage. Directly
+ // adding an arena_ element to RepeatedField is quite costly. By using
+ // indirection in this way, we keep the same size when the RepeatedField is
+ // empty (common case), and add only an 8-byte header to the elements array
+ // when non-empty. We make sure to place the size fields directly in the
+ // RepeatedField class to avoid costly cache misses due to the indirection.
+ int current_size_;
+ int total_size_;
+ struct Rep {
+ Arena* arena;
+ Element elements[1];
+ };
+ // We can not use sizeof(Rep) - sizeof(Element) due to the trailing padding on
+ // the struct. We can not use sizeof(Arena*) as well because there might be
+ // a "gap" after the field arena and before the field elements (e.g., when
+ // Element is double and pointer is 32bit).
+ static const size_t kRepHeaderSize;
+ // Contains arena ptr and the elements array. We also keep the invariant that
+ // if rep_ is NULL, then arena is NULL.
+ Rep* rep_;
+
+ friend class Arena;
+ typedef void InternalArenaConstructable_;
+
+ // Move the contents of |from| into |to|, possibly clobbering |from| in the
+ // process. For primitive types this is just a memcpy(), but it could be
+ // specialized for non-primitive types to, say, swap each element instead.
+ void MoveArray(Element* to, Element* from, int size);
+
+ // Copy the elements of |from| into |to|.
+ void CopyArray(Element* to, const Element* from, int size);
+
+ inline void InternalSwap(RepeatedField* other);
+
+ // Internal helper expected by Arena methods.
+ inline Arena* GetArenaNoVirtual() const {
+ return (rep_ == NULL) ? NULL : rep_->arena;
+ }
+
+ // Internal helper to delete all elements and deallocate the storage.
+ // If Element has a trivial destructor (for example, if it's a fundamental
+ // type, like int32), the loop will be removed by the optimizer.
+ void InternalDeallocate(Rep* rep, int size) {
+ if (rep != NULL) {
+ Element* e = &rep->elements[0];
+ Element* limit = &rep->elements[size];
+ for (; e < limit; e++) {
+ e->Element::~Element();
+ }
+ if (rep->arena == NULL) {
+ delete[] reinterpret_cast<char*>(rep);
+ }
+ }
+ }
+};
+
+template<typename Element>
+const size_t RepeatedField<Element>::kRepHeaderSize =
+ reinterpret_cast<size_t>(&reinterpret_cast<Rep*>(16)->elements[0]) - 16;
+
+namespace internal {
+template <typename It> class RepeatedPtrIterator;
+template <typename It, typename VoidPtr> class RepeatedPtrOverPtrsIterator;
+} // namespace internal
+
+namespace internal {
+
+// This is a helper template to copy an array of elements effeciently when they
+// have a trivial copy constructor, and correctly otherwise. This really
+// shouldn't be necessary, but our compiler doesn't optimize std::copy very
+// effectively.
+template <typename Element,
+ bool HasTrivialCopy = has_trivial_copy<Element>::value>
+struct ElementCopier {
+ void operator()(Element* to, const Element* from, int array_size);
+};
+
+} // namespace internal
+
+namespace internal {
+
+// type-traits helper for RepeatedPtrFieldBase: we only want to invoke
+// arena-related "copy if on different arena" behavior if the necessary methods
+// exist on the contained type. In particular, we rely on MergeFrom() existing
+// as a general proxy for the fact that a copy will work, and we also provide a
+// specific override for string*.
+template<typename T>
+struct TypeImplementsMergeBehavior {
+ typedef char HasMerge;
+ typedef long HasNoMerge;
+
+ // We accept either of:
+ // - void MergeFrom(const T& other)
+ // - bool MergeFrom(const T& other)
+ //
+ // We mangle these names a bit to avoid compatibility issues in 'unclean'
+ // include environments that may have, e.g., "#define test ..." (yes, this
+ // exists).
+ template<typename U, typename RetType, RetType (U::*)(const U& arg)>
+ struct CheckType;
+ template<typename U> static HasMerge Check(
+ CheckType<U, void, &U::MergeFrom>*);
+ template<typename U> static HasMerge Check(
+ CheckType<U, bool, &U::MergeFrom>*);
+ template<typename U> static HasNoMerge Check(...);
+
+ // Resovles to either google::protobuf::internal::true_type or google::protobuf::internal::false_type.
+ typedef google::protobuf::internal::integral_constant<bool,
+ (sizeof(Check<T>(0)) == sizeof(HasMerge))> type;
+};
+
+template<>
+struct TypeImplementsMergeBehavior< ::std::string > {
+ typedef google::protobuf::internal::true_type type;
+};
+
+// This is the common base class for RepeatedPtrFields. It deals only in void*
+// pointers. Users should not use this interface directly.
+//
+// The methods of this interface correspond to the methods of RepeatedPtrField,
+// but may have a template argument called TypeHandler. Its signature is:
+// class TypeHandler {
+// public:
+// typedef MyType Type;
+// static Type* New();
+// static void Delete(Type*);
+// static void Clear(Type*);
+// static void Merge(const Type& from, Type* to);
+//
+// // Only needs to be implemented if SpaceUsedExcludingSelf() is called.
+// static int SpaceUsed(const Type&);
+// };
+class LIBPROTOBUF_EXPORT RepeatedPtrFieldBase {
+ protected:
+ // The reflection implementation needs to call protected methods directly,
+ // reinterpreting pointers as being to Message instead of a specific Message
+ // subclass.
+ friend class GeneratedMessageReflection;
+
+ // ExtensionSet stores repeated message extensions as
+ // RepeatedPtrField<MessageLite>, but non-lite ExtensionSets need to
+ // implement SpaceUsed(), and thus need to call SpaceUsedExcludingSelf()
+ // reinterpreting MessageLite as Message. ExtensionSet also needs to make
+ // use of AddFromCleared(), which is not part of the public interface.
+ friend class ExtensionSet;
+
+ // The MapFieldBase implementation needs to call protected methods directly,
+ // reinterpreting pointers as being to Message instead of a specific Message
+ // subclass.
+ friend class MapFieldBase;
+
+ // To parse directly into a proto2 generated class, the upb class GMR_Handlers
+ // needs to be able to modify a RepeatedPtrFieldBase directly.
+ friend class upb::google_opensource::GMR_Handlers;
+
+ RepeatedPtrFieldBase();
+ explicit RepeatedPtrFieldBase(::google::protobuf::Arena* arena);
+ ~RepeatedPtrFieldBase() {}
+
+ // Must be called from destructor.
+ template <typename TypeHandler>
+ void Destroy();
+
+ bool empty() const;
+ int size() const;
+
+ template <typename TypeHandler>
+ const typename TypeHandler::Type& Get(int index) const;
+ template <typename TypeHandler>
+ typename TypeHandler::Type* Mutable(int index);
+ template <typename TypeHandler>
+ void Delete(int index);
+ template <typename TypeHandler>
+ typename TypeHandler::Type* Add(typename TypeHandler::Type* prototype = NULL);
+
+ template <typename TypeHandler>
+ void RemoveLast();
+ template <typename TypeHandler>
+ void Clear();
+ template <typename TypeHandler>
+ void MergeFrom(const RepeatedPtrFieldBase& other);
+ template <typename TypeHandler>
+ void CopyFrom(const RepeatedPtrFieldBase& other);
+
+ void CloseGap(int start, int num);
+
+ void Reserve(int new_size);
+
+ int Capacity() const;
+
+ // Used for constructing iterators.
+ void* const* raw_data() const;
+ void** raw_mutable_data() const;
+
+ template <typename TypeHandler>
+ typename TypeHandler::Type** mutable_data();
+ template <typename TypeHandler>
+ const typename TypeHandler::Type* const* data() const;
+
+ template <typename TypeHandler>
+ GOOGLE_ATTRIBUTE_ALWAYS_INLINE void Swap(RepeatedPtrFieldBase* other);
+
+ void SwapElements(int index1, int index2);
+
+ template <typename TypeHandler>
+ int SpaceUsedExcludingSelf() const;
+
+
+ // Advanced memory management --------------------------------------
+
+ // Like Add(), but if there are no cleared objects to use, returns NULL.
+ template <typename TypeHandler>
+ typename TypeHandler::Type* AddFromCleared();
+
+ template<typename TypeHandler>
+ void AddAllocated(typename TypeHandler::Type* value) {
+ typename TypeImplementsMergeBehavior<typename TypeHandler::Type>::type t;
+ AddAllocatedInternal<TypeHandler>(value, t);
+ }
+
+ template <typename TypeHandler>
+ void UnsafeArenaAddAllocated(typename TypeHandler::Type* value);
+
+ template <typename TypeHandler>
+ typename TypeHandler::Type* ReleaseLast() {
+ typename TypeImplementsMergeBehavior<typename TypeHandler::Type>::type t;
+ return ReleaseLastInternal<TypeHandler>(t);
+ }
+
+ // Releases last element and returns it, but does not do out-of-arena copy.
+ // And just returns the raw pointer to the contained element in the arena.
+ template <typename TypeHandler>
+ typename TypeHandler::Type* UnsafeArenaReleaseLast();
+
+ int ClearedCount() const;
+ template <typename TypeHandler>
+ void AddCleared(typename TypeHandler::Type* value);
+ template <typename TypeHandler>
+ typename TypeHandler::Type* ReleaseCleared();
+
+ protected:
+ inline void InternalSwap(RepeatedPtrFieldBase* other);
+
+ template <typename TypeHandler>
+ void AddAllocatedInternal(typename TypeHandler::Type* value,
+ google::protobuf::internal::true_type);
+ template <typename TypeHandler>
+ void AddAllocatedInternal(typename TypeHandler::Type* value,
+ google::protobuf::internal::false_type);
+
+ template <typename TypeHandler> GOOGLE_ATTRIBUTE_NOINLINE
+ void AddAllocatedSlowWithCopy(typename TypeHandler::Type* value,
+ Arena* value_arena,
+ Arena* my_arena);
+ template <typename TypeHandler> GOOGLE_ATTRIBUTE_NOINLINE
+ void AddAllocatedSlowWithoutCopy(typename TypeHandler::Type* value);
+
+ template <typename TypeHandler>
+ typename TypeHandler::Type* ReleaseLastInternal(google::protobuf::internal::true_type);
+ template <typename TypeHandler>
+ typename TypeHandler::Type* ReleaseLastInternal(google::protobuf::internal::false_type);
+
+ template<typename TypeHandler> GOOGLE_ATTRIBUTE_NOINLINE
+ void SwapFallback(RepeatedPtrFieldBase* other);
+
+ inline Arena* GetArenaNoVirtual() const {
+ return arena_;
+ }
+
+ private:
+ static const int kInitialSize = 0;
+ // A few notes on internal representation:
+ //
+ // We use an indirected approach, with struct Rep, to keep
+ // sizeof(RepeatedPtrFieldBase) equivalent to what it was before arena support
+ // was added, namely, 3 8-byte machine words on x86-64. An instance of Rep is
+ // allocated only when the repeated field is non-empty, and it is a
+ // dynamically-sized struct (the header is directly followed by elements[]).
+ // We place arena_ and current_size_ directly in the object to avoid cache
+ // misses due to the indirection, because these fields are checked frequently.
+ // Placing all fields directly in the RepeatedPtrFieldBase instance costs
+ // significant performance for memory-sensitive workloads.
+ Arena* arena_;
+ int current_size_;
+ int total_size_;
+ struct Rep {
+ int allocated_size;
+ void* elements[1];
+ };
+ static const size_t kRepHeaderSize = sizeof(Rep) - sizeof(void*);
+ // Contains arena ptr and the elements array. We also keep the invariant that
+ // if rep_ is NULL, then arena is NULL.
+ Rep* rep_;
+
+ template <typename TypeHandler>
+ static inline typename TypeHandler::Type* cast(void* element) {
+ return reinterpret_cast<typename TypeHandler::Type*>(element);
+ }
+ template <typename TypeHandler>
+ static inline const typename TypeHandler::Type* cast(const void* element) {
+ return reinterpret_cast<const typename TypeHandler::Type*>(element);
+ }
+
+ // Non-templated inner function to avoid code duplication. Takes a function
+ // pointer to the type-specific (templated) inner allocate/merge loop.
+ void MergeFromInternal(
+ const RepeatedPtrFieldBase& other,
+ void (RepeatedPtrFieldBase::*inner_loop)(void**, void**, int, int));
+
+ template<typename TypeHandler>
+ void MergeFromInnerLoop(
+ void** our_elems, void** other_elems, int length, int already_allocated);
+
+ // Internal helper: extend array space if necessary to contain |extend_amount|
+ // more elements, and return a pointer to the element immediately following
+ // the old list of elements. This interface factors out common behavior from
+ // Reserve() and MergeFrom() to reduce code size. |extend_amount| must be > 0.
+ void** InternalExtend(int extend_amount);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RepeatedPtrFieldBase);
+};
+
+template <typename GenericType>
+class GenericTypeHandler {
+ public:
+ typedef GenericType Type;
+ static inline GenericType* New(Arena* arena) {
+ return ::google::protobuf::Arena::CreateMaybeMessage<Type>(
+ arena, static_cast<GenericType*>(0));
+ }
+ // We force NewFromPrototype() to be non-inline to reduce code size:
+ // else, several other methods get inlined copies of message types'
+ // constructors.
+ GOOGLE_ATTRIBUTE_NOINLINE static GenericType* NewFromPrototype(
+ const GenericType* prototype, ::google::protobuf::Arena* arena = NULL);
+ static inline void Delete(GenericType* value, Arena* arena) {
+ if (arena == NULL) {
+ delete value;
+ }
+ }
+ static inline ::google::protobuf::Arena* GetArena(GenericType* value) {
+ return ::google::protobuf::Arena::GetArena<Type>(value);
+ }
+ static inline void* GetMaybeArenaPointer(GenericType* value) {
+ return ::google::protobuf::Arena::GetArena<Type>(value);
+ }
+
+ static inline void Clear(GenericType* value) { value->Clear(); }
+ GOOGLE_ATTRIBUTE_NOINLINE static void Merge(const GenericType& from,
+ GenericType* to);
+ static inline int SpaceUsed(const GenericType& value) {
+ return value.SpaceUsed();
+ }
+ static inline const Type& default_instance() {
+ return Type::default_instance();
+ }
+};
+
+template <typename GenericType>
+GenericType* GenericTypeHandler<GenericType>::NewFromPrototype(
+ const GenericType* /* prototype */, ::google::protobuf::Arena* arena) {
+ return New(arena);
+}
+template <typename GenericType>
+void GenericTypeHandler<GenericType>::Merge(const GenericType& from,
+ GenericType* to) {
+ to->MergeFrom(from);
+}
+
+// NewFromPrototype() and Merge() cannot be defined here; if they're declared
+// inline the compiler will complain about not matching GOOGLE_ATTRIBUTE_NOINLINE
+// above, and if not, compilation will result in multiple definitions. These
+// are therefore declared as specializations here and defined in
+// message_lite.cc.
+template<>
+MessageLite* GenericTypeHandler<MessageLite>::NewFromPrototype(
+ const MessageLite* prototype, google::protobuf::Arena* arena);
+template<>
+inline google::protobuf::Arena* GenericTypeHandler<MessageLite>::GetArena(
+ MessageLite* value) {
+ return value->GetArena();
+}
+template<>
+inline void* GenericTypeHandler<MessageLite>::GetMaybeArenaPointer(
+ MessageLite* value) {
+ return value->GetMaybeArenaPointer();
+}
+template <>
+void GenericTypeHandler<MessageLite>::Merge(const MessageLite& from,
+ MessageLite* to);
+template<>
+inline void GenericTypeHandler<string>::Clear(string* value) {
+ value->clear();
+}
+template<>
+void GenericTypeHandler<string>::Merge(const string& from,
+ string* to);
+
+// Declarations of the specialization as we cannot define them here, as the
+// header that defines ProtocolMessage depends on types defined in this header.
+#define DECLARE_SPECIALIZATIONS_FOR_BASE_PROTO_TYPES(TypeName) \
+ template<> \
+ TypeName* GenericTypeHandler<TypeName>::NewFromPrototype( \
+ const TypeName* prototype, google::protobuf::Arena* arena); \
+ template<> \
+ google::protobuf::Arena* GenericTypeHandler<TypeName>::GetArena( \
+ TypeName* value); \
+ template<> \
+ void* GenericTypeHandler<TypeName>::GetMaybeArenaPointer( \
+ TypeName* value);
+
+// Message specialization bodies defined in message.cc. This split is necessary
+// to allow proto2-lite (which includes this header) to be independent of
+// Message.
+DECLARE_SPECIALIZATIONS_FOR_BASE_PROTO_TYPES(Message)
+
+
+#undef DECLARE_SPECIALIZATIONS_FOR_BASE_PROTO_TYPES
+
+template <>
+inline const MessageLite& GenericTypeHandler<MessageLite>::default_instance() {
+ // Yes, the behavior of the code is undefined, but this function is only
+ // called when we're already deep into the world of undefined, because the
+ // caller called Get(index) out of bounds.
+ MessageLite* null = NULL;
+ return *null;
+}
+
+template <>
+inline const Message& GenericTypeHandler<Message>::default_instance() {
+ // Yes, the behavior of the code is undefined, but this function is only
+ // called when we're already deep into the world of undefined, because the
+ // caller called Get(index) out of bounds.
+ Message* null = NULL;
+ return *null;
+}
+
+
+// HACK: If a class is declared as DLL-exported in MSVC, it insists on
+// generating copies of all its methods -- even inline ones -- to include
+// in the DLL. But SpaceUsed() calls StringSpaceUsedExcludingSelf() which
+// isn't in the lite library, therefore the lite library cannot link if
+// StringTypeHandler is exported. So, we factor out StringTypeHandlerBase,
+// export that, then make StringTypeHandler be a subclass which is NOT
+// exported.
+// TODO(kenton): Now that StringSpaceUsedExcludingSelf() is in the lite
+// library, this can be cleaned up.
+class LIBPROTOBUF_EXPORT StringTypeHandlerBase {
+ public:
+ typedef string Type;
+
+ static inline string* New(Arena* arena) {
+ return Arena::Create<string>(arena);
+ }
+ static inline string* NewFromPrototype(const string*,
+ ::google::protobuf::Arena* arena) {
+ return New(arena);
+ }
+ static inline ::google::protobuf::Arena* GetArena(string*) {
+ return NULL;
+ }
+ static inline void* GetMaybeArenaPointer(string* /* value */) {
+ return NULL;
+ }
+ static inline void Delete(string* value, Arena* arena) {
+ if (arena == NULL) {
+ delete value;
+ }
+ }
+ static inline void Clear(string* value) { value->clear(); }
+ static inline void Merge(const string& from, string* to) { *to = from; }
+ static inline const Type& default_instance() {
+ return ::google::protobuf::internal::GetEmptyString();
+ }
+};
+
+class StringTypeHandler : public StringTypeHandlerBase {
+ public:
+ static int SpaceUsed(const string& value) {
+ return static_cast<int>(sizeof(value)) + StringSpaceUsedExcludingSelf(value);
+ }
+};
+
+
+} // namespace internal
+
+// RepeatedPtrField is like RepeatedField, but used for repeated strings or
+// Messages.
+template <typename Element>
+class RepeatedPtrField : public internal::RepeatedPtrFieldBase {
+ public:
+ RepeatedPtrField();
+ explicit RepeatedPtrField(::google::protobuf::Arena* arena);
+
+ RepeatedPtrField(const RepeatedPtrField& other);
+ template <typename Iter>
+ RepeatedPtrField(Iter begin, const Iter& end);
+ ~RepeatedPtrField();
+
+ RepeatedPtrField& operator=(const RepeatedPtrField& other);
+
+ bool empty() const;
+ int size() const;
+
+ const Element& Get(int index) const;
+ Element* Mutable(int index);
+ Element* Add();
+
+ // Remove the last element in the array.
+ // Ownership of the element is retained by the array.
+ void RemoveLast();
+
+ // Delete elements with indices in the range [start .. start+num-1].
+ // Caution: implementation moves all elements with indices [start+num .. ].
+ // Calling this routine inside a loop can cause quadratic behavior.
+ void DeleteSubrange(int start, int num);
+
+ void Clear();
+ void MergeFrom(const RepeatedPtrField& other);
+ void CopyFrom(const RepeatedPtrField& other);
+
+ // Reserve space to expand the field to at least the given size. This only
+ // resizes the pointer array; it doesn't allocate any objects. If the
+ // array is grown, it will always be at least doubled in size.
+ void Reserve(int new_size);
+
+ int Capacity() const;
+
+ // Gets the underlying array. This pointer is possibly invalidated by
+ // any add or remove operation.
+ Element** mutable_data();
+ const Element* const* data() const;
+
+ // Swap entire contents with "other". If they are on separate arenas, then
+ // copies data.
+ void Swap(RepeatedPtrField* other);
+
+ // Swap entire contents with "other". Caller should guarantee that either both
+ // fields are on the same arena or both are on the heap. Swapping between
+ // different arenas with this function is disallowed and is caught via
+ // GOOGLE_DCHECK.
+ void UnsafeArenaSwap(RepeatedPtrField* other);
+
+ // Swap two elements.
+ void SwapElements(int index1, int index2);
+
+ // STL-like iterator support
+ typedef internal::RepeatedPtrIterator<Element> iterator;
+ typedef internal::RepeatedPtrIterator<const Element> const_iterator;
+ typedef Element value_type;
+ typedef value_type& reference;
+ typedef const value_type& const_reference;
+ typedef value_type* pointer;
+ typedef const value_type* const_pointer;
+ typedef int size_type;
+ typedef ptrdiff_t difference_type;
+
+ iterator begin();
+ const_iterator begin() const;
+ const_iterator cbegin() const;
+ iterator end();
+ const_iterator end() const;
+ const_iterator cend() const;
+
+ // Reverse iterator support
+ typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
+ typedef std::reverse_iterator<iterator> reverse_iterator;
+ reverse_iterator rbegin() {
+ return reverse_iterator(end());
+ }
+ const_reverse_iterator rbegin() const {
+ return const_reverse_iterator(end());
+ }
+ reverse_iterator rend() {
+ return reverse_iterator(begin());
+ }
+ const_reverse_iterator rend() const {
+ return const_reverse_iterator(begin());
+ }
+
+ // Custom STL-like iterator that iterates over and returns the underlying
+ // pointers to Element rather than Element itself.
+ typedef internal::RepeatedPtrOverPtrsIterator<Element, void*>
+ pointer_iterator;
+ typedef internal::RepeatedPtrOverPtrsIterator<const Element, const void*>
+ const_pointer_iterator;
+ pointer_iterator pointer_begin();
+ const_pointer_iterator pointer_begin() const;
+ pointer_iterator pointer_end();
+ const_pointer_iterator pointer_end() const;
+
+ // Returns (an estimate of) the number of bytes used by the repeated field,
+ // excluding sizeof(*this).
+ int SpaceUsedExcludingSelf() const;
+
+ // Advanced memory management --------------------------------------
+ // When hardcore memory management becomes necessary -- as it sometimes
+ // does here at Google -- the following methods may be useful.
+
+ // Add an already-allocated object, passing ownership to the
+ // RepeatedPtrField.
+ //
+ // Note that some special behavior occurs with respect to arenas:
+ //
+ // (i) if this field holds submessages, the new submessage will be copied if
+ // the original is in an arena and this RepeatedPtrField is either in a
+ // different arena, or on the heap.
+ // (ii) if this field holds strings, the passed-in string *must* be
+ // heap-allocated, not arena-allocated. There is no way to dynamically check
+ // this at runtime, so User Beware.
+ void AddAllocated(Element* value);
+
+ // Remove the last element and return it, passing ownership to the caller.
+ // Requires: size() > 0
+ //
+ // If this RepeatedPtrField is on an arena, an object copy is required to pass
+ // ownership back to the user (for compatible semantics). Use
+ // UnsafeArenaReleaseLast() if this behavior is undesired.
+ Element* ReleaseLast();
+
+ // Add an already-allocated object, skipping arena-ownership checks. The user
+ // must guarantee that the given object is in the same arena as this
+ // RepeatedPtrField.
+ // It is also useful in legacy code that uses temporary ownership to avoid
+ // copies. Example:
+ // RepeatedPtrField<T> temp_field;
+ // temp_field.AddAllocated(new T);
+ // ... // Do something with temp_field
+ // temp_field.ExtractSubrange(0, temp_field.size(), NULL);
+ // If you put temp_field on the arena this fails, because the ownership
+ // transfers to the arena at the "AddAllocated" call and is not released
+ // anymore causing a double delete. UnsafeArenaAddAllocated prevents this.
+ void UnsafeArenaAddAllocated(Element* value);
+
+ // Remove the last element and return it. Works only when operating on an
+ // arena. The returned pointer is to the original object in the arena, hence
+ // has the arena's lifetime.
+ // Requires: current_size_ > 0
+ Element* UnsafeArenaReleaseLast();
+
+ // Extract elements with indices in the range "[start .. start+num-1]".
+ // The caller assumes ownership of the extracted elements and is responsible
+ // for deleting them when they are no longer needed.
+ // If "elements" is non-NULL, then pointers to the extracted elements
+ // are stored in "elements[0 .. num-1]" for the convenience of the caller.
+ // If "elements" is NULL, then the caller must use some other mechanism
+ // to perform any further operations (like deletion) on these elements.
+ // Caution: implementation also moves elements with indices [start+num ..].
+ // Calling this routine inside a loop can cause quadratic behavior.
+ //
+ // Memory copying behavior is identical to ReleaseLast(), described above: if
+ // this RepeatedPtrField is on an arena, an object copy is performed for each
+ // returned element, so that all returned element pointers are to
+ // heap-allocated copies. If this copy is not desired, the user should call
+ // UnsafeArenaExtractSubrange().
+ void ExtractSubrange(int start, int num, Element** elements);
+
+ // Identical to ExtractSubrange() described above, except that when this
+ // repeated field is on an arena, no object copies are performed. Instead, the
+ // raw object pointers are returned. Thus, if on an arena, the returned
+ // objects must not be freed, because they will not be heap-allocated objects.
+ void UnsafeArenaExtractSubrange(int start, int num, Element** elements);
+
+ // When elements are removed by calls to RemoveLast() or Clear(), they
+ // are not actually freed. Instead, they are cleared and kept so that
+ // they can be reused later. This can save lots of CPU time when
+ // repeatedly reusing a protocol message for similar purposes.
+ //
+ // Hardcore programs may choose to manipulate these cleared objects
+ // to better optimize memory management using the following routines.
+
+ // Get the number of cleared objects that are currently being kept
+ // around for reuse.
+ int ClearedCount() const;
+ // Add an element to the pool of cleared objects, passing ownership to
+ // the RepeatedPtrField. The element must be cleared prior to calling
+ // this method.
+ //
+ // This method cannot be called when the repeated field is on an arena or when
+ // |value| is; both cases will trigger a GOOGLE_DCHECK-failure.
+ void AddCleared(Element* value);
+ // Remove a single element from the cleared pool and return it, passing
+ // ownership to the caller. The element is guaranteed to be cleared.
+ // Requires: ClearedCount() > 0
+ //
+ //
+ // This method cannot be called when the repeated field is on an arena; doing
+ // so will trigger a GOOGLE_DCHECK-failure.
+ Element* ReleaseCleared();
+
+ // Removes the element referenced by position.
+ //
+ // Returns an iterator to the element immediately following the removed
+ // element.
+ //
+ // Invalidates all iterators at or after the removed element, including end().
+ iterator erase(const_iterator position);
+
+ // Removes the elements in the range [first, last).
+ //
+ // Returns an iterator to the element immediately following the removed range.
+ //
+ // Invalidates all iterators at or after the removed range, including end().
+ iterator erase(const_iterator first, const_iterator last);
+
+ // Gets the arena on which this RepeatedPtrField stores its elements.
+ ::google::protobuf::Arena* GetArena() const {
+ return GetArenaNoVirtual();
+ }
+
+ protected:
+ // Note: RepeatedPtrField SHOULD NOT be subclassed by users. We only
+ // subclass it in one place as a hack for compatibility with proto1. The
+ // subclass needs to know about TypeHandler in order to call protected
+ // methods on RepeatedPtrFieldBase.
+ class TypeHandler;
+
+ // Internal arena accessor expected by helpers in Arena.
+ inline Arena* GetArenaNoVirtual() const;
+
+ private:
+ // Implementations for ExtractSubrange(). The copying behavior must be
+ // included only if the type supports the necessary operations (e.g.,
+ // MergeFrom()), so we must resolve this at compile time. ExtractSubrange()
+ // uses SFINAE to choose one of the below implementations.
+ void ExtractSubrangeInternal(int start, int num, Element** elements,
+ google::protobuf::internal::true_type);
+ void ExtractSubrangeInternal(int start, int num, Element** elements,
+ google::protobuf::internal::false_type);
+
+ friend class Arena;
+ typedef void InternalArenaConstructable_;
+
+};
+
+// implementation ====================================================
+
+template <typename Element>
+inline RepeatedField<Element>::RepeatedField()
+ : current_size_(0),
+ total_size_(0),
+ rep_(NULL) {
+}
+
+template <typename Element>
+inline RepeatedField<Element>::RepeatedField(Arena* arena)
+ : current_size_(0),
+ total_size_(0),
+ rep_(NULL) {
+ // In case arena is NULL, then we do not create rep_, as code has an invariant
+ // `rep_ == NULL then arena == NULL`.
+ if (arena != NULL) {
+ rep_ = reinterpret_cast<Rep*>(
+ ::google::protobuf::Arena::CreateArray<char>(arena, kRepHeaderSize));
+ rep_->arena = arena;
+ }
+}
+
+template <typename Element>
+inline RepeatedField<Element>::RepeatedField(const RepeatedField& other)
+ : current_size_(0),
+ total_size_(0),
+ rep_(NULL) {
+ CopyFrom(other);
+}
+
+template <typename Element>
+template <typename Iter>
+RepeatedField<Element>::RepeatedField(Iter begin, const Iter& end)
+ : current_size_(0),
+ total_size_(0),
+ rep_(NULL) {
+ int reserve = internal::CalculateReserve(begin, end);
+ if (reserve != -1) {
+ Reserve(reserve);
+ for (; begin != end; ++begin) {
+ AddAlreadyReserved(*begin);
+ }
+ } else {
+ for (; begin != end; ++begin) {
+ Add(*begin);
+ }
+ }
+}
+
+template <typename Element>
+RepeatedField<Element>::~RepeatedField() {
+ // See explanation in Reserve(): we need to invoke destructors here for the
+ // case that Element has a non-trivial destructor.
+ InternalDeallocate(rep_, total_size_);
+}
+
+template <typename Element>
+inline RepeatedField<Element>&
+RepeatedField<Element>::operator=(const RepeatedField& other) {
+ if (this != &other)
+ CopyFrom(other);
+ return *this;
+}
+
+template <typename Element>
+inline bool RepeatedField<Element>::empty() const {
+ return current_size_ == 0;
+}
+
+template <typename Element>
+inline int RepeatedField<Element>::size() const {
+ return current_size_;
+}
+
+template <typename Element>
+inline int RepeatedField<Element>::Capacity() const {
+ return total_size_;
+}
+
+template<typename Element>
+inline void RepeatedField<Element>::AddAlreadyReserved(const Element& value) {
+ GOOGLE_DCHECK_LT(current_size_, total_size_);
+ rep_->elements[current_size_++] = value;
+}
+
+template<typename Element>
+inline Element* RepeatedField<Element>::AddAlreadyReserved() {
+ GOOGLE_DCHECK_LT(current_size_, total_size_);
+ return &rep_->elements[current_size_++];
+}
+
+template<typename Element>
+inline void RepeatedField<Element>::Resize(int new_size, const Element& value) {
+ GOOGLE_DCHECK_GE(new_size, 0);
+ if (new_size > current_size_) {
+ Reserve(new_size);
+ std::fill(&rep_->elements[current_size_],
+ &rep_->elements[new_size], value);
+ }
+ current_size_ = new_size;
+}
+
+template <typename Element>
+inline const Element& RepeatedField<Element>::Get(int index) const {
+ GOOGLE_DCHECK_GE(index, 0);
+ GOOGLE_DCHECK_LT(index, current_size_);
+ return rep_->elements[index];
+}
+
+template <typename Element>
+inline Element* RepeatedField<Element>::Mutable(int index) {
+ GOOGLE_DCHECK_GE(index, 0);
+ GOOGLE_DCHECK_LT(index, current_size_);
+ return &rep_->elements[index];
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::Set(int index, const Element& value) {
+ GOOGLE_DCHECK_GE(index, 0);
+ GOOGLE_DCHECK_LT(index, current_size_);
+ rep_->elements[index] = value;
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::Add(const Element& value) {
+ if (current_size_ == total_size_) Reserve(total_size_ + 1);
+ rep_->elements[current_size_++] = value;
+}
+
+template <typename Element>
+inline Element* RepeatedField<Element>::Add() {
+ if (current_size_ == total_size_) Reserve(total_size_ + 1);
+ return &rep_->elements[current_size_++];
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::RemoveLast() {
+ GOOGLE_DCHECK_GT(current_size_, 0);
+ current_size_--;
+}
+
+template <typename Element>
+void RepeatedField<Element>::ExtractSubrange(
+ int start, int num, Element* elements) {
+ GOOGLE_DCHECK_GE(start, 0);
+ GOOGLE_DCHECK_GE(num, 0);
+ GOOGLE_DCHECK_LE(start + num, this->current_size_);
+
+ // Save the values of the removed elements if requested.
+ if (elements != NULL) {
+ for (int i = 0; i < num; ++i)
+ elements[i] = this->Get(i + start);
+ }
+
+ // Slide remaining elements down to fill the gap.
+ if (num > 0) {
+ for (int i = start + num; i < this->current_size_; ++i)
+ this->Set(i - num, this->Get(i));
+ this->Truncate(this->current_size_ - num);
+ }
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::Clear() {
+ current_size_ = 0;
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::MergeFrom(const RepeatedField& other) {
+ GOOGLE_CHECK_NE(&other, this);
+ if (other.current_size_ != 0) {
+ Reserve(current_size_ + other.current_size_);
+ CopyArray(rep_->elements + current_size_,
+ other.rep_->elements, other.current_size_);
+ current_size_ += other.current_size_;
+ }
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::CopyFrom(const RepeatedField& other) {
+ if (&other == this) return;
+ Clear();
+ MergeFrom(other);
+}
+
+template <typename Element>
+inline typename RepeatedField<Element>::iterator RepeatedField<Element>::erase(
+ const_iterator position) {
+ return erase(position, position + 1);
+}
+
+template <typename Element>
+inline typename RepeatedField<Element>::iterator RepeatedField<Element>::erase(
+ const_iterator first, const_iterator last) {
+ size_type first_offset = first - cbegin();
+ if (first != last) {
+ Truncate(std::copy(last, cend(), begin() + first_offset) - cbegin());
+ }
+ return begin() + first_offset;
+}
+
+template <typename Element>
+inline Element* RepeatedField<Element>::mutable_data() {
+ return rep_ ? rep_->elements : NULL;
+}
+
+template <typename Element>
+inline const Element* RepeatedField<Element>::data() const {
+ return rep_ ? rep_->elements : NULL;
+}
+
+
+template <typename Element>
+inline void RepeatedField<Element>::InternalSwap(RepeatedField* other) {
+ std::swap(rep_, other->rep_);
+ std::swap(current_size_, other->current_size_);
+ std::swap(total_size_, other->total_size_);
+}
+
+template <typename Element>
+void RepeatedField<Element>::Swap(RepeatedField* other) {
+ if (this == other) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ RepeatedField<Element> temp(other->GetArenaNoVirtual());
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->UnsafeArenaSwap(&temp);
+ }
+}
+
+template <typename Element>
+void RepeatedField<Element>::UnsafeArenaSwap(RepeatedField* other) {
+ if (this == other) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+
+template <typename Element>
+void RepeatedField<Element>::SwapElements(int index1, int index2) {
+ using std::swap; // enable ADL with fallback
+ swap(rep_->elements[index1], rep_->elements[index2]);
+}
+
+template <typename Element>
+inline typename RepeatedField<Element>::iterator
+RepeatedField<Element>::begin() {
+ return rep_ ? rep_->elements : NULL;
+}
+template <typename Element>
+inline typename RepeatedField<Element>::const_iterator
+RepeatedField<Element>::begin() const {
+ return rep_ ? rep_->elements : NULL;
+}
+template <typename Element>
+inline typename RepeatedField<Element>::const_iterator
+RepeatedField<Element>::cbegin() const {
+ return rep_ ? rep_->elements : NULL;
+}
+template <typename Element>
+inline typename RepeatedField<Element>::iterator
+RepeatedField<Element>::end() {
+ return rep_ ? rep_->elements + current_size_ : NULL;
+}
+template <typename Element>
+inline typename RepeatedField<Element>::const_iterator
+RepeatedField<Element>::end() const {
+ return rep_ ? rep_->elements + current_size_ : NULL;
+}
+template <typename Element>
+inline typename RepeatedField<Element>::const_iterator
+RepeatedField<Element>::cend() const {
+ return rep_ ? rep_->elements + current_size_ : NULL;
+}
+
+template <typename Element>
+inline int RepeatedField<Element>::SpaceUsedExcludingSelf() const {
+ return rep_ ?
+ (total_size_ * sizeof(Element) + kRepHeaderSize) : 0;
+}
+
+// Avoid inlining of Reserve(): new, copy, and delete[] lead to a significant
+// amount of code bloat.
+template <typename Element>
+void RepeatedField<Element>::Reserve(int new_size) {
+ if (total_size_ >= new_size) return;
+ Rep* old_rep = rep_;
+ Arena* arena = GetArenaNoVirtual();
+ new_size = std::max(google::protobuf::internal::kMinRepeatedFieldAllocationSize,
+ std::max(total_size_ * 2, new_size));
+ GOOGLE_CHECK_LE(static_cast<size_t>(new_size),
+ (std::numeric_limits<size_t>::max() - kRepHeaderSize) /
+ sizeof(Element))
+ << "Requested size is too large to fit into size_t.";
+ if (arena == NULL) {
+ rep_ = reinterpret_cast<Rep*>(
+ new char[kRepHeaderSize + sizeof(Element) * new_size]);
+ } else {
+ rep_ = reinterpret_cast<Rep*>(
+ ::google::protobuf::Arena::CreateArray<char>(arena,
+ kRepHeaderSize + sizeof(Element) * new_size));
+ }
+ rep_->arena = arena;
+ int old_total_size = total_size_;
+ total_size_ = new_size;
+ // Invoke placement-new on newly allocated elements. We shouldn't have to do
+ // this, since Element is supposed to be POD, but a previous version of this
+ // code allocated storage with "new Element[size]" and some code uses
+ // RepeatedField with non-POD types, relying on constructor invocation. If
+ // Element has a trivial constructor (e.g., int32), gcc (tested with -O2)
+ // completely removes this loop because the loop body is empty, so this has no
+ // effect unless its side-effects are required for correctness.
+ // Note that we do this before MoveArray() below because Element's copy
+ // assignment implementation will want an initialized instance first.
+ Element* e = &rep_->elements[0];
+ Element* limit = &rep_->elements[total_size_];
+ for (; e < limit; e++) {
+ new (e) Element();
+ }
+ if (current_size_ > 0) {
+ MoveArray(rep_->elements, old_rep->elements, current_size_);
+ }
+
+ // Likewise, we need to invoke destructors on the old array.
+ InternalDeallocate(old_rep, old_total_size);
+
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::Truncate(int new_size) {
+ GOOGLE_DCHECK_LE(new_size, current_size_);
+ if (current_size_ > 0) {
+ current_size_ = new_size;
+ }
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::MoveArray(
+ Element* to, Element* from, int array_size) {
+ CopyArray(to, from, array_size);
+}
+
+template <typename Element>
+inline void RepeatedField<Element>::CopyArray(
+ Element* to, const Element* from, int array_size) {
+ internal::ElementCopier<Element>()(to, from, array_size);
+}
+
+namespace internal {
+
+template <typename Element, bool HasTrivialCopy>
+void ElementCopier<Element, HasTrivialCopy>::operator()(
+ Element* to, const Element* from, int array_size) {
+ std::copy(from, from + array_size, to);
+}
+
+template <typename Element>
+struct ElementCopier<Element, true> {
+ void operator()(Element* to, const Element* from, int array_size) {
+ memcpy(to, from, array_size * sizeof(Element));
+ }
+};
+
+} // namespace internal
+
+
+// -------------------------------------------------------------------
+
+namespace internal {
+
+inline RepeatedPtrFieldBase::RepeatedPtrFieldBase()
+ : arena_(NULL),
+ current_size_(0),
+ total_size_(0),
+ rep_(NULL) {
+}
+
+inline RepeatedPtrFieldBase::RepeatedPtrFieldBase(::google::protobuf::Arena* arena)
+ : arena_(arena),
+ current_size_(0),
+ total_size_(0),
+ rep_(NULL) {
+}
+
+template <typename TypeHandler>
+void RepeatedPtrFieldBase::Destroy() {
+ if (rep_ != NULL && arena_ == NULL) {
+ int n = rep_->allocated_size;
+ void* const* elements = rep_->elements;
+ for (int i = 0; i < n; i++) {
+ TypeHandler::Delete(cast<TypeHandler>(elements[i]), NULL);
+ }
+ delete[] reinterpret_cast<char*>(rep_);
+ }
+ rep_ = NULL;
+}
+
+template <typename TypeHandler>
+inline void RepeatedPtrFieldBase::Swap(RepeatedPtrFieldBase* other) {
+ if (other->GetArenaNoVirtual() == GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ SwapFallback<TypeHandler>(other);
+ }
+}
+
+template <typename TypeHandler>
+void RepeatedPtrFieldBase::SwapFallback(RepeatedPtrFieldBase* other) {
+ GOOGLE_DCHECK(other->GetArenaNoVirtual() != GetArenaNoVirtual());
+
+ // Copy semantics in this case. We try to improve efficiency by placing the
+ // temporary on |other|'s arena so that messages are copied cross-arena only
+ // once, not twice.
+ RepeatedPtrFieldBase temp(other->GetArenaNoVirtual());
+ temp.MergeFrom<TypeHandler>(*this);
+ this->Clear<TypeHandler>();
+ this->MergeFrom<TypeHandler>(*other);
+ other->Clear<TypeHandler>();
+ other->InternalSwap(&temp);
+ temp.Destroy<TypeHandler>(); // Frees rep_ if `other` had no arena.
+}
+
+inline bool RepeatedPtrFieldBase::empty() const {
+ return current_size_ == 0;
+}
+
+inline int RepeatedPtrFieldBase::size() const {
+ return current_size_;
+}
+
+template <typename TypeHandler>
+inline const typename TypeHandler::Type&
+RepeatedPtrFieldBase::Get(int index) const {
+ GOOGLE_DCHECK_GE(index, 0);
+ GOOGLE_DCHECK_LT(index, current_size_);
+ return *cast<TypeHandler>(rep_->elements[index]);
+}
+
+
+template <typename TypeHandler>
+inline typename TypeHandler::Type*
+RepeatedPtrFieldBase::Mutable(int index) {
+ GOOGLE_DCHECK_GE(index, 0);
+ GOOGLE_DCHECK_LT(index, current_size_);
+ return cast<TypeHandler>(rep_->elements[index]);
+}
+
+template <typename TypeHandler>
+inline void RepeatedPtrFieldBase::Delete(int index) {
+ GOOGLE_DCHECK_GE(index, 0);
+ GOOGLE_DCHECK_LT(index, current_size_);
+ TypeHandler::Delete(cast<TypeHandler>(rep_->elements[index]), arena_);
+}
+
+template <typename TypeHandler>
+inline typename TypeHandler::Type* RepeatedPtrFieldBase::Add(
+ typename TypeHandler::Type* prototype) {
+ if (rep_ != NULL && current_size_ < rep_->allocated_size) {
+ return cast<TypeHandler>(rep_->elements[current_size_++]);
+ }
+ if (!rep_ || rep_->allocated_size == total_size_) {
+ Reserve(total_size_ + 1);
+ }
+ ++rep_->allocated_size;
+ typename TypeHandler::Type* result =
+ TypeHandler::NewFromPrototype(prototype, arena_);
+ rep_->elements[current_size_++] = result;
+ return result;
+}
+
+template <typename TypeHandler>
+inline void RepeatedPtrFieldBase::RemoveLast() {
+ GOOGLE_DCHECK_GT(current_size_, 0);
+ TypeHandler::Clear(cast<TypeHandler>(rep_->elements[--current_size_]));
+}
+
+template <typename TypeHandler>
+void RepeatedPtrFieldBase::Clear() {
+ const int n = current_size_;
+ GOOGLE_DCHECK_GE(n, 0);
+ if (n > 0) {
+ void* const* elements = rep_->elements;
+ int i = 0;
+ do {
+ TypeHandler::Clear(cast<TypeHandler>(elements[i++]));
+ } while (i < n);
+ current_size_ = 0;
+ }
+}
+
+// To avoid unnecessary code duplication and reduce binary size, we use a
+// layered approach to implementing MergeFrom(). The toplevel method is
+// templated, so we get a small thunk per concrete message type in the binary.
+// This calls a shared implementation with most of the logic, passing a function
+// pointer to another type-specific piece of code that calls the object-allocate
+// and merge handlers.
+template <typename TypeHandler>
+inline void RepeatedPtrFieldBase::MergeFrom(const RepeatedPtrFieldBase& other) {
+ GOOGLE_DCHECK_NE(&other, this);
+ if (other.current_size_ == 0) return;
+ MergeFromInternal(
+ other, &RepeatedPtrFieldBase::MergeFromInnerLoop<TypeHandler>);
+}
+
+inline void RepeatedPtrFieldBase::MergeFromInternal(
+ const RepeatedPtrFieldBase& other,
+ void (RepeatedPtrFieldBase::*inner_loop)(void**, void**, int, int)) {
+ // Note: wrapper has already guaranteed that other.rep_ != NULL here.
+ int other_size = other.current_size_;
+ void** other_elements = other.rep_->elements;
+ void** new_elements = InternalExtend(other_size);
+ int allocated_elems = rep_->allocated_size - current_size_;
+ (this->*inner_loop)(new_elements, other_elements,
+ other_size, allocated_elems);
+ current_size_ += other_size;
+ if (rep_->allocated_size < current_size_) {
+ rep_->allocated_size = current_size_;
+ }
+}
+
+// Merges other_elems to our_elems.
+template<typename TypeHandler>
+void RepeatedPtrFieldBase::MergeFromInnerLoop(
+ void** our_elems, void** other_elems, int length, int already_allocated) {
+ // Split into two loops, over ranges [0, allocated) and [allocated, length),
+ // to avoid a branch within the loop.
+ for (int i = 0; i < already_allocated && i < length; i++) {
+ // Already allocated: use existing element.
+ typename TypeHandler::Type* other_elem =
+ reinterpret_cast<typename TypeHandler::Type*>(other_elems[i]);
+ typename TypeHandler::Type* new_elem =
+ reinterpret_cast<typename TypeHandler::Type*>(our_elems[i]);
+ TypeHandler::Merge(*other_elem, new_elem);
+ }
+ Arena* arena = GetArenaNoVirtual();
+ for (int i = already_allocated; i < length; i++) {
+ // Not allocated: alloc a new element first, then merge it.
+ typename TypeHandler::Type* other_elem =
+ reinterpret_cast<typename TypeHandler::Type*>(other_elems[i]);
+ typename TypeHandler::Type* new_elem =
+ TypeHandler::NewFromPrototype(other_elem, arena);
+ TypeHandler::Merge(*other_elem, new_elem);
+ our_elems[i] = new_elem;
+ }
+}
+
+template <typename TypeHandler>
+inline void RepeatedPtrFieldBase::CopyFrom(const RepeatedPtrFieldBase& other) {
+ if (&other == this) return;
+ RepeatedPtrFieldBase::Clear<TypeHandler>();
+ RepeatedPtrFieldBase::MergeFrom<TypeHandler>(other);
+}
+
+inline int RepeatedPtrFieldBase::Capacity() const {
+ return total_size_;
+}
+
+inline void* const* RepeatedPtrFieldBase::raw_data() const {
+ return rep_ ? rep_->elements : NULL;
+}
+
+inline void** RepeatedPtrFieldBase::raw_mutable_data() const {
+ return rep_ ? const_cast<void**>(rep_->elements) : NULL;
+}
+
+template <typename TypeHandler>
+inline typename TypeHandler::Type** RepeatedPtrFieldBase::mutable_data() {
+ // TODO(kenton): Breaks C++ aliasing rules. We should probably remove this
+ // method entirely.
+ return reinterpret_cast<typename TypeHandler::Type**>(raw_mutable_data());
+}
+
+template <typename TypeHandler>
+inline const typename TypeHandler::Type* const*
+RepeatedPtrFieldBase::data() const {
+ // TODO(kenton): Breaks C++ aliasing rules. We should probably remove this
+ // method entirely.
+ return reinterpret_cast<const typename TypeHandler::Type* const*>(raw_data());
+}
+
+inline void RepeatedPtrFieldBase::SwapElements(int index1, int index2) {
+ using std::swap; // enable ADL with fallback
+ swap(rep_->elements[index1], rep_->elements[index2]);
+}
+
+template <typename TypeHandler>
+inline int RepeatedPtrFieldBase::SpaceUsedExcludingSelf() const {
+ int allocated_bytes = total_size_ * sizeof(void*);
+ if (rep_ != NULL) {
+ for (int i = 0; i < rep_->allocated_size; ++i) {
+ allocated_bytes += TypeHandler::SpaceUsed(
+ *cast<TypeHandler>(rep_->elements[i]));
+ }
+ allocated_bytes += kRepHeaderSize;
+ }
+ return allocated_bytes;
+}
+
+template <typename TypeHandler>
+inline typename TypeHandler::Type* RepeatedPtrFieldBase::AddFromCleared() {
+ if (rep_ != NULL && current_size_ < rep_->allocated_size) {
+ return cast<TypeHandler>(rep_->elements[current_size_++]);
+ } else {
+ return NULL;
+ }
+}
+
+// AddAllocated version that implements arena-safe copying behavior.
+template <typename TypeHandler>
+void RepeatedPtrFieldBase::AddAllocatedInternal(
+ typename TypeHandler::Type* value,
+ google::protobuf::internal::true_type) {
+ Arena* element_arena = reinterpret_cast<Arena*>(
+ TypeHandler::GetMaybeArenaPointer(value));
+ Arena* arena = GetArenaNoVirtual();
+ if (arena == element_arena && rep_ &&
+ rep_->allocated_size < total_size_) {
+ // Fast path: underlying arena representation (tagged pointer) is equal to
+ // our arena pointer, and we can add to array without resizing it (at least
+ // one slot that is not allocated).
+ void** elems = rep_->elements;
+ if (current_size_ < rep_->allocated_size) {
+ // Make space at [current] by moving first allocated element to end of
+ // allocated list.
+ elems[rep_->allocated_size] = elems[current_size_];
+ }
+ elems[current_size_] = value;
+ current_size_ = current_size_ + 1;
+ rep_->allocated_size = rep_->allocated_size + 1;
+ return;
+ } else {
+ AddAllocatedSlowWithCopy<TypeHandler>(
+ value, TypeHandler::GetArena(value), arena);
+ }
+}
+
+// Slowpath handles all cases, copying if necessary.
+template<typename TypeHandler>
+void RepeatedPtrFieldBase::AddAllocatedSlowWithCopy(
+ // Pass value_arena and my_arena to avoid duplicate virtual call (value) or
+ // load (mine).
+ typename TypeHandler::Type* value, Arena* value_arena, Arena* my_arena) {
+ // Ensure that either the value is in the same arena, or if not, we do the
+ // appropriate thing: Own() it (if it's on heap and we're in an arena) or copy
+ // it to our arena/heap (otherwise).
+ if (my_arena != NULL && value_arena == NULL) {
+ my_arena->Own(value);
+ } else if (my_arena != value_arena) {
+ typename TypeHandler::Type* new_value =
+ TypeHandler::NewFromPrototype(value, my_arena);
+ TypeHandler::Merge(*value, new_value);
+ TypeHandler::Delete(value, value_arena);
+ value = new_value;
+ }
+
+ UnsafeArenaAddAllocated<TypeHandler>(value);
+}
+
+// AddAllocated version that does not implement arena-safe copying behavior.
+template <typename TypeHandler>
+void RepeatedPtrFieldBase::AddAllocatedInternal(
+ typename TypeHandler::Type* value,
+ google::protobuf::internal::false_type) {
+ if (rep_ && rep_->allocated_size < total_size_) {
+ // Fast path: underlying arena representation (tagged pointer) is equal to
+ // our arena pointer, and we can add to array without resizing it (at least
+ // one slot that is not allocated).
+ void** elems = rep_->elements;
+ if (current_size_ < rep_->allocated_size) {
+ // Make space at [current] by moving first allocated element to end of
+ // allocated list.
+ elems[rep_->allocated_size] = elems[current_size_];
+ }
+ elems[current_size_] = value;
+ current_size_ = current_size_ + 1;
+ ++rep_->allocated_size;
+ return;
+ } else {
+ UnsafeArenaAddAllocated<TypeHandler>(value);
+ }
+}
+
+template <typename TypeHandler>
+void RepeatedPtrFieldBase::UnsafeArenaAddAllocated(
+ typename TypeHandler::Type* value) {
+ // Make room for the new pointer.
+ if (!rep_ || current_size_ == total_size_) {
+ // The array is completely full with no cleared objects, so grow it.
+ Reserve(total_size_ + 1);
+ ++rep_->allocated_size;
+ } else if (rep_->allocated_size == total_size_) {
+ // There is no more space in the pointer array because it contains some
+ // cleared objects awaiting reuse. We don't want to grow the array in this
+ // case because otherwise a loop calling AddAllocated() followed by Clear()
+ // would leak memory.
+ TypeHandler::Delete(
+ cast<TypeHandler>(rep_->elements[current_size_]), arena_);
+ } else if (current_size_ < rep_->allocated_size) {
+ // We have some cleared objects. We don't care about their order, so we
+ // can just move the first one to the end to make space.
+ rep_->elements[rep_->allocated_size] = rep_->elements[current_size_];
+ ++rep_->allocated_size;
+ } else {
+ // There are no cleared objects.
+ ++rep_->allocated_size;
+ }
+
+ rep_->elements[current_size_++] = value;
+}
+
+// ReleaseLast() for types that implement merge/copy behavior.
+template <typename TypeHandler>
+inline typename TypeHandler::Type*
+RepeatedPtrFieldBase::ReleaseLastInternal(google::protobuf::internal::true_type) {
+ // First, release an element.
+ typename TypeHandler::Type* result = UnsafeArenaReleaseLast<TypeHandler>();
+ // Now perform a copy if we're on an arena.
+ Arena* arena = GetArenaNoVirtual();
+ if (arena == NULL) {
+ return result;
+ } else {
+ typename TypeHandler::Type* new_result =
+ TypeHandler::NewFromPrototype(result, NULL);
+ TypeHandler::Merge(*result, new_result);
+ return new_result;
+ }
+}
+
+// ReleaseLast() for types that *do not* implement merge/copy behavior -- this
+// is the same as UnsafeArenaReleaseLast(). Note that we GOOGLE_DCHECK-fail if we're on
+// an arena, since the user really should implement the copy operation in this
+// case.
+template <typename TypeHandler>
+inline typename TypeHandler::Type*
+RepeatedPtrFieldBase::ReleaseLastInternal(google::protobuf::internal::false_type) {
+ GOOGLE_DCHECK(GetArenaNoVirtual() == NULL)
+ << "ReleaseLast() called on a RepeatedPtrField that is on an arena, "
+ << "with a type that does not implement MergeFrom. This is unsafe; "
+ << "please implement MergeFrom for your type.";
+ return UnsafeArenaReleaseLast<TypeHandler>();
+}
+
+template <typename TypeHandler>
+inline typename TypeHandler::Type*
+ RepeatedPtrFieldBase::UnsafeArenaReleaseLast() {
+ GOOGLE_DCHECK_GT(current_size_, 0);
+ typename TypeHandler::Type* result =
+ cast<TypeHandler>(rep_->elements[--current_size_]);
+ --rep_->allocated_size;
+ if (current_size_ < rep_->allocated_size) {
+ // There are cleared elements on the end; replace the removed element
+ // with the last allocated element.
+ rep_->elements[current_size_] = rep_->elements[rep_->allocated_size];
+ }
+ return result;
+}
+
+inline int RepeatedPtrFieldBase::ClearedCount() const {
+ return rep_ ? (rep_->allocated_size - current_size_) : 0;
+}
+
+template <typename TypeHandler>
+inline void RepeatedPtrFieldBase::AddCleared(
+ typename TypeHandler::Type* value) {
+ GOOGLE_DCHECK(GetArenaNoVirtual() == NULL)
+ << "AddCleared() can only be used on a RepeatedPtrField not on an arena.";
+ GOOGLE_DCHECK(TypeHandler::GetArena(value) == NULL)
+ << "AddCleared() can only accept values not on an arena.";
+ if (!rep_ || rep_->allocated_size == total_size_) {
+ Reserve(total_size_ + 1);
+ }
+ rep_->elements[rep_->allocated_size++] = value;
+}
+
+template <typename TypeHandler>
+inline typename TypeHandler::Type* RepeatedPtrFieldBase::ReleaseCleared() {
+ GOOGLE_DCHECK(GetArenaNoVirtual() == NULL)
+ << "ReleaseCleared() can only be used on a RepeatedPtrField not on "
+ << "an arena.";
+ GOOGLE_DCHECK(GetArenaNoVirtual() == NULL);
+ GOOGLE_DCHECK(rep_ != NULL);
+ GOOGLE_DCHECK_GT(rep_->allocated_size, current_size_);
+ return cast<TypeHandler>(rep_->elements[--rep_->allocated_size]);
+}
+
+} // namespace internal
+
+// -------------------------------------------------------------------
+
+template <typename Element>
+class RepeatedPtrField<Element>::TypeHandler
+ : public internal::GenericTypeHandler<Element> {
+};
+
+template <>
+class RepeatedPtrField<string>::TypeHandler
+ : public internal::StringTypeHandler {
+};
+
+
+template <typename Element>
+inline RepeatedPtrField<Element>::RepeatedPtrField()
+ : RepeatedPtrFieldBase() {}
+
+template <typename Element>
+inline RepeatedPtrField<Element>::RepeatedPtrField(::google::protobuf::Arena* arena) :
+ RepeatedPtrFieldBase(arena) {}
+
+template <typename Element>
+inline RepeatedPtrField<Element>::RepeatedPtrField(
+ const RepeatedPtrField& other)
+ : RepeatedPtrFieldBase() {
+ CopyFrom(other);
+}
+
+template <typename Element>
+template <typename Iter>
+inline RepeatedPtrField<Element>::RepeatedPtrField(
+ Iter begin, const Iter& end) {
+ int reserve = internal::CalculateReserve(begin, end);
+ if (reserve != -1) {
+ Reserve(reserve);
+ }
+ for (; begin != end; ++begin) {
+ *Add() = *begin;
+ }
+}
+
+template <typename Element>
+RepeatedPtrField<Element>::~RepeatedPtrField() {
+ Destroy<TypeHandler>();
+}
+
+template <typename Element>
+inline RepeatedPtrField<Element>& RepeatedPtrField<Element>::operator=(
+ const RepeatedPtrField& other) {
+ if (this != &other)
+ CopyFrom(other);
+ return *this;
+}
+
+template <typename Element>
+inline bool RepeatedPtrField<Element>::empty() const {
+ return RepeatedPtrFieldBase::empty();
+}
+
+template <typename Element>
+inline int RepeatedPtrField<Element>::size() const {
+ return RepeatedPtrFieldBase::size();
+}
+
+template <typename Element>
+inline const Element& RepeatedPtrField<Element>::Get(int index) const {
+ return RepeatedPtrFieldBase::Get<TypeHandler>(index);
+}
+
+
+template <typename Element>
+inline Element* RepeatedPtrField<Element>::Mutable(int index) {
+ return RepeatedPtrFieldBase::Mutable<TypeHandler>(index);
+}
+
+template <typename Element>
+inline Element* RepeatedPtrField<Element>::Add() {
+ return RepeatedPtrFieldBase::Add<TypeHandler>();
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::RemoveLast() {
+ RepeatedPtrFieldBase::RemoveLast<TypeHandler>();
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::DeleteSubrange(int start, int num) {
+ GOOGLE_DCHECK_GE(start, 0);
+ GOOGLE_DCHECK_GE(num, 0);
+ GOOGLE_DCHECK_LE(start + num, size());
+ for (int i = 0; i < num; ++i) {
+ RepeatedPtrFieldBase::Delete<TypeHandler>(start + i);
+ }
+ ExtractSubrange(start, num, NULL);
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::ExtractSubrange(
+ int start, int num, Element** elements) {
+ typename internal::TypeImplementsMergeBehavior<
+ typename TypeHandler::Type>::type t;
+ ExtractSubrangeInternal(start, num, elements, t);
+}
+
+// ExtractSubrange() implementation for types that implement merge/copy
+// behavior.
+template <typename Element>
+inline void RepeatedPtrField<Element>::ExtractSubrangeInternal(
+ int start, int num, Element** elements, google::protobuf::internal::true_type) {
+ GOOGLE_DCHECK_GE(start, 0);
+ GOOGLE_DCHECK_GE(num, 0);
+ GOOGLE_DCHECK_LE(start + num, size());
+
+ if (num > 0) {
+ // Save the values of the removed elements if requested.
+ if (elements != NULL) {
+ if (GetArenaNoVirtual() != NULL) {
+ // If we're on an arena, we perform a copy for each element so that the
+ // returned elements are heap-allocated.
+ for (int i = 0; i < num; ++i) {
+ Element* element = RepeatedPtrFieldBase::
+ Mutable<TypeHandler>(i + start);
+ typename TypeHandler::Type* new_value =
+ TypeHandler::NewFromPrototype(element, NULL);
+ TypeHandler::Merge(*element, new_value);
+ elements[i] = new_value;
+ }
+ } else {
+ for (int i = 0; i < num; ++i) {
+ elements[i] = RepeatedPtrFieldBase::Mutable<TypeHandler>(i + start);
+ }
+ }
+ }
+ CloseGap(start, num);
+ }
+}
+
+// ExtractSubrange() implementation for types that do not implement merge/copy
+// behavior.
+template<typename Element>
+inline void RepeatedPtrField<Element>::ExtractSubrangeInternal(
+ int start, int num, Element** elements, google::protobuf::internal::false_type) {
+ // This case is identical to UnsafeArenaExtractSubrange(). However, since
+ // ExtractSubrange() must return heap-allocated objects by contract, and we
+ // cannot fulfill this contract if we are an on arena, we must GOOGLE_DCHECK() that
+ // we are not on an arena.
+ GOOGLE_DCHECK(GetArenaNoVirtual() == NULL)
+ << "ExtractSubrange() when arena is non-NULL is only supported when "
+ << "the Element type supplies a MergeFrom() operation to make copies.";
+ UnsafeArenaExtractSubrange(start, num, elements);
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::UnsafeArenaExtractSubrange(
+ int start, int num, Element** elements) {
+ GOOGLE_DCHECK_GE(start, 0);
+ GOOGLE_DCHECK_GE(num, 0);
+ GOOGLE_DCHECK_LE(start + num, size());
+
+ if (num > 0) {
+ // Save the values of the removed elements if requested.
+ if (elements != NULL) {
+ for (int i = 0; i < num; ++i) {
+ elements[i] = RepeatedPtrFieldBase::Mutable<TypeHandler>(i + start);
+ }
+ }
+ CloseGap(start, num);
+ }
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::Clear() {
+ RepeatedPtrFieldBase::Clear<TypeHandler>();
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::MergeFrom(
+ const RepeatedPtrField& other) {
+ RepeatedPtrFieldBase::MergeFrom<TypeHandler>(other);
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::CopyFrom(
+ const RepeatedPtrField& other) {
+ RepeatedPtrFieldBase::CopyFrom<TypeHandler>(other);
+}
+
+template <typename Element>
+inline typename RepeatedPtrField<Element>::iterator
+RepeatedPtrField<Element>::erase(const_iterator position) {
+ return erase(position, position + 1);
+}
+
+template <typename Element>
+inline typename RepeatedPtrField<Element>::iterator
+RepeatedPtrField<Element>::erase(const_iterator first, const_iterator last) {
+ size_type pos_offset = std::distance(cbegin(), first);
+ size_type last_offset = std::distance(cbegin(), last);
+ DeleteSubrange(pos_offset, last_offset - pos_offset);
+ return begin() + pos_offset;
+}
+
+template <typename Element>
+inline Element** RepeatedPtrField<Element>::mutable_data() {
+ return RepeatedPtrFieldBase::mutable_data<TypeHandler>();
+}
+
+template <typename Element>
+inline const Element* const* RepeatedPtrField<Element>::data() const {
+ return RepeatedPtrFieldBase::data<TypeHandler>();
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::Swap(RepeatedPtrField* other) {
+ if (this == other)
+ return;
+ RepeatedPtrFieldBase::Swap<TypeHandler>(other);
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::UnsafeArenaSwap(
+ RepeatedPtrField* other) {
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ if (this == other)
+ return;
+ RepeatedPtrFieldBase::InternalSwap(other);
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::SwapElements(int index1, int index2) {
+ RepeatedPtrFieldBase::SwapElements(index1, index2);
+}
+
+template <typename Element>
+inline Arena* RepeatedPtrField<Element>::GetArenaNoVirtual() const {
+ return RepeatedPtrFieldBase::GetArenaNoVirtual();
+}
+
+template <typename Element>
+inline int RepeatedPtrField<Element>::SpaceUsedExcludingSelf() const {
+ return RepeatedPtrFieldBase::SpaceUsedExcludingSelf<TypeHandler>();
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::AddAllocated(Element* value) {
+ RepeatedPtrFieldBase::AddAllocated<TypeHandler>(value);
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::UnsafeArenaAddAllocated(Element* value) {
+ RepeatedPtrFieldBase::UnsafeArenaAddAllocated<TypeHandler>(value);
+}
+
+template <typename Element>
+inline Element* RepeatedPtrField<Element>::ReleaseLast() {
+ return RepeatedPtrFieldBase::ReleaseLast<TypeHandler>();
+}
+
+template <typename Element>
+inline Element* RepeatedPtrField<Element>::UnsafeArenaReleaseLast() {
+ return RepeatedPtrFieldBase::UnsafeArenaReleaseLast<TypeHandler>();
+}
+
+template <typename Element>
+inline int RepeatedPtrField<Element>::ClearedCount() const {
+ return RepeatedPtrFieldBase::ClearedCount();
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::AddCleared(Element* value) {
+ return RepeatedPtrFieldBase::AddCleared<TypeHandler>(value);
+}
+
+template <typename Element>
+inline Element* RepeatedPtrField<Element>::ReleaseCleared() {
+ return RepeatedPtrFieldBase::ReleaseCleared<TypeHandler>();
+}
+
+template <typename Element>
+inline void RepeatedPtrField<Element>::Reserve(int new_size) {
+ return RepeatedPtrFieldBase::Reserve(new_size);
+}
+
+template <typename Element>
+inline int RepeatedPtrField<Element>::Capacity() const {
+ return RepeatedPtrFieldBase::Capacity();
+}
+
+// -------------------------------------------------------------------
+
+namespace internal {
+
+// STL-like iterator implementation for RepeatedPtrField. You should not
+// refer to this class directly; use RepeatedPtrField<T>::iterator instead.
+//
+// The iterator for RepeatedPtrField<T>, RepeatedPtrIterator<T>, is
+// very similar to iterator_ptr<T**> in util/gtl/iterator_adaptors.h,
+// but adds random-access operators and is modified to wrap a void** base
+// iterator (since RepeatedPtrField stores its array as a void* array and
+// casting void** to T** would violate C++ aliasing rules).
+//
+// This code based on net/proto/proto-array-internal.h by Jeffrey Yasskin
+// (jyasskin@google.com).
+template<typename Element>
+class RepeatedPtrIterator
+ : public std::iterator<
+ std::random_access_iterator_tag, Element> {
+ public:
+ typedef RepeatedPtrIterator<Element> iterator;
+ typedef std::iterator<
+ std::random_access_iterator_tag, Element> superclass;
+
+ // Shadow the value_type in std::iterator<> because const_iterator::value_type
+ // needs to be T, not const T.
+ typedef typename remove_const<Element>::type value_type;
+
+ // Let the compiler know that these are type names, so we don't have to
+ // write "typename" in front of them everywhere.
+ typedef typename superclass::reference reference;
+ typedef typename superclass::pointer pointer;
+ typedef typename superclass::difference_type difference_type;
+
+ RepeatedPtrIterator() : it_(NULL) {}
+ explicit RepeatedPtrIterator(void* const* it) : it_(it) {}
+
+ // Allow "upcasting" from RepeatedPtrIterator<T**> to
+ // RepeatedPtrIterator<const T*const*>.
+ template<typename OtherElement>
+ RepeatedPtrIterator(const RepeatedPtrIterator<OtherElement>& other)
+ : it_(other.it_) {
+ // Force a compiler error if the other type is not convertible to ours.
+ if (false) {
+ implicit_cast<Element*, OtherElement*>(0);
+ }
+ }
+
+ // dereferenceable
+ reference operator*() const { return *reinterpret_cast<Element*>(*it_); }
+ pointer operator->() const { return &(operator*()); }
+
+ // {inc,dec}rementable
+ iterator& operator++() { ++it_; return *this; }
+ iterator operator++(int) { return iterator(it_++); }
+ iterator& operator--() { --it_; return *this; }
+ iterator operator--(int) { return iterator(it_--); }
+
+ // equality_comparable
+ bool operator==(const iterator& x) const { return it_ == x.it_; }
+ bool operator!=(const iterator& x) const { return it_ != x.it_; }
+
+ // less_than_comparable
+ bool operator<(const iterator& x) const { return it_ < x.it_; }
+ bool operator<=(const iterator& x) const { return it_ <= x.it_; }
+ bool operator>(const iterator& x) const { return it_ > x.it_; }
+ bool operator>=(const iterator& x) const { return it_ >= x.it_; }
+
+ // addable, subtractable
+ iterator& operator+=(difference_type d) {
+ it_ += d;
+ return *this;
+ }
+ friend iterator operator+(iterator it, const difference_type d) {
+ it += d;
+ return it;
+ }
+ friend iterator operator+(const difference_type d, iterator it) {
+ it += d;
+ return it;
+ }
+ iterator& operator-=(difference_type d) {
+ it_ -= d;
+ return *this;
+ }
+ friend iterator operator-(iterator it, difference_type d) {
+ it -= d;
+ return it;
+ }
+
+ // indexable
+ reference operator[](difference_type d) const { return *(*this + d); }
+
+ // random access iterator
+ difference_type operator-(const iterator& x) const { return it_ - x.it_; }
+
+ private:
+ template<typename OtherElement>
+ friend class RepeatedPtrIterator;
+
+ // The internal iterator.
+ void* const* it_;
+};
+
+// Provide an iterator that operates on pointers to the underlying objects
+// rather than the objects themselves as RepeatedPtrIterator does.
+// Consider using this when working with stl algorithms that change
+// the array.
+// The VoidPtr template parameter holds the type-agnostic pointer value
+// referenced by the iterator. It should either be "void *" for a mutable
+// iterator, or "const void *" for a constant iterator.
+template<typename Element, typename VoidPtr>
+class RepeatedPtrOverPtrsIterator
+ : public std::iterator<std::random_access_iterator_tag, Element*> {
+ public:
+ typedef RepeatedPtrOverPtrsIterator<Element, VoidPtr> iterator;
+ typedef std::iterator<
+ std::random_access_iterator_tag, Element*> superclass;
+
+ // Shadow the value_type in std::iterator<> because const_iterator::value_type
+ // needs to be T, not const T.
+ typedef typename remove_const<Element*>::type value_type;
+
+ // Let the compiler know that these are type names, so we don't have to
+ // write "typename" in front of them everywhere.
+ typedef typename superclass::reference reference;
+ typedef typename superclass::pointer pointer;
+ typedef typename superclass::difference_type difference_type;
+
+ RepeatedPtrOverPtrsIterator() : it_(NULL) {}
+ explicit RepeatedPtrOverPtrsIterator(VoidPtr* it) : it_(it) {}
+
+ // dereferenceable
+ reference operator*() const { return *reinterpret_cast<Element**>(it_); }
+ pointer operator->() const { return &(operator*()); }
+
+ // {inc,dec}rementable
+ iterator& operator++() { ++it_; return *this; }
+ iterator operator++(int) { return iterator(it_++); }
+ iterator& operator--() { --it_; return *this; }
+ iterator operator--(int) { return iterator(it_--); }
+
+ // equality_comparable
+ bool operator==(const iterator& x) const { return it_ == x.it_; }
+ bool operator!=(const iterator& x) const { return it_ != x.it_; }
+
+ // less_than_comparable
+ bool operator<(const iterator& x) const { return it_ < x.it_; }
+ bool operator<=(const iterator& x) const { return it_ <= x.it_; }
+ bool operator>(const iterator& x) const { return it_ > x.it_; }
+ bool operator>=(const iterator& x) const { return it_ >= x.it_; }
+
+ // addable, subtractable
+ iterator& operator+=(difference_type d) {
+ it_ += d;
+ return *this;
+ }
+ friend iterator operator+(iterator it, difference_type d) {
+ it += d;
+ return it;
+ }
+ friend iterator operator+(difference_type d, iterator it) {
+ it += d;
+ return it;
+ }
+ iterator& operator-=(difference_type d) {
+ it_ -= d;
+ return *this;
+ }
+ friend iterator operator-(iterator it, difference_type d) {
+ it -= d;
+ return it;
+ }
+
+ // indexable
+ reference operator[](difference_type d) const { return *(*this + d); }
+
+ // random access iterator
+ difference_type operator-(const iterator& x) const { return it_ - x.it_; }
+
+ private:
+ template<typename OtherElement>
+ friend class RepeatedPtrIterator;
+
+ // The internal iterator.
+ VoidPtr* it_;
+};
+
+void RepeatedPtrFieldBase::InternalSwap(RepeatedPtrFieldBase* other) {
+ std::swap(rep_, other->rep_);
+ std::swap(current_size_, other->current_size_);
+ std::swap(total_size_, other->total_size_);
+}
+
+} // namespace internal
+
+template <typename Element>
+inline typename RepeatedPtrField<Element>::iterator
+RepeatedPtrField<Element>::begin() {
+ return iterator(raw_data());
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::const_iterator
+RepeatedPtrField<Element>::begin() const {
+ return iterator(raw_data());
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::const_iterator
+RepeatedPtrField<Element>::cbegin() const {
+ return begin();
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::iterator
+RepeatedPtrField<Element>::end() {
+ return iterator(raw_data() + size());
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::const_iterator
+RepeatedPtrField<Element>::end() const {
+ return iterator(raw_data() + size());
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::const_iterator
+RepeatedPtrField<Element>::cend() const {
+ return end();
+}
+
+template <typename Element>
+inline typename RepeatedPtrField<Element>::pointer_iterator
+RepeatedPtrField<Element>::pointer_begin() {
+ return pointer_iterator(raw_mutable_data());
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::const_pointer_iterator
+RepeatedPtrField<Element>::pointer_begin() const {
+ return const_pointer_iterator(const_cast<const void**>(raw_mutable_data()));
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::pointer_iterator
+RepeatedPtrField<Element>::pointer_end() {
+ return pointer_iterator(raw_mutable_data() + size());
+}
+template <typename Element>
+inline typename RepeatedPtrField<Element>::const_pointer_iterator
+RepeatedPtrField<Element>::pointer_end() const {
+ return const_pointer_iterator(
+ const_cast<const void**>(raw_mutable_data() + size()));
+}
+
+
+// Iterators and helper functions that follow the spirit of the STL
+// std::back_insert_iterator and std::back_inserter but are tailor-made
+// for RepeatedField and RepeatedPtrField. Typical usage would be:
+//
+// std::copy(some_sequence.begin(), some_sequence.end(),
+// google::protobuf::RepeatedFieldBackInserter(proto.mutable_sequence()));
+//
+// Ported by johannes from util/gtl/proto-array-iterators.h
+
+namespace internal {
+// A back inserter for RepeatedField objects.
+template<typename T> class RepeatedFieldBackInsertIterator
+ : public std::iterator<std::output_iterator_tag, T> {
+ public:
+ explicit RepeatedFieldBackInsertIterator(
+ RepeatedField<T>* const mutable_field)
+ : field_(mutable_field) {
+ }
+ RepeatedFieldBackInsertIterator<T>& operator=(const T& value) {
+ field_->Add(value);
+ return *this;
+ }
+ RepeatedFieldBackInsertIterator<T>& operator*() {
+ return *this;
+ }
+ RepeatedFieldBackInsertIterator<T>& operator++() {
+ return *this;
+ }
+ RepeatedFieldBackInsertIterator<T>& operator++(int /* unused */) {
+ return *this;
+ }
+
+ private:
+ RepeatedField<T>* field_;
+};
+
+// A back inserter for RepeatedPtrField objects.
+template<typename T> class RepeatedPtrFieldBackInsertIterator
+ : public std::iterator<std::output_iterator_tag, T> {
+ public:
+ RepeatedPtrFieldBackInsertIterator(
+ RepeatedPtrField<T>* const mutable_field)
+ : field_(mutable_field) {
+ }
+ RepeatedPtrFieldBackInsertIterator<T>& operator=(const T& value) {
+ *field_->Add() = value;
+ return *this;
+ }
+ RepeatedPtrFieldBackInsertIterator<T>& operator=(
+ const T* const ptr_to_value) {
+ *field_->Add() = *ptr_to_value;
+ return *this;
+ }
+ RepeatedPtrFieldBackInsertIterator<T>& operator*() {
+ return *this;
+ }
+ RepeatedPtrFieldBackInsertIterator<T>& operator++() {
+ return *this;
+ }
+ RepeatedPtrFieldBackInsertIterator<T>& operator++(int /* unused */) {
+ return *this;
+ }
+
+ private:
+ RepeatedPtrField<T>* field_;
+};
+
+// A back inserter for RepeatedPtrFields that inserts by transferring ownership
+// of a pointer.
+template<typename T> class AllocatedRepeatedPtrFieldBackInsertIterator
+ : public std::iterator<std::output_iterator_tag, T> {
+ public:
+ explicit AllocatedRepeatedPtrFieldBackInsertIterator(
+ RepeatedPtrField<T>* const mutable_field)
+ : field_(mutable_field) {
+ }
+ AllocatedRepeatedPtrFieldBackInsertIterator<T>& operator=(
+ T* const ptr_to_value) {
+ field_->AddAllocated(ptr_to_value);
+ return *this;
+ }
+ AllocatedRepeatedPtrFieldBackInsertIterator<T>& operator*() {
+ return *this;
+ }
+ AllocatedRepeatedPtrFieldBackInsertIterator<T>& operator++() {
+ return *this;
+ }
+ AllocatedRepeatedPtrFieldBackInsertIterator<T>& operator++(
+ int /* unused */) {
+ return *this;
+ }
+
+ private:
+ RepeatedPtrField<T>* field_;
+};
+
+// Almost identical to AllocatedRepeatedPtrFieldBackInsertIterator. This one
+// uses the UnsafeArenaAddAllocated instead.
+template<typename T>
+class UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator
+ : public std::iterator<std::output_iterator_tag, T> {
+ public:
+ explicit UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator(
+ ::google::protobuf::RepeatedPtrField<T>* const mutable_field)
+ : field_(mutable_field) {
+ }
+ UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator<T>& operator=(
+ T const* const ptr_to_value) {
+ field_->UnsafeArenaAddAllocated(const_cast<T*>(ptr_to_value));
+ return *this;
+ }
+ UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator<T>& operator*() {
+ return *this;
+ }
+ UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator<T>& operator++() {
+ return *this;
+ }
+ UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator<T>& operator++(
+ int /* unused */) {
+ return *this;
+ }
+
+ private:
+ ::google::protobuf::RepeatedPtrField<T>* field_;
+};
+
+} // namespace internal
+
+// Provides a back insert iterator for RepeatedField instances,
+// similar to std::back_inserter().
+template<typename T> internal::RepeatedFieldBackInsertIterator<T>
+RepeatedFieldBackInserter(RepeatedField<T>* const mutable_field) {
+ return internal::RepeatedFieldBackInsertIterator<T>(mutable_field);
+}
+
+// Provides a back insert iterator for RepeatedPtrField instances,
+// similar to std::back_inserter().
+template<typename T> internal::RepeatedPtrFieldBackInsertIterator<T>
+RepeatedPtrFieldBackInserter(RepeatedPtrField<T>* const mutable_field) {
+ return internal::RepeatedPtrFieldBackInsertIterator<T>(mutable_field);
+}
+
+// Special back insert iterator for RepeatedPtrField instances, just in
+// case someone wants to write generic template code that can access both
+// RepeatedFields and RepeatedPtrFields using a common name.
+template<typename T> internal::RepeatedPtrFieldBackInsertIterator<T>
+RepeatedFieldBackInserter(RepeatedPtrField<T>* const mutable_field) {
+ return internal::RepeatedPtrFieldBackInsertIterator<T>(mutable_field);
+}
+
+// Provides a back insert iterator for RepeatedPtrField instances
+// similar to std::back_inserter() which transfers the ownership while
+// copying elements.
+template<typename T> internal::AllocatedRepeatedPtrFieldBackInsertIterator<T>
+AllocatedRepeatedPtrFieldBackInserter(
+ RepeatedPtrField<T>* const mutable_field) {
+ return internal::AllocatedRepeatedPtrFieldBackInsertIterator<T>(
+ mutable_field);
+}
+
+// Similar to AllocatedRepeatedPtrFieldBackInserter, using
+// UnsafeArenaAddAllocated instead of AddAllocated.
+// This is slightly faster if that matters. It is also useful in legacy code
+// that uses temporary ownership to avoid copies. Example:
+// RepeatedPtrField<T> temp_field;
+// temp_field.AddAllocated(new T);
+// ... // Do something with temp_field
+// temp_field.ExtractSubrange(0, temp_field.size(), NULL);
+// If you put temp_field on the arena this fails, because the ownership
+// transfers to the arena at the "AddAllocated" call and is not released anymore
+// causing a double delete. Using UnsafeArenaAddAllocated prevents this.
+template<typename T>
+internal::UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator<T>
+UnsafeArenaAllocatedRepeatedPtrFieldBackInserter(
+ ::google::protobuf::RepeatedPtrField<T>* const mutable_field) {
+ return internal::UnsafeArenaAllocatedRepeatedPtrFieldBackInsertIterator<T>(
+ mutable_field);
+}
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_REPEATED_FIELD_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_reflection_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_reflection_unittest.cc
new file mode 100644
index 0000000000..fcebe5ce33
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_reflection_unittest.cc
@@ -0,0 +1,706 @@
+// 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: tgs@google.com (Tom Szymanski)
+//
+// Test reflection methods for aggregate access to Repeated[Ptr]Fields.
+// This test proto2 methods on a proto2 layout.
+
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/reflection.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+using unittest::ForeignMessage;
+using unittest::TestAllTypes;
+using unittest::TestAllExtensions;
+
+namespace {
+
+static int Func(int i, int j) {
+ return i * j;
+}
+
+static string StrFunc(int i, int j) {
+ string str;
+ SStringPrintf(&str, "%d", Func(i, 4));
+ return str;
+}
+
+TEST(RepeatedFieldReflectionTest, RegularFields) {
+ TestAllTypes message;
+ const Reflection* refl = message.GetReflection();
+ const Descriptor* desc = message.GetDescriptor();
+
+ for (int i = 0; i < 10; ++i) {
+ message.add_repeated_int32(Func(i, 1));
+ message.add_repeated_double(Func(i, 2));
+ message.add_repeated_string(StrFunc(i, 5));
+ message.add_repeated_foreign_message()->set_c(Func(i, 6));
+ }
+
+ // Get FieldDescriptors for all the fields of interest.
+ const FieldDescriptor* fd_repeated_int32 =
+ desc->FindFieldByName("repeated_int32");
+ const FieldDescriptor* fd_repeated_double =
+ desc->FindFieldByName("repeated_double");
+ const FieldDescriptor* fd_repeated_string =
+ desc->FindFieldByName("repeated_string");
+ const FieldDescriptor* fd_repeated_foreign_message =
+ desc->FindFieldByName("repeated_foreign_message");
+
+ // Get RepeatedField objects for all fields of interest.
+ const RepeatedField<int32>& rf_int32 =
+ refl->GetRepeatedField<int32>(message, fd_repeated_int32);
+ const RepeatedField<double>& rf_double =
+ refl->GetRepeatedField<double>(message, fd_repeated_double);
+
+ // Get mutable RepeatedField objects for all fields of interest.
+ RepeatedField<int32>* mrf_int32 =
+ refl->MutableRepeatedField<int32>(&message, fd_repeated_int32);
+ RepeatedField<double>* mrf_double =
+ refl->MutableRepeatedField<double>(&message, fd_repeated_double);
+
+ // Get RepeatedPtrField objects for all fields of interest.
+ const RepeatedPtrField<string>& rpf_string =
+ refl->GetRepeatedPtrField<string>(message, fd_repeated_string);
+ const RepeatedPtrField<ForeignMessage>& rpf_foreign_message =
+ refl->GetRepeatedPtrField<ForeignMessage>(
+ message, fd_repeated_foreign_message);
+ const RepeatedPtrField<Message>& rpf_message =
+ refl->GetRepeatedPtrField<Message>(
+ message, fd_repeated_foreign_message);
+
+ // Get mutable RepeatedPtrField objects for all fields of interest.
+ RepeatedPtrField<string>* mrpf_string =
+ refl->MutableRepeatedPtrField<string>(&message, fd_repeated_string);
+ RepeatedPtrField<ForeignMessage>* mrpf_foreign_message =
+ refl->MutableRepeatedPtrField<ForeignMessage>(
+ &message, fd_repeated_foreign_message);
+ RepeatedPtrField<Message>* mrpf_message =
+ refl->MutableRepeatedPtrField<Message>(
+ &message, fd_repeated_foreign_message);
+
+ // Make sure we can do gets and sets through the Repeated[Ptr]Field objects.
+ for (int i = 0; i < 10; ++i) {
+ // Check gets through const objects.
+ EXPECT_EQ(rf_int32.Get(i), Func(i, 1));
+ EXPECT_EQ(rf_double.Get(i), Func(i, 2));
+ EXPECT_EQ(rpf_string.Get(i), StrFunc(i, 5));
+ EXPECT_EQ(rpf_foreign_message.Get(i).c(), Func(i, 6));
+ EXPECT_EQ(down_cast<const ForeignMessage*>(&rpf_message.Get(i))->c(),
+ Func(i, 6));
+
+ // Check gets through mutable objects.
+ EXPECT_EQ(mrf_int32->Get(i), Func(i, 1));
+ EXPECT_EQ(mrf_double->Get(i), Func(i, 2));
+ EXPECT_EQ(mrpf_string->Get(i), StrFunc(i, 5));
+ EXPECT_EQ(mrpf_foreign_message->Get(i).c(), Func(i, 6));
+ EXPECT_EQ(down_cast<const ForeignMessage*>(&mrpf_message->Get(i))->c(),
+ Func(i, 6));
+
+ // Check sets through mutable objects.
+ mrf_int32->Set(i, Func(i, -1));
+ mrf_double->Set(i, Func(i, -2));
+ mrpf_string->Mutable(i)->assign(StrFunc(i, -5));
+ mrpf_foreign_message->Mutable(i)->set_c(Func(i, -6));
+ EXPECT_EQ(message.repeated_int32(i), Func(i, -1));
+ EXPECT_EQ(message.repeated_double(i), Func(i, -2));
+ EXPECT_EQ(message.repeated_string(i), StrFunc(i, -5));
+ EXPECT_EQ(message.repeated_foreign_message(i).c(), Func(i, -6));
+ down_cast<ForeignMessage*>(mrpf_message->Mutable(i))->set_c(Func(i, 7));
+ EXPECT_EQ(message.repeated_foreign_message(i).c(), Func(i, 7));
+ }
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+ // Make sure types are checked correctly at runtime.
+ const FieldDescriptor* fd_optional_int32 =
+ desc->FindFieldByName("optional_int32");
+ EXPECT_DEATH(refl->GetRepeatedField<int32>(
+ message, fd_optional_int32), "requires a repeated field");
+ EXPECT_DEATH(refl->GetRepeatedField<double>(
+ message, fd_repeated_int32), "not the right type");
+ EXPECT_DEATH(refl->GetRepeatedPtrField<TestAllTypes>(
+ message, fd_repeated_foreign_message), "wrong submessage type");
+#endif // PROTOBUF_HAS_DEATH_TEST
+}
+
+
+TEST(RepeatedFieldReflectionTest, ExtensionFields) {
+ TestAllExtensions extended_message;
+ const Reflection* refl = extended_message.GetReflection();
+ const Descriptor* desc = extended_message.GetDescriptor();
+
+ for (int i = 0; i < 10; ++i) {
+ extended_message.AddExtension(
+ unittest::repeated_int64_extension, Func(i, 1));
+ }
+
+ const FieldDescriptor* fd_repeated_int64_extension =
+ desc->file()->FindExtensionByName("repeated_int64_extension");
+ GOOGLE_CHECK(fd_repeated_int64_extension != NULL);
+
+ const RepeatedField<int64>& rf_int64_extension =
+ refl->GetRepeatedField<int64>(extended_message,
+ fd_repeated_int64_extension);
+
+ RepeatedField<int64>* mrf_int64_extension =
+ refl->MutableRepeatedField<int64>(&extended_message,
+ fd_repeated_int64_extension);
+
+ for (int i = 0; i < 10; ++i) {
+ EXPECT_EQ(Func(i, 1), rf_int64_extension.Get(i));
+ mrf_int64_extension->Set(i, Func(i, -1));
+ EXPECT_EQ(Func(i, -1),
+ extended_message.GetExtension(unittest::repeated_int64_extension, i));
+ }
+}
+
+template<typename Ref, typename MessageType, typename ValueType>
+void TestRepeatedFieldRefIterator(
+ const Ref& handle, const MessageType& message,
+ ValueType (MessageType::*GetFunc)(int) const) {
+ int index = 0;
+ for (typename Ref::const_iterator it = handle.begin();
+ it != handle.end(); ++it) {
+ EXPECT_EQ((message.*GetFunc)(index), *it);
+ ++index;
+ }
+ EXPECT_EQ(handle.size(), index);
+}
+
+TEST(RepeatedFieldReflectionTest, RepeatedFieldRefForRegularFields) {
+ TestAllTypes message;
+ const Reflection* refl = message.GetReflection();
+ const Descriptor* desc = message.GetDescriptor();
+
+ for (int i = 0; i < 10; ++i) {
+ message.add_repeated_int32(Func(i, 1));
+ message.add_repeated_double(Func(i, 2));
+ message.add_repeated_string(StrFunc(i, 5));
+ message.add_repeated_foreign_message()->set_c(Func(i, 6));
+ }
+
+ // Get FieldDescriptors for all the fields of interest.
+ const FieldDescriptor* fd_repeated_int32 =
+ desc->FindFieldByName("repeated_int32");
+ const FieldDescriptor* fd_repeated_double =
+ desc->FindFieldByName("repeated_double");
+ const FieldDescriptor* fd_repeated_string =
+ desc->FindFieldByName("repeated_string");
+ const FieldDescriptor* fd_repeated_foreign_message =
+ desc->FindFieldByName("repeated_foreign_message");
+
+ // Get RepeatedFieldRef objects for all fields of interest.
+ const RepeatedFieldRef<int32> rf_int32 =
+ refl->GetRepeatedFieldRef<int32>(message, fd_repeated_int32);
+ const RepeatedFieldRef<double> rf_double =
+ refl->GetRepeatedFieldRef<double>(message, fd_repeated_double);
+ const RepeatedFieldRef<string> rf_string =
+ refl->GetRepeatedFieldRef<string>(message, fd_repeated_string);
+ const RepeatedFieldRef<ForeignMessage> rf_foreign_message =
+ refl->GetRepeatedFieldRef<ForeignMessage>(
+ message, fd_repeated_foreign_message);
+ const RepeatedFieldRef<Message> rf_message =
+ refl->GetRepeatedFieldRef<Message>(
+ message, fd_repeated_foreign_message);
+
+ // Get MutableRepeatedFieldRef objects for all fields of interest.
+ const MutableRepeatedFieldRef<int32> mrf_int32 =
+ refl->GetMutableRepeatedFieldRef<int32>(&message, fd_repeated_int32);
+ const MutableRepeatedFieldRef<double> mrf_double =
+ refl->GetMutableRepeatedFieldRef<double>(&message, fd_repeated_double);
+ const MutableRepeatedFieldRef<string> mrf_string =
+ refl->GetMutableRepeatedFieldRef<string>(&message, fd_repeated_string);
+ const MutableRepeatedFieldRef<ForeignMessage> mrf_foreign_message =
+ refl->GetMutableRepeatedFieldRef<ForeignMessage>(
+ &message, fd_repeated_foreign_message);
+ const MutableRepeatedFieldRef<Message> mrf_message =
+ refl->GetMutableRepeatedFieldRef<Message>(
+ &message, fd_repeated_foreign_message);
+
+ EXPECT_EQ(message.repeated_int32_size(), rf_int32.size());
+ EXPECT_EQ(message.repeated_int32_size(), mrf_int32.size());
+ EXPECT_EQ(message.repeated_double_size(), rf_double.size());
+ EXPECT_EQ(message.repeated_double_size(), mrf_double.size());
+ EXPECT_EQ(message.repeated_string_size(), rf_string.size());
+ EXPECT_EQ(message.repeated_string_size(), mrf_string.size());
+ EXPECT_EQ(message.repeated_foreign_message_size(),
+ rf_foreign_message.size());
+ EXPECT_EQ(message.repeated_foreign_message_size(),
+ mrf_foreign_message.size());
+ EXPECT_EQ(message.repeated_foreign_message_size(), rf_message.size());
+ EXPECT_EQ(message.repeated_foreign_message_size(), mrf_message.size());
+
+ EXPECT_FALSE(rf_int32.empty());
+ EXPECT_FALSE(mrf_int32.empty());
+ EXPECT_FALSE(rf_double.empty());
+ EXPECT_FALSE(mrf_double.empty());
+ EXPECT_FALSE(rf_string.empty());
+ EXPECT_FALSE(mrf_string.empty());
+ EXPECT_FALSE(rf_foreign_message.empty());
+ EXPECT_FALSE(mrf_foreign_message.empty());
+ EXPECT_FALSE(rf_message.empty());
+ EXPECT_FALSE(mrf_message.empty());
+
+ // Make sure we can do gets and sets through the RepeatedFieldRef objects.
+ for (int i = 0; i < 10; ++i) {
+ // Check gets through const objects.
+ EXPECT_EQ(rf_int32.Get(i), Func(i, 1));
+ EXPECT_EQ(rf_double.Get(i), Func(i, 2));
+ EXPECT_EQ(rf_string.Get(i), StrFunc(i, 5));
+ ForeignMessage scratch_space;
+ EXPECT_EQ(rf_foreign_message.Get(i, &scratch_space).c(), Func(i, 6));
+ EXPECT_EQ(down_cast<const ForeignMessage&>(
+ rf_message.Get(i, &scratch_space)).c(), Func(i, 6));
+
+ // Check gets through mutable objects.
+ EXPECT_EQ(mrf_int32.Get(i), Func(i, 1));
+ EXPECT_EQ(mrf_double.Get(i), Func(i, 2));
+ EXPECT_EQ(mrf_string.Get(i), StrFunc(i, 5));
+ EXPECT_EQ(mrf_foreign_message.Get(i, &scratch_space).c(), Func(i, 6));
+ EXPECT_EQ(down_cast<const ForeignMessage&>(
+ mrf_message.Get(i, &scratch_space)).c(), Func(i, 6));
+
+ // Check sets through mutable objects.
+ mrf_int32.Set(i, Func(i, -1));
+ mrf_double.Set(i, Func(i, -2));
+ mrf_string.Set(i, StrFunc(i, -5));
+ ForeignMessage foreign_message;
+ foreign_message.set_c(Func(i, -6));
+ mrf_foreign_message.Set(i, foreign_message);
+ EXPECT_EQ(message.repeated_int32(i), Func(i, -1));
+ EXPECT_EQ(message.repeated_double(i), Func(i, -2));
+ EXPECT_EQ(message.repeated_string(i), StrFunc(i, -5));
+ EXPECT_EQ(message.repeated_foreign_message(i).c(), Func(i, -6));
+ foreign_message.set_c(Func(i, 7));
+ mrf_message.Set(i, foreign_message);
+ EXPECT_EQ(message.repeated_foreign_message(i).c(), Func(i, 7));
+ }
+
+ // Test iterators.
+ TestRepeatedFieldRefIterator(rf_int32, message,
+ &TestAllTypes::repeated_int32);
+ TestRepeatedFieldRefIterator(rf_double, message,
+ &TestAllTypes::repeated_double);
+ TestRepeatedFieldRefIterator(rf_string, message,
+ &TestAllTypes::repeated_string);
+
+ // Test iterators for message fields.
+ typedef RepeatedFieldRef<ForeignMessage>::iterator MessageIterator;
+ int index = 0;
+ for (MessageIterator it = rf_foreign_message.begin();
+ it != rf_foreign_message.end(); ++it) {
+ EXPECT_EQ(message.repeated_foreign_message(index).c(), it->c());
+ ++index;
+ }
+ EXPECT_EQ(10, index);
+
+ // Test iterator operators that are not ususally used in regular for-loops.
+ // Including: post increment, assign, ==.
+ MessageIterator old_it = rf_foreign_message.begin();
+ MessageIterator new_it = old_it++;
+ EXPECT_FALSE(old_it == new_it);
+ // Check that old_it++ increments old_it once.
+ for (index = 1; old_it != rf_foreign_message.end(); ++old_it, ++index) {
+ EXPECT_EQ(message.repeated_foreign_message(index).c(), old_it->c());
+ }
+ EXPECT_EQ(10, index);
+ // Test assign operator.
+ old_it = new_it;
+ for (index = 0; old_it != rf_foreign_message.end(); ++old_it, ++index) {
+ EXPECT_EQ(message.repeated_foreign_message(index).c(), old_it->c());
+ }
+ EXPECT_EQ(10, index);
+ // Check that the returned value of old_it++ is the one before increment.
+ for (index = 0; new_it != rf_foreign_message.end(); ++new_it, ++index) {
+ EXPECT_EQ(message.repeated_foreign_message(index).c(), new_it->c());
+ }
+ EXPECT_EQ(10, index);
+
+ // Test MutableRepeatedFieldRef::Add()
+ mrf_int32.Add(1234);
+ mrf_double.Add(1234.0);
+ mrf_string.Add("1234");
+ ForeignMessage foreign_message;
+ foreign_message.set_c(1234);
+ mrf_foreign_message.Add(foreign_message);
+ EXPECT_EQ(1234, message.repeated_int32(10));
+ EXPECT_EQ(1234.0, message.repeated_double(10));
+ EXPECT_EQ("1234", message.repeated_string(10));
+ EXPECT_EQ(1234, message.repeated_foreign_message(10).c());
+
+ // Test MutableRepeatedFieldRef::RemoveLast()
+ mrf_int32.RemoveLast();
+ mrf_double.RemoveLast();
+ mrf_string.RemoveLast();
+ mrf_foreign_message.RemoveLast();
+ EXPECT_EQ(10, message.repeated_int32_size());
+ EXPECT_EQ(10, message.repeated_double_size());
+ EXPECT_EQ(10, message.repeated_string_size());
+ EXPECT_EQ(10, message.repeated_foreign_message_size());
+
+ // Test MutableRepeatedFieldRef::SwapElements()
+ mrf_int32.SwapElements(0, 9);
+ mrf_double.SwapElements(0, 9);
+ mrf_string.SwapElements(0, 9);
+ mrf_foreign_message.SwapElements(0, 9);
+ EXPECT_EQ(Func(9, -1), message.repeated_int32(0));
+ EXPECT_EQ(Func(0, -1), message.repeated_int32(9));
+ EXPECT_EQ(Func(9, -2), message.repeated_double(0));
+ EXPECT_EQ(Func(0, -2), message.repeated_double(9));
+ EXPECT_EQ(StrFunc(9, -5), message.repeated_string(0));
+ EXPECT_EQ(StrFunc(0, -5), message.repeated_string(9));
+ EXPECT_EQ(Func(9, 7), message.repeated_foreign_message(0).c());
+ EXPECT_EQ(Func(0, 7), message.repeated_foreign_message(9).c());
+
+ // Test MutableRepeatedFieldRef::Clear()
+ mrf_int32.Clear();
+ mrf_double.Clear();
+ mrf_string.Clear();
+ mrf_foreign_message.Clear();
+ EXPECT_EQ(0, message.repeated_int32_size());
+ EXPECT_EQ(0, message.repeated_double_size());
+ EXPECT_EQ(0, message.repeated_string_size());
+ EXPECT_EQ(0, message.repeated_foreign_message_size());
+
+ // Test (Mutable)RepeatedFieldRef::empty()
+ EXPECT_TRUE(rf_int32.empty());
+ EXPECT_TRUE(mrf_int32.empty());
+ EXPECT_TRUE(rf_double.empty());
+ EXPECT_TRUE(mrf_double.empty());
+ EXPECT_TRUE(rf_string.empty());
+ EXPECT_TRUE(mrf_string.empty());
+ EXPECT_TRUE(rf_foreign_message.empty());
+ EXPECT_TRUE(mrf_foreign_message.empty());
+ EXPECT_TRUE(rf_message.empty());
+ EXPECT_TRUE(mrf_message.empty());
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+
+ // Make sure types are checked correctly at runtime.
+ const FieldDescriptor* fd_optional_int32 =
+ desc->FindFieldByName("optional_int32");
+ EXPECT_DEATH(refl->GetRepeatedFieldRef<int32>(
+ message, fd_optional_int32), "");
+ EXPECT_DEATH(refl->GetRepeatedFieldRef<double>(
+ message, fd_repeated_int32), "");
+ EXPECT_DEATH(refl->GetRepeatedFieldRef<TestAllTypes>(
+ message, fd_repeated_foreign_message), "");
+
+#endif // PROTOBUF_HAS_DEATH_TEST
+}
+
+TEST(RepeatedFieldReflectionTest, RepeatedFieldRefForEnums) {
+ TestAllTypes message;
+ const Reflection* refl = message.GetReflection();
+ const Descriptor* desc = message.GetDescriptor();
+
+ for (int i = 0; i < 10; ++i) {
+ message.add_repeated_nested_enum(TestAllTypes::BAR);
+ }
+
+ const FieldDescriptor* fd_repeated_nested_enum =
+ desc->FindFieldByName("repeated_nested_enum");
+ const RepeatedFieldRef<TestAllTypes::NestedEnum> enum_ref =
+ refl->GetRepeatedFieldRef<TestAllTypes::NestedEnum>(
+ message, fd_repeated_nested_enum);
+ const MutableRepeatedFieldRef<TestAllTypes::NestedEnum>
+ mutable_enum_ref =
+ refl->GetMutableRepeatedFieldRef<TestAllTypes::NestedEnum>(
+ &message, fd_repeated_nested_enum);
+ const RepeatedFieldRef<int32> int32_ref =
+ refl->GetRepeatedFieldRef<int32>(
+ message, fd_repeated_nested_enum);
+ const MutableRepeatedFieldRef<int32> mutable_int32_ref =
+ refl->GetMutableRepeatedFieldRef<int32>(
+ &message, fd_repeated_nested_enum);
+
+ EXPECT_EQ(message.repeated_nested_enum_size(), enum_ref.size());
+ EXPECT_EQ(message.repeated_nested_enum_size(), mutable_enum_ref.size());
+ EXPECT_EQ(message.repeated_nested_enum_size(), int32_ref.size());
+ EXPECT_EQ(message.repeated_nested_enum_size(), mutable_int32_ref.size());
+
+ EXPECT_FALSE(enum_ref.empty());
+ EXPECT_FALSE(mutable_enum_ref.empty());
+ EXPECT_FALSE(int32_ref.empty());
+ EXPECT_FALSE(mutable_int32_ref.empty());
+
+ for (int i = 0; i < 10; ++i) {
+ EXPECT_EQ(TestAllTypes::BAR, enum_ref.Get(i));
+ EXPECT_EQ(TestAllTypes::BAR, mutable_enum_ref.Get(i));
+ mutable_enum_ref.Set(i, TestAllTypes::BAZ);
+ EXPECT_EQ(TestAllTypes::BAZ, enum_ref.Get(i));
+ EXPECT_EQ(TestAllTypes::BAZ, message.repeated_nested_enum(i));
+
+ message.set_repeated_nested_enum(i, TestAllTypes::BAR);
+ EXPECT_EQ(TestAllTypes::BAR, int32_ref.Get(i));
+ EXPECT_EQ(TestAllTypes::BAR, mutable_int32_ref.Get(i));
+ mutable_int32_ref.Set(i, TestAllTypes::BAZ);
+ EXPECT_EQ(TestAllTypes::BAZ, int32_ref.Get(i));
+ EXPECT_EQ(TestAllTypes::BAZ, message.repeated_nested_enum(i));
+ }
+
+ TestRepeatedFieldRefIterator(enum_ref, message,
+ &TestAllTypes::repeated_nested_enum);
+ TestRepeatedFieldRefIterator(int32_ref, message,
+ &TestAllTypes::repeated_nested_enum);
+
+ // Test Add()
+ mutable_enum_ref.Add(TestAllTypes::FOO);
+ EXPECT_EQ(TestAllTypes::FOO, message.repeated_nested_enum(10));
+ mutable_int32_ref.Add(TestAllTypes::BAR);
+ EXPECT_EQ(TestAllTypes::BAR, message.repeated_nested_enum(11));
+
+ // Test RemoveLast()
+ mutable_enum_ref.RemoveLast();
+ EXPECT_EQ(11, message.repeated_nested_enum_size());
+ mutable_int32_ref.RemoveLast();
+ EXPECT_EQ(10, message.repeated_nested_enum_size());
+
+ // Test SwapElements()
+ mutable_enum_ref.Set(0, TestAllTypes::BAR);
+ mutable_enum_ref.Set(9, TestAllTypes::BAZ);
+ mutable_enum_ref.SwapElements(0, 9);
+ EXPECT_EQ(TestAllTypes::BAZ, enum_ref.Get(0));
+ EXPECT_EQ(TestAllTypes::BAR, enum_ref.Get(9));
+ mutable_int32_ref.SwapElements(0, 9);
+ EXPECT_EQ(TestAllTypes::BAR, enum_ref.Get(0));
+ EXPECT_EQ(TestAllTypes::BAZ, enum_ref.Get(9));
+
+ // Test Clear()
+ mutable_enum_ref.Clear();
+ EXPECT_EQ(0, message.repeated_nested_enum_size());
+ mutable_enum_ref.Add(TestAllTypes::FOO);
+ EXPECT_EQ(1, message.repeated_nested_enum_size());
+ mutable_int32_ref.Clear();
+ EXPECT_EQ(0, message.repeated_nested_enum_size());
+
+ // Test empty()
+ EXPECT_TRUE(enum_ref.empty());
+ EXPECT_TRUE(mutable_enum_ref.empty());
+ EXPECT_TRUE(int32_ref.empty());
+ EXPECT_TRUE(mutable_int32_ref.empty());
+}
+
+TEST(RepeatedFieldReflectionTest, RepeatedFieldRefForExtensionFields) {
+ TestAllExtensions extended_message;
+ const Reflection* refl = extended_message.GetReflection();
+ const Descriptor* desc = extended_message.GetDescriptor();
+
+ for (int i = 0; i < 10; ++i) {
+ extended_message.AddExtension(
+ unittest::repeated_int64_extension, Func(i, 1));
+ }
+
+ const FieldDescriptor* fd_repeated_int64_extension =
+ desc->file()->FindExtensionByName("repeated_int64_extension");
+ GOOGLE_CHECK(fd_repeated_int64_extension != NULL);
+
+ const RepeatedFieldRef<int64> rf_int64_extension =
+ refl->GetRepeatedFieldRef<int64>(extended_message,
+ fd_repeated_int64_extension);
+
+ const MutableRepeatedFieldRef<int64> mrf_int64_extension =
+ refl->GetMutableRepeatedFieldRef<int64>(&extended_message,
+ fd_repeated_int64_extension);
+
+ for (int i = 0; i < 10; ++i) {
+ EXPECT_EQ(Func(i, 1), rf_int64_extension.Get(i));
+ mrf_int64_extension.Set(i, Func(i, -1));
+ EXPECT_EQ(Func(i, -1),
+ extended_message.GetExtension(unittest::repeated_int64_extension, i));
+ }
+}
+
+
+TEST(RepeatedFieldReflectionTest, RepeatedFieldRefMergeFromAndSwap) {
+ // Set-up message content.
+ TestAllTypes m0, m1, m2;
+ for (int i = 0; i < 10; ++i) {
+ m0.add_repeated_int32(Func(i, 1));
+ m0.add_repeated_double(Func(i, 2));
+ m0.add_repeated_string(StrFunc(i, 5));
+ m0.add_repeated_foreign_message()->set_c(Func(i, 6));
+ m0.add_repeated_nested_enum(TestAllTypes::FOO);
+ m1.add_repeated_int32(Func(i, 11));
+ m1.add_repeated_double(Func(i, 12));
+ m1.add_repeated_string(StrFunc(i, 15));
+ m1.add_repeated_foreign_message()->set_c(Func(i, 16));
+ m1.add_repeated_nested_enum(TestAllTypes::BAR);
+ m2.add_repeated_int32(Func(i, 21));
+ m2.add_repeated_double(Func(i, 22));
+ m2.add_repeated_string(StrFunc(i, 25));
+ m2.add_repeated_foreign_message()->set_c(Func(i, 26));
+ m2.add_repeated_nested_enum(TestAllTypes::BAZ);
+ }
+
+ const Reflection* refl = m0.GetReflection();
+ const Descriptor* desc = m0.GetDescriptor();
+
+ // Get FieldDescriptors for all the fields of interest.
+ const FieldDescriptor* fd_repeated_int32 =
+ desc->FindFieldByName("repeated_int32");
+ const FieldDescriptor* fd_repeated_double =
+ desc->FindFieldByName("repeated_double");
+ const FieldDescriptor* fd_repeated_string =
+ desc->FindFieldByName("repeated_string");
+ const FieldDescriptor* fd_repeated_foreign_message =
+ desc->FindFieldByName("repeated_foreign_message");
+ const FieldDescriptor* fd_repeated_nested_enum =
+ desc->FindFieldByName("repeated_nested_enum");
+
+ // Get MutableRepeatedFieldRef objects for all fields of interest.
+ const MutableRepeatedFieldRef<int32> mrf_int32 =
+ refl->GetMutableRepeatedFieldRef<int32>(&m0, fd_repeated_int32);
+ const MutableRepeatedFieldRef<double> mrf_double =
+ refl->GetMutableRepeatedFieldRef<double>(&m0, fd_repeated_double);
+ const MutableRepeatedFieldRef<string> mrf_string =
+ refl->GetMutableRepeatedFieldRef<string>(&m0, fd_repeated_string);
+ const MutableRepeatedFieldRef<ForeignMessage> mrf_foreign_message =
+ refl->GetMutableRepeatedFieldRef<ForeignMessage>(
+ &m0, fd_repeated_foreign_message);
+ const MutableRepeatedFieldRef<TestAllTypes::NestedEnum>
+ mrf_nested_enum =
+ refl->GetMutableRepeatedFieldRef<TestAllTypes::NestedEnum>(
+ &m0, fd_repeated_nested_enum);
+
+ // Test MutableRepeatedRef::CopyFrom
+ mrf_int32.CopyFrom(
+ refl->GetRepeatedFieldRef<int32>(m1, fd_repeated_int32));
+ mrf_double.CopyFrom(
+ refl->GetRepeatedFieldRef<double>(m1, fd_repeated_double));
+ mrf_string.CopyFrom(
+ refl->GetRepeatedFieldRef<string>(m1, fd_repeated_string));
+ mrf_foreign_message.CopyFrom(
+ refl->GetRepeatedFieldRef<ForeignMessage>(
+ m1, fd_repeated_foreign_message));
+ mrf_nested_enum.CopyFrom(
+ refl->GetRepeatedFieldRef<TestAllTypes::NestedEnum>(
+ m1, fd_repeated_nested_enum));
+ for (int i = 0; i < 10; ++i) {
+ EXPECT_EQ(Func(i, 11), m0.repeated_int32(i));
+ EXPECT_EQ(Func(i, 12), m0.repeated_double(i));
+ EXPECT_EQ(StrFunc(i, 15), m0.repeated_string(i));
+ EXPECT_EQ(Func(i, 16), m0.repeated_foreign_message(i).c());
+ EXPECT_EQ(TestAllTypes::BAR, m0.repeated_nested_enum(i));
+ }
+
+ // Test MutableRepeatedRef::MergeFrom
+ mrf_int32.MergeFrom(
+ refl->GetRepeatedFieldRef<int32>(m2, fd_repeated_int32));
+ mrf_double.MergeFrom(
+ refl->GetRepeatedFieldRef<double>(m2, fd_repeated_double));
+ mrf_string.MergeFrom(
+ refl->GetRepeatedFieldRef<string>(m2, fd_repeated_string));
+ mrf_foreign_message.MergeFrom(
+ refl->GetRepeatedFieldRef<ForeignMessage>(
+ m2, fd_repeated_foreign_message));
+ mrf_nested_enum.MergeFrom(
+ refl->GetRepeatedFieldRef<TestAllTypes::NestedEnum>(
+ m2, fd_repeated_nested_enum));
+ for (int i = 0; i < 10; ++i) {
+ EXPECT_EQ(Func(i, 21), m0.repeated_int32(i + 10));
+ EXPECT_EQ(Func(i, 22), m0.repeated_double(i + 10));
+ EXPECT_EQ(StrFunc(i, 25), m0.repeated_string(i + 10));
+ EXPECT_EQ(Func(i, 26), m0.repeated_foreign_message(i + 10).c());
+ EXPECT_EQ(TestAllTypes::BAZ, m0.repeated_nested_enum(i + 10));
+ }
+
+ // Test MutableRepeatedRef::Swap
+ // Swap between m0 and m2.
+ mrf_int32.Swap(
+ refl->GetMutableRepeatedFieldRef<int32>(&m2, fd_repeated_int32));
+ mrf_double.Swap(
+ refl->GetMutableRepeatedFieldRef<double>(&m2, fd_repeated_double));
+ mrf_string.Swap(
+ refl->GetMutableRepeatedFieldRef<string>(&m2, fd_repeated_string));
+ mrf_foreign_message.Swap(
+ refl->GetMutableRepeatedFieldRef<ForeignMessage>(
+ &m2, fd_repeated_foreign_message));
+ mrf_nested_enum.Swap(
+ refl->GetMutableRepeatedFieldRef<TestAllTypes::NestedEnum>(
+ &m2, fd_repeated_nested_enum));
+ for (int i = 0; i < 10; ++i) {
+ // Check the content of m0.
+ EXPECT_EQ(Func(i, 21), m0.repeated_int32(i));
+ EXPECT_EQ(Func(i, 22), m0.repeated_double(i));
+ EXPECT_EQ(StrFunc(i, 25), m0.repeated_string(i));
+ EXPECT_EQ(Func(i, 26), m0.repeated_foreign_message(i).c());
+ EXPECT_EQ(TestAllTypes::BAZ, m0.repeated_nested_enum(i));
+
+ // Check the content of m2.
+ EXPECT_EQ(Func(i, 11), m2.repeated_int32(i));
+ EXPECT_EQ(Func(i, 12), m2.repeated_double(i));
+ EXPECT_EQ(StrFunc(i, 15), m2.repeated_string(i));
+ EXPECT_EQ(Func(i, 16), m2.repeated_foreign_message(i).c());
+ EXPECT_EQ(TestAllTypes::BAR, m2.repeated_nested_enum(i));
+ EXPECT_EQ(Func(i, 21), m2.repeated_int32(i + 10));
+ EXPECT_EQ(Func(i, 22), m2.repeated_double(i + 10));
+ EXPECT_EQ(StrFunc(i, 25), m2.repeated_string(i + 10));
+ EXPECT_EQ(Func(i, 26), m2.repeated_foreign_message(i + 10).c());
+ EXPECT_EQ(TestAllTypes::BAZ, m2.repeated_nested_enum(i + 10));
+ }
+}
+
+// Test that GetRepeatedFieldRef/MutableRepeatedFieldRef works with
+// DynamicMessage.
+TEST(RepeatedFieldReflectionTest, RepeatedFieldRefDynamicMessage) {
+ // DynamicMessage shares the same memory layout as generated message
+ // and use the same GeneratedMessageReflection code for reflection.
+ // All code paths should already be covered by the other tests for
+ // generated messages. Here we just test one field.
+
+ const Descriptor* desc = TestAllTypes::descriptor();
+ const FieldDescriptor* fd_repeated_int32 =
+ desc->FindFieldByName("repeated_int32");
+
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> dynamic_message(factory.GetPrototype(desc)->New());
+ const Reflection* refl = dynamic_message->GetReflection();
+
+ MutableRepeatedFieldRef<int32> rf_int32 =
+ refl->GetMutableRepeatedFieldRef<int32>(
+ dynamic_message.get(), fd_repeated_int32);
+ rf_int32.Add(1234);
+ EXPECT_EQ(1, refl->FieldSize(*dynamic_message, fd_repeated_int32));
+ EXPECT_EQ(1234, refl->GetRepeatedInt32(*dynamic_message,
+ fd_repeated_int32, 0));
+}
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_unittest.cc
new file mode 100644
index 0000000000..39b24b3375
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/repeated_field_unittest.cc
@@ -0,0 +1,1566 @@
+// 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.
+//
+// TODO(kenton): Improve this unittest to bring it up to the standards of
+// other proto2 unittests.
+
+#include <algorithm>
+#include <limits>
+#include <list>
+#include <vector>
+
+#include <google/protobuf/repeated_field.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+using protobuf_unittest::TestAllTypes;
+
+namespace protobuf {
+namespace {
+
+// Test operations on a small RepeatedField.
+TEST(RepeatedField, Small) {
+ RepeatedField<int> field;
+
+ EXPECT_TRUE(field.empty());
+ EXPECT_EQ(field.size(), 0);
+
+ field.Add(5);
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 1);
+ EXPECT_EQ(field.Get(0), 5);
+
+ field.Add(42);
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 2);
+ EXPECT_EQ(field.Get(0), 5);
+ EXPECT_EQ(field.Get(1), 42);
+
+ field.Set(1, 23);
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 2);
+ EXPECT_EQ(field.Get(0), 5);
+ EXPECT_EQ(field.Get(1), 23);
+
+ field.RemoveLast();
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 1);
+ EXPECT_EQ(field.Get(0), 5);
+
+ field.Clear();
+
+ EXPECT_TRUE(field.empty());
+ EXPECT_EQ(field.size(), 0);
+ // Additional bytes are for 'struct Rep' header.
+ int expected_usage = 4 * sizeof(int) + sizeof(Arena*);
+ EXPECT_EQ(field.SpaceUsedExcludingSelf(), expected_usage);
+}
+
+
+// Test operations on a RepeatedField which is large enough to allocate a
+// separate array.
+TEST(RepeatedField, Large) {
+ RepeatedField<int> field;
+
+ for (int i = 0; i < 16; i++) {
+ field.Add(i * i);
+ }
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 16);
+
+ for (int i = 0; i < 16; i++) {
+ EXPECT_EQ(field.Get(i), i * i);
+ }
+
+ int expected_usage = 16 * sizeof(int);
+ EXPECT_GE(field.SpaceUsedExcludingSelf(), expected_usage);
+}
+
+// Test swapping between various types of RepeatedFields.
+TEST(RepeatedField, SwapSmallSmall) {
+ RepeatedField<int> field1;
+ RepeatedField<int> field2;
+
+ field1.Add(5);
+ field1.Add(42);
+
+ EXPECT_FALSE(field1.empty());
+ EXPECT_EQ(field1.size(), 2);
+ EXPECT_EQ(field1.Get(0), 5);
+ EXPECT_EQ(field1.Get(1), 42);
+
+ EXPECT_TRUE(field2.empty());
+ EXPECT_EQ(field2.size(), 0);
+
+ field1.Swap(&field2);
+
+ EXPECT_TRUE(field1.empty());
+ EXPECT_EQ(field1.size(), 0);
+
+ EXPECT_FALSE(field2.empty());
+ EXPECT_EQ(field2.size(), 2);
+ EXPECT_EQ(field2.Get(0), 5);
+ EXPECT_EQ(field2.Get(1), 42);
+}
+
+TEST(RepeatedField, SwapLargeSmall) {
+ RepeatedField<int> field1;
+ RepeatedField<int> field2;
+
+ for (int i = 0; i < 16; i++) {
+ field1.Add(i * i);
+ }
+ field2.Add(5);
+ field2.Add(42);
+ field1.Swap(&field2);
+
+ EXPECT_EQ(field1.size(), 2);
+ EXPECT_EQ(field1.Get(0), 5);
+ EXPECT_EQ(field1.Get(1), 42);
+ EXPECT_EQ(field2.size(), 16);
+ for (int i = 0; i < 16; i++) {
+ EXPECT_EQ(field2.Get(i), i * i);
+ }
+}
+
+TEST(RepeatedField, SwapLargeLarge) {
+ RepeatedField<int> field1;
+ RepeatedField<int> field2;
+
+ field1.Add(5);
+ field1.Add(42);
+ for (int i = 0; i < 16; i++) {
+ field1.Add(i);
+ field2.Add(i * i);
+ }
+ field2.Swap(&field1);
+
+ EXPECT_EQ(field1.size(), 16);
+ for (int i = 0; i < 16; i++) {
+ EXPECT_EQ(field1.Get(i), i * i);
+ }
+ EXPECT_EQ(field2.size(), 18);
+ EXPECT_EQ(field2.Get(0), 5);
+ EXPECT_EQ(field2.Get(1), 42);
+ for (int i = 2; i < 18; i++) {
+ EXPECT_EQ(field2.Get(i), i - 2);
+ }
+}
+
+// Determines how much space was reserved by the given field by adding elements
+// to it until it re-allocates its space.
+static int ReservedSpace(RepeatedField<int>* field) {
+ const int* ptr = field->data();
+ do {
+ field->Add(0);
+ } while (field->data() == ptr);
+
+ return field->size() - 1;
+}
+
+TEST(RepeatedField, ReserveMoreThanDouble) {
+ // Reserve more than double the previous space in the field and expect the
+ // field to reserve exactly the amount specified.
+ RepeatedField<int> field;
+ field.Reserve(20);
+
+ EXPECT_EQ(20, ReservedSpace(&field));
+}
+
+TEST(RepeatedField, ReserveLessThanDouble) {
+ // Reserve less than double the previous space in the field and expect the
+ // field to grow by double instead.
+ RepeatedField<int> field;
+ field.Reserve(20);
+ field.Reserve(30);
+
+ EXPECT_EQ(40, ReservedSpace(&field));
+}
+
+TEST(RepeatedField, ReserveLessThanExisting) {
+ // Reserve less than the previous space in the field and expect the
+ // field to not re-allocate at all.
+ RepeatedField<int> field;
+ field.Reserve(20);
+ const int* previous_ptr = field.data();
+ field.Reserve(10);
+
+ EXPECT_EQ(previous_ptr, field.data());
+ EXPECT_EQ(20, ReservedSpace(&field));
+}
+
+TEST(RepeatedField, Resize) {
+ RepeatedField<int> field;
+ field.Resize(2, 1);
+ EXPECT_EQ(2, field.size());
+ field.Resize(5, 2);
+ EXPECT_EQ(5, field.size());
+ field.Resize(4, 3);
+ ASSERT_EQ(4, field.size());
+ EXPECT_EQ(1, field.Get(0));
+ EXPECT_EQ(1, field.Get(1));
+ EXPECT_EQ(2, field.Get(2));
+ EXPECT_EQ(2, field.Get(3));
+ field.Resize(0, 4);
+ EXPECT_TRUE(field.empty());
+}
+
+TEST(RepeatedField, MergeFrom) {
+ RepeatedField<int> source, destination;
+ source.Add(4);
+ source.Add(5);
+ destination.Add(1);
+ destination.Add(2);
+ destination.Add(3);
+
+ destination.MergeFrom(source);
+
+ ASSERT_EQ(5, destination.size());
+ EXPECT_EQ(1, destination.Get(0));
+ EXPECT_EQ(2, destination.Get(1));
+ EXPECT_EQ(3, destination.Get(2));
+ EXPECT_EQ(4, destination.Get(3));
+ EXPECT_EQ(5, destination.Get(4));
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+TEST(RepeatedField, MergeFromSelf) {
+ RepeatedField<int> me;
+ me.Add(3);
+ EXPECT_DEATH(me.MergeFrom(me), "");
+}
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST(RepeatedField, CopyFrom) {
+ RepeatedField<int> source, destination;
+ source.Add(4);
+ source.Add(5);
+ destination.Add(1);
+ destination.Add(2);
+ destination.Add(3);
+
+ destination.CopyFrom(source);
+
+ ASSERT_EQ(2, destination.size());
+ EXPECT_EQ(4, destination.Get(0));
+ EXPECT_EQ(5, destination.Get(1));
+}
+
+TEST(RepeatedField, CopyFromSelf) {
+ RepeatedField<int> me;
+ me.Add(3);
+ me.CopyFrom(me);
+ ASSERT_EQ(1, me.size());
+ EXPECT_EQ(3, me.Get(0));
+}
+
+TEST(RepeatedField, Erase) {
+ RepeatedField<int> me;
+ RepeatedField<int>::iterator it = me.erase(me.begin(), me.end());
+ EXPECT_TRUE(me.begin() == it);
+ EXPECT_EQ(0, me.size());
+
+ me.Add(1);
+ me.Add(2);
+ me.Add(3);
+ it = me.erase(me.begin(), me.end());
+ EXPECT_TRUE(me.begin() == it);
+ EXPECT_EQ(0, me.size());
+
+ me.Add(4);
+ me.Add(5);
+ me.Add(6);
+ it = me.erase(me.begin() + 2, me.end());
+ EXPECT_TRUE(me.begin() + 2 == it);
+ EXPECT_EQ(2, me.size());
+ EXPECT_EQ(4, me.Get(0));
+ EXPECT_EQ(5, me.Get(1));
+
+ me.Add(6);
+ me.Add(7);
+ me.Add(8);
+ it = me.erase(me.begin() + 1, me.begin() + 3);
+ EXPECT_TRUE(me.begin() + 1 == it);
+ EXPECT_EQ(3, me.size());
+ EXPECT_EQ(4, me.Get(0));
+ EXPECT_EQ(7, me.Get(1));
+ EXPECT_EQ(8, me.Get(2));
+}
+
+TEST(RepeatedField, CopyConstruct) {
+ RepeatedField<int> source;
+ source.Add(1);
+ source.Add(2);
+
+ RepeatedField<int> destination(source);
+
+ ASSERT_EQ(2, destination.size());
+ EXPECT_EQ(1, destination.Get(0));
+ EXPECT_EQ(2, destination.Get(1));
+}
+
+TEST(RepeatedField, IteratorConstruct) {
+ vector<int> values;
+ values.push_back(1);
+ values.push_back(2);
+
+ RepeatedField<int> field(values.begin(), values.end());
+ ASSERT_EQ(values.size(), field.size());
+ EXPECT_EQ(values[0], field.Get(0));
+ EXPECT_EQ(values[1], field.Get(1));
+
+ RepeatedField<int> other(field.begin(), field.end());
+ ASSERT_EQ(values.size(), other.size());
+ EXPECT_EQ(values[0], other.Get(0));
+ EXPECT_EQ(values[1], other.Get(1));
+}
+
+TEST(RepeatedField, CopyAssign) {
+ RepeatedField<int> source, destination;
+ source.Add(4);
+ source.Add(5);
+ destination.Add(1);
+ destination.Add(2);
+ destination.Add(3);
+
+ destination = source;
+
+ ASSERT_EQ(2, destination.size());
+ EXPECT_EQ(4, destination.Get(0));
+ EXPECT_EQ(5, destination.Get(1));
+}
+
+TEST(RepeatedField, SelfAssign) {
+ // Verify that assignment to self does not destroy data.
+ RepeatedField<int> source, *p;
+ p = &source;
+ source.Add(7);
+ source.Add(8);
+
+ *p = source;
+
+ ASSERT_EQ(2, source.size());
+ EXPECT_EQ(7, source.Get(0));
+ EXPECT_EQ(8, source.Get(1));
+}
+
+TEST(RepeatedField, MutableDataIsMutable) {
+ RepeatedField<int> field;
+ field.Add(1);
+ EXPECT_EQ(1, field.Get(0));
+ // The fact that this line compiles would be enough, but we'll check the
+ // value anyway.
+ *field.mutable_data() = 2;
+ EXPECT_EQ(2, field.Get(0));
+}
+
+TEST(RepeatedField, Truncate) {
+ RepeatedField<int> field;
+
+ field.Add(12);
+ field.Add(34);
+ field.Add(56);
+ field.Add(78);
+ EXPECT_EQ(4, field.size());
+
+ field.Truncate(3);
+ EXPECT_EQ(3, field.size());
+
+ field.Add(90);
+ EXPECT_EQ(4, field.size());
+ EXPECT_EQ(90, field.Get(3));
+
+ // Truncations that don't change the size are allowed, but growing is not
+ // allowed.
+ field.Truncate(field.size());
+#ifdef PROTOBUF_HAS_DEATH_TEST
+ EXPECT_DEBUG_DEATH(field.Truncate(field.size() + 1), "new_size");
+#endif
+}
+
+
+TEST(RepeatedField, ExtractSubrange) {
+ // Exhaustively test every subrange in arrays of all sizes from 0 through 9.
+ for (int sz = 0; sz < 10; ++sz) {
+ for (int num = 0; num <= sz; ++num) {
+ for (int start = 0; start < sz - num; ++start) {
+ // Create RepeatedField with sz elements having values 0 through sz-1.
+ RepeatedField<int32> field;
+ for (int i = 0; i < sz; ++i)
+ field.Add(i);
+ EXPECT_EQ(field.size(), sz);
+
+ // Create a catcher array and call ExtractSubrange.
+ int32 catcher[10];
+ for (int i = 0; i < 10; ++i)
+ catcher[i] = -1;
+ field.ExtractSubrange(start, num, catcher);
+
+ // Does the resulting array have the right size?
+ EXPECT_EQ(field.size(), sz - num);
+
+ // Were the removed elements extracted into the catcher array?
+ for (int i = 0; i < num; ++i)
+ EXPECT_EQ(catcher[i], start + i);
+ EXPECT_EQ(catcher[num], -1);
+
+ // Does the resulting array contain the right values?
+ for (int i = 0; i < start; ++i)
+ EXPECT_EQ(field.Get(i), i);
+ for (int i = start; i < field.size(); ++i)
+ EXPECT_EQ(field.Get(i), i + num);
+ }
+ }
+ }
+}
+
+TEST(RepeatedField, ClearThenReserveMore) {
+ // Test that Reserve properly destroys the old internal array when it's forced
+ // to allocate a new one, even when cleared-but-not-deleted objects are
+ // present. Use a 'string' and > 16 bytes length so that the elements are
+ // non-POD and allocate -- the leak checker will catch any skipped destructor
+ // calls here.
+ RepeatedField<string> field;
+ for (int i = 0; i < 32; i++) {
+ field.Add(string("abcdefghijklmnopqrstuvwxyz0123456789"));
+ }
+ EXPECT_EQ(32, field.size());
+ field.Clear();
+ EXPECT_EQ(0, field.size());
+ EXPECT_EQ(32, field.Capacity());
+
+ field.Reserve(1024);
+ EXPECT_EQ(0, field.size());
+ EXPECT_EQ(1024, field.Capacity());
+ // Finish test -- |field| should destroy the cleared-but-not-yet-destroyed
+ // strings.
+}
+
+// ===================================================================
+// RepeatedPtrField tests. These pretty much just mirror the RepeatedField
+// tests above.
+
+TEST(RepeatedPtrField, Small) {
+ RepeatedPtrField<string> field;
+
+ EXPECT_TRUE(field.empty());
+ EXPECT_EQ(field.size(), 0);
+
+ field.Add()->assign("foo");
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 1);
+ EXPECT_EQ(field.Get(0), "foo");
+
+ field.Add()->assign("bar");
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 2);
+ EXPECT_EQ(field.Get(0), "foo");
+ EXPECT_EQ(field.Get(1), "bar");
+
+ field.Mutable(1)->assign("baz");
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 2);
+ EXPECT_EQ(field.Get(0), "foo");
+ EXPECT_EQ(field.Get(1), "baz");
+
+ field.RemoveLast();
+
+ EXPECT_FALSE(field.empty());
+ EXPECT_EQ(field.size(), 1);
+ EXPECT_EQ(field.Get(0), "foo");
+
+ field.Clear();
+
+ EXPECT_TRUE(field.empty());
+ EXPECT_EQ(field.size(), 0);
+}
+
+TEST(RepeatedPtrField, Large) {
+ RepeatedPtrField<string> field;
+
+ for (int i = 0; i < 16; i++) {
+ *field.Add() += 'a' + i;
+ }
+
+ EXPECT_EQ(field.size(), 16);
+
+ for (int i = 0; i < 16; i++) {
+ EXPECT_EQ(field.Get(i).size(), 1);
+ EXPECT_EQ(field.Get(i)[0], 'a' + i);
+ }
+
+ int min_expected_usage = 16 * sizeof(string);
+ EXPECT_GE(field.SpaceUsedExcludingSelf(), min_expected_usage);
+}
+
+TEST(RepeatedPtrField, SwapSmallSmall) {
+ RepeatedPtrField<string> field1;
+ RepeatedPtrField<string> field2;
+
+ EXPECT_TRUE(field1.empty());
+ EXPECT_EQ(field1.size(), 0);
+ EXPECT_TRUE(field2.empty());
+ EXPECT_EQ(field2.size(), 0);
+
+ field1.Add()->assign("foo");
+ field1.Add()->assign("bar");
+
+ EXPECT_FALSE(field1.empty());
+ EXPECT_EQ(field1.size(), 2);
+ EXPECT_EQ(field1.Get(0), "foo");
+ EXPECT_EQ(field1.Get(1), "bar");
+
+ EXPECT_TRUE(field2.empty());
+ EXPECT_EQ(field2.size(), 0);
+
+ field1.Swap(&field2);
+
+ EXPECT_TRUE(field1.empty());
+ EXPECT_EQ(field1.size(), 0);
+
+ EXPECT_EQ(field2.size(), 2);
+ EXPECT_EQ(field2.Get(0), "foo");
+ EXPECT_EQ(field2.Get(1), "bar");
+}
+
+TEST(RepeatedPtrField, SwapLargeSmall) {
+ RepeatedPtrField<string> field1;
+ RepeatedPtrField<string> field2;
+
+ field2.Add()->assign("foo");
+ field2.Add()->assign("bar");
+ for (int i = 0; i < 16; i++) {
+ *field1.Add() += 'a' + i;
+ }
+ field1.Swap(&field2);
+
+ EXPECT_EQ(field1.size(), 2);
+ EXPECT_EQ(field1.Get(0), "foo");
+ EXPECT_EQ(field1.Get(1), "bar");
+ EXPECT_EQ(field2.size(), 16);
+ for (int i = 0; i < 16; i++) {
+ EXPECT_EQ(field2.Get(i).size(), 1);
+ EXPECT_EQ(field2.Get(i)[0], 'a' + i);
+ }
+}
+
+TEST(RepeatedPtrField, SwapLargeLarge) {
+ RepeatedPtrField<string> field1;
+ RepeatedPtrField<string> field2;
+
+ field1.Add()->assign("foo");
+ field1.Add()->assign("bar");
+ for (int i = 0; i < 16; i++) {
+ *field1.Add() += 'A' + i;
+ *field2.Add() += 'a' + i;
+ }
+ field2.Swap(&field1);
+
+ EXPECT_EQ(field1.size(), 16);
+ for (int i = 0; i < 16; i++) {
+ EXPECT_EQ(field1.Get(i).size(), 1);
+ EXPECT_EQ(field1.Get(i)[0], 'a' + i);
+ }
+ EXPECT_EQ(field2.size(), 18);
+ EXPECT_EQ(field2.Get(0), "foo");
+ EXPECT_EQ(field2.Get(1), "bar");
+ for (int i = 2; i < 18; i++) {
+ EXPECT_EQ(field2.Get(i).size(), 1);
+ EXPECT_EQ(field2.Get(i)[0], 'A' + i - 2);
+ }
+}
+
+static int ReservedSpace(RepeatedPtrField<string>* field) {
+ const string* const* ptr = field->data();
+ do {
+ field->Add();
+ } while (field->data() == ptr);
+
+ return field->size() - 1;
+}
+
+TEST(RepeatedPtrField, ReserveMoreThanDouble) {
+ RepeatedPtrField<string> field;
+ field.Reserve(20);
+
+ EXPECT_EQ(20, ReservedSpace(&field));
+}
+
+TEST(RepeatedPtrField, ReserveLessThanDouble) {
+ RepeatedPtrField<string> field;
+ field.Reserve(20);
+ field.Reserve(30);
+
+ EXPECT_EQ(40, ReservedSpace(&field));
+}
+
+TEST(RepeatedPtrField, ReserveLessThanExisting) {
+ RepeatedPtrField<string> field;
+ field.Reserve(20);
+ const string* const* previous_ptr = field.data();
+ field.Reserve(10);
+
+ EXPECT_EQ(previous_ptr, field.data());
+ EXPECT_EQ(20, ReservedSpace(&field));
+}
+
+TEST(RepeatedPtrField, ReserveDoesntLoseAllocated) {
+ // Check that a bug is fixed: An earlier implementation of Reserve()
+ // failed to copy pointers to allocated-but-cleared objects, possibly
+ // leading to segfaults.
+ RepeatedPtrField<string> field;
+ string* first = field.Add();
+ field.RemoveLast();
+
+ field.Reserve(20);
+ EXPECT_EQ(first, field.Add());
+}
+
+// Clearing elements is tricky with RepeatedPtrFields since the memory for
+// the elements is retained and reused.
+TEST(RepeatedPtrField, ClearedElements) {
+ RepeatedPtrField<string> field;
+
+ string* original = field.Add();
+ *original = "foo";
+
+ EXPECT_EQ(field.ClearedCount(), 0);
+
+ field.RemoveLast();
+ EXPECT_TRUE(original->empty());
+ EXPECT_EQ(field.ClearedCount(), 1);
+
+ EXPECT_EQ(field.Add(), original); // Should return same string for reuse.
+
+ EXPECT_EQ(field.ReleaseLast(), original); // We take ownership.
+ EXPECT_EQ(field.ClearedCount(), 0);
+
+ EXPECT_NE(field.Add(), original); // Should NOT return the same string.
+ EXPECT_EQ(field.ClearedCount(), 0);
+
+ field.AddAllocated(original); // Give ownership back.
+ EXPECT_EQ(field.ClearedCount(), 0);
+ EXPECT_EQ(field.Mutable(1), original);
+
+ field.Clear();
+ EXPECT_EQ(field.ClearedCount(), 2);
+ EXPECT_EQ(field.ReleaseCleared(), original); // Take ownership again.
+ EXPECT_EQ(field.ClearedCount(), 1);
+ EXPECT_NE(field.Add(), original);
+ EXPECT_EQ(field.ClearedCount(), 0);
+ EXPECT_NE(field.Add(), original);
+ EXPECT_EQ(field.ClearedCount(), 0);
+
+ field.AddCleared(original); // Give ownership back, but as a cleared object.
+ EXPECT_EQ(field.ClearedCount(), 1);
+ EXPECT_EQ(field.Add(), original);
+ EXPECT_EQ(field.ClearedCount(), 0);
+}
+
+// Test all code paths in AddAllocated().
+TEST(RepeatedPtrField, AddAlocated) {
+ RepeatedPtrField<string> field;
+ while (field.size() < field.Capacity()) {
+ field.Add()->assign("filler");
+ }
+
+ int index = field.size();
+
+ // First branch: Field is at capacity with no cleared objects.
+ string* foo = new string("foo");
+ field.AddAllocated(foo);
+ EXPECT_EQ(index + 1, field.size());
+ EXPECT_EQ(0, field.ClearedCount());
+ EXPECT_EQ(foo, &field.Get(index));
+
+ // Last branch: Field is not at capacity and there are no cleared objects.
+ string* bar = new string("bar");
+ field.AddAllocated(bar);
+ ++index;
+ EXPECT_EQ(index + 1, field.size());
+ EXPECT_EQ(0, field.ClearedCount());
+ EXPECT_EQ(bar, &field.Get(index));
+
+ // Third branch: Field is not at capacity and there are no cleared objects.
+ field.RemoveLast();
+ string* baz = new string("baz");
+ field.AddAllocated(baz);
+ EXPECT_EQ(index + 1, field.size());
+ EXPECT_EQ(1, field.ClearedCount());
+ EXPECT_EQ(baz, &field.Get(index));
+
+ // Second branch: Field is at capacity but has some cleared objects.
+ while (field.size() < field.Capacity()) {
+ field.Add()->assign("filler2");
+ }
+ field.RemoveLast();
+ index = field.size();
+ string* qux = new string("qux");
+ field.AddAllocated(qux);
+ EXPECT_EQ(index + 1, field.size());
+ // We should have discarded the cleared object.
+ EXPECT_EQ(0, field.ClearedCount());
+ EXPECT_EQ(qux, &field.Get(index));
+}
+
+TEST(RepeatedPtrField, MergeFrom) {
+ RepeatedPtrField<string> source, destination;
+ source.Add()->assign("4");
+ source.Add()->assign("5");
+ destination.Add()->assign("1");
+ destination.Add()->assign("2");
+ destination.Add()->assign("3");
+
+ destination.MergeFrom(source);
+
+ ASSERT_EQ(5, destination.size());
+ EXPECT_EQ("1", destination.Get(0));
+ EXPECT_EQ("2", destination.Get(1));
+ EXPECT_EQ("3", destination.Get(2));
+ EXPECT_EQ("4", destination.Get(3));
+ EXPECT_EQ("5", destination.Get(4));
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+TEST(RepeatedPtrField, MergeFromSelf) {
+ RepeatedPtrField<string> me;
+ me.Add()->assign("1");
+ EXPECT_DEATH(me.MergeFrom(me), "");
+}
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST(RepeatedPtrField, CopyFrom) {
+ RepeatedPtrField<string> source, destination;
+ source.Add()->assign("4");
+ source.Add()->assign("5");
+ destination.Add()->assign("1");
+ destination.Add()->assign("2");
+ destination.Add()->assign("3");
+
+ destination.CopyFrom(source);
+
+ ASSERT_EQ(2, destination.size());
+ EXPECT_EQ("4", destination.Get(0));
+ EXPECT_EQ("5", destination.Get(1));
+}
+
+TEST(RepeatedPtrField, CopyFromSelf) {
+ RepeatedPtrField<string> me;
+ me.Add()->assign("1");
+ me.CopyFrom(me);
+ ASSERT_EQ(1, me.size());
+ EXPECT_EQ("1", me.Get(0));
+}
+
+TEST(RepeatedPtrField, Erase) {
+ RepeatedPtrField<string> me;
+ RepeatedPtrField<string>::iterator it = me.erase(me.begin(), me.end());
+ EXPECT_TRUE(me.begin() == it);
+ EXPECT_EQ(0, me.size());
+
+ *me.Add() = "1";
+ *me.Add() = "2";
+ *me.Add() = "3";
+ it = me.erase(me.begin(), me.end());
+ EXPECT_TRUE(me.begin() == it);
+ EXPECT_EQ(0, me.size());
+
+ *me.Add() = "4";
+ *me.Add() = "5";
+ *me.Add() = "6";
+ it = me.erase(me.begin() + 2, me.end());
+ EXPECT_TRUE(me.begin() + 2 == it);
+ EXPECT_EQ(2, me.size());
+ EXPECT_EQ("4", me.Get(0));
+ EXPECT_EQ("5", me.Get(1));
+
+ *me.Add() = "6";
+ *me.Add() = "7";
+ *me.Add() = "8";
+ it = me.erase(me.begin() + 1, me.begin() + 3);
+ EXPECT_TRUE(me.begin() + 1 == it);
+ EXPECT_EQ(3, me.size());
+ EXPECT_EQ("4", me.Get(0));
+ EXPECT_EQ("7", me.Get(1));
+ EXPECT_EQ("8", me.Get(2));
+}
+
+TEST(RepeatedPtrField, CopyConstruct) {
+ RepeatedPtrField<string> source;
+ source.Add()->assign("1");
+ source.Add()->assign("2");
+
+ RepeatedPtrField<string> destination(source);
+
+ ASSERT_EQ(2, destination.size());
+ EXPECT_EQ("1", destination.Get(0));
+ EXPECT_EQ("2", destination.Get(1));
+}
+
+TEST(RepeatedPtrField, IteratorConstruct_String) {
+ vector<string> values;
+ values.push_back("1");
+ values.push_back("2");
+
+ RepeatedPtrField<string> field(values.begin(), values.end());
+ ASSERT_EQ(values.size(), field.size());
+ EXPECT_EQ(values[0], field.Get(0));
+ EXPECT_EQ(values[1], field.Get(1));
+
+ RepeatedPtrField<string> other(field.begin(), field.end());
+ ASSERT_EQ(values.size(), other.size());
+ EXPECT_EQ(values[0], other.Get(0));
+ EXPECT_EQ(values[1], other.Get(1));
+}
+
+TEST(RepeatedPtrField, IteratorConstruct_Proto) {
+ typedef TestAllTypes::NestedMessage Nested;
+ vector<Nested> values;
+ values.push_back(Nested());
+ values.back().set_bb(1);
+ values.push_back(Nested());
+ values.back().set_bb(2);
+
+ RepeatedPtrField<Nested> field(values.begin(), values.end());
+ ASSERT_EQ(values.size(), field.size());
+ EXPECT_EQ(values[0].bb(), field.Get(0).bb());
+ EXPECT_EQ(values[1].bb(), field.Get(1).bb());
+
+ RepeatedPtrField<Nested> other(field.begin(), field.end());
+ ASSERT_EQ(values.size(), other.size());
+ EXPECT_EQ(values[0].bb(), other.Get(0).bb());
+ EXPECT_EQ(values[1].bb(), other.Get(1).bb());
+}
+
+TEST(RepeatedPtrField, CopyAssign) {
+ RepeatedPtrField<string> source, destination;
+ source.Add()->assign("4");
+ source.Add()->assign("5");
+ destination.Add()->assign("1");
+ destination.Add()->assign("2");
+ destination.Add()->assign("3");
+
+ destination = source;
+
+ ASSERT_EQ(2, destination.size());
+ EXPECT_EQ("4", destination.Get(0));
+ EXPECT_EQ("5", destination.Get(1));
+}
+
+TEST(RepeatedPtrField, SelfAssign) {
+ // Verify that assignment to self does not destroy data.
+ RepeatedPtrField<string> source, *p;
+ p = &source;
+ source.Add()->assign("7");
+ source.Add()->assign("8");
+
+ *p = source;
+
+ ASSERT_EQ(2, source.size());
+ EXPECT_EQ("7", source.Get(0));
+ EXPECT_EQ("8", source.Get(1));
+}
+
+TEST(RepeatedPtrField, MutableDataIsMutable) {
+ RepeatedPtrField<string> field;
+ *field.Add() = "1";
+ EXPECT_EQ("1", field.Get(0));
+ // The fact that this line compiles would be enough, but we'll check the
+ // value anyway.
+ string** data = field.mutable_data();
+ **data = "2";
+ EXPECT_EQ("2", field.Get(0));
+}
+
+TEST(RepeatedPtrField, ExtractSubrange) {
+ // Exhaustively test every subrange in arrays of all sizes from 0 through 9
+ // with 0 through 3 cleared elements at the end.
+ for (int sz = 0; sz < 10; ++sz) {
+ for (int num = 0; num <= sz; ++num) {
+ for (int start = 0; start < sz - num; ++start) {
+ for (int extra = 0; extra < 4; ++extra) {
+ vector<string*> subject;
+
+ // Create an array with "sz" elements and "extra" cleared elements.
+ RepeatedPtrField<string> field;
+ for (int i = 0; i < sz + extra; ++i) {
+ subject.push_back(new string());
+ field.AddAllocated(subject[i]);
+ }
+ EXPECT_EQ(field.size(), sz + extra);
+ for (int i = 0; i < extra; ++i)
+ field.RemoveLast();
+ EXPECT_EQ(field.size(), sz);
+ EXPECT_EQ(field.ClearedCount(), extra);
+
+ // Create a catcher array and call ExtractSubrange.
+ string* catcher[10];
+ for (int i = 0; i < 10; ++i)
+ catcher[i] = NULL;
+ field.ExtractSubrange(start, num, catcher);
+
+ // Does the resulting array have the right size?
+ EXPECT_EQ(field.size(), sz - num);
+
+ // Were the removed elements extracted into the catcher array?
+ for (int i = 0; i < num; ++i)
+ EXPECT_EQ(catcher[i], subject[start + i]);
+ EXPECT_EQ(NULL, catcher[num]);
+
+ // Does the resulting array contain the right values?
+ for (int i = 0; i < start; ++i)
+ EXPECT_EQ(field.Mutable(i), subject[i]);
+ for (int i = start; i < field.size(); ++i)
+ EXPECT_EQ(field.Mutable(i), subject[i + num]);
+
+ // Reinstate the cleared elements.
+ EXPECT_EQ(field.ClearedCount(), extra);
+ for (int i = 0; i < extra; ++i)
+ field.Add();
+ EXPECT_EQ(field.ClearedCount(), 0);
+ EXPECT_EQ(field.size(), sz - num + extra);
+
+ // Make sure the extra elements are all there (in some order).
+ for (int i = sz; i < sz + extra; ++i) {
+ int count = 0;
+ for (int j = sz; j < sz + extra; ++j) {
+ if (field.Mutable(j - num) == subject[i])
+ count += 1;
+ }
+ EXPECT_EQ(count, 1);
+ }
+
+ // Release the caught elements.
+ for (int i = 0; i < num; ++i)
+ delete catcher[i];
+ }
+ }
+ }
+ }
+}
+
+TEST(RepeatedPtrField, DeleteSubrange) {
+ // DeleteSubrange is a trivial extension of ExtendSubrange.
+}
+
+// ===================================================================
+
+// Iterator tests stolen from net/proto/proto-array_unittest.
+class RepeatedFieldIteratorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ for (int i = 0; i < 3; ++i) {
+ proto_array_.Add(i);
+ }
+ }
+
+ RepeatedField<int> proto_array_;
+};
+
+TEST_F(RepeatedFieldIteratorTest, Convertible) {
+ RepeatedField<int>::iterator iter = proto_array_.begin();
+ RepeatedField<int>::const_iterator c_iter = iter;
+ RepeatedField<int>::value_type value = *c_iter;
+ EXPECT_EQ(0, value);
+}
+
+TEST_F(RepeatedFieldIteratorTest, MutableIteration) {
+ RepeatedField<int>::iterator iter = proto_array_.begin();
+ EXPECT_EQ(0, *iter);
+ ++iter;
+ EXPECT_EQ(1, *iter++);
+ EXPECT_EQ(2, *iter);
+ ++iter;
+ EXPECT_TRUE(proto_array_.end() == iter);
+
+ EXPECT_EQ(2, *(proto_array_.end() - 1));
+}
+
+TEST_F(RepeatedFieldIteratorTest, ConstIteration) {
+ const RepeatedField<int>& const_proto_array = proto_array_;
+ RepeatedField<int>::const_iterator iter = const_proto_array.begin();
+ EXPECT_EQ(0, *iter);
+ ++iter;
+ EXPECT_EQ(1, *iter++);
+ EXPECT_EQ(2, *iter);
+ ++iter;
+ EXPECT_TRUE(proto_array_.end() == iter);
+ EXPECT_EQ(2, *(proto_array_.end() - 1));
+}
+
+TEST_F(RepeatedFieldIteratorTest, Mutation) {
+ RepeatedField<int>::iterator iter = proto_array_.begin();
+ *iter = 7;
+ EXPECT_EQ(7, proto_array_.Get(0));
+}
+
+// -------------------------------------------------------------------
+
+class RepeatedPtrFieldIteratorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ proto_array_.Add()->assign("foo");
+ proto_array_.Add()->assign("bar");
+ proto_array_.Add()->assign("baz");
+ }
+
+ RepeatedPtrField<string> proto_array_;
+};
+
+TEST_F(RepeatedPtrFieldIteratorTest, Convertible) {
+ RepeatedPtrField<string>::iterator iter = proto_array_.begin();
+ RepeatedPtrField<string>::const_iterator c_iter = iter;
+ RepeatedPtrField<string>::value_type value = *c_iter;
+ EXPECT_EQ("foo", value);
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, MutableIteration) {
+ RepeatedPtrField<string>::iterator iter = proto_array_.begin();
+ EXPECT_EQ("foo", *iter);
+ ++iter;
+ EXPECT_EQ("bar", *(iter++));
+ EXPECT_EQ("baz", *iter);
+ ++iter;
+ EXPECT_TRUE(proto_array_.end() == iter);
+ EXPECT_EQ("baz", *(--proto_array_.end()));
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, ConstIteration) {
+ const RepeatedPtrField<string>& const_proto_array = proto_array_;
+ RepeatedPtrField<string>::const_iterator iter = const_proto_array.begin();
+ EXPECT_EQ("foo", *iter);
+ ++iter;
+ EXPECT_EQ("bar", *(iter++));
+ EXPECT_EQ("baz", *iter);
+ ++iter;
+ EXPECT_TRUE(const_proto_array.end() == iter);
+ EXPECT_EQ("baz", *(--const_proto_array.end()));
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, MutableReverseIteration) {
+ RepeatedPtrField<string>::reverse_iterator iter = proto_array_.rbegin();
+ EXPECT_EQ("baz", *iter);
+ ++iter;
+ EXPECT_EQ("bar", *(iter++));
+ EXPECT_EQ("foo", *iter);
+ ++iter;
+ EXPECT_TRUE(proto_array_.rend() == iter);
+ EXPECT_EQ("foo", *(--proto_array_.rend()));
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, ConstReverseIteration) {
+ const RepeatedPtrField<string>& const_proto_array = proto_array_;
+ RepeatedPtrField<string>::const_reverse_iterator iter
+ = const_proto_array.rbegin();
+ EXPECT_EQ("baz", *iter);
+ ++iter;
+ EXPECT_EQ("bar", *(iter++));
+ EXPECT_EQ("foo", *iter);
+ ++iter;
+ EXPECT_TRUE(const_proto_array.rend() == iter);
+ EXPECT_EQ("foo", *(--const_proto_array.rend()));
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, RandomAccess) {
+ RepeatedPtrField<string>::iterator iter = proto_array_.begin();
+ RepeatedPtrField<string>::iterator iter2 = iter;
+ ++iter2;
+ ++iter2;
+ EXPECT_TRUE(iter + 2 == iter2);
+ EXPECT_TRUE(iter == iter2 - 2);
+ EXPECT_EQ("baz", iter[2]);
+ EXPECT_EQ("baz", *(iter + 2));
+ EXPECT_EQ(3, proto_array_.end() - proto_array_.begin());
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, Comparable) {
+ RepeatedPtrField<string>::const_iterator iter = proto_array_.begin();
+ RepeatedPtrField<string>::const_iterator iter2 = iter + 1;
+ EXPECT_TRUE(iter == iter);
+ EXPECT_TRUE(iter != iter2);
+ EXPECT_TRUE(iter < iter2);
+ EXPECT_TRUE(iter <= iter2);
+ EXPECT_TRUE(iter <= iter);
+ EXPECT_TRUE(iter2 > iter);
+ EXPECT_TRUE(iter2 >= iter);
+ EXPECT_TRUE(iter >= iter);
+}
+
+// Uninitialized iterator does not point to any of the RepeatedPtrField.
+TEST_F(RepeatedPtrFieldIteratorTest, UninitializedIterator) {
+ RepeatedPtrField<string>::iterator iter;
+ EXPECT_TRUE(iter != proto_array_.begin());
+ EXPECT_TRUE(iter != proto_array_.begin() + 1);
+ EXPECT_TRUE(iter != proto_array_.begin() + 2);
+ EXPECT_TRUE(iter != proto_array_.begin() + 3);
+ EXPECT_TRUE(iter != proto_array_.end());
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, STLAlgorithms_lower_bound) {
+ proto_array_.Clear();
+ proto_array_.Add()->assign("a");
+ proto_array_.Add()->assign("c");
+ proto_array_.Add()->assign("d");
+ proto_array_.Add()->assign("n");
+ proto_array_.Add()->assign("p");
+ proto_array_.Add()->assign("x");
+ proto_array_.Add()->assign("y");
+
+ string v = "f";
+ RepeatedPtrField<string>::const_iterator it =
+ std::lower_bound(proto_array_.begin(), proto_array_.end(), v);
+
+ EXPECT_EQ(*it, "n");
+ EXPECT_TRUE(it == proto_array_.begin() + 3);
+}
+
+TEST_F(RepeatedPtrFieldIteratorTest, Mutation) {
+ RepeatedPtrField<string>::iterator iter = proto_array_.begin();
+ *iter = "qux";
+ EXPECT_EQ("qux", proto_array_.Get(0));
+}
+
+// -------------------------------------------------------------------
+
+class RepeatedPtrFieldPtrsIteratorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ proto_array_.Add()->assign("foo");
+ proto_array_.Add()->assign("bar");
+ proto_array_.Add()->assign("baz");
+ const_proto_array_ = &proto_array_;
+ }
+
+ RepeatedPtrField<string> proto_array_;
+ const RepeatedPtrField<string>* const_proto_array_;
+};
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, ConvertiblePtr) {
+ RepeatedPtrField<string>::pointer_iterator iter =
+ proto_array_.pointer_begin();
+ static_cast<void>(iter);
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, ConvertibleConstPtr) {
+ RepeatedPtrField<string>::const_pointer_iterator iter =
+ const_proto_array_->pointer_begin();
+ static_cast<void>(iter);
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, MutablePtrIteration) {
+ RepeatedPtrField<string>::pointer_iterator iter =
+ proto_array_.pointer_begin();
+ EXPECT_EQ("foo", **iter);
+ ++iter;
+ EXPECT_EQ("bar", **(iter++));
+ EXPECT_EQ("baz", **iter);
+ ++iter;
+ EXPECT_TRUE(proto_array_.pointer_end() == iter);
+ EXPECT_EQ("baz", **(--proto_array_.pointer_end()));
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, MutableConstPtrIteration) {
+ RepeatedPtrField<string>::const_pointer_iterator iter =
+ const_proto_array_->pointer_begin();
+ EXPECT_EQ("foo", **iter);
+ ++iter;
+ EXPECT_EQ("bar", **(iter++));
+ EXPECT_EQ("baz", **iter);
+ ++iter;
+ EXPECT_TRUE(const_proto_array_->pointer_end() == iter);
+ EXPECT_EQ("baz", **(--const_proto_array_->pointer_end()));
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, RandomPtrAccess) {
+ RepeatedPtrField<string>::pointer_iterator iter =
+ proto_array_.pointer_begin();
+ RepeatedPtrField<string>::pointer_iterator iter2 = iter;
+ ++iter2;
+ ++iter2;
+ EXPECT_TRUE(iter + 2 == iter2);
+ EXPECT_TRUE(iter == iter2 - 2);
+ EXPECT_EQ("baz", *iter[2]);
+ EXPECT_EQ("baz", **(iter + 2));
+ EXPECT_EQ(3, proto_array_.end() - proto_array_.begin());
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, RandomConstPtrAccess) {
+ RepeatedPtrField<string>::const_pointer_iterator iter =
+ const_proto_array_->pointer_begin();
+ RepeatedPtrField<string>::const_pointer_iterator iter2 = iter;
+ ++iter2;
+ ++iter2;
+ EXPECT_TRUE(iter + 2 == iter2);
+ EXPECT_TRUE(iter == iter2 - 2);
+ EXPECT_EQ("baz", *iter[2]);
+ EXPECT_EQ("baz", **(iter + 2));
+ EXPECT_EQ(3, const_proto_array_->end() - const_proto_array_->begin());
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, ComparablePtr) {
+ RepeatedPtrField<string>::pointer_iterator iter =
+ proto_array_.pointer_begin();
+ RepeatedPtrField<string>::pointer_iterator iter2 = iter + 1;
+ EXPECT_TRUE(iter == iter);
+ EXPECT_TRUE(iter != iter2);
+ EXPECT_TRUE(iter < iter2);
+ EXPECT_TRUE(iter <= iter2);
+ EXPECT_TRUE(iter <= iter);
+ EXPECT_TRUE(iter2 > iter);
+ EXPECT_TRUE(iter2 >= iter);
+ EXPECT_TRUE(iter >= iter);
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, ComparableConstPtr) {
+ RepeatedPtrField<string>::const_pointer_iterator iter =
+ const_proto_array_->pointer_begin();
+ RepeatedPtrField<string>::const_pointer_iterator iter2 = iter + 1;
+ EXPECT_TRUE(iter == iter);
+ EXPECT_TRUE(iter != iter2);
+ EXPECT_TRUE(iter < iter2);
+ EXPECT_TRUE(iter <= iter2);
+ EXPECT_TRUE(iter <= iter);
+ EXPECT_TRUE(iter2 > iter);
+ EXPECT_TRUE(iter2 >= iter);
+ EXPECT_TRUE(iter >= iter);
+}
+
+// Uninitialized iterator does not point to any of the RepeatedPtrOverPtrs.
+// Dereferencing an uninitialized iterator crashes the process.
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, UninitializedPtrIterator) {
+ RepeatedPtrField<string>::pointer_iterator iter;
+ EXPECT_TRUE(iter != proto_array_.pointer_begin());
+ EXPECT_TRUE(iter != proto_array_.pointer_begin() + 1);
+ EXPECT_TRUE(iter != proto_array_.pointer_begin() + 2);
+ EXPECT_TRUE(iter != proto_array_.pointer_begin() + 3);
+ EXPECT_TRUE(iter != proto_array_.pointer_end());
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, UninitializedConstPtrIterator) {
+ RepeatedPtrField<string>::const_pointer_iterator iter;
+ EXPECT_TRUE(iter != const_proto_array_->pointer_begin());
+ EXPECT_TRUE(iter != const_proto_array_->pointer_begin() + 1);
+ EXPECT_TRUE(iter != const_proto_array_->pointer_begin() + 2);
+ EXPECT_TRUE(iter != const_proto_array_->pointer_begin() + 3);
+ EXPECT_TRUE(iter != const_proto_array_->pointer_end());
+}
+
+// This comparison functor is required by the tests for RepeatedPtrOverPtrs.
+// They operate on strings and need to compare strings as strings in
+// any stl algorithm, even though the iterator returns a pointer to a string
+// - i.e. *iter has type string*.
+struct StringLessThan {
+ bool operator()(const string* z, const string& y) {
+ return *z < y;
+ }
+ bool operator()(const string* z, const string* y) const { return *z < *y; }
+};
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, PtrSTLAlgorithms_lower_bound) {
+ proto_array_.Clear();
+ proto_array_.Add()->assign("a");
+ proto_array_.Add()->assign("c");
+ proto_array_.Add()->assign("d");
+ proto_array_.Add()->assign("n");
+ proto_array_.Add()->assign("p");
+ proto_array_.Add()->assign("x");
+ proto_array_.Add()->assign("y");
+
+ {
+ string v = "f";
+ RepeatedPtrField<string>::pointer_iterator it =
+ std::lower_bound(proto_array_.pointer_begin(),
+ proto_array_.pointer_end(), &v, StringLessThan());
+
+ GOOGLE_CHECK(*it != NULL);
+
+ EXPECT_EQ(**it, "n");
+ EXPECT_TRUE(it == proto_array_.pointer_begin() + 3);
+ }
+ {
+ string v = "f";
+ RepeatedPtrField<string>::const_pointer_iterator it = std::lower_bound(
+ const_proto_array_->pointer_begin(), const_proto_array_->pointer_end(),
+ &v, StringLessThan());
+
+ GOOGLE_CHECK(*it != NULL);
+
+ EXPECT_EQ(**it, "n");
+ EXPECT_TRUE(it == const_proto_array_->pointer_begin() + 3);
+ }
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, PtrMutation) {
+ RepeatedPtrField<string>::pointer_iterator iter =
+ proto_array_.pointer_begin();
+ **iter = "qux";
+ EXPECT_EQ("qux", proto_array_.Get(0));
+
+ EXPECT_EQ("bar", proto_array_.Get(1));
+ EXPECT_EQ("baz", proto_array_.Get(2));
+ ++iter;
+ delete *iter;
+ *iter = new string("a");
+ ++iter;
+ delete *iter;
+ *iter = new string("b");
+ EXPECT_EQ("a", proto_array_.Get(1));
+ EXPECT_EQ("b", proto_array_.Get(2));
+}
+
+TEST_F(RepeatedPtrFieldPtrsIteratorTest, Sort) {
+ proto_array_.Add()->assign("c");
+ proto_array_.Add()->assign("d");
+ proto_array_.Add()->assign("n");
+ proto_array_.Add()->assign("p");
+ proto_array_.Add()->assign("a");
+ proto_array_.Add()->assign("y");
+ proto_array_.Add()->assign("x");
+ EXPECT_EQ("foo", proto_array_.Get(0));
+ EXPECT_EQ("n", proto_array_.Get(5));
+ EXPECT_EQ("x", proto_array_.Get(9));
+ std::sort(proto_array_.pointer_begin(), proto_array_.pointer_end(),
+ StringLessThan());
+ EXPECT_EQ("a", proto_array_.Get(0));
+ EXPECT_EQ("baz", proto_array_.Get(2));
+ EXPECT_EQ("y", proto_array_.Get(9));
+}
+
+
+// -----------------------------------------------------------------------------
+// Unit-tests for the insert iterators
+// google::protobuf::RepeatedFieldBackInserter,
+// google::protobuf::AllocatedRepeatedPtrFieldBackInserter
+// Ported from util/gtl/proto-array-iterators_unittest.
+
+class RepeatedFieldInsertionIteratorsTest : public testing::Test {
+ protected:
+ std::list<double> halves;
+ std::list<int> fibonacci;
+ std::vector<string> words;
+ typedef TestAllTypes::NestedMessage Nested;
+ Nested nesteds[2];
+ std::vector<Nested*> nested_ptrs;
+ TestAllTypes protobuffer;
+
+ virtual void SetUp() {
+ fibonacci.push_back(1);
+ fibonacci.push_back(1);
+ fibonacci.push_back(2);
+ fibonacci.push_back(3);
+ fibonacci.push_back(5);
+ fibonacci.push_back(8);
+ std::copy(fibonacci.begin(), fibonacci.end(),
+ RepeatedFieldBackInserter(protobuffer.mutable_repeated_int32()));
+
+ halves.push_back(1.0);
+ halves.push_back(0.5);
+ halves.push_back(0.25);
+ halves.push_back(0.125);
+ halves.push_back(0.0625);
+ std::copy(halves.begin(), halves.end(),
+ RepeatedFieldBackInserter(protobuffer.mutable_repeated_double()));
+
+ words.push_back("Able");
+ words.push_back("was");
+ words.push_back("I");
+ words.push_back("ere");
+ words.push_back("I");
+ words.push_back("saw");
+ words.push_back("Elba");
+ std::copy(words.begin(), words.end(),
+ RepeatedFieldBackInserter(protobuffer.mutable_repeated_string()));
+
+ nesteds[0].set_bb(17);
+ nesteds[1].set_bb(4711);
+ std::copy(&nesteds[0], &nesteds[2],
+ RepeatedFieldBackInserter(
+ protobuffer.mutable_repeated_nested_message()));
+
+ nested_ptrs.push_back(new Nested);
+ nested_ptrs.back()->set_bb(170);
+ nested_ptrs.push_back(new Nested);
+ nested_ptrs.back()->set_bb(47110);
+ std::copy(nested_ptrs.begin(), nested_ptrs.end(),
+ RepeatedFieldBackInserter(
+ protobuffer.mutable_repeated_nested_message()));
+ }
+
+ virtual void TearDown() {
+ STLDeleteContainerPointers(nested_ptrs.begin(), nested_ptrs.end());
+ }
+};
+
+TEST_F(RepeatedFieldInsertionIteratorsTest, Fibonacci) {
+ EXPECT_TRUE(std::equal(fibonacci.begin(),
+ fibonacci.end(),
+ protobuffer.repeated_int32().begin()));
+ EXPECT_TRUE(std::equal(protobuffer.repeated_int32().begin(),
+ protobuffer.repeated_int32().end(),
+ fibonacci.begin()));
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest, Halves) {
+ EXPECT_TRUE(std::equal(halves.begin(),
+ halves.end(),
+ protobuffer.repeated_double().begin()));
+ EXPECT_TRUE(std::equal(protobuffer.repeated_double().begin(),
+ protobuffer.repeated_double().end(),
+ halves.begin()));
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest, Words) {
+ ASSERT_EQ(words.size(), protobuffer.repeated_string_size());
+ for (int i = 0; i < words.size(); ++i)
+ EXPECT_EQ(words.at(i), protobuffer.repeated_string(i));
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest, Words2) {
+ words.clear();
+ words.push_back("sing");
+ words.push_back("a");
+ words.push_back("song");
+ words.push_back("of");
+ words.push_back("six");
+ words.push_back("pence");
+ protobuffer.mutable_repeated_string()->Clear();
+ std::copy(words.begin(), words.end(), RepeatedPtrFieldBackInserter(
+ protobuffer.mutable_repeated_string()));
+ ASSERT_EQ(words.size(), protobuffer.repeated_string_size());
+ for (int i = 0; i < words.size(); ++i)
+ EXPECT_EQ(words.at(i), protobuffer.repeated_string(i));
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest, Nesteds) {
+ ASSERT_EQ(protobuffer.repeated_nested_message_size(), 4);
+ EXPECT_EQ(protobuffer.repeated_nested_message(0).bb(), 17);
+ EXPECT_EQ(protobuffer.repeated_nested_message(1).bb(), 4711);
+ EXPECT_EQ(protobuffer.repeated_nested_message(2).bb(), 170);
+ EXPECT_EQ(protobuffer.repeated_nested_message(3).bb(), 47110);
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest,
+ AllocatedRepeatedPtrFieldWithStringIntData) {
+ vector<Nested*> data;
+ TestAllTypes goldenproto;
+ for (int i = 0; i < 10; ++i) {
+ Nested* new_data = new Nested;
+ new_data->set_bb(i);
+ data.push_back(new_data);
+
+ new_data = goldenproto.add_repeated_nested_message();
+ new_data->set_bb(i);
+ }
+ TestAllTypes testproto;
+ std::copy(data.begin(), data.end(),
+ AllocatedRepeatedPtrFieldBackInserter(
+ testproto.mutable_repeated_nested_message()));
+ EXPECT_EQ(testproto.DebugString(), goldenproto.DebugString());
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest,
+ AllocatedRepeatedPtrFieldWithString) {
+ vector<string*> data;
+ TestAllTypes goldenproto;
+ for (int i = 0; i < 10; ++i) {
+ string* new_data = new string;
+ *new_data = "name-" + SimpleItoa(i);
+ data.push_back(new_data);
+
+ new_data = goldenproto.add_repeated_string();
+ *new_data = "name-" + SimpleItoa(i);
+ }
+ TestAllTypes testproto;
+ std::copy(data.begin(), data.end(), AllocatedRepeatedPtrFieldBackInserter(
+ testproto.mutable_repeated_string()));
+ EXPECT_EQ(testproto.DebugString(), goldenproto.DebugString());
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest,
+ UnsafeArenaAllocatedRepeatedPtrFieldWithStringIntData) {
+ vector<Nested*> data;
+ TestAllTypes goldenproto;
+ for (int i = 0; i < 10; ++i) {
+ Nested* new_data = new Nested;
+ new_data->set_bb(i);
+ data.push_back(new_data);
+
+ new_data = goldenproto.add_repeated_nested_message();
+ new_data->set_bb(i);
+ }
+ TestAllTypes testproto;
+ std::copy(data.begin(), data.end(),
+ UnsafeArenaAllocatedRepeatedPtrFieldBackInserter(
+ testproto.mutable_repeated_nested_message()));
+ EXPECT_EQ(testproto.DebugString(), goldenproto.DebugString());
+}
+
+TEST_F(RepeatedFieldInsertionIteratorsTest,
+ UnsafeArenaAllocatedRepeatedPtrFieldWithString) {
+ vector<string*> data;
+ TestAllTypes goldenproto;
+ for (int i = 0; i < 10; ++i) {
+ string* new_data = new string;
+ *new_data = "name-" + SimpleItoa(i);
+ data.push_back(new_data);
+
+ new_data = goldenproto.add_repeated_string();
+ *new_data = "name-" + SimpleItoa(i);
+ }
+ TestAllTypes testproto;
+ std::copy(data.begin(), data.end(),
+ UnsafeArenaAllocatedRepeatedPtrFieldBackInserter(
+ testproto.mutable_repeated_string()));
+ EXPECT_EQ(testproto.DebugString(), goldenproto.DebugString());
+}
+
+} // namespace
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/service.cc b/third_party/protobuf/3.0.0/src/google/protobuf/service.cc
new file mode 100644
index 0000000000..ffa919daa7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/service.cc
@@ -0,0 +1,46 @@
+// 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.
+
+#include <google/protobuf/service.h>
+
+namespace google {
+namespace protobuf {
+
+Service::~Service() {}
+RpcChannel::~RpcChannel() {}
+RpcController::~RpcController() {}
+
+} // namespace protobuf
+
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/service.h b/third_party/protobuf/3.0.0/src/google/protobuf/service.h
new file mode 100644
index 0000000000..ad6f968548
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/service.h
@@ -0,0 +1,292 @@
+// 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.
+//
+// DEPRECATED: This module declares the abstract interfaces underlying proto2
+// RPC services. These are intented to be independent of any particular RPC
+// implementation, so that proto2 services can be used on top of a variety
+// of implementations. Starting with version 2.3.0, RPC implementations should
+// not try to build on these, but should instead provide code generator plugins
+// which generate code specific to the particular RPC implementation. This way
+// the generated code can be more appropriate for the implementation in use
+// and can avoid unnecessary layers of indirection.
+//
+//
+// When you use the protocol compiler to compile a service definition, it
+// generates two classes: An abstract interface for the service (with
+// methods matching the service definition) and a "stub" implementation.
+// A stub is just a type-safe wrapper around an RpcChannel which emulates a
+// local implementation of the service.
+//
+// For example, the service definition:
+// service MyService {
+// rpc Foo(MyRequest) returns(MyResponse);
+// }
+// will generate abstract interface "MyService" and class "MyService::Stub".
+// You could implement a MyService as follows:
+// class MyServiceImpl : public MyService {
+// public:
+// MyServiceImpl() {}
+// ~MyServiceImpl() {}
+//
+// // implements MyService ---------------------------------------
+//
+// void Foo(google::protobuf::RpcController* controller,
+// const MyRequest* request,
+// MyResponse* response,
+// Closure* done) {
+// // ... read request and fill in response ...
+// done->Run();
+// }
+// };
+// You would then register an instance of MyServiceImpl with your RPC server
+// implementation. (How to do that depends on the implementation.)
+//
+// To call a remote MyServiceImpl, first you need an RpcChannel connected to it.
+// How to construct a channel depends, again, on your RPC implementation.
+// Here we use a hypothetical "MyRpcChannel" as an example:
+// MyRpcChannel channel("rpc:hostname:1234/myservice");
+// MyRpcController controller;
+// MyServiceImpl::Stub stub(&channel);
+// FooRequest request;
+// FooResponse response;
+//
+// // ... fill in request ...
+//
+// stub.Foo(&controller, request, &response, NewCallback(HandleResponse));
+//
+// On Thread-Safety:
+//
+// Different RPC implementations may make different guarantees about what
+// threads they may run callbacks on, and what threads the application is
+// allowed to use to call the RPC system. Portable software should be ready
+// for callbacks to be called on any thread, but should not try to call the
+// RPC system from any thread except for the ones on which it received the
+// callbacks. Realistically, though, simple software will probably want to
+// use a single-threaded RPC system while high-end software will want to
+// use multiple threads. RPC implementations should provide multiple
+// choices.
+
+#ifndef GOOGLE_PROTOBUF_SERVICE_H__
+#define GOOGLE_PROTOBUF_SERVICE_H__
+
+#include <string>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/callback.h>
+
+namespace google {
+namespace protobuf {
+
+// Defined in this file.
+class Service;
+class RpcController;
+class RpcChannel;
+
+// Defined in other files.
+class Descriptor; // descriptor.h
+class ServiceDescriptor; // descriptor.h
+class MethodDescriptor; // descriptor.h
+class Message; // message.h
+
+// Abstract base interface for protocol-buffer-based RPC services. Services
+// themselves are abstract interfaces (implemented either by servers or as
+// stubs), but they subclass this base interface. The methods of this
+// interface can be used to call the methods of the Service without knowing
+// its exact type at compile time (analogous to Reflection).
+class LIBPROTOBUF_EXPORT Service {
+ public:
+ inline Service() {}
+ virtual ~Service();
+
+ // When constructing a stub, you may pass STUB_OWNS_CHANNEL as the second
+ // parameter to the constructor to tell it to delete its RpcChannel when
+ // destroyed.
+ enum ChannelOwnership {
+ STUB_OWNS_CHANNEL,
+ STUB_DOESNT_OWN_CHANNEL
+ };
+
+ // Get the ServiceDescriptor describing this service and its methods.
+ virtual const ServiceDescriptor* GetDescriptor() = 0;
+
+ // Call a method of the service specified by MethodDescriptor. This is
+ // normally implemented as a simple switch() that calls the standard
+ // definitions of the service's methods.
+ //
+ // Preconditions:
+ // * method->service() == GetDescriptor()
+ // * request and response are of the exact same classes as the objects
+ // returned by GetRequestPrototype(method) and
+ // GetResponsePrototype(method).
+ // * After the call has started, the request must not be modified and the
+ // response must not be accessed at all until "done" is called.
+ // * "controller" is of the correct type for the RPC implementation being
+ // used by this Service. For stubs, the "correct type" depends on the
+ // RpcChannel which the stub is using. Server-side Service
+ // implementations are expected to accept whatever type of RpcController
+ // the server-side RPC implementation uses.
+ //
+ // Postconditions:
+ // * "done" will be called when the method is complete. This may be
+ // before CallMethod() returns or it may be at some point in the future.
+ // * If the RPC succeeded, "response" contains the response returned by
+ // the server.
+ // * If the RPC failed, "response"'s contents are undefined. The
+ // RpcController can be queried to determine if an error occurred and
+ // possibly to get more information about the error.
+ virtual void CallMethod(const MethodDescriptor* method,
+ RpcController* controller,
+ const Message* request,
+ Message* response,
+ Closure* done) = 0;
+
+ // CallMethod() requires that the request and response passed in are of a
+ // particular subclass of Message. GetRequestPrototype() and
+ // GetResponsePrototype() get the default instances of these required types.
+ // You can then call Message::New() on these instances to construct mutable
+ // objects which you can then pass to CallMethod().
+ //
+ // Example:
+ // const MethodDescriptor* method =
+ // service->GetDescriptor()->FindMethodByName("Foo");
+ // Message* request = stub->GetRequestPrototype (method)->New();
+ // Message* response = stub->GetResponsePrototype(method)->New();
+ // request->ParseFromString(input);
+ // service->CallMethod(method, *request, response, callback);
+ virtual const Message& GetRequestPrototype(
+ const MethodDescriptor* method) const = 0;
+ virtual const Message& GetResponsePrototype(
+ const MethodDescriptor* method) const = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Service);
+};
+
+// An RpcController mediates a single method call. The primary purpose of
+// the controller is to provide a way to manipulate settings specific to the
+// RPC implementation and to find out about RPC-level errors.
+//
+// The methods provided by the RpcController interface are intended to be a
+// "least common denominator" set of features which we expect all
+// implementations to support. Specific implementations may provide more
+// advanced features (e.g. deadline propagation).
+class LIBPROTOBUF_EXPORT RpcController {
+ public:
+ inline RpcController() {}
+ virtual ~RpcController();
+
+ // Client-side methods ---------------------------------------------
+ // These calls may be made from the client side only. Their results
+ // are undefined on the server side (may crash).
+
+ // Resets the RpcController to its initial state so that it may be reused in
+ // a new call. Must not be called while an RPC is in progress.
+ virtual void Reset() = 0;
+
+ // After a call has finished, returns true if the call failed. The possible
+ // reasons for failure depend on the RPC implementation. Failed() must not
+ // be called before a call has finished. If Failed() returns true, the
+ // contents of the response message are undefined.
+ virtual bool Failed() const = 0;
+
+ // If Failed() is true, returns a human-readable description of the error.
+ virtual string ErrorText() const = 0;
+
+ // Advises the RPC system that the caller desires that the RPC call be
+ // canceled. The RPC system may cancel it immediately, may wait awhile and
+ // then cancel it, or may not even cancel the call at all. If the call is
+ // canceled, the "done" callback will still be called and the RpcController
+ // will indicate that the call failed at that time.
+ virtual void StartCancel() = 0;
+
+ // Server-side methods ---------------------------------------------
+ // These calls may be made from the server side only. Their results
+ // are undefined on the client side (may crash).
+
+ // Causes Failed() to return true on the client side. "reason" will be
+ // incorporated into the message returned by ErrorText(). If you find
+ // you need to return machine-readable information about failures, you
+ // should incorporate it into your response protocol buffer and should
+ // NOT call SetFailed().
+ virtual void SetFailed(const string& reason) = 0;
+
+ // If true, indicates that the client canceled the RPC, so the server may
+ // as well give up on replying to it. The server should still call the
+ // final "done" callback.
+ virtual bool IsCanceled() const = 0;
+
+ // Asks that the given callback be called when the RPC is canceled. The
+ // callback will always be called exactly once. If the RPC completes without
+ // being canceled, the callback will be called after completion. If the RPC
+ // has already been canceled when NotifyOnCancel() is called, the callback
+ // will be called immediately.
+ //
+ // NotifyOnCancel() must be called no more than once per request.
+ virtual void NotifyOnCancel(Closure* callback) = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RpcController);
+};
+
+// Abstract interface for an RPC channel. An RpcChannel represents a
+// communication line to a Service which can be used to call that Service's
+// methods. The Service may be running on another machine. Normally, you
+// should not call an RpcChannel directly, but instead construct a stub Service
+// wrapping it. Example:
+// RpcChannel* channel = new MyRpcChannel("remotehost.example.com:1234");
+// MyService* service = new MyService::Stub(channel);
+// service->MyMethod(request, &response, callback);
+class LIBPROTOBUF_EXPORT RpcChannel {
+ public:
+ inline RpcChannel() {}
+ virtual ~RpcChannel();
+
+ // Call the given method of the remote service. The signature of this
+ // procedure looks the same as Service::CallMethod(), but the requirements
+ // are less strict in one important way: the request and response objects
+ // need not be of any specific class as long as their descriptors are
+ // method->input_type() and method->output_type().
+ virtual void CallMethod(const MethodDescriptor* method,
+ RpcController* controller,
+ const Message* request,
+ Message* response,
+ Closure* done) = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(RpcChannel);
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_SERVICE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.cc
new file mode 100644
index 0000000000..5cc77bf34a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.cc
@@ -0,0 +1,394 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/source_context.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/source_context.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* SourceContext_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ SourceContext_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fsource_5fcontext_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fsource_5fcontext_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/source_context.proto");
+ GOOGLE_CHECK(file != NULL);
+ SourceContext_descriptor_ = file->message_type(0);
+ static const int SourceContext_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceContext, file_name_),
+ };
+ SourceContext_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ SourceContext_descriptor_,
+ SourceContext::default_instance_,
+ SourceContext_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(SourceContext),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceContext, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(SourceContext, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fsource_5fcontext_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ SourceContext_descriptor_, &SourceContext::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fsource_5fcontext_2eproto() {
+ delete SourceContext::default_instance_;
+ delete SourceContext_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n$google/protobuf/source_context.proto\022\017"
+ "google.protobuf\"\"\n\rSourceContext\022\021\n\tfile"
+ "_name\030\001 \001(\tBU\n\023com.google.protobufB\022Sour"
+ "ceContextProtoP\001\240\001\001\242\002\003GPB\252\002\036Google.Proto"
+ "buf.WellKnownTypesb\006proto3", 186);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/source_context.proto", &protobuf_RegisterTypes);
+ SourceContext::default_instance_ = new SourceContext();
+ SourceContext::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fsource_5fcontext_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fsource_5fcontext_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fsource_5fcontext_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fsource_5fcontext_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int SourceContext::kFileNameFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+SourceContext::SourceContext()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.SourceContext)
+}
+
+void SourceContext::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+SourceContext::SourceContext(const SourceContext& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.SourceContext)
+}
+
+void SourceContext::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ file_name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+SourceContext::~SourceContext() {
+ // @@protoc_insertion_point(destructor:google.protobuf.SourceContext)
+ SharedDtor();
+}
+
+void SourceContext::SharedDtor() {
+ file_name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void SourceContext::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* SourceContext::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return SourceContext_descriptor_;
+}
+
+const SourceContext& SourceContext::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+ return *default_instance_;
+}
+
+SourceContext* SourceContext::default_instance_ = NULL;
+
+SourceContext* SourceContext::New(::google::protobuf::Arena* arena) const {
+ SourceContext* n = new SourceContext;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void SourceContext::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.SourceContext)
+ file_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+bool SourceContext::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.SourceContext)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string file_name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_file_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->file_name().data(), this->file_name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.SourceContext.file_name"));
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.SourceContext)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.SourceContext)
+ return false;
+#undef DO_
+}
+
+void SourceContext::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.SourceContext)
+ // optional string file_name = 1;
+ if (this->file_name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->file_name().data(), this->file_name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.SourceContext.file_name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->file_name(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.SourceContext)
+}
+
+::google::protobuf::uint8* SourceContext::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.SourceContext)
+ // optional string file_name = 1;
+ if (this->file_name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->file_name().data(), this->file_name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.SourceContext.file_name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->file_name(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.SourceContext)
+ return target;
+}
+
+int SourceContext::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.SourceContext)
+ int total_size = 0;
+
+ // optional string file_name = 1;
+ if (this->file_name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->file_name());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void SourceContext::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.SourceContext)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const SourceContext* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const SourceContext>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.SourceContext)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.SourceContext)
+ MergeFrom(*source);
+ }
+}
+
+void SourceContext::MergeFrom(const SourceContext& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.SourceContext)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.file_name().size() > 0) {
+
+ file_name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.file_name_);
+ }
+}
+
+void SourceContext::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.SourceContext)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void SourceContext::CopyFrom(const SourceContext& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.SourceContext)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool SourceContext::IsInitialized() const {
+
+ return true;
+}
+
+void SourceContext::Swap(SourceContext* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void SourceContext::InternalSwap(SourceContext* other) {
+ file_name_.Swap(&other->file_name_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata SourceContext::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = SourceContext_descriptor_;
+ metadata.reflection = SourceContext_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// SourceContext
+
+// optional string file_name = 1;
+void SourceContext::clear_file_name() {
+ file_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& SourceContext::file_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceContext.file_name)
+ return file_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void SourceContext::set_file_name(const ::std::string& value) {
+
+ file_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceContext.file_name)
+}
+ void SourceContext::set_file_name(const char* value) {
+
+ file_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceContext.file_name)
+}
+ void SourceContext::set_file_name(const char* value, size_t size) {
+
+ file_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceContext.file_name)
+}
+ ::std::string* SourceContext::mutable_file_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceContext.file_name)
+ return file_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* SourceContext::release_file_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.SourceContext.file_name)
+
+ return file_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void SourceContext::set_allocated_file_name(::std::string* file_name) {
+ if (file_name != NULL) {
+
+ } else {
+
+ }
+ file_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), file_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.SourceContext.file_name)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.h
new file mode 100644
index 0000000000..341a4534ab
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/source_context.pb.h
@@ -0,0 +1,190 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/source_context.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fsource_5fcontext_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fsource_5fcontext_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fsource_5fcontext_2eproto();
+
+class SourceContext;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT SourceContext : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.SourceContext) */ {
+ public:
+ SourceContext();
+ virtual ~SourceContext();
+
+ SourceContext(const SourceContext& from);
+
+ inline SourceContext& operator=(const SourceContext& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const SourceContext& default_instance();
+
+ void Swap(SourceContext* other);
+
+ // implements Message ----------------------------------------------
+
+ inline SourceContext* New() const { return New(NULL); }
+
+ SourceContext* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const SourceContext& from);
+ void MergeFrom(const SourceContext& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(SourceContext* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string file_name = 1;
+ void clear_file_name();
+ static const int kFileNameFieldNumber = 1;
+ const ::std::string& file_name() const;
+ void set_file_name(const ::std::string& value);
+ void set_file_name(const char* value);
+ void set_file_name(const char* value, size_t size);
+ ::std::string* mutable_file_name();
+ ::std::string* release_file_name();
+ void set_allocated_file_name(::std::string* file_name);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.SourceContext)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr file_name_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fsource_5fcontext_2eproto();
+
+ void InitAsDefaultInstance();
+ static SourceContext* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// SourceContext
+
+// optional string file_name = 1;
+inline void SourceContext::clear_file_name() {
+ file_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& SourceContext::file_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.SourceContext.file_name)
+ return file_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void SourceContext::set_file_name(const ::std::string& value) {
+
+ file_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.SourceContext.file_name)
+}
+inline void SourceContext::set_file_name(const char* value) {
+
+ file_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.SourceContext.file_name)
+}
+inline void SourceContext::set_file_name(const char* value, size_t size) {
+
+ file_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.SourceContext.file_name)
+}
+inline ::std::string* SourceContext::mutable_file_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.SourceContext.file_name)
+ return file_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* SourceContext::release_file_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.SourceContext.file_name)
+
+ return file_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void SourceContext::set_allocated_file_name(::std::string* file_name) {
+ if (file_name != NULL) {
+
+ } else {
+
+ }
+ file_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), file_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.SourceContext.file_name)
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fsource_5fcontext_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/source_context.proto b/third_party/protobuf/3.0.0/src/google/protobuf/source_context.proto
new file mode 100644
index 0000000000..a2c08e2b57
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/source_context.proto
@@ -0,0 +1,48 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "SourceContextProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+// `SourceContext` represents information about the source of a
+// protobuf element, like the file in which it is defined.
+message SourceContext {
+ // The path-qualified name of the .proto file that contained the associated
+ // protobuf element. For example: `"google/protobuf/source_context.proto"`.
+ string file_name = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.cc
new file mode 100644
index 0000000000..a551384cfd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.cc
@@ -0,0 +1,1579 @@
+// 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>
+// @@protoc_insertion_point(includes)
+
+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 {
+ 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() GOOGLE_ATTRIBUTE_COLD;
+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&) GOOGLE_ATTRIBUTE_COLD;
+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() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ 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\000B\201\001\n\023com.google.pro"
+ "tobufB\013StructProtoP\001Z1github.com/golang/"
+ "protobuf/ptypes/struct;structpb\240\001\001\242\002\003GPB"
+ "\252\002\036Google.Protobuf.WellKnownTypesb\006proto"
+ "3", 641);
+ ::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);
+}
+
+// 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() {
+ protobuf_AssignDescriptorsOnce();
+ return NullValue_descriptor_;
+}
+bool NullValue_IsValid(int value) {
+ switch(value) {
+ case 0:
+ return true;
+ default:
+ return false;
+ }
+}
+
+
+// ===================================================================
+
+#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) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Struct)
+}
+
+void Struct::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Struct::Struct(const Struct& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Struct)
+}
+
+void Struct::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ fields_.SetAssignDescriptorCallback(
+ protobuf_AssignDescriptorsOnce);
+ fields_.SetEntryDescriptor(
+ &::google::protobuf::Struct_FieldsEntry_descriptor_);
+}
+
+Struct::~Struct() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Struct)
+ SharedDtor();
+}
+
+void Struct::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void Struct::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Struct::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Struct_descriptor_;
+}
+
+const Struct& Struct::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
+ return *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)
+ fields_.Clear();
+}
+
+bool Struct::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#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);
+ 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:
+ Struct_FieldsEntry::Parser< ::google::protobuf::internal::MapField<
+ ::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, &parser));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ parser.key().data(), 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Struct)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Struct)
+ return false;
+#undef DO_
+}
+
+void Struct::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Struct)
+ // map<string, .google.protobuf.Value> fields = 1;
+ 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(), p->first.length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Struct.FieldsEntry.key");
+ }
+ };
+
+ if (output->IsSerializationDeterminstic() &&
+ this->fields().size() > 1) {
+ ::google::protobuf::scoped_array<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[n] = SortItem(&*it);
+ }
+ ::std::sort(&items[0], &items[n], Less());
+ ::google::protobuf::scoped_ptr<Struct_FieldsEntry> entry;
+ for (size_type i = 0; i < n; i++) {
+ entry.reset(fields_.NewEntryWrapper(
+ items[i]->first, items[i]->second));
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 1, *entry, output);
+ Utf8Check::Check(items[i]);
+ }
+ } else {
+ ::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);
+ Utf8Check::Check(&*it);
+ }
+ }
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Struct)
+}
+
+::google::protobuf::uint8* Struct::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Struct)
+ // map<string, .google.protobuf.Value> fields = 1;
+ 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(), p->first.length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Struct.FieldsEntry.key");
+ }
+ };
+
+ if (deterministic &&
+ this->fields().size() > 1) {
+ ::google::protobuf::scoped_array<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[n] = SortItem(&*it);
+ }
+ ::std::sort(&items[0], &items[n], Less());
+ ::google::protobuf::scoped_ptr<Struct_FieldsEntry> entry;
+ for (size_type i = 0; i < n; i++) {
+ entry.reset(fields_.NewEntryWrapper(
+ items[i]->first, items[i]->second));
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 1, *entry, deterministic, target);
+;
+ Utf8Check::Check(items[i]);
+ }
+ } else {
+ ::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::
+ InternalWriteMessageNoVirtualToArray(
+ 1, *entry, deterministic, target);
+;
+ Utf8Check::Check(&*it);
+ }
+ }
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Struct)
+ return target;
+}
+
+int Struct::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Struct)
+ int total_size = 0;
+
+ // map<string, .google.protobuf.Value> fields = 1;
+ total_size += 1 * this->fields_size();
+ {
+ ::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));
+ total_size += ::google::protobuf::internal::WireFormatLite::
+ MessageSizeNoVirtual(*entry);
+ }
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Struct::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Struct)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ 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) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Struct)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ 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;
+ InternalSwap(other);
+}
+void Struct::InternalSwap(Struct* other) {
+ 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;
+}
+
+#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
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Value::kNullValueFieldNumber;
+const int Value::kNumberValueFieldNumber;
+const int Value::kStringValueFieldNumber;
+const int Value::kBoolValueFieldNumber;
+const int Value::kStructValueFieldNumber;
+const int Value::kListValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Value::Value()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ 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(const Value& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@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();
+}
+
+Value::~Value() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Value)
+ SharedDtor();
+}
+
+void Value::SharedDtor() {
+ if (has_kind()) {
+ clear_kind();
+ }
+ if (this != default_instance_) {
+ }
+}
+
+void Value::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Value::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Value_descriptor_;
+}
+
+const Value& Value::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
+ return *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() {
+// @@protoc_insertion_point(one_of_clear_start:google.protobuf.Value)
+ switch(kind_case()) {
+ case kNullValue: {
+ // No need to clear
+ break;
+ }
+ case kNumberValue: {
+ // No need to clear
+ break;
+ }
+ case kStringValue: {
+ kind_.string_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ break;
+ }
+ case kBoolValue: {
+ // No need to clear
+ break;
+ }
+ case kStructValue: {
+ delete kind_.struct_value_;
+ break;
+ }
+ case kListValue: {
+ delete kind_.list_value_;
+ break;
+ }
+ case KIND_NOT_SET: {
+ break;
+ }
+ }
+ _oneof_case_[0] = KIND_NOT_SET;
+}
+
+
+void Value::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Value)
+ clear_kind();
+}
+
+bool Value::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#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);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional .google.protobuf.NullValue null_value = 1;
+ case 1: {
+ if (tag == 8) {
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ set_null_value(static_cast< ::google::protobuf::NullValue >(value));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(17)) goto parse_number_value;
+ break;
+ }
+
+ // optional double number_value = 2;
+ case 2: {
+ if (tag == 17) {
+ parse_number_value:
+ clear_kind();
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ double, ::google::protobuf::internal::WireFormatLite::TYPE_DOUBLE>(
+ input, &kind_.number_value_)));
+ set_has_number_value();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_string_value;
+ break;
+ }
+
+ // optional string string_value = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_string_value:
+ 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(),
+ ::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;
+ case 4: {
+ if (tag == 32) {
+ parse_bool_value:
+ clear_kind();
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &kind_.bool_value_)));
+ set_has_bool_value();
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(42)) goto parse_struct_value;
+ break;
+ }
+
+ // optional .google.protobuf.Struct struct_value = 5;
+ case 5: {
+ if (tag == 42) {
+ parse_struct_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_struct_value()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_list_value;
+ break;
+ }
+
+ // optional .google.protobuf.ListValue list_value = 6;
+ case 6: {
+ if (tag == 50) {
+ parse_list_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Value)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Value)
+ return false;
+#undef DO_
+}
+
+void Value::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Value)
+ // optional .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;
+ if (has_number_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteDouble(2, this->number_value(), output);
+ }
+
+ // optional string string_value = 3;
+ if (has_string_value()) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->string_value().data(), 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;
+ if (has_bool_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(4, this->bool_value(), output);
+ }
+
+ // optional .google.protobuf.Struct struct_value = 5;
+ if (has_struct_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 5, *kind_.struct_value_, output);
+ }
+
+ // optional .google.protobuf.ListValue list_value = 6;
+ if (has_list_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 6, *kind_.list_value_, output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Value)
+}
+
+::google::protobuf::uint8* Value::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Value)
+ // optional .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;
+ if (has_number_value()) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteDoubleToArray(2, this->number_value(), target);
+ }
+
+ // optional string string_value = 3;
+ if (has_string_value()) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->string_value().data(), this->string_value().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Value.string_value");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 3, this->string_value(), target);
+ }
+
+ // optional 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;
+ if (has_struct_value()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 5, *kind_.struct_value_, false, target);
+ }
+
+ // optional .google.protobuf.ListValue list_value = 6;
+ if (has_list_value()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 6, *kind_.list_value_, false, target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Value)
+ return target;
+}
+
+int Value::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Value)
+ int total_size = 0;
+
+ switch (kind_case()) {
+ // optional .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;
+ case kNumberValue: {
+ total_size += 1 + 8;
+ break;
+ }
+ // optional string string_value = 3;
+ case kStringValue: {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->string_value());
+ break;
+ }
+ // optional bool bool_value = 4;
+ case kBoolValue: {
+ total_size += 1 + 1;
+ break;
+ }
+ // optional .google.protobuf.Struct struct_value = 5;
+ case kStructValue: {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *kind_.struct_value_);
+ break;
+ }
+ // optional .google.protobuf.ListValue list_value = 6;
+ case kListValue: {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *kind_.list_value_);
+ break;
+ }
+ case KIND_NOT_SET: {
+ break;
+ }
+ }
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Value::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ 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) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ 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;
+ }
+ }
+}
+
+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;
+ InternalSwap(other);
+}
+void Value::InternalSwap(Value* other) {
+ std::swap(kind_, other->kind_);
+ std::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;
+}
+
+#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() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Value.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() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Value.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() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Value.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
+
+// ===================================================================
+
+#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) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.ListValue)
+}
+
+void ListValue::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+ListValue::ListValue(const ListValue& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.ListValue)
+}
+
+void ListValue::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+}
+
+ListValue::~ListValue() {
+ // @@protoc_insertion_point(destructor:google.protobuf.ListValue)
+ SharedDtor();
+}
+
+void ListValue::SharedDtor() {
+ if (this != default_instance_) {
+ }
+}
+
+void ListValue::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* ListValue::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return ListValue_descriptor_;
+}
+
+const ListValue& ListValue::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
+ return *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)
+ values_.Clear();
+}
+
+bool ListValue::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#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);
+ 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(
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.ListValue)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.ListValue)
+ return false;
+#undef DO_
+}
+
+void ListValue::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.ListValue)
+ // repeated .google.protobuf.Value values = 1;
+ for (unsigned int i = 0, n = this->values_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 1, this->values(i), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.ListValue)
+}
+
+::google::protobuf::uint8* ListValue::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.ListValue)
+ // repeated .google.protobuf.Value values = 1;
+ for (unsigned int i = 0, n = this->values_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 1, this->values(i), false, target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.ListValue)
+ return target;
+}
+
+int ListValue::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.ListValue)
+ int total_size = 0;
+
+ // repeated .google.protobuf.Value values = 1;
+ total_size += 1 * this->values_size();
+ for (int i = 0; i < this->values_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->values(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void ListValue::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.ListValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ 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) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.ListValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ 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;
+ InternalSwap(other);
+}
+void ListValue::InternalSwap(ListValue* other) {
+ values_.UnsafeArenaSwap(&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;
+}
+
+#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
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.h
new file mode 100644
index 0000000000..b085b84963
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/struct.pb.h
@@ -0,0 +1,781 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/struct.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fstruct_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fstruct_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/map.h>
+#include <google/protobuf/map_field_inl.h>
+#include <google/protobuf/generated_enum_reflection.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fstruct_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fstruct_2eproto();
+
+class ListValue;
+class Struct;
+class Value;
+
+enum NullValue {
+ NULL_VALUE = 0,
+ NullValue_INT_MIN_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32min,
+ NullValue_INT_MAX_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32max
+};
+LIBPROTOBUF_EXPORT bool NullValue_IsValid(int value);
+const NullValue NullValue_MIN = NULL_VALUE;
+const NullValue NullValue_MAX = NULL_VALUE;
+const int NullValue_ARRAYSIZE = NullValue_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* NullValue_descriptor();
+inline const ::std::string& NullValue_Name(NullValue value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ NullValue_descriptor(), value);
+}
+inline bool NullValue_Parse(
+ const ::std::string& name, NullValue* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<NullValue>(
+ NullValue_descriptor(), name, value);
+}
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT Struct : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Struct) */ {
+ public:
+ Struct();
+ virtual ~Struct();
+
+ Struct(const Struct& from);
+
+ inline Struct& operator=(const Struct& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Struct& default_instance();
+
+ void Swap(Struct* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Struct* New() const { return New(NULL); }
+
+ Struct* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Struct& from);
+ void MergeFrom(const Struct& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Struct* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+
+ // accessors -------------------------------------------------------
+
+ // map<string, .google.protobuf.Value> fields = 1;
+ int fields_size() const;
+ void clear_fields();
+ static const int kFieldsFieldNumber = 1;
+ const ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >&
+ fields() const;
+ ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >*
+ mutable_fields();
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Struct)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ typedef ::google::protobuf::internal::MapEntryLite<
+ ::std::string, ::google::protobuf::Value,
+ ::google::protobuf::internal::WireFormatLite::TYPE_STRING,
+ ::google::protobuf::internal::WireFormatLite::TYPE_MESSAGE,
+ 0 >
+ Struct_FieldsEntry;
+ ::google::protobuf::internal::MapField<
+ ::std::string, ::google::protobuf::Value,
+ ::google::protobuf::internal::WireFormatLite::TYPE_STRING,
+ ::google::protobuf::internal::WireFormatLite::TYPE_MESSAGE,
+ 0 > fields_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fstruct_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fstruct_2eproto();
+
+ void InitAsDefaultInstance();
+ static Struct* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Value : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Value) */ {
+ public:
+ Value();
+ virtual ~Value();
+
+ Value(const Value& from);
+
+ inline Value& operator=(const Value& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Value& default_instance();
+
+ enum KindCase {
+ kNullValue = 1,
+ kNumberValue = 2,
+ kStringValue = 3,
+ kBoolValue = 4,
+ kStructValue = 5,
+ kListValue = 6,
+ KIND_NOT_SET = 0,
+ };
+
+ void Swap(Value* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Value* New() const { return New(NULL); }
+
+ Value* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Value& from);
+ void MergeFrom(const Value& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Value* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional .google.protobuf.NullValue null_value = 1;
+ private:
+ bool has_null_value() const;
+ public:
+ void clear_null_value();
+ static const int kNullValueFieldNumber = 1;
+ ::google::protobuf::NullValue null_value() const;
+ void set_null_value(::google::protobuf::NullValue value);
+
+ // optional double number_value = 2;
+ private:
+ bool has_number_value() const;
+ public:
+ void clear_number_value();
+ static const int kNumberValueFieldNumber = 2;
+ double number_value() const;
+ void set_number_value(double value);
+
+ // optional string string_value = 3;
+ private:
+ bool has_string_value() const;
+ public:
+ void clear_string_value();
+ static const int kStringValueFieldNumber = 3;
+ const ::std::string& string_value() const;
+ void set_string_value(const ::std::string& value);
+ void set_string_value(const char* value);
+ void set_string_value(const char* value, size_t size);
+ ::std::string* mutable_string_value();
+ ::std::string* release_string_value();
+ void set_allocated_string_value(::std::string* string_value);
+
+ // optional bool bool_value = 4;
+ private:
+ bool has_bool_value() const;
+ public:
+ void clear_bool_value();
+ static const int kBoolValueFieldNumber = 4;
+ bool bool_value() const;
+ void set_bool_value(bool value);
+
+ // optional .google.protobuf.Struct struct_value = 5;
+ bool has_struct_value() const;
+ void clear_struct_value();
+ static const int kStructValueFieldNumber = 5;
+ const ::google::protobuf::Struct& struct_value() const;
+ ::google::protobuf::Struct* mutable_struct_value();
+ ::google::protobuf::Struct* release_struct_value();
+ void set_allocated_struct_value(::google::protobuf::Struct* struct_value);
+
+ // optional .google.protobuf.ListValue list_value = 6;
+ bool has_list_value() const;
+ void clear_list_value();
+ static const int kListValueFieldNumber = 6;
+ const ::google::protobuf::ListValue& list_value() const;
+ ::google::protobuf::ListValue* mutable_list_value();
+ ::google::protobuf::ListValue* release_list_value();
+ void set_allocated_list_value(::google::protobuf::ListValue* list_value);
+
+ KindCase kind_case() const;
+ // @@protoc_insertion_point(class_scope:google.protobuf.Value)
+ private:
+ inline void set_has_null_value();
+ inline void set_has_number_value();
+ inline void set_has_string_value();
+ inline void set_has_bool_value();
+ inline void set_has_struct_value();
+ inline void set_has_list_value();
+
+ inline bool has_kind() const;
+ void clear_kind();
+ inline void clear_has_kind();
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ union KindUnion {
+ KindUnion() {}
+ int null_value_;
+ double number_value_;
+ ::google::protobuf::internal::ArenaStringPtr string_value_;
+ bool bool_value_;
+ ::google::protobuf::Struct* struct_value_;
+ ::google::protobuf::ListValue* list_value_;
+ } kind_;
+ mutable int _cached_size_;
+ ::google::protobuf::uint32 _oneof_case_[1];
+
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fstruct_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fstruct_2eproto();
+
+ void InitAsDefaultInstance();
+ static Value* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT ListValue : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.ListValue) */ {
+ public:
+ ListValue();
+ virtual ~ListValue();
+
+ ListValue(const ListValue& from);
+
+ inline ListValue& operator=(const ListValue& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const ListValue& default_instance();
+
+ void Swap(ListValue* other);
+
+ // implements Message ----------------------------------------------
+
+ inline ListValue* New() const { return New(NULL); }
+
+ ListValue* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const ListValue& from);
+ void MergeFrom(const ListValue& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(ListValue* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // repeated .google.protobuf.Value values = 1;
+ int values_size() const;
+ void clear_values();
+ static const int kValuesFieldNumber = 1;
+ const ::google::protobuf::Value& values(int index) const;
+ ::google::protobuf::Value* mutable_values(int index);
+ ::google::protobuf::Value* add_values();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Value >*
+ mutable_values();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Value >&
+ values() const;
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.ListValue)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Value > values_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fstruct_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fstruct_2eproto();
+
+ void InitAsDefaultInstance();
+ static ListValue* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// Struct
+
+// map<string, .google.protobuf.Value> fields = 1;
+inline int Struct::fields_size() const {
+ return fields_.size();
+}
+inline void Struct::clear_fields() {
+ fields_.Clear();
+}
+inline const ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >&
+Struct::fields() const {
+ // @@protoc_insertion_point(field_map:google.protobuf.Struct.fields)
+ return fields_.GetMap();
+}
+inline ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >*
+Struct::mutable_fields() {
+ // @@protoc_insertion_point(field_mutable_map:google.protobuf.Struct.fields)
+ return fields_.MutableMap();
+}
+
+// -------------------------------------------------------------------
+
+// Value
+
+// optional .google.protobuf.NullValue null_value = 1;
+inline bool Value::has_null_value() const {
+ return kind_case() == kNullValue;
+}
+inline void Value::set_has_null_value() {
+ _oneof_case_[0] = kNullValue;
+}
+inline void Value::clear_null_value() {
+ if (has_null_value()) {
+ kind_.null_value_ = 0;
+ clear_has_kind();
+ }
+}
+inline ::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);
+}
+inline 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;
+inline bool Value::has_number_value() const {
+ return kind_case() == kNumberValue;
+}
+inline void Value::set_has_number_value() {
+ _oneof_case_[0] = kNumberValue;
+}
+inline void Value::clear_number_value() {
+ if (has_number_value()) {
+ kind_.number_value_ = 0;
+ clear_has_kind();
+ }
+}
+inline 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;
+}
+inline 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;
+inline bool Value::has_string_value() const {
+ return kind_case() == kStringValue;
+}
+inline void Value::set_has_string_value() {
+ _oneof_case_[0] = kStringValue;
+}
+inline void Value::clear_string_value() {
+ if (has_string_value()) {
+ kind_.string_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ clear_has_kind();
+ }
+}
+inline 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();
+}
+inline 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)
+}
+inline 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)
+}
+inline 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)
+}
+inline ::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());
+}
+inline ::std::string* Value::release_string_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Value.string_value)
+ if (has_string_value()) {
+ clear_has_kind();
+ return kind_.string_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ } else {
+ return NULL;
+ }
+}
+inline 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;
+inline bool Value::has_bool_value() const {
+ return kind_case() == kBoolValue;
+}
+inline void Value::set_has_bool_value() {
+ _oneof_case_[0] = kBoolValue;
+}
+inline void Value::clear_bool_value() {
+ if (has_bool_value()) {
+ kind_.bool_value_ = false;
+ clear_has_kind();
+ }
+}
+inline 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;
+}
+inline 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;
+inline bool Value::has_struct_value() const {
+ return kind_case() == kStructValue;
+}
+inline void Value::set_has_struct_value() {
+ _oneof_case_[0] = kStructValue;
+}
+inline void Value::clear_struct_value() {
+ if (has_struct_value()) {
+ delete kind_.struct_value_;
+ clear_has_kind();
+ }
+}
+inline 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();
+}
+inline ::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_;
+}
+inline ::google::protobuf::Struct* Value::release_struct_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Value.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;
+ }
+}
+inline 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;
+inline bool Value::has_list_value() const {
+ return kind_case() == kListValue;
+}
+inline void Value::set_has_list_value() {
+ _oneof_case_[0] = kListValue;
+}
+inline void Value::clear_list_value() {
+ if (has_list_value()) {
+ delete kind_.list_value_;
+ clear_has_kind();
+ }
+}
+inline 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();
+}
+inline ::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_;
+}
+inline ::google::protobuf::ListValue* Value::release_list_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Value.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;
+ }
+}
+inline 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)
+}
+
+inline bool Value::has_kind() const {
+ return kind_case() != KIND_NOT_SET;
+}
+inline void Value::clear_has_kind() {
+ _oneof_case_[0] = KIND_NOT_SET;
+}
+inline Value::KindCase Value::kind_case() const {
+ return Value::KindCase(_oneof_case_[0]);
+}
+// -------------------------------------------------------------------
+
+// ListValue
+
+// repeated .google.protobuf.Value values = 1;
+inline int ListValue::values_size() const {
+ return values_.size();
+}
+inline void ListValue::clear_values() {
+ values_.Clear();
+}
+inline const ::google::protobuf::Value& ListValue::values(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.ListValue.values)
+ return values_.Get(index);
+}
+inline ::google::protobuf::Value* ListValue::mutable_values(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.ListValue.values)
+ return values_.Mutable(index);
+}
+inline ::google::protobuf::Value* ListValue::add_values() {
+ // @@protoc_insertion_point(field_add:google.protobuf.ListValue.values)
+ return values_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Value >*
+ListValue::mutable_values() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.ListValue.values)
+ return &values_;
+}
+inline 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
+
+#ifndef SWIG
+namespace google {
+namespace protobuf {
+
+template <> struct is_proto_enum< ::google::protobuf::NullValue> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::NullValue>() {
+ return ::google::protobuf::NullValue_descriptor();
+}
+
+} // namespace protobuf
+} // namespace google
+#endif // SWIG
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fstruct_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/struct.proto b/third_party/protobuf/3.0.0/src/google/protobuf/struct.proto
new file mode 100644
index 0000000000..beeba81188
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/struct.proto
@@ -0,0 +1,96 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option go_package = "github.com/golang/protobuf/ptypes/struct;structpb";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "StructProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+
+// `Struct` represents a structured data value, consisting of fields
+// which map to dynamically typed values. In some languages, `Struct`
+// might be supported by a native representation. For example, in
+// scripting languages like JS a struct is represented as an
+// object. The details of that representation are described together
+// with the proto support for the language.
+//
+// The JSON representation for `Struct` is JSON object.
+message Struct {
+ // Unordered map of dynamically typed values.
+ map<string, Value> fields = 1;
+}
+
+// `Value` represents a dynamically typed value which can be either
+// null, a number, a string, a boolean, a recursive struct value, or a
+// list of values. A producer of value is expected to set one of that
+// variants, absence of any variant indicates an error.
+//
+// The JSON representation for `Value` is JSON value.
+message Value {
+ // The kind of value.
+ oneof kind {
+ // Represents a null value.
+ NullValue null_value = 1;
+ // Represents a double value.
+ double number_value = 2;
+ // Represents a string value.
+ string string_value = 3;
+ // Represents a boolean value.
+ bool bool_value = 4;
+ // Represents a structured value.
+ Struct struct_value = 5;
+ // Represents a repeated `Value`.
+ ListValue list_value = 6;
+ }
+}
+
+// `NullValue` is a singleton enumeration to represent the null value for the
+// `Value` type union.
+//
+// The JSON representation for `NullValue` is JSON `null`.
+enum NullValue {
+ // Null value.
+ NULL_VALUE = 0;
+}
+
+// `ListValue` is a wrapper around a repeated field of values.
+//
+// The JSON representation for `ListValue` is JSON array.
+message ListValue {
+ // Repeated field of dynamically typed values.
+ repeated Value values = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomic_sequence_num.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomic_sequence_num.h
new file mode 100644
index 0000000000..bb20942f2f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomic_sequence_num.h
@@ -0,0 +1,54 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+#ifndef GOOGLE_PROTOBUF_ATOMIC_SEQUENCE_NUM_H_
+#define GOOGLE_PROTOBUF_ATOMIC_SEQUENCE_NUM_H_
+
+#include <google/protobuf/stubs/atomicops.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+class SequenceNumber {
+ public:
+ SequenceNumber() : word_(0) {}
+
+ AtomicWord GetNext() {
+ return NoBarrier_AtomicIncrement(&word_, 1) - 1;
+ }
+ private:
+ AtomicWord word_;
+};
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMIC_SEQUENCE_NUM_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops.h
new file mode 100644
index 0000000000..9b3d1e6b57
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops.h
@@ -0,0 +1,246 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// The routines exported by this module are subtle. If you use them, even if
+// you get the code right, it will depend on careful reasoning about atomicity
+// and memory ordering; it will be less readable, and harder to maintain. If
+// you plan to use these routines, you should have a good reason, such as solid
+// evidence that performance would otherwise suffer, or there being no
+// alternative. You should assume only properties explicitly guaranteed by the
+// specifications in this file. You are almost certainly _not_ writing code
+// just for the x86; if you assume x86 semantics, x86 hardware bugs and
+// implementations on other archtectures will cause your code to break. If you
+// do not know what you are doing, avoid these routines, and use a Mutex.
+//
+// It is incorrect to make direct assignments to/from an atomic variable.
+// You should use one of the Load or Store routines. The NoBarrier
+// versions are provided when no barriers are needed:
+// NoBarrier_Store()
+// NoBarrier_Load()
+// Although there are currently no compiler enforcement, you are encouraged
+// to use these.
+
+// This header and the implementations for each platform (located in
+// atomicops_internals_*) must be kept in sync with the upstream code (V8).
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_H_
+
+// Don't include this file for people not concerned about thread safety.
+#ifndef GOOGLE_PROTOBUF_NO_THREAD_SAFETY
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/platform_macros.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+#if defined(GOOGLE_PROTOBUF_ARCH_POWER)
+#if defined(_LP64) || defined(__LP64__)
+typedef int32 Atomic32;
+typedef intptr_t Atomic64;
+#else
+typedef intptr_t Atomic32;
+typedef int64 Atomic64;
+#endif
+#else
+typedef int32 Atomic32;
+#ifdef GOOGLE_PROTOBUF_ARCH_64_BIT
+// We need to be able to go between Atomic64 and AtomicWord implicitly. This
+// means Atomic64 and AtomicWord should be the same type on 64-bit.
+#if defined(__ILP32__) || defined(GOOGLE_PROTOBUF_OS_NACL)
+// NaCl's intptr_t is not actually 64-bits on 64-bit!
+// http://code.google.com/p/nativeclient/issues/detail?id=1162
+// sparcv9's pointer type is 32bits
+typedef int64 Atomic64;
+#else
+typedef intptr_t Atomic64;
+#endif
+#endif
+#endif
+
+// Use AtomicWord for a machine-sized pointer. It will use the Atomic32 or
+// Atomic64 routines below, depending on your architecture.
+typedef intptr_t AtomicWord;
+
+// Atomically execute:
+// result = *ptr;
+// if (*ptr == old_value)
+// *ptr = new_value;
+// return result;
+//
+// I.e., replace "*ptr" with "new_value" if "*ptr" used to be "old_value".
+// Always return the old value of "*ptr"
+//
+// This routine implies no memory barriers.
+Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value);
+
+// Atomically store new_value into *ptr, returning the previous value held in
+// *ptr. This routine implies no memory barriers.
+Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr, Atomic32 new_value);
+
+// Atomically increment *ptr by "increment". Returns the new value of
+// *ptr with the increment applied. This routine implies no memory barriers.
+Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr, Atomic32 increment);
+
+Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment);
+
+// These following lower-level operations are typically useful only to people
+// implementing higher-level synchronization operations like spinlocks,
+// mutexes, and condition-variables. They combine CompareAndSwap(), a load, or
+// a store with appropriate memory-ordering instructions. "Acquire" operations
+// ensure that no later memory access can be reordered ahead of the operation.
+// "Release" operations ensure that no previous memory access can be reordered
+// after the operation. "Barrier" operations have both "Acquire" and "Release"
+// semantics. A MemoryBarrier() has "Barrier" semantics, but does no memory
+// access.
+Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value);
+Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value);
+
+#if defined(__MINGW32__) && defined(MemoryBarrier)
+#undef MemoryBarrier
+#endif
+void MemoryBarrier();
+void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value);
+void Acquire_Store(volatile Atomic32* ptr, Atomic32 value);
+void Release_Store(volatile Atomic32* ptr, Atomic32 value);
+
+Atomic32 NoBarrier_Load(volatile const Atomic32* ptr);
+Atomic32 Acquire_Load(volatile const Atomic32* ptr);
+Atomic32 Release_Load(volatile const Atomic32* ptr);
+
+// 64-bit atomic operations (only available on 64-bit processors).
+#ifdef GOOGLE_PROTOBUF_ARCH_64_BIT
+Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value);
+Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr, Atomic64 new_value);
+Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr, Atomic64 increment);
+Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr, Atomic64 increment);
+
+Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value);
+Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value);
+void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value);
+void Acquire_Store(volatile Atomic64* ptr, Atomic64 value);
+void Release_Store(volatile Atomic64* ptr, Atomic64 value);
+Atomic64 NoBarrier_Load(volatile const Atomic64* ptr);
+Atomic64 Acquire_Load(volatile const Atomic64* ptr);
+Atomic64 Release_Load(volatile const Atomic64* ptr);
+#endif // GOOGLE_PROTOBUF_ARCH_64_BIT
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+// Include our platform specific implementation.
+#define GOOGLE_PROTOBUF_ATOMICOPS_ERROR \
+"Atomic operations are not supported on your platform"
+
+// ThreadSanitizer, http://clang.llvm.org/docs/ThreadSanitizer.html.
+#if defined(THREAD_SANITIZER)
+#include <google/protobuf/stubs/atomicops_internals_tsan.h>
+// MSVC.
+#elif defined(_MSC_VER)
+#if defined(GOOGLE_PROTOBUF_ARCH_IA32) || defined(GOOGLE_PROTOBUF_ARCH_X64)
+#include <google/protobuf/stubs/atomicops_internals_x86_msvc.h>
+#else
+#error GOOGLE_PROTOBUF_ATOMICOPS_ERROR
+#endif
+
+// Solaris
+#elif defined(GOOGLE_PROTOBUF_OS_SOLARIS)
+#include <google/protobuf/stubs/atomicops_internals_solaris.h>
+
+// AIX
+#elif defined(GOOGLE_PROTOBUF_OS_AIX)
+#include <google/protobuf/stubs/atomicops_internals_power.h>
+
+// Apple.
+#elif defined(GOOGLE_PROTOBUF_OS_APPLE)
+#include <google/protobuf/stubs/atomicops_internals_macosx.h>
+
+// GCC.
+#elif defined(__GNUC__)
+#if defined(GOOGLE_PROTOBUF_ARCH_IA32) || defined(GOOGLE_PROTOBUF_ARCH_X64)
+#include <google/protobuf/stubs/atomicops_internals_x86_gcc.h>
+#elif defined(GOOGLE_PROTOBUF_ARCH_ARM) && defined(__linux__)
+#include <google/protobuf/stubs/atomicops_internals_arm_gcc.h>
+#elif defined(GOOGLE_PROTOBUF_ARCH_AARCH64)
+#include <google/protobuf/stubs/atomicops_internals_arm64_gcc.h>
+#elif defined(GOOGLE_PROTOBUF_ARCH_ARM_QNX)
+#include <google/protobuf/stubs/atomicops_internals_arm_qnx.h>
+#elif defined(GOOGLE_PROTOBUF_ARCH_MIPS) || defined(GOOGLE_PROTOBUF_ARCH_MIPS64)
+#include <google/protobuf/stubs/atomicops_internals_mips_gcc.h>
+#elif defined(GOOGLE_PROTOBUF_ARCH_POWER)
+#include <google/protobuf/stubs/atomicops_internals_power.h>
+#elif defined(__native_client__)
+#include <google/protobuf/stubs/atomicops_internals_pnacl.h>
+#elif defined(GOOGLE_PROTOBUF_ARCH_PPC)
+#include <google/protobuf/stubs/atomicops_internals_ppc_gcc.h>
+#elif (((__GNUC__ == 4) && (__GNUC_MINOR__ >= 7)) || (__GNUC__ > 4))
+#include <google/protobuf/stubs/atomicops_internals_generic_gcc.h>
+#elif defined(__clang__)
+#if __has_extension(c_atomic)
+#include <google/protobuf/stubs/atomicops_internals_generic_gcc.h>
+#else
+#error GOOGLE_PROTOBUF_ATOMICOPS_ERROR
+#endif
+#else
+#error GOOGLE_PROTOBUF_ATOMICOPS_ERROR
+#endif
+
+// Unknown.
+#else
+#error GOOGLE_PROTOBUF_ATOMICOPS_ERROR
+#endif
+
+// On some platforms we need additional declarations to make AtomicWord
+// compatible with our other Atomic* types.
+#if defined(GOOGLE_PROTOBUF_OS_APPLE)
+#include <google/protobuf/stubs/atomicops_internals_atomicword_compat.h>
+#endif
+
+#undef GOOGLE_PROTOBUF_ATOMICOPS_ERROR
+
+#endif // GOOGLE_PROTOBUF_NO_THREAD_SAFETY
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm64_gcc.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm64_gcc.h
new file mode 100644
index 0000000000..0a2d2b894b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm64_gcc.h
@@ -0,0 +1,325 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM64_GCC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM64_GCC_H_
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline void MemoryBarrier() {
+ __asm__ __volatile__ ("dmb ish" ::: "memory"); // NOLINT
+}
+
+// NoBarrier versions of the operation include "memory" in the clobber list.
+// This is not required for direct usage of the NoBarrier versions of the
+// operations. However this is required for correctness when they are used as
+// part of the Acquire or Release versions, to ensure that nothing from outside
+// the call is reordered between the operation and the memory barrier. This does
+// not change the code generated, so has no or minimal impact on the
+// NoBarrier operations.
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev;
+ int32_t temp;
+
+ __asm__ __volatile__ ( // NOLINT
+ "0: \n\t"
+ "ldxr %w[prev], %[ptr] \n\t" // Load the previous value.
+ "cmp %w[prev], %w[old_value] \n\t"
+ "bne 1f \n\t"
+ "stxr %w[temp], %w[new_value], %[ptr] \n\t" // Try to store the new value.
+ "cbnz %w[temp], 0b \n\t" // Retry if it did not work.
+ "1: \n\t"
+ : [prev]"=&r" (prev),
+ [temp]"=&r" (temp),
+ [ptr]"+Q" (*ptr)
+ : [old_value]"IJr" (old_value),
+ [new_value]"r" (new_value)
+ : "cc", "memory"
+ ); // NOLINT
+
+ return prev;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ Atomic32 result;
+ int32_t temp;
+
+ __asm__ __volatile__ ( // NOLINT
+ "0: \n\t"
+ "ldxr %w[result], %[ptr] \n\t" // Load the previous value.
+ "stxr %w[temp], %w[new_value], %[ptr] \n\t" // Try to store the new value.
+ "cbnz %w[temp], 0b \n\t" // Retry if it did not work.
+ : [result]"=&r" (result),
+ [temp]"=&r" (temp),
+ [ptr]"+Q" (*ptr)
+ : [new_value]"r" (new_value)
+ : "memory"
+ ); // NOLINT
+
+ return result;
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ Atomic32 result;
+ int32_t temp;
+
+ __asm__ __volatile__ ( // NOLINT
+ "0: \n\t"
+ "ldxr %w[result], %[ptr] \n\t" // Load the previous value.
+ "add %w[result], %w[result], %w[increment]\n\t"
+ "stxr %w[temp], %w[result], %[ptr] \n\t" // Try to store the result.
+ "cbnz %w[temp], 0b \n\t" // Retry on failure.
+ : [result]"=&r" (result),
+ [temp]"=&r" (temp),
+ [ptr]"+Q" (*ptr)
+ : [increment]"IJr" (increment)
+ : "memory"
+ ); // NOLINT
+
+ return result;
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ MemoryBarrier();
+ Atomic32 result = NoBarrier_AtomicIncrement(ptr, increment);
+ MemoryBarrier();
+
+ return result;
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ MemoryBarrier();
+
+ return prev;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ MemoryBarrier();
+ Atomic32 prev = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+
+ return prev;
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ __asm__ __volatile__ ( // NOLINT
+ "stlr %w[value], %[ptr] \n\t"
+ : [ptr]"=Q" (*ptr)
+ : [value]"r" (value)
+ : "memory"
+ ); // NOLINT
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 value;
+
+ __asm__ __volatile__ ( // NOLINT
+ "ldar %w[value], %[ptr] \n\t"
+ : [value]"=r" (value)
+ : [ptr]"Q" (*ptr)
+ : "memory"
+ ); // NOLINT
+
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+// 64-bit versions of the operations.
+// See the 32-bit versions for comments.
+
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 prev;
+ int32_t temp;
+
+ __asm__ __volatile__ ( // NOLINT
+ "0: \n\t"
+ "ldxr %[prev], %[ptr] \n\t"
+ "cmp %[prev], %[old_value] \n\t"
+ "bne 1f \n\t"
+ "stxr %w[temp], %[new_value], %[ptr] \n\t"
+ "cbnz %w[temp], 0b \n\t"
+ "1: \n\t"
+ : [prev]"=&r" (prev),
+ [temp]"=&r" (temp),
+ [ptr]"+Q" (*ptr)
+ : [old_value]"IJr" (old_value),
+ [new_value]"r" (new_value)
+ : "cc", "memory"
+ ); // NOLINT
+
+ return prev;
+}
+
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr,
+ Atomic64 new_value) {
+ Atomic64 result;
+ int32_t temp;
+
+ __asm__ __volatile__ ( // NOLINT
+ "0: \n\t"
+ "ldxr %[result], %[ptr] \n\t"
+ "stxr %w[temp], %[new_value], %[ptr] \n\t"
+ "cbnz %w[temp], 0b \n\t"
+ : [result]"=&r" (result),
+ [temp]"=&r" (temp),
+ [ptr]"+Q" (*ptr)
+ : [new_value]"r" (new_value)
+ : "memory"
+ ); // NOLINT
+
+ return result;
+}
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ Atomic64 result;
+ int32_t temp;
+
+ __asm__ __volatile__ ( // NOLINT
+ "0: \n\t"
+ "ldxr %[result], %[ptr] \n\t"
+ "add %[result], %[result], %[increment] \n\t"
+ "stxr %w[temp], %[result], %[ptr] \n\t"
+ "cbnz %w[temp], 0b \n\t"
+ : [result]"=&r" (result),
+ [temp]"=&r" (temp),
+ [ptr]"+Q" (*ptr)
+ : [increment]"IJr" (increment)
+ : "memory"
+ ); // NOLINT
+
+ return result;
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ MemoryBarrier();
+ Atomic64 result = NoBarrier_AtomicIncrement(ptr, increment);
+ MemoryBarrier();
+
+ return result;
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 prev = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ MemoryBarrier();
+
+ return prev;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ MemoryBarrier();
+ Atomic64 prev = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+
+ return prev;
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ __asm__ __volatile__ ( // NOLINT
+ "stlr %x[value], %[ptr] \n\t"
+ : [ptr]"=Q" (*ptr)
+ : [value]"r" (value)
+ : "memory"
+ ); // NOLINT
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return *ptr;
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ Atomic64 value;
+
+ __asm__ __volatile__ ( // NOLINT
+ "ldar %x[value], %[ptr] \n\t"
+ : [value]"=r" (value)
+ : [ptr]"Q" (*ptr)
+ : "memory"
+ ); // NOLINT
+
+ return value;
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM64_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h
new file mode 100644
index 0000000000..90e727b0bc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h
@@ -0,0 +1,151 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+//
+// LinuxKernelCmpxchg and Barrier_AtomicIncrement are from Google Gears.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM_GCC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM_GCC_H_
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// 0xffff0fc0 is the hard coded address of a function provided by
+// the kernel which implements an atomic compare-exchange. On older
+// ARM architecture revisions (pre-v6) this may be implemented using
+// a syscall. This address is stable, and in active use (hard coded)
+// by at least glibc-2.7 and the Android C library.
+typedef Atomic32 (*LinuxKernelCmpxchgFunc)(Atomic32 old_value,
+ Atomic32 new_value,
+ volatile Atomic32* ptr);
+LinuxKernelCmpxchgFunc pLinuxKernelCmpxchg __attribute__((weak)) =
+ (LinuxKernelCmpxchgFunc) 0xffff0fc0;
+
+typedef void (*LinuxKernelMemoryBarrierFunc)(void);
+LinuxKernelMemoryBarrierFunc pLinuxKernelMemoryBarrier __attribute__((weak)) =
+ (LinuxKernelMemoryBarrierFunc) 0xffff0fa0;
+
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev_value = *ptr;
+ do {
+ if (!pLinuxKernelCmpxchg(old_value, new_value,
+ const_cast<Atomic32*>(ptr))) {
+ return old_value;
+ }
+ prev_value = *ptr;
+ } while (prev_value == old_value);
+ return prev_value;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ Atomic32 old_value;
+ do {
+ old_value = *ptr;
+ } while (pLinuxKernelCmpxchg(old_value, new_value,
+ const_cast<Atomic32*>(ptr)));
+ return old_value;
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return Barrier_AtomicIncrement(ptr, increment);
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ for (;;) {
+ // Atomic exchange the old value with an incremented one.
+ Atomic32 old_value = *ptr;
+ Atomic32 new_value = old_value + increment;
+ if (pLinuxKernelCmpxchg(old_value, new_value,
+ const_cast<Atomic32*>(ptr)) == 0) {
+ // The exchange took place as expected.
+ return new_value;
+ }
+ // Otherwise, *ptr changed mid-loop and we need to retry.
+ }
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void MemoryBarrier() {
+ pLinuxKernelMemoryBarrier();
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ MemoryBarrier();
+ *ptr = value;
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 value = *ptr;
+ MemoryBarrier();
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_qnx.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_qnx.h
new file mode 100644
index 0000000000..17dfaa5182
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_arm_qnx.h
@@ -0,0 +1,146 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM_QNX_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM_QNX_H_
+
+// For _smp_cmpxchg()
+#include <pthread.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 QNXCmpxchg(Atomic32 old_value,
+ Atomic32 new_value,
+ volatile Atomic32* ptr) {
+ return static_cast<Atomic32>(
+ _smp_cmpxchg((volatile unsigned *)ptr,
+ (unsigned)old_value,
+ (unsigned)new_value));
+}
+
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev_value = *ptr;
+ do {
+ if (!QNXCmpxchg(old_value, new_value,
+ const_cast<Atomic32*>(ptr))) {
+ return old_value;
+ }
+ prev_value = *ptr;
+ } while (prev_value == old_value);
+ return prev_value;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ Atomic32 old_value;
+ do {
+ old_value = *ptr;
+ } while (QNXCmpxchg(old_value, new_value,
+ const_cast<Atomic32*>(ptr)));
+ return old_value;
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return Barrier_AtomicIncrement(ptr, increment);
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ for (;;) {
+ // Atomic exchange the old value with an incremented one.
+ Atomic32 old_value = *ptr;
+ Atomic32 new_value = old_value + increment;
+ if (QNXCmpxchg(old_value, new_value,
+ const_cast<Atomic32*>(ptr)) == 0) {
+ // The exchange took place as expected.
+ return new_value;
+ }
+ // Otherwise, *ptr changed mid-loop and we need to retry.
+ }
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void MemoryBarrier() {
+ __sync_synchronize();
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ MemoryBarrier();
+ *ptr = value;
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 value = *ptr;
+ MemoryBarrier();
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ARM_QNX_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_atomicword_compat.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_atomicword_compat.h
new file mode 100644
index 0000000000..eb198ff5cc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_atomicword_compat.h
@@ -0,0 +1,122 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ATOMICWORD_COMPAT_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ATOMICWORD_COMPAT_H_
+
+// AtomicWord is a synonym for intptr_t, and Atomic32 is a synonym for int32,
+// which in turn means int. On some LP32 platforms, intptr_t is an int, but
+// on others, it's a long. When AtomicWord and Atomic32 are based on different
+// fundamental types, their pointers are incompatible.
+//
+// This file defines function overloads to allow both AtomicWord and Atomic32
+// data to be used with this interface.
+//
+// On LP64 platforms, AtomicWord and Atomic64 are both always long,
+// so this problem doesn't occur.
+
+#if !defined(GOOGLE_PROTOBUF_ARCH_64_BIT)
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline AtomicWord NoBarrier_CompareAndSwap(volatile AtomicWord* ptr,
+ AtomicWord old_value,
+ AtomicWord new_value) {
+ return NoBarrier_CompareAndSwap(
+ reinterpret_cast<volatile Atomic32*>(ptr), old_value, new_value);
+}
+
+inline AtomicWord NoBarrier_AtomicExchange(volatile AtomicWord* ptr,
+ AtomicWord new_value) {
+ return NoBarrier_AtomicExchange(
+ reinterpret_cast<volatile Atomic32*>(ptr), new_value);
+}
+
+inline AtomicWord NoBarrier_AtomicIncrement(volatile AtomicWord* ptr,
+ AtomicWord increment) {
+ return NoBarrier_AtomicIncrement(
+ reinterpret_cast<volatile Atomic32*>(ptr), increment);
+}
+
+inline AtomicWord Barrier_AtomicIncrement(volatile AtomicWord* ptr,
+ AtomicWord increment) {
+ return Barrier_AtomicIncrement(
+ reinterpret_cast<volatile Atomic32*>(ptr), increment);
+}
+
+inline AtomicWord Acquire_CompareAndSwap(volatile AtomicWord* ptr,
+ AtomicWord old_value,
+ AtomicWord new_value) {
+ return Acquire_CompareAndSwap(
+ reinterpret_cast<volatile Atomic32*>(ptr), old_value, new_value);
+}
+
+inline AtomicWord Release_CompareAndSwap(volatile AtomicWord* ptr,
+ AtomicWord old_value,
+ AtomicWord new_value) {
+ return Release_CompareAndSwap(
+ reinterpret_cast<volatile Atomic32*>(ptr), old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile AtomicWord *ptr, AtomicWord value) {
+ NoBarrier_Store(reinterpret_cast<volatile Atomic32*>(ptr), value);
+}
+
+inline void Acquire_Store(volatile AtomicWord* ptr, AtomicWord value) {
+ return Acquire_Store(reinterpret_cast<volatile Atomic32*>(ptr), value);
+}
+
+inline void Release_Store(volatile AtomicWord* ptr, AtomicWord value) {
+ return Release_Store(reinterpret_cast<volatile Atomic32*>(ptr), value);
+}
+
+inline AtomicWord NoBarrier_Load(volatile const AtomicWord *ptr) {
+ return NoBarrier_Load(reinterpret_cast<volatile const Atomic32*>(ptr));
+}
+
+inline AtomicWord Acquire_Load(volatile const AtomicWord* ptr) {
+ return Acquire_Load(reinterpret_cast<volatile const Atomic32*>(ptr));
+}
+
+inline AtomicWord Release_Load(volatile const AtomicWord* ptr) {
+ return Release_Load(reinterpret_cast<volatile const Atomic32*>(ptr));
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // !defined(GOOGLE_PROTOBUF_ARCH_64_BIT)
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_ATOMICWORD_COMPAT_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_generic_gcc.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_generic_gcc.h
new file mode 100644
index 0000000000..a0116a60ee
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_generic_gcc.h
@@ -0,0 +1,137 @@
+// Copyright 2013 Red Hat Inc. All rights reserved.
+//
+// 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 Red Hat 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_GENERIC_GCC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_GENERIC_GCC_H_
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ __atomic_compare_exchange_n(ptr, &old_value, new_value, true,
+ __ATOMIC_RELAXED, __ATOMIC_RELAXED);
+ return old_value;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ return __atomic_exchange_n(ptr, new_value, __ATOMIC_RELAXED);
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return __atomic_add_fetch(ptr, increment, __ATOMIC_RELAXED);
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return __atomic_add_fetch(ptr, increment, __ATOMIC_SEQ_CST);
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ __atomic_compare_exchange_n(ptr, &old_value, new_value, true,
+ __ATOMIC_ACQUIRE, __ATOMIC_ACQUIRE);
+ return old_value;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ __atomic_compare_exchange_n(ptr, &old_value, new_value, true,
+ __ATOMIC_RELEASE, __ATOMIC_ACQUIRE);
+ return old_value;
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ __atomic_store_n(ptr, value, __ATOMIC_RELAXED);
+}
+
+inline void MemoryBarrier() {
+ __sync_synchronize();
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ __atomic_store_n(ptr, value, __ATOMIC_SEQ_CST);
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ __atomic_store_n(ptr, value, __ATOMIC_RELEASE);
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return __atomic_load_n(ptr, __ATOMIC_RELAXED);
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ return __atomic_load_n(ptr, __ATOMIC_ACQUIRE);
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ return __atomic_load_n(ptr, __ATOMIC_SEQ_CST);
+}
+
+#ifdef __LP64__
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ __atomic_store_n(ptr, value, __ATOMIC_RELEASE);
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ return __atomic_load_n(ptr, __ATOMIC_ACQUIRE);
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ __atomic_compare_exchange_n(ptr, &old_value, new_value, true,
+ __ATOMIC_ACQUIRE, __ATOMIC_ACQUIRE);
+ return old_value;
+}
+
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ __atomic_compare_exchange_n(ptr, &old_value, new_value, true,
+ __ATOMIC_RELAXED, __ATOMIC_RELAXED);
+ return old_value;
+}
+
+#endif // defined(__LP64__)
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_GENERIC_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_macosx.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_macosx.h
new file mode 100644
index 0000000000..796332417f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_macosx.h
@@ -0,0 +1,225 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_MACOSX_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_MACOSX_H_
+
+#include <libkern/OSAtomic.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev_value;
+ do {
+ if (OSAtomicCompareAndSwap32(old_value, new_value,
+ const_cast<Atomic32*>(ptr))) {
+ return old_value;
+ }
+ prev_value = *ptr;
+ } while (prev_value == old_value);
+ return prev_value;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ Atomic32 old_value;
+ do {
+ old_value = *ptr;
+ } while (!OSAtomicCompareAndSwap32(old_value, new_value,
+ const_cast<Atomic32*>(ptr)));
+ return old_value;
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return OSAtomicAdd32(increment, const_cast<Atomic32*>(ptr));
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return OSAtomicAdd32Barrier(increment, const_cast<Atomic32*>(ptr));
+}
+
+inline void MemoryBarrier() {
+ OSMemoryBarrier();
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev_value;
+ do {
+ if (OSAtomicCompareAndSwap32Barrier(old_value, new_value,
+ const_cast<Atomic32*>(ptr))) {
+ return old_value;
+ }
+ prev_value = *ptr;
+ } while (prev_value == old_value);
+ return prev_value;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return Acquire_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ MemoryBarrier();
+ *ptr = value;
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 value = *ptr;
+ MemoryBarrier();
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+#ifdef __LP64__
+
+// 64-bit implementation on 64-bit platform
+
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 prev_value;
+ do {
+ if (OSAtomicCompareAndSwap64(old_value, new_value,
+ reinterpret_cast<volatile int64_t*>(ptr))) {
+ return old_value;
+ }
+ prev_value = *ptr;
+ } while (prev_value == old_value);
+ return prev_value;
+}
+
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr,
+ Atomic64 new_value) {
+ Atomic64 old_value;
+ do {
+ old_value = *ptr;
+ } while (!OSAtomicCompareAndSwap64(old_value, new_value,
+ reinterpret_cast<volatile int64_t*>(ptr)));
+ return old_value;
+}
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ return OSAtomicAdd64(increment, reinterpret_cast<volatile int64_t*>(ptr));
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ return OSAtomicAdd64Barrier(increment,
+ reinterpret_cast<volatile int64_t*>(ptr));
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 prev_value;
+ do {
+ if (OSAtomicCompareAndSwap64Barrier(
+ old_value, new_value, reinterpret_cast<volatile int64_t*>(ptr))) {
+ return old_value;
+ }
+ prev_value = *ptr;
+ } while (prev_value == old_value);
+ return prev_value;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ // The lib kern interface does not distinguish between
+ // Acquire and Release memory barriers; they are equivalent.
+ return Acquire_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ MemoryBarrier();
+ *ptr = value;
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return *ptr;
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ Atomic64 value = *ptr;
+ MemoryBarrier();
+ return value;
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+#endif // defined(__LP64__)
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_MACOSX_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_mips_gcc.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_mips_gcc.h
new file mode 100644
index 0000000000..f5837c9ec2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_mips_gcc.h
@@ -0,0 +1,313 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_MIPS_GCC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_MIPS_GCC_H_
+
+#define ATOMICOPS_COMPILER_BARRIER() __asm__ __volatile__("" : : : "memory")
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Atomically execute:
+// result = *ptr;
+// if (*ptr == old_value)
+// *ptr = new_value;
+// return result;
+//
+// I.e., replace "*ptr" with "new_value" if "*ptr" used to be "old_value".
+// Always return the old value of "*ptr"
+//
+// This routine implies no memory barriers.
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev, tmp;
+ __asm__ __volatile__(".set push\n"
+ ".set noreorder\n"
+ "1:\n"
+ "ll %0, %5\n" // prev = *ptr
+ "bne %0, %3, 2f\n" // if (prev != old_value) goto 2
+ "move %2, %4\n" // tmp = new_value
+ "sc %2, %1\n" // *ptr = tmp (with atomic check)
+ "beqz %2, 1b\n" // start again on atomic error
+ "nop\n" // delay slot nop
+ "2:\n"
+ ".set pop\n"
+ : "=&r" (prev), "=m" (*ptr), "=&r" (tmp)
+ : "r" (old_value), "r" (new_value), "m" (*ptr)
+ : "memory");
+ return prev;
+}
+
+// Atomically store new_value into *ptr, returning the previous value held in
+// *ptr. This routine implies no memory barriers.
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ Atomic32 temp, old;
+ __asm__ __volatile__(".set push\n"
+ ".set noreorder\n"
+ "1:\n"
+ "ll %1, %4\n" // old = *ptr
+ "move %0, %3\n" // temp = new_value
+ "sc %0, %2\n" // *ptr = temp (with atomic check)
+ "beqz %0, 1b\n" // start again on atomic error
+ "nop\n" // delay slot nop
+ ".set pop\n"
+ : "=&r" (temp), "=&r" (old), "=m" (*ptr)
+ : "r" (new_value), "m" (*ptr)
+ : "memory");
+
+ return old;
+}
+
+// Atomically increment *ptr by "increment". Returns the new value of
+// *ptr with the increment applied. This routine implies no memory barriers.
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ Atomic32 temp, temp2;
+
+ __asm__ __volatile__(".set push\n"
+ ".set noreorder\n"
+ "1:\n"
+ "ll %0, %4\n" // temp = *ptr
+ "addu %1, %0, %3\n" // temp2 = temp + increment
+ "sc %1, %2\n" // *ptr = temp2 (with atomic check)
+ "beqz %1, 1b\n" // start again on atomic error
+ "addu %1, %0, %3\n" // temp2 = temp + increment
+ ".set pop\n"
+ : "=&r" (temp), "=&r" (temp2), "=m" (*ptr)
+ : "Ir" (increment), "m" (*ptr)
+ : "memory");
+ // temp2 now holds the final value.
+ return temp2;
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ ATOMICOPS_COMPILER_BARRIER();
+ Atomic32 res = NoBarrier_AtomicIncrement(ptr, increment);
+ ATOMICOPS_COMPILER_BARRIER();
+ return res;
+}
+
+// "Acquire" operations
+// ensure that no later memory access can be reordered ahead of the operation.
+// "Release" operations ensure that no previous memory access can be reordered
+// after the operation. "Barrier" operations have both "Acquire" and "Release"
+// semantics. A MemoryBarrier() has "Barrier" semantics, but does no memory
+// access.
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ ATOMICOPS_COMPILER_BARRIER();
+ Atomic32 res = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ ATOMICOPS_COMPILER_BARRIER();
+ return res;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ ATOMICOPS_COMPILER_BARRIER();
+ Atomic32 res = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ ATOMICOPS_COMPILER_BARRIER();
+ return res;
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void MemoryBarrier() {
+ __asm__ __volatile__("sync" : : : "memory");
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ MemoryBarrier();
+ *ptr = value;
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 value = *ptr;
+ MemoryBarrier();
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+#if defined(__LP64__)
+// 64-bit versions of the atomic ops.
+
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 prev, tmp;
+ __asm__ __volatile__(".set push\n"
+ ".set noreorder\n"
+ "1:\n"
+ "lld %0, %5\n" // prev = *ptr
+ "bne %0, %3, 2f\n" // if (prev != old_value) goto 2
+ "move %2, %4\n" // tmp = new_value
+ "scd %2, %1\n" // *ptr = tmp (with atomic check)
+ "beqz %2, 1b\n" // start again on atomic error
+ "nop\n" // delay slot nop
+ "2:\n"
+ ".set pop\n"
+ : "=&r" (prev), "=m" (*ptr), "=&r" (tmp)
+ : "r" (old_value), "r" (new_value), "m" (*ptr)
+ : "memory");
+ return prev;
+}
+
+// Atomically store new_value into *ptr, returning the previous value held in
+// *ptr. This routine implies no memory barriers.
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr,
+ Atomic64 new_value) {
+ Atomic64 temp, old;
+ __asm__ __volatile__(".set push\n"
+ ".set noreorder\n"
+ "1:\n"
+ "lld %1, %4\n" // old = *ptr
+ "move %0, %3\n" // temp = new_value
+ "scd %0, %2\n" // *ptr = temp (with atomic check)
+ "beqz %0, 1b\n" // start again on atomic error
+ "nop\n" // delay slot nop
+ ".set pop\n"
+ : "=&r" (temp), "=&r" (old), "=m" (*ptr)
+ : "r" (new_value), "m" (*ptr)
+ : "memory");
+
+ return old;
+}
+
+// Atomically increment *ptr by "increment". Returns the new value of
+// *ptr with the increment applied. This routine implies no memory barriers.
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ Atomic64 temp, temp2;
+
+ __asm__ __volatile__(".set push\n"
+ ".set noreorder\n"
+ "1:\n"
+ "lld %0, %4\n" // temp = *ptr
+ "daddu %1, %0, %3\n" // temp2 = temp + increment
+ "scd %1, %2\n" // *ptr = temp2 (with atomic check)
+ "beqz %1, 1b\n" // start again on atomic error
+ "daddu %1, %0, %3\n" // temp2 = temp + increment
+ ".set pop\n"
+ : "=&r" (temp), "=&r" (temp2), "=m" (*ptr)
+ : "Ir" (increment), "m" (*ptr)
+ : "memory");
+ // temp2 now holds the final value.
+ return temp2;
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ MemoryBarrier();
+ Atomic64 res = NoBarrier_AtomicIncrement(ptr, increment);
+ MemoryBarrier();
+ return res;
+}
+
+// "Acquire" operations
+// ensure that no later memory access can be reordered ahead of the operation.
+// "Release" operations ensure that no previous memory access can be reordered
+// after the operation. "Barrier" operations have both "Acquire" and "Release"
+// semantics. A MemoryBarrier() has "Barrier" semantics, but does no memory
+// access.
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 res = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ MemoryBarrier();
+ return res;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ MemoryBarrier();
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ MemoryBarrier();
+ *ptr = value;
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return *ptr;
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ Atomic64 value = *ptr;
+ MemoryBarrier();
+ return value;
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+#endif
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#undef ATOMICOPS_COMPILER_BARRIER
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_MIPS_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_pnacl.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_pnacl.h
new file mode 100644
index 0000000000..3b314fd0c9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_pnacl.h
@@ -0,0 +1,231 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_PNACL_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_PNACL_H_
+
+#include <atomic>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// This implementation is transitional and maintains the original API for
+// atomicops.h. This requires casting memory locations to the atomic types, and
+// assumes that the API and the C++11 implementation are layout-compatible,
+// which isn't true for all implementations or hardware platforms. The static
+// assertion should detect this issue, were it to fire then this header
+// shouldn't be used.
+//
+// TODO(jfb) If this header manages to stay committed then the API should be
+// modified, and all call sites updated.
+typedef volatile std::atomic<Atomic32>* AtomicLocation32;
+static_assert(sizeof(*(AtomicLocation32) nullptr) == sizeof(Atomic32),
+ "incompatible 32-bit atomic layout");
+
+inline void MemoryBarrier() {
+#if defined(__GLIBCXX__)
+ // Work around libstdc++ bug 51038 where atomic_thread_fence was declared but
+ // not defined, leading to the linker complaining about undefined references.
+ __atomic_thread_fence(std::memory_order_seq_cst);
+#else
+ std::atomic_thread_fence(std::memory_order_seq_cst);
+#endif
+}
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ ((AtomicLocation32)ptr)
+ ->compare_exchange_strong(old_value,
+ new_value,
+ std::memory_order_relaxed,
+ std::memory_order_relaxed);
+ return old_value;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ return ((AtomicLocation32)ptr)
+ ->exchange(new_value, std::memory_order_relaxed);
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return increment +
+ ((AtomicLocation32)ptr)
+ ->fetch_add(increment, std::memory_order_relaxed);
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return increment + ((AtomicLocation32)ptr)->fetch_add(increment);
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ ((AtomicLocation32)ptr)
+ ->compare_exchange_strong(old_value,
+ new_value,
+ std::memory_order_acquire,
+ std::memory_order_acquire);
+ return old_value;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ ((AtomicLocation32)ptr)
+ ->compare_exchange_strong(old_value,
+ new_value,
+ std::memory_order_release,
+ std::memory_order_relaxed);
+ return old_value;
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ ((AtomicLocation32)ptr)->store(value, std::memory_order_relaxed);
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ ((AtomicLocation32)ptr)->store(value, std::memory_order_relaxed);
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ ((AtomicLocation32)ptr)->store(value, std::memory_order_release);
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return ((AtomicLocation32)ptr)->load(std::memory_order_relaxed);
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ return ((AtomicLocation32)ptr)->load(std::memory_order_acquire);
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return ((AtomicLocation32)ptr)->load(std::memory_order_relaxed);
+}
+
+#if defined(GOOGLE_PROTOBUF_ARCH_64_BIT)
+
+typedef volatile std::atomic<Atomic64>* AtomicLocation64;
+static_assert(sizeof(*(AtomicLocation64) nullptr) == sizeof(Atomic64),
+ "incompatible 64-bit atomic layout");
+
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ ((AtomicLocation64)ptr)
+ ->compare_exchange_strong(old_value,
+ new_value,
+ std::memory_order_relaxed,
+ std::memory_order_relaxed);
+ return old_value;
+}
+
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr,
+ Atomic64 new_value) {
+ return ((AtomicLocation64)ptr)
+ ->exchange(new_value, std::memory_order_relaxed);
+}
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ return increment +
+ ((AtomicLocation64)ptr)
+ ->fetch_add(increment, std::memory_order_relaxed);
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ return increment + ((AtomicLocation64)ptr)->fetch_add(increment);
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ ((AtomicLocation64)ptr)
+ ->compare_exchange_strong(old_value,
+ new_value,
+ std::memory_order_acquire,
+ std::memory_order_acquire);
+ return old_value;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ ((AtomicLocation64)ptr)
+ ->compare_exchange_strong(old_value,
+ new_value,
+ std::memory_order_release,
+ std::memory_order_relaxed);
+ return old_value;
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ ((AtomicLocation64)ptr)->store(value, std::memory_order_relaxed);
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ ((AtomicLocation64)ptr)->store(value, std::memory_order_relaxed);
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ ((AtomicLocation64)ptr)->store(value, std::memory_order_release);
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return ((AtomicLocation64)ptr)->load(std::memory_order_relaxed);
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ return ((AtomicLocation64)ptr)->load(std::memory_order_acquire);
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ MemoryBarrier();
+ return ((AtomicLocation64)ptr)->load(std::memory_order_relaxed);
+}
+
+#endif // defined(GOOGLE_PROTOBUF_ARCH_64_BIT)
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_PNACL_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_power.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_power.h
new file mode 100644
index 0000000000..b8a42f21f0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_power.h
@@ -0,0 +1,440 @@
+// Copyright 2014 Bloomberg Finance LP. All rights reserved.
+//
+// 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 Bloomberg Finance LP. 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_AIX_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_AIX_H_
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 result;
+
+ asm volatile (
+ "1: lwarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " cmpw %[cmp], %[res] \n\t" // compare values
+ " bne- 2f \n\t"
+ " stwcx. %[val], %[zero], %[obj] \n\t" // store new value
+ " bne- 1b \n\t"
+ "2: \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [cmp] "b" (old_value),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ Atomic32 result;
+
+ asm volatile (
+ "1: lwarx %[res], %[zero], %[obj] \n\t"
+ " stwcx. %[val], %[zero], %[obj] \n\t"
+ " bne- 1b \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ Atomic32 result;
+
+ asm volatile (
+ "1: lwarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " add %[res], %[val], %[res] \n\t" // add the operand
+ " stwcx. %[res], %[zero], %[obj] \n\t" // store old value
+ // if still reserved
+ " bne- 1b \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [val] "b" (increment),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline void MemoryBarrier(void) {
+ asm volatile (
+ " lwsync \n\t"
+ " isync \n\t"
+ :
+ :
+ : "memory");
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ Atomic32 result;
+
+ asm volatile (
+ " lwsync \n\t"
+
+ "1: lwarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " add %[res], %[val], %[res] \n\t" // add the operand
+ " stwcx. %[res], %[zero], %[obj] \n\t" // store old value
+ // if still reserved
+ " bne- 1b \n\t"
+ " isync \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [val] "b" (increment),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 result;
+
+ asm volatile (
+ "1: lwarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " cmpw %[cmp], %[res] \n\t" // compare values
+ " bne- 2f \n\t"
+ " stwcx. %[val], %[zero], %[obj] \n\t" // store new value
+ " bne- 1b \n\t"
+
+ " isync \n\t"
+ "2: \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [cmp] "b" (old_value),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 result;
+
+ asm volatile (
+ " lwsync \n\t"
+
+ "1: lwarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " cmpw %[cmp], %[res] \n\t" // compare values
+ " bne- 2f \n\t"
+ " stwcx. %[val], %[zero], %[obj] \n\t" // store new value
+ " bne- 1b \n\t"
+
+ "2: \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [cmp] "b" (old_value),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ asm volatile (
+ " stw %[val], %[obj] \n\t"
+ " isync \n\t"
+ : [obj] "=m" (*ptr)
+ : [val] "b" (value));
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ asm volatile (
+ " lwsync \n\t"
+ " stw %[val], %[obj] \n\t"
+ : [obj] "=m" (*ptr)
+ : [val] "b" (value));
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 result;
+
+ asm volatile (
+ "1: lwz %[res], %[obj] \n\t"
+ " cmpw %[res], %[res] \n\t" // create data
+ // dependency for
+ // load/load ordering
+ " bne- 1b \n\t" // never taken
+
+ " isync \n\t"
+ : [res] "=b" (result)
+ : [obj] "m" (*ptr),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ Atomic32 result;
+
+ asm volatile (
+ " lwsync \n\t"
+
+ "1: lwz %[res], %[obj] \n\t"
+ " cmpw %[res], %[res] \n\t" // create data
+ // dependency for
+ // load/load ordering
+ " bne- 1b \n\t" // never taken
+ : [res] "=b" (result)
+ : [obj] "m" (*ptr),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+#ifdef GOOGLE_PROTOBUF_ARCH_64_BIT
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 result;
+
+ asm volatile (
+ "1: ldarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " cmpd %[cmp], %[res] \n\t" // compare values
+ " bne- 2f \n\t"
+
+ " stdcx. %[val], %[zero], %[obj] \n\t" // store the new value
+ " bne- 1b \n\t"
+ "2: \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [cmp] "b" (old_value),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr,
+ Atomic64 new_value) {
+ Atomic64 result;
+
+ asm volatile (
+ "1: ldarx %[res], %[zero], %[obj] \n\t"
+ " stdcx. %[val], %[zero], %[obj] \n\t"
+ " bne- 1b \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ Atomic64 result;
+
+ asm volatile (
+ "1: ldarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " add %[res], %[res], %[val] \n\t" // add the operand
+ " stdcx. %[res], %[zero], %[obj] \n\t" // store old value if
+ // still reserved
+
+ " bne- 1b \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [val] "b" (increment),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+
+ Atomic64 result;
+
+ asm volatile (
+ " lwsync \n\t"
+
+ "1: ldarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " add %[res], %[res], %[val] \n\t" // add the operand
+ " stdcx. %[res], %[zero], %[obj] \n\t" // store old value if
+ // still reserved
+
+ " bne- 1b \n\t"
+
+ " isync \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [val] "b" (increment),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 result;
+
+ asm volatile (
+ "1: ldarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " cmpd %[cmp], %[res] \n\t" // compare values
+ " bne- 2f \n\t"
+
+ " stdcx. %[val], %[zero], %[obj] \n\t" // store the new value
+ " bne- 1b \n\t"
+ " isync \n\t"
+ "2: \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [cmp] "b" (old_value),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 result;
+
+ asm volatile (
+ " lwsync \n\t"
+
+ "1: ldarx %[res], %[zero], %[obj] \n\t" // load and reserve
+ " cmpd %[cmp], %[res] \n\t" // compare values
+ " bne- 2f \n\t"
+
+ " stdcx. %[val], %[zero], %[obj] \n\t" // store the new value
+ " bne- 1b \n\t"
+ "2: \n\t"
+ : [res] "=&b" (result)
+ : [obj] "b" (ptr),
+ [cmp] "b" (old_value),
+ [val] "b" (new_value),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ asm volatile (
+ " std %[val], %[obj] \n\t"
+ " isync \n\t"
+ : [obj] "=m" (*ptr)
+ : [val] "b" (value));
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ asm volatile (
+ " lwsync \n\t"
+ " std %[val], %[obj] \n\t"
+ : [obj] "=m" (*ptr)
+ : [val] "b" (value));
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return *ptr;
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ Atomic64 result;
+
+ asm volatile (
+ "1: ld %[res], %[obj] \n\t"
+ " cmpd %[res], %[res] \n\t" // create data
+ // dependency for
+ // load/load ordering
+ " bne- 1b \n\t" // never taken
+
+ " isync \n\t"
+ : [res] "=b" (result)
+ : [obj] "m" (*ptr),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ Atomic64 result;
+
+ asm volatile (
+ " lwsync \n\t"
+
+ "1: ld %[res], %[obj] \n\t"
+ " cmpd %[res], %[res] \n\t" // create data
+ // dependency for
+ // load/load ordering
+ " bne- 1b \n\t" // never taken
+ : [res] "=b" (result)
+ : [obj] "m" (*ptr),
+ [zero] "i" (0)
+ : "cr0", "ctr");
+
+ return result;
+}
+#endif
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_SPARC_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_ppc_gcc.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_ppc_gcc.h
new file mode 100644
index 0000000000..8231a578f3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_ppc_gcc.h
@@ -0,0 +1,155 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2015 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: ogabbay@advaoptical.com (Oded Gabbay)
+// Cleaned up by: bsilver16384@gmail.com (Brian Silverman)
+//
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_PPC_GCC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_PPC_GCC_H_
+
+#define ATOMICOPS_COMPILER_BARRIER() __asm__ __volatile__("" : : : "memory")
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32 *ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev;
+
+ __asm__ __volatile__(
+ "0: \n\t"
+ "lwarx %[prev],0,%[ptr] \n\t"
+ "cmpw 0,%[prev],%[old_value] \n\t"
+ "bne- 1f \n\t"
+ "stwcx. %[new_value],0,%[ptr] \n\t"
+ "bne- 0b \n\t"
+ "1: \n\t"
+ : [prev] "=&r"(prev), "+m"(*ptr)
+ : [ptr] "r"(ptr), [old_value] "r"(old_value), [new_value] "r"(new_value)
+ : "cc", "memory");
+
+ return prev;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32 *ptr,
+ Atomic32 new_value) {
+ Atomic32 old;
+
+ __asm__ __volatile__(
+ "0: \n\t"
+ "lwarx %[old],0,%[ptr] \n\t"
+ "stwcx. %[new_value],0,%[ptr] \n\t"
+ "bne- 0b \n\t"
+ : [old] "=&r"(old), "+m"(*ptr)
+ : [ptr] "r"(ptr), [new_value] "r"(new_value)
+ : "cc", "memory");
+
+ return old;
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32 *ptr,
+ Atomic32 increment) {
+ Atomic32 temp;
+
+ __asm__ __volatile__(
+ "0: \n\t"
+ "lwarx %[temp],0,%[ptr] \n\t"
+ "add %[temp],%[increment],%[temp] \n\t"
+ "stwcx. %[temp],0,%[ptr] \n\t"
+ "bne- 0b \n\t"
+ : [temp] "=&r"(temp)
+ : [increment] "r"(increment), [ptr] "r"(ptr)
+ : "cc", "memory");
+
+ return temp;
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32 *ptr,
+ Atomic32 increment) {
+ MemoryBarrier();
+ Atomic32 res = NoBarrier_AtomicIncrement(ptr, increment);
+ MemoryBarrier();
+ return res;
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32 *ptr,
+ Atomic32 old_value, Atomic32 new_value) {
+ Atomic32 res = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ MemoryBarrier();
+ return res;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32 *ptr,
+ Atomic32 old_value, Atomic32 new_value) {
+ MemoryBarrier();
+ Atomic32 res = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ return res;
+}
+
+inline void NoBarrier_Store(volatile Atomic32 *ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void MemoryBarrier() { __asm__ __volatile__("sync" : : : "memory"); }
+
+inline void Acquire_Store(volatile Atomic32 *ptr, Atomic32 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic32 *ptr, Atomic32 value) {
+ MemoryBarrier();
+ *ptr = value;
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32 *ptr) { return *ptr; }
+
+inline Atomic32 Acquire_Load(volatile const Atomic32 *ptr) {
+ Atomic32 value = *ptr;
+ MemoryBarrier();
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32 *ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#undef ATOMICOPS_COMPILER_BARRIER
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_PPC_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_solaris.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_solaris.h
new file mode 100644
index 0000000000..d8057ecdea
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_solaris.h
@@ -0,0 +1,188 @@
+// Copyright 2014 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_SPARC_GCC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_SPARC_GCC_H_
+
+#include <atomic.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return (Atomic32)atomic_cas_32((volatile uint32_t*)ptr, (uint32_t)old_value, (uint32_t)new_value);
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ return (Atomic32)atomic_swap_32((volatile uint32_t*)ptr, (uint32_t)new_value);
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return (Atomic32)atomic_add_32_nv((volatile uint32_t*)ptr, (uint32_t)increment);
+}
+
+inline void MemoryBarrier(void) {
+ membar_producer();
+ membar_consumer();
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ MemoryBarrier();
+ Atomic32 ret = NoBarrier_AtomicIncrement(ptr, increment);
+ MemoryBarrier();
+
+ return ret;
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 ret = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ MemoryBarrier();
+
+ return ret;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ MemoryBarrier();
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+ membar_producer();
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ membar_consumer();
+ *ptr = value;
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 val = *ptr;
+ membar_consumer();
+ return val;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ membar_producer();
+ return *ptr;
+}
+
+#ifdef GOOGLE_PROTOBUF_ARCH_64_BIT
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ return atomic_cas_64((volatile uint64_t*)ptr, (uint64_t)old_value, (uint64_t)new_value);
+}
+
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr, Atomic64 new_value) {
+ return atomic_swap_64((volatile uint64_t*)ptr, (uint64_t)new_value);
+}
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr, Atomic64 increment) {
+ return atomic_add_64_nv((volatile uint64_t*)ptr, increment);
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr, Atomic64 increment) {
+ MemoryBarrier();
+ Atomic64 ret = atomic_add_64_nv((volatile uint64_t*)ptr, increment);
+ MemoryBarrier();
+ return ret;
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 ret = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ MemoryBarrier();
+ return ret;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ MemoryBarrier();
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+ membar_producer();
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ membar_consumer();
+ *ptr = value;
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return *ptr;
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ Atomic64 ret = *ptr;
+ membar_consumer();
+ return ret;
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ membar_producer();
+ return *ptr;
+}
+#endif
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_SPARC_GCC_H_
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_tsan.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_tsan.h
new file mode 100644
index 0000000000..0c903545cd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_tsan.h
@@ -0,0 +1,219 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2013 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.
+
+// This file is an internal atomic implementation for compiler-based
+// ThreadSanitizer (http://clang.llvm.org/docs/ThreadSanitizer.html).
+// Use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_TSAN_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_TSAN_H_
+
+#define ATOMICOPS_COMPILER_BARRIER() __asm__ __volatile__("" : : : "memory")
+
+#include <sanitizer/tsan_interface_atomic.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32 *ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 cmp = old_value;
+ __tsan_atomic32_compare_exchange_strong(ptr, &cmp, new_value,
+ __tsan_memory_order_relaxed, __tsan_memory_order_relaxed);
+ return cmp;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32 *ptr,
+ Atomic32 new_value) {
+ return __tsan_atomic32_exchange(ptr, new_value,
+ __tsan_memory_order_relaxed);
+}
+
+inline Atomic32 Acquire_AtomicExchange(volatile Atomic32 *ptr,
+ Atomic32 new_value) {
+ return __tsan_atomic32_exchange(ptr, new_value,
+ __tsan_memory_order_acquire);
+}
+
+inline Atomic32 Release_AtomicExchange(volatile Atomic32 *ptr,
+ Atomic32 new_value) {
+ return __tsan_atomic32_exchange(ptr, new_value,
+ __tsan_memory_order_release);
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32 *ptr,
+ Atomic32 increment) {
+ return increment + __tsan_atomic32_fetch_add(ptr, increment,
+ __tsan_memory_order_relaxed);
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32 *ptr,
+ Atomic32 increment) {
+ return increment + __tsan_atomic32_fetch_add(ptr, increment,
+ __tsan_memory_order_acq_rel);
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32 *ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 cmp = old_value;
+ __tsan_atomic32_compare_exchange_strong(ptr, &cmp, new_value,
+ __tsan_memory_order_acquire, __tsan_memory_order_acquire);
+ return cmp;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32 *ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 cmp = old_value;
+ __tsan_atomic32_compare_exchange_strong(ptr, &cmp, new_value,
+ __tsan_memory_order_release, __tsan_memory_order_relaxed);
+ return cmp;
+}
+
+inline void NoBarrier_Store(volatile Atomic32 *ptr, Atomic32 value) {
+ __tsan_atomic32_store(ptr, value, __tsan_memory_order_relaxed);
+}
+
+inline void Acquire_Store(volatile Atomic32 *ptr, Atomic32 value) {
+ __tsan_atomic32_store(ptr, value, __tsan_memory_order_relaxed);
+ __tsan_atomic_thread_fence(__tsan_memory_order_seq_cst);
+}
+
+inline void Release_Store(volatile Atomic32 *ptr, Atomic32 value) {
+ __tsan_atomic32_store(ptr, value, __tsan_memory_order_release);
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32 *ptr) {
+ return __tsan_atomic32_load(ptr, __tsan_memory_order_relaxed);
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32 *ptr) {
+ return __tsan_atomic32_load(ptr, __tsan_memory_order_acquire);
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32 *ptr) {
+ __tsan_atomic_thread_fence(__tsan_memory_order_seq_cst);
+ return __tsan_atomic32_load(ptr, __tsan_memory_order_relaxed);
+}
+
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64 *ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 cmp = old_value;
+ __tsan_atomic64_compare_exchange_strong(ptr, &cmp, new_value,
+ __tsan_memory_order_relaxed, __tsan_memory_order_relaxed);
+ return cmp;
+}
+
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64 *ptr,
+ Atomic64 new_value) {
+ return __tsan_atomic64_exchange(ptr, new_value, __tsan_memory_order_relaxed);
+}
+
+inline Atomic64 Acquire_AtomicExchange(volatile Atomic64 *ptr,
+ Atomic64 new_value) {
+ return __tsan_atomic64_exchange(ptr, new_value, __tsan_memory_order_acquire);
+}
+
+inline Atomic64 Release_AtomicExchange(volatile Atomic64 *ptr,
+ Atomic64 new_value) {
+ return __tsan_atomic64_exchange(ptr, new_value, __tsan_memory_order_release);
+}
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64 *ptr,
+ Atomic64 increment) {
+ return increment + __tsan_atomic64_fetch_add(ptr, increment,
+ __tsan_memory_order_relaxed);
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64 *ptr,
+ Atomic64 increment) {
+ return increment + __tsan_atomic64_fetch_add(ptr, increment,
+ __tsan_memory_order_acq_rel);
+}
+
+inline void NoBarrier_Store(volatile Atomic64 *ptr, Atomic64 value) {
+ __tsan_atomic64_store(ptr, value, __tsan_memory_order_relaxed);
+}
+
+inline void Acquire_Store(volatile Atomic64 *ptr, Atomic64 value) {
+ __tsan_atomic64_store(ptr, value, __tsan_memory_order_relaxed);
+ __tsan_atomic_thread_fence(__tsan_memory_order_seq_cst);
+}
+
+inline void Release_Store(volatile Atomic64 *ptr, Atomic64 value) {
+ __tsan_atomic64_store(ptr, value, __tsan_memory_order_release);
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64 *ptr) {
+ return __tsan_atomic64_load(ptr, __tsan_memory_order_relaxed);
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64 *ptr) {
+ return __tsan_atomic64_load(ptr, __tsan_memory_order_acquire);
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64 *ptr) {
+ __tsan_atomic_thread_fence(__tsan_memory_order_seq_cst);
+ return __tsan_atomic64_load(ptr, __tsan_memory_order_relaxed);
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64 *ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 cmp = old_value;
+ __tsan_atomic64_compare_exchange_strong(ptr, &cmp, new_value,
+ __tsan_memory_order_acquire, __tsan_memory_order_acquire);
+ return cmp;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64 *ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 cmp = old_value;
+ __tsan_atomic64_compare_exchange_strong(ptr, &cmp, new_value,
+ __tsan_memory_order_release, __tsan_memory_order_relaxed);
+ return cmp;
+}
+
+inline void MemoryBarrier() {
+ __tsan_atomic_thread_fence(__tsan_memory_order_seq_cst);
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#undef ATOMICOPS_COMPILER_BARRIER
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_TSAN_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.cc
new file mode 100644
index 0000000000..53c9eae0fa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.cc
@@ -0,0 +1,137 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This module gets enough CPU information to optimize the
+// atomicops module on x86.
+
+#include <cstring>
+
+#include <google/protobuf/stubs/atomicops.h>
+
+// This file only makes sense with atomicops_internals_x86_gcc.h -- it
+// depends on structs that are defined in that file. If atomicops.h
+// doesn't sub-include that file, then we aren't needed, and shouldn't
+// try to do anything.
+#ifdef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_GCC_H_
+
+// Inline cpuid instruction. In PIC compilations, %ebx contains the address
+// of the global offset table. To avoid breaking such executables, this code
+// must preserve that register's value across cpuid instructions.
+#if defined(__i386__)
+#define cpuid(a, b, c, d, inp) \
+ asm("mov %%ebx, %%edi\n" \
+ "cpuid\n" \
+ "xchg %%edi, %%ebx\n" \
+ : "=a" (a), "=D" (b), "=c" (c), "=d" (d) : "a" (inp))
+#elif defined(__x86_64__)
+#define cpuid(a, b, c, d, inp) \
+ asm("mov %%rbx, %%rdi\n" \
+ "cpuid\n" \
+ "xchg %%rdi, %%rbx\n" \
+ : "=a" (a), "=D" (b), "=c" (c), "=d" (d) : "a" (inp))
+#endif
+
+#if defined(cpuid) // initialize the struct only on x86
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Set the flags so that code will run correctly and conservatively, so even
+// if we haven't been initialized yet, we're probably single threaded, and our
+// default values should hopefully be pretty safe.
+struct AtomicOps_x86CPUFeatureStruct AtomicOps_Internalx86CPUFeatures = {
+ false, // bug can't exist before process spawns multiple threads
+ false, // no SSE2
+};
+
+namespace {
+
+// Initialize the AtomicOps_Internalx86CPUFeatures struct.
+void AtomicOps_Internalx86CPUFeaturesInit() {
+ uint32_t eax;
+ uint32_t ebx;
+ uint32_t ecx;
+ uint32_t edx;
+
+ // Get vendor string (issue CPUID with eax = 0)
+ cpuid(eax, ebx, ecx, edx, 0);
+ char vendor[13];
+ memcpy(vendor, &ebx, 4);
+ memcpy(vendor + 4, &edx, 4);
+ memcpy(vendor + 8, &ecx, 4);
+ vendor[12] = 0;
+
+ // get feature flags in ecx/edx, and family/model in eax
+ cpuid(eax, ebx, ecx, edx, 1);
+
+ int family = (eax >> 8) & 0xf; // family and model fields
+ int model = (eax >> 4) & 0xf;
+ if (family == 0xf) { // use extended family and model fields
+ family += (eax >> 20) & 0xff;
+ model += ((eax >> 16) & 0xf) << 4;
+ }
+
+ // Opteron Rev E has a bug in which on very rare occasions a locked
+ // instruction doesn't act as a read-acquire barrier if followed by a
+ // non-locked read-modify-write instruction. Rev F has this bug in
+ // pre-release versions, but not in versions released to customers,
+ // so we test only for Rev E, which is family 15, model 32..63 inclusive.
+ if (strcmp(vendor, "AuthenticAMD") == 0 && // AMD
+ family == 15 &&
+ 32 <= model && model <= 63) {
+ AtomicOps_Internalx86CPUFeatures.has_amd_lock_mb_bug = true;
+ } else {
+ AtomicOps_Internalx86CPUFeatures.has_amd_lock_mb_bug = false;
+ }
+
+ // edx bit 26 is SSE2 which we use to tell use whether we can use mfence
+ AtomicOps_Internalx86CPUFeatures.has_sse2 = ((edx >> 26) & 1);
+}
+
+class AtomicOpsx86Initializer {
+ public:
+ AtomicOpsx86Initializer() {
+ AtomicOps_Internalx86CPUFeaturesInit();
+ }
+};
+
+// A global to get use initialized on startup via static initialization :/
+AtomicOpsx86Initializer g_initer;
+
+} // namespace
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // __i386__
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.h
new file mode 100644
index 0000000000..edccc59dee
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_gcc.h
@@ -0,0 +1,293 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_GCC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_GCC_H_
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// This struct is not part of the public API of this module; clients may not
+// use it.
+// Features of this x86. Values may not be correct before main() is run,
+// but are set conservatively.
+struct AtomicOps_x86CPUFeatureStruct {
+ bool has_amd_lock_mb_bug; // Processor has AMD memory-barrier bug; do lfence
+ // after acquire compare-and-swap.
+ bool has_sse2; // Processor has SSE2.
+};
+extern struct AtomicOps_x86CPUFeatureStruct AtomicOps_Internalx86CPUFeatures;
+
+#define ATOMICOPS_COMPILER_BARRIER() __asm__ __volatile__("" : : : "memory")
+
+// 32-bit low-level operations on any platform.
+
+inline Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 prev;
+ __asm__ __volatile__("lock; cmpxchgl %1,%2"
+ : "=a" (prev)
+ : "q" (new_value), "m" (*ptr), "0" (old_value)
+ : "memory");
+ return prev;
+}
+
+inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ __asm__ __volatile__("xchgl %1,%0" // The lock prefix is implicit for xchg.
+ : "=r" (new_value)
+ : "m" (*ptr), "0" (new_value)
+ : "memory");
+ return new_value; // Now it's the previous value.
+}
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ Atomic32 temp = increment;
+ __asm__ __volatile__("lock; xaddl %0,%1"
+ : "+r" (temp), "+m" (*ptr)
+ : : "memory");
+ // temp now holds the old value of *ptr
+ return temp + increment;
+}
+
+inline Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ Atomic32 temp = increment;
+ __asm__ __volatile__("lock; xaddl %0,%1"
+ : "+r" (temp), "+m" (*ptr)
+ : : "memory");
+ // temp now holds the old value of *ptr
+ if (AtomicOps_Internalx86CPUFeatures.has_amd_lock_mb_bug) {
+ __asm__ __volatile__("lfence" : : : "memory");
+ }
+ return temp + increment;
+}
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ Atomic32 x = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ if (AtomicOps_Internalx86CPUFeatures.has_amd_lock_mb_bug) {
+ __asm__ __volatile__("lfence" : : : "memory");
+ }
+ return x;
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+#if defined(__x86_64__)
+
+// 64-bit implementations of memory barrier can be simpler, because it
+// "mfence" is guaranteed to exist.
+inline void MemoryBarrier() {
+ __asm__ __volatile__("mfence" : : : "memory");
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+#else
+
+inline void MemoryBarrier() {
+ if (AtomicOps_Internalx86CPUFeatures.has_sse2) {
+ __asm__ __volatile__("mfence" : : : "memory");
+ } else { // mfence is faster but not present on PIII
+ Atomic32 x = 0;
+ NoBarrier_AtomicExchange(&x, 0); // acts as a barrier on PIII
+ }
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ if (AtomicOps_Internalx86CPUFeatures.has_sse2) {
+ *ptr = value;
+ __asm__ __volatile__("mfence" : : : "memory");
+ } else {
+ NoBarrier_AtomicExchange(ptr, value);
+ // acts as a barrier on PIII
+ }
+}
+#endif
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ ATOMICOPS_COMPILER_BARRIER();
+ *ptr = value; // An x86 store acts as a release barrier.
+ // See comments in Atomic64 version of Release_Store(), below.
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 value = *ptr; // An x86 load acts as a acquire barrier.
+ // See comments in Atomic64 version of Release_Store(), below.
+ ATOMICOPS_COMPILER_BARRIER();
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+#if defined(__x86_64__)
+
+// 64-bit low-level operations on 64-bit platform.
+
+inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 prev;
+ __asm__ __volatile__("lock; cmpxchgq %1,%2"
+ : "=a" (prev)
+ : "q" (new_value), "m" (*ptr), "0" (old_value)
+ : "memory");
+ return prev;
+}
+
+inline Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr,
+ Atomic64 new_value) {
+ __asm__ __volatile__("xchgq %1,%0" // The lock prefix is implicit for xchg.
+ : "=r" (new_value)
+ : "m" (*ptr), "0" (new_value)
+ : "memory");
+ return new_value; // Now it's the previous value.
+}
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ Atomic64 temp = increment;
+ __asm__ __volatile__("lock; xaddq %0,%1"
+ : "+r" (temp), "+m" (*ptr)
+ : : "memory");
+ // temp now contains the previous value of *ptr
+ return temp + increment;
+}
+
+inline Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ Atomic64 temp = increment;
+ __asm__ __volatile__("lock; xaddq %0,%1"
+ : "+r" (temp), "+m" (*ptr)
+ : : "memory");
+ // temp now contains the previous value of *ptr
+ if (AtomicOps_Internalx86CPUFeatures.has_amd_lock_mb_bug) {
+ __asm__ __volatile__("lfence" : : : "memory");
+ }
+ return temp + increment;
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+ MemoryBarrier();
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ ATOMICOPS_COMPILER_BARRIER();
+
+ *ptr = value; // An x86 store acts as a release barrier
+ // for current AMD/Intel chips as of Jan 2008.
+ // See also Acquire_Load(), below.
+
+ // When new chips come out, check:
+ // IA-32 Intel Architecture Software Developer's Manual, Volume 3:
+ // System Programming Guide, Chatper 7: Multiple-processor management,
+ // Section 7.2, Memory Ordering.
+ // Last seen at:
+ // http://developer.intel.com/design/pentium4/manuals/index_new.htm
+ //
+ // x86 stores/loads fail to act as barriers for a few instructions (clflush
+ // maskmovdqu maskmovq movntdq movnti movntpd movntps movntq) but these are
+ // not generated by the compiler, and are rare. Users of these instructions
+ // need to know about cache behaviour in any case since all of these involve
+ // either flushing cache lines or non-temporal cache hints.
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return *ptr;
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ Atomic64 value = *ptr; // An x86 load acts as a acquire barrier,
+ // for current AMD/Intel chips as of Jan 2008.
+ // See also Release_Store(), above.
+ ATOMICOPS_COMPILER_BARRIER();
+ return value;
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ Atomic64 x = NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+ if (AtomicOps_Internalx86CPUFeatures.has_amd_lock_mb_bug) {
+ __asm__ __volatile__("lfence" : : : "memory");
+ }
+ return x;
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+#endif // defined(__x86_64__)
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#undef ATOMICOPS_COMPILER_BARRIER
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_GCC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.cc
new file mode 100644
index 0000000000..741b164f0f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.cc
@@ -0,0 +1,112 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// The compilation of extension_set.cc fails when windows.h is included.
+// Therefore we move the code depending on windows.h to this separate cc file.
+
+// Don't compile this file for people not concerned about thread safety.
+#ifndef GOOGLE_PROTOBUF_NO_THREAD_SAFETY
+
+#include <google/protobuf/stubs/atomicops.h>
+
+#ifdef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_MSVC_H_
+
+#include <windows.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline void MemoryBarrier() {
+ // We use MemoryBarrier from WinNT.h
+ ::MemoryBarrier();
+}
+
+Atomic32 NoBarrier_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ LONG result = InterlockedCompareExchange(
+ reinterpret_cast<volatile LONG*>(ptr),
+ static_cast<LONG>(new_value),
+ static_cast<LONG>(old_value));
+ return static_cast<Atomic32>(result);
+}
+
+Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr,
+ Atomic32 new_value) {
+ LONG result = InterlockedExchange(
+ reinterpret_cast<volatile LONG*>(ptr),
+ static_cast<LONG>(new_value));
+ return static_cast<Atomic32>(result);
+}
+
+Atomic32 Barrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return InterlockedExchangeAdd(
+ reinterpret_cast<volatile LONG*>(ptr),
+ static_cast<LONG>(increment)) + increment;
+}
+
+#if defined(_WIN64)
+
+// 64-bit low-level operations on 64-bit platform.
+
+Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ PVOID result = InterlockedCompareExchangePointer(
+ reinterpret_cast<volatile PVOID*>(ptr),
+ reinterpret_cast<PVOID>(new_value), reinterpret_cast<PVOID>(old_value));
+ return reinterpret_cast<Atomic64>(result);
+}
+
+Atomic64 NoBarrier_AtomicExchange(volatile Atomic64* ptr,
+ Atomic64 new_value) {
+ PVOID result = InterlockedExchangePointer(
+ reinterpret_cast<volatile PVOID*>(ptr),
+ reinterpret_cast<PVOID>(new_value));
+ return reinterpret_cast<Atomic64>(result);
+}
+
+Atomic64 Barrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ return InterlockedExchangeAdd64(
+ reinterpret_cast<volatile LONGLONG*>(ptr),
+ static_cast<LONGLONG>(increment)) + increment;
+}
+
+#endif // defined(_WIN64)
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_MSVC_H_
+#endif // GOOGLE_PROTOBUF_NO_THREAD_SAFETY
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.h
new file mode 100644
index 0000000000..e53a641f09
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/atomicops_internals_x86_msvc.h
@@ -0,0 +1,150 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// This file is an internal atomic implementation, use atomicops.h instead.
+
+#ifndef GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_MSVC_H_
+#define GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_MSVC_H_
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+inline Atomic32 NoBarrier_AtomicIncrement(volatile Atomic32* ptr,
+ Atomic32 increment) {
+ return Barrier_AtomicIncrement(ptr, increment);
+}
+
+#if !(defined(_MSC_VER) && _MSC_VER >= 1400)
+#error "We require at least vs2005 for MemoryBarrier"
+#endif
+
+inline Atomic32 Acquire_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr,
+ Atomic32 old_value,
+ Atomic32 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline void NoBarrier_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) {
+ NoBarrier_AtomicExchange(ptr, value);
+ // acts as a barrier in this implementation
+}
+
+inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) {
+ *ptr = value; // works w/o barrier for current Intel chips as of June 2005
+ // See comments in Atomic64 version of Release_Store() below.
+}
+
+inline Atomic32 NoBarrier_Load(volatile const Atomic32* ptr) {
+ return *ptr;
+}
+
+inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) {
+ Atomic32 value = *ptr;
+ return value;
+}
+
+inline Atomic32 Release_Load(volatile const Atomic32* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+#if defined(_WIN64)
+
+// 64-bit low-level operations on 64-bit platform.
+
+inline Atomic64 NoBarrier_AtomicIncrement(volatile Atomic64* ptr,
+ Atomic64 increment) {
+ return Barrier_AtomicIncrement(ptr, increment);
+}
+
+inline void NoBarrier_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value;
+}
+
+inline void Acquire_Store(volatile Atomic64* ptr, Atomic64 value) {
+ NoBarrier_AtomicExchange(ptr, value);
+ // acts as a barrier in this implementation
+}
+
+inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) {
+ *ptr = value; // works w/o barrier for current Intel chips as of June 2005
+
+ // When new chips come out, check:
+ // IA-32 Intel Architecture Software Developer's Manual, Volume 3:
+ // System Programming Guide, Chatper 7: Multiple-processor management,
+ // Section 7.2, Memory Ordering.
+ // Last seen at:
+ // http://developer.intel.com/design/pentium4/manuals/index_new.htm
+}
+
+inline Atomic64 NoBarrier_Load(volatile const Atomic64* ptr) {
+ return *ptr;
+}
+
+inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) {
+ Atomic64 value = *ptr;
+ return value;
+}
+
+inline Atomic64 Release_Load(volatile const Atomic64* ptr) {
+ MemoryBarrier();
+ return *ptr;
+}
+
+inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+inline Atomic64 Release_CompareAndSwap(volatile Atomic64* ptr,
+ Atomic64 old_value,
+ Atomic64 new_value) {
+ return NoBarrier_CompareAndSwap(ptr, old_value, new_value);
+}
+
+#endif // defined(_WIN64)
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_ATOMICOPS_INTERNALS_X86_MSVC_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.cc
new file mode 100644
index 0000000000..f4af6a50ab
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.cc
@@ -0,0 +1,196 @@
+// 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.
+
+#include <google/protobuf/stubs/bytestream.h>
+
+#include <string.h>
+#include <algorithm>
+
+namespace google {
+namespace protobuf {
+namespace strings {
+
+void ByteSource::CopyTo(ByteSink* sink, size_t n) {
+ while (n > 0) {
+ StringPiece fragment = Peek();
+ if (fragment.empty()) {
+ GOOGLE_LOG(DFATAL) << "ByteSource::CopyTo() overran input.";
+ break;
+ }
+ std::size_t fragment_size = std::min<std::size_t>(n, fragment.size());
+ sink->Append(fragment.data(), fragment_size);
+ Skip(fragment_size);
+ n -= fragment_size;
+ }
+}
+
+void ByteSink::Flush() {}
+
+void UncheckedArrayByteSink::Append(const char* data, size_t n) {
+ if (data != dest_) {
+ // Catch cases where the pointer returned by GetAppendBuffer() was modified.
+ GOOGLE_DCHECK(!(dest_ <= data && data < (dest_ + n)))
+ << "Append() data[] overlaps with dest_[]";
+ memcpy(dest_, data, n);
+ }
+ dest_ += n;
+}
+
+CheckedArrayByteSink::CheckedArrayByteSink(char* outbuf, size_t capacity)
+ : outbuf_(outbuf), capacity_(capacity), size_(0), overflowed_(false) {
+}
+
+void CheckedArrayByteSink::Append(const char* bytes, size_t n) {
+ size_t available = capacity_ - size_;
+ if (n > available) {
+ n = available;
+ overflowed_ = true;
+ }
+ if (n > 0 && bytes != (outbuf_ + size_)) {
+ // Catch cases where the pointer returned by GetAppendBuffer() was modified.
+ GOOGLE_DCHECK(!(outbuf_ <= bytes && bytes < (outbuf_ + capacity_)))
+ << "Append() bytes[] overlaps with outbuf_[]";
+ memcpy(outbuf_ + size_, bytes, n);
+ }
+ size_ += n;
+}
+
+GrowingArrayByteSink::GrowingArrayByteSink(size_t estimated_size)
+ : capacity_(estimated_size),
+ buf_(new char[estimated_size]),
+ size_(0) {
+}
+
+GrowingArrayByteSink::~GrowingArrayByteSink() {
+ delete[] buf_; // Just in case the user didn't call GetBuffer.
+}
+
+void GrowingArrayByteSink::Append(const char* bytes, size_t n) {
+ size_t available = capacity_ - size_;
+ if (bytes != (buf_ + size_)) {
+ // Catch cases where the pointer returned by GetAppendBuffer() was modified.
+ // We need to test for this before calling Expand() which may reallocate.
+ GOOGLE_DCHECK(!(buf_ <= bytes && bytes < (buf_ + capacity_)))
+ << "Append() bytes[] overlaps with buf_[]";
+ }
+ if (n > available) {
+ Expand(n - available);
+ }
+ if (n > 0 && bytes != (buf_ + size_)) {
+ memcpy(buf_ + size_, bytes, n);
+ }
+ size_ += n;
+}
+
+char* GrowingArrayByteSink::GetBuffer(size_t* nbytes) {
+ ShrinkToFit();
+ char* b = buf_;
+ *nbytes = size_;
+ buf_ = NULL;
+ size_ = capacity_ = 0;
+ return b;
+}
+
+void GrowingArrayByteSink::Expand(size_t amount) { // Expand by at least 50%.
+ size_t new_capacity = std::max(capacity_ + amount, (3 * capacity_) / 2);
+ char* bigger = new char[new_capacity];
+ memcpy(bigger, buf_, size_);
+ delete[] buf_;
+ buf_ = bigger;
+ capacity_ = new_capacity;
+}
+
+void GrowingArrayByteSink::ShrinkToFit() {
+ // Shrink only if the buffer is large and size_ is less than 3/4
+ // of capacity_.
+ if (capacity_ > 256 && size_ < (3 * capacity_) / 4) {
+ char* just_enough = new char[size_];
+ memcpy(just_enough, buf_, size_);
+ delete[] buf_;
+ buf_ = just_enough;
+ capacity_ = size_;
+ }
+}
+
+void StringByteSink::Append(const char* data, size_t n) {
+ dest_->append(data, n);
+}
+
+size_t ArrayByteSource::Available() const {
+ return input_.size();
+}
+
+StringPiece ArrayByteSource::Peek() {
+ return input_;
+}
+
+void ArrayByteSource::Skip(size_t n) {
+ GOOGLE_DCHECK_LE(n, input_.size());
+ input_.remove_prefix(n);
+}
+
+LimitByteSource::LimitByteSource(ByteSource *source, size_t limit)
+ : source_(source),
+ limit_(limit) {
+}
+
+size_t LimitByteSource::Available() const {
+ size_t available = source_->Available();
+ if (available > limit_) {
+ available = limit_;
+ }
+
+ return available;
+}
+
+StringPiece LimitByteSource::Peek() {
+ StringPiece piece(source_->Peek());
+ if (piece.size() > limit_) {
+ piece.set(piece.data(), limit_);
+ }
+
+ return piece;
+}
+
+void LimitByteSource::Skip(size_t n) {
+ GOOGLE_DCHECK_LE(n, limit_);
+ source_->Skip(n);
+ limit_ -= n;
+}
+
+void LimitByteSource::CopyTo(ByteSink *sink, size_t n) {
+ GOOGLE_DCHECK_LE(n, limit_);
+ source_->CopyTo(sink, n);
+ limit_ -= n;
+}
+
+} // namespace strings
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.h
new file mode 100644
index 0000000000..07604e17a0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream.h
@@ -0,0 +1,348 @@
+// 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.
+
+// This file declares the ByteSink and ByteSource abstract interfaces. These
+// interfaces represent objects that consume (ByteSink) or produce (ByteSource)
+// a sequence of bytes. Using these abstract interfaces in your APIs can help
+// make your code work with a variety of input and output types.
+//
+// This file also declares the following commonly used implementations of these
+// interfaces.
+//
+// ByteSink:
+// UncheckedArrayByteSink Writes to an array, without bounds checking
+// CheckedArrayByteSink Writes to an array, with bounds checking
+// GrowingArrayByteSink Allocates and writes to a growable buffer
+// StringByteSink Writes to an STL string
+// NullByteSink Consumes a never-ending stream of bytes
+//
+// ByteSource:
+// ArrayByteSource Reads from an array or string/StringPiece
+// LimitedByteSource Limits the number of bytes read from an
+
+#ifndef GOOGLE_PROTOBUF_STUBS_BYTESTREAM_H_
+#define GOOGLE_PROTOBUF_STUBS_BYTESTREAM_H_
+
+#include <stddef.h>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+
+class CordByteSink;
+class MemBlock;
+
+namespace google {
+namespace protobuf {
+namespace strings {
+
+// An abstract interface for an object that consumes a sequence of bytes. This
+// interface offers 3 different ways to append data, and a Flush() function.
+//
+// Example:
+//
+// string my_data;
+// ...
+// ByteSink* sink = ...
+// sink->Append(my_data.data(), my_data.size());
+// sink->Flush();
+//
+class LIBPROTOBUF_EXPORT ByteSink {
+ public:
+ ByteSink() {}
+ virtual ~ByteSink() {}
+
+ // Appends the "n" bytes starting at "bytes".
+ virtual void Append(const char* bytes, size_t n) = 0;
+
+ // Flushes internal buffers. The default implemenation does nothing. ByteSink
+ // subclasses may use internal buffers that require calling Flush() at the end
+ // of the stream.
+ virtual void Flush();
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ByteSink);
+};
+
+// An abstract interface for an object that produces a fixed-size sequence of
+// bytes.
+//
+// Example:
+//
+// ByteSource* source = ...
+// while (source->Available() > 0) {
+// StringPiece data = source->Peek();
+// ... do something with "data" ...
+// source->Skip(data.length());
+// }
+//
+class LIBPROTOBUF_EXPORT ByteSource {
+ public:
+ ByteSource() {}
+ virtual ~ByteSource() {}
+
+ // Returns the number of bytes left to read from the source. Available()
+ // should decrease by N each time Skip(N) is called. Available() may not
+ // increase. Available() returning 0 indicates that the ByteSource is
+ // exhausted.
+ //
+ // Note: Size() may have been a more appropriate name as it's more
+ // indicative of the fixed-size nature of a ByteSource.
+ virtual size_t Available() const = 0;
+
+ // Returns a StringPiece of the next contiguous region of the source. Does not
+ // reposition the source. The returned region is empty iff Available() == 0.
+ //
+ // The returned region is valid until the next call to Skip() or until this
+ // object is destroyed, whichever occurs first.
+ //
+ // The length of the returned StringPiece will be <= Available().
+ virtual StringPiece Peek() = 0;
+
+ // Skips the next n bytes. Invalidates any StringPiece returned by a previous
+ // call to Peek().
+ //
+ // REQUIRES: Available() >= n
+ virtual void Skip(size_t n) = 0;
+
+ // Writes the next n bytes in this ByteSource to the given ByteSink, and
+ // advances this ByteSource past the copied bytes. The default implementation
+ // of this method just copies the bytes normally, but subclasses might
+ // override CopyTo to optimize certain cases.
+ //
+ // REQUIRES: Available() >= n
+ virtual void CopyTo(ByteSink* sink, size_t n);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ByteSource);
+};
+
+//
+// Some commonly used implementations of ByteSink
+//
+
+// Implementation of ByteSink that writes to an unsized byte array. No
+// bounds-checking is performed--it is the caller's responsibility to ensure
+// that the destination array is large enough.
+//
+// Example:
+//
+// char buf[10];
+// UncheckedArrayByteSink sink(buf);
+// sink.Append("hi", 2); // OK
+// sink.Append(data, 100); // WOOPS! Overflows buf[10].
+//
+class LIBPROTOBUF_EXPORT UncheckedArrayByteSink : public ByteSink {
+ public:
+ explicit UncheckedArrayByteSink(char* dest) : dest_(dest) {}
+ virtual void Append(const char* data, size_t n);
+
+ // Returns the current output pointer so that a caller can see how many bytes
+ // were produced.
+ //
+ // Note: this method is not part of the ByteSink interface.
+ char* CurrentDestination() const { return dest_; }
+
+ private:
+ char* dest_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(UncheckedArrayByteSink);
+};
+
+// Implementation of ByteSink that writes to a sized byte array. This sink will
+// not write more than "capacity" bytes to outbuf. Once "capacity" bytes are
+// appended, subsequent bytes will be ignored and Overflowed() will return true.
+// Overflowed() does not cause a runtime error (i.e., it does not CHECK fail).
+//
+// Example:
+//
+// char buf[10];
+// CheckedArrayByteSink sink(buf, 10);
+// sink.Append("hi", 2); // OK
+// sink.Append(data, 100); // Will only write 8 more bytes
+//
+class LIBPROTOBUF_EXPORT CheckedArrayByteSink : public ByteSink {
+ public:
+ CheckedArrayByteSink(char* outbuf, size_t capacity);
+ virtual void Append(const char* bytes, size_t n);
+
+ // Returns the number of bytes actually written to the sink.
+ size_t NumberOfBytesWritten() const { return size_; }
+
+ // Returns true if any bytes were discarded, i.e., if there was an
+ // attempt to write more than 'capacity' bytes.
+ bool Overflowed() const { return overflowed_; }
+
+ private:
+ char* outbuf_;
+ const size_t capacity_;
+ size_t size_;
+ bool overflowed_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CheckedArrayByteSink);
+};
+
+// Implementation of ByteSink that allocates an internal buffer (a char array)
+// and expands it as needed to accommodate appended data (similar to a string),
+// and allows the caller to take ownership of the internal buffer via the
+// GetBuffer() method. The buffer returned from GetBuffer() must be deleted by
+// the caller with delete[]. GetBuffer() also sets the internal buffer to be
+// empty, and subsequent appends to the sink will create a new buffer. The
+// destructor will free the internal buffer if GetBuffer() was not called.
+//
+// Example:
+//
+// GrowingArrayByteSink sink(10);
+// sink.Append("hi", 2);
+// sink.Append(data, n);
+// const char* buf = sink.GetBuffer(); // Ownership transferred
+// delete[] buf;
+//
+class LIBPROTOBUF_EXPORT GrowingArrayByteSink : public strings::ByteSink {
+ public:
+ explicit GrowingArrayByteSink(size_t estimated_size);
+ virtual ~GrowingArrayByteSink();
+ virtual void Append(const char* bytes, size_t n);
+
+ // Returns the allocated buffer, and sets nbytes to its size. The caller takes
+ // ownership of the buffer and must delete it with delete[].
+ char* GetBuffer(size_t* nbytes);
+
+ private:
+ void Expand(size_t amount);
+ void ShrinkToFit();
+
+ size_t capacity_;
+ char* buf_;
+ size_t size_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(GrowingArrayByteSink);
+};
+
+// Implementation of ByteSink that appends to the given string.
+// Existing contents of "dest" are not modified; new data is appended.
+//
+// Example:
+//
+// string dest = "Hello ";
+// StringByteSink sink(&dest);
+// sink.Append("World", 5);
+// assert(dest == "Hello World");
+//
+class LIBPROTOBUF_EXPORT StringByteSink : public ByteSink {
+ public:
+ explicit StringByteSink(string* dest) : dest_(dest) {}
+ virtual void Append(const char* data, size_t n);
+
+ private:
+ string* dest_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StringByteSink);
+};
+
+// Implementation of ByteSink that discards all data.
+//
+// Example:
+//
+// NullByteSink sink;
+// sink.Append(data, data.size()); // All data ignored.
+//
+class LIBPROTOBUF_EXPORT NullByteSink : public ByteSink {
+ public:
+ NullByteSink() {}
+ virtual void Append(const char *data, size_t n) {}
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(NullByteSink);
+};
+
+//
+// Some commonly used implementations of ByteSource
+//
+
+// Implementation of ByteSource that reads from a StringPiece.
+//
+// Example:
+//
+// string data = "Hello";
+// ArrayByteSource source(data);
+// assert(source.Available() == 5);
+// assert(source.Peek() == "Hello");
+//
+class LIBPROTOBUF_EXPORT ArrayByteSource : public ByteSource {
+ public:
+ explicit ArrayByteSource(StringPiece s) : input_(s) {}
+
+ virtual size_t Available() const;
+ virtual StringPiece Peek();
+ virtual void Skip(size_t n);
+
+ private:
+ StringPiece input_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ArrayByteSource);
+};
+
+// Implementation of ByteSource that wraps another ByteSource, limiting the
+// number of bytes returned.
+//
+// The caller maintains ownership of the underlying source, and may not use the
+// underlying source while using the LimitByteSource object. The underlying
+// source's pointer is advanced by n bytes every time this LimitByteSource
+// object is advanced by n.
+//
+// Example:
+//
+// string data = "Hello World";
+// ArrayByteSource abs(data);
+// assert(abs.Available() == data.size());
+//
+// LimitByteSource limit(abs, 5);
+// assert(limit.Available() == 5);
+// assert(limit.Peek() == "Hello");
+//
+class LIBPROTOBUF_EXPORT LimitByteSource : public ByteSource {
+ public:
+ // Returns at most "limit" bytes from "source".
+ LimitByteSource(ByteSource* source, size_t limit);
+
+ virtual size_t Available() const;
+ virtual StringPiece Peek();
+ virtual void Skip(size_t n);
+
+ // We override CopyTo so that we can forward to the underlying source, in
+ // case it has an efficient implementation of CopyTo.
+ virtual void CopyTo(ByteSink* sink, size_t n);
+
+ private:
+ ByteSource* source_;
+ size_t limit_;
+};
+
+} // namespace strings
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_BYTESTREAM_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream_unittest.cc
new file mode 100644
index 0000000000..06f114abc7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/bytestream_unittest.cc
@@ -0,0 +1,146 @@
+// 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.
+
+#include <google/protobuf/stubs/bytestream.h>
+
+#include <stdio.h>
+#include <string.h>
+#include <algorithm>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace strings {
+namespace {
+
+// We use this class instead of ArrayByteSource to simulate a ByteSource that
+// contains multiple fragments. ArrayByteSource returns the entire array in
+// one fragment.
+class MockByteSource : public ByteSource {
+ public:
+ MockByteSource(StringPiece data, int block_size)
+ : data_(data), block_size_(block_size) {}
+
+ size_t Available() const { return data_.size(); }
+ StringPiece Peek() {
+ return data_.substr(0, block_size_);
+ }
+ void Skip(size_t n) { data_.remove_prefix(n); }
+
+ private:
+ StringPiece data_;
+ int block_size_;
+};
+
+TEST(ByteSourceTest, CopyTo) {
+ StringPiece data("Hello world!");
+ MockByteSource source(data, 3);
+ string str;
+ StringByteSink sink(&str);
+
+ source.CopyTo(&sink, data.size());
+ EXPECT_EQ(data, str);
+}
+
+TEST(ByteSourceTest, CopySubstringTo) {
+ StringPiece data("Hello world!");
+ MockByteSource source(data, 3);
+ source.Skip(1);
+ string str;
+ StringByteSink sink(&str);
+
+ source.CopyTo(&sink, data.size() - 2);
+ EXPECT_EQ(data.substr(1, data.size() - 2), str);
+ EXPECT_EQ("!", source.Peek());
+}
+
+TEST(ByteSourceTest, LimitByteSource) {
+ StringPiece data("Hello world!");
+ MockByteSource source(data, 3);
+ LimitByteSource limit_source(&source, 6);
+ EXPECT_EQ(6, limit_source.Available());
+ limit_source.Skip(1);
+ EXPECT_EQ(5, limit_source.Available());
+
+ {
+ string str;
+ StringByteSink sink(&str);
+ limit_source.CopyTo(&sink, limit_source.Available());
+ EXPECT_EQ("ello ", str);
+ EXPECT_EQ(0, limit_source.Available());
+ EXPECT_EQ(6, source.Available());
+ }
+
+ {
+ string str;
+ StringByteSink sink(&str);
+ source.CopyTo(&sink, source.Available());
+ EXPECT_EQ("world!", str);
+ EXPECT_EQ(0, source.Available());
+ }
+}
+
+TEST(ByteSourceTest, CopyToStringByteSink) {
+ StringPiece data("Hello world!");
+ MockByteSource source(data, 3);
+ string str;
+ StringByteSink sink(&str);
+ source.CopyTo(&sink, data.size());
+ EXPECT_EQ(data, str);
+}
+
+// Verify that ByteSink is subclassable and Flush() overridable.
+class FlushingByteSink : public StringByteSink {
+ public:
+ explicit FlushingByteSink(string* dest) : StringByteSink(dest) {}
+ virtual void Flush() { Append("z", 1); }
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FlushingByteSink);
+};
+
+// Write and Flush via the ByteSink superclass interface.
+void WriteAndFlush(ByteSink* s) {
+ s->Append("abc", 3);
+ s->Flush();
+}
+
+TEST(ByteSinkTest, Flush) {
+ string str;
+ FlushingByteSink f_sink(&str);
+ WriteAndFlush(&f_sink);
+ EXPECT_STREQ("abcz", str.c_str());
+}
+
+} // namespace
+} // namespace strings
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/callback.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/callback.h
new file mode 100644
index 0000000000..87271c5eb8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/callback.h
@@ -0,0 +1,546 @@
+#ifndef GOOGLE_PROTOBUF_STUBS_CALLBACK_H_
+#define GOOGLE_PROTOBUF_STUBS_CALLBACK_H_
+
+#include <google/protobuf/stubs/macros.h>
+#include <google/protobuf/stubs/type_traits.h>
+
+// ===================================================================
+// emulates google3/base/callback.h
+
+namespace google {
+namespace protobuf {
+
+// Abstract interface for a callback. When calling an RPC, you must provide
+// a Closure to call when the procedure completes. See the Service interface
+// in service.h.
+//
+// To automatically construct a Closure which calls a particular function or
+// method with a particular set of parameters, use the NewCallback() function.
+// Example:
+// void FooDone(const FooResponse* response) {
+// ...
+// }
+//
+// void CallFoo() {
+// ...
+// // When done, call FooDone() and pass it a pointer to the response.
+// Closure* callback = NewCallback(&FooDone, response);
+// // Make the call.
+// service->Foo(controller, request, response, callback);
+// }
+//
+// Example that calls a method:
+// class Handler {
+// public:
+// ...
+//
+// void FooDone(const FooResponse* response) {
+// ...
+// }
+//
+// void CallFoo() {
+// ...
+// // When done, call FooDone() and pass it a pointer to the response.
+// Closure* callback = NewCallback(this, &Handler::FooDone, response);
+// // Make the call.
+// service->Foo(controller, request, response, callback);
+// }
+// };
+//
+// Currently NewCallback() supports binding zero, one, or two arguments.
+//
+// Callbacks created with NewCallback() automatically delete themselves when
+// executed. They should be used when a callback is to be called exactly
+// once (usually the case with RPC callbacks). If a callback may be called
+// a different number of times (including zero), create it with
+// NewPermanentCallback() instead. You are then responsible for deleting the
+// callback (using the "delete" keyword as normal).
+//
+// Note that NewCallback() is a bit touchy regarding argument types. Generally,
+// the values you provide for the parameter bindings must exactly match the
+// types accepted by the callback function. For example:
+// void Foo(string s);
+// NewCallback(&Foo, "foo"); // WON'T WORK: const char* != string
+// NewCallback(&Foo, string("foo")); // WORKS
+// Also note that the arguments cannot be references:
+// void Foo(const string& s);
+// string my_str;
+// NewCallback(&Foo, my_str); // WON'T WORK: Can't use referecnes.
+// However, correctly-typed pointers will work just fine.
+class LIBPROTOBUF_EXPORT Closure {
+ public:
+ Closure() {}
+ virtual ~Closure();
+
+ virtual void Run() = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Closure);
+};
+
+template<typename R>
+class ResultCallback {
+ public:
+ ResultCallback() {}
+ virtual ~ResultCallback() {}
+
+ virtual R Run() = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ResultCallback);
+};
+
+template<typename R, typename A1>
+class LIBPROTOBUF_EXPORT ResultCallback1 {
+ public:
+ ResultCallback1() {}
+ virtual ~ResultCallback1() {}
+
+ virtual R Run(A1) = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ResultCallback1);
+};
+
+template<typename R, typename A1, typename A2>
+class LIBPROTOBUF_EXPORT ResultCallback2 {
+ public:
+ ResultCallback2() {}
+ virtual ~ResultCallback2() {}
+
+ virtual R Run(A1,A2) = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ResultCallback2);
+};
+
+namespace internal {
+
+class LIBPROTOBUF_EXPORT FunctionClosure0 : public Closure {
+ public:
+ typedef void (*FunctionType)();
+
+ FunctionClosure0(FunctionType function, bool self_deleting)
+ : function_(function), self_deleting_(self_deleting) {}
+ ~FunctionClosure0();
+
+ void Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ function_();
+ if (needs_delete) delete this;
+ }
+
+ private:
+ FunctionType function_;
+ bool self_deleting_;
+};
+
+template <typename Class>
+class MethodClosure0 : public Closure {
+ public:
+ typedef void (Class::*MethodType)();
+
+ MethodClosure0(Class* object, MethodType method, bool self_deleting)
+ : object_(object), method_(method), self_deleting_(self_deleting) {}
+ ~MethodClosure0() {}
+
+ void Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ (object_->*method_)();
+ if (needs_delete) delete this;
+ }
+
+ private:
+ Class* object_;
+ MethodType method_;
+ bool self_deleting_;
+};
+
+template <typename Arg1>
+class FunctionClosure1 : public Closure {
+ public:
+ typedef void (*FunctionType)(Arg1 arg1);
+
+ FunctionClosure1(FunctionType function, bool self_deleting,
+ Arg1 arg1)
+ : function_(function), self_deleting_(self_deleting),
+ arg1_(arg1) {}
+ ~FunctionClosure1() {}
+
+ void Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ function_(arg1_);
+ if (needs_delete) delete this;
+ }
+
+ private:
+ FunctionType function_;
+ bool self_deleting_;
+ Arg1 arg1_;
+};
+
+template <typename Class, typename Arg1>
+class MethodClosure1 : public Closure {
+ public:
+ typedef void (Class::*MethodType)(Arg1 arg1);
+
+ MethodClosure1(Class* object, MethodType method, bool self_deleting,
+ Arg1 arg1)
+ : object_(object), method_(method), self_deleting_(self_deleting),
+ arg1_(arg1) {}
+ ~MethodClosure1() {}
+
+ void Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ (object_->*method_)(arg1_);
+ if (needs_delete) delete this;
+ }
+
+ private:
+ Class* object_;
+ MethodType method_;
+ bool self_deleting_;
+ Arg1 arg1_;
+};
+
+template <typename Arg1, typename Arg2>
+class FunctionClosure2 : public Closure {
+ public:
+ typedef void (*FunctionType)(Arg1 arg1, Arg2 arg2);
+
+ FunctionClosure2(FunctionType function, bool self_deleting,
+ Arg1 arg1, Arg2 arg2)
+ : function_(function), self_deleting_(self_deleting),
+ arg1_(arg1), arg2_(arg2) {}
+ ~FunctionClosure2() {}
+
+ void Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ function_(arg1_, arg2_);
+ if (needs_delete) delete this;
+ }
+
+ private:
+ FunctionType function_;
+ bool self_deleting_;
+ Arg1 arg1_;
+ Arg2 arg2_;
+};
+
+template <typename Class, typename Arg1, typename Arg2>
+class MethodClosure2 : public Closure {
+ public:
+ typedef void (Class::*MethodType)(Arg1 arg1, Arg2 arg2);
+
+ MethodClosure2(Class* object, MethodType method, bool self_deleting,
+ Arg1 arg1, Arg2 arg2)
+ : object_(object), method_(method), self_deleting_(self_deleting),
+ arg1_(arg1), arg2_(arg2) {}
+ ~MethodClosure2() {}
+
+ void Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ (object_->*method_)(arg1_, arg2_);
+ if (needs_delete) delete this;
+ }
+
+ private:
+ Class* object_;
+ MethodType method_;
+ bool self_deleting_;
+ Arg1 arg1_;
+ Arg2 arg2_;
+};
+
+template<typename R>
+class FunctionResultCallback_0_0 : public ResultCallback<R> {
+ public:
+ typedef R (*FunctionType)();
+
+ FunctionResultCallback_0_0(FunctionType function, bool self_deleting)
+ : function_(function), self_deleting_(self_deleting) {}
+ ~FunctionResultCallback_0_0() {}
+
+ R Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ R result = function_();
+ if (needs_delete) delete this;
+ return result;
+ }
+
+ private:
+ FunctionType function_;
+ bool self_deleting_;
+};
+
+template<typename R, typename P1>
+class FunctionResultCallback_1_0 : public ResultCallback<R> {
+ public:
+ typedef R (*FunctionType)(P1);
+
+ FunctionResultCallback_1_0(FunctionType function, bool self_deleting,
+ P1 p1)
+ : function_(function), self_deleting_(self_deleting), p1_(p1) {}
+ ~FunctionResultCallback_1_0() {}
+
+ R Run() {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ R result = function_(p1_);
+ if (needs_delete) delete this;
+ return result;
+ }
+
+ private:
+ FunctionType function_;
+ bool self_deleting_;
+ P1 p1_;
+};
+
+template<typename R, typename Arg1>
+class FunctionResultCallback_0_1 : public ResultCallback1<R, Arg1> {
+ public:
+ typedef R (*FunctionType)(Arg1 arg1);
+
+ FunctionResultCallback_0_1(FunctionType function, bool self_deleting)
+ : function_(function), self_deleting_(self_deleting) {}
+ ~FunctionResultCallback_0_1() {}
+
+ R Run(Arg1 a1) {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ R result = function_(a1);
+ if (needs_delete) delete this;
+ return result;
+ }
+
+ private:
+ FunctionType function_;
+ bool self_deleting_;
+};
+
+template<typename R, typename P1, typename A1>
+class FunctionResultCallback_1_1 : public ResultCallback1<R, A1> {
+ public:
+ typedef R (*FunctionType)(P1, A1);
+
+ FunctionResultCallback_1_1(FunctionType function, bool self_deleting,
+ P1 p1)
+ : function_(function), self_deleting_(self_deleting), p1_(p1) {}
+ ~FunctionResultCallback_1_1() {}
+
+ R Run(A1 a1) {
+ bool needs_delete = self_deleting_; // read in case callback deletes
+ R result = function_(p1_, a1);
+ if (needs_delete) delete this;
+ return result;
+ }
+
+ private:
+ FunctionType function_;
+ bool self_deleting_;
+ P1 p1_;
+};
+
+template <typename T>
+struct InternalConstRef {
+ typedef typename remove_reference<T>::type base_type;
+ typedef const base_type& type;
+};
+
+template <typename R, typename T, typename P1, typename P2, typename P3,
+ typename P4, typename P5, typename A1, typename A2>
+class MethodResultCallback_5_2 : public ResultCallback2<R, A1, A2> {
+ public:
+ typedef R (T::*MethodType)(P1, P2, P3, P4, P5, A1, A2);
+ MethodResultCallback_5_2(T* object, MethodType method, bool self_deleting,
+ P1 p1, P2 p2, P3 p3, P4 p4, P5 p5)
+ : object_(object),
+ method_(method),
+ self_deleting_(self_deleting),
+ p1_(p1),
+ p2_(p2),
+ p3_(p3),
+ p4_(p4),
+ p5_(p5) {}
+ ~MethodResultCallback_5_2() {}
+
+ R Run(A1 a1, A2 a2) {
+ bool needs_delete = self_deleting_;
+ R result = (object_->*method_)(p1_, p2_, p3_, p4_, p5_, a1, a2);
+ if (needs_delete) delete this;
+ return result;
+ }
+
+ private:
+ T* object_;
+ MethodType method_;
+ bool self_deleting_;
+ typename remove_reference<P1>::type p1_;
+ typename remove_reference<P2>::type p2_;
+ typename remove_reference<P3>::type p3_;
+ typename remove_reference<P4>::type p4_;
+ typename remove_reference<P5>::type p5_;
+};
+
+// See Closure.
+inline Closure* NewCallback(void (*function)()) {
+ return new internal::FunctionClosure0(function, true);
+}
+
+// See Closure.
+inline Closure* NewPermanentCallback(void (*function)()) {
+ return new internal::FunctionClosure0(function, false);
+}
+
+// See Closure.
+template <typename Class>
+inline Closure* NewCallback(Class* object, void (Class::*method)()) {
+ return new internal::MethodClosure0<Class>(object, method, true);
+}
+
+// See Closure.
+template <typename Class>
+inline Closure* NewPermanentCallback(Class* object, void (Class::*method)()) {
+ return new internal::MethodClosure0<Class>(object, method, false);
+}
+
+// See Closure.
+template <typename Arg1>
+inline Closure* NewCallback(void (*function)(Arg1),
+ Arg1 arg1) {
+ return new internal::FunctionClosure1<Arg1>(function, true, arg1);
+}
+
+// See Closure.
+template <typename Arg1>
+inline Closure* NewPermanentCallback(void (*function)(Arg1),
+ Arg1 arg1) {
+ return new internal::FunctionClosure1<Arg1>(function, false, arg1);
+}
+
+// See Closure.
+template <typename Class, typename Arg1>
+inline Closure* NewCallback(Class* object, void (Class::*method)(Arg1),
+ Arg1 arg1) {
+ return new internal::MethodClosure1<Class, Arg1>(object, method, true, arg1);
+}
+
+// See Closure.
+template <typename Class, typename Arg1>
+inline Closure* NewPermanentCallback(Class* object, void (Class::*method)(Arg1),
+ Arg1 arg1) {
+ return new internal::MethodClosure1<Class, Arg1>(object, method, false, arg1);
+}
+
+// See Closure.
+template <typename Arg1, typename Arg2>
+inline Closure* NewCallback(void (*function)(Arg1, Arg2),
+ Arg1 arg1, Arg2 arg2) {
+ return new internal::FunctionClosure2<Arg1, Arg2>(
+ function, true, arg1, arg2);
+}
+
+// See Closure.
+template <typename Arg1, typename Arg2>
+inline Closure* NewPermanentCallback(void (*function)(Arg1, Arg2),
+ Arg1 arg1, Arg2 arg2) {
+ return new internal::FunctionClosure2<Arg1, Arg2>(
+ function, false, arg1, arg2);
+}
+
+// See Closure.
+template <typename Class, typename Arg1, typename Arg2>
+inline Closure* NewCallback(Class* object, void (Class::*method)(Arg1, Arg2),
+ Arg1 arg1, Arg2 arg2) {
+ return new internal::MethodClosure2<Class, Arg1, Arg2>(
+ object, method, true, arg1, arg2);
+}
+
+// See Closure.
+template <typename Class, typename Arg1, typename Arg2>
+inline Closure* NewPermanentCallback(
+ Class* object, void (Class::*method)(Arg1, Arg2),
+ Arg1 arg1, Arg2 arg2) {
+ return new internal::MethodClosure2<Class, Arg1, Arg2>(
+ object, method, false, arg1, arg2);
+}
+
+// See ResultCallback
+template<typename R>
+inline ResultCallback<R>* NewCallback(R (*function)()) {
+ return new internal::FunctionResultCallback_0_0<R>(function, true);
+}
+
+// See ResultCallback
+template<typename R>
+inline ResultCallback<R>* NewPermanentCallback(R (*function)()) {
+ return new internal::FunctionResultCallback_0_0<R>(function, false);
+}
+
+// See ResultCallback
+template<typename R, typename P1>
+inline ResultCallback<R>* NewCallback(R (*function)(P1), P1 p1) {
+ return new internal::FunctionResultCallback_1_0<R, P1>(
+ function, true, p1);
+}
+
+// See ResultCallback
+template<typename R, typename P1>
+inline ResultCallback<R>* NewPermanentCallback(
+ R (*function)(P1), P1 p1) {
+ return new internal::FunctionResultCallback_1_0<R, P1>(
+ function, false, p1);
+}
+
+// See ResultCallback1
+template<typename R, typename A1>
+inline ResultCallback1<R, A1>* NewCallback(R (*function)(A1)) {
+ return new internal::FunctionResultCallback_0_1<R, A1>(function, true);
+}
+
+// See ResultCallback1
+template<typename R, typename A1>
+inline ResultCallback1<R, A1>* NewPermanentCallback(R (*function)(A1)) {
+ return new internal::FunctionResultCallback_0_1<R, A1>(function, false);
+}
+
+// See ResultCallback1
+template<typename R, typename P1, typename A1>
+inline ResultCallback1<R, A1>* NewCallback(R (*function)(P1, A1), P1 p1) {
+ return new internal::FunctionResultCallback_1_1<R, P1, A1>(
+ function, true, p1);
+}
+
+// See ResultCallback1
+template<typename R, typename P1, typename A1>
+inline ResultCallback1<R, A1>* NewPermanentCallback(
+ R (*function)(P1, A1), P1 p1) {
+ return new internal::FunctionResultCallback_1_1<R, P1, A1>(
+ function, false, p1);
+}
+
+// See MethodResultCallback_5_2
+template <typename R, typename T, typename P1, typename P2, typename P3,
+ typename P4, typename P5, typename A1, typename A2>
+inline ResultCallback2<R, A1, A2>* NewPermanentCallback(
+ T* object, R (T::*function)(P1, P2, P3, P4, P5, A1, A2),
+ typename internal::InternalConstRef<P1>::type p1,
+ typename internal::InternalConstRef<P2>::type p2,
+ typename internal::InternalConstRef<P3>::type p3,
+ typename internal::InternalConstRef<P4>::type p4,
+ typename internal::InternalConstRef<P5>::type p5) {
+ return new internal::MethodResultCallback_5_2<R, T, P1, P2, P3, P4, P5, A1,
+ A2>(object, function, false, p1,
+ p2, p3, p4, p5);
+}
+
+} // namespace internal
+
+// A function which does nothing. Useful for creating no-op callbacks, e.g.:
+// Closure* nothing = NewCallback(&DoNothing);
+void LIBPROTOBUF_EXPORT DoNothing();
+
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_CALLBACK_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/casts.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/casts.h
new file mode 100644
index 0000000000..be652849ef
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/casts.h
@@ -0,0 +1,133 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+
+#ifndef GOOGLE_PROTOBUF_CASTS_H__
+#define GOOGLE_PROTOBUF_CASTS_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/type_traits.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+// Use implicit_cast as a safe version of static_cast or const_cast
+// for upcasting in the type hierarchy (i.e. casting a pointer to Foo
+// to a pointer to SuperclassOfFoo or casting a pointer to Foo to
+// a const pointer to Foo).
+// When you use implicit_cast, the compiler checks that the cast is safe.
+// Such explicit implicit_casts are necessary in surprisingly many
+// situations where C++ demands an exact type match instead of an
+// argument type convertable to a target type.
+//
+// The From type can be inferred, so the preferred syntax for using
+// implicit_cast is the same as for static_cast etc.:
+//
+// implicit_cast<ToType>(expr)
+//
+// implicit_cast would have been part of the C++ standard library,
+// but the proposal was submitted too late. It will probably make
+// its way into the language in the future.
+template<typename To, typename From>
+inline To implicit_cast(From const &f) {
+ return f;
+}
+
+// When you upcast (that is, cast a pointer from type Foo to type
+// SuperclassOfFoo), it's fine to use implicit_cast<>, since upcasts
+// always succeed. When you downcast (that is, cast a pointer from
+// type Foo to type SubclassOfFoo), static_cast<> isn't safe, because
+// how do you know the pointer is really of type SubclassOfFoo? It
+// could be a bare Foo, or of type DifferentSubclassOfFoo. Thus,
+// when you downcast, you should use this macro. In debug mode, we
+// use dynamic_cast<> to double-check the downcast is legal (we die
+// if it's not). In normal mode, we do the efficient static_cast<>
+// instead. Thus, it's important to test in debug mode to make sure
+// the cast is legal!
+// This is the only place in the code we should use dynamic_cast<>.
+// In particular, you SHOULDN'T be using dynamic_cast<> in order to
+// do RTTI (eg code like this:
+// if (dynamic_cast<Subclass1>(foo)) HandleASubclass1Object(foo);
+// if (dynamic_cast<Subclass2>(foo)) HandleASubclass2Object(foo);
+// You should design the code some other way not to need this.
+
+template<typename To, typename From> // use like this: down_cast<T*>(foo);
+inline To down_cast(From* f) { // so we only accept pointers
+ // Ensures that To is a sub-type of From *. This test is here only
+ // for compile-time type checking, and has no overhead in an
+ // optimized build at run-time, as it will be optimized away
+ // completely.
+ if (false) {
+ implicit_cast<From*, To>(0);
+ }
+
+#if !defined(NDEBUG) && !defined(GOOGLE_PROTOBUF_NO_RTTI)
+ assert(f == NULL || dynamic_cast<To>(f) != NULL); // RTTI: debug mode only!
+#endif
+ return static_cast<To>(f);
+}
+
+template<typename To, typename From> // use like this: down_cast<T&>(foo);
+inline To down_cast(From& f) {
+ typedef typename remove_reference<To>::type* ToAsPointer;
+ // Ensures that To is a sub-type of From *. This test is here only
+ // for compile-time type checking, and has no overhead in an
+ // optimized build at run-time, as it will be optimized away
+ // completely.
+ if (false) {
+ implicit_cast<From*, ToAsPointer>(0);
+ }
+
+#if !defined(NDEBUG) && !defined(GOOGLE_PROTOBUF_NO_RTTI)
+ // RTTI: debug mode only!
+ assert(dynamic_cast<ToAsPointer>(&f) != NULL);
+#endif
+ return *static_cast<ToAsPointer>(&f);
+}
+
+template<typename To, typename From>
+inline To bit_cast(const From& from) {
+ GOOGLE_COMPILE_ASSERT(sizeof(From) == sizeof(To),
+ bit_cast_with_different_sizes);
+ To dest;
+ memcpy(&dest, &from, sizeof(dest));
+ return dest;
+}
+
+} // namespace internal
+
+// We made these internal so that they would show up as such in the docs,
+// but we don't want to stick "internal::" in front of them everywhere.
+using internal::implicit_cast;
+using internal::down_cast;
+using internal::bit_cast;
+
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_CASTS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.cc
new file mode 100644
index 0000000000..54dbafab5d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.cc
@@ -0,0 +1,459 @@
+// 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)
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/once.h>
+#include <google/protobuf/stubs/status.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/int128.h>
+#include <errno.h>
+#include <sstream>
+#include <stdio.h>
+#include <vector>
+
+#ifdef _WIN32
+#define WIN32_LEAN_AND_MEAN // We only need minimal includes
+#include <windows.h>
+#define snprintf _snprintf // see comment in strutil.cc
+#elif defined(HAVE_PTHREAD)
+#include <pthread.h>
+#else
+#error "No suitable threading library available."
+#endif
+#if defined(__ANDROID__)
+#include <android/log.h>
+#endif
+
+namespace google {
+namespace protobuf {
+
+namespace internal {
+
+void VerifyVersion(int headerVersion,
+ int minLibraryVersion,
+ const char* filename) {
+ if (GOOGLE_PROTOBUF_VERSION < minLibraryVersion) {
+ // Library is too old for headers.
+ GOOGLE_LOG(FATAL)
+ << "This program requires version " << VersionString(minLibraryVersion)
+ << " of the Protocol Buffer runtime library, but the installed version "
+ "is " << VersionString(GOOGLE_PROTOBUF_VERSION) << ". Please update "
+ "your library. If you compiled the program yourself, make sure that "
+ "your headers are from the same version of Protocol Buffers as your "
+ "link-time library. (Version verification failed in \""
+ << filename << "\".)";
+ }
+ if (headerVersion < kMinHeaderVersionForLibrary) {
+ // Headers are too old for library.
+ GOOGLE_LOG(FATAL)
+ << "This program was compiled against version "
+ << VersionString(headerVersion) << " of the Protocol Buffer runtime "
+ "library, which is not compatible with the installed version ("
+ << VersionString(GOOGLE_PROTOBUF_VERSION) << "). Contact the program "
+ "author for an update. If you compiled the program yourself, make "
+ "sure that your headers are from the same version of Protocol Buffers "
+ "as your link-time library. (Version verification failed in \""
+ << filename << "\".)";
+ }
+}
+
+string VersionString(int version) {
+ int major = version / 1000000;
+ int minor = (version / 1000) % 1000;
+ int micro = version % 1000;
+
+ // 128 bytes should always be enough, but we use snprintf() anyway to be
+ // safe.
+ char buffer[128];
+ snprintf(buffer, sizeof(buffer), "%d.%d.%d", major, minor, micro);
+
+ // Guard against broken MSVC snprintf().
+ buffer[sizeof(buffer)-1] = '\0';
+
+ return buffer;
+}
+
+} // namespace internal
+
+// ===================================================================
+// emulates google3/base/logging.cc
+
+namespace internal {
+#if defined(__ANDROID__)
+inline void DefaultLogHandler(LogLevel level, const char* filename, int line,
+ const string& message) {
+#ifdef GOOGLE_PROTOBUF_MIN_LOG_LEVEL
+ if (level < GOOGLE_PROTOBUF_MIN_LOG_LEVEL) {
+ return;
+ }
+ static const char* level_names[] = {"INFO", "WARNING", "ERROR", "FATAL"};
+
+ static const int android_log_levels[] = {
+ ANDROID_LOG_INFO, // LOG(INFO),
+ ANDROID_LOG_WARN, // LOG(WARNING)
+ ANDROID_LOG_ERROR, // LOG(ERROR)
+ ANDROID_LOG_FATAL, // LOG(FATAL)
+ };
+
+ // Bound the logging level.
+ const int android_log_level = android_log_levels[level];
+ ::std::ostringstream ostr;
+ ostr << "[libprotobuf " << level_names[level] << " " << filename << ":"
+ << line << "] " << message.c_str();
+
+ // Output the log string the Android log at the appropriate level.
+ __android_log_write(android_log_level, "libprotobuf-native",
+ ostr.str().c_str());
+ // Also output to std::cerr.
+ fprintf(stderr, "%s", ostr.str().c_str());
+ fflush(stderr);
+
+ // Indicate termination if needed.
+ if (android_log_level == ANDROID_LOG_FATAL) {
+ __android_log_write(ANDROID_LOG_FATAL, "libprotobuf-native",
+ "terminating.\n");
+ }
+#endif
+}
+#else
+void DefaultLogHandler(LogLevel level, const char* filename, int line,
+ const string& message) {
+ static const char* level_names[] = { "INFO", "WARNING", "ERROR", "FATAL" };
+
+ // We use fprintf() instead of cerr because we want this to work at static
+ // initialization time.
+ fprintf(stderr, "[libprotobuf %s %s:%d] %s\n",
+ level_names[level], filename, line, message.c_str());
+ fflush(stderr); // Needed on MSVC.
+}
+#endif
+
+void NullLogHandler(LogLevel /* level */, const char* /* filename */,
+ int /* line */, const string& /* message */) {
+ // Nothing.
+}
+
+static LogHandler* log_handler_ = &DefaultLogHandler;
+static int log_silencer_count_ = 0;
+
+static Mutex* log_silencer_count_mutex_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(log_silencer_count_init_);
+
+void DeleteLogSilencerCount() {
+ delete log_silencer_count_mutex_;
+ log_silencer_count_mutex_ = NULL;
+}
+void InitLogSilencerCount() {
+ log_silencer_count_mutex_ = new Mutex;
+ OnShutdown(&DeleteLogSilencerCount);
+}
+void InitLogSilencerCountOnce() {
+ GoogleOnceInit(&log_silencer_count_init_, &InitLogSilencerCount);
+}
+
+LogMessage& LogMessage::operator<<(const string& value) {
+ message_ += value;
+ return *this;
+}
+
+LogMessage& LogMessage::operator<<(const char* value) {
+ message_ += value;
+ return *this;
+}
+
+LogMessage& LogMessage::operator<<(const StringPiece& value) {
+ message_ += value.ToString();
+ return *this;
+}
+
+LogMessage& LogMessage::operator<<(
+ const ::google::protobuf::util::Status& status) {
+ message_ += status.ToString();
+ return *this;
+}
+
+LogMessage& LogMessage::operator<<(const uint128& value) {
+ std::ostringstream str;
+ str << value;
+ message_ += str.str();
+ return *this;
+}
+
+// Since this is just for logging, we don't care if the current locale changes
+// the results -- in fact, we probably prefer that. So we use snprintf()
+// instead of Simple*toa().
+#undef DECLARE_STREAM_OPERATOR
+#define DECLARE_STREAM_OPERATOR(TYPE, FORMAT) \
+ LogMessage& LogMessage::operator<<(TYPE value) { \
+ /* 128 bytes should be big enough for any of the primitive */ \
+ /* values which we print with this, but well use snprintf() */ \
+ /* anyway to be extra safe. */ \
+ char buffer[128]; \
+ snprintf(buffer, sizeof(buffer), FORMAT, value); \
+ /* Guard against broken MSVC snprintf(). */ \
+ buffer[sizeof(buffer)-1] = '\0'; \
+ message_ += buffer; \
+ return *this; \
+ }
+
+DECLARE_STREAM_OPERATOR(char , "%c" )
+DECLARE_STREAM_OPERATOR(int , "%d" )
+DECLARE_STREAM_OPERATOR(unsigned int , "%u" )
+DECLARE_STREAM_OPERATOR(long , "%ld")
+DECLARE_STREAM_OPERATOR(unsigned long, "%lu")
+DECLARE_STREAM_OPERATOR(double , "%g" )
+DECLARE_STREAM_OPERATOR(void* , "%p" )
+DECLARE_STREAM_OPERATOR(long long , "%" GOOGLE_LL_FORMAT "d")
+DECLARE_STREAM_OPERATOR(unsigned long long, "%" GOOGLE_LL_FORMAT "u")
+#undef DECLARE_STREAM_OPERATOR
+
+LogMessage::LogMessage(LogLevel level, const char* filename, int line)
+ : level_(level), filename_(filename), line_(line) {}
+LogMessage::~LogMessage() {}
+
+void LogMessage::Finish() {
+ bool suppress = false;
+
+ if (level_ != LOGLEVEL_FATAL) {
+ InitLogSilencerCountOnce();
+ MutexLock lock(log_silencer_count_mutex_);
+ suppress = log_silencer_count_ > 0;
+ }
+
+ if (!suppress) {
+ log_handler_(level_, filename_, line_, message_);
+ }
+
+ if (level_ == LOGLEVEL_FATAL) {
+#if PROTOBUF_USE_EXCEPTIONS
+ throw FatalException(filename_, line_, message_);
+#else
+ abort();
+#endif
+ }
+}
+
+void LogFinisher::operator=(LogMessage& other) {
+ other.Finish();
+}
+
+} // namespace internal
+
+LogHandler* SetLogHandler(LogHandler* new_func) {
+ LogHandler* old = internal::log_handler_;
+ if (old == &internal::NullLogHandler) {
+ old = NULL;
+ }
+ if (new_func == NULL) {
+ internal::log_handler_ = &internal::NullLogHandler;
+ } else {
+ internal::log_handler_ = new_func;
+ }
+ return old;
+}
+
+LogSilencer::LogSilencer() {
+ internal::InitLogSilencerCountOnce();
+ MutexLock lock(internal::log_silencer_count_mutex_);
+ ++internal::log_silencer_count_;
+};
+
+LogSilencer::~LogSilencer() {
+ internal::InitLogSilencerCountOnce();
+ MutexLock lock(internal::log_silencer_count_mutex_);
+ --internal::log_silencer_count_;
+};
+
+// ===================================================================
+// emulates google3/base/callback.cc
+
+Closure::~Closure() {}
+
+namespace internal { FunctionClosure0::~FunctionClosure0() {} }
+
+void DoNothing() {}
+
+// ===================================================================
+// emulates google3/base/mutex.cc
+
+#ifdef _WIN32
+
+struct Mutex::Internal {
+ CRITICAL_SECTION mutex;
+#ifndef NDEBUG
+ // Used only to implement AssertHeld().
+ DWORD thread_id;
+#endif
+};
+
+Mutex::Mutex()
+ : mInternal(new Internal) {
+ InitializeCriticalSection(&mInternal->mutex);
+}
+
+Mutex::~Mutex() {
+ DeleteCriticalSection(&mInternal->mutex);
+ delete mInternal;
+}
+
+void Mutex::Lock() {
+ EnterCriticalSection(&mInternal->mutex);
+#ifndef NDEBUG
+ mInternal->thread_id = GetCurrentThreadId();
+#endif
+}
+
+void Mutex::Unlock() {
+#ifndef NDEBUG
+ mInternal->thread_id = 0;
+#endif
+ LeaveCriticalSection(&mInternal->mutex);
+}
+
+void Mutex::AssertHeld() {
+#ifndef NDEBUG
+ GOOGLE_DCHECK_EQ(mInternal->thread_id, GetCurrentThreadId());
+#endif
+}
+
+#elif defined(HAVE_PTHREAD)
+
+struct Mutex::Internal {
+ pthread_mutex_t mutex;
+};
+
+Mutex::Mutex()
+ : mInternal(new Internal) {
+ pthread_mutex_init(&mInternal->mutex, NULL);
+}
+
+Mutex::~Mutex() {
+ pthread_mutex_destroy(&mInternal->mutex);
+ delete mInternal;
+}
+
+void Mutex::Lock() {
+ int result = pthread_mutex_lock(&mInternal->mutex);
+ if (result != 0) {
+ GOOGLE_LOG(FATAL) << "pthread_mutex_lock: " << strerror(result);
+ }
+}
+
+void Mutex::Unlock() {
+ int result = pthread_mutex_unlock(&mInternal->mutex);
+ if (result != 0) {
+ GOOGLE_LOG(FATAL) << "pthread_mutex_unlock: " << strerror(result);
+ }
+}
+
+void Mutex::AssertHeld() {
+ // pthreads dosn't provide a way to check which thread holds the mutex.
+ // TODO(kenton): Maybe keep track of locking thread ID like with WIN32?
+}
+
+#endif
+
+// ===================================================================
+// emulates google3/util/endian/endian.h
+//
+// TODO(xiaofeng): PROTOBUF_LITTLE_ENDIAN is unfortunately defined in
+// google/protobuf/io/coded_stream.h and therefore can not be used here.
+// Maybe move that macro definition here in the furture.
+uint32 ghtonl(uint32 x) {
+ union {
+ uint32 result;
+ uint8 result_array[4];
+ };
+ result_array[0] = static_cast<uint8>(x >> 24);
+ result_array[1] = static_cast<uint8>((x >> 16) & 0xFF);
+ result_array[2] = static_cast<uint8>((x >> 8) & 0xFF);
+ result_array[3] = static_cast<uint8>(x & 0xFF);
+ return result;
+}
+
+// ===================================================================
+// Shutdown support.
+
+namespace internal {
+
+typedef void OnShutdownFunc();
+vector<void (*)()>* shutdown_functions = NULL;
+Mutex* shutdown_functions_mutex = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(shutdown_functions_init);
+
+void InitShutdownFunctions() {
+ shutdown_functions = new vector<void (*)()>;
+ shutdown_functions_mutex = new Mutex;
+}
+
+inline void InitShutdownFunctionsOnce() {
+ GoogleOnceInit(&shutdown_functions_init, &InitShutdownFunctions);
+}
+
+void OnShutdown(void (*func)()) {
+ InitShutdownFunctionsOnce();
+ MutexLock lock(shutdown_functions_mutex);
+ shutdown_functions->push_back(func);
+}
+
+} // namespace internal
+
+void ShutdownProtobufLibrary() {
+ internal::InitShutdownFunctionsOnce();
+
+ // We don't need to lock shutdown_functions_mutex because it's up to the
+ // caller to make sure that no one is using the library before this is
+ // called.
+
+ // Make it safe to call this multiple times.
+ if (internal::shutdown_functions == NULL) return;
+
+ for (int i = 0; i < internal::shutdown_functions->size(); i++) {
+ internal::shutdown_functions->at(i)();
+ }
+ delete internal::shutdown_functions;
+ internal::shutdown_functions = NULL;
+ delete internal::shutdown_functions_mutex;
+ internal::shutdown_functions_mutex = NULL;
+}
+
+#if PROTOBUF_USE_EXCEPTIONS
+FatalException::~FatalException() throw() {}
+
+const char* FatalException::what() const throw() {
+ return message_.c_str();
+}
+#endif
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.h
new file mode 100644
index 0000000000..9c05cac360
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common.h
@@ -0,0 +1,225 @@
+// 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) and others
+//
+// Contains basic types and utilities used by the rest of the library.
+
+#ifndef GOOGLE_PROTOBUF_COMMON_H__
+#define GOOGLE_PROTOBUF_COMMON_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/port.h>
+#include <google/protobuf/stubs/macros.h>
+#include <google/protobuf/stubs/platform_macros.h>
+
+// TODO(liujisi): Remove the following includes after the include clean-up.
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/scoped_ptr.h>
+#include <google/protobuf/stubs/mutex.h>
+#include <google/protobuf/stubs/callback.h>
+
+#ifndef PROTOBUF_USE_EXCEPTIONS
+#if defined(_MSC_VER) && defined(_CPPUNWIND)
+ #define PROTOBUF_USE_EXCEPTIONS 1
+#elif defined(__EXCEPTIONS)
+ #define PROTOBUF_USE_EXCEPTIONS 1
+#else
+ #define PROTOBUF_USE_EXCEPTIONS 0
+#endif
+#endif
+
+#if PROTOBUF_USE_EXCEPTIONS
+#include <exception>
+#endif
+#if defined(__APPLE__)
+#include <TargetConditionals.h> // for TARGET_OS_IPHONE
+#endif
+
+#if defined(__ANDROID__) || defined(GOOGLE_PROTOBUF_OS_ANDROID) || (defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE) || defined(GOOGLE_PROTOBUF_OS_IPHONE)
+#include <pthread.h>
+#endif
+
+#if defined(_WIN32) && defined(GetMessage)
+// Allow GetMessage to be used as a valid method name in protobuf classes.
+// windows.h defines GetMessage() as a macro. Let's re-define it as an inline
+// function. The inline function should be equivalent for C++ users.
+inline BOOL GetMessage_Win32(
+ LPMSG lpMsg, HWND hWnd,
+ UINT wMsgFilterMin, UINT wMsgFilterMax) {
+ return GetMessage(lpMsg, hWnd, wMsgFilterMin, wMsgFilterMax);
+}
+#undef GetMessage
+inline BOOL GetMessage(
+ LPMSG lpMsg, HWND hWnd,
+ UINT wMsgFilterMin, UINT wMsgFilterMax) {
+ return GetMessage_Win32(lpMsg, hWnd, wMsgFilterMin, wMsgFilterMax);
+}
+#endif
+
+namespace std {}
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Some of these constants are macros rather than const ints so that they can
+// be used in #if directives.
+
+// The current version, represented as a single integer to make comparison
+// easier: major * 10^6 + minor * 10^3 + micro
+#define GOOGLE_PROTOBUF_VERSION 3000000
+
+// The minimum library version which works with the current version of the
+// headers.
+#define GOOGLE_PROTOBUF_MIN_LIBRARY_VERSION 3000000
+
+// The minimum header version which works with the current version of
+// the library. This constant should only be used by protoc's C++ code
+// generator.
+static const int kMinHeaderVersionForLibrary = 3000000;
+
+// The minimum protoc version which works with the current version of the
+// headers.
+#define GOOGLE_PROTOBUF_MIN_PROTOC_VERSION 3000000
+
+// The minimum header version which works with the current version of
+// protoc. This constant should only be used in VerifyVersion().
+static const int kMinHeaderVersionForProtoc = 3000000;
+
+// Verifies that the headers and libraries are compatible. Use the macro
+// below to call this.
+void LIBPROTOBUF_EXPORT VerifyVersion(int headerVersion, int minLibraryVersion,
+ const char* filename);
+
+// Converts a numeric version number to a string.
+std::string LIBPROTOBUF_EXPORT VersionString(int version);
+
+} // namespace internal
+
+// Place this macro in your main() function (or somewhere before you attempt
+// to use the protobuf library) to verify that the version you link against
+// matches the headers you compiled against. If a version mismatch is
+// detected, the process will abort.
+#define GOOGLE_PROTOBUF_VERIFY_VERSION \
+ ::google::protobuf::internal::VerifyVersion( \
+ GOOGLE_PROTOBUF_VERSION, GOOGLE_PROTOBUF_MIN_LIBRARY_VERSION, \
+ __FILE__)
+
+
+// ===================================================================
+// from google3/util/utf8/public/unilib.h
+
+class StringPiece;
+namespace internal {
+
+// Checks if the buffer contains structurally-valid UTF-8. Implemented in
+// structurally_valid.cc.
+LIBPROTOBUF_EXPORT bool IsStructurallyValidUTF8(const char* buf, int len);
+
+inline bool IsStructurallyValidUTF8(const std::string& str) {
+ return IsStructurallyValidUTF8(str.data(), static_cast<int>(str.length()));
+}
+
+// Returns initial number of bytes of structually valid UTF-8.
+LIBPROTOBUF_EXPORT int UTF8SpnStructurallyValid(const StringPiece& str);
+
+// Coerce UTF-8 byte string in src_str to be
+// a structurally-valid equal-length string by selectively
+// overwriting illegal bytes with replace_char (typically ' ' or '?').
+// replace_char must be legal printable 7-bit Ascii 0x20..0x7e.
+// src_str is read-only.
+//
+// Returns pointer to output buffer, src_str.data() if no changes were made,
+// or idst if some bytes were changed. idst is allocated by the caller
+// and must be at least as big as src_str
+//
+// Optimized for: all structurally valid and no byte copying is done.
+//
+LIBPROTOBUF_EXPORT char* UTF8CoerceToStructurallyValid(
+ const StringPiece& str, char* dst, char replace_char);
+
+} // namespace internal
+
+
+// ===================================================================
+// Shutdown support.
+
+// Shut down the entire protocol buffers library, deleting all static-duration
+// objects allocated by the library or by generated .pb.cc files.
+//
+// There are two reasons you might want to call this:
+// * You use a draconian definition of "memory leak" in which you expect
+// every single malloc() to have a corresponding free(), even for objects
+// which live until program exit.
+// * You are writing a dynamically-loaded library which needs to clean up
+// after itself when the library is unloaded.
+//
+// It is safe to call this multiple times. However, it is not safe to use
+// any other part of the protocol buffers library after
+// ShutdownProtobufLibrary() has been called.
+LIBPROTOBUF_EXPORT void ShutdownProtobufLibrary();
+
+namespace internal {
+
+// Register a function to be called when ShutdownProtocolBuffers() is called.
+LIBPROTOBUF_EXPORT void OnShutdown(void (*func)());
+
+} // namespace internal
+
+#if PROTOBUF_USE_EXCEPTIONS
+class FatalException : public std::exception {
+ public:
+ FatalException(const char* filename, int line, const std::string& message)
+ : filename_(filename), line_(line), message_(message) {}
+ virtual ~FatalException() throw();
+
+ virtual const char* what() const throw();
+
+ const char* filename() const { return filename_; }
+ int line() const { return line_; }
+ const std::string& message() const { return message_; }
+
+ private:
+ const char* filename_;
+ const int line_;
+ const std::string message_;
+};
+#endif
+
+// This is at the end of the file instead of the beginning to work around a bug
+// in some versions of MSVC.
+using namespace std; // Don't do this at home, kids.
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_COMMON_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common_unittest.cc
new file mode 100644
index 0000000000..25bae9b074
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/common_unittest.cc
@@ -0,0 +1,358 @@
+// 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)
+
+#include <vector>
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+using internal::NewCallback;
+using internal::NewPermanentCallback;
+namespace {
+
+// TODO(kenton): More tests.
+
+#ifdef PACKAGE_VERSION // only defined when using automake, not MSVC
+
+TEST(VersionTest, VersionMatchesConfig) {
+ // Verify that the version string specified in config.h matches the one
+ // in common.h. The config.h version is a string which may have a suffix
+ // like "beta" or "rc1", so we remove that.
+ string version = PACKAGE_VERSION;
+ int pos = 0;
+ while (pos < version.size() &&
+ (ascii_isdigit(version[pos]) || version[pos] == '.')) {
+ ++pos;
+ }
+ version.erase(pos);
+
+ EXPECT_EQ(version, internal::VersionString(GOOGLE_PROTOBUF_VERSION));
+}
+
+#endif // PACKAGE_VERSION
+
+TEST(CommonTest, IntMinMaxConstants) {
+ // kint32min was declared incorrectly in the first release of protobufs.
+ // Ugh.
+ EXPECT_LT(kint32min, kint32max);
+ EXPECT_EQ(static_cast<uint32>(kint32min), static_cast<uint32>(kint32max) + 1);
+ EXPECT_LT(kint64min, kint64max);
+ EXPECT_EQ(static_cast<uint64>(kint64min), static_cast<uint64>(kint64max) + 1);
+ EXPECT_EQ(0, kuint32max + 1);
+ EXPECT_EQ(0, kuint64max + 1);
+}
+
+vector<string> captured_messages_;
+
+void CaptureLog(LogLevel level, const char* filename, int line,
+ const string& message) {
+ captured_messages_.push_back(
+ strings::Substitute("$0 $1:$2: $3",
+ implicit_cast<int>(level), filename, line, message));
+}
+
+TEST(LoggingTest, DefaultLogging) {
+ CaptureTestStderr();
+ int line = __LINE__;
+ GOOGLE_LOG(INFO ) << "A message.";
+ GOOGLE_LOG(WARNING) << "A warning.";
+ GOOGLE_LOG(ERROR ) << "An error.";
+
+ string text = GetCapturedTestStderr();
+ EXPECT_EQ(
+ "[libprotobuf INFO " __FILE__ ":" + SimpleItoa(line + 1) + "] A message.\n"
+ "[libprotobuf WARNING " __FILE__ ":" + SimpleItoa(line + 2) + "] A warning.\n"
+ "[libprotobuf ERROR " __FILE__ ":" + SimpleItoa(line + 3) + "] An error.\n",
+ text);
+}
+
+TEST(LoggingTest, NullLogging) {
+ LogHandler* old_handler = SetLogHandler(NULL);
+
+ CaptureTestStderr();
+ GOOGLE_LOG(INFO ) << "A message.";
+ GOOGLE_LOG(WARNING) << "A warning.";
+ GOOGLE_LOG(ERROR ) << "An error.";
+
+ EXPECT_TRUE(SetLogHandler(old_handler) == NULL);
+
+ string text = GetCapturedTestStderr();
+ EXPECT_EQ("", text);
+}
+
+TEST(LoggingTest, CaptureLogging) {
+ captured_messages_.clear();
+
+ LogHandler* old_handler = SetLogHandler(&CaptureLog);
+
+ int start_line = __LINE__;
+ GOOGLE_LOG(ERROR) << "An error.";
+ GOOGLE_LOG(WARNING) << "A warning.";
+
+ EXPECT_TRUE(SetLogHandler(old_handler) == &CaptureLog);
+
+ ASSERT_EQ(2, captured_messages_.size());
+ EXPECT_EQ(
+ "2 " __FILE__ ":" + SimpleItoa(start_line + 1) + ": An error.",
+ captured_messages_[0]);
+ EXPECT_EQ(
+ "1 " __FILE__ ":" + SimpleItoa(start_line + 2) + ": A warning.",
+ captured_messages_[1]);
+}
+
+TEST(LoggingTest, SilenceLogging) {
+ captured_messages_.clear();
+
+ LogHandler* old_handler = SetLogHandler(&CaptureLog);
+
+ int line1 = __LINE__; GOOGLE_LOG(INFO) << "Visible1";
+ LogSilencer* silencer1 = new LogSilencer;
+ GOOGLE_LOG(INFO) << "Not visible.";
+ LogSilencer* silencer2 = new LogSilencer;
+ GOOGLE_LOG(INFO) << "Not visible.";
+ delete silencer1;
+ GOOGLE_LOG(INFO) << "Not visible.";
+ delete silencer2;
+ int line2 = __LINE__; GOOGLE_LOG(INFO) << "Visible2";
+
+ EXPECT_TRUE(SetLogHandler(old_handler) == &CaptureLog);
+
+ ASSERT_EQ(2, captured_messages_.size());
+ EXPECT_EQ(
+ "0 " __FILE__ ":" + SimpleItoa(line1) + ": Visible1",
+ captured_messages_[0]);
+ EXPECT_EQ(
+ "0 " __FILE__ ":" + SimpleItoa(line2) + ": Visible2",
+ captured_messages_[1]);
+}
+
+class ClosureTest : public testing::Test {
+ public:
+ void SetA123Method() { a_ = 123; }
+ static void SetA123Function() { current_instance_->a_ = 123; }
+
+ void SetAMethod(int a) { a_ = a; }
+ void SetCMethod(string c) { c_ = c; }
+
+ static void SetAFunction(int a) { current_instance_->a_ = a; }
+ static void SetCFunction(string c) { current_instance_->c_ = c; }
+
+ void SetABMethod(int a, const char* b) { a_ = a; b_ = b; }
+ static void SetABFunction(int a, const char* b) {
+ current_instance_->a_ = a;
+ current_instance_->b_ = b;
+ }
+
+ virtual void SetUp() {
+ current_instance_ = this;
+ a_ = 0;
+ b_ = NULL;
+ c_.clear();
+ permanent_closure_ = NULL;
+ }
+
+ void DeleteClosureInCallback() {
+ delete permanent_closure_;
+ }
+
+ int a_;
+ const char* b_;
+ string c_;
+ Closure* permanent_closure_;
+
+ static ClosureTest* current_instance_;
+};
+
+ClosureTest* ClosureTest::current_instance_ = NULL;
+
+TEST_F(ClosureTest, TestClosureFunction0) {
+ Closure* closure = NewCallback(&SetA123Function);
+ EXPECT_NE(123, a_);
+ closure->Run();
+ EXPECT_EQ(123, a_);
+}
+
+TEST_F(ClosureTest, TestClosureMethod0) {
+ Closure* closure = NewCallback(current_instance_,
+ &ClosureTest::SetA123Method);
+ EXPECT_NE(123, a_);
+ closure->Run();
+ EXPECT_EQ(123, a_);
+}
+
+TEST_F(ClosureTest, TestClosureFunction1) {
+ Closure* closure = NewCallback(&SetAFunction, 456);
+ EXPECT_NE(456, a_);
+ closure->Run();
+ EXPECT_EQ(456, a_);
+}
+
+TEST_F(ClosureTest, TestClosureMethod1) {
+ Closure* closure = NewCallback(current_instance_,
+ &ClosureTest::SetAMethod, 456);
+ EXPECT_NE(456, a_);
+ closure->Run();
+ EXPECT_EQ(456, a_);
+}
+
+TEST_F(ClosureTest, TestClosureFunction1String) {
+ Closure* closure = NewCallback(&SetCFunction, string("test"));
+ EXPECT_NE("test", c_);
+ closure->Run();
+ EXPECT_EQ("test", c_);
+}
+
+TEST_F(ClosureTest, TestClosureMethod1String) {
+ Closure* closure = NewCallback(current_instance_,
+ &ClosureTest::SetCMethod, string("test"));
+ EXPECT_NE("test", c_);
+ closure->Run();
+ EXPECT_EQ("test", c_);
+}
+
+TEST_F(ClosureTest, TestClosureFunction2) {
+ const char* cstr = "hello";
+ Closure* closure = NewCallback(&SetABFunction, 789, cstr);
+ EXPECT_NE(789, a_);
+ EXPECT_NE(cstr, b_);
+ closure->Run();
+ EXPECT_EQ(789, a_);
+ EXPECT_EQ(cstr, b_);
+}
+
+TEST_F(ClosureTest, TestClosureMethod2) {
+ const char* cstr = "hello";
+ Closure* closure = NewCallback(current_instance_,
+ &ClosureTest::SetABMethod, 789, cstr);
+ EXPECT_NE(789, a_);
+ EXPECT_NE(cstr, b_);
+ closure->Run();
+ EXPECT_EQ(789, a_);
+ EXPECT_EQ(cstr, b_);
+}
+
+// Repeat all of the above with NewPermanentCallback()
+
+TEST_F(ClosureTest, TestPermanentClosureFunction0) {
+ Closure* closure = NewPermanentCallback(&SetA123Function);
+ EXPECT_NE(123, a_);
+ closure->Run();
+ EXPECT_EQ(123, a_);
+ a_ = 0;
+ closure->Run();
+ EXPECT_EQ(123, a_);
+ delete closure;
+}
+
+TEST_F(ClosureTest, TestPermanentClosureMethod0) {
+ Closure* closure = NewPermanentCallback(current_instance_,
+ &ClosureTest::SetA123Method);
+ EXPECT_NE(123, a_);
+ closure->Run();
+ EXPECT_EQ(123, a_);
+ a_ = 0;
+ closure->Run();
+ EXPECT_EQ(123, a_);
+ delete closure;
+}
+
+TEST_F(ClosureTest, TestPermanentClosureFunction1) {
+ Closure* closure = NewPermanentCallback(&SetAFunction, 456);
+ EXPECT_NE(456, a_);
+ closure->Run();
+ EXPECT_EQ(456, a_);
+ a_ = 0;
+ closure->Run();
+ EXPECT_EQ(456, a_);
+ delete closure;
+}
+
+TEST_F(ClosureTest, TestPermanentClosureMethod1) {
+ Closure* closure = NewPermanentCallback(current_instance_,
+ &ClosureTest::SetAMethod, 456);
+ EXPECT_NE(456, a_);
+ closure->Run();
+ EXPECT_EQ(456, a_);
+ a_ = 0;
+ closure->Run();
+ EXPECT_EQ(456, a_);
+ delete closure;
+}
+
+TEST_F(ClosureTest, TestPermanentClosureFunction2) {
+ const char* cstr = "hello";
+ Closure* closure = NewPermanentCallback(&SetABFunction, 789, cstr);
+ EXPECT_NE(789, a_);
+ EXPECT_NE(cstr, b_);
+ closure->Run();
+ EXPECT_EQ(789, a_);
+ EXPECT_EQ(cstr, b_);
+ a_ = 0;
+ b_ = NULL;
+ closure->Run();
+ EXPECT_EQ(789, a_);
+ EXPECT_EQ(cstr, b_);
+ delete closure;
+}
+
+TEST_F(ClosureTest, TestPermanentClosureMethod2) {
+ const char* cstr = "hello";
+ Closure* closure = NewPermanentCallback(current_instance_,
+ &ClosureTest::SetABMethod, 789, cstr);
+ EXPECT_NE(789, a_);
+ EXPECT_NE(cstr, b_);
+ closure->Run();
+ EXPECT_EQ(789, a_);
+ EXPECT_EQ(cstr, b_);
+ a_ = 0;
+ b_ = NULL;
+ closure->Run();
+ EXPECT_EQ(789, a_);
+ EXPECT_EQ(cstr, b_);
+ delete closure;
+}
+
+TEST_F(ClosureTest, TestPermanentClosureDeleteInCallback) {
+ permanent_closure_ = NewPermanentCallback((ClosureTest*) this,
+ &ClosureTest::DeleteClosureInCallback);
+ permanent_closure_->Run();
+}
+
+} // anonymous namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/fastmem.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/fastmem.h
new file mode 100644
index 0000000000..763a6e6024
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/fastmem.h
@@ -0,0 +1,152 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+
+// Fast memory copying and comparison routines.
+// strings::fastmemcmp_inlined() replaces memcmp()
+// strings::memcpy_inlined() replaces memcpy()
+// strings::memeq(a, b, n) replaces memcmp(a, b, n) == 0
+//
+// strings::*_inlined() routines are inline versions of the
+// routines exported by this module. Sometimes using the inlined
+// versions is faster. Measure before using the inlined versions.
+//
+// Performance measurement:
+// strings::fastmemcmp_inlined
+// Analysis: memcmp, fastmemcmp_inlined, fastmemcmp
+// 2012-01-30
+
+#ifndef GOOGLE_PROTOBUF_STUBS_FASTMEM_H_
+#define GOOGLE_PROTOBUF_STUBS_FASTMEM_H_
+
+#include <stddef.h>
+#include <stdio.h>
+#include <string.h>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Return true if the n bytes at a equal the n bytes at b.
+// The regions are allowed to overlap.
+//
+// The performance is similar to the performance memcmp(), but faster for
+// moderately-sized inputs, or inputs that share a common prefix and differ
+// somewhere in their last 8 bytes. Further optimizations can be added later
+// if it makes sense to do so.:w
+inline bool memeq(const char* a, const char* b, size_t n) {
+ size_t n_rounded_down = n & ~static_cast<size_t>(7);
+ if (GOOGLE_PREDICT_FALSE(n_rounded_down == 0)) { // n <= 7
+ return memcmp(a, b, n) == 0;
+ }
+ // n >= 8
+ uint64 u = GOOGLE_UNALIGNED_LOAD64(a) ^ GOOGLE_UNALIGNED_LOAD64(b);
+ uint64 v = GOOGLE_UNALIGNED_LOAD64(a + n - 8) ^ GOOGLE_UNALIGNED_LOAD64(b + n - 8);
+ if ((u | v) != 0) { // The first or last 8 bytes differ.
+ return false;
+ }
+ a += 8;
+ b += 8;
+ n = n_rounded_down - 8;
+ if (n > 128) {
+ // As of 2012, memcmp on x86-64 uses a big unrolled loop with SSE2
+ // instructions, and while we could try to do something faster, it
+ // doesn't seem worth pursuing.
+ return memcmp(a, b, n) == 0;
+ }
+ for (; n >= 16; n -= 16) {
+ uint64 x = GOOGLE_UNALIGNED_LOAD64(a) ^ GOOGLE_UNALIGNED_LOAD64(b);
+ uint64 y = GOOGLE_UNALIGNED_LOAD64(a + 8) ^ GOOGLE_UNALIGNED_LOAD64(b + 8);
+ if ((x | y) != 0) {
+ return false;
+ }
+ a += 16;
+ b += 16;
+ }
+ // n must be 0 or 8 now because it was a multiple of 8 at the top of the loop.
+ return n == 0 || GOOGLE_UNALIGNED_LOAD64(a) == GOOGLE_UNALIGNED_LOAD64(b);
+}
+
+inline int fastmemcmp_inlined(const char *a, const char *b, size_t n) {
+ if (n >= 64) {
+ return memcmp(a, b, n);
+ }
+ const char* a_limit = a + n;
+ while (a + sizeof(uint64) <= a_limit &&
+ GOOGLE_UNALIGNED_LOAD64(a) == GOOGLE_UNALIGNED_LOAD64(b)) {
+ a += sizeof(uint64);
+ b += sizeof(uint64);
+ }
+ if (a + sizeof(uint32) <= a_limit &&
+ GOOGLE_UNALIGNED_LOAD32(a) == GOOGLE_UNALIGNED_LOAD32(b)) {
+ a += sizeof(uint32);
+ b += sizeof(uint32);
+ }
+ while (a < a_limit) {
+ int d = static_cast<uint32>(*a++) - static_cast<uint32>(*b++);
+ if (d) return d;
+ }
+ return 0;
+}
+
+// The standard memcpy operation is slow for variable small sizes.
+// This implementation inlines the optimal realization for sizes 1 to 16.
+// To avoid code bloat don't use it in case of not performance-critical spots,
+// nor when you don't expect very frequent values of size <= 16.
+inline void memcpy_inlined(char *dst, const char *src, size_t size) {
+ // Compiler inlines code with minimal amount of data movement when third
+ // parameter of memcpy is a constant.
+ switch (size) {
+ case 1: memcpy(dst, src, 1); break;
+ case 2: memcpy(dst, src, 2); break;
+ case 3: memcpy(dst, src, 3); break;
+ case 4: memcpy(dst, src, 4); break;
+ case 5: memcpy(dst, src, 5); break;
+ case 6: memcpy(dst, src, 6); break;
+ case 7: memcpy(dst, src, 7); break;
+ case 8: memcpy(dst, src, 8); break;
+ case 9: memcpy(dst, src, 9); break;
+ case 10: memcpy(dst, src, 10); break;
+ case 11: memcpy(dst, src, 11); break;
+ case 12: memcpy(dst, src, 12); break;
+ case 13: memcpy(dst, src, 13); break;
+ case 14: memcpy(dst, src, 14); break;
+ case 15: memcpy(dst, src, 15); break;
+ case 16: memcpy(dst, src, 16); break;
+ default: memcpy(dst, src, size); break;
+ }
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_FASTMEM_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/hash.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/hash.h
new file mode 100644
index 0000000000..4eac7d5d25
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/hash.h
@@ -0,0 +1,438 @@
+// 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)
+//
+// Deals with the fact that hash_map is not defined everywhere.
+
+#ifndef GOOGLE_PROTOBUF_STUBS_HASH_H__
+#define GOOGLE_PROTOBUF_STUBS_HASH_H__
+
+#include <string.h>
+#include <google/protobuf/stubs/common.h>
+
+#define GOOGLE_PROTOBUF_HAVE_HASH_MAP 1
+#define GOOGLE_PROTOBUF_HAVE_HASH_SET 1
+
+// Android
+#if defined(__ANDROID__)
+# undef GOOGLE_PROTOBUF_HAVE_HASH_MAP
+# undef GOOGLE_PROTOBUF_HAVE_HASH_MAP
+
+// Use C++11 unordered_{map|set} if available.
+#elif ((_LIBCPP_STD_VER >= 11) || \
+ (((__cplusplus >= 201103L) || defined(__GXX_EXPERIMENTAL_CXX0X)) && \
+ (__GLIBCXX__ > 20090421)))
+# define GOOGLE_PROTOBUF_HAS_CXX11_HASH
+
+// For XCode >= 4.6: the compiler is clang with libc++.
+// For earlier XCode version: the compiler is gcc-4.2.1 with libstdc++.
+// libc++ provides <unordered_map> and friends even in non C++11 mode,
+// and it does not provide the tr1 library. Therefore the following macro
+// checks against this special case.
+// Note that we should not test the __APPLE_CC__ version number or the
+// __clang__ macro, since the new compiler can still use -stdlib=libstdc++, in
+// which case <unordered_map> is not compilable without -std=c++11
+#elif defined(__APPLE_CC__)
+# if __GNUC__ >= 4
+# define GOOGLE_PROTOBUF_HAS_TR1
+# else
+// Not tested for gcc < 4... These setting can compile under 4.2.1 though.
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE __gnu_cxx
+# include <ext/hash_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS hash_map
+# include <ext/hash_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS hash_set
+# endif
+
+// Version checks for gcc.
+#elif defined(__GNUC__)
+// For GCC 4.x+, use tr1::unordered_map/set; otherwise, follow the
+// instructions from:
+// https://gcc.gnu.org/onlinedocs/libstdc++/manual/backwards.html
+# if __GNUC__ >= 4
+# define GOOGLE_PROTOBUF_HAS_TR1
+# elif __GNUC__ >= 3
+# include <backward/hash_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS hash_map
+# include <backward/hash_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS hash_set
+# if __GNUC__ == 3 && __GNUC_MINOR__ == 0
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE std // GCC 3.0
+# else
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE __gnu_cxx // GCC 3.1 and later
+# endif
+# else
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE
+# include <hash_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS hash_map
+# include <hash_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS hash_set
+# endif
+
+// Version checks for MSC.
+// Apparently Microsoft decided to move hash_map *back* to the std namespace in
+// MSVC 2010:
+// http://blogs.msdn.com/vcblog/archive/2009/05/25/stl-breaking-changes-in-visual-studio-2010-beta-1.aspx
+// And.. they are moved back to stdext in MSVC 2013 (haven't checked 2012). That
+// said, use unordered_map for MSVC 2010 and beyond is our safest bet.
+#elif defined(_MSC_VER)
+# if _MSC_VER >= 1600 // Since Visual Studio 2010
+# define GOOGLE_PROTOBUF_HAS_CXX11_HASH
+# define GOOGLE_PROTOBUF_HASH_COMPARE std::hash_compare
+# elif _MSC_VER >= 1500 // Since Visual Studio 2008
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE stdext
+# include <hash_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS hash_map
+# include <hash_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS hash_set
+# define GOOGLE_PROTOBUF_HASH_COMPARE stdext::hash_compare
+# define GOOGLE_PROTOBUF_CONTAINERS_NEED_HASH_COMPARE
+# elif _MSC_VER >= 1310
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE stdext
+# include <hash_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS hash_map
+# include <hash_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS hash_set
+# define GOOGLE_PROTOBUF_HASH_COMPARE stdext::hash_compare
+# else
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE std
+# include <hash_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS hash_map
+# include <hash_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS hash_set
+# define GOOGLE_PROTOBUF_HASH_COMPARE stdext::hash_compare
+# endif
+
+// **ADD NEW COMPILERS SUPPORT HERE.**
+// For other compilers, undefine the macro and fallback to use std::map, in
+// google/protobuf/stubs/hash.h
+#else
+# undef GOOGLE_PROTOBUF_HAVE_HASH_MAP
+# undef GOOGLE_PROTOBUF_HAVE_HASH_SET
+#endif
+
+#if defined(GOOGLE_PROTOBUF_HAS_CXX11_HASH)
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE std
+# include <unordered_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS unordered_map
+# include <unordered_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS unordered_set
+#elif defined(GOOGLE_PROTOBUF_HAS_TR1)
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE std::tr1
+# include <tr1/unordered_map>
+# define GOOGLE_PROTOBUF_HASH_MAP_CLASS unordered_map
+# include <tr1/unordered_set>
+# define GOOGLE_PROTOBUF_HASH_SET_CLASS unordered_set
+#endif
+
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE_DECLARATION_START \
+ namespace google { \
+ namespace protobuf {
+# define GOOGLE_PROTOBUF_HASH_NAMESPACE_DECLARATION_END }}
+
+#undef GOOGLE_PROTOBUF_HAS_CXX11_HASH
+#undef GOOGLE_PROTOBUF_HAS_TR1
+
+#if defined(GOOGLE_PROTOBUF_HAVE_HASH_MAP) && \
+ defined(GOOGLE_PROTOBUF_HAVE_HASH_SET)
+#else
+#define GOOGLE_PROTOBUF_MISSING_HASH
+#include <map>
+#include <set>
+#endif
+
+namespace google {
+namespace protobuf {
+
+#ifdef GOOGLE_PROTOBUF_MISSING_HASH
+#undef GOOGLE_PROTOBUF_MISSING_HASH
+
+// This system doesn't have hash_map or hash_set. Emulate them using map and
+// set.
+
+// Make hash<T> be the same as less<T>. Note that everywhere where custom
+// hash functions are defined in the protobuf code, they are also defined such
+// that they can be used as "less" functions, which is required by MSVC anyway.
+template <typename Key>
+struct hash {
+ // Dummy, just to make derivative hash functions compile.
+ int operator()(const Key& key) {
+ GOOGLE_LOG(FATAL) << "Should never be called.";
+ return 0;
+ }
+
+ inline bool operator()(const Key& a, const Key& b) const {
+ return a < b;
+ }
+};
+
+// Make sure char* is compared by value.
+template <>
+struct hash<const char*> {
+ // Dummy, just to make derivative hash functions compile.
+ int operator()(const char* key) {
+ GOOGLE_LOG(FATAL) << "Should never be called.";
+ return 0;
+ }
+
+ inline bool operator()(const char* a, const char* b) const {
+ return strcmp(a, b) < 0;
+ }
+};
+
+template <typename Key, typename Data,
+ typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key>,
+ typename Alloc = std::allocator< std::pair<const Key, Data> > >
+class hash_map : public std::map<Key, Data, HashFcn, Alloc> {
+ typedef std::map<Key, Data, HashFcn, Alloc> BaseClass;
+
+ public:
+ hash_map(int a = 0, const HashFcn& b = HashFcn(),
+ const EqualKey& c = EqualKey(),
+ const Alloc& d = Alloc()) : BaseClass(b, d) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+
+template <typename Key,
+ typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key> >
+class hash_set : public std::set<Key, HashFcn> {
+ public:
+ hash_set(int = 0) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+
+#elif defined(_MSC_VER) && !defined(_STLPORT_VERSION)
+
+template <typename Key>
+struct hash : public GOOGLE_PROTOBUF_HASH_COMPARE<Key> {
+};
+
+// MSVC's hash_compare<const char*> hashes based on the string contents but
+// compares based on the string pointer. WTF?
+class CstringLess {
+ public:
+ inline bool operator()(const char* a, const char* b) const {
+ return strcmp(a, b) < 0;
+ }
+};
+
+template <>
+struct hash<const char*>
+ : public GOOGLE_PROTOBUF_HASH_COMPARE<const char*, CstringLess> {};
+
+#ifdef GOOGLE_PROTOBUF_CONTAINERS_NEED_HASH_COMPARE
+
+template <typename Key, typename HashFcn, typename EqualKey>
+struct InternalHashCompare : public GOOGLE_PROTOBUF_HASH_COMPARE<Key> {
+ InternalHashCompare() {}
+ InternalHashCompare(HashFcn hashfcn, EqualKey equalkey)
+ : hashfcn_(hashfcn), equalkey_(equalkey) {}
+ size_t operator()(const Key& key) const { return hashfcn_(key); }
+ bool operator()(const Key& key1, const Key& key2) const {
+ return !equalkey_(key1, key2);
+ }
+ HashFcn hashfcn_;
+ EqualKey equalkey_;
+};
+
+template <typename Key, typename Data,
+ typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key>,
+ typename Alloc = std::allocator< std::pair<const Key, Data> > >
+class hash_map
+ : public GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_MAP_CLASS<
+ Key, Data, InternalHashCompare<Key, HashFcn, EqualKey>, Alloc> {
+ typedef GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_MAP_CLASS<
+ Key, Data, InternalHashCompare<Key, HashFcn, EqualKey>, Alloc> BaseClass;
+
+ public:
+ hash_map(int a = 0, const HashFcn& b = HashFcn(),
+ const EqualKey& c = EqualKey(), const Alloc& d = Alloc())
+ : BaseClass(InternalHashCompare<Key, HashFcn, EqualKey>(b, c), d) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+
+template <typename Key, typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key> >
+class hash_set
+ : public GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_SET_CLASS<
+ Key, InternalHashCompare<Key, HashFcn, EqualKey> > {
+ public:
+ hash_set(int = 0) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+
+#else // GOOGLE_PROTOBUF_CONTAINERS_NEED_HASH_COMPARE
+
+template <typename Key, typename Data,
+ typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key>,
+ typename Alloc = std::allocator< std::pair<const Key, Data> > >
+class hash_map
+ : public GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_MAP_CLASS<
+ Key, Data, HashFcn, EqualKey, Alloc> {
+ typedef GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_MAP_CLASS<
+ Key, Data, HashFcn, EqualKey, Alloc> BaseClass;
+
+ public:
+ hash_map(int a = 0, const HashFcn& b = HashFcn(),
+ const EqualKey& c = EqualKey(),
+ const Alloc& d = Alloc()) : BaseClass(a, b, c, d) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+
+template <typename Key, typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key> >
+class hash_set
+ : public GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_SET_CLASS<
+ Key, HashFcn, EqualKey> {
+ public:
+ hash_set(int = 0) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+#endif // GOOGLE_PROTOBUF_CONTAINERS_NEED_HASH_COMPARE
+
+#else // defined(_MSC_VER) && !defined(_STLPORT_VERSION)
+
+template <typename Key>
+struct hash : public GOOGLE_PROTOBUF_HASH_NAMESPACE::hash<Key> {
+};
+
+template <typename Key>
+struct hash<const Key*> {
+ inline size_t operator()(const Key* key) const {
+ return reinterpret_cast<size_t>(key);
+ }
+};
+
+// Unlike the old SGI version, the TR1 "hash" does not special-case char*. So,
+// we go ahead and provide our own implementation.
+template <>
+struct hash<const char*> {
+ inline size_t operator()(const char* str) const {
+ size_t result = 0;
+ for (; *str != '\0'; str++) {
+ result = 5 * result + *str;
+ }
+ return result;
+ }
+};
+
+template<>
+struct hash<bool> {
+ size_t operator()(bool x) const {
+ return static_cast<size_t>(x);
+ }
+};
+
+template <typename Key, typename Data,
+ typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key>,
+ typename Alloc = std::allocator< std::pair<const Key, Data> > >
+class hash_map
+ : public GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_MAP_CLASS<
+ Key, Data, HashFcn, EqualKey, Alloc> {
+ typedef GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_MAP_CLASS<
+ Key, Data, HashFcn, EqualKey, Alloc> BaseClass;
+
+ public:
+ hash_map(int a = 0, const HashFcn& b = HashFcn(),
+ const EqualKey& c = EqualKey(),
+ const Alloc& d = Alloc()) : BaseClass(a, b, c, d) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+
+template <typename Key, typename HashFcn = hash<Key>,
+ typename EqualKey = std::equal_to<Key> >
+class hash_set
+ : public GOOGLE_PROTOBUF_HASH_NAMESPACE::GOOGLE_PROTOBUF_HASH_SET_CLASS<
+ Key, HashFcn, EqualKey> {
+ public:
+ hash_set(int = 0) {}
+
+ HashFcn hash_function() const { return HashFcn(); }
+};
+
+#endif // !GOOGLE_PROTOBUF_MISSING_HASH
+
+template <>
+struct hash<string> {
+ inline size_t operator()(const string& key) const {
+ return hash<const char*>()(key.c_str());
+ }
+
+ static const size_t bucket_size = 4;
+ static const size_t min_buckets = 8;
+ inline bool operator()(const string& a, const string& b) const {
+ return a < b;
+ }
+};
+
+template <typename First, typename Second>
+struct hash<pair<First, Second> > {
+ inline size_t operator()(const pair<First, Second>& key) const {
+ size_t first_hash = hash<First>()(key.first);
+ size_t second_hash = hash<Second>()(key.second);
+
+ // FIXME(kenton): What is the best way to compute this hash? I have
+ // no idea! This seems a bit better than an XOR.
+ return first_hash * ((1 << 16) - 1) + second_hash;
+ }
+
+ static const size_t bucket_size = 4;
+ static const size_t min_buckets = 8;
+ inline bool operator()(const pair<First, Second>& a,
+ const pair<First, Second>& b) const {
+ return a < b;
+ }
+};
+
+// Used by GCC/SGI STL only. (Why isn't this provided by the standard
+// library? :( )
+struct streq {
+ inline bool operator()(const char* a, const char* b) const {
+ return strcmp(a, b) == 0;
+ }
+};
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_HASH_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.cc
new file mode 100644
index 0000000000..a509080148
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.cc
@@ -0,0 +1,201 @@
+// 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.
+
+#include <google/protobuf/stubs/int128.h>
+
+#include <iomanip>
+#include <ostream> // NOLINT(readability/streams)
+#include <sstream>
+
+namespace google {
+namespace protobuf {
+
+const uint128_pod kuint128max = {
+ static_cast<uint64>(GOOGLE_LONGLONG(0xFFFFFFFFFFFFFFFF)),
+ static_cast<uint64>(GOOGLE_LONGLONG(0xFFFFFFFFFFFFFFFF))
+};
+
+// Returns the 0-based position of the last set bit (i.e., most significant bit)
+// in the given uint64. The argument may not be 0.
+//
+// For example:
+// Given: 5 (decimal) == 101 (binary)
+// Returns: 2
+#define STEP(T, n, pos, sh) \
+ do { \
+ if ((n) >= (static_cast<T>(1) << (sh))) { \
+ (n) = (n) >> (sh); \
+ (pos) |= (sh); \
+ } \
+ } while (0)
+static inline int Fls64(uint64 n) {
+ GOOGLE_DCHECK_NE(0, n);
+ int pos = 0;
+ STEP(uint64, n, pos, 0x20);
+ uint32 n32 = n;
+ STEP(uint32, n32, pos, 0x10);
+ STEP(uint32, n32, pos, 0x08);
+ STEP(uint32, n32, pos, 0x04);
+ return pos + ((GOOGLE_ULONGLONG(0x3333333322221100) >> (n32 << 2)) & 0x3);
+}
+#undef STEP
+
+// Like Fls64() above, but returns the 0-based position of the last set bit
+// (i.e., most significant bit) in the given uint128. The argument may not be 0.
+static inline int Fls128(uint128 n) {
+ if (uint64 hi = Uint128High64(n)) {
+ return Fls64(hi) + 64;
+ }
+ return Fls64(Uint128Low64(n));
+}
+
+// Long division/modulo for uint128 implemented using the shift-subtract
+// division algorithm adapted from:
+// http://stackoverflow.com/questions/5386377/division-without-using
+void uint128::DivModImpl(uint128 dividend, uint128 divisor,
+ uint128* quotient_ret, uint128* remainder_ret) {
+ if (divisor == 0) {
+ GOOGLE_LOG(FATAL) << "Division or mod by zero: dividend.hi=" << dividend.hi_
+ << ", lo=" << dividend.lo_;
+ }
+
+ if (divisor > dividend) {
+ *quotient_ret = 0;
+ *remainder_ret = dividend;
+ return;
+ }
+
+ if (divisor == dividend) {
+ *quotient_ret = 1;
+ *remainder_ret = 0;
+ return;
+ }
+
+ uint128 denominator = divisor;
+ uint128 position = 1;
+ uint128 quotient = 0;
+
+ // Left aligns the MSB of the denominator and the dividend.
+ int shift = Fls128(dividend) - Fls128(denominator);
+ denominator <<= shift;
+ position <<= shift;
+
+ // Uses shift-subtract algorithm to divide dividend by denominator. The
+ // remainder will be left in dividend.
+ while (position > 0) {
+ if (dividend >= denominator) {
+ dividend -= denominator;
+ quotient |= position;
+ }
+ position >>= 1;
+ denominator >>= 1;
+ }
+
+ *quotient_ret = quotient;
+ *remainder_ret = dividend;
+}
+
+uint128& uint128::operator/=(const uint128& divisor) {
+ uint128 quotient = 0;
+ uint128 remainder = 0;
+ DivModImpl(*this, divisor, &quotient, &remainder);
+ *this = quotient;
+ return *this;
+}
+uint128& uint128::operator%=(const uint128& divisor) {
+ uint128 quotient = 0;
+ uint128 remainder = 0;
+ DivModImpl(*this, divisor, &quotient, &remainder);
+ *this = remainder;
+ return *this;
+}
+
+std::ostream& operator<<(std::ostream& o, const uint128& b) {
+ std::ios_base::fmtflags flags = o.flags();
+
+ // Select a divisor which is the largest power of the base < 2^64.
+ uint128 div;
+ std::streamsize div_base_log;
+ switch (flags & std::ios::basefield) {
+ case std::ios::hex:
+ div = static_cast<uint64>(GOOGLE_ULONGLONG(0x1000000000000000)); // 16^15
+ div_base_log = 15;
+ break;
+ case std::ios::oct:
+ div = static_cast<uint64>(GOOGLE_ULONGLONG(01000000000000000000000)); // 8^21
+ div_base_log = 21;
+ break;
+ default: // std::ios::dec
+ div = static_cast<uint64>(GOOGLE_ULONGLONG(10000000000000000000)); // 10^19
+ div_base_log = 19;
+ break;
+ }
+
+ // Now piece together the uint128 representation from three chunks of
+ // the original value, each less than "div" and therefore representable
+ // as a uint64.
+ std::ostringstream os;
+ std::ios_base::fmtflags copy_mask =
+ std::ios::basefield | std::ios::showbase | std::ios::uppercase;
+ os.setf(flags & copy_mask, copy_mask);
+ uint128 high = b;
+ uint128 low;
+ uint128::DivModImpl(high, div, &high, &low);
+ uint128 mid;
+ uint128::DivModImpl(high, div, &high, &mid);
+ if (high.lo_ != 0) {
+ os << high.lo_;
+ os << std::noshowbase << std::setfill('0') << std::setw(div_base_log);
+ os << mid.lo_;
+ os << std::setw(div_base_log);
+ } else if (mid.lo_ != 0) {
+ os << mid.lo_;
+ os << std::noshowbase << std::setfill('0') << std::setw(div_base_log);
+ }
+ os << low.lo_;
+ std::string rep = os.str();
+
+ // Add the requisite padding.
+ std::streamsize width = o.width(0);
+ if (width > rep.size()) {
+ if ((flags & std::ios::adjustfield) == std::ios::left) {
+ rep.append(width - rep.size(), o.fill());
+ } else {
+ rep.insert(static_cast<std::string::size_type>(0),
+ width - rep.size(), o.fill());
+ }
+ }
+
+ // Stream the final representation in a single "<<" call.
+ return o << rep;
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.h
new file mode 100644
index 0000000000..1499bb76d5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128.h
@@ -0,0 +1,383 @@
+// 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.
+#ifndef GOOGLE_PROTOBUF_STUBS_INT128_H_
+#define GOOGLE_PROTOBUF_STUBS_INT128_H_
+
+#include <google/protobuf/stubs/common.h>
+
+#include <iosfwd>
+
+namespace google {
+namespace protobuf {
+
+struct uint128_pod;
+
+// TODO(xiaofeng): Define GOOGLE_PROTOBUF_HAS_CONSTEXPR when constexpr is
+// available.
+#ifdef GOOGLE_PROTOBUF_HAS_CONSTEXPR
+# define UINT128_CONSTEXPR constexpr
+#else
+# define UINT128_CONSTEXPR
+#endif
+
+// An unsigned 128-bit integer type. Thread-compatible.
+class LIBPROTOBUF_EXPORT uint128 {
+ public:
+ UINT128_CONSTEXPR uint128(); // Sets to 0, but don't trust on this behavior.
+ UINT128_CONSTEXPR uint128(uint64 top, uint64 bottom);
+#ifndef SWIG
+ UINT128_CONSTEXPR uint128(int bottom);
+ UINT128_CONSTEXPR uint128(uint32 bottom); // Top 96 bits = 0
+#endif
+ UINT128_CONSTEXPR uint128(uint64 bottom); // hi_ = 0
+ UINT128_CONSTEXPR uint128(const uint128_pod &val);
+
+ // Trivial copy constructor, assignment operator and destructor.
+
+ void Initialize(uint64 top, uint64 bottom);
+
+ // Arithmetic operators.
+ uint128& operator+=(const uint128& b);
+ uint128& operator-=(const uint128& b);
+ uint128& operator*=(const uint128& b);
+ // Long division/modulo for uint128.
+ uint128& operator/=(const uint128& b);
+ uint128& operator%=(const uint128& b);
+ uint128 operator++(int);
+ uint128 operator--(int);
+ uint128& operator<<=(int);
+ uint128& operator>>=(int);
+ uint128& operator&=(const uint128& b);
+ uint128& operator|=(const uint128& b);
+ uint128& operator^=(const uint128& b);
+ uint128& operator++();
+ uint128& operator--();
+
+ friend uint64 Uint128Low64(const uint128& v);
+ friend uint64 Uint128High64(const uint128& v);
+
+ // We add "std::" to avoid including all of port.h.
+ LIBPROTOBUF_EXPORT friend std::ostream& operator<<(std::ostream& o,
+ const uint128& b);
+
+ private:
+ static void DivModImpl(uint128 dividend, uint128 divisor,
+ uint128* quotient_ret, uint128* remainder_ret);
+
+ // Little-endian memory order optimizations can benefit from
+ // having lo_ first, hi_ last.
+ // See util/endian/endian.h and Load128/Store128 for storing a uint128.
+ uint64 lo_;
+ uint64 hi_;
+
+ // Not implemented, just declared for catching automatic type conversions.
+ uint128(uint8);
+ uint128(uint16);
+ uint128(float v);
+ uint128(double v);
+};
+
+// This is a POD form of uint128 which can be used for static variables which
+// need to be operated on as uint128.
+struct uint128_pod {
+ // Note: The ordering of fields is different than 'class uint128' but the
+ // same as its 2-arg constructor. This enables more obvious initialization
+ // of static instances, which is the primary reason for this struct in the
+ // first place. This does not seem to defeat any optimizations wrt
+ // operations involving this struct.
+ uint64 hi;
+ uint64 lo;
+};
+
+LIBPROTOBUF_EXPORT extern const uint128_pod kuint128max;
+
+// allow uint128 to be logged
+LIBPROTOBUF_EXPORT extern std::ostream& operator<<(std::ostream& o,
+ const uint128& b);
+
+// Methods to access low and high pieces of 128-bit value.
+// Defined externally from uint128 to facilitate conversion
+// to native 128-bit types when compilers support them.
+inline uint64 Uint128Low64(const uint128& v) { return v.lo_; }
+inline uint64 Uint128High64(const uint128& v) { return v.hi_; }
+
+// TODO: perhaps it would be nice to have int128, a signed 128-bit type?
+
+// --------------------------------------------------------------------------
+// Implementation details follow
+// --------------------------------------------------------------------------
+inline bool operator==(const uint128& lhs, const uint128& rhs) {
+ return (Uint128Low64(lhs) == Uint128Low64(rhs) &&
+ Uint128High64(lhs) == Uint128High64(rhs));
+}
+inline bool operator!=(const uint128& lhs, const uint128& rhs) {
+ return !(lhs == rhs);
+}
+
+inline UINT128_CONSTEXPR uint128::uint128() : lo_(0), hi_(0) {}
+inline UINT128_CONSTEXPR uint128::uint128(uint64 top, uint64 bottom)
+ : lo_(bottom), hi_(top) {}
+inline UINT128_CONSTEXPR uint128::uint128(const uint128_pod& v)
+ : lo_(v.lo), hi_(v.hi) {}
+inline UINT128_CONSTEXPR uint128::uint128(uint64 bottom)
+ : lo_(bottom), hi_(0) {}
+#ifndef SWIG
+inline UINT128_CONSTEXPR uint128::uint128(uint32 bottom)
+ : lo_(bottom), hi_(0) {}
+inline UINT128_CONSTEXPR uint128::uint128(int bottom)
+ : lo_(bottom), hi_(static_cast<int64>((bottom < 0) ? -1 : 0)) {}
+#endif
+
+#undef UINT128_CONSTEXPR
+
+inline void uint128::Initialize(uint64 top, uint64 bottom) {
+ hi_ = top;
+ lo_ = bottom;
+}
+
+// Comparison operators.
+
+#define CMP128(op) \
+inline bool operator op(const uint128& lhs, const uint128& rhs) { \
+ return (Uint128High64(lhs) == Uint128High64(rhs)) ? \
+ (Uint128Low64(lhs) op Uint128Low64(rhs)) : \
+ (Uint128High64(lhs) op Uint128High64(rhs)); \
+}
+
+CMP128(<)
+CMP128(>)
+CMP128(>=)
+CMP128(<=)
+
+#undef CMP128
+
+// Unary operators
+
+inline uint128 operator-(const uint128& val) {
+ const uint64 hi_flip = ~Uint128High64(val);
+ const uint64 lo_flip = ~Uint128Low64(val);
+ const uint64 lo_add = lo_flip + 1;
+ if (lo_add < lo_flip) {
+ return uint128(hi_flip + 1, lo_add);
+ }
+ return uint128(hi_flip, lo_add);
+}
+
+inline bool operator!(const uint128& val) {
+ return !Uint128High64(val) && !Uint128Low64(val);
+}
+
+// Logical operators.
+
+inline uint128 operator~(const uint128& val) {
+ return uint128(~Uint128High64(val), ~Uint128Low64(val));
+}
+
+#define LOGIC128(op) \
+inline uint128 operator op(const uint128& lhs, const uint128& rhs) { \
+ return uint128(Uint128High64(lhs) op Uint128High64(rhs), \
+ Uint128Low64(lhs) op Uint128Low64(rhs)); \
+}
+
+LOGIC128(|)
+LOGIC128(&)
+LOGIC128(^)
+
+#undef LOGIC128
+
+#define LOGICASSIGN128(op) \
+inline uint128& uint128::operator op(const uint128& other) { \
+ hi_ op other.hi_; \
+ lo_ op other.lo_; \
+ return *this; \
+}
+
+LOGICASSIGN128(|=)
+LOGICASSIGN128(&=)
+LOGICASSIGN128(^=)
+
+#undef LOGICASSIGN128
+
+// Shift operators.
+
+inline uint128 operator<<(const uint128& val, int amount) {
+ // uint64 shifts of >= 64 are undefined, so we will need some special-casing.
+ if (amount < 64) {
+ if (amount == 0) {
+ return val;
+ }
+ uint64 new_hi = (Uint128High64(val) << amount) |
+ (Uint128Low64(val) >> (64 - amount));
+ uint64 new_lo = Uint128Low64(val) << amount;
+ return uint128(new_hi, new_lo);
+ } else if (amount < 128) {
+ return uint128(Uint128Low64(val) << (amount - 64), 0);
+ } else {
+ return uint128(0, 0);
+ }
+}
+
+inline uint128 operator>>(const uint128& val, int amount) {
+ // uint64 shifts of >= 64 are undefined, so we will need some special-casing.
+ if (amount < 64) {
+ if (amount == 0) {
+ return val;
+ }
+ uint64 new_hi = Uint128High64(val) >> amount;
+ uint64 new_lo = (Uint128Low64(val) >> amount) |
+ (Uint128High64(val) << (64 - amount));
+ return uint128(new_hi, new_lo);
+ } else if (amount < 128) {
+ return uint128(0, Uint128High64(val) >> (amount - 64));
+ } else {
+ return uint128(0, 0);
+ }
+}
+
+inline uint128& uint128::operator<<=(int amount) {
+ // uint64 shifts of >= 64 are undefined, so we will need some special-casing.
+ if (amount < 64) {
+ if (amount != 0) {
+ hi_ = (hi_ << amount) | (lo_ >> (64 - amount));
+ lo_ = lo_ << amount;
+ }
+ } else if (amount < 128) {
+ hi_ = lo_ << (amount - 64);
+ lo_ = 0;
+ } else {
+ hi_ = 0;
+ lo_ = 0;
+ }
+ return *this;
+}
+
+inline uint128& uint128::operator>>=(int amount) {
+ // uint64 shifts of >= 64 are undefined, so we will need some special-casing.
+ if (amount < 64) {
+ if (amount != 0) {
+ lo_ = (lo_ >> amount) | (hi_ << (64 - amount));
+ hi_ = hi_ >> amount;
+ }
+ } else if (amount < 128) {
+ lo_ = hi_ >> (amount - 64);
+ hi_ = 0;
+ } else {
+ lo_ = 0;
+ hi_ = 0;
+ }
+ return *this;
+}
+
+inline uint128 operator+(const uint128& lhs, const uint128& rhs) {
+ return uint128(lhs) += rhs;
+}
+
+inline uint128 operator-(const uint128& lhs, const uint128& rhs) {
+ return uint128(lhs) -= rhs;
+}
+
+inline uint128 operator*(const uint128& lhs, const uint128& rhs) {
+ return uint128(lhs) *= rhs;
+}
+
+inline uint128 operator/(const uint128& lhs, const uint128& rhs) {
+ return uint128(lhs) /= rhs;
+}
+
+inline uint128 operator%(const uint128& lhs, const uint128& rhs) {
+ return uint128(lhs) %= rhs;
+}
+
+inline uint128& uint128::operator+=(const uint128& b) {
+ hi_ += b.hi_;
+ uint64 lolo = lo_ + b.lo_;
+ if (lolo < lo_)
+ ++hi_;
+ lo_ = lolo;
+ return *this;
+}
+
+inline uint128& uint128::operator-=(const uint128& b) {
+ hi_ -= b.hi_;
+ if (b.lo_ > lo_)
+ --hi_;
+ lo_ -= b.lo_;
+ return *this;
+}
+
+inline uint128& uint128::operator*=(const uint128& b) {
+ uint64 a96 = hi_ >> 32;
+ uint64 a64 = hi_ & 0xffffffffu;
+ uint64 a32 = lo_ >> 32;
+ uint64 a00 = lo_ & 0xffffffffu;
+ uint64 b96 = b.hi_ >> 32;
+ uint64 b64 = b.hi_ & 0xffffffffu;
+ uint64 b32 = b.lo_ >> 32;
+ uint64 b00 = b.lo_ & 0xffffffffu;
+ // multiply [a96 .. a00] x [b96 .. b00]
+ // terms higher than c96 disappear off the high side
+ // terms c96 and c64 are safe to ignore carry bit
+ uint64 c96 = a96 * b00 + a64 * b32 + a32 * b64 + a00 * b96;
+ uint64 c64 = a64 * b00 + a32 * b32 + a00 * b64;
+ this->hi_ = (c96 << 32) + c64;
+ this->lo_ = 0;
+ // add terms after this one at a time to capture carry
+ *this += uint128(a32 * b00) << 32;
+ *this += uint128(a00 * b32) << 32;
+ *this += a00 * b00;
+ return *this;
+}
+
+inline uint128 uint128::operator++(int) {
+ uint128 tmp(*this);
+ *this += 1;
+ return tmp;
+}
+
+inline uint128 uint128::operator--(int) {
+ uint128 tmp(*this);
+ *this -= 1;
+ return tmp;
+}
+
+inline uint128& uint128::operator++() {
+ *this += 1;
+ return *this;
+}
+
+inline uint128& uint128::operator--() {
+ *this -= 1;
+ return *this;
+}
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_INT128_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128_unittest.cc
new file mode 100644
index 0000000000..5d33292ccc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/int128_unittest.cc
@@ -0,0 +1,513 @@
+// 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.
+
+#include <google/protobuf/stubs/int128.h>
+
+#include <algorithm>
+#include <sstream>
+#include <utility>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+TEST(Int128, AllTests) {
+ uint128 zero(0);
+ uint128 one(1);
+ uint128 one_2arg(0, 1);
+ uint128 two(0, 2);
+ uint128 three(0, 3);
+ uint128 big(2000, 2);
+ uint128 big_minus_one(2000, 1);
+ uint128 bigger(2001, 1);
+ uint128 biggest(kuint128max);
+ uint128 high_low(1, 0);
+ uint128 low_high(0, kuint64max);
+ EXPECT_LT(one, two);
+ EXPECT_GT(two, one);
+ EXPECT_LT(one, big);
+ EXPECT_LT(one, big);
+ EXPECT_EQ(one, one_2arg);
+ EXPECT_NE(one, two);
+ EXPECT_GT(big, one);
+ EXPECT_GE(big, two);
+ EXPECT_GE(big, big_minus_one);
+ EXPECT_GT(big, big_minus_one);
+ EXPECT_LT(big_minus_one, big);
+ EXPECT_LE(big_minus_one, big);
+ EXPECT_NE(big_minus_one, big);
+ EXPECT_LT(big, biggest);
+ EXPECT_LE(big, biggest);
+ EXPECT_GT(biggest, big);
+ EXPECT_GE(biggest, big);
+ EXPECT_EQ(big, ~~big);
+ EXPECT_EQ(one, one | one);
+ EXPECT_EQ(big, big | big);
+ EXPECT_EQ(one, one | zero);
+ EXPECT_EQ(one, one & one);
+ EXPECT_EQ(big, big & big);
+ EXPECT_EQ(zero, one & zero);
+ EXPECT_EQ(zero, big & ~big);
+ EXPECT_EQ(zero, one ^ one);
+ EXPECT_EQ(zero, big ^ big);
+ EXPECT_EQ(one, one ^ zero);
+
+ // Shift operators.
+ EXPECT_EQ(big, big << 0);
+ EXPECT_EQ(big, big >> 0);
+ EXPECT_GT(big << 1, big);
+ EXPECT_LT(big >> 1, big);
+ EXPECT_EQ(big, (big << 10) >> 10);
+ EXPECT_EQ(big, (big >> 1) << 1);
+ EXPECT_EQ(one, (one << 80) >> 80);
+ EXPECT_EQ(zero, (one >> 80) << 80);
+ EXPECT_EQ(zero, big >> 128);
+ EXPECT_EQ(zero, big << 128);
+
+ // Shift assignments.
+ uint128 big_copy = big;
+ EXPECT_EQ(big << 0, big_copy <<= 0);
+ big_copy = big;
+ EXPECT_EQ(big >> 0, big_copy >>= 0);
+ big_copy = big;
+ EXPECT_EQ(big << 1, big_copy <<= 1);
+ big_copy = big;
+ EXPECT_EQ(big >> 1, big_copy >>= 1);
+ big_copy = big;
+ EXPECT_EQ(big << 10, big_copy <<= 10);
+ big_copy = big;
+ EXPECT_EQ(big >> 10, big_copy >>= 10);
+ big_copy = big;
+ EXPECT_EQ(big << 64, big_copy <<= 64);
+ big_copy = big;
+ EXPECT_EQ(big >> 64, big_copy >>= 64);
+ big_copy = big;
+ EXPECT_EQ(big << 73, big_copy <<= 73);
+ big_copy = big;
+ EXPECT_EQ(big >> 73, big_copy >>= 73);
+ big_copy = big;
+ EXPECT_EQ(big << 128, big_copy <<= 128);
+ big_copy = big;
+ EXPECT_EQ(big >> 128, big_copy >>= 128);
+
+ EXPECT_EQ(Uint128High64(biggest), kuint64max);
+ EXPECT_EQ(Uint128Low64(biggest), kuint64max);
+ EXPECT_EQ(zero + one, one);
+ EXPECT_EQ(one + one, two);
+ EXPECT_EQ(big_minus_one + one, big);
+ EXPECT_EQ(one - one, zero);
+ EXPECT_EQ(one - zero, one);
+ EXPECT_EQ(zero - one, biggest);
+ EXPECT_EQ(big - big, zero);
+ EXPECT_EQ(big - one, big_minus_one);
+ EXPECT_EQ(big + kuint64max, bigger);
+ EXPECT_EQ(biggest + 1, zero);
+ EXPECT_EQ(zero - 1, biggest);
+ EXPECT_EQ(high_low - one, low_high);
+ EXPECT_EQ(low_high + one, high_low);
+ EXPECT_EQ(Uint128High64((uint128(1) << 64) - 1), 0);
+ EXPECT_EQ(Uint128Low64((uint128(1) << 64) - 1), kuint64max);
+ EXPECT_TRUE(!!one);
+ EXPECT_TRUE(!!high_low);
+ EXPECT_FALSE(!!zero);
+ EXPECT_FALSE(!one);
+ EXPECT_FALSE(!high_low);
+ EXPECT_TRUE(!zero);
+ EXPECT_TRUE(zero == 0);
+ EXPECT_FALSE(zero != 0);
+ EXPECT_FALSE(one == 0);
+ EXPECT_TRUE(one != 0);
+
+ uint128 test = zero;
+ EXPECT_EQ(++test, one);
+ EXPECT_EQ(test, one);
+ EXPECT_EQ(test++, one);
+ EXPECT_EQ(test, two);
+ EXPECT_EQ(test -= 2, zero);
+ EXPECT_EQ(test, zero);
+ EXPECT_EQ(test += 2, two);
+ EXPECT_EQ(test, two);
+ EXPECT_EQ(--test, one);
+ EXPECT_EQ(test, one);
+ EXPECT_EQ(test--, one);
+ EXPECT_EQ(test, zero);
+ EXPECT_EQ(test |= three, three);
+ EXPECT_EQ(test &= one, one);
+ EXPECT_EQ(test ^= three, two);
+ EXPECT_EQ(test >>= 1, one);
+ EXPECT_EQ(test <<= 1, two);
+
+ EXPECT_EQ(big, -(-big));
+ EXPECT_EQ(two, -((-one) - 1));
+ EXPECT_EQ(kuint128max, -one);
+ EXPECT_EQ(zero, -zero);
+
+ GOOGLE_LOG(INFO) << one;
+ GOOGLE_LOG(INFO) << big_minus_one;
+}
+
+TEST(Int128, PodTests) {
+ uint128_pod pod = { 12345, 67890 };
+ uint128 from_pod(pod);
+ EXPECT_EQ(12345, Uint128High64(from_pod));
+ EXPECT_EQ(67890, Uint128Low64(from_pod));
+
+ uint128 zero(0);
+ uint128_pod zero_pod = {0, 0};
+ uint128 one(1);
+ uint128_pod one_pod = {0, 1};
+ uint128 two(2);
+ uint128_pod two_pod = {0, 2};
+ uint128 three(3);
+ uint128_pod three_pod = {0, 3};
+ uint128 big(1, 0);
+ uint128_pod big_pod = {1, 0};
+
+ EXPECT_EQ(zero, zero_pod);
+ EXPECT_EQ(zero_pod, zero);
+ EXPECT_EQ(zero_pod, zero_pod);
+ EXPECT_EQ(one, one_pod);
+ EXPECT_EQ(one_pod, one);
+ EXPECT_EQ(one_pod, one_pod);
+ EXPECT_EQ(two, two_pod);
+ EXPECT_EQ(two_pod, two);
+ EXPECT_EQ(two_pod, two_pod);
+
+ EXPECT_NE(one, two_pod);
+ EXPECT_NE(one_pod, two);
+ EXPECT_NE(one_pod, two_pod);
+
+ EXPECT_LT(one, two_pod);
+ EXPECT_LT(one_pod, two);
+ EXPECT_LT(one_pod, two_pod);
+ EXPECT_LE(one, one_pod);
+ EXPECT_LE(one_pod, one);
+ EXPECT_LE(one_pod, one_pod);
+ EXPECT_LE(one, two_pod);
+ EXPECT_LE(one_pod, two);
+ EXPECT_LE(one_pod, two_pod);
+
+ EXPECT_GT(two, one_pod);
+ EXPECT_GT(two_pod, one);
+ EXPECT_GT(two_pod, one_pod);
+ EXPECT_GE(two, two_pod);
+ EXPECT_GE(two_pod, two);
+ EXPECT_GE(two_pod, two_pod);
+ EXPECT_GE(two, one_pod);
+ EXPECT_GE(two_pod, one);
+ EXPECT_GE(two_pod, one_pod);
+
+ EXPECT_EQ(three, one | two_pod);
+ EXPECT_EQ(three, one_pod | two);
+ EXPECT_EQ(three, one_pod | two_pod);
+ EXPECT_EQ(one, three & one_pod);
+ EXPECT_EQ(one, three_pod & one);
+ EXPECT_EQ(one, three_pod & one_pod);
+ EXPECT_EQ(two, three ^ one_pod);
+ EXPECT_EQ(two, three_pod ^ one);
+ EXPECT_EQ(two, three_pod ^ one_pod);
+ EXPECT_EQ(two, three & (~one));
+ EXPECT_EQ(three, ~~three);
+
+ EXPECT_EQ(two, two_pod << 0);
+ EXPECT_EQ(two, one_pod << 1);
+ EXPECT_EQ(big, one_pod << 64);
+ EXPECT_EQ(zero, one_pod << 128);
+ EXPECT_EQ(two, two_pod >> 0);
+ EXPECT_EQ(one, two_pod >> 1);
+ EXPECT_EQ(one, big_pod >> 64);
+
+ EXPECT_EQ(one, zero + one_pod);
+ EXPECT_EQ(one, zero_pod + one);
+ EXPECT_EQ(one, zero_pod + one_pod);
+ EXPECT_EQ(one, two - one_pod);
+ EXPECT_EQ(one, two_pod - one);
+ EXPECT_EQ(one, two_pod - one_pod);
+}
+
+TEST(Int128, OperatorAssignReturnRef) {
+ uint128 v(1);
+ (v += 4) -= 3;
+ EXPECT_EQ(2, v);
+}
+
+TEST(Int128, Multiply) {
+ uint128 a, b, c;
+
+ // Zero test.
+ a = 0;
+ b = 0;
+ c = a * b;
+ EXPECT_EQ(0, c);
+
+ // Max carries.
+ a = uint128(0) - 1;
+ b = uint128(0) - 1;
+ c = a * b;
+ EXPECT_EQ(1, c);
+
+ // Self-operation with max carries.
+ c = uint128(0) - 1;
+ c *= c;
+ EXPECT_EQ(1, c);
+
+ // 1-bit x 1-bit.
+ for (int i = 0; i < 64; ++i) {
+ for (int j = 0; j < 64; ++j) {
+ a = uint128(1) << i;
+ b = uint128(1) << j;
+ c = a * b;
+ EXPECT_EQ(uint128(1) << (i+j), c);
+ }
+ }
+
+ // Verified with dc.
+ a = uint128(GOOGLE_ULONGLONG(0xffffeeeeddddcccc),
+ GOOGLE_ULONGLONG(0xbbbbaaaa99998888));
+ b = uint128(GOOGLE_ULONGLONG(0x7777666655554444),
+ GOOGLE_ULONGLONG(0x3333222211110000));
+ c = a * b;
+ EXPECT_EQ(uint128(GOOGLE_ULONGLONG(0x530EDA741C71D4C3),
+ GOOGLE_ULONGLONG(0xBF25975319080000)), c);
+ EXPECT_EQ(0, c - b * a);
+ EXPECT_EQ(a*a - b*b, (a+b) * (a-b));
+
+ // Verified with dc.
+ a = uint128(GOOGLE_ULONGLONG(0x0123456789abcdef),
+ GOOGLE_ULONGLONG(0xfedcba9876543210));
+ b = uint128(GOOGLE_ULONGLONG(0x02468ace13579bdf),
+ GOOGLE_ULONGLONG(0xfdb97531eca86420));
+ c = a * b;
+ EXPECT_EQ(uint128(GOOGLE_ULONGLONG(0x97a87f4f261ba3f2),
+ GOOGLE_ULONGLONG(0x342d0bbf48948200)), c);
+ EXPECT_EQ(0, c - b * a);
+ EXPECT_EQ(a*a - b*b, (a+b) * (a-b));
+}
+
+TEST(Int128, AliasTests) {
+ uint128 x1(1, 2);
+ uint128 x2(2, 4);
+ x1 += x1;
+ EXPECT_EQ(x2, x1);
+
+ uint128 x3(1, static_cast<uint64>(1) << 63);
+ uint128 x4(3, 0);
+ x3 += x3;
+ EXPECT_EQ(x4, x3);
+}
+
+#ifdef PROTOBUF_HAS_DEATH_TEST
+TEST(Int128, DivideByZeroCheckFails) {
+ uint128 a = 0;
+ uint128 b = 0;
+ EXPECT_DEATH(a / b, "Division or mod by zero:");
+ a = 123;
+ EXPECT_DEATH(a / b, "Division or mod by zero:");
+}
+
+TEST(Int128, ModByZeroCheckFails) {
+ uint128 a = 0;
+ uint128 b = 0;
+ EXPECT_DEATH(a % b, "Division or mod by zero:");
+ a = 123;
+ EXPECT_DEATH(a % b, "Division or mod by zero:");
+}
+#endif // PROTOBUF_HAS_DEATH_TEST
+
+TEST(Int128, DivideAndMod) {
+ // a := q * b + r
+ uint128 a, b, q, r;
+
+ // Zero test.
+ a = 0;
+ b = 123;
+ q = a / b;
+ r = a % b;
+ EXPECT_EQ(0, q);
+ EXPECT_EQ(0, r);
+
+ a = uint128(GOOGLE_ULONGLONG(0x530eda741c71d4c3),
+ GOOGLE_ULONGLONG(0xbf25975319080000));
+ q = uint128(GOOGLE_ULONGLONG(0x4de2cab081),
+ GOOGLE_ULONGLONG(0x14c34ab4676e4bab));
+ b = uint128(0x1110001);
+ r = uint128(0x3eb455);
+ ASSERT_EQ(a, q * b + r); // Sanity-check.
+
+ uint128 result_q, result_r;
+ result_q = a / b;
+ result_r = a % b;
+ EXPECT_EQ(q, result_q);
+ EXPECT_EQ(r, result_r);
+
+ // Try the other way around.
+ swap(q, b);
+ result_q = a / b;
+ result_r = a % b;
+ EXPECT_EQ(q, result_q);
+ EXPECT_EQ(r, result_r);
+ // Restore.
+ swap(b, q);
+
+ // Dividend < divisor; result should be q:0 r:<dividend>.
+ swap(a, b);
+ result_q = a / b;
+ result_r = a % b;
+ EXPECT_EQ(0, result_q);
+ EXPECT_EQ(a, result_r);
+ // Try the other way around.
+ swap(a, q);
+ result_q = a / b;
+ result_r = a % b;
+ EXPECT_EQ(0, result_q);
+ EXPECT_EQ(a, result_r);
+ // Restore.
+ swap(q, a);
+ swap(b, a);
+
+ // Try a large remainder.
+ b = a / 2 + 1;
+ uint128 expected_r(GOOGLE_ULONGLONG(0x29876d3a0e38ea61),
+ GOOGLE_ULONGLONG(0xdf92cba98c83ffff));
+ // Sanity checks.
+ ASSERT_EQ(a / 2 - 1, expected_r);
+ ASSERT_EQ(a, b + expected_r);
+ result_q = a / b;
+ result_r = a % b;
+ EXPECT_EQ(1, result_q);
+ EXPECT_EQ(expected_r, result_r);
+}
+
+static uint64 RandomUint64() {
+ uint64 v1 = rand();
+ uint64 v2 = rand();
+ uint64 v3 = rand();
+ return v1 * v2 + v3;
+}
+
+TEST(Int128, DivideAndModRandomInputs) {
+ const int kNumIters = 1 << 18;
+ for (int i = 0; i < kNumIters; ++i) {
+ const uint128 a(RandomUint64(), RandomUint64());
+ const uint128 b(RandomUint64(), RandomUint64());
+ if (b == 0) {
+ continue; // Avoid a div-by-zero.
+ }
+ const uint128 q = a / b;
+ const uint128 r = a % b;
+ ASSERT_EQ(a, b * q + r);
+ }
+}
+
+#ifdef GOOGLE_PROTOBUF_HAS_CONSTEXPR
+TEST(Int128, ConstexprTest) {
+ constexpr uint128 zero;
+ constexpr uint128 one = 1;
+ constexpr uint128_pod pod = {2, 3};
+ constexpr uint128 from_pod = pod;
+ constexpr uint128 minus_two = -2;
+ EXPECT_EQ(one, uint128(1));
+ EXPECT_EQ(from_pod, uint128(2, 3));
+ EXPECT_EQ(minus_two, uint128(-1ULL, -2ULL));
+}
+
+TEST(Int128, Traits) {
+ EXPECT_TRUE(std::is_trivially_copy_constructible<uint128>::value);
+ EXPECT_TRUE(std::is_trivially_copy_assignable<uint128>::value);
+ EXPECT_TRUE(std::is_trivially_destructible<uint128>::value);
+}
+#endif // GOOGLE_PROTOBUF_HAS_CONSTEXPR
+
+TEST(Int128, OStream) {
+ struct {
+ uint128 val;
+ std::ios_base::fmtflags flags;
+ std::streamsize width;
+ char fill;
+ const char* rep;
+ } cases[] = {
+ // zero with different bases
+ {uint128(0), std::ios::dec, 0, '_', "0"},
+ {uint128(0), std::ios::oct, 0, '_', "0"},
+ {uint128(0), std::ios::hex, 0, '_', "0"},
+ // crossover between lo_ and hi_
+ {uint128(0, -1), std::ios::dec, 0, '_', "18446744073709551615"},
+ {uint128(0, -1), std::ios::oct, 0, '_', "1777777777777777777777"},
+ {uint128(0, -1), std::ios::hex, 0, '_', "ffffffffffffffff"},
+ {uint128(1, 0), std::ios::dec, 0, '_', "18446744073709551616"},
+ {uint128(1, 0), std::ios::oct, 0, '_', "2000000000000000000000"},
+ {uint128(1, 0), std::ios::hex, 0, '_', "10000000000000000"},
+ // just the top bit
+ {uint128(GOOGLE_ULONGLONG(0x8000000000000000), 0), std::ios::dec, 0, '_',
+ "170141183460469231731687303715884105728"},
+ {uint128(GOOGLE_ULONGLONG(0x8000000000000000), 0), std::ios::oct, 0, '_',
+ "2000000000000000000000000000000000000000000"},
+ {uint128(GOOGLE_ULONGLONG(0x8000000000000000), 0), std::ios::hex, 0, '_',
+ "80000000000000000000000000000000"},
+ // maximum uint128 value
+ {uint128(-1, -1), std::ios::dec, 0, '_',
+ "340282366920938463463374607431768211455"},
+ {uint128(-1, -1), std::ios::oct, 0, '_',
+ "3777777777777777777777777777777777777777777"},
+ {uint128(-1, -1), std::ios::hex, 0, '_',
+ "ffffffffffffffffffffffffffffffff"},
+ // uppercase
+ {uint128(-1, -1), std::ios::hex | std::ios::uppercase, 0, '_',
+ "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"},
+ // showbase
+ {uint128(1), std::ios::dec | std::ios::showbase, 0, '_', "1"},
+ {uint128(1), std::ios::oct | std::ios::showbase, 0, '_', "01"},
+ {uint128(1), std::ios::hex | std::ios::showbase, 0, '_', "0x1"},
+ // showbase does nothing on zero
+ {uint128(0), std::ios::dec | std::ios::showbase, 0, '_', "0"},
+ {uint128(0), std::ios::oct | std::ios::showbase, 0, '_', "0"},
+ {uint128(0), std::ios::hex | std::ios::showbase, 0, '_', "0"},
+ // showpos does nothing on unsigned types
+ {uint128(1), std::ios::dec | std::ios::showpos, 0, '_', "1"},
+ // padding
+ {uint128(9), std::ios::dec, 6, '_', "_____9"},
+ {uint128(12345), std::ios::dec, 6, '_', "_12345"},
+ // left adjustment
+ {uint128(9), std::ios::dec | std::ios::left, 6, '_', "9_____"},
+ {uint128(12345), std::ios::dec | std::ios::left, 6, '_', "12345_"},
+ };
+ for (size_t i = 0; i < GOOGLE_ARRAYSIZE(cases); ++i) {
+ ostringstream os;
+ os.flags(cases[i].flags);
+ os.width(cases[i].width);
+ os.fill(cases[i].fill);
+ os << cases[i].val;
+ EXPECT_EQ(cases[i].rep, os.str());
+ }
+}
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/logging.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/logging.h
new file mode 100644
index 0000000000..f69605d9f6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/logging.h
@@ -0,0 +1,237 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_STUBS_LOGGING_H_
+#define GOOGLE_PROTOBUF_STUBS_LOGGING_H_
+
+#include <google/protobuf/stubs/macros.h>
+#include <google/protobuf/stubs/port.h>
+
+// ===================================================================
+// emulates google3/base/logging.h
+
+namespace google {
+namespace protobuf {
+
+enum LogLevel {
+ LOGLEVEL_INFO, // Informational. This is never actually used by
+ // libprotobuf.
+ LOGLEVEL_WARNING, // Warns about issues that, although not technically a
+ // problem now, could cause problems in the future. For
+ // example, a // warning will be printed when parsing a
+ // message that is near the message size limit.
+ LOGLEVEL_ERROR, // An error occurred which should never happen during
+ // normal use.
+ LOGLEVEL_FATAL, // An error occurred from which the library cannot
+ // recover. This usually indicates a programming error
+ // in the code which calls the library, especially when
+ // compiled in debug mode.
+
+#ifdef NDEBUG
+ LOGLEVEL_DFATAL = LOGLEVEL_ERROR
+#else
+ LOGLEVEL_DFATAL = LOGLEVEL_FATAL
+#endif
+};
+
+class StringPiece;
+namespace util {
+class Status;
+}
+class uint128;
+namespace internal {
+
+class LogFinisher;
+
+class LIBPROTOBUF_EXPORT LogMessage {
+ public:
+ LogMessage(LogLevel level, const char* filename, int line);
+ ~LogMessage();
+
+ LogMessage& operator<<(const std::string& value);
+ LogMessage& operator<<(const char* value);
+ LogMessage& operator<<(char value);
+ LogMessage& operator<<(int value);
+ LogMessage& operator<<(uint value);
+ LogMessage& operator<<(long value);
+ LogMessage& operator<<(unsigned long value);
+ LogMessage& operator<<(long long value);
+ LogMessage& operator<<(unsigned long long value);
+ LogMessage& operator<<(double value);
+ LogMessage& operator<<(void* value);
+ LogMessage& operator<<(const StringPiece& value);
+ LogMessage& operator<<(const ::google::protobuf::util::Status& status);
+ LogMessage& operator<<(const uint128& value);
+
+ private:
+ friend class LogFinisher;
+ void Finish();
+
+ LogLevel level_;
+ const char* filename_;
+ int line_;
+ std::string message_;
+};
+
+// Used to make the entire "LOG(BLAH) << etc." expression have a void return
+// type and print a newline after each message.
+class LIBPROTOBUF_EXPORT LogFinisher {
+ public:
+ void operator=(LogMessage& other);
+};
+
+template<typename T>
+bool IsOk(T status) { return status.ok(); }
+template<>
+inline bool IsOk(bool status) { return status; }
+
+} // namespace internal
+
+// Undef everything in case we're being mixed with some other Google library
+// which already defined them itself. Presumably all Google libraries will
+// support the same syntax for these so it should not be a big deal if they
+// end up using our definitions instead.
+#undef GOOGLE_LOG
+#undef GOOGLE_LOG_IF
+
+#undef GOOGLE_CHECK
+#undef GOOGLE_CHECK_OK
+#undef GOOGLE_CHECK_EQ
+#undef GOOGLE_CHECK_NE
+#undef GOOGLE_CHECK_LT
+#undef GOOGLE_CHECK_LE
+#undef GOOGLE_CHECK_GT
+#undef GOOGLE_CHECK_GE
+#undef GOOGLE_CHECK_NOTNULL
+
+#undef GOOGLE_DLOG
+#undef GOOGLE_DCHECK
+#undef GOOGLE_DCHECK_OK
+#undef GOOGLE_DCHECK_EQ
+#undef GOOGLE_DCHECK_NE
+#undef GOOGLE_DCHECK_LT
+#undef GOOGLE_DCHECK_LE
+#undef GOOGLE_DCHECK_GT
+#undef GOOGLE_DCHECK_GE
+
+#define GOOGLE_LOG(LEVEL) \
+ ::google::protobuf::internal::LogFinisher() = \
+ ::google::protobuf::internal::LogMessage( \
+ ::google::protobuf::LOGLEVEL_##LEVEL, __FILE__, __LINE__)
+#define GOOGLE_LOG_IF(LEVEL, CONDITION) \
+ !(CONDITION) ? (void)0 : GOOGLE_LOG(LEVEL)
+
+#define GOOGLE_CHECK(EXPRESSION) \
+ GOOGLE_LOG_IF(FATAL, !(EXPRESSION)) << "CHECK failed: " #EXPRESSION ": "
+#define GOOGLE_CHECK_OK(A) GOOGLE_CHECK(::google::protobuf::internal::IsOk(A))
+#define GOOGLE_CHECK_EQ(A, B) GOOGLE_CHECK((A) == (B))
+#define GOOGLE_CHECK_NE(A, B) GOOGLE_CHECK((A) != (B))
+#define GOOGLE_CHECK_LT(A, B) GOOGLE_CHECK((A) < (B))
+#define GOOGLE_CHECK_LE(A, B) GOOGLE_CHECK((A) <= (B))
+#define GOOGLE_CHECK_GT(A, B) GOOGLE_CHECK((A) > (B))
+#define GOOGLE_CHECK_GE(A, B) GOOGLE_CHECK((A) >= (B))
+
+namespace internal {
+template<typename T>
+T* CheckNotNull(const char* /* file */, int /* line */,
+ const char* name, T* val) {
+ if (val == NULL) {
+ GOOGLE_LOG(FATAL) << name;
+ }
+ return val;
+}
+} // namespace internal
+#define GOOGLE_CHECK_NOTNULL(A) \
+ ::google::protobuf::internal::CheckNotNull(\
+ __FILE__, __LINE__, "'" #A "' must not be NULL", (A))
+
+#ifdef NDEBUG
+
+#define GOOGLE_DLOG(LEVEL) GOOGLE_LOG_IF(LEVEL, false)
+
+#define GOOGLE_DCHECK(EXPRESSION) while(false) GOOGLE_CHECK(EXPRESSION)
+#define GOOGLE_DCHECK_OK(E) GOOGLE_DCHECK(::google::protobuf::internal::IsOk(E))
+#define GOOGLE_DCHECK_EQ(A, B) GOOGLE_DCHECK((A) == (B))
+#define GOOGLE_DCHECK_NE(A, B) GOOGLE_DCHECK((A) != (B))
+#define GOOGLE_DCHECK_LT(A, B) GOOGLE_DCHECK((A) < (B))
+#define GOOGLE_DCHECK_LE(A, B) GOOGLE_DCHECK((A) <= (B))
+#define GOOGLE_DCHECK_GT(A, B) GOOGLE_DCHECK((A) > (B))
+#define GOOGLE_DCHECK_GE(A, B) GOOGLE_DCHECK((A) >= (B))
+
+#else // NDEBUG
+
+#define GOOGLE_DLOG GOOGLE_LOG
+
+#define GOOGLE_DCHECK GOOGLE_CHECK
+#define GOOGLE_DCHECK_OK GOOGLE_CHECK_OK
+#define GOOGLE_DCHECK_EQ GOOGLE_CHECK_EQ
+#define GOOGLE_DCHECK_NE GOOGLE_CHECK_NE
+#define GOOGLE_DCHECK_LT GOOGLE_CHECK_LT
+#define GOOGLE_DCHECK_LE GOOGLE_CHECK_LE
+#define GOOGLE_DCHECK_GT GOOGLE_CHECK_GT
+#define GOOGLE_DCHECK_GE GOOGLE_CHECK_GE
+
+#endif // !NDEBUG
+
+typedef void LogHandler(LogLevel level, const char* filename, int line,
+ const std::string& message);
+
+// The protobuf library sometimes writes warning and error messages to
+// stderr. These messages are primarily useful for developers, but may
+// also help end users figure out a problem. If you would prefer that
+// these messages be sent somewhere other than stderr, call SetLogHandler()
+// to set your own handler. This returns the old handler. Set the handler
+// to NULL to ignore log messages (but see also LogSilencer, below).
+//
+// Obviously, SetLogHandler is not thread-safe. You should only call it
+// at initialization time, and probably not from library code. If you
+// simply want to suppress log messages temporarily (e.g. because you
+// have some code that tends to trigger them frequently and you know
+// the warnings are not important to you), use the LogSilencer class
+// below.
+LIBPROTOBUF_EXPORT LogHandler* SetLogHandler(LogHandler* new_func);
+
+// Create a LogSilencer if you want to temporarily suppress all log
+// messages. As long as any LogSilencer objects exist, non-fatal
+// log messages will be discarded (the current LogHandler will *not*
+// be called). Constructing a LogSilencer is thread-safe. You may
+// accidentally suppress log messages occurring in another thread, but
+// since messages are generally for debugging purposes only, this isn't
+// a big deal. If you want to intercept log messages, use SetLogHandler().
+class LIBPROTOBUF_EXPORT LogSilencer {
+ public:
+ LogSilencer();
+ ~LogSilencer();
+};
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_LOGGING_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/macros.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/macros.h
new file mode 100644
index 0000000000..0e9a9ec198
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/macros.h
@@ -0,0 +1,168 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_MACROS_H__
+#define GOOGLE_PROTOBUF_MACROS_H__
+
+#include <google/protobuf/stubs/port.h>
+
+namespace google {
+namespace protobuf {
+
+#undef GOOGLE_DISALLOW_EVIL_CONSTRUCTORS
+#define GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TypeName) \
+ TypeName(const TypeName&); \
+ void operator=(const TypeName&)
+
+#undef GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS
+#define GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(TypeName) \
+ TypeName(); \
+ TypeName(const TypeName&); \
+ void operator=(const TypeName&)
+
+// ===================================================================
+// from google3/base/basictypes.h
+
+// The GOOGLE_ARRAYSIZE(arr) macro returns the # of elements in an array arr.
+// The expression is a compile-time constant, and therefore can be
+// used in defining new arrays, for example.
+//
+// GOOGLE_ARRAYSIZE catches a few type errors. If you see a compiler error
+//
+// "warning: division by zero in ..."
+//
+// when using GOOGLE_ARRAYSIZE, you are (wrongfully) giving it a pointer.
+// You should only use GOOGLE_ARRAYSIZE on statically allocated arrays.
+//
+// The following comments are on the implementation details, and can
+// be ignored by the users.
+//
+// ARRAYSIZE(arr) works by inspecting sizeof(arr) (the # of bytes in
+// the array) and sizeof(*(arr)) (the # of bytes in one array
+// element). If the former is divisible by the latter, perhaps arr is
+// indeed an array, in which case the division result is the # of
+// elements in the array. Otherwise, arr cannot possibly be an array,
+// and we generate a compiler error to prevent the code from
+// compiling.
+//
+// Since the size of bool is implementation-defined, we need to cast
+// !(sizeof(a) & sizeof(*(a))) to size_t in order to ensure the final
+// result has type size_t.
+//
+// This macro is not perfect as it wrongfully accepts certain
+// pointers, namely where the pointer size is divisible by the pointee
+// size. Since all our code has to go through a 32-bit compiler,
+// where a pointer is 4 bytes, this means all pointers to a type whose
+// size is 3 or greater than 4 will be (righteously) rejected.
+//
+// Kudos to Jorg Brown for this simple and elegant implementation.
+
+#undef GOOGLE_ARRAYSIZE
+#define GOOGLE_ARRAYSIZE(a) \
+ ((sizeof(a) / sizeof(*(a))) / \
+ static_cast<size_t>(!(sizeof(a) % sizeof(*(a)))))
+
+// The COMPILE_ASSERT macro can be used to verify that a compile time
+// expression is true. For example, you could use it to verify the
+// size of a static array:
+//
+// COMPILE_ASSERT(ARRAYSIZE(content_type_names) == CONTENT_NUM_TYPES,
+// content_type_names_incorrect_size);
+//
+// or to make sure a struct is smaller than a certain size:
+//
+// COMPILE_ASSERT(sizeof(foo) < 128, foo_too_large);
+//
+// The second argument to the macro is the name of the variable. If
+// the expression is false, most compilers will issue a warning/error
+// containing the name of the variable.
+
+namespace internal {
+
+template <bool>
+struct CompileAssert {
+};
+
+} // namespace internal
+
+#undef GOOGLE_COMPILE_ASSERT
+#if __cplusplus >= 201103L
+#define GOOGLE_COMPILE_ASSERT(expr, msg) static_assert(expr, #msg)
+#else
+#define GOOGLE_COMPILE_ASSERT(expr, msg) \
+ ::google::protobuf::internal::CompileAssert<(bool(expr))> \
+ msg[bool(expr) ? 1 : -1]; \
+ (void)msg
+// Implementation details of COMPILE_ASSERT:
+//
+// - COMPILE_ASSERT works by defining an array type that has -1
+// elements (and thus is invalid) when the expression is false.
+//
+// - The simpler definition
+//
+// #define COMPILE_ASSERT(expr, msg) typedef char msg[(expr) ? 1 : -1]
+//
+// does not work, as gcc supports variable-length arrays whose sizes
+// are determined at run-time (this is gcc's extension and not part
+// of the C++ standard). As a result, gcc fails to reject the
+// following code with the simple definition:
+//
+// int foo;
+// COMPILE_ASSERT(foo, msg); // not supposed to compile as foo is
+// // not a compile-time constant.
+//
+// - By using the type CompileAssert<(bool(expr))>, we ensures that
+// expr is a compile-time constant. (Template arguments must be
+// determined at compile-time.)
+//
+// - The outter parentheses in CompileAssert<(bool(expr))> are necessary
+// to work around a bug in gcc 3.4.4 and 4.0.1. If we had written
+//
+// CompileAssert<bool(expr)>
+//
+// instead, these compilers will refuse to compile
+//
+// COMPILE_ASSERT(5 > 0, some_message);
+//
+// (They seem to think the ">" in "5 > 0" marks the end of the
+// template argument list.)
+//
+// - The array size is (bool(expr) ? 1 : -1), instead of simply
+//
+// ((expr) ? 1 : -1).
+//
+// This is to avoid running into a bug in MS VC 7.1, which
+// causes ((0.0) ? 1 : -1) to incorrectly evaluate to 1.
+#endif // __cplusplus >= 201103L
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_MACROS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/map_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/map_util.h
new file mode 100644
index 0000000000..4cccbbedcb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/map_util.h
@@ -0,0 +1,769 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+
+// from google3/util/gtl/map_util.h
+// Author: Anton Carver
+
+#ifndef GOOGLE_PROTOBUF_STUBS_MAP_UTIL_H__
+#define GOOGLE_PROTOBUF_STUBS_MAP_UTIL_H__
+
+#include <stddef.h>
+#include <iterator>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+// Local implementation of RemoveConst to avoid including base/type_traits.h.
+template <class T> struct RemoveConst { typedef T type; };
+template <class T> struct RemoveConst<const T> : RemoveConst<T> {};
+} // namespace internal
+
+//
+// Find*()
+//
+
+// Returns a const reference to the value associated with the given key if it
+// exists. Crashes otherwise.
+//
+// This is intended as a replacement for operator[] as an rvalue (for reading)
+// when the key is guaranteed to exist.
+//
+// operator[] for lookup is discouraged for several reasons:
+// * It has a side-effect of inserting missing keys
+// * It is not thread-safe (even when it is not inserting, it can still
+// choose to resize the underlying storage)
+// * It invalidates iterators (when it chooses to resize)
+// * It default constructs a value object even if it doesn't need to
+//
+// This version assumes the key is printable, and includes it in the fatal log
+// message.
+template <class Collection>
+const typename Collection::value_type::second_type&
+FindOrDie(const Collection& collection,
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::const_iterator it = collection.find(key);
+ GOOGLE_CHECK(it != collection.end()) << "Map key not found: " << key;
+ return it->second;
+}
+
+// Same as above, but returns a non-const reference.
+template <class Collection>
+typename Collection::value_type::second_type&
+FindOrDie(Collection& collection, // NOLINT
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::iterator it = collection.find(key);
+ GOOGLE_CHECK(it != collection.end()) << "Map key not found: " << key;
+ return it->second;
+}
+
+// Same as FindOrDie above, but doesn't log the key on failure.
+template <class Collection>
+const typename Collection::value_type::second_type&
+FindOrDieNoPrint(const Collection& collection,
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::const_iterator it = collection.find(key);
+ GOOGLE_CHECK(it != collection.end()) << "Map key not found";
+ return it->second;
+}
+
+// Same as above, but returns a non-const reference.
+template <class Collection>
+typename Collection::value_type::second_type&
+FindOrDieNoPrint(Collection& collection, // NOLINT
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::iterator it = collection.find(key);
+ GOOGLE_CHECK(it != collection.end()) << "Map key not found";
+ return it->second;
+}
+
+// Returns a const reference to the value associated with the given key if it
+// exists, otherwise returns a const reference to the provided default value.
+//
+// WARNING: If a temporary object is passed as the default "value,"
+// this function will return a reference to that temporary object,
+// which will be destroyed at the end of the statement. A common
+// example: if you have a map with string values, and you pass a char*
+// as the default "value," either use the returned value immediately
+// or store it in a string (not string&).
+// Details: http://go/findwithdefault
+template <class Collection>
+const typename Collection::value_type::second_type&
+FindWithDefault(const Collection& collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& value) {
+ typename Collection::const_iterator it = collection.find(key);
+ if (it == collection.end()) {
+ return value;
+ }
+ return it->second;
+}
+
+// Returns a pointer to the const value associated with the given key if it
+// exists, or NULL otherwise.
+template <class Collection>
+const typename Collection::value_type::second_type*
+FindOrNull(const Collection& collection,
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::const_iterator it = collection.find(key);
+ if (it == collection.end()) {
+ return 0;
+ }
+ return &it->second;
+}
+
+// Same as above but returns a pointer to the non-const value.
+template <class Collection>
+typename Collection::value_type::second_type*
+FindOrNull(Collection& collection, // NOLINT
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::iterator it = collection.find(key);
+ if (it == collection.end()) {
+ return 0;
+ }
+ return &it->second;
+}
+
+// Returns the pointer value associated with the given key. If none is found,
+// NULL is returned. The function is designed to be used with a map of keys to
+// pointers.
+//
+// This function does not distinguish between a missing key and a key mapped
+// to a NULL value.
+template <class Collection>
+typename Collection::value_type::second_type
+FindPtrOrNull(const Collection& collection,
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::const_iterator it = collection.find(key);
+ if (it == collection.end()) {
+ return typename Collection::value_type::second_type();
+ }
+ return it->second;
+}
+
+// Same as above, except takes non-const reference to collection.
+//
+// This function is needed for containers that propagate constness to the
+// pointee, such as boost::ptr_map.
+template <class Collection>
+typename Collection::value_type::second_type
+FindPtrOrNull(Collection& collection, // NOLINT
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::iterator it = collection.find(key);
+ if (it == collection.end()) {
+ return typename Collection::value_type::second_type();
+ }
+ return it->second;
+}
+
+// Finds the pointer value associated with the given key in a map whose values
+// are linked_ptrs. Returns NULL if key is not found.
+template <class Collection>
+typename Collection::value_type::second_type::element_type*
+FindLinkedPtrOrNull(const Collection& collection,
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::const_iterator it = collection.find(key);
+ if (it == collection.end()) {
+ return 0;
+ }
+ // Since linked_ptr::get() is a const member returning a non const,
+ // we do not need a version of this function taking a non const collection.
+ return it->second.get();
+}
+
+// Same as above, but dies if the key is not found.
+template <class Collection>
+typename Collection::value_type::second_type::element_type&
+FindLinkedPtrOrDie(const Collection& collection,
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::const_iterator it = collection.find(key);
+ CHECK(it != collection.end()) << "key not found: " << key;
+ // Since linked_ptr::operator*() is a const member returning a non const,
+ // we do not need a version of this function taking a non const collection.
+ return *it->second;
+}
+
+// Finds the value associated with the given key and copies it to *value (if not
+// NULL). Returns false if the key was not found, true otherwise.
+template <class Collection, class Key, class Value>
+bool FindCopy(const Collection& collection,
+ const Key& key,
+ Value* const value) {
+ typename Collection::const_iterator it = collection.find(key);
+ if (it == collection.end()) {
+ return false;
+ }
+ if (value) {
+ *value = it->second;
+ }
+ return true;
+}
+
+//
+// Contains*()
+//
+
+// Returns true if and only if the given collection contains the given key.
+template <class Collection, class Key>
+bool ContainsKey(const Collection& collection, const Key& key) {
+ return collection.find(key) != collection.end();
+}
+
+// Returns true if and only if the given collection contains the given key-value
+// pair.
+template <class Collection, class Key, class Value>
+bool ContainsKeyValuePair(const Collection& collection,
+ const Key& key,
+ const Value& value) {
+ typedef typename Collection::const_iterator const_iterator;
+ std::pair<const_iterator, const_iterator> range = collection.equal_range(key);
+ for (const_iterator it = range.first; it != range.second; ++it) {
+ if (it->second == value) {
+ return true;
+ }
+ }
+ return false;
+}
+
+//
+// Insert*()
+//
+
+// Inserts the given key-value pair into the collection. Returns true if and
+// only if the key from the given pair didn't previously exist. Otherwise, the
+// value in the map is replaced with the value from the given pair.
+template <class Collection>
+bool InsertOrUpdate(Collection* const collection,
+ const typename Collection::value_type& vt) {
+ std::pair<typename Collection::iterator, bool> ret = collection->insert(vt);
+ if (!ret.second) {
+ // update
+ ret.first->second = vt.second;
+ return false;
+ }
+ return true;
+}
+
+// Same as above, except that the key and value are passed separately.
+template <class Collection>
+bool InsertOrUpdate(Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& value) {
+ return InsertOrUpdate(
+ collection, typename Collection::value_type(key, value));
+}
+
+// Inserts/updates all the key-value pairs from the range defined by the
+// iterators "first" and "last" into the given collection.
+template <class Collection, class InputIterator>
+void InsertOrUpdateMany(Collection* const collection,
+ InputIterator first, InputIterator last) {
+ for (; first != last; ++first) {
+ InsertOrUpdate(collection, *first);
+ }
+}
+
+// Change the value associated with a particular key in a map or hash_map
+// of the form map<Key, Value*> which owns the objects pointed to by the
+// value pointers. If there was an existing value for the key, it is deleted.
+// True indicates an insert took place, false indicates an update + delete.
+template <class Collection>
+bool InsertAndDeleteExisting(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& value) {
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(key, value));
+ if (!ret.second) {
+ delete ret.first->second;
+ ret.first->second = value;
+ return false;
+ }
+ return true;
+}
+
+// Inserts the given key and value into the given collection if and only if the
+// given key did NOT already exist in the collection. If the key previously
+// existed in the collection, the value is not changed. Returns true if the
+// key-value pair was inserted; returns false if the key was already present.
+template <class Collection>
+bool InsertIfNotPresent(Collection* const collection,
+ const typename Collection::value_type& vt) {
+ return collection->insert(vt).second;
+}
+
+// Same as above except the key and value are passed separately.
+template <class Collection>
+bool InsertIfNotPresent(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& value) {
+ return InsertIfNotPresent(
+ collection, typename Collection::value_type(key, value));
+}
+
+// Same as above except dies if the key already exists in the collection.
+template <class Collection>
+void InsertOrDie(Collection* const collection,
+ const typename Collection::value_type& value) {
+ CHECK(InsertIfNotPresent(collection, value)) << "duplicate value: " << value;
+}
+
+// Same as above except doesn't log the value on error.
+template <class Collection>
+void InsertOrDieNoPrint(Collection* const collection,
+ const typename Collection::value_type& value) {
+ CHECK(InsertIfNotPresent(collection, value)) << "duplicate value.";
+}
+
+// Inserts the key-value pair into the collection. Dies if key was already
+// present.
+template <class Collection>
+void InsertOrDie(Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& data) {
+ GOOGLE_CHECK(InsertIfNotPresent(collection, key, data))
+ << "duplicate key: " << key;
+}
+
+// Same as above except doesn't log the key on error.
+template <class Collection>
+void InsertOrDieNoPrint(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& data) {
+ GOOGLE_CHECK(InsertIfNotPresent(collection, key, data)) << "duplicate key.";
+}
+
+// Inserts a new key and default-initialized value. Dies if the key was already
+// present. Returns a reference to the value. Example usage:
+//
+// map<int, SomeProto> m;
+// SomeProto& proto = InsertKeyOrDie(&m, 3);
+// proto.set_field("foo");
+template <class Collection>
+typename Collection::value_type::second_type& InsertKeyOrDie(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key) {
+ typedef typename Collection::value_type value_type;
+ std::pair<typename Collection::iterator, bool> res =
+ collection->insert(value_type(key, typename value_type::second_type()));
+ GOOGLE_CHECK(res.second) << "duplicate key: " << key;
+ return res.first->second;
+}
+
+//
+// Lookup*()
+//
+
+// Looks up a given key and value pair in a collection and inserts the key-value
+// pair if it's not already present. Returns a reference to the value associated
+// with the key.
+template <class Collection>
+typename Collection::value_type::second_type&
+LookupOrInsert(Collection* const collection,
+ const typename Collection::value_type& vt) {
+ return collection->insert(vt).first->second;
+}
+
+// Same as above except the key-value are passed separately.
+template <class Collection>
+typename Collection::value_type::second_type&
+LookupOrInsert(Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& value) {
+ return LookupOrInsert(
+ collection, typename Collection::value_type(key, value));
+}
+
+// Counts the number of equivalent elements in the given "sequence", and stores
+// the results in "count_map" with element as the key and count as the value.
+//
+// Example:
+// vector<string> v = {"a", "b", "c", "a", "b"};
+// map<string, int> m;
+// AddTokenCounts(v, 1, &m);
+// assert(m["a"] == 2);
+// assert(m["b"] == 2);
+// assert(m["c"] == 1);
+template <typename Sequence, typename Collection>
+void AddTokenCounts(
+ const Sequence& sequence,
+ const typename Collection::value_type::second_type& increment,
+ Collection* const count_map) {
+ for (typename Sequence::const_iterator it = sequence.begin();
+ it != sequence.end(); ++it) {
+ typename Collection::value_type::second_type& value =
+ LookupOrInsert(count_map, *it,
+ typename Collection::value_type::second_type());
+ value += increment;
+ }
+}
+
+// Returns a reference to the value associated with key. If not found, a value
+// is default constructed on the heap and added to the map.
+//
+// This function is useful for containers of the form map<Key, Value*>, where
+// inserting a new key, value pair involves constructing a new heap-allocated
+// Value, and storing a pointer to that in the collection.
+template <class Collection>
+typename Collection::value_type::second_type&
+LookupOrInsertNew(Collection* const collection,
+ const typename Collection::value_type::first_type& key) {
+ typedef typename std::iterator_traits<
+ typename Collection::value_type::second_type>::value_type Element;
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(
+ key,
+ static_cast<typename Collection::value_type::second_type>(NULL)));
+ if (ret.second) {
+ ret.first->second = new Element();
+ }
+ return ret.first->second;
+}
+
+// Same as above but constructs the value using the single-argument constructor
+// and the given "arg".
+template <class Collection, class Arg>
+typename Collection::value_type::second_type&
+LookupOrInsertNew(Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const Arg& arg) {
+ typedef typename std::iterator_traits<
+ typename Collection::value_type::second_type>::value_type Element;
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(
+ key,
+ static_cast<typename Collection::value_type::second_type>(NULL)));
+ if (ret.second) {
+ ret.first->second = new Element(arg);
+ }
+ return ret.first->second;
+}
+
+// Lookup of linked/shared pointers is used in two scenarios:
+//
+// Use LookupOrInsertNewLinkedPtr if the container owns the elements.
+// In this case it is fine working with the raw pointer as long as it is
+// guaranteed that no other thread can delete/update an accessed element.
+// A mutex will need to lock the container operation as well as the use
+// of the returned elements. Finding an element may be performed using
+// FindLinkedPtr*().
+//
+// Use LookupOrInsertNewSharedPtr if the container does not own the elements
+// for their whole lifetime. This is typically the case when a reader allows
+// parallel updates to the container. In this case a Mutex only needs to lock
+// container operations, but all element operations must be performed on the
+// shared pointer. Finding an element must be performed using FindPtr*() and
+// cannot be done with FindLinkedPtr*() even though it compiles.
+
+// Lookup a key in a map or hash_map whose values are linked_ptrs. If it is
+// missing, set collection[key].reset(new Value::element_type) and return that.
+// Value::element_type must be default constructable.
+template <class Collection>
+typename Collection::value_type::second_type::element_type*
+LookupOrInsertNewLinkedPtr(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key) {
+ typedef typename Collection::value_type::second_type Value;
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(key, Value()));
+ if (ret.second) {
+ ret.first->second.reset(new typename Value::element_type);
+ }
+ return ret.first->second.get();
+}
+
+// A variant of LookupOrInsertNewLinkedPtr where the value is constructed using
+// a single-parameter constructor. Note: the constructor argument is computed
+// even if it will not be used, so only values cheap to compute should be passed
+// here. On the other hand it does not matter how expensive the construction of
+// the actual stored value is, as that only occurs if necessary.
+template <class Collection, class Arg>
+typename Collection::value_type::second_type::element_type*
+LookupOrInsertNewLinkedPtr(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const Arg& arg) {
+ typedef typename Collection::value_type::second_type Value;
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(key, Value()));
+ if (ret.second) {
+ ret.first->second.reset(new typename Value::element_type(arg));
+ }
+ return ret.first->second.get();
+}
+
+// Lookup a key in a map or hash_map whose values are shared_ptrs. If it is
+// missing, set collection[key].reset(new Value::element_type). Unlike
+// LookupOrInsertNewLinkedPtr, this function returns the shared_ptr instead of
+// the raw pointer. Value::element_type must be default constructable.
+template <class Collection>
+typename Collection::value_type::second_type&
+LookupOrInsertNewSharedPtr(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key) {
+ typedef typename Collection::value_type::second_type SharedPtr;
+ typedef typename Collection::value_type::second_type::element_type Element;
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(key, SharedPtr()));
+ if (ret.second) {
+ ret.first->second.reset(new Element());
+ }
+ return ret.first->second;
+}
+
+// A variant of LookupOrInsertNewSharedPtr where the value is constructed using
+// a single-parameter constructor. Note: the constructor argument is computed
+// even if it will not be used, so only values cheap to compute should be passed
+// here. On the other hand it does not matter how expensive the construction of
+// the actual stored value is, as that only occurs if necessary.
+template <class Collection, class Arg>
+typename Collection::value_type::second_type&
+LookupOrInsertNewSharedPtr(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const Arg& arg) {
+ typedef typename Collection::value_type::second_type SharedPtr;
+ typedef typename Collection::value_type::second_type::element_type Element;
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(key, SharedPtr()));
+ if (ret.second) {
+ ret.first->second.reset(new Element(arg));
+ }
+ return ret.first->second;
+}
+
+//
+// Misc Utility Functions
+//
+
+// Updates the value associated with the given key. If the key was not already
+// present, then the key-value pair are inserted and "previous" is unchanged. If
+// the key was already present, the value is updated and "*previous" will
+// contain a copy of the old value.
+//
+// InsertOrReturnExisting has complementary behavior that returns the
+// address of an already existing value, rather than updating it.
+template <class Collection>
+bool UpdateReturnCopy(Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& value,
+ typename Collection::value_type::second_type* previous) {
+ std::pair<typename Collection::iterator, bool> ret =
+ collection->insert(typename Collection::value_type(key, value));
+ if (!ret.second) {
+ // update
+ if (previous) {
+ *previous = ret.first->second;
+ }
+ ret.first->second = value;
+ return true;
+ }
+ return false;
+}
+
+// Same as above except that the key and value are passed as a pair.
+template <class Collection>
+bool UpdateReturnCopy(Collection* const collection,
+ const typename Collection::value_type& vt,
+ typename Collection::value_type::second_type* previous) {
+ std::pair<typename Collection::iterator, bool> ret = collection->insert(vt);
+ if (!ret.second) {
+ // update
+ if (previous) {
+ *previous = ret.first->second;
+ }
+ ret.first->second = vt.second;
+ return true;
+ }
+ return false;
+}
+
+// Tries to insert the given key-value pair into the collection. Returns NULL if
+// the insert succeeds. Otherwise, returns a pointer to the existing value.
+//
+// This complements UpdateReturnCopy in that it allows to update only after
+// verifying the old value and still insert quickly without having to look up
+// twice. Unlike UpdateReturnCopy this also does not come with the issue of an
+// undefined previous* in case new data was inserted.
+template <class Collection>
+typename Collection::value_type::second_type* const
+InsertOrReturnExisting(Collection* const collection,
+ const typename Collection::value_type& vt) {
+ std::pair<typename Collection::iterator, bool> ret = collection->insert(vt);
+ if (ret.second) {
+ return NULL; // Inserted, no existing previous value.
+ } else {
+ return &ret.first->second; // Return address of already existing value.
+ }
+}
+
+// Same as above, except for explicit key and data.
+template <class Collection>
+typename Collection::value_type::second_type* const
+InsertOrReturnExisting(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key,
+ const typename Collection::value_type::second_type& data) {
+ return InsertOrReturnExisting(collection,
+ typename Collection::value_type(key, data));
+}
+
+// Erases the collection item identified by the given key, and returns the value
+// associated with that key. It is assumed that the value (i.e., the
+// mapped_type) is a pointer. Returns NULL if the key was not found in the
+// collection.
+//
+// Examples:
+// map<string, MyType*> my_map;
+//
+// One line cleanup:
+// delete EraseKeyReturnValuePtr(&my_map, "abc");
+//
+// Use returned value:
+// scoped_ptr<MyType> value_ptr(EraseKeyReturnValuePtr(&my_map, "abc"));
+// if (value_ptr.get())
+// value_ptr->DoSomething();
+//
+template <class Collection>
+typename Collection::value_type::second_type EraseKeyReturnValuePtr(
+ Collection* const collection,
+ const typename Collection::value_type::first_type& key) {
+ typename Collection::iterator it = collection->find(key);
+ if (it == collection->end()) {
+ return NULL;
+ }
+ typename Collection::value_type::second_type v = it->second;
+ collection->erase(it);
+ return v;
+}
+
+// Inserts all the keys from map_container into key_container, which must
+// support insert(MapContainer::key_type).
+//
+// Note: any initial contents of the key_container are not cleared.
+template <class MapContainer, class KeyContainer>
+void InsertKeysFromMap(const MapContainer& map_container,
+ KeyContainer* key_container) {
+ GOOGLE_CHECK(key_container != NULL);
+ for (typename MapContainer::const_iterator it = map_container.begin();
+ it != map_container.end(); ++it) {
+ key_container->insert(it->first);
+ }
+}
+
+// Appends all the keys from map_container into key_container, which must
+// support push_back(MapContainer::key_type).
+//
+// Note: any initial contents of the key_container are not cleared.
+template <class MapContainer, class KeyContainer>
+void AppendKeysFromMap(const MapContainer& map_container,
+ KeyContainer* key_container) {
+ GOOGLE_CHECK(key_container != NULL);
+ for (typename MapContainer::const_iterator it = map_container.begin();
+ it != map_container.end(); ++it) {
+ key_container->push_back(it->first);
+ }
+}
+
+// A more specialized overload of AppendKeysFromMap to optimize reallocations
+// for the common case in which we're appending keys to a vector and hence can
+// (and sometimes should) call reserve() first.
+//
+// (It would be possible to play SFINAE games to call reserve() for any
+// container that supports it, but this seems to get us 99% of what we need
+// without the complexity of a SFINAE-based solution.)
+template <class MapContainer, class KeyType>
+void AppendKeysFromMap(const MapContainer& map_container,
+ vector<KeyType>* key_container) {
+ GOOGLE_CHECK(key_container != NULL);
+ // We now have the opportunity to call reserve(). Calling reserve() every
+ // time is a bad idea for some use cases: libstdc++'s implementation of
+ // vector<>::reserve() resizes the vector's backing store to exactly the
+ // given size (unless it's already at least that big). Because of this,
+ // the use case that involves appending a lot of small maps (total size
+ // N) one by one to a vector would be O(N^2). But never calling reserve()
+ // loses the opportunity to improve the use case of adding from a large
+ // map to an empty vector (this improves performance by up to 33%). A
+ // number of heuristics are possible; see the discussion in
+ // cl/34081696. Here we use the simplest one.
+ if (key_container->empty()) {
+ key_container->reserve(map_container.size());
+ }
+ for (typename MapContainer::const_iterator it = map_container.begin();
+ it != map_container.end(); ++it) {
+ key_container->push_back(it->first);
+ }
+}
+
+// Inserts all the values from map_container into value_container, which must
+// support push_back(MapContainer::mapped_type).
+//
+// Note: any initial contents of the value_container are not cleared.
+template <class MapContainer, class ValueContainer>
+void AppendValuesFromMap(const MapContainer& map_container,
+ ValueContainer* value_container) {
+ GOOGLE_CHECK(value_container != NULL);
+ for (typename MapContainer::const_iterator it = map_container.begin();
+ it != map_container.end(); ++it) {
+ value_container->push_back(it->second);
+ }
+}
+
+// A more specialized overload of AppendValuesFromMap to optimize reallocations
+// for the common case in which we're appending values to a vector and hence
+// can (and sometimes should) call reserve() first.
+//
+// (It would be possible to play SFINAE games to call reserve() for any
+// container that supports it, but this seems to get us 99% of what we need
+// without the complexity of a SFINAE-based solution.)
+template <class MapContainer, class ValueType>
+void AppendValuesFromMap(const MapContainer& map_container,
+ vector<ValueType>* value_container) {
+ GOOGLE_CHECK(value_container != NULL);
+ // See AppendKeysFromMap for why this is done.
+ if (value_container->empty()) {
+ value_container->reserve(map_container.size());
+ }
+ for (typename MapContainer::const_iterator it = map_container.begin();
+ it != map_container.end(); ++it) {
+ value_container->push_back(it->second);
+ }
+}
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_MAP_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.cc
new file mode 100644
index 0000000000..0373b2bb97
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.cc
@@ -0,0 +1,144 @@
+// 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.
+
+// All Rights Reserved.
+//
+// Author: Maxim Lifantsev
+//
+
+#include <google/protobuf/stubs/mathlimits.h>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+// MSVC++ 2005 and older compilers think the header declaration was a
+// definition, and erroneously flag these as a duplicate definition.
+#if defined(COMPILER_MSVC) || __cpluscplus < 201103L
+
+#define DEF_COMMON_LIMITS(Type)
+#define DEF_UNSIGNED_INT_LIMITS(Type)
+#define DEF_SIGNED_INT_LIMITS(Type)
+#define DEF_PRECISION_LIMITS(Type)
+
+#else
+
+#define DEF_COMMON_LIMITS(Type) \
+const bool MathLimits<Type>::kIsSigned; \
+const bool MathLimits<Type>::kIsInteger; \
+const int MathLimits<Type>::kMin10Exp; \
+const int MathLimits<Type>::kMax10Exp;
+
+#define DEF_UNSIGNED_INT_LIMITS(Type) \
+DEF_COMMON_LIMITS(Type) \
+const Type MathLimits<Type>::kPosMin; \
+const Type MathLimits<Type>::kPosMax; \
+const Type MathLimits<Type>::kMin; \
+const Type MathLimits<Type>::kMax; \
+const Type MathLimits<Type>::kEpsilon; \
+const Type MathLimits<Type>::kStdError;
+
+#define DEF_SIGNED_INT_LIMITS(Type) \
+DEF_UNSIGNED_INT_LIMITS(Type) \
+const Type MathLimits<Type>::kNegMin; \
+const Type MathLimits<Type>::kNegMax;
+
+#define DEF_PRECISION_LIMITS(Type) \
+const int MathLimits<Type>::kPrecisionDigits;
+
+#endif // not COMPILER_MSVC
+
+// http://en.wikipedia.org/wiki/Quadruple_precision_floating-point_format#Double-double_arithmetic
+// With some compilers (gcc 4.6.x) on some platforms (powerpc64),
+// "long double" is implemented as a pair of double: "double double" format.
+// This causes a problem with epsilon (eps).
+// eps is the smallest positive number such that 1.0 + eps > 1.0
+//
+// Normal format: 1.0 + e = 1.0...01 // N-1 zeros for N fraction bits
+// D-D format: 1.0 + e = 1.000...0001 // epsilon can be very small
+//
+// In the normal format, 1.0 + e has to fit in one stretch of bits.
+// The maximum rounding error is half of eps.
+//
+// In the double-double format, 1.0 + e splits across two doubles:
+// 1.0 in the high double, e in the low double, and they do not have to
+// be contiguous. The maximum rounding error on a value close to 1.0 is
+// much larger than eps.
+//
+// Some code checks for errors by comparing a computed value to a golden
+// value +/- some multiple of the maximum rounding error. The maximum
+// rounding error is not available so we use eps as an approximation
+// instead. That fails when long double is in the double-double format.
+// Therefore, we define kStdError as a multiple of
+// max(DBL_EPSILON * DBL_EPSILON, kEpsilon) rather than a multiple of kEpsilon.
+
+#define DEF_FP_LIMITS(Type, PREFIX) \
+DEF_COMMON_LIMITS(Type) \
+const Type MathLimits<Type>::kPosMin = PREFIX##_MIN; \
+const Type MathLimits<Type>::kPosMax = PREFIX##_MAX; \
+const Type MathLimits<Type>::kMin = -MathLimits<Type>::kPosMax; \
+const Type MathLimits<Type>::kMax = MathLimits<Type>::kPosMax; \
+const Type MathLimits<Type>::kNegMin = -MathLimits<Type>::kPosMin; \
+const Type MathLimits<Type>::kNegMax = -MathLimits<Type>::kPosMax; \
+const Type MathLimits<Type>::kEpsilon = PREFIX##_EPSILON; \
+/* 32 is 5 bits of mantissa error; should be adequate for common errors */ \
+const Type MathLimits<Type>::kStdError = \
+ 32 * (DBL_EPSILON * DBL_EPSILON > MathLimits<Type>::kEpsilon \
+ ? DBL_EPSILON * DBL_EPSILON : MathLimits<Type>::kEpsilon); \
+DEF_PRECISION_LIMITS(Type) \
+const Type MathLimits<Type>::kNaN = HUGE_VAL - HUGE_VAL; \
+const Type MathLimits<Type>::kPosInf = HUGE_VAL; \
+const Type MathLimits<Type>::kNegInf = -HUGE_VAL;
+
+// The following are *not* casts!
+DEF_SIGNED_INT_LIMITS(int8)
+DEF_SIGNED_INT_LIMITS(int16) // NOLINT(readability/casting)
+DEF_SIGNED_INT_LIMITS(int32) // NOLINT(readability/casting)
+DEF_SIGNED_INT_LIMITS(int64) // NOLINT(readability/casting)
+DEF_UNSIGNED_INT_LIMITS(uint8)
+DEF_UNSIGNED_INT_LIMITS(uint16) // NOLINT(readability/casting)
+DEF_UNSIGNED_INT_LIMITS(uint32) // NOLINT(readability/casting)
+DEF_UNSIGNED_INT_LIMITS(uint64) // NOLINT(readability/casting)
+
+DEF_SIGNED_INT_LIMITS(long int)
+DEF_UNSIGNED_INT_LIMITS(unsigned long int)
+
+DEF_FP_LIMITS(float, FLT)
+DEF_FP_LIMITS(double, DBL)
+DEF_FP_LIMITS(long double, LDBL);
+
+#undef DEF_COMMON_LIMITS
+#undef DEF_SIGNED_INT_LIMITS
+#undef DEF_UNSIGNED_INT_LIMITS
+#undef DEF_FP_LIMITS
+#undef DEF_PRECISION_LIMITS
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.h
new file mode 100644
index 0000000000..70e47bff18
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathlimits.h
@@ -0,0 +1,279 @@
+// 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.
+
+// All Rights Reserved.
+//
+// Author: Maxim Lifantsev
+//
+// Useful integer and floating point limits and type traits.
+//
+// This partially replaces/duplictes numeric_limits<> from <limits>.
+// We get a Google-style class that we have a greater control over
+// and thus can add new features to it or fix whatever happens to be broken in
+// numeric_limits for the compilers we use.
+//
+
+#ifndef UTIL_MATH_MATHLIMITS_H__
+#define UTIL_MATH_MATHLIMITS_H__
+
+// <math.h> lacks a lot of prototypes. However, this file needs <math.h> to
+// access old-fashioned isinf et al. Even worse more: this file must not
+// include <cmath> because that breaks the definition of isinf with gcc 4.9.
+//
+// TODO(mec): after C++11 everywhere, use <cmath> and std::isinf in this file.
+#include <math.h>
+#include <string.h>
+
+#include <cfloat>
+
+#include <google/protobuf/stubs/common.h>
+
+// ========================================================================= //
+
+// Useful integer and floating point limits and type traits.
+// This is just for the documentation;
+// real members are defined in our specializations below.
+namespace google {
+namespace protobuf {
+template<typename T> struct MathLimits {
+ // Type name.
+ typedef T Type;
+ // Unsigned version of the Type with the same byte size.
+ // Same as Type for floating point and unsigned types.
+ typedef T UnsignedType;
+ // If the type supports negative values.
+ static const bool kIsSigned;
+ // If the type supports only integer values.
+ static const bool kIsInteger;
+ // Magnitude-wise smallest representable positive value.
+ static const Type kPosMin;
+ // Magnitude-wise largest representable positive value.
+ static const Type kPosMax;
+ // Smallest representable value.
+ static const Type kMin;
+ // Largest representable value.
+ static const Type kMax;
+ // Magnitude-wise smallest representable negative value.
+ // Present only if kIsSigned.
+ static const Type kNegMin;
+ // Magnitude-wise largest representable negative value.
+ // Present only if kIsSigned.
+ static const Type kNegMax;
+ // Smallest integer x such that 10^x is representable.
+ static const int kMin10Exp;
+ // Largest integer x such that 10^x is representable.
+ static const int kMax10Exp;
+ // Smallest positive value such that Type(1) + kEpsilon != Type(1)
+ static const Type kEpsilon;
+ // Typical rounding error that is enough to cover
+ // a few simple floating-point operations.
+ // Slightly larger than kEpsilon to account for a few rounding errors.
+ // Is zero if kIsInteger.
+ static const Type kStdError;
+ // Number of decimal digits of mantissa precision.
+ // Present only if !kIsInteger.
+ static const int kPrecisionDigits;
+ // Not a number, i.e. result of 0/0.
+ // Present only if !kIsInteger.
+ static const Type kNaN;
+ // Positive infinity, i.e. result of 1/0.
+ // Present only if !kIsInteger.
+ static const Type kPosInf;
+ // Negative infinity, i.e. result of -1/0.
+ // Present only if !kIsInteger.
+ static const Type kNegInf;
+
+ // NOTE: Special floating point values behave
+ // in a special (but mathematically-logical) way
+ // in terms of (in)equalty comparison and mathematical operations
+ // -- see out unittest for examples.
+
+ // Special floating point value testers.
+ // Present in integer types for convenience.
+ static bool IsFinite(const Type x);
+ static bool IsNaN(const Type x);
+ static bool IsInf(const Type x);
+ static bool IsPosInf(const Type x);
+ static bool IsNegInf(const Type x);
+};
+
+// ========================================================================= //
+
+// All #define-s below are simply to refactor the declarations of
+// MathLimits template specializations.
+// They are all #undef-ined below.
+
+// The hoop-jumping in *_INT_(MAX|MIN) below is so that the compiler does not
+// get an overflow while computing the constants.
+
+#define SIGNED_INT_MAX(Type) \
+ (((Type(1) << (sizeof(Type)*8 - 2)) - 1) + (Type(1) << (sizeof(Type)*8 - 2)))
+
+#define SIGNED_INT_MIN(Type) \
+ (-(Type(1) << (sizeof(Type)*8 - 2)) - (Type(1) << (sizeof(Type)*8 - 2)))
+
+#define UNSIGNED_INT_MAX(Type) \
+ (((Type(1) << (sizeof(Type)*8 - 1)) - 1) + (Type(1) << (sizeof(Type)*8 - 1)))
+
+// Compile-time selected log10-related constants for integer types.
+#define SIGNED_MAX_10_EXP(Type) \
+ (sizeof(Type) == 1 ? 2 : ( \
+ sizeof(Type) == 2 ? 4 : ( \
+ sizeof(Type) == 4 ? 9 : ( \
+ sizeof(Type) == 8 ? 18 : -1))))
+
+#define UNSIGNED_MAX_10_EXP(Type) \
+ (sizeof(Type) == 1 ? 2 : ( \
+ sizeof(Type) == 2 ? 4 : ( \
+ sizeof(Type) == 4 ? 9 : ( \
+ sizeof(Type) == 8 ? 19 : -1))))
+
+#define DECL_INT_LIMIT_FUNCS \
+ static bool IsFinite(const Type /*x*/) { return true; } \
+ static bool IsNaN(const Type /*x*/) { return false; } \
+ static bool IsInf(const Type /*x*/) { return false; } \
+ static bool IsPosInf(const Type /*x*/) { return false; } \
+ static bool IsNegInf(const Type /*x*/) { return false; }
+
+#define DECL_SIGNED_INT_LIMITS(IntType, UnsignedIntType) \
+template<> \
+struct LIBPROTOBUF_EXPORT MathLimits<IntType> { \
+ typedef IntType Type; \
+ typedef UnsignedIntType UnsignedType; \
+ static const bool kIsSigned = true; \
+ static const bool kIsInteger = true; \
+ static const Type kPosMin = 1; \
+ static const Type kPosMax = SIGNED_INT_MAX(Type); \
+ static const Type kMin = SIGNED_INT_MIN(Type); \
+ static const Type kMax = kPosMax; \
+ static const Type kNegMin = -1; \
+ static const Type kNegMax = kMin; \
+ static const int kMin10Exp = 0; \
+ static const int kMax10Exp = SIGNED_MAX_10_EXP(Type); \
+ static const Type kEpsilon = 1; \
+ static const Type kStdError = 0; \
+ DECL_INT_LIMIT_FUNCS \
+};
+
+#define DECL_UNSIGNED_INT_LIMITS(IntType) \
+template<> \
+struct LIBPROTOBUF_EXPORT MathLimits<IntType> { \
+ typedef IntType Type; \
+ typedef IntType UnsignedType; \
+ static const bool kIsSigned = false; \
+ static const bool kIsInteger = true; \
+ static const Type kPosMin = 1; \
+ static const Type kPosMax = UNSIGNED_INT_MAX(Type); \
+ static const Type kMin = 0; \
+ static const Type kMax = kPosMax; \
+ static const int kMin10Exp = 0; \
+ static const int kMax10Exp = UNSIGNED_MAX_10_EXP(Type); \
+ static const Type kEpsilon = 1; \
+ static const Type kStdError = 0; \
+ DECL_INT_LIMIT_FUNCS \
+};
+
+DECL_SIGNED_INT_LIMITS(signed char, unsigned char)
+DECL_SIGNED_INT_LIMITS(signed short int, unsigned short int)
+DECL_SIGNED_INT_LIMITS(signed int, unsigned int)
+DECL_SIGNED_INT_LIMITS(signed long int, unsigned long int)
+DECL_SIGNED_INT_LIMITS(signed long long int, unsigned long long int)
+DECL_UNSIGNED_INT_LIMITS(unsigned char)
+DECL_UNSIGNED_INT_LIMITS(unsigned short int)
+DECL_UNSIGNED_INT_LIMITS(unsigned int)
+DECL_UNSIGNED_INT_LIMITS(unsigned long int)
+DECL_UNSIGNED_INT_LIMITS(unsigned long long int)
+
+#undef DECL_SIGNED_INT_LIMITS
+#undef DECL_UNSIGNED_INT_LIMITS
+#undef SIGNED_INT_MAX
+#undef SIGNED_INT_MIN
+#undef UNSIGNED_INT_MAX
+#undef SIGNED_MAX_10_EXP
+#undef UNSIGNED_MAX_10_EXP
+#undef DECL_INT_LIMIT_FUNCS
+
+// ========================================================================= //
+#ifdef WIN32 // Lacks built-in isnan() and isinf()
+#define DECL_FP_LIMIT_FUNCS \
+ static bool IsFinite(const Type x) { return _finite(x); } \
+ static bool IsNaN(const Type x) { return _isnan(x); } \
+ static bool IsInf(const Type x) { return (_fpclass(x) & (_FPCLASS_NINF | _FPCLASS_PINF)) != 0; } \
+ static bool IsPosInf(const Type x) { return _fpclass(x) == _FPCLASS_PINF; } \
+ static bool IsNegInf(const Type x) { return _fpclass(x) == _FPCLASS_NINF; }
+#else
+#define DECL_FP_LIMIT_FUNCS \
+ static bool IsFinite(const Type x) { return !isinf(x) && !isnan(x); } \
+ static bool IsNaN(const Type x) { return isnan(x); } \
+ static bool IsInf(const Type x) { return isinf(x); } \
+ static bool IsPosInf(const Type x) { return isinf(x) && x > 0; } \
+ static bool IsNegInf(const Type x) { return isinf(x) && x < 0; }
+#endif
+
+// We can't put floating-point constant values in the header here because
+// such constants are not considered to be primitive-type constants by gcc.
+// CAVEAT: Hence, they are going to be initialized only during
+// the global objects construction time.
+#define DECL_FP_LIMITS(FP_Type, PREFIX) \
+template<> \
+struct LIBPROTOBUF_EXPORT MathLimits<FP_Type> { \
+ typedef FP_Type Type; \
+ typedef FP_Type UnsignedType; \
+ static const bool kIsSigned = true; \
+ static const bool kIsInteger = false; \
+ static const Type kPosMin; \
+ static const Type kPosMax; \
+ static const Type kMin; \
+ static const Type kMax; \
+ static const Type kNegMin; \
+ static const Type kNegMax; \
+ static const int kMin10Exp = PREFIX##_MIN_10_EXP; \
+ static const int kMax10Exp = PREFIX##_MAX_10_EXP; \
+ static const Type kEpsilon; \
+ static const Type kStdError; \
+ static const int kPrecisionDigits = PREFIX##_DIG; \
+ static const Type kNaN; \
+ static const Type kPosInf; \
+ static const Type kNegInf; \
+ DECL_FP_LIMIT_FUNCS \
+};
+
+DECL_FP_LIMITS(float, FLT)
+DECL_FP_LIMITS(double, DBL)
+DECL_FP_LIMITS(long double, LDBL)
+
+#undef DECL_FP_LIMITS
+#undef DECL_FP_LIMIT_FUNCS
+
+// ========================================================================= //
+} // namespace protobuf
+} // namespace google
+
+#endif // UTIL_MATH_MATHLIMITS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathutil.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathutil.h
new file mode 100644
index 0000000000..27956a8ea0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mathutil.h
@@ -0,0 +1,162 @@
+// 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.
+#ifndef GOOGLE_PROTOBUF_STUBS_MATHUTIL_H_
+#define GOOGLE_PROTOBUF_STUBS_MATHUTIL_H_
+
+#include <float.h>
+#include <math.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/mathlimits.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+template<typename T>
+bool IsNan(T value) {
+ return false;
+}
+template<>
+inline bool IsNan(float value) {
+#ifdef _MSC_VER
+ return _isnan(value);
+#else
+ return isnan(value);
+#endif
+}
+template<>
+inline bool IsNan(double value) {
+#ifdef _MSC_VER
+ return _isnan(value);
+#else
+ return isnan(value);
+#endif
+}
+
+template<typename T>
+bool AlmostEquals(T a, T b) {
+ return a == b;
+}
+template<>
+inline bool AlmostEquals(float a, float b) {
+ return fabs(a - b) < 32 * FLT_EPSILON;
+}
+
+template<>
+inline bool AlmostEquals(double a, double b) {
+ return fabs(a - b) < 32 * DBL_EPSILON;
+}
+} // namespace internal
+
+class MathUtil {
+ public:
+ template<typename T>
+ static T Sign(T value) {
+ if (value == T(0) || ::google::protobuf::internal::IsNan<T>(value)) {
+ return value;
+ }
+ return value > T(0) ? 1 : -1;
+ }
+
+ template<typename T>
+ static bool AlmostEquals(T a, T b) {
+ return ::google::protobuf::internal::AlmostEquals(a, b);
+ }
+
+ // Largest of two values.
+ // Works correctly for special floating point values.
+ // Note: 0.0 and -0.0 are not differentiated by Max (Max(0.0, -0.0) is -0.0),
+ // which should be OK because, although they (can) have different
+ // bit representation, they are observably the same when examined
+ // with arithmetic and (in)equality operators.
+ template<typename T>
+ static T Max(const T x, const T y) {
+ return MathLimits<T>::IsNaN(x) || x > y ? x : y;
+ }
+
+ // Absolute value of x
+ // Works correctly for unsigned types and
+ // for special floating point values.
+ // Note: 0.0 and -0.0 are not differentiated by Abs (Abs(0.0) is -0.0),
+ // which should be OK: see the comment for Max above.
+ template<typename T>
+ static T Abs(const T x) {
+ return x > T(0) ? x : -x;
+ }
+
+ // Absolute value of the difference between two numbers.
+ // Works correctly for signed types and special floating point values.
+ template<typename T>
+ static typename MathLimits<T>::UnsignedType AbsDiff(const T x, const T y) {
+ // Carries out arithmetic as unsigned to avoid overflow.
+ typedef typename MathLimits<T>::UnsignedType R;
+ return x > y ? R(x) - R(y) : R(y) - R(x);
+ }
+
+ // If two (usually floating point) numbers are within a certain
+ // fraction of their magnitude or within a certain absolute margin of error.
+ // This is the same as the following but faster:
+ // WithinFraction(x, y, fraction) || WithinMargin(x, y, margin)
+ // E.g. WithinFraction(0.0, 1e-10, 1e-5) is false but
+ // WithinFractionOrMargin(0.0, 1e-10, 1e-5, 1e-5) is true.
+ template<typename T>
+ static bool WithinFractionOrMargin(const T x, const T y,
+ const T fraction, const T margin);
+};
+
+template<typename T>
+bool MathUtil::WithinFractionOrMargin(const T x, const T y,
+ const T fraction, const T margin) {
+ // Not just "0 <= fraction" to fool the compiler for unsigned types.
+ GOOGLE_DCHECK((T(0) < fraction || T(0) == fraction) &&
+ fraction < T(1) &&
+ margin >= T(0));
+
+ // Template specialization will convert the if() condition to a constant,
+ // which will cause the compiler to generate code for either the "if" part
+ // or the "then" part. In this way we avoid a compiler warning
+ // about a potential integer overflow in crosstool v12 (gcc 4.3.1).
+ if (MathLimits<T>::kIsInteger) {
+ return x == y;
+ } else {
+ // IsFinite checks are to make kPosInf and kNegInf not within fraction
+ if (!MathLimits<T>::IsFinite(x) && !MathLimits<T>::IsFinite(y)) {
+ return false;
+ }
+ T relative_margin = static_cast<T>(fraction * Max(Abs(x), Abs(y)));
+ return AbsDiff(x, y) <= Max(margin, relative_margin);
+ }
+}
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_MATHUTIL_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mutex.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mutex.h
new file mode 100644
index 0000000000..7ef1cb6916
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/mutex.h
@@ -0,0 +1,148 @@
+// Copyright (c) 2006, Google Inc.
+// All rights reserved.
+//
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_STUBS_MUTEX_H_
+#define GOOGLE_PROTOBUF_STUBS_MUTEX_H_
+
+#ifdef GOOGLE_PROTOBUF_NO_THREADLOCAL
+#include <pthread.h>
+#endif
+
+#include <google/protobuf/stubs/macros.h>
+
+// ===================================================================
+// emulates google3/base/mutex.h
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// A Mutex is a non-reentrant (aka non-recursive) mutex. At most one thread T
+// may hold a mutex at a given time. If T attempts to Lock() the same Mutex
+// while holding it, T will deadlock.
+class LIBPROTOBUF_EXPORT Mutex {
+ public:
+ // Create a Mutex that is not held by anybody.
+ Mutex();
+
+ // Destructor
+ ~Mutex();
+
+ // Block if necessary until this Mutex is free, then acquire it exclusively.
+ void Lock();
+
+ // Release this Mutex. Caller must hold it exclusively.
+ void Unlock();
+
+ // Crash if this Mutex is not held exclusively by this thread.
+ // May fail to crash when it should; will never crash when it should not.
+ void AssertHeld();
+
+ private:
+ struct Internal;
+ Internal* mInternal;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Mutex);
+};
+
+// Undefine the macros to workaround the conflicts with Google internal
+// MutexLock implementation.
+// TODO(liujisi): Remove the undef once internal macros are removed.
+#undef MutexLock
+#undef ReaderMutexLock
+#undef WriterMutexLock
+#undef MutexLockMaybe
+
+// MutexLock(mu) acquires mu when constructed and releases it when destroyed.
+class LIBPROTOBUF_EXPORT MutexLock {
+ public:
+ explicit MutexLock(Mutex *mu) : mu_(mu) { this->mu_->Lock(); }
+ ~MutexLock() { this->mu_->Unlock(); }
+ private:
+ Mutex *const mu_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MutexLock);
+};
+
+// TODO(kenton): Implement these? Hard to implement portably.
+typedef MutexLock ReaderMutexLock;
+typedef MutexLock WriterMutexLock;
+
+// MutexLockMaybe is like MutexLock, but is a no-op when mu is NULL.
+class LIBPROTOBUF_EXPORT MutexLockMaybe {
+ public:
+ explicit MutexLockMaybe(Mutex *mu) :
+ mu_(mu) { if (this->mu_ != NULL) { this->mu_->Lock(); } }
+ ~MutexLockMaybe() { if (this->mu_ != NULL) { this->mu_->Unlock(); } }
+ private:
+ Mutex *const mu_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MutexLockMaybe);
+};
+
+#if defined(GOOGLE_PROTOBUF_NO_THREADLOCAL)
+template<typename T>
+class ThreadLocalStorage {
+ public:
+ ThreadLocalStorage() {
+ pthread_key_create(&key_, &ThreadLocalStorage::Delete);
+ }
+ ~ThreadLocalStorage() {
+ pthread_key_delete(key_);
+ }
+ T* Get() {
+ T* result = static_cast<T*>(pthread_getspecific(key_));
+ if (result == NULL) {
+ result = new T();
+ pthread_setspecific(key_, result);
+ }
+ return result;
+ }
+ private:
+ static void Delete(void* value) {
+ delete static_cast<T*>(value);
+ }
+ pthread_key_t key_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ThreadLocalStorage);
+};
+#endif
+
+} // namespace internal
+
+// We made these internal so that they would show up as such in the docs,
+// but we don't want to stick "internal::" in front of them everywhere.
+using internal::Mutex;
+using internal::MutexLock;
+using internal::ReaderMutexLock;
+using internal::WriterMutexLock;
+using internal::MutexLockMaybe;
+
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_MUTEX_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.cc
new file mode 100644
index 0000000000..889c647660
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.cc
@@ -0,0 +1,99 @@
+// 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)
+//
+// emulates google3/base/once.h
+//
+// This header is intended to be included only by internal .cc files and
+// generated .pb.cc files. Users should not use this directly.
+
+#include <google/protobuf/stubs/once.h>
+
+#ifndef GOOGLE_PROTOBUF_NO_THREAD_SAFETY
+
+#ifdef _WIN32
+#include <windows.h>
+#else
+#include <sched.h>
+#endif
+
+#include <google/protobuf/stubs/atomicops.h>
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+void SchedYield() {
+#ifdef _WIN32
+ Sleep(0);
+#else // POSIX
+ sched_yield();
+#endif
+}
+
+} // namespace
+
+void GoogleOnceInitImpl(ProtobufOnceType* once, Closure* closure) {
+ internal::AtomicWord state = internal::Acquire_Load(once);
+ // Fast path. The provided closure was already executed.
+ if (state == ONCE_STATE_DONE) {
+ return;
+ }
+ // The closure execution did not complete yet. The once object can be in one
+ // of the two following states:
+ // - UNINITIALIZED: We are the first thread calling this function.
+ // - EXECUTING_CLOSURE: Another thread is already executing the closure.
+ //
+ // First, try to change the state from UNINITIALIZED to EXECUTING_CLOSURE
+ // atomically.
+ state = internal::Acquire_CompareAndSwap(
+ once, ONCE_STATE_UNINITIALIZED, ONCE_STATE_EXECUTING_CLOSURE);
+ if (state == ONCE_STATE_UNINITIALIZED) {
+ // We are the first thread to call this function, so we have to call the
+ // closure.
+ closure->Run();
+ internal::Release_Store(once, ONCE_STATE_DONE);
+ } else {
+ // Another thread has already started executing the closure. We need to
+ // wait until it completes the initialization.
+ while (state == ONCE_STATE_EXECUTING_CLOSURE) {
+ // Note that futex() could be used here on Linux as an improvement.
+ SchedYield();
+ state = internal::Acquire_Load(once);
+ }
+ }
+}
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_NO_THREAD_SAFETY
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.h
new file mode 100644
index 0000000000..1f082c37e9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once.h
@@ -0,0 +1,167 @@
+// 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)
+//
+// emulates google3/base/once.h
+//
+// This header is intended to be included only by internal .cc files and
+// generated .pb.cc files. Users should not use this directly.
+//
+// This is basically a portable version of pthread_once().
+//
+// This header declares:
+// * A type called ProtobufOnceType.
+// * A macro GOOGLE_PROTOBUF_DECLARE_ONCE() which declares a variable of type
+// ProtobufOnceType. This is the only legal way to declare such a variable.
+// The macro may only be used at the global scope (you cannot create local or
+// class member variables of this type).
+// * A function GoogleOnceInit(ProtobufOnceType* once, void (*init_func)()).
+// This function, when invoked multiple times given the same ProtobufOnceType
+// object, will invoke init_func on the first call only, and will make sure
+// none of the calls return before that first call to init_func has finished.
+// * The user can provide a parameter which GoogleOnceInit() forwards to the
+// user-provided function when it is called. Usage example:
+// int a = 10;
+// GoogleOnceInit(&my_once, &MyFunctionExpectingIntArgument, &a);
+// * This implementation guarantees that ProtobufOnceType is a POD (i.e. no
+// static initializer generated).
+//
+// This implements a way to perform lazy initialization. It's more efficient
+// than using mutexes as no lock is needed if initialization has already
+// happened.
+//
+// Example usage:
+// void Init();
+// GOOGLE_PROTOBUF_DECLARE_ONCE(once_init);
+//
+// // Calls Init() exactly once.
+// void InitOnce() {
+// GoogleOnceInit(&once_init, &Init);
+// }
+//
+// Note that if GoogleOnceInit() is called before main() has begun, it must
+// only be called by the thread that will eventually call main() -- that is,
+// the thread that performs dynamic initialization. In general this is a safe
+// assumption since people don't usually construct threads before main() starts,
+// but it is technically not guaranteed. Unfortunately, Win32 provides no way
+// whatsoever to statically-initialize its synchronization primitives, so our
+// only choice is to assume that dynamic initialization is single-threaded.
+
+#ifndef GOOGLE_PROTOBUF_STUBS_ONCE_H__
+#define GOOGLE_PROTOBUF_STUBS_ONCE_H__
+
+#include <google/protobuf/stubs/atomicops.h>
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+#ifdef GOOGLE_PROTOBUF_NO_THREAD_SAFETY
+
+typedef bool ProtobufOnceType;
+
+#define GOOGLE_PROTOBUF_ONCE_INIT false
+
+inline void GoogleOnceInit(ProtobufOnceType* once, void (*init_func)()) {
+ if (!*once) {
+ *once = true;
+ init_func();
+ }
+}
+
+template <typename Arg>
+inline void GoogleOnceInit(ProtobufOnceType* once, void (*init_func)(Arg),
+ Arg arg) {
+ if (!*once) {
+ *once = true;
+ init_func(arg);
+ }
+}
+
+#else
+
+enum {
+ ONCE_STATE_UNINITIALIZED = 0,
+ ONCE_STATE_EXECUTING_CLOSURE = 1,
+ ONCE_STATE_DONE = 2
+};
+
+typedef internal::AtomicWord ProtobufOnceType;
+
+#define GOOGLE_PROTOBUF_ONCE_INIT ::google::protobuf::ONCE_STATE_UNINITIALIZED
+
+LIBPROTOBUF_EXPORT
+void GoogleOnceInitImpl(ProtobufOnceType* once, Closure* closure);
+
+inline void GoogleOnceInit(ProtobufOnceType* once, void (*init_func)()) {
+ if (internal::Acquire_Load(once) != ONCE_STATE_DONE) {
+ internal::FunctionClosure0 func(init_func, false);
+ GoogleOnceInitImpl(once, &func);
+ }
+}
+
+template <typename Arg>
+inline void GoogleOnceInit(ProtobufOnceType* once, void (*init_func)(Arg*),
+ Arg* arg) {
+ if (internal::Acquire_Load(once) != ONCE_STATE_DONE) {
+ internal::FunctionClosure1<Arg*> func(init_func, false, arg);
+ GoogleOnceInitImpl(once, &func);
+ }
+}
+
+#endif // GOOGLE_PROTOBUF_NO_THREAD_SAFETY
+
+class GoogleOnceDynamic {
+ public:
+ GoogleOnceDynamic() : state_(GOOGLE_PROTOBUF_ONCE_INIT) { }
+
+ // If this->Init() has not been called before by any thread,
+ // execute (*func_with_arg)(arg) then return.
+ // Otherwise, wait until that prior invocation has finished
+ // executing its function, then return.
+ template<typename T>
+ void Init(void (*func_with_arg)(T*), T* arg) {
+ GoogleOnceInit<T>(&this->state_,
+ func_with_arg,
+ arg);
+ }
+ private:
+ ProtobufOnceType state_;
+};
+
+#define GOOGLE_PROTOBUF_DECLARE_ONCE(NAME) \
+ ::google::protobuf::ProtobufOnceType NAME = GOOGLE_PROTOBUF_ONCE_INIT
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_ONCE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once_unittest.cc
new file mode 100644
index 0000000000..37def58d03
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/once_unittest.cc
@@ -0,0 +1,255 @@
+// 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)
+
+#ifdef _WIN32
+#include <windows.h>
+#else
+#include <unistd.h>
+#include <pthread.h>
+#endif
+
+#include <google/protobuf/stubs/once.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+using internal::NewCallback;
+namespace {
+
+class OnceInitTest : public testing::Test {
+ protected:
+ void SetUp() {
+ state_ = INIT_NOT_STARTED;
+ current_test_ = this;
+ }
+
+ // Since ProtobufOnceType is only allowed to be allocated in static storage,
+ // each test must use a different pair of ProtobufOnceType objects which it
+ // must declare itself.
+ void SetOnces(ProtobufOnceType* once, ProtobufOnceType* recursive_once) {
+ once_ = once;
+ recursive_once_ = recursive_once;
+ }
+
+ void InitOnce() {
+ GoogleOnceInit(once_, &InitStatic);
+ }
+ void InitRecursiveOnce() {
+ GoogleOnceInit(recursive_once_, &InitRecursiveStatic);
+ }
+
+ void BlockInit() { init_blocker_.Lock(); }
+ void UnblockInit() { init_blocker_.Unlock(); }
+
+ class TestThread {
+ public:
+ TestThread(Closure* callback)
+ : done_(false), joined_(false), callback_(callback) {
+#ifdef _WIN32
+ thread_ = CreateThread(NULL, 0, &Start, this, 0, NULL);
+#else
+ pthread_create(&thread_, NULL, &Start, this);
+#endif
+ }
+ ~TestThread() {
+ if (!joined_) Join();
+ }
+
+ bool IsDone() {
+ MutexLock lock(&done_mutex_);
+ return done_;
+ }
+ void Join() {
+ joined_ = true;
+#ifdef _WIN32
+ WaitForSingleObject(thread_, INFINITE);
+ CloseHandle(thread_);
+#else
+ pthread_join(thread_, NULL);
+#endif
+ }
+
+ private:
+#ifdef _WIN32
+ HANDLE thread_;
+#else
+ pthread_t thread_;
+#endif
+
+ Mutex done_mutex_;
+ bool done_;
+ bool joined_;
+ Closure* callback_;
+
+#ifdef _WIN32
+ static DWORD WINAPI Start(LPVOID arg) {
+#else
+ static void* Start(void* arg) {
+#endif
+ reinterpret_cast<TestThread*>(arg)->Run();
+ return 0;
+ }
+
+ void Run() {
+ callback_->Run();
+ MutexLock lock(&done_mutex_);
+ done_ = true;
+ }
+ };
+
+ TestThread* RunInitOnceInNewThread() {
+ return new TestThread(internal::NewCallback(this, &OnceInitTest::InitOnce));
+ }
+ TestThread* RunInitRecursiveOnceInNewThread() {
+ return new TestThread(
+ internal::NewCallback(this, &OnceInitTest::InitRecursiveOnce));
+ }
+
+ enum State {
+ INIT_NOT_STARTED,
+ INIT_STARTED,
+ INIT_DONE
+ };
+ State CurrentState() {
+ MutexLock lock(&mutex_);
+ return state_;
+ }
+
+ void WaitABit() {
+#ifdef _WIN32
+ Sleep(1000);
+#else
+ sleep(1);
+#endif
+ }
+
+ private:
+ Mutex mutex_;
+ Mutex init_blocker_;
+ State state_;
+ ProtobufOnceType* once_;
+ ProtobufOnceType* recursive_once_;
+
+ void Init() {
+ MutexLock lock(&mutex_);
+ EXPECT_EQ(INIT_NOT_STARTED, state_);
+ state_ = INIT_STARTED;
+ mutex_.Unlock();
+ init_blocker_.Lock();
+ init_blocker_.Unlock();
+ mutex_.Lock();
+ state_ = INIT_DONE;
+ }
+
+ static OnceInitTest* current_test_;
+ static void InitStatic() { current_test_->Init(); }
+ static void InitRecursiveStatic() { current_test_->InitOnce(); }
+};
+
+OnceInitTest* OnceInitTest::current_test_ = NULL;
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(simple_once);
+
+TEST_F(OnceInitTest, Simple) {
+ SetOnces(&simple_once, NULL);
+
+ EXPECT_EQ(INIT_NOT_STARTED, CurrentState());
+ InitOnce();
+ EXPECT_EQ(INIT_DONE, CurrentState());
+
+ // Calling again has no effect.
+ InitOnce();
+ EXPECT_EQ(INIT_DONE, CurrentState());
+}
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(recursive_once1);
+GOOGLE_PROTOBUF_DECLARE_ONCE(recursive_once2);
+
+TEST_F(OnceInitTest, Recursive) {
+ SetOnces(&recursive_once1, &recursive_once2);
+
+ EXPECT_EQ(INIT_NOT_STARTED, CurrentState());
+ InitRecursiveOnce();
+ EXPECT_EQ(INIT_DONE, CurrentState());
+}
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(multiple_threads_once);
+
+TEST_F(OnceInitTest, MultipleThreads) {
+ SetOnces(&multiple_threads_once, NULL);
+
+ scoped_ptr<TestThread> threads[4];
+ EXPECT_EQ(INIT_NOT_STARTED, CurrentState());
+ for (int i = 0; i < 4; i++) {
+ threads[i].reset(RunInitOnceInNewThread());
+ }
+ for (int i = 0; i < 4; i++) {
+ threads[i]->Join();
+ }
+ EXPECT_EQ(INIT_DONE, CurrentState());
+}
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(multiple_threads_blocked_once1);
+GOOGLE_PROTOBUF_DECLARE_ONCE(multiple_threads_blocked_once2);
+
+TEST_F(OnceInitTest, MultipleThreadsBlocked) {
+ SetOnces(&multiple_threads_blocked_once1, &multiple_threads_blocked_once2);
+
+ scoped_ptr<TestThread> threads[8];
+ EXPECT_EQ(INIT_NOT_STARTED, CurrentState());
+
+ BlockInit();
+ for (int i = 0; i < 4; i++) {
+ threads[i].reset(RunInitOnceInNewThread());
+ }
+ for (int i = 4; i < 8; i++) {
+ threads[i].reset(RunInitRecursiveOnceInNewThread());
+ }
+
+ WaitABit();
+
+ // We should now have one thread blocked inside Init(), four blocked waiting
+ // for Init() to complete, and three blocked waiting for InitRecursive() to
+ // complete.
+ EXPECT_EQ(INIT_STARTED, CurrentState());
+ UnblockInit();
+
+ for (int i = 0; i < 8; i++) {
+ threads[i]->Join();
+ }
+ EXPECT_EQ(INIT_DONE, CurrentState());
+}
+
+} // anonymous namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/platform_macros.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/platform_macros.h
new file mode 100644
index 0000000000..4ba4b348c7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/platform_macros.h
@@ -0,0 +1,125 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+#ifndef GOOGLE_PROTOBUF_PLATFORM_MACROS_H_
+#define GOOGLE_PROTOBUF_PLATFORM_MACROS_H_
+
+#define GOOGLE_PROTOBUF_PLATFORM_ERROR \
+#error "Host platform was not detected as supported by protobuf"
+
+// Processor architecture detection. For more info on what's defined, see:
+// http://msdn.microsoft.com/en-us/library/b0084kay.aspx
+// http://www.agner.org/optimize/calling_conventions.pdf
+// or with gcc, run: "echo | gcc -E -dM -"
+#if defined(_M_X64) || defined(__x86_64__)
+#define GOOGLE_PROTOBUF_ARCH_X64 1
+#define GOOGLE_PROTOBUF_ARCH_64_BIT 1
+#elif defined(_M_IX86) || defined(__i386__)
+#define GOOGLE_PROTOBUF_ARCH_IA32 1
+#define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+#elif defined(__QNX__)
+#define GOOGLE_PROTOBUF_ARCH_ARM_QNX 1
+#define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+#elif defined(__ARMEL__)
+#define GOOGLE_PROTOBUF_ARCH_ARM 1
+#define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+#elif defined(__aarch64__)
+#define GOOGLE_PROTOBUF_ARCH_AARCH64 1
+#define GOOGLE_PROTOBUF_ARCH_64_BIT 1
+#elif defined(__MIPSEL__)
+#if defined(__LP64__)
+#define GOOGLE_PROTOBUF_ARCH_MIPS64 1
+#define GOOGLE_PROTOBUF_ARCH_64_BIT 1
+#else
+#define GOOGLE_PROTOBUF_ARCH_MIPS 1
+#define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+#endif
+#elif defined(__pnacl__)
+#define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+#elif defined(sparc)
+#define GOOGLE_PROTOBUF_ARCH_SPARC 1
+#if defined(__sparc_v9__) || defined(__sparcv9) || defined(__arch64__)
+#define GOOGLE_PROTOBUF_ARCH_64_BIT 1
+#else
+#define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+#endif
+#elif defined(_POWER) || defined(__powerpc64__) || defined(__PPC64__)
+#define GOOGLE_PROTOBUF_ARCH_POWER 1
+#define GOOGLE_PROTOBUF_ARCH_64_BIT 1
+#elif defined(__PPC__)
+#define GOOGLE_PROTOBUF_ARCH_PPC 1
+#define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+#elif defined(__GNUC__)
+# if (((__GNUC__ == 4) && (__GNUC_MINOR__ >= 7)) || (__GNUC__ > 4))
+// We fallback to the generic Clang/GCC >= 4.7 implementation in atomicops.h
+# elif defined(__clang__)
+# if !__has_extension(c_atomic)
+GOOGLE_PROTOBUF_PLATFORM_ERROR
+# endif
+// We fallback to the generic Clang/GCC >= 4.7 implementation in atomicops.h
+# endif
+# if __LP64__
+# define GOOGLE_PROTOBUF_ARCH_64_BIT 1
+# else
+# define GOOGLE_PROTOBUF_ARCH_32_BIT 1
+# endif
+#else
+GOOGLE_PROTOBUF_PLATFORM_ERROR
+#endif
+
+#if defined(__APPLE__)
+#define GOOGLE_PROTOBUF_OS_APPLE
+#include <TargetConditionals.h>
+#if TARGET_OS_IPHONE
+#define GOOGLE_PROTOBUF_OS_IPHONE
+#endif
+#elif defined(__EMSCRIPTEN__)
+#define GOOGLE_PROTOBUF_OS_EMSCRIPTEN
+#elif defined(__native_client__)
+#define GOOGLE_PROTOBUF_OS_NACL
+#elif defined(sun)
+#define GOOGLE_PROTOBUF_OS_SOLARIS
+#elif defined(_AIX)
+#define GOOGLE_PROTOBUF_OS_AIX
+#elif defined(__ANDROID__)
+#define GOOGLE_PROTOBUF_OS_ANDROID
+#endif
+
+#undef GOOGLE_PROTOBUF_PLATFORM_ERROR
+
+#if defined(GOOGLE_PROTOBUF_OS_ANDROID) || defined(GOOGLE_PROTOBUF_OS_IPHONE)
+// Android ndk does not support the __thread keyword very well yet. Here
+// we use pthread_key_create()/pthread_getspecific()/... methods for
+// TLS support on android.
+// iOS also does not support the __thread keyword.
+#define GOOGLE_PROTOBUF_NO_THREADLOCAL
+#endif
+
+#endif // GOOGLE_PROTOBUF_PLATFORM_MACROS_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/port.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/port.h
new file mode 100644
index 0000000000..d7f93b4cbd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/port.h
@@ -0,0 +1,393 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_STUBS_PORT_H_
+#define GOOGLE_PROTOBUF_STUBS_PORT_H_
+
+#include <assert.h>
+#include <stdlib.h>
+#include <cstddef>
+#include <string>
+#include <string.h>
+#if defined(__osf__)
+// Tru64 lacks stdint.h, but has inttypes.h which defines a superset of
+// what stdint.h would define.
+#include <inttypes.h>
+#elif !defined(_MSC_VER)
+#include <stdint.h>
+#endif
+
+#undef PROTOBUF_LITTLE_ENDIAN
+#ifdef _WIN32
+ // Assuming windows is always little-endian.
+ // TODO(xiaofeng): The PROTOBUF_LITTLE_ENDIAN is not only used for
+ // optimization but also for correctness. We should define an
+ // different macro to test the big-endian code path in coded_stream.
+ #if !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
+ #define PROTOBUF_LITTLE_ENDIAN 1
+ #endif
+ #if _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
+#else
+ #include <sys/param.h> // __BYTE_ORDER
+ #if ((defined(__LITTLE_ENDIAN__) && !defined(__BIG_ENDIAN__)) || \
+ (defined(__BYTE_ORDER) && __BYTE_ORDER == __LITTLE_ENDIAN)) && \
+ !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
+ #define PROTOBUF_LITTLE_ENDIAN 1
+ #endif
+#endif
+#if defined(_MSC_VER) && defined(PROTOBUF_USE_DLLS)
+ #ifdef LIBPROTOBUF_EXPORTS
+ #define LIBPROTOBUF_EXPORT __declspec(dllexport)
+ #else
+ #define LIBPROTOBUF_EXPORT __declspec(dllimport)
+ #endif
+ #ifdef LIBPROTOC_EXPORTS
+ #define LIBPROTOC_EXPORT __declspec(dllexport)
+ #else
+ #define LIBPROTOC_EXPORT __declspec(dllimport)
+ #endif
+#else
+ #define LIBPROTOBUF_EXPORT
+ #define LIBPROTOC_EXPORT
+#endif
+
+// These #includes are for the byte swap functions declared later on.
+#ifdef _MSC_VER
+#include <stdlib.h> // NOLINT(build/include)
+#elif defined(__APPLE__)
+#include <libkern/OSByteOrder.h>
+#elif defined(__GLIBC__) || defined(__CYGWIN__)
+#include <byteswap.h> // IWYU pragma: export
+#endif
+
+// ===================================================================
+// from google3/base/port.h
+namespace google {
+namespace protobuf {
+
+typedef unsigned int uint;
+
+#ifdef _MSC_VER
+typedef signed __int8 int8;
+typedef __int16 int16;
+typedef __int32 int32;
+typedef __int64 int64;
+
+typedef unsigned __int8 uint8;
+typedef unsigned __int16 uint16;
+typedef unsigned __int32 uint32;
+typedef unsigned __int64 uint64;
+#else
+typedef int8_t int8;
+typedef int16_t int16;
+typedef int32_t int32;
+typedef int64_t int64;
+
+typedef uint8_t uint8;
+typedef uint16_t uint16;
+typedef uint32_t uint32;
+typedef uint64_t uint64;
+#endif
+
+// long long macros to be used because gcc and vc++ use different suffixes,
+// and different size specifiers in format strings
+#undef GOOGLE_LONGLONG
+#undef GOOGLE_ULONGLONG
+#undef GOOGLE_LL_FORMAT
+
+#ifdef _MSC_VER
+#define GOOGLE_LONGLONG(x) x##I64
+#define GOOGLE_ULONGLONG(x) x##UI64
+#define GOOGLE_LL_FORMAT "I64" // As in printf("%I64d", ...)
+#else
+// By long long, we actually mean int64.
+#define GOOGLE_LONGLONG(x) x##LL
+#define GOOGLE_ULONGLONG(x) x##ULL
+// Used to format real long long integers.
+#define GOOGLE_LL_FORMAT "ll" // As in "%lld". Note that "q" is poor form also.
+#endif
+
+static const int32 kint32max = 0x7FFFFFFF;
+static const int32 kint32min = -kint32max - 1;
+static const int64 kint64max = GOOGLE_LONGLONG(0x7FFFFFFFFFFFFFFF);
+static const int64 kint64min = -kint64max - 1;
+static const uint32 kuint32max = 0xFFFFFFFFu;
+static const uint64 kuint64max = GOOGLE_ULONGLONG(0xFFFFFFFFFFFFFFFF);
+
+// -------------------------------------------------------------------
+// Annotations: Some parts of the code have been annotated in ways that might
+// be useful to some compilers or tools, but are not supported universally.
+// You can #define these annotations yourself if the default implementation
+// is not right for you.
+
+#ifndef GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+#if defined(__GNUC__) && (__GNUC__ > 3 ||(__GNUC__ == 3 && __GNUC_MINOR__ >= 1))
+// For functions we want to force inline.
+// Introduced in gcc 3.1.
+#define GOOGLE_ATTRIBUTE_ALWAYS_INLINE __attribute__ ((always_inline))
+#else
+// Other compilers will have to figure it out for themselves.
+#define GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+#endif
+#endif
+
+#ifndef GOOGLE_ATTRIBUTE_NOINLINE
+#if defined(__GNUC__) && (__GNUC__ > 3 ||(__GNUC__ == 3 && __GNUC_MINOR__ >= 1))
+// For functions we want to force not inline.
+// Introduced in gcc 3.1.
+#define GOOGLE_ATTRIBUTE_NOINLINE __attribute__ ((noinline))
+#elif defined(_MSC_VER) && (_MSC_VER >= 1400)
+// Seems to have been around since at least Visual Studio 2005
+#define GOOGLE_ATTRIBUTE_NOINLINE __declspec(noinline)
+#else
+// Other compilers will have to figure it out for themselves.
+#define GOOGLE_ATTRIBUTE_NOINLINE
+#endif
+#endif
+
+#ifndef GOOGLE_ATTRIBUTE_NORETURN
+#ifdef __GNUC__
+// Tell the compiler that a given function never returns.
+#define GOOGLE_ATTRIBUTE_NORETURN __attribute__((noreturn))
+#else
+#define GOOGLE_ATTRIBUTE_NORETURN
+#endif
+#endif
+
+#ifndef GOOGLE_ATTRIBUTE_DEPRECATED
+#ifdef __GNUC__
+// If the method/variable/type is used anywhere, produce a warning.
+#define GOOGLE_ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define GOOGLE_ATTRIBUTE_DEPRECATED
+#endif
+#endif
+
+#ifndef GOOGLE_PREDICT_TRUE
+#ifdef __GNUC__
+// Provided at least since GCC 3.0.
+#define GOOGLE_PREDICT_TRUE(x) (__builtin_expect(!!(x), 1))
+#else
+#define GOOGLE_PREDICT_TRUE(x) (x)
+#endif
+#endif
+
+#ifndef GOOGLE_PREDICT_FALSE
+#ifdef __GNUC__
+// Provided at least since GCC 3.0.
+#define GOOGLE_PREDICT_FALSE(x) (__builtin_expect(x, 0))
+#else
+#define GOOGLE_PREDICT_FALSE(x) (x)
+#endif
+#endif
+
+// Delimits a block of code which may write to memory which is simultaneously
+// written by other threads, but which has been determined to be thread-safe
+// (e.g. because it is an idempotent write).
+#ifndef GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN
+#define GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN()
+#endif
+#ifndef GOOGLE_SAFE_CONCURRENT_WRITES_END
+#define GOOGLE_SAFE_CONCURRENT_WRITES_END()
+#endif
+
+#if defined(__clang__) && defined(__has_cpp_attribute) \
+ && !defined(GOOGLE_PROTOBUF_OS_APPLE)
+# if defined(GOOGLE_PROTOBUF_OS_NACL) || defined(EMSCRIPTEN) || \
+ __has_cpp_attribute(clang::fallthrough)
+# define GOOGLE_FALLTHROUGH_INTENDED [[clang::fallthrough]]
+# endif
+#endif
+
+#ifndef GOOGLE_FALLTHROUGH_INTENDED
+# define GOOGLE_FALLTHROUGH_INTENDED
+#endif
+
+#define GOOGLE_GUARDED_BY(x)
+#define GOOGLE_ATTRIBUTE_COLD
+
+// x86 and x86-64 can perform unaligned loads/stores directly.
+#if defined(_M_X64) || defined(__x86_64__) || \
+ defined(_M_IX86) || defined(__i386__)
+
+#define GOOGLE_UNALIGNED_LOAD16(_p) (*reinterpret_cast<const uint16 *>(_p))
+#define GOOGLE_UNALIGNED_LOAD32(_p) (*reinterpret_cast<const uint32 *>(_p))
+#define GOOGLE_UNALIGNED_LOAD64(_p) (*reinterpret_cast<const uint64 *>(_p))
+
+#define GOOGLE_UNALIGNED_STORE16(_p, _val) (*reinterpret_cast<uint16 *>(_p) = (_val))
+#define GOOGLE_UNALIGNED_STORE32(_p, _val) (*reinterpret_cast<uint32 *>(_p) = (_val))
+#define GOOGLE_UNALIGNED_STORE64(_p, _val) (*reinterpret_cast<uint64 *>(_p) = (_val))
+
+#else
+inline uint16 GOOGLE_UNALIGNED_LOAD16(const void *p) {
+ uint16 t;
+ memcpy(&t, p, sizeof t);
+ return t;
+}
+
+inline uint32 GOOGLE_UNALIGNED_LOAD32(const void *p) {
+ uint32 t;
+ memcpy(&t, p, sizeof t);
+ return t;
+}
+
+inline uint64 GOOGLE_UNALIGNED_LOAD64(const void *p) {
+ uint64 t;
+ memcpy(&t, p, sizeof t);
+ return t;
+}
+
+inline void GOOGLE_UNALIGNED_STORE16(void *p, uint16 v) {
+ memcpy(p, &v, sizeof v);
+}
+
+inline void GOOGLE_UNALIGNED_STORE32(void *p, uint32 v) {
+ memcpy(p, &v, sizeof v);
+}
+
+inline void GOOGLE_UNALIGNED_STORE64(void *p, uint64 v) {
+ memcpy(p, &v, sizeof v);
+}
+#endif
+
+#if defined(_MSC_VER)
+#define GOOGLE_THREAD_LOCAL __declspec(thread)
+#else
+#define GOOGLE_THREAD_LOCAL __thread
+#endif
+
+// The following guarantees declaration of the byte swap functions.
+#ifdef _MSC_VER
+#define bswap_16(x) _byteswap_ushort(x)
+#define bswap_32(x) _byteswap_ulong(x)
+#define bswap_64(x) _byteswap_uint64(x)
+
+#elif defined(__APPLE__)
+// Mac OS X / Darwin features
+#define bswap_16(x) OSSwapInt16(x)
+#define bswap_32(x) OSSwapInt32(x)
+#define bswap_64(x) OSSwapInt64(x)
+
+#elif !defined(__GLIBC__) && !defined(__CYGWIN__)
+
+static inline uint16 bswap_16(uint16 x) {
+ return static_cast<uint16>(((x & 0xFF) << 8) | ((x & 0xFF00) >> 8));
+}
+#define bswap_16(x) bswap_16(x)
+static inline uint32 bswap_32(uint32 x) {
+ return (((x & 0xFF) << 24) |
+ ((x & 0xFF00) << 8) |
+ ((x & 0xFF0000) >> 8) |
+ ((x & 0xFF000000) >> 24));
+}
+#define bswap_32(x) bswap_32(x)
+static inline uint64 bswap_64(uint64 x) {
+ return (((x & GOOGLE_ULONGLONG(0xFF)) << 56) |
+ ((x & GOOGLE_ULONGLONG(0xFF00)) << 40) |
+ ((x & GOOGLE_ULONGLONG(0xFF0000)) << 24) |
+ ((x & GOOGLE_ULONGLONG(0xFF000000)) << 8) |
+ ((x & GOOGLE_ULONGLONG(0xFF00000000)) >> 8) |
+ ((x & GOOGLE_ULONGLONG(0xFF0000000000)) >> 24) |
+ ((x & GOOGLE_ULONGLONG(0xFF000000000000)) >> 40) |
+ ((x & GOOGLE_ULONGLONG(0xFF00000000000000)) >> 56));
+}
+#define bswap_64(x) bswap_64(x)
+
+#endif
+
+// ===================================================================
+// from google3/util/endian/endian.h
+LIBPROTOBUF_EXPORT uint32 ghtonl(uint32 x);
+
+class BigEndian {
+ public:
+#ifdef PROTOBUF_LITTLE_ENDIAN
+
+ static uint16 FromHost16(uint16 x) { return bswap_16(x); }
+ static uint16 ToHost16(uint16 x) { return bswap_16(x); }
+
+ static uint32 FromHost32(uint32 x) { return bswap_32(x); }
+ static uint32 ToHost32(uint32 x) { return bswap_32(x); }
+
+ static uint64 FromHost64(uint64 x) { return bswap_64(x); }
+ static uint64 ToHost64(uint64 x) { return bswap_64(x); }
+
+ static bool IsLittleEndian() { return true; }
+
+#else
+
+ static uint16 FromHost16(uint16 x) { return x; }
+ static uint16 ToHost16(uint16 x) { return x; }
+
+ static uint32 FromHost32(uint32 x) { return x; }
+ static uint32 ToHost32(uint32 x) { return x; }
+
+ static uint64 FromHost64(uint64 x) { return x; }
+ static uint64 ToHost64(uint64 x) { return x; }
+
+ static bool IsLittleEndian() { return false; }
+
+#endif /* ENDIAN */
+
+ // Functions to do unaligned loads and stores in big-endian order.
+ static uint16 Load16(const void *p) {
+ return ToHost16(GOOGLE_UNALIGNED_LOAD16(p));
+ }
+
+ static void Store16(void *p, uint16 v) {
+ GOOGLE_UNALIGNED_STORE16(p, FromHost16(v));
+ }
+
+ static uint32 Load32(const void *p) {
+ return ToHost32(GOOGLE_UNALIGNED_LOAD32(p));
+ }
+
+ static void Store32(void *p, uint32 v) {
+ GOOGLE_UNALIGNED_STORE32(p, FromHost32(v));
+ }
+
+ static uint64 Load64(const void *p) {
+ return ToHost64(GOOGLE_UNALIGNED_LOAD64(p));
+ }
+
+ static void Store64(void *p, uint64 v) {
+ GOOGLE_UNALIGNED_STORE64(p, FromHost64(v));
+ }
+};
+
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_PORT_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/scoped_ptr.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/scoped_ptr.h
new file mode 100644
index 0000000000..4423c118c4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/scoped_ptr.h
@@ -0,0 +1,236 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_STUBS_SCOPED_PTR_H_
+#define GOOGLE_PROTOBUF_STUBS_SCOPED_PTR_H_
+
+#include <google/protobuf/stubs/port.h>
+
+namespace google {
+namespace protobuf {
+
+// ===================================================================
+// from google3/base/scoped_ptr.h
+
+namespace internal {
+
+// This is an implementation designed to match the anticipated future TR2
+// implementation of the scoped_ptr class, and its closely-related brethren,
+// scoped_array, scoped_ptr_malloc, and make_scoped_ptr.
+
+template <class C> class scoped_ptr;
+template <class C> class scoped_array;
+
+// A scoped_ptr<T> is like a T*, except that the destructor of scoped_ptr<T>
+// automatically deletes the pointer it holds (if any).
+// That is, scoped_ptr<T> owns the T object that it points to.
+// Like a T*, a scoped_ptr<T> may hold either NULL or a pointer to a T object.
+//
+// The size of a scoped_ptr is small:
+// sizeof(scoped_ptr<C>) == sizeof(C*)
+template <class C>
+class scoped_ptr {
+ public:
+
+ // The element type
+ typedef C element_type;
+
+ // Constructor. Defaults to initializing with NULL.
+ // There is no way to create an uninitialized scoped_ptr.
+ // The input parameter must be allocated with new.
+ explicit scoped_ptr(C* p = NULL) : ptr_(p) { }
+
+ // Destructor. If there is a C object, delete it.
+ // We don't need to test ptr_ == NULL because C++ does that for us.
+ ~scoped_ptr() {
+ enum { type_must_be_complete = sizeof(C) };
+ delete ptr_;
+ }
+
+ // Reset. Deletes the current owned object, if any.
+ // Then takes ownership of a new object, if given.
+ // this->reset(this->get()) works.
+ void reset(C* p = NULL) {
+ if (p != ptr_) {
+ enum { type_must_be_complete = sizeof(C) };
+ delete ptr_;
+ ptr_ = p;
+ }
+ }
+
+ // Accessors to get the owned object.
+ // operator* and operator-> will assert() if there is no current object.
+ C& operator*() const {
+ assert(ptr_ != NULL);
+ return *ptr_;
+ }
+ C* operator->() const {
+ assert(ptr_ != NULL);
+ return ptr_;
+ }
+ C* get() const { return ptr_; }
+
+ // Comparison operators.
+ // These return whether two scoped_ptr refer to the same object, not just to
+ // two different but equal objects.
+ bool operator==(C* p) const { return ptr_ == p; }
+ bool operator!=(C* p) const { return ptr_ != p; }
+
+ // Swap two scoped pointers.
+ void swap(scoped_ptr& p2) {
+ C* tmp = ptr_;
+ ptr_ = p2.ptr_;
+ p2.ptr_ = tmp;
+ }
+
+ // Release a pointer.
+ // The return value is the current pointer held by this object.
+ // If this object holds a NULL pointer, the return value is NULL.
+ // After this operation, this object will hold a NULL pointer,
+ // and will not own the object any more.
+ C* release() {
+ C* retVal = ptr_;
+ ptr_ = NULL;
+ return retVal;
+ }
+
+ private:
+ C* ptr_;
+
+ // Forbid comparison of scoped_ptr types. If C2 != C, it totally doesn't
+ // make sense, and if C2 == C, it still doesn't make sense because you should
+ // never have the same object owned by two different scoped_ptrs.
+ template <class C2> bool operator==(scoped_ptr<C2> const& p2) const;
+ template <class C2> bool operator!=(scoped_ptr<C2> const& p2) const;
+
+ // Disallow evil constructors
+ scoped_ptr(const scoped_ptr&);
+ void operator=(const scoped_ptr&);
+};
+
+// scoped_array<C> is like scoped_ptr<C>, except that the caller must allocate
+// with new [] and the destructor deletes objects with delete [].
+//
+// As with scoped_ptr<C>, a scoped_array<C> either points to an object
+// or is NULL. A scoped_array<C> owns the object that it points to.
+//
+// Size: sizeof(scoped_array<C>) == sizeof(C*)
+template <class C>
+class scoped_array {
+ public:
+
+ // The element type
+ typedef C element_type;
+
+ // Constructor. Defaults to initializing with NULL.
+ // There is no way to create an uninitialized scoped_array.
+ // The input parameter must be allocated with new [].
+ explicit scoped_array(C* p = NULL) : array_(p) { }
+
+ // Destructor. If there is a C object, delete it.
+ // We don't need to test ptr_ == NULL because C++ does that for us.
+ ~scoped_array() {
+ enum { type_must_be_complete = sizeof(C) };
+ delete[] array_;
+ }
+
+ // Reset. Deletes the current owned object, if any.
+ // Then takes ownership of a new object, if given.
+ // this->reset(this->get()) works.
+ void reset(C* p = NULL) {
+ if (p != array_) {
+ enum { type_must_be_complete = sizeof(C) };
+ delete[] array_;
+ array_ = p;
+ }
+ }
+
+ // Get one element of the current object.
+ // Will assert() if there is no current object, or index i is negative.
+ C& operator[](std::ptrdiff_t i) const {
+ assert(i >= 0);
+ assert(array_ != NULL);
+ return array_[i];
+ }
+
+ // Get a pointer to the zeroth element of the current object.
+ // If there is no current object, return NULL.
+ C* get() const {
+ return array_;
+ }
+
+ // Comparison operators.
+ // These return whether two scoped_array refer to the same object, not just to
+ // two different but equal objects.
+ bool operator==(C* p) const { return array_ == p; }
+ bool operator!=(C* p) const { return array_ != p; }
+
+ // Swap two scoped arrays.
+ void swap(scoped_array& p2) {
+ C* tmp = array_;
+ array_ = p2.array_;
+ p2.array_ = tmp;
+ }
+
+ // Release an array.
+ // The return value is the current pointer held by this object.
+ // If this object holds a NULL pointer, the return value is NULL.
+ // After this operation, this object will hold a NULL pointer,
+ // and will not own the object any more.
+ C* release() {
+ C* retVal = array_;
+ array_ = NULL;
+ return retVal;
+ }
+
+ private:
+ C* array_;
+
+ // Forbid comparison of different scoped_array types.
+ template <class C2> bool operator==(scoped_array<C2> const& p2) const;
+ template <class C2> bool operator!=(scoped_array<C2> const& p2) const;
+
+ // Disallow evil constructors
+ scoped_array(const scoped_array&);
+ void operator=(const scoped_array&);
+};
+
+} // namespace internal
+
+// We made these internal so that they would show up as such in the docs,
+// but we don't want to stick "internal::" in front of them everywhere.
+using internal::scoped_ptr;
+using internal::scoped_array;
+
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_SCOPED_PTR_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/shared_ptr.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/shared_ptr.h
new file mode 100644
index 0000000000..d250bf4d33
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/shared_ptr.h
@@ -0,0 +1,470 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+
+// from google3/util/gtl/shared_ptr.h
+
+#ifndef GOOGLE_PROTOBUF_STUBS_SHARED_PTR_H__
+#define GOOGLE_PROTOBUF_STUBS_SHARED_PTR_H__
+
+#include <google/protobuf/stubs/atomicops.h>
+
+#include <algorithm> // for swap
+#include <stddef.h>
+#include <memory>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Alias to std::shared_ptr for any C++11 platform,
+// and for any supported MSVC compiler.
+#if !defined(UTIL_GTL_USE_STD_SHARED_PTR) && \
+ (defined(COMPILER_MSVC) || defined(LANG_CXX11))
+#define UTIL_GTL_USE_STD_SHARED_PTR 1
+#endif
+
+#if defined(UTIL_GTL_USE_STD_SHARED_PTR) && UTIL_GTL_USE_STD_SHARED_PTR
+
+// These are transitional. They will be going away soon.
+// Please just #include <memory> and just type std::shared_ptr yourself, instead
+// of relying on this file.
+//
+// Migration doc: http://go/std-shared-ptr-lsc
+using std::enable_shared_from_this;
+using std::shared_ptr;
+using std::static_pointer_cast;
+using std::weak_ptr;
+
+#else // below, UTIL_GTL_USE_STD_SHARED_PTR not set or set to 0.
+
+// For everything else there is the google3 implementation.
+inline bool RefCountDec(volatile Atomic32 *ptr) {
+ return Barrier_AtomicIncrement(ptr, -1) != 0;
+}
+
+inline void RefCountInc(volatile Atomic32 *ptr) {
+ NoBarrier_AtomicIncrement(ptr, 1);
+}
+
+template <typename T> class shared_ptr;
+template <typename T> class weak_ptr;
+
+// This class is an internal implementation detail for shared_ptr. If two
+// shared_ptrs point to the same object, they also share a control block.
+// An "empty" shared_pointer refers to NULL and also has a NULL control block.
+// It contains all of the state that's needed for reference counting or any
+// other kind of resource management. In this implementation the control block
+// happens to consist of two atomic words, the reference count (the number
+// of shared_ptrs that share ownership of the object) and the weak count
+// (the number of weak_ptrs that observe the object, plus 1 if the
+// refcount is nonzero).
+//
+// The "plus 1" is to prevent a race condition in the shared_ptr and
+// weak_ptr destructors. We need to make sure the control block is
+// only deleted once, so we need to make sure that at most one
+// object sees the weak count decremented from 1 to 0.
+class SharedPtrControlBlock {
+ template <typename T> friend class shared_ptr;
+ template <typename T> friend class weak_ptr;
+ private:
+ SharedPtrControlBlock() : refcount_(1), weak_count_(1) { }
+ Atomic32 refcount_;
+ Atomic32 weak_count_;
+};
+
+// Forward declaration. The class is defined below.
+template <typename T> class enable_shared_from_this;
+
+template <typename T>
+class shared_ptr {
+ template <typename U> friend class weak_ptr;
+ public:
+ typedef T element_type;
+
+ shared_ptr() : ptr_(NULL), control_block_(NULL) {}
+
+ explicit shared_ptr(T* ptr)
+ : ptr_(ptr),
+ control_block_(ptr != NULL ? new SharedPtrControlBlock : NULL) {
+ // If p is non-null and T inherits from enable_shared_from_this, we
+ // set up the data that shared_from_this needs.
+ MaybeSetupWeakThis(ptr);
+ }
+
+ // Copy constructor: makes this object a copy of ptr, and increments
+ // the reference count.
+ template <typename U>
+ shared_ptr(const shared_ptr<U>& ptr)
+ : ptr_(NULL),
+ control_block_(NULL) {
+ Initialize(ptr);
+ }
+ // Need non-templated version to prevent the compiler-generated default
+ shared_ptr(const shared_ptr<T>& ptr)
+ : ptr_(NULL),
+ control_block_(NULL) {
+ Initialize(ptr);
+ }
+
+ // Assignment operator. Replaces the existing shared_ptr with ptr.
+ // Increment ptr's reference count and decrement the one being replaced.
+ template <typename U>
+ shared_ptr<T>& operator=(const shared_ptr<U>& ptr) {
+ if (ptr_ != ptr.ptr_) {
+ shared_ptr<T> me(ptr); // will hold our previous state to be destroyed.
+ swap(me);
+ }
+ return *this;
+ }
+
+ // Need non-templated version to prevent the compiler-generated default
+ shared_ptr<T>& operator=(const shared_ptr<T>& ptr) {
+ if (ptr_ != ptr.ptr_) {
+ shared_ptr<T> me(ptr); // will hold our previous state to be destroyed.
+ swap(me);
+ }
+ return *this;
+ }
+
+ // TODO(austern): Consider providing this constructor. The draft C++ standard
+ // (20.8.10.2.1) includes it. However, it says that this constructor throws
+ // a bad_weak_ptr exception when ptr is expired. Is it better to provide this
+ // constructor and make it do something else, like fail with a CHECK, or to
+ // leave this constructor out entirely?
+ //
+ // template <typename U>
+ // shared_ptr(const weak_ptr<U>& ptr);
+
+ ~shared_ptr() {
+ if (ptr_ != NULL) {
+ if (!RefCountDec(&control_block_->refcount_)) {
+ delete ptr_;
+
+ // weak_count_ is defined as the number of weak_ptrs that observe
+ // ptr_, plus 1 if refcount_ is nonzero.
+ if (!RefCountDec(&control_block_->weak_count_)) {
+ delete control_block_;
+ }
+ }
+ }
+ }
+
+ // Replaces underlying raw pointer with the one passed in. The reference
+ // count is set to one (or zero if the pointer is NULL) for the pointer
+ // being passed in and decremented for the one being replaced.
+ //
+ // If you have a compilation error with this code, make sure you aren't
+ // passing NULL, nullptr, or 0 to this function. Call reset without an
+ // argument to reset to a null ptr.
+ template <typename Y>
+ void reset(Y* p) {
+ if (p != ptr_) {
+ shared_ptr<T> tmp(p);
+ tmp.swap(*this);
+ }
+ }
+
+ void reset() {
+ reset(static_cast<T*>(NULL));
+ }
+
+ // Exchanges the contents of this with the contents of r. This function
+ // supports more efficient swapping since it eliminates the need for a
+ // temporary shared_ptr object.
+ void swap(shared_ptr<T>& r) {
+ using std::swap; // http://go/using-std-swap
+ swap(ptr_, r.ptr_);
+ swap(control_block_, r.control_block_);
+ }
+
+ // The following function is useful for gaining access to the underlying
+ // pointer when a shared_ptr remains in scope so the reference-count is
+ // known to be > 0 (e.g. for parameter passing).
+ T* get() const {
+ return ptr_;
+ }
+
+ T& operator*() const {
+ return *ptr_;
+ }
+
+ T* operator->() const {
+ return ptr_;
+ }
+
+ long use_count() const {
+ return control_block_ ? control_block_->refcount_ : 1;
+ }
+
+ bool unique() const {
+ return use_count() == 1;
+ }
+
+ private:
+ // If r is non-empty, initialize *this to share ownership with r,
+ // increasing the underlying reference count.
+ // If r is empty, *this remains empty.
+ // Requires: this is empty, namely this->ptr_ == NULL.
+ template <typename U>
+ void Initialize(const shared_ptr<U>& r) {
+ // This performs a static_cast on r.ptr_ to U*, which is a no-op since it
+ // is already a U*. So initialization here requires that r.ptr_ is
+ // implicitly convertible to T*.
+ InitializeWithStaticCast<U>(r);
+ }
+
+ // Initializes *this as described in Initialize, but additionally performs a
+ // static_cast from r.ptr_ (V*) to U*.
+ // NOTE(gfc): We'd need a more general form to support const_pointer_cast and
+ // dynamic_pointer_cast, but those operations are sufficiently discouraged
+ // that supporting static_pointer_cast is sufficient.
+ template <typename U, typename V>
+ void InitializeWithStaticCast(const shared_ptr<V>& r) {
+ if (r.control_block_ != NULL) {
+ RefCountInc(&r.control_block_->refcount_);
+
+ ptr_ = static_cast<U*>(r.ptr_);
+ control_block_ = r.control_block_;
+ }
+ }
+
+ // Helper function for the constructor that takes a raw pointer. If T
+ // doesn't inherit from enable_shared_from_this<T> then we have nothing to
+ // do, so this function is trivial and inline. The other version is declared
+ // out of line, after the class definition of enable_shared_from_this.
+ void MaybeSetupWeakThis(enable_shared_from_this<T>* ptr);
+ void MaybeSetupWeakThis(...) { }
+
+ T* ptr_;
+ SharedPtrControlBlock* control_block_;
+
+#ifndef SWIG
+ template <typename U>
+ friend class shared_ptr;
+
+ template <typename U, typename V>
+ friend shared_ptr<U> static_pointer_cast(const shared_ptr<V>& rhs);
+#endif
+};
+
+// Matches the interface of std::swap as an aid to generic programming.
+template <typename T> void swap(shared_ptr<T>& r, shared_ptr<T>& s) {
+ r.swap(s);
+}
+
+template <typename T, typename U>
+shared_ptr<T> static_pointer_cast(const shared_ptr<U>& rhs) {
+ shared_ptr<T> lhs;
+ lhs.template InitializeWithStaticCast<T>(rhs);
+ return lhs;
+}
+
+// See comments at the top of the file for a description of why this
+// class exists, and the draft C++ standard (as of July 2009 the
+// latest draft is N2914) for the detailed specification.
+template <typename T>
+class weak_ptr {
+ template <typename U> friend class weak_ptr;
+ public:
+ typedef T element_type;
+
+ // Create an empty (i.e. already expired) weak_ptr.
+ weak_ptr() : ptr_(NULL), control_block_(NULL) { }
+
+ // Create a weak_ptr that observes the same object that ptr points
+ // to. Note that there is no race condition here: we know that the
+ // control block can't disappear while we're looking at it because
+ // it is owned by at least one shared_ptr, ptr.
+ template <typename U> weak_ptr(const shared_ptr<U>& ptr) {
+ CopyFrom(ptr.ptr_, ptr.control_block_);
+ }
+
+ // Copy a weak_ptr. The object it points to might disappear, but we
+ // don't care: we're only working with the control block, and it can't
+ // disappear while we're looking at because it's owned by at least one
+ // weak_ptr, ptr.
+ template <typename U> weak_ptr(const weak_ptr<U>& ptr) {
+ CopyFrom(ptr.ptr_, ptr.control_block_);
+ }
+
+ // Need non-templated version to prevent default copy constructor
+ weak_ptr(const weak_ptr& ptr) {
+ CopyFrom(ptr.ptr_, ptr.control_block_);
+ }
+
+ // Destroy the weak_ptr. If no shared_ptr owns the control block, and if
+ // we are the last weak_ptr to own it, then it can be deleted. Note that
+ // weak_count_ is defined as the number of weak_ptrs sharing this control
+ // block, plus 1 if there are any shared_ptrs. We therefore know that it's
+ // safe to delete the control block when weak_count_ reaches 0, without
+ // having to perform any additional tests.
+ ~weak_ptr() {
+ if (control_block_ != NULL &&
+ !RefCountDec(&control_block_->weak_count_)) {
+ delete control_block_;
+ }
+ }
+
+ weak_ptr& operator=(const weak_ptr& ptr) {
+ if (&ptr != this) {
+ weak_ptr tmp(ptr);
+ tmp.swap(*this);
+ }
+ return *this;
+ }
+ template <typename U> weak_ptr& operator=(const weak_ptr<U>& ptr) {
+ weak_ptr tmp(ptr);
+ tmp.swap(*this);
+ return *this;
+ }
+ template <typename U> weak_ptr& operator=(const shared_ptr<U>& ptr) {
+ weak_ptr tmp(ptr);
+ tmp.swap(*this);
+ return *this;
+ }
+
+ void swap(weak_ptr& ptr) {
+ using std::swap; // http://go/using-std-swap
+ swap(ptr_, ptr.ptr_);
+ swap(control_block_, ptr.control_block_);
+ }
+
+ void reset() {
+ weak_ptr tmp;
+ tmp.swap(*this);
+ }
+
+ // Return the number of shared_ptrs that own the object we are observing.
+ // Note that this number can be 0 (if this pointer has expired).
+ long use_count() const {
+ return control_block_ != NULL ? control_block_->refcount_ : 0;
+ }
+
+ bool expired() const { return use_count() == 0; }
+
+ // Return a shared_ptr that owns the object we are observing. If we
+ // have expired, the shared_ptr will be empty. We have to be careful
+ // about concurrency, though, since some other thread might be
+ // destroying the last owning shared_ptr while we're in this
+ // function. We want to increment the refcount only if it's nonzero
+ // and get the new value, and we want that whole operation to be
+ // atomic.
+ shared_ptr<T> lock() const {
+ shared_ptr<T> result;
+ if (control_block_ != NULL) {
+ Atomic32 old_refcount;
+ do {
+ old_refcount = control_block_->refcount_;
+ if (old_refcount == 0)
+ break;
+ } while (old_refcount !=
+ NoBarrier_CompareAndSwap(
+ &control_block_->refcount_, old_refcount,
+ old_refcount + 1));
+ if (old_refcount > 0) {
+ result.ptr_ = ptr_;
+ result.control_block_ = control_block_;
+ }
+ }
+
+ return result;
+ }
+
+ private:
+ void CopyFrom(T* ptr, SharedPtrControlBlock* control_block) {
+ ptr_ = ptr;
+ control_block_ = control_block;
+ if (control_block_ != NULL)
+ RefCountInc(&control_block_->weak_count_);
+ }
+
+ private:
+ element_type* ptr_;
+ SharedPtrControlBlock* control_block_;
+};
+
+template <typename T> void swap(weak_ptr<T>& r, weak_ptr<T>& s) {
+ r.swap(s);
+}
+
+// See comments at the top of the file for a description of why this class
+// exists, and section 20.8.10.5 of the draft C++ standard (as of July 2009
+// the latest draft is N2914) for the detailed specification.
+template <typename T>
+class enable_shared_from_this {
+ friend class shared_ptr<T>;
+ public:
+ // Precondition: there must be a shared_ptr that owns *this and that was
+ // created, directly or indirectly, from a raw pointer of type T*. (The
+ // latter part of the condition is technical but not quite redundant; it
+ // rules out some complicated uses involving inheritance hierarchies.)
+ shared_ptr<T> shared_from_this() {
+ // Behavior is undefined if the precondition isn't satisfied; we choose
+ // to die with a CHECK failure.
+ CHECK(!weak_this_.expired()) << "No shared_ptr owns this object";
+ return weak_this_.lock();
+ }
+ shared_ptr<const T> shared_from_this() const {
+ CHECK(!weak_this_.expired()) << "No shared_ptr owns this object";
+ return weak_this_.lock();
+ }
+
+ protected:
+ enable_shared_from_this() { }
+ enable_shared_from_this(const enable_shared_from_this& other) { }
+ enable_shared_from_this& operator=(const enable_shared_from_this& other) {
+ return *this;
+ }
+ ~enable_shared_from_this() { }
+
+ private:
+ weak_ptr<T> weak_this_;
+};
+
+// This is a helper function called by shared_ptr's constructor from a raw
+// pointer. If T inherits from enable_shared_from_this<T>, it sets up
+// weak_this_ so that shared_from_this works correctly. If T does not inherit
+// from weak_this we get a different overload, defined inline, which does
+// nothing.
+template<typename T>
+void shared_ptr<T>::MaybeSetupWeakThis(enable_shared_from_this<T>* ptr) {
+ if (ptr) {
+ CHECK(ptr->weak_this_.expired()) << "Object already owned by a shared_ptr";
+ ptr->weak_this_ = *this;
+ }
+}
+
+#endif // UTIL_GTL_USE_STD_SHARED_PTR
+
+} // internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_SHARED_PTR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/singleton.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/singleton.h
new file mode 100644
index 0000000000..9301f549b1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/singleton.h
@@ -0,0 +1,68 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2014 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.
+#ifndef GOOGLE_PROTOBUF_STUBS_SINGLETON_H__
+#define GOOGLE_PROTOBUF_STUBS_SINGLETON_H__
+
+#include <google/protobuf/stubs/atomicops.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/once.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+template<typename T>
+class Singleton {
+ public:
+ static T* get() {
+ GoogleOnceInit(&once_, &Singleton<T>::Init);
+ return instance_;
+ }
+ static void ShutDown() {
+ delete instance_;
+ instance_ = NULL;
+ }
+ private:
+ static void Init() {
+ instance_ = new T();
+ }
+ static ProtobufOnceType once_;
+ static T* instance_;
+};
+
+template<typename T>
+ProtobufOnceType Singleton<T>::once_;
+
+template<typename T>
+T* Singleton<T>::instance_ = NULL;
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_SINGLETON_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.cc
new file mode 100644
index 0000000000..dd1bd6141a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.cc
@@ -0,0 +1,134 @@
+// 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.
+#include <google/protobuf/stubs/status.h>
+
+#include <ostream>
+#include <stdio.h>
+#include <string>
+#include <utility>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace error {
+inline string CodeEnumToString(error::Code code) {
+ switch (code) {
+ case OK:
+ return "OK";
+ case CANCELLED:
+ return "CANCELLED";
+ case UNKNOWN:
+ return "UNKNOWN";
+ case INVALID_ARGUMENT:
+ return "INVALID_ARGUMENT";
+ case DEADLINE_EXCEEDED:
+ return "DEADLINE_EXCEEDED";
+ case NOT_FOUND:
+ return "NOT_FOUND";
+ case ALREADY_EXISTS:
+ return "ALREADY_EXISTS";
+ case PERMISSION_DENIED:
+ return "PERMISSION_DENIED";
+ case UNAUTHENTICATED:
+ return "UNAUTHENTICATED";
+ case RESOURCE_EXHAUSTED:
+ return "RESOURCE_EXHAUSTED";
+ case FAILED_PRECONDITION:
+ return "FAILED_PRECONDITION";
+ case ABORTED:
+ return "ABORTED";
+ case OUT_OF_RANGE:
+ return "OUT_OF_RANGE";
+ case UNIMPLEMENTED:
+ return "UNIMPLEMENTED";
+ case INTERNAL:
+ return "INTERNAL";
+ case UNAVAILABLE:
+ return "UNAVAILABLE";
+ case DATA_LOSS:
+ return "DATA_LOSS";
+ }
+
+ // No default clause, clang will abort if a code is missing from
+ // above switch.
+ return "UNKNOWN";
+}
+} // namespace error.
+
+const Status Status::OK = Status();
+const Status Status::CANCELLED = Status(error::CANCELLED, "");
+const Status Status::UNKNOWN = Status(error::UNKNOWN, "");
+
+Status::Status() : error_code_(error::OK) {
+}
+
+Status::Status(error::Code error_code, StringPiece error_message)
+ : error_code_(error_code) {
+ if (error_code != error::OK) {
+ error_message_ = error_message.ToString();
+ }
+}
+
+Status::Status(const Status& other)
+ : error_code_(other.error_code_), error_message_(other.error_message_) {
+}
+
+Status& Status::operator=(const Status& other) {
+ error_code_ = other.error_code_;
+ error_message_ = other.error_message_;
+ return *this;
+}
+
+bool Status::operator==(const Status& x) const {
+ return error_code_ == x.error_code_ &&
+ error_message_ == x.error_message_;
+}
+
+string Status::ToString() const {
+ if (error_code_ == error::OK) {
+ return "OK";
+ } else {
+ if (error_message_.empty()) {
+ return error::CodeEnumToString(error_code_);
+ } else {
+ return error::CodeEnumToString(error_code_) + ":" +
+ error_message_;
+ }
+ }
+}
+
+ostream& operator<<(ostream& os, const Status& x) {
+ os << x.ToString();
+ return os;
+}
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.h
new file mode 100644
index 0000000000..614ab9941a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status.h
@@ -0,0 +1,116 @@
+// 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.
+#ifndef GOOGLE_PROTOBUF_STUBS_STATUS_H_
+#define GOOGLE_PROTOBUF_STUBS_STATUS_H_
+
+#include <iosfwd>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace error {
+// These values must match error codes defined in google/rpc/code.proto.
+enum Code {
+ OK = 0,
+ CANCELLED = 1,
+ UNKNOWN = 2,
+ INVALID_ARGUMENT = 3,
+ DEADLINE_EXCEEDED = 4,
+ NOT_FOUND = 5,
+ ALREADY_EXISTS = 6,
+ PERMISSION_DENIED = 7,
+ UNAUTHENTICATED = 16,
+ RESOURCE_EXHAUSTED = 8,
+ FAILED_PRECONDITION = 9,
+ ABORTED = 10,
+ OUT_OF_RANGE = 11,
+ UNIMPLEMENTED = 12,
+ INTERNAL = 13,
+ UNAVAILABLE = 14,
+ DATA_LOSS = 15,
+};
+} // namespace error
+
+class LIBPROTOBUF_EXPORT Status {
+ public:
+ // Creates a "successful" status.
+ Status();
+
+ // Create a status in the canonical error space with the specified
+ // code, and error message. If "code == 0", error_message is
+ // ignored and a Status object identical to Status::OK is
+ // constructed.
+ Status(error::Code error_code, StringPiece error_message);
+ Status(const Status&);
+ Status& operator=(const Status& x);
+ ~Status() {}
+
+ // Some pre-defined Status objects
+ static const Status OK; // Identical to 0-arg constructor
+ static const Status CANCELLED;
+ static const Status UNKNOWN;
+
+ // Accessor
+ bool ok() const {
+ return error_code_ == error::OK;
+ }
+ int error_code() const {
+ return error_code_;
+ }
+ StringPiece error_message() const {
+ return error_message_;
+ }
+
+ bool operator==(const Status& x) const;
+ bool operator!=(const Status& x) const {
+ return !operator==(x);
+ }
+
+ // Return a combination of the error code name and message.
+ string ToString() const;
+
+ private:
+ error::Code error_code_;
+ string error_message_;
+};
+
+// Prints a human-readable representation of 'x' to 'os'.
+LIBPROTOBUF_EXPORT ostream& operator<<(ostream& os, const Status& x);
+
+#define EXPECT_OK(value) EXPECT_TRUE((value).ok())
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_STUBS_STATUS_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_macros.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_macros.h
new file mode 100644
index 0000000000..743e79a727
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_macros.h
@@ -0,0 +1,89 @@
+// 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.
+
+// From: util/task/contrib/status_macros/status_macros.h
+
+#ifndef GOOGLE_PROTOBUF_STUBS_STATUS_MACROS_H_
+#define GOOGLE_PROTOBUF_STUBS_STATUS_MACROS_H_
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/status.h>
+#include <google/protobuf/stubs/statusor.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+// Run a command that returns a util::Status. If the called code returns an
+// error status, return that status up out of this method too.
+//
+// Example:
+// RETURN_IF_ERROR(DoThings(4));
+#define RETURN_IF_ERROR(expr) \
+ do { \
+ /* Using _status below to avoid capture problems if expr is "status". */ \
+ const ::google::protobuf::util::Status _status = (expr); \
+ if (GOOGLE_PREDICT_FALSE(!_status.ok())) return _status; \
+ } while (0)
+
+// Internal helper for concatenating macro values.
+#define STATUS_MACROS_CONCAT_NAME_INNER(x, y) x##y
+#define STATUS_MACROS_CONCAT_NAME(x, y) STATUS_MACROS_CONCAT_NAME_INNER(x, y)
+
+template<typename T>
+Status DoAssignOrReturn(T& lhs, StatusOr<T> result) {
+ if (result.ok()) {
+ lhs = result.ValueOrDie();
+ }
+ return result.status();
+}
+
+#define ASSIGN_OR_RETURN_IMPL(status, lhs, rexpr) \
+ Status status = DoAssignOrReturn(lhs, (rexpr)); \
+ if (GOOGLE_PREDICT_FALSE(!status.ok())) return status;
+
+// Executes an expression that returns a util::StatusOr, extracting its value
+// into the variable defined by lhs (or returning on error).
+//
+// Example: Assigning to an existing value
+// ValueType value;
+// ASSIGN_OR_RETURN(value, MaybeGetValue(arg));
+//
+// WARNING: ASSIGN_OR_RETURN expands into multiple statements; it cannot be used
+// in a single statement (e.g. as the body of an if statement without {})!
+#define ASSIGN_OR_RETURN(lhs, rexpr) \
+ ASSIGN_OR_RETURN_IMPL( \
+ STATUS_MACROS_CONCAT_NAME(_status_or_value, __COUNTER__), lhs, rexpr);
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_STATUS_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_test.cc
new file mode 100644
index 0000000000..c70c33c474
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/status_test.cc
@@ -0,0 +1,131 @@
+// 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.
+#include <google/protobuf/stubs/status.h>
+
+#include <stdio.h>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+TEST(Status, Empty) {
+ util::Status status;
+ EXPECT_EQ(util::error::OK, util::Status::OK.error_code());
+ EXPECT_EQ("OK", util::Status::OK.ToString());
+}
+
+TEST(Status, GenericCodes) {
+ EXPECT_EQ(util::error::OK, util::Status::OK.error_code());
+ EXPECT_EQ(util::error::CANCELLED, util::Status::CANCELLED.error_code());
+ EXPECT_EQ(util::error::UNKNOWN, util::Status::UNKNOWN.error_code());
+}
+
+TEST(Status, ConstructorZero) {
+ util::Status status(util::error::OK, "msg");
+ EXPECT_TRUE(status.ok());
+ EXPECT_EQ("OK", status.ToString());
+}
+
+TEST(Status, CheckOK) {
+ util::Status status;
+ GOOGLE_CHECK_OK(status);
+ GOOGLE_CHECK_OK(status) << "Failed";
+ GOOGLE_DCHECK_OK(status) << "Failed";
+}
+
+TEST(Status, ErrorMessage) {
+ util::Status status(util::error::INVALID_ARGUMENT, "");
+ EXPECT_FALSE(status.ok());
+ EXPECT_EQ("", status.error_message().ToString());
+ EXPECT_EQ("INVALID_ARGUMENT", status.ToString());
+ status = util::Status(util::error::INVALID_ARGUMENT, "msg");
+ EXPECT_FALSE(status.ok());
+ EXPECT_EQ("msg", status.error_message().ToString());
+ EXPECT_EQ("INVALID_ARGUMENT:msg", status.ToString());
+ status = util::Status(util::error::OK, "msg");
+ EXPECT_TRUE(status.ok());
+ EXPECT_EQ("", status.error_message().ToString());
+ EXPECT_EQ("OK", status.ToString());
+}
+
+TEST(Status, Copy) {
+ util::Status a(util::error::UNKNOWN, "message");
+ util::Status b(a);
+ ASSERT_EQ(a.ToString(), b.ToString());
+}
+
+TEST(Status, Assign) {
+ util::Status a(util::error::UNKNOWN, "message");
+ util::Status b;
+ b = a;
+ ASSERT_EQ(a.ToString(), b.ToString());
+}
+
+TEST(Status, AssignEmpty) {
+ util::Status a(util::error::UNKNOWN, "message");
+ util::Status b;
+ a = b;
+ ASSERT_EQ(string("OK"), a.ToString());
+ ASSERT_TRUE(b.ok());
+ ASSERT_TRUE(a.ok());
+}
+
+TEST(Status, EqualsOK) {
+ ASSERT_EQ(util::Status::OK, util::Status());
+}
+
+TEST(Status, EqualsSame) {
+ const util::Status a = util::Status(util::error::CANCELLED, "message");
+ const util::Status b = util::Status(util::error::CANCELLED, "message");
+ ASSERT_EQ(a, b);
+}
+
+TEST(Status, EqualsCopy) {
+ const util::Status a = util::Status(util::error::CANCELLED, "message");
+ const util::Status b = a;
+ ASSERT_EQ(a, b);
+}
+
+TEST(Status, EqualsDifferentCode) {
+ const util::Status a = util::Status(util::error::CANCELLED, "message");
+ const util::Status b = util::Status(util::error::UNKNOWN, "message");
+ ASSERT_NE(a, b);
+}
+
+TEST(Status, EqualsDifferentMessage) {
+ const util::Status a = util::Status(util::error::CANCELLED, "message");
+ const util::Status b = util::Status(util::error::CANCELLED, "another");
+ ASSERT_NE(a, b);
+}
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.cc
new file mode 100644
index 0000000000..48d1402ae0
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.cc
@@ -0,0 +1,46 @@
+// 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.
+
+#include <google/protobuf/stubs/statusor.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace internal {
+
+void StatusOrHelper::Crash(const Status& status) {
+ GOOGLE_LOG(FATAL) << "Attempting to fetch value instead of handling error "
+ << status.ToString();
+}
+
+} // namespace internal
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.h
new file mode 100644
index 0000000000..29f869ad5e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor.h
@@ -0,0 +1,259 @@
+// 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.
+
+// StatusOr<T> is the union of a Status object and a T
+// object. StatusOr models the concept of an object that is either a
+// usable value, or an error Status explaining why such a value is
+// not present. To this end, StatusOr<T> does not allow its Status
+// value to be Status::OK. Further, StatusOr<T*> does not allow the
+// contained pointer to be NULL.
+//
+// The primary use-case for StatusOr<T> is as the return value of a
+// function which may fail.
+//
+// Example client usage for a StatusOr<T>, where T is not a pointer:
+//
+// StatusOr<float> result = DoBigCalculationThatCouldFail();
+// if (result.ok()) {
+// float answer = result.ValueOrDie();
+// printf("Big calculation yielded: %f", answer);
+// } else {
+// LOG(ERROR) << result.status();
+// }
+//
+// Example client usage for a StatusOr<T*>:
+//
+// StatusOr<Foo*> result = FooFactory::MakeNewFoo(arg);
+// if (result.ok()) {
+// std::unique_ptr<Foo> foo(result.ValueOrDie());
+// foo->DoSomethingCool();
+// } else {
+// LOG(ERROR) << result.status();
+// }
+//
+// Example client usage for a StatusOr<std::unique_ptr<T>>:
+//
+// StatusOr<std::unique_ptr<Foo>> result = FooFactory::MakeNewFoo(arg);
+// if (result.ok()) {
+// std::unique_ptr<Foo> foo = result.ConsumeValueOrDie();
+// foo->DoSomethingCool();
+// } else {
+// LOG(ERROR) << result.status();
+// }
+//
+// Example factory implementation returning StatusOr<T*>:
+//
+// StatusOr<Foo*> FooFactory::MakeNewFoo(int arg) {
+// if (arg <= 0) {
+// return ::util::Status(::util::error::INVALID_ARGUMENT,
+// "Arg must be positive");
+// } else {
+// return new Foo(arg);
+// }
+// }
+//
+
+#ifndef GOOGLE_PROTOBUF_STUBS_STATUSOR_H_
+#define GOOGLE_PROTOBUF_STUBS_STATUSOR_H_
+
+#include <new>
+#include <string>
+#include <utility>
+
+#include <google/protobuf/stubs/status.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+template<typename T>
+class StatusOr {
+ template<typename U> friend class StatusOr;
+
+ public:
+ // Construct a new StatusOr with Status::UNKNOWN status
+ StatusOr();
+
+ // Construct a new StatusOr with the given non-ok status. After calling
+ // this constructor, calls to ValueOrDie() will CHECK-fail.
+ //
+ // NOTE: Not explicit - we want to use StatusOr<T> as a return
+ // value, so it is convenient and sensible to be able to do 'return
+ // Status()' when the return type is StatusOr<T>.
+ //
+ // REQUIRES: status != Status::OK. This requirement is DCHECKed.
+ // In optimized builds, passing Status::OK here will have the effect
+ // of passing PosixErrorSpace::EINVAL as a fallback.
+ StatusOr(const Status& status); // NOLINT
+
+ // Construct a new StatusOr with the given value. If T is a plain pointer,
+ // value must not be NULL. After calling this constructor, calls to
+ // ValueOrDie() will succeed, and calls to status() will return OK.
+ //
+ // NOTE: Not explicit - we want to use StatusOr<T> as a return type
+ // so it is convenient and sensible to be able to do 'return T()'
+ // when when the return type is StatusOr<T>.
+ //
+ // REQUIRES: if T is a plain pointer, value != NULL. This requirement is
+ // DCHECKed. In optimized builds, passing a NULL pointer here will have
+ // the effect of passing PosixErrorSpace::EINVAL as a fallback.
+ StatusOr(const T& value); // NOLINT
+
+ // Copy constructor.
+ StatusOr(const StatusOr& other);
+
+ // Conversion copy constructor, T must be copy constructible from U
+ template<typename U>
+ StatusOr(const StatusOr<U>& other);
+
+ // Assignment operator.
+ StatusOr& operator=(const StatusOr& other);
+
+ // Conversion assignment operator, T must be assignable from U
+ template<typename U>
+ StatusOr& operator=(const StatusOr<U>& other);
+
+ // Returns a reference to our status. If this contains a T, then
+ // returns Status::OK.
+ const Status& status() const;
+
+ // Returns this->status().ok()
+ bool ok() const;
+
+ // Returns a reference to our current value, or CHECK-fails if !this->ok().
+ // If you need to initialize a T object from the stored value,
+ // ConsumeValueOrDie() may be more efficient.
+ const T& ValueOrDie() const;
+
+ private:
+ Status status_;
+ T value_;
+};
+
+////////////////////////////////////////////////////////////////////////////////
+// Implementation details for StatusOr<T>
+
+namespace internal {
+
+class LIBPROTOBUF_EXPORT StatusOrHelper {
+ public:
+ // Move type-agnostic error handling to the .cc.
+ static void Crash(const util::Status& status);
+
+ // Customized behavior for StatusOr<T> vs. StatusOr<T*>
+ template<typename T>
+ struct Specialize;
+};
+
+template<typename T>
+struct StatusOrHelper::Specialize {
+ // For non-pointer T, a reference can never be NULL.
+ static inline bool IsValueNull(const T& t) { return false; }
+};
+
+template<typename T>
+struct StatusOrHelper::Specialize<T*> {
+ static inline bool IsValueNull(const T* t) { return t == NULL; }
+};
+
+} // namespace internal
+
+template<typename T>
+inline StatusOr<T>::StatusOr()
+ : status_(util::Status::UNKNOWN) {
+}
+
+template<typename T>
+inline StatusOr<T>::StatusOr(const Status& status) {
+ if (status.ok()) {
+ status_ = Status(error::INTERNAL, "Status::OK is not a valid argument.");
+ } else {
+ status_ = status;
+ }
+}
+
+template<typename T>
+inline StatusOr<T>::StatusOr(const T& value) {
+ if (internal::StatusOrHelper::Specialize<T>::IsValueNull(value)) {
+ status_ = Status(error::INTERNAL, "NULL is not a vaild argument.");
+ } else {
+ status_ = Status::OK;
+ value_ = value;
+ }
+}
+
+template<typename T>
+inline StatusOr<T>::StatusOr(const StatusOr<T>& other)
+ : status_(other.status_), value_(other.value_) {
+}
+
+template<typename T>
+inline StatusOr<T>& StatusOr<T>::operator=(const StatusOr<T>& other) {
+ status_ = other.status_;
+ value_ = other.value_;
+ return *this;
+}
+
+template<typename T>
+template<typename U>
+inline StatusOr<T>::StatusOr(const StatusOr<U>& other)
+ : status_(other.status_), value_(other.status_.ok() ? other.value_ : T()) {
+}
+
+template<typename T>
+template<typename U>
+inline StatusOr<T>& StatusOr<T>::operator=(const StatusOr<U>& other) {
+ status_ = other.status_;
+ if (status_.ok()) value_ = other.value_;
+ return *this;
+}
+
+template<typename T>
+inline const Status& StatusOr<T>::status() const {
+ return status_;
+}
+
+template<typename T>
+inline bool StatusOr<T>::ok() const {
+ return status().ok();
+}
+
+template<typename T>
+inline const T& StatusOr<T>::ValueOrDie() const {
+ if (!status_.ok()) {
+ internal::StatusOrHelper::Crash(status_);
+ }
+ return value_;
+}
+} // namespace util
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_STATUSOR_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor_test.cc
new file mode 100644
index 0000000000..6e2a9e5545
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/statusor_test.cc
@@ -0,0 +1,274 @@
+// 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.
+
+#include <google/protobuf/stubs/statusor.h>
+
+#include <errno.h>
+#include <memory>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace {
+
+class Base1 {
+ public:
+ virtual ~Base1() {}
+ int pad;
+};
+
+class Base2 {
+ public:
+ virtual ~Base2() {}
+ int yetotherpad;
+};
+
+class Derived : public Base1, public Base2 {
+ public:
+ virtual ~Derived() {}
+ int evenmorepad;
+};
+
+class CopyNoAssign {
+ public:
+ explicit CopyNoAssign(int value) : foo(value) {}
+ CopyNoAssign(const CopyNoAssign& other) : foo(other.foo) {}
+ int foo;
+ private:
+ const CopyNoAssign& operator=(const CopyNoAssign&);
+};
+
+TEST(StatusOr, TestDefaultCtor) {
+ StatusOr<int> thing;
+ EXPECT_FALSE(thing.ok());
+ EXPECT_EQ(Status::UNKNOWN, thing.status());
+}
+
+TEST(StatusOr, TestStatusCtor) {
+ StatusOr<int> thing(Status::CANCELLED);
+ EXPECT_FALSE(thing.ok());
+ EXPECT_EQ(Status::CANCELLED, thing.status());
+}
+
+TEST(StatusOr, TestValueCtor) {
+ const int kI = 4;
+ StatusOr<int> thing(kI);
+ EXPECT_TRUE(thing.ok());
+ EXPECT_EQ(kI, thing.ValueOrDie());
+}
+
+TEST(StatusOr, TestCopyCtorStatusOk) {
+ const int kI = 4;
+ StatusOr<int> original(kI);
+ StatusOr<int> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+ EXPECT_EQ(original.ValueOrDie(), copy.ValueOrDie());
+}
+
+TEST(StatusOr, TestCopyCtorStatusNotOk) {
+ StatusOr<int> original(Status::CANCELLED);
+ StatusOr<int> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+}
+
+TEST(StatusOr, TestCopyCtorStatusOKConverting) {
+ const int kI = 4;
+ StatusOr<int> original(kI);
+ StatusOr<double> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+ EXPECT_EQ(original.ValueOrDie(), copy.ValueOrDie());
+}
+
+TEST(StatusOr, TestCopyCtorStatusNotOkConverting) {
+ StatusOr<int> original(Status::CANCELLED);
+ StatusOr<double> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+}
+
+TEST(StatusOr, TestAssignmentStatusOk) {
+ const int kI = 4;
+ StatusOr<int> source(kI);
+ StatusOr<int> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+ EXPECT_EQ(source.ValueOrDie(), target.ValueOrDie());
+}
+
+TEST(StatusOr, TestAssignmentStatusNotOk) {
+ StatusOr<int> source(Status::CANCELLED);
+ StatusOr<int> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+}
+
+TEST(StatusOr, TestAssignmentStatusOKConverting) {
+ const int kI = 4;
+ StatusOr<int> source(kI);
+ StatusOr<double> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+ EXPECT_DOUBLE_EQ(source.ValueOrDie(), target.ValueOrDie());
+}
+
+TEST(StatusOr, TestAssignmentStatusNotOkConverting) {
+ StatusOr<int> source(Status::CANCELLED);
+ StatusOr<double> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+}
+
+TEST(StatusOr, TestStatus) {
+ StatusOr<int> good(4);
+ EXPECT_TRUE(good.ok());
+ StatusOr<int> bad(Status::CANCELLED);
+ EXPECT_FALSE(bad.ok());
+ EXPECT_EQ(Status::CANCELLED, bad.status());
+}
+
+TEST(StatusOr, TestValue) {
+ const int kI = 4;
+ StatusOr<int> thing(kI);
+ EXPECT_EQ(kI, thing.ValueOrDie());
+}
+
+TEST(StatusOr, TestValueConst) {
+ const int kI = 4;
+ const StatusOr<int> thing(kI);
+ EXPECT_EQ(kI, thing.ValueOrDie());
+}
+
+TEST(StatusOr, TestPointerDefaultCtor) {
+ StatusOr<int*> thing;
+ EXPECT_FALSE(thing.ok());
+ EXPECT_EQ(Status::UNKNOWN, thing.status());
+}
+
+TEST(StatusOr, TestPointerStatusCtor) {
+ StatusOr<int*> thing(Status::CANCELLED);
+ EXPECT_FALSE(thing.ok());
+ EXPECT_EQ(Status::CANCELLED, thing.status());
+}
+
+TEST(StatusOr, TestPointerValueCtor) {
+ const int kI = 4;
+ StatusOr<const int*> thing(&kI);
+ EXPECT_TRUE(thing.ok());
+ EXPECT_EQ(&kI, thing.ValueOrDie());
+}
+
+TEST(StatusOr, TestPointerCopyCtorStatusOk) {
+ const int kI = 0;
+ StatusOr<const int*> original(&kI);
+ StatusOr<const int*> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+ EXPECT_EQ(original.ValueOrDie(), copy.ValueOrDie());
+}
+
+TEST(StatusOr, TestPointerCopyCtorStatusNotOk) {
+ StatusOr<int*> original(Status::CANCELLED);
+ StatusOr<int*> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+}
+
+TEST(StatusOr, TestPointerCopyCtorStatusOKConverting) {
+ Derived derived;
+ StatusOr<Derived*> original(&derived);
+ StatusOr<Base2*> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+ EXPECT_EQ(static_cast<const Base2*>(original.ValueOrDie()),
+ copy.ValueOrDie());
+}
+
+TEST(StatusOr, TestPointerCopyCtorStatusNotOkConverting) {
+ StatusOr<Derived*> original(Status::CANCELLED);
+ StatusOr<Base2*> copy(original);
+ EXPECT_EQ(original.status(), copy.status());
+}
+
+TEST(StatusOr, TestPointerAssignmentStatusOk) {
+ const int kI = 0;
+ StatusOr<const int*> source(&kI);
+ StatusOr<const int*> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+ EXPECT_EQ(source.ValueOrDie(), target.ValueOrDie());
+}
+
+TEST(StatusOr, TestPointerAssignmentStatusNotOk) {
+ StatusOr<int*> source(Status::CANCELLED);
+ StatusOr<int*> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+}
+
+TEST(StatusOr, TestPointerAssignmentStatusOKConverting) {
+ Derived derived;
+ StatusOr<Derived*> source(&derived);
+ StatusOr<Base2*> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+ EXPECT_EQ(static_cast<const Base2*>(source.ValueOrDie()),
+ target.ValueOrDie());
+}
+
+TEST(StatusOr, TestPointerAssignmentStatusNotOkConverting) {
+ StatusOr<Derived*> source(Status::CANCELLED);
+ StatusOr<Base2*> target;
+ target = source;
+ EXPECT_EQ(source.status(), target.status());
+}
+
+TEST(StatusOr, TestPointerStatus) {
+ const int kI = 0;
+ StatusOr<const int*> good(&kI);
+ EXPECT_TRUE(good.ok());
+ StatusOr<const int*> bad(Status::CANCELLED);
+ EXPECT_EQ(Status::CANCELLED, bad.status());
+}
+
+TEST(StatusOr, TestPointerValue) {
+ const int kI = 0;
+ StatusOr<const int*> thing(&kI);
+ EXPECT_EQ(&kI, thing.ValueOrDie());
+}
+
+TEST(StatusOr, TestPointerValueConst) {
+ const int kI = 0;
+ const StatusOr<const int*> thing(&kI);
+ EXPECT_EQ(&kI, thing.ValueOrDie());
+}
+
+} // namespace
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stl_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stl_util.h
new file mode 100644
index 0000000000..9e4c82a4c3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stl_util.h
@@ -0,0 +1,121 @@
+// 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.
+
+// from google3/util/gtl/stl_util.h
+
+#ifndef GOOGLE_PROTOBUF_STUBS_STL_UTIL_H__
+#define GOOGLE_PROTOBUF_STUBS_STL_UTIL_H__
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+// STLDeleteContainerPointers()
+// For a range within a container of pointers, calls delete
+// (non-array version) on these pointers.
+// NOTE: for these three functions, we could just implement a DeleteObject
+// functor and then call for_each() on the range and functor, but this
+// requires us to pull in all of algorithm.h, which seems expensive.
+// For hash_[multi]set, it is important that this deletes behind the iterator
+// because the hash_set may call the hash function on the iterator when it is
+// advanced, which could result in the hash function trying to deference a
+// stale pointer.
+template <class ForwardIterator>
+void STLDeleteContainerPointers(ForwardIterator begin,
+ ForwardIterator end) {
+ while (begin != end) {
+ ForwardIterator temp = begin;
+ ++begin;
+ delete *temp;
+ }
+}
+
+// Inside Google, this function implements a horrible, disgusting hack in which
+// we reach into the string's private implementation and resize it without
+// initializing the new bytes. In some cases doing this can significantly
+// improve performance. However, since it's totally non-portable it has no
+// place in open source code. Feel free to fill this function in with your
+// own disgusting hack if you want the perf boost.
+inline void STLStringResizeUninitialized(string* s, size_t new_size) {
+ s->resize(new_size);
+}
+
+// Return a mutable char* pointing to a string's internal buffer,
+// which may not be null-terminated. Writing through this pointer will
+// modify the string.
+//
+// string_as_array(&str)[i] is valid for 0 <= i < str.size() until the
+// next call to a string method that invalidates iterators.
+//
+// As of 2006-04, there is no standard-blessed way of getting a
+// mutable reference to a string's internal buffer. However, issue 530
+// (http://www.open-std.org/JTC1/SC22/WG21/docs/lwg-active.html#530)
+// proposes this as the method. According to Matt Austern, this should
+// already work on all current implementations.
+inline char* string_as_array(string* str) {
+ // DO NOT USE const_cast<char*>(str->data())! See the unittest for why.
+ return str->empty() ? NULL : &*str->begin();
+}
+
+// STLDeleteElements() deletes all the elements in an STL container and clears
+// the container. This function is suitable for use with a vector, set,
+// hash_set, or any other STL container which defines sensible begin(), end(),
+// and clear() methods.
+//
+// If container is NULL, this function is a no-op.
+//
+// As an alternative to calling STLDeleteElements() directly, consider
+// ElementDeleter (defined below), which ensures that your container's elements
+// are deleted when the ElementDeleter goes out of scope.
+template <class T>
+void STLDeleteElements(T *container) {
+ if (!container) return;
+ STLDeleteContainerPointers(container->begin(), container->end());
+ container->clear();
+}
+
+// Given an STL container consisting of (key, value) pairs, STLDeleteValues
+// deletes all the "value" components and clears the container. Does nothing
+// in the case it's given a NULL pointer.
+
+template <class T>
+void STLDeleteValues(T *v) {
+ if (!v) return;
+ for (typename T::iterator i = v->begin(); i != v->end(); ++i) {
+ delete i->second;
+ }
+ v->clear();
+}
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_STL_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.cc
new file mode 100644
index 0000000000..989474b747
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.cc
@@ -0,0 +1,268 @@
+// 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.
+#include <google/protobuf/stubs/stringpiece.h>
+
+#include <string.h>
+#include <algorithm>
+#include <climits>
+#include <string>
+#include <ostream>
+
+namespace google {
+namespace protobuf {
+std::ostream& operator<<(std::ostream& o, StringPiece piece) {
+ o.write(piece.data(), piece.size());
+ return o;
+}
+
+// Out-of-line error path.
+void StringPiece::LogFatalSizeTooBig(size_t size, const char* details) {
+ GOOGLE_LOG(FATAL) << "size too big: " << size << " details: " << details;
+}
+
+StringPiece::StringPiece(StringPiece x, stringpiece_ssize_type pos)
+ : ptr_(x.ptr_ + pos), length_(x.length_ - pos) {
+ GOOGLE_DCHECK_LE(0, pos);
+ GOOGLE_DCHECK_LE(pos, x.length_);
+}
+
+StringPiece::StringPiece(StringPiece x,
+ stringpiece_ssize_type pos,
+ stringpiece_ssize_type len)
+ : ptr_(x.ptr_ + pos), length_(std::min(len, x.length_ - pos)) {
+ GOOGLE_DCHECK_LE(0, pos);
+ GOOGLE_DCHECK_LE(pos, x.length_);
+ GOOGLE_DCHECK_GE(len, 0);
+}
+
+void StringPiece::CopyToString(string* target) const {
+ target->assign(ptr_, length_);
+}
+
+void StringPiece::AppendToString(string* target) const {
+ target->append(ptr_, length_);
+}
+
+bool StringPiece::Consume(StringPiece x) {
+ if (starts_with(x)) {
+ ptr_ += x.length_;
+ length_ -= x.length_;
+ return true;
+ }
+ return false;
+}
+
+bool StringPiece::ConsumeFromEnd(StringPiece x) {
+ if (ends_with(x)) {
+ length_ -= x.length_;
+ return true;
+ }
+ return false;
+}
+
+stringpiece_ssize_type StringPiece::copy(char* buf,
+ size_type n,
+ size_type pos) const {
+ stringpiece_ssize_type ret = std::min(length_ - pos, n);
+ memcpy(buf, ptr_ + pos, ret);
+ return ret;
+}
+
+bool StringPiece::contains(StringPiece s) const {
+ return find(s, 0) != npos;
+}
+
+stringpiece_ssize_type StringPiece::find(StringPiece s, size_type pos) const {
+ if (length_ <= 0 || pos > static_cast<size_type>(length_)) {
+ if (length_ == 0 && pos == 0 && s.length_ == 0) return 0;
+ return npos;
+ }
+ const char *result = std::search(ptr_ + pos, ptr_ + length_,
+ s.ptr_, s.ptr_ + s.length_);
+ return result == ptr_ + length_ ? npos : result - ptr_;
+}
+
+stringpiece_ssize_type StringPiece::find(char c, size_type pos) const {
+ if (length_ <= 0 || pos >= static_cast<size_type>(length_)) {
+ return npos;
+ }
+ const char* result = static_cast<const char*>(
+ memchr(ptr_ + pos, c, length_ - pos));
+ return result != NULL ? result - ptr_ : npos;
+}
+
+stringpiece_ssize_type StringPiece::rfind(StringPiece s, size_type pos) const {
+ if (length_ < s.length_) return npos;
+ const size_t ulen = length_;
+ if (s.length_ == 0) return std::min(ulen, pos);
+
+ const char* last = ptr_ + std::min(ulen - s.length_, pos) + s.length_;
+ const char* result = std::find_end(ptr_, last, s.ptr_, s.ptr_ + s.length_);
+ return result != last ? result - ptr_ : npos;
+}
+
+// Search range is [0..pos] inclusive. If pos == npos, search everything.
+stringpiece_ssize_type StringPiece::rfind(char c, size_type pos) const {
+ // Note: memrchr() is not available on Windows.
+ if (length_ <= 0) return npos;
+ for (stringpiece_ssize_type i =
+ std::min(pos, static_cast<size_type>(length_ - 1));
+ i >= 0; --i) {
+ if (ptr_[i] == c) {
+ return i;
+ }
+ }
+ return npos;
+}
+
+// For each character in characters_wanted, sets the index corresponding
+// to the ASCII code of that character to 1 in table. This is used by
+// the find_.*_of methods below to tell whether or not a character is in
+// the lookup table in constant time.
+// The argument `table' must be an array that is large enough to hold all
+// the possible values of an unsigned char. Thus it should be be declared
+// as follows:
+// bool table[UCHAR_MAX + 1]
+static inline void BuildLookupTable(StringPiece characters_wanted,
+ bool* table) {
+ const stringpiece_ssize_type length = characters_wanted.length();
+ const char* const data = characters_wanted.data();
+ for (stringpiece_ssize_type i = 0; i < length; ++i) {
+ table[static_cast<unsigned char>(data[i])] = true;
+ }
+}
+
+stringpiece_ssize_type StringPiece::find_first_of(StringPiece s,
+ size_type pos) const {
+ if (length_ <= 0 || s.length_ <= 0) {
+ return npos;
+ }
+ // Avoid the cost of BuildLookupTable() for a single-character search.
+ if (s.length_ == 1) return find_first_of(s.ptr_[0], pos);
+
+ bool lookup[UCHAR_MAX + 1] = { false };
+ BuildLookupTable(s, lookup);
+ for (stringpiece_ssize_type i = pos; i < length_; ++i) {
+ if (lookup[static_cast<unsigned char>(ptr_[i])]) {
+ return i;
+ }
+ }
+ return npos;
+}
+
+stringpiece_ssize_type StringPiece::find_first_not_of(StringPiece s,
+ size_type pos) const {
+ if (length_ <= 0) return npos;
+ if (s.length_ <= 0) return 0;
+ // Avoid the cost of BuildLookupTable() for a single-character search.
+ if (s.length_ == 1) return find_first_not_of(s.ptr_[0], pos);
+
+ bool lookup[UCHAR_MAX + 1] = { false };
+ BuildLookupTable(s, lookup);
+ for (stringpiece_ssize_type i = pos; i < length_; ++i) {
+ if (!lookup[static_cast<unsigned char>(ptr_[i])]) {
+ return i;
+ }
+ }
+ return npos;
+}
+
+stringpiece_ssize_type StringPiece::find_first_not_of(char c,
+ size_type pos) const {
+ if (length_ <= 0) return npos;
+
+ for (; pos < static_cast<size_type>(length_); ++pos) {
+ if (ptr_[pos] != c) {
+ return pos;
+ }
+ }
+ return npos;
+}
+
+stringpiece_ssize_type StringPiece::find_last_of(StringPiece s,
+ size_type pos) const {
+ if (length_ <= 0 || s.length_ <= 0) return npos;
+ // Avoid the cost of BuildLookupTable() for a single-character search.
+ if (s.length_ == 1) return find_last_of(s.ptr_[0], pos);
+
+ bool lookup[UCHAR_MAX + 1] = { false };
+ BuildLookupTable(s, lookup);
+ for (stringpiece_ssize_type i =
+ std::min(pos, static_cast<size_type>(length_ - 1)); i >= 0; --i) {
+ if (lookup[static_cast<unsigned char>(ptr_[i])]) {
+ return i;
+ }
+ }
+ return npos;
+}
+
+stringpiece_ssize_type StringPiece::find_last_not_of(StringPiece s,
+ size_type pos) const {
+ if (length_ <= 0) return npos;
+
+ stringpiece_ssize_type i = std::min(pos, static_cast<size_type>(length_ - 1));
+ if (s.length_ <= 0) return i;
+
+ // Avoid the cost of BuildLookupTable() for a single-character search.
+ if (s.length_ == 1) return find_last_not_of(s.ptr_[0], pos);
+
+ bool lookup[UCHAR_MAX + 1] = { false };
+ BuildLookupTable(s, lookup);
+ for (; i >= 0; --i) {
+ if (!lookup[static_cast<unsigned char>(ptr_[i])]) {
+ return i;
+ }
+ }
+ return npos;
+}
+
+stringpiece_ssize_type StringPiece::find_last_not_of(char c,
+ size_type pos) const {
+ if (length_ <= 0) return npos;
+
+ for (stringpiece_ssize_type i =
+ std::min(pos, static_cast<size_type>(length_ - 1)); i >= 0; --i) {
+ if (ptr_[i] != c) {
+ return i;
+ }
+ }
+ return npos;
+}
+
+StringPiece StringPiece::substr(size_type pos, size_type n) const {
+ if (pos > length_) pos = length_;
+ if (n > length_ - pos) n = length_ - pos;
+ return StringPiece(ptr_ + pos, n);
+}
+
+const StringPiece::size_type StringPiece::npos = size_type(-1);
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.h
new file mode 100644
index 0000000000..8910688bf4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece.h
@@ -0,0 +1,483 @@
+// 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.
+
+// A StringPiece points to part or all of a string, Cord, double-quoted string
+// literal, or other string-like object. A StringPiece does *not* own the
+// string to which it points. A StringPiece is not null-terminated.
+//
+// You can use StringPiece as a function or method parameter. A StringPiece
+// parameter can receive a double-quoted string literal argument, a "const
+// char*" argument, a string argument, or a StringPiece argument with no data
+// copying. Systematic use of StringPiece for arguments reduces data
+// copies and strlen() calls.
+//
+// Prefer passing StringPieces by value:
+// void MyFunction(StringPiece arg);
+// If circumstances require, you may also pass by const reference:
+// void MyFunction(const StringPiece& arg); // not preferred
+// Both of these have the same lifetime semantics. Passing by value
+// generates slightly smaller code. For more discussion, see the thread
+// go/stringpiecebyvalue on c-users.
+//
+// StringPiece is also suitable for local variables if you know that
+// the lifetime of the underlying object is longer than the lifetime
+// of your StringPiece variable.
+//
+// Beware of binding a StringPiece to a temporary:
+// StringPiece sp = obj.MethodReturningString(); // BAD: lifetime problem
+//
+// This code is okay:
+// string str = obj.MethodReturningString(); // str owns its contents
+// StringPiece sp(str); // GOOD, because str outlives sp
+//
+// StringPiece is sometimes a poor choice for a return value and usually a poor
+// choice for a data member. If you do use a StringPiece this way, it is your
+// responsibility to ensure that the object pointed to by the StringPiece
+// outlives the StringPiece.
+//
+// A StringPiece may represent just part of a string; thus the name "Piece".
+// For example, when splitting a string, vector<StringPiece> is a natural data
+// type for the output. For another example, a Cord is a non-contiguous,
+// potentially very long string-like object. The Cord class has an interface
+// that iteratively provides StringPiece objects that point to the
+// successive pieces of a Cord object.
+//
+// A StringPiece is not null-terminated. If you write code that scans a
+// StringPiece, you must check its length before reading any characters.
+// Common idioms that work on null-terminated strings do not work on
+// StringPiece objects.
+//
+// There are several ways to create a null StringPiece:
+// StringPiece()
+// StringPiece(NULL)
+// StringPiece(NULL, 0)
+// For all of the above, sp.data() == NULL, sp.length() == 0,
+// and sp.empty() == true. Also, if you create a StringPiece with
+// a non-NULL pointer then sp.data() != NULL. Once created,
+// sp.data() will stay either NULL or not-NULL, except if you call
+// sp.clear() or sp.set().
+//
+// Thus, you can use StringPiece(NULL) to signal an out-of-band value
+// that is different from other StringPiece values. This is similar
+// to the way that const char* p1 = NULL; is different from
+// const char* p2 = "";.
+//
+// There are many ways to create an empty StringPiece:
+// StringPiece()
+// StringPiece(NULL)
+// StringPiece(NULL, 0)
+// StringPiece("")
+// StringPiece("", 0)
+// StringPiece("abcdef", 0)
+// StringPiece("abcdef"+6, 0)
+// For all of the above, sp.length() will be 0 and sp.empty() will be true.
+// For some empty StringPiece values, sp.data() will be NULL.
+// For some empty StringPiece values, sp.data() will not be NULL.
+//
+// Be careful not to confuse: null StringPiece and empty StringPiece.
+// The set of empty StringPieces properly includes the set of null StringPieces.
+// That is, every null StringPiece is an empty StringPiece,
+// but some non-null StringPieces are empty Stringpieces too.
+//
+// All empty StringPiece values compare equal to each other.
+// Even a null StringPieces compares equal to a non-null empty StringPiece:
+// StringPiece() == StringPiece("", 0)
+// StringPiece(NULL) == StringPiece("abc", 0)
+// StringPiece(NULL, 0) == StringPiece("abcdef"+6, 0)
+//
+// Look carefully at this example:
+// StringPiece("") == NULL
+// True or false? TRUE, because StringPiece::operator== converts
+// the right-hand side from NULL to StringPiece(NULL),
+// and then compares two zero-length spans of characters.
+// However, we are working to make this example produce a compile error.
+//
+// Suppose you want to write:
+// bool TestWhat?(StringPiece sp) { return sp == NULL; } // BAD
+// Do not do that. Write one of these instead:
+// bool TestNull(StringPiece sp) { return sp.data() == NULL; }
+// bool TestEmpty(StringPiece sp) { return sp.empty(); }
+// The intent of TestWhat? is unclear. Did you mean TestNull or TestEmpty?
+// Right now, TestWhat? behaves likes TestEmpty.
+// We are working to make TestWhat? produce a compile error.
+// TestNull is good to test for an out-of-band signal.
+// TestEmpty is good to test for an empty StringPiece.
+//
+// Caveats (again):
+// (1) The lifetime of the pointed-to string (or piece of a string)
+// must be longer than the lifetime of the StringPiece.
+// (2) There may or may not be a '\0' character after the end of
+// StringPiece data.
+// (3) A null StringPiece is empty.
+// An empty StringPiece may or may not be a null StringPiece.
+
+#ifndef GOOGLE_PROTOBUF_STUBS_STRINGPIECE_H_
+#define GOOGLE_PROTOBUF_STUBS_STRINGPIECE_H_
+
+#include <assert.h>
+#include <stddef.h>
+#include <string.h>
+#include <iosfwd>
+#include <limits>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/hash.h>
+
+namespace google {
+namespace protobuf {
+// StringPiece has *two* size types.
+// StringPiece::size_type
+// is unsigned
+// is 32 bits in LP32, 64 bits in LP64, 64 bits in LLP64
+// no future changes intended
+// stringpiece_ssize_type
+// is signed
+// is 32 bits in LP32, 64 bits in LP64, 64 bits in LLP64
+// future changes intended: http://go/64BitStringPiece
+//
+typedef string::difference_type stringpiece_ssize_type;
+
+// STRINGPIECE_CHECK_SIZE protects us from 32-bit overflows.
+// TODO(mec): delete this after stringpiece_ssize_type goes 64 bit.
+#if !defined(NDEBUG)
+#define STRINGPIECE_CHECK_SIZE 1
+#elif defined(_FORTIFY_SOURCE) && _FORTIFY_SOURCE > 0
+#define STRINGPIECE_CHECK_SIZE 1
+#else
+#define STRINGPIECE_CHECK_SIZE 0
+#endif
+
+class LIBPROTOBUF_EXPORT StringPiece {
+ private:
+ const char* ptr_;
+ stringpiece_ssize_type length_;
+
+ // Prevent overflow in debug mode or fortified mode.
+ // sizeof(stringpiece_ssize_type) may be smaller than sizeof(size_t).
+ static stringpiece_ssize_type CheckedSsizeTFromSizeT(size_t size) {
+#if STRINGPIECE_CHECK_SIZE > 0
+#ifdef max
+#undef max
+#endif
+ if (size > static_cast<size_t>(
+ std::numeric_limits<stringpiece_ssize_type>::max())) {
+ // Some people grep for this message in logs
+ // so take care if you ever change it.
+ LogFatalSizeTooBig(size, "size_t to int conversion");
+ }
+#endif
+ return static_cast<stringpiece_ssize_type>(size);
+ }
+
+ // Out-of-line error path.
+ static void LogFatalSizeTooBig(size_t size, const char* details);
+
+ public:
+ // We provide non-explicit singleton constructors so users can pass
+ // in a "const char*" or a "string" wherever a "StringPiece" is
+ // expected.
+ //
+ // Style guide exception granted:
+ // http://goto/style-guide-exception-20978288
+ StringPiece() : ptr_(NULL), length_(0) {}
+
+ StringPiece(const char* str) // NOLINT(runtime/explicit)
+ : ptr_(str), length_(0) {
+ if (str != NULL) {
+ length_ = CheckedSsizeTFromSizeT(strlen(str));
+ }
+ }
+
+ template <class Allocator>
+ StringPiece( // NOLINT(runtime/explicit)
+ const std::basic_string<char, std::char_traits<char>, Allocator>& str)
+ : ptr_(str.data()), length_(0) {
+ length_ = CheckedSsizeTFromSizeT(str.size());
+ }
+
+ StringPiece(const char* offset, stringpiece_ssize_type len)
+ : ptr_(offset), length_(len) {
+ assert(len >= 0);
+ }
+
+ // Substring of another StringPiece.
+ // pos must be non-negative and <= x.length().
+ StringPiece(StringPiece x, stringpiece_ssize_type pos);
+ // Substring of another StringPiece.
+ // pos must be non-negative and <= x.length().
+ // len must be non-negative and will be pinned to at most x.length() - pos.
+ StringPiece(StringPiece x,
+ stringpiece_ssize_type pos,
+ stringpiece_ssize_type len);
+
+ // data() may return a pointer to a buffer with embedded NULs, and the
+ // returned buffer may or may not be null terminated. Therefore it is
+ // typically a mistake to pass data() to a routine that expects a NUL
+ // terminated string.
+ const char* data() const { return ptr_; }
+ stringpiece_ssize_type size() const { return length_; }
+ stringpiece_ssize_type length() const { return length_; }
+ bool empty() const { return length_ == 0; }
+
+ void clear() {
+ ptr_ = NULL;
+ length_ = 0;
+ }
+
+ void set(const char* data, stringpiece_ssize_type len) {
+ assert(len >= 0);
+ ptr_ = data;
+ length_ = len;
+ }
+
+ void set(const char* str) {
+ ptr_ = str;
+ if (str != NULL)
+ length_ = CheckedSsizeTFromSizeT(strlen(str));
+ else
+ length_ = 0;
+ }
+
+ void set(const void* data, stringpiece_ssize_type len) {
+ ptr_ = reinterpret_cast<const char*>(data);
+ length_ = len;
+ }
+
+ char operator[](stringpiece_ssize_type i) const {
+ assert(0 <= i);
+ assert(i < length_);
+ return ptr_[i];
+ }
+
+ void remove_prefix(stringpiece_ssize_type n) {
+ assert(length_ >= n);
+ ptr_ += n;
+ length_ -= n;
+ }
+
+ void remove_suffix(stringpiece_ssize_type n) {
+ assert(length_ >= n);
+ length_ -= n;
+ }
+
+ // returns {-1, 0, 1}
+ int compare(StringPiece x) const {
+ const stringpiece_ssize_type min_size =
+ length_ < x.length_ ? length_ : x.length_;
+ int r = memcmp(ptr_, x.ptr_, min_size);
+ if (r < 0) return -1;
+ if (r > 0) return 1;
+ if (length_ < x.length_) return -1;
+ if (length_ > x.length_) return 1;
+ return 0;
+ }
+
+ string as_string() const {
+ return ToString();
+ }
+ // We also define ToString() here, since many other string-like
+ // interfaces name the routine that converts to a C++ string
+ // "ToString", and it's confusing to have the method that does that
+ // for a StringPiece be called "as_string()". We also leave the
+ // "as_string()" method defined here for existing code.
+ string ToString() const {
+ if (ptr_ == NULL) return string();
+ return string(data(), size());
+ }
+
+ operator string() const {
+ return ToString();
+ }
+
+ void CopyToString(string* target) const;
+ void AppendToString(string* target) const;
+
+ bool starts_with(StringPiece x) const {
+ return (length_ >= x.length_) && (memcmp(ptr_, x.ptr_, x.length_) == 0);
+ }
+
+ bool ends_with(StringPiece x) const {
+ return ((length_ >= x.length_) &&
+ (memcmp(ptr_ + (length_-x.length_), x.ptr_, x.length_) == 0));
+ }
+
+ // Checks whether StringPiece starts with x and if so advances the beginning
+ // of it to past the match. It's basically a shortcut for starts_with
+ // followed by remove_prefix.
+ bool Consume(StringPiece x);
+ // Like above but for the end of the string.
+ bool ConsumeFromEnd(StringPiece x);
+
+ // standard STL container boilerplate
+ typedef char value_type;
+ typedef const char* pointer;
+ typedef const char& reference;
+ typedef const char& const_reference;
+ typedef size_t size_type;
+ typedef ptrdiff_t difference_type;
+ static const size_type npos;
+ typedef const char* const_iterator;
+ typedef const char* iterator;
+ typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
+ typedef std::reverse_iterator<iterator> reverse_iterator;
+ iterator begin() const { return ptr_; }
+ iterator end() const { return ptr_ + length_; }
+ const_reverse_iterator rbegin() const {
+ return const_reverse_iterator(ptr_ + length_);
+ }
+ const_reverse_iterator rend() const {
+ return const_reverse_iterator(ptr_);
+ }
+ stringpiece_ssize_type max_size() const { return length_; }
+ stringpiece_ssize_type capacity() const { return length_; }
+
+ // cpplint.py emits a false positive [build/include_what_you_use]
+ stringpiece_ssize_type copy(char* buf, size_type n, size_type pos = 0) const; // NOLINT
+
+ bool contains(StringPiece s) const;
+
+ stringpiece_ssize_type find(StringPiece s, size_type pos = 0) const;
+ stringpiece_ssize_type find(char c, size_type pos = 0) const;
+ stringpiece_ssize_type rfind(StringPiece s, size_type pos = npos) const;
+ stringpiece_ssize_type rfind(char c, size_type pos = npos) const;
+
+ stringpiece_ssize_type find_first_of(StringPiece s, size_type pos = 0) const;
+ stringpiece_ssize_type find_first_of(char c, size_type pos = 0) const {
+ return find(c, pos);
+ }
+ stringpiece_ssize_type find_first_not_of(StringPiece s,
+ size_type pos = 0) const;
+ stringpiece_ssize_type find_first_not_of(char c, size_type pos = 0) const;
+ stringpiece_ssize_type find_last_of(StringPiece s,
+ size_type pos = npos) const;
+ stringpiece_ssize_type find_last_of(char c, size_type pos = npos) const {
+ return rfind(c, pos);
+ }
+ stringpiece_ssize_type find_last_not_of(StringPiece s,
+ size_type pos = npos) const;
+ stringpiece_ssize_type find_last_not_of(char c, size_type pos = npos) const;
+
+ StringPiece substr(size_type pos, size_type n = npos) const;
+};
+
+// This large function is defined inline so that in a fairly common case where
+// one of the arguments is a literal, the compiler can elide a lot of the
+// following comparisons.
+inline bool operator==(StringPiece x, StringPiece y) {
+ stringpiece_ssize_type len = x.size();
+ if (len != y.size()) {
+ return false;
+ }
+
+ return x.data() == y.data() || len <= 0 ||
+ memcmp(x.data(), y.data(), len) == 0;
+}
+
+inline bool operator!=(StringPiece x, StringPiece y) {
+ return !(x == y);
+}
+
+inline bool operator<(StringPiece x, StringPiece y) {
+ const stringpiece_ssize_type min_size =
+ x.size() < y.size() ? x.size() : y.size();
+ const int r = memcmp(x.data(), y.data(), min_size);
+ return (r < 0) || (r == 0 && x.size() < y.size());
+}
+
+inline bool operator>(StringPiece x, StringPiece y) {
+ return y < x;
+}
+
+inline bool operator<=(StringPiece x, StringPiece y) {
+ return !(x > y);
+}
+
+inline bool operator>=(StringPiece x, StringPiece y) {
+ return !(x < y);
+}
+
+// allow StringPiece to be logged
+extern std::ostream& operator<<(std::ostream& o, StringPiece piece);
+
+namespace internal {
+// StringPiece is not a POD and can not be used in an union (pre C++11). We
+// need a POD version of it.
+struct StringPiecePod {
+ // Create from a StringPiece.
+ static StringPiecePod CreateFromStringPiece(StringPiece str) {
+ StringPiecePod pod;
+ pod.data_ = str.data();
+ pod.size_ = str.size();
+ return pod;
+ }
+
+ // Cast to StringPiece.
+ operator StringPiece() const { return StringPiece(data_, size_); }
+
+ bool operator==(const char* value) const {
+ return StringPiece(data_, size_) == StringPiece(value);
+ }
+
+ char operator[](stringpiece_ssize_type i) const {
+ assert(0 <= i);
+ assert(i < size_);
+ return data_[i];
+ }
+
+ const char* data() const { return data_; }
+
+ stringpiece_ssize_type size() const {
+ return size_;
+ }
+
+ std::string ToString() const { return std::string(data_, size_); }
+ private:
+ const char* data_;
+ stringpiece_ssize_type size_;
+};
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+GOOGLE_PROTOBUF_HASH_NAMESPACE_DECLARATION_START
+template<> struct hash<StringPiece> {
+ size_t operator()(const StringPiece& s) const {
+ size_t result = 0;
+ for (const char *str = s.data(), *end = str + s.size(); str < end; str++) {
+ result = 5 * result + *str;
+ }
+ return result;
+ }
+};
+GOOGLE_PROTOBUF_HASH_NAMESPACE_DECLARATION_END
+
+#endif // STRINGS_STRINGPIECE_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece_unittest.cc
new file mode 100644
index 0000000000..a52d81f83a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringpiece_unittest.cc
@@ -0,0 +1,794 @@
+// 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.
+#include <google/protobuf/stubs/stringpiece.h>
+
+#include <iterator>
+#include <map>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <google/protobuf/testing/googletest.h>
+#include <google/protobuf/stubs/hash.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+TEST(StringPiece, Ctor) {
+ {
+ // Null.
+ StringPiece s10;
+ EXPECT_TRUE(s10.data() == NULL);
+ EXPECT_EQ(0, s10.length());
+ }
+
+ {
+ // const char* without length.
+ const char* hello = "hello";
+ StringPiece s20(hello);
+ EXPECT_TRUE(s20.data() == hello);
+ EXPECT_EQ(5, s20.length());
+
+ // const char* with length.
+ StringPiece s21(hello, 4);
+ EXPECT_TRUE(s21.data() == hello);
+ EXPECT_EQ(4, s21.length());
+
+ // Not recommended, but valid C++
+ StringPiece s22(hello, 6);
+ EXPECT_TRUE(s22.data() == hello);
+ EXPECT_EQ(6, s22.length());
+ }
+
+ {
+ // std::string.
+ std::string hola = "hola";
+ StringPiece s30(hola);
+ EXPECT_TRUE(s30.data() == hola.data());
+ EXPECT_EQ(4, s30.length());
+
+ // std::string with embedded '\0'.
+ hola.push_back('\0');
+ hola.append("h2");
+ hola.push_back('\0');
+ StringPiece s31(hola);
+ EXPECT_TRUE(s31.data() == hola.data());
+ EXPECT_EQ(8, s31.length());
+ }
+
+#if defined(HAS_GLOBAL_STRING)
+ {
+ // ::string
+ string bonjour = "bonjour";
+ StringPiece s40(bonjour);
+ EXPECT_TRUE(s40.data() == bonjour.data());
+ EXPECT_EQ(7, s40.length());
+ }
+#endif
+
+ // TODO(mec): StringPiece(StringPiece x, int pos);
+ // TODO(mec): StringPiece(StringPiece x, int pos, int len);
+ // TODO(mec): StringPiece(const StringPiece&);
+}
+
+TEST(StringPiece, STLComparator) {
+ string s1("foo");
+ string s2("bar");
+ string s3("baz");
+
+ StringPiece p1(s1);
+ StringPiece p2(s2);
+ StringPiece p3(s3);
+
+ typedef std::map<StringPiece, int> TestMap;
+ TestMap map;
+
+ map.insert(std::make_pair(p1, 0));
+ map.insert(std::make_pair(p2, 1));
+ map.insert(std::make_pair(p3, 2));
+ EXPECT_EQ(map.size(), 3);
+
+ TestMap::const_iterator iter = map.begin();
+ EXPECT_EQ(iter->second, 1);
+ ++iter;
+ EXPECT_EQ(iter->second, 2);
+ ++iter;
+ EXPECT_EQ(iter->second, 0);
+ ++iter;
+ EXPECT_TRUE(iter == map.end());
+
+ TestMap::iterator new_iter = map.find("zot");
+ EXPECT_TRUE(new_iter == map.end());
+
+ new_iter = map.find("bar");
+ EXPECT_TRUE(new_iter != map.end());
+
+ map.erase(new_iter);
+ EXPECT_EQ(map.size(), 2);
+
+ iter = map.begin();
+ EXPECT_EQ(iter->second, 2);
+ ++iter;
+ EXPECT_EQ(iter->second, 0);
+ ++iter;
+ EXPECT_TRUE(iter == map.end());
+}
+
+TEST(StringPiece, ComparisonOperators) {
+#define COMPARE(result, op, x, y) \
+ EXPECT_EQ(result, StringPiece((x)) op StringPiece((y))); \
+ EXPECT_EQ(result, StringPiece((x)).compare(StringPiece((y))) op 0)
+
+ COMPARE(true, ==, "", "");
+ COMPARE(true, ==, "", NULL);
+ COMPARE(true, ==, NULL, "");
+ COMPARE(true, ==, "a", "a");
+ COMPARE(true, ==, "aa", "aa");
+ COMPARE(false, ==, "a", "");
+ COMPARE(false, ==, "", "a");
+ COMPARE(false, ==, "a", "b");
+ COMPARE(false, ==, "a", "aa");
+ COMPARE(false, ==, "aa", "a");
+
+ COMPARE(false, !=, "", "");
+ COMPARE(false, !=, "a", "a");
+ COMPARE(false, !=, "aa", "aa");
+ COMPARE(true, !=, "a", "");
+ COMPARE(true, !=, "", "a");
+ COMPARE(true, !=, "a", "b");
+ COMPARE(true, !=, "a", "aa");
+ COMPARE(true, !=, "aa", "a");
+
+ COMPARE(true, <, "a", "b");
+ COMPARE(true, <, "a", "aa");
+ COMPARE(true, <, "aa", "b");
+ COMPARE(true, <, "aa", "bb");
+ COMPARE(false, <, "a", "a");
+ COMPARE(false, <, "b", "a");
+ COMPARE(false, <, "aa", "a");
+ COMPARE(false, <, "b", "aa");
+ COMPARE(false, <, "bb", "aa");
+
+ COMPARE(true, <=, "a", "a");
+ COMPARE(true, <=, "a", "b");
+ COMPARE(true, <=, "a", "aa");
+ COMPARE(true, <=, "aa", "b");
+ COMPARE(true, <=, "aa", "bb");
+ COMPARE(false, <=, "b", "a");
+ COMPARE(false, <=, "aa", "a");
+ COMPARE(false, <=, "b", "aa");
+ COMPARE(false, <=, "bb", "aa");
+
+ COMPARE(false, >=, "a", "b");
+ COMPARE(false, >=, "a", "aa");
+ COMPARE(false, >=, "aa", "b");
+ COMPARE(false, >=, "aa", "bb");
+ COMPARE(true, >=, "a", "a");
+ COMPARE(true, >=, "b", "a");
+ COMPARE(true, >=, "aa", "a");
+ COMPARE(true, >=, "b", "aa");
+ COMPARE(true, >=, "bb", "aa");
+
+ COMPARE(false, >, "a", "a");
+ COMPARE(false, >, "a", "b");
+ COMPARE(false, >, "a", "aa");
+ COMPARE(false, >, "aa", "b");
+ COMPARE(false, >, "aa", "bb");
+ COMPARE(true, >, "b", "a");
+ COMPARE(true, >, "aa", "a");
+ COMPARE(true, >, "b", "aa");
+ COMPARE(true, >, "bb", "aa");
+
+ string x;
+ for (int i = 0; i < 256; i++) {
+ x += 'a';
+ string y = x;
+ COMPARE(true, ==, x, y);
+ for (int j = 0; j < i; j++) {
+ string z = x;
+ z[j] = 'b'; // Differs in position 'j'
+ COMPARE(false, ==, x, z);
+ COMPARE(true, <, x, z);
+ COMPARE(true, >, z, x);
+ if (j + 1 < i) {
+ z[j + 1] = 'A'; // Differs in position 'j+1' as well
+ COMPARE(false, ==, x, z);
+ COMPARE(true, <, x, z);
+ COMPARE(true, >, z, x);
+ z[j + 1] = 'z'; // Differs in position 'j+1' as well
+ COMPARE(false, ==, x, z);
+ COMPARE(true, <, x, z);
+ COMPARE(true, >, z, x);
+ }
+ }
+ }
+
+#undef COMPARE
+}
+
+TEST(StringPiece, STL1) {
+ const StringPiece a("abcdefghijklmnopqrstuvwxyz");
+ const StringPiece b("abc");
+ const StringPiece c("xyz");
+ const StringPiece d("foobar");
+ const StringPiece e;
+ string temp("123");
+ temp += '\0';
+ temp += "456";
+ const StringPiece f(temp);
+
+ EXPECT_EQ(a[6], 'g');
+ EXPECT_EQ(b[0], 'a');
+ EXPECT_EQ(c[2], 'z');
+ EXPECT_EQ(f[3], '\0');
+ EXPECT_EQ(f[5], '5');
+
+ EXPECT_EQ(*d.data(), 'f');
+ EXPECT_EQ(d.data()[5], 'r');
+ EXPECT_TRUE(e.data() == NULL);
+
+ EXPECT_EQ(*a.begin(), 'a');
+ EXPECT_EQ(*(b.begin() + 2), 'c');
+ EXPECT_EQ(*(c.end() - 1), 'z');
+
+ EXPECT_EQ(*a.rbegin(), 'z');
+ EXPECT_EQ(*(b.rbegin() + 2), 'a');
+ EXPECT_EQ(*(c.rend() - 1), 'x');
+ EXPECT_TRUE(a.rbegin() + 26 == a.rend());
+
+ EXPECT_EQ(a.size(), 26);
+ EXPECT_EQ(b.size(), 3);
+ EXPECT_EQ(c.size(), 3);
+ EXPECT_EQ(d.size(), 6);
+ EXPECT_EQ(e.size(), 0);
+ EXPECT_EQ(f.size(), 7);
+
+ EXPECT_TRUE(!d.empty());
+ EXPECT_TRUE(d.begin() != d.end());
+ EXPECT_TRUE(d.begin() + 6 == d.end());
+
+ EXPECT_TRUE(e.empty());
+ EXPECT_TRUE(e.begin() == e.end());
+
+ EXPECT_GE(a.max_size(), a.capacity());
+ EXPECT_GE(a.capacity(), a.size());
+
+ char buf[4] = { '%', '%', '%', '%' };
+ EXPECT_EQ(a.copy(buf, 4), 4);
+ EXPECT_EQ(buf[0], a[0]);
+ EXPECT_EQ(buf[1], a[1]);
+ EXPECT_EQ(buf[2], a[2]);
+ EXPECT_EQ(buf[3], a[3]);
+ EXPECT_EQ(a.copy(buf, 3, 7), 3);
+ EXPECT_EQ(buf[0], a[7]);
+ EXPECT_EQ(buf[1], a[8]);
+ EXPECT_EQ(buf[2], a[9]);
+ EXPECT_EQ(buf[3], a[3]);
+ EXPECT_EQ(c.copy(buf, 99), 3);
+ EXPECT_EQ(buf[0], c[0]);
+ EXPECT_EQ(buf[1], c[1]);
+ EXPECT_EQ(buf[2], c[2]);
+ EXPECT_EQ(buf[3], a[3]);
+}
+
+// Separated from STL1() because some compilers produce an overly
+// large stack frame for the combined function.
+TEST(StringPiece, STL2) {
+ const StringPiece a("abcdefghijklmnopqrstuvwxyz");
+ const StringPiece b("abc");
+ const StringPiece c("xyz");
+ StringPiece d("foobar");
+ const StringPiece e;
+ const StringPiece f("123" "\0" "456", 7);
+
+ d.clear();
+ EXPECT_EQ(d.size(), 0);
+ EXPECT_TRUE(d.empty());
+ EXPECT_TRUE(d.data() == NULL);
+ EXPECT_TRUE(d.begin() == d.end());
+
+ EXPECT_EQ(StringPiece::npos, string::npos);
+
+ EXPECT_EQ(a.find(b), 0);
+ EXPECT_EQ(a.find(b, 1), StringPiece::npos);
+ EXPECT_EQ(a.find(c), 23);
+ EXPECT_EQ(a.find(c, 9), 23);
+ EXPECT_EQ(a.find(c, StringPiece::npos), StringPiece::npos);
+ EXPECT_EQ(b.find(c), StringPiece::npos);
+ EXPECT_EQ(b.find(c, StringPiece::npos), StringPiece::npos);
+ EXPECT_EQ(a.find(d), 0);
+ EXPECT_EQ(a.find(e), 0);
+ EXPECT_EQ(a.find(d, 12), 12);
+ EXPECT_EQ(a.find(e, 17), 17);
+ StringPiece g("xx not found bb");
+ EXPECT_EQ(a.find(g), StringPiece::npos);
+ // empty string nonsense
+ EXPECT_EQ(d.find(b), StringPiece::npos);
+ EXPECT_EQ(e.find(b), StringPiece::npos);
+ EXPECT_EQ(d.find(b, 4), StringPiece::npos);
+ EXPECT_EQ(e.find(b, 7), StringPiece::npos);
+
+ size_t empty_search_pos = string().find(string());
+ EXPECT_EQ(d.find(d), empty_search_pos);
+ EXPECT_EQ(d.find(e), empty_search_pos);
+ EXPECT_EQ(e.find(d), empty_search_pos);
+ EXPECT_EQ(e.find(e), empty_search_pos);
+ EXPECT_EQ(d.find(d, 4), string().find(string(), 4));
+ EXPECT_EQ(d.find(e, 4), string().find(string(), 4));
+ EXPECT_EQ(e.find(d, 4), string().find(string(), 4));
+ EXPECT_EQ(e.find(e, 4), string().find(string(), 4));
+
+ EXPECT_EQ(a.find('a'), 0);
+ EXPECT_EQ(a.find('c'), 2);
+ EXPECT_EQ(a.find('z'), 25);
+ EXPECT_EQ(a.find('$'), StringPiece::npos);
+ EXPECT_EQ(a.find('\0'), StringPiece::npos);
+ EXPECT_EQ(f.find('\0'), 3);
+ EXPECT_EQ(f.find('3'), 2);
+ EXPECT_EQ(f.find('5'), 5);
+ EXPECT_EQ(g.find('o'), 4);
+ EXPECT_EQ(g.find('o', 4), 4);
+ EXPECT_EQ(g.find('o', 5), 8);
+ EXPECT_EQ(a.find('b', 5), StringPiece::npos);
+ // empty string nonsense
+ EXPECT_EQ(d.find('\0'), StringPiece::npos);
+ EXPECT_EQ(e.find('\0'), StringPiece::npos);
+ EXPECT_EQ(d.find('\0', 4), StringPiece::npos);
+ EXPECT_EQ(e.find('\0', 7), StringPiece::npos);
+ EXPECT_EQ(d.find('x'), StringPiece::npos);
+ EXPECT_EQ(e.find('x'), StringPiece::npos);
+ EXPECT_EQ(d.find('x', 4), StringPiece::npos);
+ EXPECT_EQ(e.find('x', 7), StringPiece::npos);
+
+ EXPECT_EQ(a.rfind(b), 0);
+ EXPECT_EQ(a.rfind(b, 1), 0);
+ EXPECT_EQ(a.rfind(c), 23);
+ EXPECT_EQ(a.rfind(c, 22), StringPiece::npos);
+ EXPECT_EQ(a.rfind(c, 1), StringPiece::npos);
+ EXPECT_EQ(a.rfind(c, 0), StringPiece::npos);
+ EXPECT_EQ(b.rfind(c), StringPiece::npos);
+ EXPECT_EQ(b.rfind(c, 0), StringPiece::npos);
+ EXPECT_EQ(a.rfind(d), a.as_string().rfind(string()));
+ EXPECT_EQ(a.rfind(e), a.as_string().rfind(string()));
+ EXPECT_EQ(a.rfind(d, 12), 12);
+ EXPECT_EQ(a.rfind(e, 17), 17);
+ EXPECT_EQ(a.rfind(g), StringPiece::npos);
+ EXPECT_EQ(d.rfind(b), StringPiece::npos);
+ EXPECT_EQ(e.rfind(b), StringPiece::npos);
+ EXPECT_EQ(d.rfind(b, 4), StringPiece::npos);
+ EXPECT_EQ(e.rfind(b, 7), StringPiece::npos);
+ // empty string nonsense
+ EXPECT_EQ(d.rfind(d, 4), string().rfind(string()));
+ EXPECT_EQ(e.rfind(d, 7), string().rfind(string()));
+ EXPECT_EQ(d.rfind(e, 4), string().rfind(string()));
+ EXPECT_EQ(e.rfind(e, 7), string().rfind(string()));
+ EXPECT_EQ(d.rfind(d), string().rfind(string()));
+ EXPECT_EQ(e.rfind(d), string().rfind(string()));
+ EXPECT_EQ(d.rfind(e), string().rfind(string()));
+ EXPECT_EQ(e.rfind(e), string().rfind(string()));
+
+ EXPECT_EQ(g.rfind('o'), 8);
+ EXPECT_EQ(g.rfind('q'), StringPiece::npos);
+ EXPECT_EQ(g.rfind('o', 8), 8);
+ EXPECT_EQ(g.rfind('o', 7), 4);
+ EXPECT_EQ(g.rfind('o', 3), StringPiece::npos);
+ EXPECT_EQ(f.rfind('\0'), 3);
+ EXPECT_EQ(f.rfind('\0', 12), 3);
+ EXPECT_EQ(f.rfind('3'), 2);
+ EXPECT_EQ(f.rfind('5'), 5);
+ // empty string nonsense
+ EXPECT_EQ(d.rfind('o'), StringPiece::npos);
+ EXPECT_EQ(e.rfind('o'), StringPiece::npos);
+ EXPECT_EQ(d.rfind('o', 4), StringPiece::npos);
+ EXPECT_EQ(e.rfind('o', 7), StringPiece::npos);
+
+ EXPECT_EQ(a.find_first_of(b), 0);
+ EXPECT_EQ(a.find_first_of(b, 0), 0);
+ EXPECT_EQ(a.find_first_of(b, 1), 1);
+ EXPECT_EQ(a.find_first_of(b, 2), 2);
+ EXPECT_EQ(a.find_first_of(b, 3), StringPiece::npos);
+ EXPECT_EQ(a.find_first_of(c), 23);
+ EXPECT_EQ(a.find_first_of(c, 23), 23);
+ EXPECT_EQ(a.find_first_of(c, 24), 24);
+ EXPECT_EQ(a.find_first_of(c, 25), 25);
+ EXPECT_EQ(a.find_first_of(c, 26), StringPiece::npos);
+ EXPECT_EQ(g.find_first_of(b), 13);
+ EXPECT_EQ(g.find_first_of(c), 0);
+ EXPECT_EQ(a.find_first_of(f), StringPiece::npos);
+ EXPECT_EQ(f.find_first_of(a), StringPiece::npos);
+ // empty string nonsense
+ EXPECT_EQ(a.find_first_of(d), StringPiece::npos);
+ EXPECT_EQ(a.find_first_of(e), StringPiece::npos);
+ EXPECT_EQ(d.find_first_of(b), StringPiece::npos);
+ EXPECT_EQ(e.find_first_of(b), StringPiece::npos);
+ EXPECT_EQ(d.find_first_of(d), StringPiece::npos);
+ EXPECT_EQ(e.find_first_of(d), StringPiece::npos);
+ EXPECT_EQ(d.find_first_of(e), StringPiece::npos);
+ EXPECT_EQ(e.find_first_of(e), StringPiece::npos);
+
+ EXPECT_EQ(a.find_first_not_of(b), 3);
+ EXPECT_EQ(a.find_first_not_of(c), 0);
+ EXPECT_EQ(b.find_first_not_of(a), StringPiece::npos);
+ EXPECT_EQ(c.find_first_not_of(a), StringPiece::npos);
+ EXPECT_EQ(f.find_first_not_of(a), 0);
+ EXPECT_EQ(a.find_first_not_of(f), 0);
+ EXPECT_EQ(a.find_first_not_of(d), 0);
+ EXPECT_EQ(a.find_first_not_of(e), 0);
+ // empty string nonsense
+ EXPECT_EQ(d.find_first_not_of(a), StringPiece::npos);
+ EXPECT_EQ(e.find_first_not_of(a), StringPiece::npos);
+ EXPECT_EQ(d.find_first_not_of(d), StringPiece::npos);
+ EXPECT_EQ(e.find_first_not_of(d), StringPiece::npos);
+ EXPECT_EQ(d.find_first_not_of(e), StringPiece::npos);
+ EXPECT_EQ(e.find_first_not_of(e), StringPiece::npos);
+
+ StringPiece h("====");
+ EXPECT_EQ(h.find_first_not_of('='), StringPiece::npos);
+ EXPECT_EQ(h.find_first_not_of('=', 3), StringPiece::npos);
+ EXPECT_EQ(h.find_first_not_of('\0'), 0);
+ EXPECT_EQ(g.find_first_not_of('x'), 2);
+ EXPECT_EQ(f.find_first_not_of('\0'), 0);
+ EXPECT_EQ(f.find_first_not_of('\0', 3), 4);
+ EXPECT_EQ(f.find_first_not_of('\0', 2), 2);
+ // empty string nonsense
+ EXPECT_EQ(d.find_first_not_of('x'), StringPiece::npos);
+ EXPECT_EQ(e.find_first_not_of('x'), StringPiece::npos);
+ EXPECT_EQ(d.find_first_not_of('\0'), StringPiece::npos);
+ EXPECT_EQ(e.find_first_not_of('\0'), StringPiece::npos);
+
+ // StringPiece g("xx not found bb");
+ StringPiece i("56");
+ EXPECT_EQ(h.find_last_of(a), StringPiece::npos);
+ EXPECT_EQ(g.find_last_of(a), g.size()-1);
+ EXPECT_EQ(a.find_last_of(b), 2);
+ EXPECT_EQ(a.find_last_of(c), a.size()-1);
+ EXPECT_EQ(f.find_last_of(i), 6);
+ EXPECT_EQ(a.find_last_of('a'), 0);
+ EXPECT_EQ(a.find_last_of('b'), 1);
+ EXPECT_EQ(a.find_last_of('z'), 25);
+ EXPECT_EQ(a.find_last_of('a', 5), 0);
+ EXPECT_EQ(a.find_last_of('b', 5), 1);
+ EXPECT_EQ(a.find_last_of('b', 0), StringPiece::npos);
+ EXPECT_EQ(a.find_last_of('z', 25), 25);
+ EXPECT_EQ(a.find_last_of('z', 24), StringPiece::npos);
+ EXPECT_EQ(f.find_last_of(i, 5), 5);
+ EXPECT_EQ(f.find_last_of(i, 6), 6);
+ EXPECT_EQ(f.find_last_of(a, 4), StringPiece::npos);
+ // empty string nonsense
+ EXPECT_EQ(f.find_last_of(d), StringPiece::npos);
+ EXPECT_EQ(f.find_last_of(e), StringPiece::npos);
+ EXPECT_EQ(f.find_last_of(d, 4), StringPiece::npos);
+ EXPECT_EQ(f.find_last_of(e, 4), StringPiece::npos);
+ EXPECT_EQ(d.find_last_of(d), StringPiece::npos);
+ EXPECT_EQ(d.find_last_of(e), StringPiece::npos);
+ EXPECT_EQ(e.find_last_of(d), StringPiece::npos);
+ EXPECT_EQ(e.find_last_of(e), StringPiece::npos);
+ EXPECT_EQ(d.find_last_of(f), StringPiece::npos);
+ EXPECT_EQ(e.find_last_of(f), StringPiece::npos);
+ EXPECT_EQ(d.find_last_of(d, 4), StringPiece::npos);
+ EXPECT_EQ(d.find_last_of(e, 4), StringPiece::npos);
+ EXPECT_EQ(e.find_last_of(d, 4), StringPiece::npos);
+ EXPECT_EQ(e.find_last_of(e, 4), StringPiece::npos);
+ EXPECT_EQ(d.find_last_of(f, 4), StringPiece::npos);
+ EXPECT_EQ(e.find_last_of(f, 4), StringPiece::npos);
+
+ EXPECT_EQ(a.find_last_not_of(b), a.size()-1);
+ EXPECT_EQ(a.find_last_not_of(c), 22);
+ EXPECT_EQ(b.find_last_not_of(a), StringPiece::npos);
+ EXPECT_EQ(b.find_last_not_of(b), StringPiece::npos);
+ EXPECT_EQ(f.find_last_not_of(i), 4);
+ EXPECT_EQ(a.find_last_not_of(c, 24), 22);
+ EXPECT_EQ(a.find_last_not_of(b, 3), 3);
+ EXPECT_EQ(a.find_last_not_of(b, 2), StringPiece::npos);
+ // empty string nonsense
+ EXPECT_EQ(f.find_last_not_of(d), f.size()-1);
+ EXPECT_EQ(f.find_last_not_of(e), f.size()-1);
+ EXPECT_EQ(f.find_last_not_of(d, 4), 4);
+ EXPECT_EQ(f.find_last_not_of(e, 4), 4);
+ EXPECT_EQ(d.find_last_not_of(d), StringPiece::npos);
+ EXPECT_EQ(d.find_last_not_of(e), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of(d), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of(e), StringPiece::npos);
+ EXPECT_EQ(d.find_last_not_of(f), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of(f), StringPiece::npos);
+ EXPECT_EQ(d.find_last_not_of(d, 4), StringPiece::npos);
+ EXPECT_EQ(d.find_last_not_of(e, 4), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of(d, 4), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of(e, 4), StringPiece::npos);
+ EXPECT_EQ(d.find_last_not_of(f, 4), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of(f, 4), StringPiece::npos);
+
+ EXPECT_EQ(h.find_last_not_of('x'), h.size() - 1);
+ EXPECT_EQ(h.find_last_not_of('='), StringPiece::npos);
+ EXPECT_EQ(b.find_last_not_of('c'), 1);
+ EXPECT_EQ(h.find_last_not_of('x', 2), 2);
+ EXPECT_EQ(h.find_last_not_of('=', 2), StringPiece::npos);
+ EXPECT_EQ(b.find_last_not_of('b', 1), 0);
+ // empty string nonsense
+ EXPECT_EQ(d.find_last_not_of('x'), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of('x'), StringPiece::npos);
+ EXPECT_EQ(d.find_last_not_of('\0'), StringPiece::npos);
+ EXPECT_EQ(e.find_last_not_of('\0'), StringPiece::npos);
+
+ EXPECT_EQ(a.substr(0, 3), b);
+ EXPECT_EQ(a.substr(23), c);
+ EXPECT_EQ(a.substr(23, 3), c);
+ EXPECT_EQ(a.substr(23, 99), c);
+ EXPECT_EQ(a.substr(0), a);
+ EXPECT_EQ(a.substr(3, 2), "de");
+ // empty string nonsense
+ EXPECT_EQ(a.substr(99, 2), e);
+ EXPECT_EQ(d.substr(99), e);
+ EXPECT_EQ(d.substr(0, 99), e);
+ EXPECT_EQ(d.substr(99, 99), e);
+ // use of npos
+ EXPECT_EQ(a.substr(0, StringPiece::npos), a);
+ EXPECT_EQ(a.substr(23, StringPiece::npos), c);
+ EXPECT_EQ(a.substr(StringPiece::npos, 0), e);
+ EXPECT_EQ(a.substr(StringPiece::npos, 1), e);
+ EXPECT_EQ(a.substr(StringPiece::npos, StringPiece::npos), e);
+
+ // Substring constructors.
+ EXPECT_EQ(StringPiece(a, 0, 3), b);
+ EXPECT_EQ(StringPiece(a, 23), c);
+ EXPECT_EQ(StringPiece(a, 23, 3), c);
+ EXPECT_EQ(StringPiece(a, 23, 99), c);
+ EXPECT_EQ(StringPiece(a, 0), a);
+ EXPECT_EQ(StringPiece(a, 3, 2), "de");
+ // empty string nonsense
+ EXPECT_EQ(StringPiece(d, 0, 99), e);
+ // Verify that they work taking an actual string, not just a StringPiece.
+ string a2 = a.as_string();
+ EXPECT_EQ(StringPiece(a2, 0, 3), b);
+ EXPECT_EQ(StringPiece(a2, 23), c);
+ EXPECT_EQ(StringPiece(a2, 23, 3), c);
+ EXPECT_EQ(StringPiece(a2, 23, 99), c);
+ EXPECT_EQ(StringPiece(a2, 0), a);
+ EXPECT_EQ(StringPiece(a2, 3, 2), "de");
+}
+
+TEST(StringPiece, Custom) {
+ StringPiece a("foobar");
+ string s1("123");
+ s1 += '\0';
+ s1 += "456";
+ StringPiece b(s1);
+ StringPiece e;
+ string s2;
+
+ // CopyToString
+ a.CopyToString(&s2);
+ EXPECT_EQ(s2.size(), 6);
+ EXPECT_EQ(s2, "foobar");
+ b.CopyToString(&s2);
+ EXPECT_EQ(s2.size(), 7);
+ EXPECT_EQ(s1, s2);
+ e.CopyToString(&s2);
+ EXPECT_TRUE(s2.empty());
+
+ // AppendToString
+ s2.erase();
+ a.AppendToString(&s2);
+ EXPECT_EQ(s2.size(), 6);
+ EXPECT_EQ(s2, "foobar");
+ a.AppendToString(&s2);
+ EXPECT_EQ(s2.size(), 12);
+ EXPECT_EQ(s2, "foobarfoobar");
+
+ // starts_with
+ EXPECT_TRUE(a.starts_with(a));
+ EXPECT_TRUE(a.starts_with("foo"));
+ EXPECT_TRUE(a.starts_with(e));
+ EXPECT_TRUE(b.starts_with(s1));
+ EXPECT_TRUE(b.starts_with(b));
+ EXPECT_TRUE(b.starts_with(e));
+ EXPECT_TRUE(e.starts_with(""));
+ EXPECT_TRUE(!a.starts_with(b));
+ EXPECT_TRUE(!b.starts_with(a));
+ EXPECT_TRUE(!e.starts_with(a));
+
+ // ends with
+ EXPECT_TRUE(a.ends_with(a));
+ EXPECT_TRUE(a.ends_with("bar"));
+ EXPECT_TRUE(a.ends_with(e));
+ EXPECT_TRUE(b.ends_with(s1));
+ EXPECT_TRUE(b.ends_with(b));
+ EXPECT_TRUE(b.ends_with(e));
+ EXPECT_TRUE(e.ends_with(""));
+ EXPECT_TRUE(!a.ends_with(b));
+ EXPECT_TRUE(!b.ends_with(a));
+ EXPECT_TRUE(!e.ends_with(a));
+
+ // remove_prefix
+ StringPiece c(a);
+ c.remove_prefix(3);
+ EXPECT_EQ(c, "bar");
+ c = a;
+ c.remove_prefix(0);
+ EXPECT_EQ(c, a);
+ c.remove_prefix(c.size());
+ EXPECT_EQ(c, e);
+
+ // remove_suffix
+ c = a;
+ c.remove_suffix(3);
+ EXPECT_EQ(c, "foo");
+ c = a;
+ c.remove_suffix(0);
+ EXPECT_EQ(c, a);
+ c.remove_suffix(c.size());
+ EXPECT_EQ(c, e);
+
+ // set
+ c.set("foobar", 6);
+ EXPECT_EQ(c, a);
+ c.set("foobar", 0);
+ EXPECT_EQ(c, e);
+ c.set("foobar", 7);
+ EXPECT_NE(c, a);
+
+ c.set("foobar");
+ EXPECT_EQ(c, a);
+
+ c.set(static_cast<const void*>("foobar"), 6);
+ EXPECT_EQ(c, a);
+ c.set(static_cast<const void*>("foobar"), 0);
+ EXPECT_EQ(c, e);
+ c.set(static_cast<const void*>("foobar"), 7);
+ EXPECT_NE(c, a);
+
+ // as_string
+ string s3(a.as_string().c_str(), 7);
+ EXPECT_EQ(c, s3);
+ string s4(e.as_string());
+ EXPECT_TRUE(s4.empty());
+
+ // ToString
+ {
+ string s5(a.ToString().c_str(), 7);
+ EXPECT_EQ(c, s5);
+ string s6(e.ToString());
+ EXPECT_TRUE(s6.empty());
+ }
+
+ // Consume
+ a.set("foobar");
+ EXPECT_TRUE(a.Consume("foo"));
+ EXPECT_EQ(a, "bar");
+ EXPECT_FALSE(a.Consume("foo"));
+ EXPECT_FALSE(a.Consume("barbar"));
+ EXPECT_FALSE(a.Consume("ar"));
+ EXPECT_EQ(a, "bar");
+
+ a.set("foobar");
+ EXPECT_TRUE(a.ConsumeFromEnd("bar"));
+ EXPECT_EQ(a, "foo");
+ EXPECT_FALSE(a.ConsumeFromEnd("bar"));
+ EXPECT_FALSE(a.ConsumeFromEnd("foofoo"));
+ EXPECT_FALSE(a.ConsumeFromEnd("fo"));
+ EXPECT_EQ(a, "foo");
+}
+
+TEST(StringPiece, Contains) {
+ StringPiece a("abcdefg");
+ StringPiece b("abcd");
+ StringPiece c("efg");
+ StringPiece d("gh");
+ EXPECT_TRUE(a.contains(b));
+ EXPECT_TRUE(a.contains(c));
+ EXPECT_TRUE(!a.contains(d));
+}
+
+TEST(StringPiece, NULLInput) {
+ // we used to crash here, but now we don't.
+ StringPiece s(NULL);
+ EXPECT_EQ(s.data(), (const char*)NULL);
+ EXPECT_EQ(s.size(), 0);
+
+ s.set(NULL);
+ EXPECT_EQ(s.data(), (const char*)NULL);
+ EXPECT_EQ(s.size(), 0);
+
+ // .ToString() on a StringPiece with NULL should produce the empty string.
+ EXPECT_EQ("", s.ToString());
+ EXPECT_EQ("", s.as_string());
+}
+
+TEST(StringPiece, Comparisons2) {
+ StringPiece abc("abcdefghijklmnopqrstuvwxyz");
+
+ // check comparison operations on strings longer than 4 bytes.
+ EXPECT_EQ(abc, StringPiece("abcdefghijklmnopqrstuvwxyz"));
+ EXPECT_EQ(abc.compare(StringPiece("abcdefghijklmnopqrstuvwxyz")), 0);
+
+ EXPECT_LT(abc, StringPiece("abcdefghijklmnopqrstuvwxzz"));
+ EXPECT_LT(abc.compare(StringPiece("abcdefghijklmnopqrstuvwxzz")), 0);
+
+ EXPECT_GT(abc, StringPiece("abcdefghijklmnopqrstuvwxyy"));
+ EXPECT_GT(abc.compare(StringPiece("abcdefghijklmnopqrstuvwxyy")), 0);
+
+ // starts_with
+ EXPECT_TRUE(abc.starts_with(abc));
+ EXPECT_TRUE(abc.starts_with("abcdefghijklm"));
+ EXPECT_TRUE(!abc.starts_with("abcdefguvwxyz"));
+
+ // ends_with
+ EXPECT_TRUE(abc.ends_with(abc));
+ EXPECT_TRUE(!abc.ends_with("abcdefguvwxyz"));
+ EXPECT_TRUE(abc.ends_with("nopqrstuvwxyz"));
+}
+
+TEST(ComparisonOpsTest, StringCompareNotAmbiguous) {
+ EXPECT_EQ("hello", string("hello"));
+ EXPECT_LT("hello", string("world"));
+}
+
+TEST(ComparisonOpsTest, HeterogenousStringPieceEquals) {
+ EXPECT_EQ(StringPiece("hello"), string("hello"));
+ EXPECT_EQ("hello", StringPiece("hello"));
+}
+
+TEST(FindOneCharTest, EdgeCases) {
+ StringPiece a("xxyyyxx");
+
+ // Set a = "xyyyx".
+ a.remove_prefix(1);
+ a.remove_suffix(1);
+
+ EXPECT_EQ(0, a.find('x'));
+ EXPECT_EQ(0, a.find('x', 0));
+ EXPECT_EQ(4, a.find('x', 1));
+ EXPECT_EQ(4, a.find('x', 4));
+ EXPECT_EQ(StringPiece::npos, a.find('x', 5));
+
+ EXPECT_EQ(4, a.rfind('x'));
+ EXPECT_EQ(4, a.rfind('x', 5));
+ EXPECT_EQ(4, a.rfind('x', 4));
+ EXPECT_EQ(0, a.rfind('x', 3));
+ EXPECT_EQ(0, a.rfind('x', 0));
+
+ // Set a = "yyy".
+ a.remove_prefix(1);
+ a.remove_suffix(1);
+
+ EXPECT_EQ(StringPiece::npos, a.find('x'));
+ EXPECT_EQ(StringPiece::npos, a.rfind('x'));
+}
+
+#ifndef NDEBUG
+TEST(NonNegativeLenTest, NonNegativeLen) {
+ EXPECT_DEATH(StringPiece("xyz", -1), "len >= 0");
+}
+#endif // ndef DEBUG
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.cc
new file mode 100644
index 0000000000..83fdfe454e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.cc
@@ -0,0 +1,174 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// from google3/base/stringprintf.cc
+
+#include <google/protobuf/stubs/stringprintf.h>
+
+#include <errno.h>
+#include <stdarg.h> // For va_list and related operations
+#include <stdio.h> // MSVC requires this for _vsnprintf
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+#ifdef _MSC_VER
+enum { IS_COMPILER_MSVC = 1 };
+#ifndef va_copy
+// Define va_copy for MSVC. This is a hack, assuming va_list is simply a
+// pointer into the stack and is safe to copy.
+#define va_copy(dest, src) ((dest) = (src))
+#endif
+#else
+enum { IS_COMPILER_MSVC = 0 };
+#endif
+
+void StringAppendV(string* dst, const char* format, va_list ap) {
+ // First try with a small fixed size buffer
+ static const int kSpaceLength = 1024;
+ char space[kSpaceLength];
+
+ // It's possible for methods that use a va_list to invalidate
+ // the data in it upon use. The fix is to make a copy
+ // of the structure before using it and use that copy instead.
+ va_list backup_ap;
+ va_copy(backup_ap, ap);
+ int result = vsnprintf(space, kSpaceLength, format, backup_ap);
+ va_end(backup_ap);
+
+ if (result < kSpaceLength) {
+ if (result >= 0) {
+ // Normal case -- everything fit.
+ dst->append(space, result);
+ return;
+ }
+
+ if (IS_COMPILER_MSVC) {
+ // Error or MSVC running out of space. MSVC 8.0 and higher
+ // can be asked about space needed with the special idiom below:
+ va_copy(backup_ap, ap);
+ result = vsnprintf(NULL, 0, format, backup_ap);
+ va_end(backup_ap);
+ }
+
+ if (result < 0) {
+ // Just an error.
+ return;
+ }
+ }
+
+ // Increase the buffer size to the size requested by vsnprintf,
+ // plus one for the closing \0.
+ int length = result+1;
+ char* buf = new char[length];
+
+ // Restore the va_list before we use it again
+ va_copy(backup_ap, ap);
+ result = vsnprintf(buf, length, format, backup_ap);
+ va_end(backup_ap);
+
+ if (result >= 0 && result < length) {
+ // It fit
+ dst->append(buf, result);
+ }
+ delete[] buf;
+}
+
+
+string StringPrintf(const char* format, ...) {
+ va_list ap;
+ va_start(ap, format);
+ string result;
+ StringAppendV(&result, format, ap);
+ va_end(ap);
+ return result;
+}
+
+const string& SStringPrintf(string* dst, const char* format, ...) {
+ va_list ap;
+ va_start(ap, format);
+ dst->clear();
+ StringAppendV(dst, format, ap);
+ va_end(ap);
+ return *dst;
+}
+
+void StringAppendF(string* dst, const char* format, ...) {
+ va_list ap;
+ va_start(ap, format);
+ StringAppendV(dst, format, ap);
+ va_end(ap);
+}
+
+// Max arguments supported by StringPrintVector
+const int kStringPrintfVectorMaxArgs = 32;
+
+// An empty block of zero for filler arguments. This is const so that if
+// printf tries to write to it (via %n) then the program gets a SIGSEGV
+// and we can fix the problem or protect against an attack.
+static const char string_printf_empty_block[256] = { '\0' };
+
+string StringPrintfVector(const char* format, const vector<string>& v) {
+ GOOGLE_CHECK_LE(v.size(), kStringPrintfVectorMaxArgs)
+ << "StringPrintfVector currently only supports up to "
+ << kStringPrintfVectorMaxArgs << " arguments. "
+ << "Feel free to add support for more if you need it.";
+
+ // Add filler arguments so that bogus format+args have a harder time
+ // crashing the program, corrupting the program (%n),
+ // or displaying random chunks of memory to users.
+
+ const char* cstr[kStringPrintfVectorMaxArgs];
+ for (int i = 0; i < v.size(); ++i) {
+ cstr[i] = v[i].c_str();
+ }
+ for (int i = v.size(); i < GOOGLE_ARRAYSIZE(cstr); ++i) {
+ cstr[i] = &string_printf_empty_block[0];
+ }
+
+ // I do not know any way to pass kStringPrintfVectorMaxArgs arguments,
+ // or any way to build a va_list by hand, or any API for printf
+ // that accepts an array of arguments. The best I can do is stick
+ // this COMPILE_ASSERT right next to the actual statement.
+
+ GOOGLE_COMPILE_ASSERT(kStringPrintfVectorMaxArgs == 32, arg_count_mismatch);
+ return StringPrintf(format,
+ cstr[0], cstr[1], cstr[2], cstr[3], cstr[4],
+ cstr[5], cstr[6], cstr[7], cstr[8], cstr[9],
+ cstr[10], cstr[11], cstr[12], cstr[13], cstr[14],
+ cstr[15], cstr[16], cstr[17], cstr[18], cstr[19],
+ cstr[20], cstr[21], cstr[22], cstr[23], cstr[24],
+ cstr[25], cstr[26], cstr[27], cstr[28], cstr[29],
+ cstr[30], cstr[31]);
+}
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.h
new file mode 100644
index 0000000000..ab1ab55832
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf.h
@@ -0,0 +1,76 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// from google3/base/stringprintf.h
+//
+// Printf variants that place their output in a C++ string.
+//
+// Usage:
+// string result = StringPrintf("%d %s\n", 10, "hello");
+// SStringPrintf(&result, "%d %s\n", 10, "hello");
+// StringAppendF(&result, "%d %s\n", 20, "there");
+
+#ifndef GOOGLE_PROTOBUF_STUBS_STRINGPRINTF_H
+#define GOOGLE_PROTOBUF_STUBS_STRINGPRINTF_H
+
+#include <stdarg.h>
+#include <string>
+#include <vector>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+// Return a C++ string
+LIBPROTOBUF_EXPORT extern string StringPrintf(const char* format, ...);
+
+// Store result into a supplied string and return it
+LIBPROTOBUF_EXPORT extern const string& SStringPrintf(string* dst, const char* format, ...);
+
+// Append result to a supplied string
+LIBPROTOBUF_EXPORT extern void StringAppendF(string* dst, const char* format, ...);
+
+// Lower-level routine that takes a va_list and appends to a specified
+// string. All other routines are just convenience wrappers around it.
+LIBPROTOBUF_EXPORT extern void StringAppendV(string* dst, const char* format, va_list ap);
+
+// The max arguments supported by StringPrintfVector
+LIBPROTOBUF_EXPORT extern const int kStringPrintfVectorMaxArgs;
+
+// You can use this version when all your arguments are strings, but
+// you don't know how many arguments you'll have at compile time.
+// StringPrintfVector will LOG(FATAL) if v.size() > kStringPrintfVectorMaxArgs
+LIBPROTOBUF_EXPORT extern string StringPrintfVector(const char* format, const vector<string>& v);
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_STRINGPRINTF_H
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf_unittest.cc
new file mode 100644
index 0000000000..15895e596c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/stringprintf_unittest.cc
@@ -0,0 +1,152 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2012 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.
+
+// from google3/base/stringprintf_unittest.cc
+
+#include <google/protobuf/stubs/stringprintf.h>
+
+#include <cerrno>
+#include <string>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+
+TEST(StringPrintfTest, Empty) {
+#if 0
+ // gcc 2.95.3, gcc 4.1.0, and gcc 4.2.2 all warn about this:
+ // warning: zero-length printf format string.
+ // so we do not allow them in google3.
+ EXPECT_EQ("", StringPrintf(""));
+#endif
+ EXPECT_EQ("", StringPrintf("%s", string().c_str()));
+ EXPECT_EQ("", StringPrintf("%s", ""));
+}
+
+TEST(StringPrintfTest, Misc) {
+// MSVC and mingw does not support $ format specifier.
+#if !defined(_MSC_VER) && !defined(__MINGW32__)
+ EXPECT_EQ("123hello w", StringPrintf("%3$d%2$s %1$c", 'w', "hello", 123));
+#endif // !_MSC_VER
+}
+
+TEST(StringAppendFTest, Empty) {
+ string value("Hello");
+ const char* empty = "";
+ StringAppendF(&value, "%s", empty);
+ EXPECT_EQ("Hello", value);
+}
+
+TEST(StringAppendFTest, EmptyString) {
+ string value("Hello");
+ StringAppendF(&value, "%s", "");
+ EXPECT_EQ("Hello", value);
+}
+
+TEST(StringAppendFTest, String) {
+ string value("Hello");
+ StringAppendF(&value, " %s", "World");
+ EXPECT_EQ("Hello World", value);
+}
+
+TEST(StringAppendFTest, Int) {
+ string value("Hello");
+ StringAppendF(&value, " %d", 123);
+ EXPECT_EQ("Hello 123", value);
+}
+
+TEST(StringPrintfTest, Multibyte) {
+ // If we are in multibyte mode and feed invalid multibyte sequence,
+ // StringPrintf should return an empty string instead of running
+ // out of memory while trying to determine destination buffer size.
+ // see b/4194543.
+
+ char* old_locale = setlocale(LC_CTYPE, NULL);
+ // Push locale with multibyte mode
+ setlocale(LC_CTYPE, "en_US.utf8");
+
+ const char kInvalidCodePoint[] = "\375\067s";
+ string value = StringPrintf("%.*s", 3, kInvalidCodePoint);
+
+ // In some versions of glibc (e.g. eglibc-2.11.1, aka GRTEv2), snprintf
+ // returns error given an invalid codepoint. Other versions
+ // (e.g. eglibc-2.15, aka pre-GRTEv3) emit the codepoint verbatim.
+ // We test that the output is one of the above.
+ EXPECT_TRUE(value.empty() || value == kInvalidCodePoint);
+
+ // Repeat with longer string, to make sure that the dynamically
+ // allocated path in StringAppendV is handled correctly.
+ int n = 2048;
+ char* buf = new char[n+1];
+ memset(buf, ' ', n-3);
+ memcpy(buf + n - 3, kInvalidCodePoint, 4);
+ value = StringPrintf("%.*s", n, buf);
+ // See GRTEv2 vs. GRTEv3 comment above.
+ EXPECT_TRUE(value.empty() || value == buf);
+ delete[] buf;
+
+ setlocale(LC_CTYPE, old_locale);
+}
+
+TEST(StringPrintfTest, NoMultibyte) {
+ // No multibyte handling, but the string contains funny chars.
+ char* old_locale = setlocale(LC_CTYPE, NULL);
+ setlocale(LC_CTYPE, "POSIX");
+ string value = StringPrintf("%.*s", 3, "\375\067s");
+ setlocale(LC_CTYPE, old_locale);
+ EXPECT_EQ("\375\067s", value);
+}
+
+TEST(StringPrintfTest, DontOverwriteErrno) {
+ // Check that errno isn't overwritten unless we're printing
+ // something significantly larger than what people are normally
+ // printing in their badly written PLOG() statements.
+ errno = ECHILD;
+ string value = StringPrintf("Hello, %s!", "World");
+ EXPECT_EQ(ECHILD, errno);
+}
+
+TEST(StringPrintfTest, LargeBuf) {
+ // Check that the large buffer is handled correctly.
+ int n = 2048;
+ char* buf = new char[n+1];
+ memset(buf, ' ', n);
+ buf[n] = 0;
+ string value = StringPrintf("%s", buf);
+ EXPECT_EQ(buf, value);
+ delete[] buf;
+}
+
+} // anonymous namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid.cc
new file mode 100644
index 0000000000..d79a6ee450
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid.cc
@@ -0,0 +1,588 @@
+// Copyright 2005-2008 Google Inc. All Rights Reserved.
+// Author: jrm@google.com (Jim Meehan)
+
+#include <google/protobuf/stubs/common.h>
+
+#include <google/protobuf/stubs/stringpiece.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// These four-byte entries compactly encode how many bytes 0..255 to delete
+// in making a string replacement, how many bytes to add 0..255, and the offset
+// 0..64k-1 of the replacement string in remap_string.
+struct RemapEntry {
+ uint8 delete_bytes;
+ uint8 add_bytes;
+ uint16 bytes_offset;
+};
+
+// Exit type codes for state tables. All but the first get stuffed into
+// signed one-byte entries. The first is only generated by executable code.
+// To distinguish from next-state entries, these must be contiguous and
+// all <= kExitNone
+typedef enum {
+ kExitDstSpaceFull = 239,
+ kExitIllegalStructure, // 240
+ kExitOK, // 241
+ kExitReject, // ...
+ kExitReplace1,
+ kExitReplace2,
+ kExitReplace3,
+ kExitReplace21,
+ kExitReplace31,
+ kExitReplace32,
+ kExitReplaceOffset1,
+ kExitReplaceOffset2,
+ kExitReplace1S0,
+ kExitSpecial,
+ kExitDoAgain,
+ kExitRejectAlt,
+ kExitNone // 255
+} ExitReason;
+
+
+// This struct represents one entire state table. The three initialized byte
+// areas are state_table, remap_base, and remap_string. state0 and state0_size
+// give the byte offset and length within state_table of the initial state --
+// table lookups are expected to start and end in this state, but for
+// truncated UTF-8 strings, may end in a different state. These allow a quick
+// test for that condition. entry_shift is 8 for tables subscripted by a full
+// byte value and 6 for space-optimized tables subscripted by only six
+// significant bits in UTF-8 continuation bytes.
+typedef struct {
+ const uint32 state0;
+ const uint32 state0_size;
+ const uint32 total_size;
+ const int max_expand;
+ const int entry_shift;
+ const int bytes_per_entry;
+ const uint32 losub;
+ const uint32 hiadd;
+ const uint8* state_table;
+ const RemapEntry* remap_base;
+ const uint8* remap_string;
+ const uint8* fast_state;
+} UTF8StateMachineObj;
+
+typedef UTF8StateMachineObj UTF8ScanObj;
+
+#define X__ (kExitIllegalStructure)
+#define RJ_ (kExitReject)
+#define S1_ (kExitReplace1)
+#define S2_ (kExitReplace2)
+#define S3_ (kExitReplace3)
+#define S21 (kExitReplace21)
+#define S31 (kExitReplace31)
+#define S32 (kExitReplace32)
+#define T1_ (kExitReplaceOffset1)
+#define T2_ (kExitReplaceOffset2)
+#define S11 (kExitReplace1S0)
+#define SP_ (kExitSpecial)
+#define D__ (kExitDoAgain)
+#define RJA (kExitRejectAlt)
+
+// Entire table has 9 state blocks of 256 entries each
+static const unsigned int utf8acceptnonsurrogates_STATE0 = 0; // state[0]
+static const unsigned int utf8acceptnonsurrogates_STATE0_SIZE = 256; // =[1]
+static const unsigned int utf8acceptnonsurrogates_TOTAL_SIZE = 2304;
+static const unsigned int utf8acceptnonsurrogates_MAX_EXPAND_X4 = 0;
+static const unsigned int utf8acceptnonsurrogates_SHIFT = 8;
+static const unsigned int utf8acceptnonsurrogates_BYTES = 1;
+static const unsigned int utf8acceptnonsurrogates_LOSUB = 0x20202020;
+static const unsigned int utf8acceptnonsurrogates_HIADD = 0x00000000;
+
+static const uint8 utf8acceptnonsurrogates[] = {
+// state[0] 0x000000 Byte 1
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 7, 3, 3,
+ 4, 5, 5, 5, 6, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[1] 0x000080 Byte 2 of 2
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[2] 0x000000 Byte 2 of 3
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[3] 0x001000 Byte 2 of 3
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[4] 0x000000 Byte 2 of 4
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[5] 0x040000 Byte 2 of 4
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[6] 0x100000 Byte 2 of 4
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[7] 0x00d000 Byte 2 of 3
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
+ 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+// state[8] 0x00d800 Byte 3 of 3
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+
+RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_,
+RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_,
+RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_,
+RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_, RJ_,
+
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__, X__,
+};
+
+// Remap base[0] = (del, add, string_offset)
+static const RemapEntry utf8acceptnonsurrogates_remap_base[] = {
+{0, 0, 0} };
+
+// Remap string[0]
+static const unsigned char utf8acceptnonsurrogates_remap_string[] = {
+0 };
+
+static const unsigned char utf8acceptnonsurrogates_fast[256] = {
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+};
+
+static const UTF8ScanObj utf8acceptnonsurrogates_obj = {
+ utf8acceptnonsurrogates_STATE0,
+ utf8acceptnonsurrogates_STATE0_SIZE,
+ utf8acceptnonsurrogates_TOTAL_SIZE,
+ utf8acceptnonsurrogates_MAX_EXPAND_X4,
+ utf8acceptnonsurrogates_SHIFT,
+ utf8acceptnonsurrogates_BYTES,
+ utf8acceptnonsurrogates_LOSUB,
+ utf8acceptnonsurrogates_HIADD,
+ utf8acceptnonsurrogates,
+ utf8acceptnonsurrogates_remap_base,
+ utf8acceptnonsurrogates_remap_string,
+ utf8acceptnonsurrogates_fast
+};
+
+
+#undef X__
+#undef RJ_
+#undef S1_
+#undef S2_
+#undef S3_
+#undef S21
+#undef S31
+#undef S32
+#undef T1_
+#undef T2_
+#undef S11
+#undef SP_
+#undef D__
+#undef RJA
+
+// Return true if current Tbl pointer is within state0 range
+// Note that unsigned compare checks both ends of range simultaneously
+static inline bool InStateZero(const UTF8ScanObj* st, const uint8* Tbl) {
+ const uint8* Tbl0 = &st->state_table[st->state0];
+ return (static_cast<uint32>(Tbl - Tbl0) < st->state0_size);
+}
+
+// Scan a UTF-8 string based on state table.
+// Always scan complete UTF-8 characters
+// Set number of bytes scanned. Return reason for exiting
+int UTF8GenericScan(const UTF8ScanObj* st,
+ const char * str,
+ int str_length,
+ int* bytes_consumed) {
+ *bytes_consumed = 0;
+ if (str_length == 0) return kExitOK;
+
+ int eshift = st->entry_shift;
+ const uint8* isrc = reinterpret_cast<const uint8*>(str);
+ const uint8* src = isrc;
+ const uint8* srclimit = isrc + str_length;
+ const uint8* srclimit8 = srclimit - 7;
+ const uint8* Tbl_0 = &st->state_table[st->state0];
+
+ DoAgain:
+ // Do state-table scan
+ int e = 0;
+ uint8 c;
+ const uint8* Tbl2 = &st->fast_state[0];
+ const uint32 losub = st->losub;
+ const uint32 hiadd = st->hiadd;
+ // Check initial few bytes one at a time until 8-byte aligned
+ //----------------------------
+ while ((((uintptr_t)src & 0x07) != 0) &&
+ (src < srclimit) &&
+ Tbl2[src[0]] == 0) {
+ src++;
+ }
+ if (((uintptr_t)src & 0x07) == 0) {
+ // Do fast for groups of 8 identity bytes.
+ // This covers a lot of 7-bit ASCII ~8x faster then the 1-byte loop,
+ // including slowing slightly on cr/lf/ht
+ //----------------------------
+ while (src < srclimit8) {
+ uint32 s0123 = (reinterpret_cast<const uint32 *>(src))[0];
+ uint32 s4567 = (reinterpret_cast<const uint32 *>(src))[1];
+ src += 8;
+ // This is a fast range check for all bytes in [lowsub..0x80-hiadd)
+ uint32 temp = (s0123 - losub) | (s0123 + hiadd) |
+ (s4567 - losub) | (s4567 + hiadd);
+ if ((temp & 0x80808080) != 0) {
+ // We typically end up here on cr/lf/ht; src was incremented
+ int e0123 = (Tbl2[src[-8]] | Tbl2[src[-7]]) |
+ (Tbl2[src[-6]] | Tbl2[src[-5]]);
+ if (e0123 != 0) {
+ src -= 8;
+ break;
+ } // Exit on Non-interchange
+ e0123 = (Tbl2[src[-4]] | Tbl2[src[-3]]) |
+ (Tbl2[src[-2]] | Tbl2[src[-1]]);
+ if (e0123 != 0) {
+ src -= 4;
+ break;
+ } // Exit on Non-interchange
+ // Else OK, go around again
+ }
+ }
+ }
+ //----------------------------
+
+ // Byte-at-a-time scan
+ //----------------------------
+ const uint8* Tbl = Tbl_0;
+ while (src < srclimit) {
+ c = *src;
+ e = Tbl[c];
+ src++;
+ if (e >= kExitIllegalStructure) {break;}
+ Tbl = &Tbl_0[e << eshift];
+ }
+ //----------------------------
+
+
+ // Exit posibilities:
+ // Some exit code, !state0, back up over last char
+ // Some exit code, state0, back up one byte exactly
+ // source consumed, !state0, back up over partial char
+ // source consumed, state0, exit OK
+ // For illegal byte in state0, avoid backup up over PREVIOUS char
+ // For truncated last char, back up to beginning of it
+
+ if (e >= kExitIllegalStructure) {
+ // Back up over exactly one byte of rejected/illegal UTF-8 character
+ src--;
+ // Back up more if needed
+ if (!InStateZero(st, Tbl)) {
+ do {
+ src--;
+ } while ((src > isrc) && ((src[0] & 0xc0) == 0x80));
+ }
+ } else if (!InStateZero(st, Tbl)) {
+ // Back up over truncated UTF-8 character
+ e = kExitIllegalStructure;
+ do {
+ src--;
+ } while ((src > isrc) && ((src[0] & 0xc0) == 0x80));
+ } else {
+ // Normal termination, source fully consumed
+ e = kExitOK;
+ }
+
+ if (e == kExitDoAgain) {
+ // Loop back up to the fast scan
+ goto DoAgain;
+ }
+
+ *bytes_consumed = src - isrc;
+ return e;
+}
+
+int UTF8GenericScanFastAscii(const UTF8ScanObj* st,
+ const char * str,
+ int str_length,
+ int* bytes_consumed) {
+ *bytes_consumed = 0;
+ if (str_length == 0) return kExitOK;
+
+ const uint8* isrc = reinterpret_cast<const uint8*>(str);
+ const uint8* src = isrc;
+ const uint8* srclimit = isrc + str_length;
+ const uint8* srclimit8 = srclimit - 7;
+ int n;
+ int rest_consumed;
+ int exit_reason;
+ do {
+ // Check initial few bytes one at a time until 8-byte aligned
+ while ((((uintptr_t)src & 0x07) != 0) &&
+ (src < srclimit) && (src[0] < 0x80)) {
+ src++;
+ }
+ if (((uintptr_t)src & 0x07) == 0) {
+ while ((src < srclimit8) &&
+ (((reinterpret_cast<const uint32*>(src)[0] |
+ reinterpret_cast<const uint32*>(src)[1]) & 0x80808080) == 0)) {
+ src += 8;
+ }
+ }
+ while ((src < srclimit) && (src[0] < 0x80)) {
+ src++;
+ }
+ // Run state table on the rest
+ n = src - isrc;
+ exit_reason = UTF8GenericScan(st, str + n, str_length - n, &rest_consumed);
+ src += rest_consumed;
+ } while ( exit_reason == kExitDoAgain );
+
+ *bytes_consumed = src - isrc;
+ return exit_reason;
+}
+
+// Hack: On some compilers the static tables are initialized at startup.
+// We can't use them until they are initialized. However, some Protocol
+// Buffer parsing happens at static init time and may try to validate
+// UTF-8 strings. Since UTF-8 validation is only used for debugging
+// anyway, we simply always return success if initialization hasn't
+// occurred yet.
+namespace {
+
+bool module_initialized_ = false;
+
+struct InitDetector {
+ InitDetector() {
+ module_initialized_ = true;
+ }
+};
+InitDetector init_detector;
+
+} // namespace
+
+bool IsStructurallyValidUTF8(const char* buf, int len) {
+ if (!module_initialized_) return true;
+
+ int bytes_consumed = 0;
+ UTF8GenericScanFastAscii(&utf8acceptnonsurrogates_obj,
+ buf, len, &bytes_consumed);
+ return (bytes_consumed == len);
+}
+
+int UTF8SpnStructurallyValid(const StringPiece& str) {
+ if (!module_initialized_) return str.size();
+
+ int bytes_consumed = 0;
+ UTF8GenericScanFastAscii(&utf8acceptnonsurrogates_obj,
+ str.data(), str.size(), &bytes_consumed);
+ return bytes_consumed;
+}
+
+// Coerce UTF-8 byte string in src_str to be
+// a structurally-valid equal-length string by selectively
+// overwriting illegal bytes with replace_char (typically blank).
+// replace_char must be legal printable 7-bit Ascii 0x20..0x7e.
+// src_str is read-only. If any overwriting is needed, a modified byte string
+// is created in idst, length isrclen.
+//
+// Returns pointer to output buffer, isrc if no changes were made,
+// or idst if some bytes were changed.
+//
+// Fast case: all is structurally valid and no byte copying is done.
+//
+char* UTF8CoerceToStructurallyValid(const StringPiece& src_str,
+ char* idst,
+ const char replace_char) {
+ const char* isrc = src_str.data();
+ const int len = src_str.length();
+ int n = UTF8SpnStructurallyValid(src_str);
+ if (n == len) { // Normal case -- all is cool, return
+ return const_cast<char*>(isrc);
+ } else { // Unusual case -- copy w/o bad bytes
+ const char* src = isrc;
+ const char* srclimit = isrc + len;
+ char* dst = idst;
+ memmove(dst, src, n); // Copy initial good chunk
+ src += n;
+ dst += n;
+ while (src < srclimit) { // src points to bogus byte or is off the end
+ dst[0] = replace_char; // replace one bad byte
+ src++;
+ dst++;
+ StringPiece str2(src, srclimit - src);
+ n = UTF8SpnStructurallyValid(str2); // scan the remainder
+ memmove(dst, src, n); // copy next good chunk
+ src += n;
+ dst += n;
+ }
+ }
+ return idst;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid_unittest.cc
new file mode 100644
index 0000000000..90888885ad
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/structurally_valid_unittest.cc
@@ -0,0 +1,40 @@
+// Copyright 2008 Google Inc. All Rights Reserved.
+// Author: xpeng@google.com (Peter Peng)
+
+#include <google/protobuf/stubs/common.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+namespace {
+
+TEST(StructurallyValidTest, ValidUTF8String) {
+ // On GCC, this string can be written as:
+ // "abcd 1234 - \u2014\u2013\u2212"
+ // MSVC seems to interpret \u differently.
+ string valid_str("abcd 1234 - \342\200\224\342\200\223\342\210\222 - xyz789");
+ EXPECT_TRUE(IsStructurallyValidUTF8(valid_str.data(),
+ valid_str.size()));
+ // Additional check for pointer alignment
+ for (int i = 1; i < 8; ++i) {
+ EXPECT_TRUE(IsStructurallyValidUTF8(valid_str.data() + i,
+ valid_str.size() - i));
+ }
+}
+
+TEST(StructurallyValidTest, InvalidUTF8String) {
+ const string invalid_str("abcd\xA0\xB0\xA0\xB0\xA0\xB0 - xyz789");
+ EXPECT_FALSE(IsStructurallyValidUTF8(invalid_str.data(),
+ invalid_str.size()));
+ // Additional check for pointer alignment
+ for (int i = 1; i < 8; ++i) {
+ EXPECT_FALSE(IsStructurallyValidUTF8(invalid_str.data() + i,
+ invalid_str.size() - i));
+ }
+}
+
+} // namespace
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.cc
new file mode 100644
index 0000000000..7ba92e8f1f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.cc
@@ -0,0 +1,2289 @@
+// 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.
+
+// from google3/strings/strutil.cc
+
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/mathlimits.h>
+
+#include <errno.h>
+#include <float.h> // FLT_DIG and DBL_DIG
+#include <limits>
+#include <limits.h>
+#include <stdio.h>
+#include <iterator>
+
+#include <google/protobuf/stubs/stl_util.h>
+
+#ifdef _WIN32
+// MSVC has only _snprintf, not snprintf.
+//
+// MinGW has both snprintf and _snprintf, but they appear to be different
+// functions. The former is buggy. When invoked like so:
+// char buffer[32];
+// snprintf(buffer, 32, "%.*g\n", FLT_DIG, 1.23e10f);
+// it prints "1.23000e+10". This is plainly wrong: %g should never print
+// trailing zeros after the decimal point. For some reason this bug only
+// occurs with some input values, not all. In any case, _snprintf does the
+// right thing, so we use it.
+#define snprintf _snprintf
+#endif
+
+namespace google {
+namespace protobuf {
+
+// These are defined as macros on some platforms. #undef them so that we can
+// redefine them.
+#undef isxdigit
+#undef isprint
+
+// The definitions of these in ctype.h change based on locale. Since our
+// string manipulation is all in relation to the protocol buffer and C++
+// languages, we always want to use the C locale. So, we re-define these
+// exactly as we want them.
+inline bool isxdigit(char c) {
+ return ('0' <= c && c <= '9') ||
+ ('a' <= c && c <= 'f') ||
+ ('A' <= c && c <= 'F');
+}
+
+inline bool isprint(char c) {
+ return c >= 0x20 && c <= 0x7E;
+}
+
+// ----------------------------------------------------------------------
+// StripString
+// Replaces any occurrence of the character 'remove' (or the characters
+// in 'remove') with the character 'replacewith'.
+// ----------------------------------------------------------------------
+void StripString(string* s, const char* remove, char replacewith) {
+ const char * str_start = s->c_str();
+ const char * str = str_start;
+ for (str = strpbrk(str, remove);
+ str != NULL;
+ str = strpbrk(str + 1, remove)) {
+ (*s)[str - str_start] = replacewith;
+ }
+}
+
+void StripWhitespace(string* str) {
+ int str_length = str->length();
+
+ // Strip off leading whitespace.
+ int first = 0;
+ while (first < str_length && ascii_isspace(str->at(first))) {
+ ++first;
+ }
+ // If entire string is white space.
+ if (first == str_length) {
+ str->clear();
+ return;
+ }
+ if (first > 0) {
+ str->erase(0, first);
+ str_length -= first;
+ }
+
+ // Strip off trailing whitespace.
+ int last = str_length - 1;
+ while (last >= 0 && ascii_isspace(str->at(last))) {
+ --last;
+ }
+ if (last != (str_length - 1) && last >= 0) {
+ str->erase(last + 1, string::npos);
+ }
+}
+
+// ----------------------------------------------------------------------
+// StringReplace()
+// Replace the "old" pattern with the "new" pattern in a string,
+// and append the result to "res". If replace_all is false,
+// it only replaces the first instance of "old."
+// ----------------------------------------------------------------------
+
+void StringReplace(const string& s, const string& oldsub,
+ const string& newsub, bool replace_all,
+ string* res) {
+ if (oldsub.empty()) {
+ res->append(s); // if empty, append the given string.
+ return;
+ }
+
+ string::size_type start_pos = 0;
+ string::size_type pos;
+ do {
+ pos = s.find(oldsub, start_pos);
+ if (pos == string::npos) {
+ break;
+ }
+ res->append(s, start_pos, pos - start_pos);
+ res->append(newsub);
+ start_pos = pos + oldsub.size(); // start searching again after the "old"
+ } while (replace_all);
+ res->append(s, start_pos, s.length() - start_pos);
+}
+
+// ----------------------------------------------------------------------
+// StringReplace()
+// Give me a string and two patterns "old" and "new", and I replace
+// the first instance of "old" in the string with "new", if it
+// exists. If "global" is true; call this repeatedly until it
+// fails. RETURN a new string, regardless of whether the replacement
+// happened or not.
+// ----------------------------------------------------------------------
+
+string StringReplace(const string& s, const string& oldsub,
+ const string& newsub, bool replace_all) {
+ string ret;
+ StringReplace(s, oldsub, newsub, replace_all, &ret);
+ return ret;
+}
+
+// ----------------------------------------------------------------------
+// SplitStringUsing()
+// Split a string using a character delimiter. Append the components
+// to 'result'.
+//
+// Note: For multi-character delimiters, this routine will split on *ANY* of
+// the characters in the string, not the entire string as a single delimiter.
+// ----------------------------------------------------------------------
+template <typename ITR>
+static inline
+void SplitStringToIteratorUsing(const string& full,
+ const char* delim,
+ ITR& result) {
+ // Optimize the common case where delim is a single character.
+ if (delim[0] != '\0' && delim[1] == '\0') {
+ char c = delim[0];
+ const char* p = full.data();
+ const char* end = p + full.size();
+ while (p != end) {
+ if (*p == c) {
+ ++p;
+ } else {
+ const char* start = p;
+ while (++p != end && *p != c);
+ *result++ = string(start, p - start);
+ }
+ }
+ return;
+ }
+
+ string::size_type begin_index, end_index;
+ begin_index = full.find_first_not_of(delim);
+ while (begin_index != string::npos) {
+ end_index = full.find_first_of(delim, begin_index);
+ if (end_index == string::npos) {
+ *result++ = full.substr(begin_index);
+ return;
+ }
+ *result++ = full.substr(begin_index, (end_index - begin_index));
+ begin_index = full.find_first_not_of(delim, end_index);
+ }
+}
+
+void SplitStringUsing(const string& full,
+ const char* delim,
+ vector<string>* result) {
+ back_insert_iterator< vector<string> > it(*result);
+ SplitStringToIteratorUsing(full, delim, it);
+}
+
+// Split a string using a character delimiter. Append the components
+// to 'result'. If there are consecutive delimiters, this function
+// will return corresponding empty strings. The string is split into
+// at most the specified number of pieces greedily. This means that the
+// last piece may possibly be split further. To split into as many pieces
+// as possible, specify 0 as the number of pieces.
+//
+// If "full" is the empty string, yields an empty string as the only value.
+//
+// If "pieces" is negative for some reason, it returns the whole string
+// ----------------------------------------------------------------------
+template <typename StringType, typename ITR>
+static inline
+void SplitStringToIteratorAllowEmpty(const StringType& full,
+ const char* delim,
+ int pieces,
+ ITR& result) {
+ string::size_type begin_index, end_index;
+ begin_index = 0;
+
+ for (int i = 0; (i < pieces-1) || (pieces == 0); i++) {
+ end_index = full.find_first_of(delim, begin_index);
+ if (end_index == string::npos) {
+ *result++ = full.substr(begin_index);
+ return;
+ }
+ *result++ = full.substr(begin_index, (end_index - begin_index));
+ begin_index = end_index + 1;
+ }
+ *result++ = full.substr(begin_index);
+}
+
+void SplitStringAllowEmpty(const string& full, const char* delim,
+ vector<string>* result) {
+ back_insert_iterator<vector<string> > it(*result);
+ SplitStringToIteratorAllowEmpty(full, delim, 0, it);
+}
+
+// ----------------------------------------------------------------------
+// JoinStrings()
+// This merges a vector of string components with delim inserted
+// as separaters between components.
+//
+// ----------------------------------------------------------------------
+template <class ITERATOR>
+static void JoinStringsIterator(const ITERATOR& start,
+ const ITERATOR& end,
+ const char* delim,
+ string* result) {
+ GOOGLE_CHECK(result != NULL);
+ result->clear();
+ int delim_length = strlen(delim);
+
+ // Precompute resulting length so we can reserve() memory in one shot.
+ int length = 0;
+ for (ITERATOR iter = start; iter != end; ++iter) {
+ if (iter != start) {
+ length += delim_length;
+ }
+ length += iter->size();
+ }
+ result->reserve(length);
+
+ // Now combine everything.
+ for (ITERATOR iter = start; iter != end; ++iter) {
+ if (iter != start) {
+ result->append(delim, delim_length);
+ }
+ result->append(iter->data(), iter->size());
+ }
+}
+
+void JoinStrings(const vector<string>& components,
+ const char* delim,
+ string * result) {
+ JoinStringsIterator(components.begin(), components.end(), delim, result);
+}
+
+// ----------------------------------------------------------------------
+// UnescapeCEscapeSequences()
+// This does all the unescaping that C does: \ooo, \r, \n, etc
+// Returns length of resulting string.
+// The implementation of \x parses any positive number of hex digits,
+// but it is an error if the value requires more than 8 bits, and the
+// result is truncated to 8 bits.
+//
+// The second call stores its errors in a supplied string vector.
+// If the string vector pointer is NULL, it reports the errors with LOG().
+// ----------------------------------------------------------------------
+
+#define IS_OCTAL_DIGIT(c) (((c) >= '0') && ((c) <= '7'))
+
+// Protocol buffers doesn't ever care about errors, but I don't want to remove
+// the code.
+#define LOG_STRING(LEVEL, VECTOR) GOOGLE_LOG_IF(LEVEL, false)
+
+int UnescapeCEscapeSequences(const char* source, char* dest) {
+ return UnescapeCEscapeSequences(source, dest, NULL);
+}
+
+int UnescapeCEscapeSequences(const char* source, char* dest,
+ vector<string> *errors) {
+ GOOGLE_DCHECK(errors == NULL) << "Error reporting not implemented.";
+
+ char* d = dest;
+ const char* p = source;
+
+ // Small optimization for case where source = dest and there's no escaping
+ while ( p == d && *p != '\0' && *p != '\\' )
+ p++, d++;
+
+ while (*p != '\0') {
+ if (*p != '\\') {
+ *d++ = *p++;
+ } else {
+ switch ( *++p ) { // skip past the '\\'
+ case '\0':
+ LOG_STRING(ERROR, errors) << "String cannot end with \\";
+ *d = '\0';
+ return d - dest; // we're done with p
+ case 'a': *d++ = '\a'; break;
+ case 'b': *d++ = '\b'; break;
+ case 'f': *d++ = '\f'; break;
+ case 'n': *d++ = '\n'; break;
+ case 'r': *d++ = '\r'; break;
+ case 't': *d++ = '\t'; break;
+ case 'v': *d++ = '\v'; break;
+ case '\\': *d++ = '\\'; break;
+ case '?': *d++ = '\?'; break; // \? Who knew?
+ case '\'': *d++ = '\''; break;
+ case '"': *d++ = '\"'; break;
+ case '0': case '1': case '2': case '3': // octal digit: 1 to 3 digits
+ case '4': case '5': case '6': case '7': {
+ char ch = *p - '0';
+ if ( IS_OCTAL_DIGIT(p[1]) )
+ ch = ch * 8 + *++p - '0';
+ if ( IS_OCTAL_DIGIT(p[1]) ) // safe (and easy) to do this twice
+ ch = ch * 8 + *++p - '0'; // now points at last digit
+ *d++ = ch;
+ break;
+ }
+ case 'x': case 'X': {
+ if (!isxdigit(p[1])) {
+ if (p[1] == '\0') {
+ LOG_STRING(ERROR, errors) << "String cannot end with \\x";
+ } else {
+ LOG_STRING(ERROR, errors) <<
+ "\\x cannot be followed by non-hex digit: \\" << *p << p[1];
+ }
+ break;
+ }
+ unsigned int ch = 0;
+ const char *hex_start = p;
+ while (isxdigit(p[1])) // arbitrarily many hex digits
+ ch = (ch << 4) + hex_digit_to_int(*++p);
+ if (ch > 0xFF)
+ LOG_STRING(ERROR, errors) << "Value of " <<
+ "\\" << string(hex_start, p+1-hex_start) << " exceeds 8 bits";
+ *d++ = ch;
+ break;
+ }
+#if 0 // TODO(kenton): Support \u and \U? Requires runetochar().
+ case 'u': {
+ // \uhhhh => convert 4 hex digits to UTF-8
+ char32 rune = 0;
+ const char *hex_start = p;
+ for (int i = 0; i < 4; ++i) {
+ if (isxdigit(p[1])) { // Look one char ahead.
+ rune = (rune << 4) + hex_digit_to_int(*++p); // Advance p.
+ } else {
+ LOG_STRING(ERROR, errors)
+ << "\\u must be followed by 4 hex digits: \\"
+ << string(hex_start, p+1-hex_start);
+ break;
+ }
+ }
+ d += runetochar(d, &rune);
+ break;
+ }
+ case 'U': {
+ // \Uhhhhhhhh => convert 8 hex digits to UTF-8
+ char32 rune = 0;
+ const char *hex_start = p;
+ for (int i = 0; i < 8; ++i) {
+ if (isxdigit(p[1])) { // Look one char ahead.
+ // Don't change rune until we're sure this
+ // is within the Unicode limit, but do advance p.
+ char32 newrune = (rune << 4) + hex_digit_to_int(*++p);
+ if (newrune > 0x10FFFF) {
+ LOG_STRING(ERROR, errors)
+ << "Value of \\"
+ << string(hex_start, p + 1 - hex_start)
+ << " exceeds Unicode limit (0x10FFFF)";
+ break;
+ } else {
+ rune = newrune;
+ }
+ } else {
+ LOG_STRING(ERROR, errors)
+ << "\\U must be followed by 8 hex digits: \\"
+ << string(hex_start, p+1-hex_start);
+ break;
+ }
+ }
+ d += runetochar(d, &rune);
+ break;
+ }
+#endif
+ default:
+ LOG_STRING(ERROR, errors) << "Unknown escape sequence: \\" << *p;
+ }
+ p++; // read past letter we escaped
+ }
+ }
+ *d = '\0';
+ return d - dest;
+}
+
+// ----------------------------------------------------------------------
+// UnescapeCEscapeString()
+// This does the same thing as UnescapeCEscapeSequences, but creates
+// a new string. The caller does not need to worry about allocating
+// a dest buffer. This should be used for non performance critical
+// tasks such as printing debug messages. It is safe for src and dest
+// to be the same.
+//
+// The second call stores its errors in a supplied string vector.
+// If the string vector pointer is NULL, it reports the errors with LOG().
+//
+// In the first and second calls, the length of dest is returned. In the
+// the third call, the new string is returned.
+// ----------------------------------------------------------------------
+int UnescapeCEscapeString(const string& src, string* dest) {
+ return UnescapeCEscapeString(src, dest, NULL);
+}
+
+int UnescapeCEscapeString(const string& src, string* dest,
+ vector<string> *errors) {
+ scoped_array<char> unescaped(new char[src.size() + 1]);
+ int len = UnescapeCEscapeSequences(src.c_str(), unescaped.get(), errors);
+ GOOGLE_CHECK(dest);
+ dest->assign(unescaped.get(), len);
+ return len;
+}
+
+string UnescapeCEscapeString(const string& src) {
+ scoped_array<char> unescaped(new char[src.size() + 1]);
+ int len = UnescapeCEscapeSequences(src.c_str(), unescaped.get(), NULL);
+ return string(unescaped.get(), len);
+}
+
+// ----------------------------------------------------------------------
+// CEscapeString()
+// CHexEscapeString()
+// Copies 'src' to 'dest', escaping dangerous characters using
+// C-style escape sequences. This is very useful for preparing query
+// flags. 'src' and 'dest' should not overlap. The 'Hex' version uses
+// hexadecimal rather than octal sequences.
+// Returns the number of bytes written to 'dest' (not including the \0)
+// or -1 if there was insufficient space.
+//
+// Currently only \n, \r, \t, ", ', \ and !isprint() chars are escaped.
+// ----------------------------------------------------------------------
+int CEscapeInternal(const char* src, int src_len, char* dest,
+ int dest_len, bool use_hex, bool utf8_safe) {
+ const char* src_end = src + src_len;
+ int used = 0;
+ bool last_hex_escape = false; // true if last output char was \xNN
+
+ for (; src < src_end; src++) {
+ if (dest_len - used < 2) // Need space for two letter escape
+ return -1;
+
+ bool is_hex_escape = false;
+ switch (*src) {
+ case '\n': dest[used++] = '\\'; dest[used++] = 'n'; break;
+ case '\r': dest[used++] = '\\'; dest[used++] = 'r'; break;
+ case '\t': dest[used++] = '\\'; dest[used++] = 't'; break;
+ case '\"': dest[used++] = '\\'; dest[used++] = '\"'; break;
+ case '\'': dest[used++] = '\\'; dest[used++] = '\''; break;
+ case '\\': dest[used++] = '\\'; dest[used++] = '\\'; break;
+ default:
+ // Note that if we emit \xNN and the src character after that is a hex
+ // digit then that digit must be escaped too to prevent it being
+ // interpreted as part of the character code by C.
+ if ((!utf8_safe || static_cast<uint8>(*src) < 0x80) &&
+ (!isprint(*src) ||
+ (last_hex_escape && isxdigit(*src)))) {
+ if (dest_len - used < 4) // need space for 4 letter escape
+ return -1;
+ sprintf(dest + used, (use_hex ? "\\x%02x" : "\\%03o"),
+ static_cast<uint8>(*src));
+ is_hex_escape = use_hex;
+ used += 4;
+ } else {
+ dest[used++] = *src; break;
+ }
+ }
+ last_hex_escape = is_hex_escape;
+ }
+
+ if (dest_len - used < 1) // make sure that there is room for \0
+ return -1;
+
+ dest[used] = '\0'; // doesn't count towards return value though
+ return used;
+}
+
+// Calculates the length of the C-style escaped version of 'src'.
+// Assumes that non-printable characters are escaped using octal sequences, and
+// that UTF-8 bytes are not handled specially.
+static inline size_t CEscapedLength(StringPiece src) {
+ static char c_escaped_len[256] = {
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2, 4, 4, 2, 4, 4, // \t, \n, \r
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 1, 1, 2, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, // ", '
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // '0'..'9'
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 'A'..'O'
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, // 'P'..'Z', '\'
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 'a'..'o'
+ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 4, // 'p'..'z', DEL
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
+ };
+
+ size_t escaped_len = 0;
+ for (int i = 0; i < src.size(); ++i) {
+ unsigned char c = static_cast<unsigned char>(src[i]);
+ escaped_len += c_escaped_len[c];
+ }
+ return escaped_len;
+}
+
+// ----------------------------------------------------------------------
+// Escapes 'src' using C-style escape sequences, and appends the escaped string
+// to 'dest'. This version is faster than calling CEscapeInternal as it computes
+// the required space using a lookup table, and also does not do any special
+// handling for Hex or UTF-8 characters.
+// ----------------------------------------------------------------------
+void CEscapeAndAppend(StringPiece src, string* dest) {
+ size_t escaped_len = CEscapedLength(src);
+ if (escaped_len == src.size()) {
+ dest->append(src.data(), src.size());
+ return;
+ }
+
+ size_t cur_dest_len = dest->size();
+ dest->resize(cur_dest_len + escaped_len);
+ char* append_ptr = &(*dest)[cur_dest_len];
+
+ for (int i = 0; i < src.size(); ++i) {
+ unsigned char c = static_cast<unsigned char>(src[i]);
+ switch (c) {
+ case '\n': *append_ptr++ = '\\'; *append_ptr++ = 'n'; break;
+ case '\r': *append_ptr++ = '\\'; *append_ptr++ = 'r'; break;
+ case '\t': *append_ptr++ = '\\'; *append_ptr++ = 't'; break;
+ case '\"': *append_ptr++ = '\\'; *append_ptr++ = '\"'; break;
+ case '\'': *append_ptr++ = '\\'; *append_ptr++ = '\''; break;
+ case '\\': *append_ptr++ = '\\'; *append_ptr++ = '\\'; break;
+ default:
+ if (!isprint(c)) {
+ *append_ptr++ = '\\';
+ *append_ptr++ = '0' + c / 64;
+ *append_ptr++ = '0' + (c % 64) / 8;
+ *append_ptr++ = '0' + c % 8;
+ } else {
+ *append_ptr++ = c;
+ }
+ break;
+ }
+ }
+}
+
+string CEscape(const string& src) {
+ string dest;
+ CEscapeAndAppend(src, &dest);
+ return dest;
+}
+
+namespace strings {
+
+string Utf8SafeCEscape(const string& src) {
+ const int dest_length = src.size() * 4 + 1; // Maximum possible expansion
+ scoped_array<char> dest(new char[dest_length]);
+ const int len = CEscapeInternal(src.data(), src.size(),
+ dest.get(), dest_length, false, true);
+ GOOGLE_DCHECK_GE(len, 0);
+ return string(dest.get(), len);
+}
+
+string CHexEscape(const string& src) {
+ const int dest_length = src.size() * 4 + 1; // Maximum possible expansion
+ scoped_array<char> dest(new char[dest_length]);
+ const int len = CEscapeInternal(src.data(), src.size(),
+ dest.get(), dest_length, true, false);
+ GOOGLE_DCHECK_GE(len, 0);
+ return string(dest.get(), len);
+}
+
+} // namespace strings
+
+// ----------------------------------------------------------------------
+// strto32_adaptor()
+// strtou32_adaptor()
+// Implementation of strto[u]l replacements that have identical
+// overflow and underflow characteristics for both ILP-32 and LP-64
+// platforms, including errno preservation in error-free calls.
+// ----------------------------------------------------------------------
+
+int32 strto32_adaptor(const char *nptr, char **endptr, int base) {
+ const int saved_errno = errno;
+ errno = 0;
+ const long result = strtol(nptr, endptr, base);
+ if (errno == ERANGE && result == LONG_MIN) {
+ return kint32min;
+ } else if (errno == ERANGE && result == LONG_MAX) {
+ return kint32max;
+ } else if (errno == 0 && result < kint32min) {
+ errno = ERANGE;
+ return kint32min;
+ } else if (errno == 0 && result > kint32max) {
+ errno = ERANGE;
+ return kint32max;
+ }
+ if (errno == 0)
+ errno = saved_errno;
+ return static_cast<int32>(result);
+}
+
+uint32 strtou32_adaptor(const char *nptr, char **endptr, int base) {
+ const int saved_errno = errno;
+ errno = 0;
+ const unsigned long result = strtoul(nptr, endptr, base);
+ if (errno == ERANGE && result == ULONG_MAX) {
+ return kuint32max;
+ } else if (errno == 0 && result > kuint32max) {
+ errno = ERANGE;
+ return kuint32max;
+ }
+ if (errno == 0)
+ errno = saved_errno;
+ return static_cast<uint32>(result);
+}
+
+inline bool safe_parse_sign(string* text /*inout*/,
+ bool* negative_ptr /*output*/) {
+ const char* start = text->data();
+ const char* end = start + text->size();
+
+ // Consume whitespace.
+ while (start < end && (start[0] == ' ')) {
+ ++start;
+ }
+ while (start < end && (end[-1] == ' ')) {
+ --end;
+ }
+ if (start >= end) {
+ return false;
+ }
+
+ // Consume sign.
+ *negative_ptr = (start[0] == '-');
+ if (*negative_ptr || start[0] == '+') {
+ ++start;
+ if (start >= end) {
+ return false;
+ }
+ }
+ *text = text->substr(start - text->data(), end - start);
+ return true;
+}
+
+template<typename IntType>
+bool safe_parse_positive_int(
+ string text, IntType* value_p) {
+ int base = 10;
+ IntType value = 0;
+ const IntType vmax = std::numeric_limits<IntType>::max();
+ assert(vmax > 0);
+ assert(vmax >= base);
+ const IntType vmax_over_base = vmax / base;
+ const char* start = text.data();
+ const char* end = start + text.size();
+ // loop over digits
+ for (; start < end; ++start) {
+ unsigned char c = static_cast<unsigned char>(start[0]);
+ int digit = c - '0';
+ if (digit >= base || digit < 0) {
+ *value_p = value;
+ return false;
+ }
+ if (value > vmax_over_base) {
+ *value_p = vmax;
+ return false;
+ }
+ value *= base;
+ if (value > vmax - digit) {
+ *value_p = vmax;
+ return false;
+ }
+ value += digit;
+ }
+ *value_p = value;
+ return true;
+}
+
+template<typename IntType>
+bool safe_parse_negative_int(
+ const string& text, IntType* value_p) {
+ int base = 10;
+ IntType value = 0;
+ const IntType vmin = std::numeric_limits<IntType>::min();
+ assert(vmin < 0);
+ assert(vmin <= 0 - base);
+ IntType vmin_over_base = vmin / base;
+ // 2003 c++ standard [expr.mul]
+ // "... the sign of the remainder is implementation-defined."
+ // Although (vmin/base)*base + vmin%base is always vmin.
+ // 2011 c++ standard tightens the spec but we cannot rely on it.
+ if (vmin % base > 0) {
+ vmin_over_base += 1;
+ }
+ const char* start = text.data();
+ const char* end = start + text.size();
+ // loop over digits
+ for (; start < end; ++start) {
+ unsigned char c = static_cast<unsigned char>(start[0]);
+ int digit = c - '0';
+ if (digit >= base || digit < 0) {
+ *value_p = value;
+ return false;
+ }
+ if (value < vmin_over_base) {
+ *value_p = vmin;
+ return false;
+ }
+ value *= base;
+ if (value < vmin + digit) {
+ *value_p = vmin;
+ return false;
+ }
+ value -= digit;
+ }
+ *value_p = value;
+ return true;
+}
+
+template<typename IntType>
+bool safe_int_internal(string text, IntType* value_p) {
+ *value_p = 0;
+ bool negative;
+ if (!safe_parse_sign(&text, &negative)) {
+ return false;
+ }
+ if (!negative) {
+ return safe_parse_positive_int(text, value_p);
+ } else {
+ return safe_parse_negative_int(text, value_p);
+ }
+}
+
+template<typename IntType>
+bool safe_uint_internal(string text, IntType* value_p) {
+ *value_p = 0;
+ bool negative;
+ if (!safe_parse_sign(&text, &negative) || negative) {
+ return false;
+ }
+ return safe_parse_positive_int(text, value_p);
+}
+
+// ----------------------------------------------------------------------
+// FastIntToBuffer()
+// FastInt64ToBuffer()
+// FastHexToBuffer()
+// FastHex64ToBuffer()
+// FastHex32ToBuffer()
+// ----------------------------------------------------------------------
+
+// Offset into buffer where FastInt64ToBuffer places the end of string
+// null character. Also used by FastInt64ToBufferLeft.
+static const int kFastInt64ToBufferOffset = 21;
+
+char *FastInt64ToBuffer(int64 i, char* buffer) {
+ // We could collapse the positive and negative sections, but that
+ // would be slightly slower for positive numbers...
+ // 22 bytes is enough to store -2**64, -18446744073709551616.
+ char* p = buffer + kFastInt64ToBufferOffset;
+ *p-- = '\0';
+ if (i >= 0) {
+ do {
+ *p-- = '0' + i % 10;
+ i /= 10;
+ } while (i > 0);
+ return p + 1;
+ } else {
+ // On different platforms, % and / have different behaviors for
+ // negative numbers, so we need to jump through hoops to make sure
+ // we don't divide negative numbers.
+ if (i > -10) {
+ i = -i;
+ *p-- = '0' + i;
+ *p = '-';
+ return p;
+ } else {
+ // Make sure we aren't at MIN_INT, in which case we can't say i = -i
+ i = i + 10;
+ i = -i;
+ *p-- = '0' + i % 10;
+ // Undo what we did a moment ago
+ i = i / 10 + 1;
+ do {
+ *p-- = '0' + i % 10;
+ i /= 10;
+ } while (i > 0);
+ *p = '-';
+ return p;
+ }
+ }
+}
+
+// Offset into buffer where FastInt32ToBuffer places the end of string
+// null character. Also used by FastInt32ToBufferLeft
+static const int kFastInt32ToBufferOffset = 11;
+
+// Yes, this is a duplicate of FastInt64ToBuffer. But, we need this for the
+// compiler to generate 32 bit arithmetic instructions. It's much faster, at
+// least with 32 bit binaries.
+char *FastInt32ToBuffer(int32 i, char* buffer) {
+ // We could collapse the positive and negative sections, but that
+ // would be slightly slower for positive numbers...
+ // 12 bytes is enough to store -2**32, -4294967296.
+ char* p = buffer + kFastInt32ToBufferOffset;
+ *p-- = '\0';
+ if (i >= 0) {
+ do {
+ *p-- = '0' + i % 10;
+ i /= 10;
+ } while (i > 0);
+ return p + 1;
+ } else {
+ // On different platforms, % and / have different behaviors for
+ // negative numbers, so we need to jump through hoops to make sure
+ // we don't divide negative numbers.
+ if (i > -10) {
+ i = -i;
+ *p-- = '0' + i;
+ *p = '-';
+ return p;
+ } else {
+ // Make sure we aren't at MIN_INT, in which case we can't say i = -i
+ i = i + 10;
+ i = -i;
+ *p-- = '0' + i % 10;
+ // Undo what we did a moment ago
+ i = i / 10 + 1;
+ do {
+ *p-- = '0' + i % 10;
+ i /= 10;
+ } while (i > 0);
+ *p = '-';
+ return p;
+ }
+ }
+}
+
+char *FastHexToBuffer(int i, char* buffer) {
+ GOOGLE_CHECK(i >= 0) << "FastHexToBuffer() wants non-negative integers, not " << i;
+
+ static const char *hexdigits = "0123456789abcdef";
+ char *p = buffer + 21;
+ *p-- = '\0';
+ do {
+ *p-- = hexdigits[i & 15]; // mod by 16
+ i >>= 4; // divide by 16
+ } while (i > 0);
+ return p + 1;
+}
+
+char *InternalFastHexToBuffer(uint64 value, char* buffer, int num_byte) {
+ static const char *hexdigits = "0123456789abcdef";
+ buffer[num_byte] = '\0';
+ for (int i = num_byte - 1; i >= 0; i--) {
+#ifdef _M_X64
+ // MSVC x64 platform has a bug optimizing the uint32(value) in the #else
+ // block. Given that the uint32 cast was to improve performance on 32-bit
+ // platforms, we use 64-bit '&' directly.
+ buffer[i] = hexdigits[value & 0xf];
+#else
+ buffer[i] = hexdigits[uint32(value) & 0xf];
+#endif
+ value >>= 4;
+ }
+ return buffer;
+}
+
+char *FastHex64ToBuffer(uint64 value, char* buffer) {
+ return InternalFastHexToBuffer(value, buffer, 16);
+}
+
+char *FastHex32ToBuffer(uint32 value, char* buffer) {
+ return InternalFastHexToBuffer(value, buffer, 8);
+}
+
+// ----------------------------------------------------------------------
+// FastInt32ToBufferLeft()
+// FastUInt32ToBufferLeft()
+// FastInt64ToBufferLeft()
+// FastUInt64ToBufferLeft()
+//
+// Like the Fast*ToBuffer() functions above, these are intended for speed.
+// Unlike the Fast*ToBuffer() functions, however, these functions write
+// their output to the beginning of the buffer (hence the name, as the
+// output is left-aligned). The caller is responsible for ensuring that
+// the buffer has enough space to hold the output.
+//
+// Returns a pointer to the end of the string (i.e. the null character
+// terminating the string).
+// ----------------------------------------------------------------------
+
+static const char two_ASCII_digits[100][2] = {
+ {'0','0'}, {'0','1'}, {'0','2'}, {'0','3'}, {'0','4'},
+ {'0','5'}, {'0','6'}, {'0','7'}, {'0','8'}, {'0','9'},
+ {'1','0'}, {'1','1'}, {'1','2'}, {'1','3'}, {'1','4'},
+ {'1','5'}, {'1','6'}, {'1','7'}, {'1','8'}, {'1','9'},
+ {'2','0'}, {'2','1'}, {'2','2'}, {'2','3'}, {'2','4'},
+ {'2','5'}, {'2','6'}, {'2','7'}, {'2','8'}, {'2','9'},
+ {'3','0'}, {'3','1'}, {'3','2'}, {'3','3'}, {'3','4'},
+ {'3','5'}, {'3','6'}, {'3','7'}, {'3','8'}, {'3','9'},
+ {'4','0'}, {'4','1'}, {'4','2'}, {'4','3'}, {'4','4'},
+ {'4','5'}, {'4','6'}, {'4','7'}, {'4','8'}, {'4','9'},
+ {'5','0'}, {'5','1'}, {'5','2'}, {'5','3'}, {'5','4'},
+ {'5','5'}, {'5','6'}, {'5','7'}, {'5','8'}, {'5','9'},
+ {'6','0'}, {'6','1'}, {'6','2'}, {'6','3'}, {'6','4'},
+ {'6','5'}, {'6','6'}, {'6','7'}, {'6','8'}, {'6','9'},
+ {'7','0'}, {'7','1'}, {'7','2'}, {'7','3'}, {'7','4'},
+ {'7','5'}, {'7','6'}, {'7','7'}, {'7','8'}, {'7','9'},
+ {'8','0'}, {'8','1'}, {'8','2'}, {'8','3'}, {'8','4'},
+ {'8','5'}, {'8','6'}, {'8','7'}, {'8','8'}, {'8','9'},
+ {'9','0'}, {'9','1'}, {'9','2'}, {'9','3'}, {'9','4'},
+ {'9','5'}, {'9','6'}, {'9','7'}, {'9','8'}, {'9','9'}
+};
+
+char* FastUInt32ToBufferLeft(uint32 u, char* buffer) {
+ int digits;
+ const char *ASCII_digits = NULL;
+ // The idea of this implementation is to trim the number of divides to as few
+ // as possible by using multiplication and subtraction rather than mod (%),
+ // and by outputting two digits at a time rather than one.
+ // The huge-number case is first, in the hopes that the compiler will output
+ // that case in one branch-free block of code, and only output conditional
+ // branches into it from below.
+ if (u >= 1000000000) { // >= 1,000,000,000
+ digits = u / 100000000; // 100,000,000
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+sublt100_000_000:
+ u -= digits * 100000000; // 100,000,000
+lt100_000_000:
+ digits = u / 1000000; // 1,000,000
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+sublt1_000_000:
+ u -= digits * 1000000; // 1,000,000
+lt1_000_000:
+ digits = u / 10000; // 10,000
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+sublt10_000:
+ u -= digits * 10000; // 10,000
+lt10_000:
+ digits = u / 100;
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+sublt100:
+ u -= digits * 100;
+lt100:
+ digits = u;
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+done:
+ *buffer = 0;
+ return buffer;
+ }
+
+ if (u < 100) {
+ digits = u;
+ if (u >= 10) goto lt100;
+ *buffer++ = '0' + digits;
+ goto done;
+ }
+ if (u < 10000) { // 10,000
+ if (u >= 1000) goto lt10_000;
+ digits = u / 100;
+ *buffer++ = '0' + digits;
+ goto sublt100;
+ }
+ if (u < 1000000) { // 1,000,000
+ if (u >= 100000) goto lt1_000_000;
+ digits = u / 10000; // 10,000
+ *buffer++ = '0' + digits;
+ goto sublt10_000;
+ }
+ if (u < 100000000) { // 100,000,000
+ if (u >= 10000000) goto lt100_000_000;
+ digits = u / 1000000; // 1,000,000
+ *buffer++ = '0' + digits;
+ goto sublt1_000_000;
+ }
+ // we already know that u < 1,000,000,000
+ digits = u / 100000000; // 100,000,000
+ *buffer++ = '0' + digits;
+ goto sublt100_000_000;
+}
+
+char* FastInt32ToBufferLeft(int32 i, char* buffer) {
+ uint32 u = i;
+ if (i < 0) {
+ *buffer++ = '-';
+ u = -i;
+ }
+ return FastUInt32ToBufferLeft(u, buffer);
+}
+
+char* FastUInt64ToBufferLeft(uint64 u64, char* buffer) {
+ int digits;
+ const char *ASCII_digits = NULL;
+
+ uint32 u = static_cast<uint32>(u64);
+ if (u == u64) return FastUInt32ToBufferLeft(u, buffer);
+
+ uint64 top_11_digits = u64 / 1000000000;
+ buffer = FastUInt64ToBufferLeft(top_11_digits, buffer);
+ u = u64 - (top_11_digits * 1000000000);
+
+ digits = u / 10000000; // 10,000,000
+ GOOGLE_DCHECK_LT(digits, 100);
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+ u -= digits * 10000000; // 10,000,000
+ digits = u / 100000; // 100,000
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+ u -= digits * 100000; // 100,000
+ digits = u / 1000; // 1,000
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+ u -= digits * 1000; // 1,000
+ digits = u / 10;
+ ASCII_digits = two_ASCII_digits[digits];
+ buffer[0] = ASCII_digits[0];
+ buffer[1] = ASCII_digits[1];
+ buffer += 2;
+ u -= digits * 10;
+ digits = u;
+ *buffer++ = '0' + digits;
+ *buffer = 0;
+ return buffer;
+}
+
+char* FastInt64ToBufferLeft(int64 i, char* buffer) {
+ uint64 u = i;
+ if (i < 0) {
+ *buffer++ = '-';
+ u = -i;
+ }
+ return FastUInt64ToBufferLeft(u, buffer);
+}
+
+// ----------------------------------------------------------------------
+// SimpleItoa()
+// Description: converts an integer to a string.
+//
+// Return value: string
+// ----------------------------------------------------------------------
+
+string SimpleItoa(int i) {
+ char buffer[kFastToBufferSize];
+ return (sizeof(i) == 4) ?
+ FastInt32ToBuffer(i, buffer) :
+ FastInt64ToBuffer(i, buffer);
+}
+
+string SimpleItoa(unsigned int i) {
+ char buffer[kFastToBufferSize];
+ return string(buffer, (sizeof(i) == 4) ?
+ FastUInt32ToBufferLeft(i, buffer) :
+ FastUInt64ToBufferLeft(i, buffer));
+}
+
+string SimpleItoa(long i) {
+ char buffer[kFastToBufferSize];
+ return (sizeof(i) == 4) ?
+ FastInt32ToBuffer(i, buffer) :
+ FastInt64ToBuffer(i, buffer);
+}
+
+string SimpleItoa(unsigned long i) {
+ char buffer[kFastToBufferSize];
+ return string(buffer, (sizeof(i) == 4) ?
+ FastUInt32ToBufferLeft(i, buffer) :
+ FastUInt64ToBufferLeft(i, buffer));
+}
+
+string SimpleItoa(long long i) {
+ char buffer[kFastToBufferSize];
+ return (sizeof(i) == 4) ?
+ FastInt32ToBuffer(i, buffer) :
+ FastInt64ToBuffer(i, buffer);
+}
+
+string SimpleItoa(unsigned long long i) {
+ char buffer[kFastToBufferSize];
+ return string(buffer, (sizeof(i) == 4) ?
+ FastUInt32ToBufferLeft(i, buffer) :
+ FastUInt64ToBufferLeft(i, buffer));
+}
+
+// ----------------------------------------------------------------------
+// SimpleDtoa()
+// SimpleFtoa()
+// DoubleToBuffer()
+// FloatToBuffer()
+// We want to print the value without losing precision, but we also do
+// not want to print more digits than necessary. This turns out to be
+// trickier than it sounds. Numbers like 0.2 cannot be represented
+// exactly in binary. If we print 0.2 with a very large precision,
+// e.g. "%.50g", we get "0.2000000000000000111022302462515654042363167".
+// On the other hand, if we set the precision too low, we lose
+// significant digits when printing numbers that actually need them.
+// It turns out there is no precision value that does the right thing
+// for all numbers.
+//
+// Our strategy is to first try printing with a precision that is never
+// over-precise, then parse the result with strtod() to see if it
+// matches. If not, we print again with a precision that will always
+// give a precise result, but may use more digits than necessary.
+//
+// An arguably better strategy would be to use the algorithm described
+// in "How to Print Floating-Point Numbers Accurately" by Steele &
+// White, e.g. as implemented by David M. Gay's dtoa(). It turns out,
+// however, that the following implementation is about as fast as
+// DMG's code. Furthermore, DMG's code locks mutexes, which means it
+// will not scale well on multi-core machines. DMG's code is slightly
+// more accurate (in that it will never use more digits than
+// necessary), but this is probably irrelevant for most users.
+//
+// Rob Pike and Ken Thompson also have an implementation of dtoa() in
+// third_party/fmt/fltfmt.cc. Their implementation is similar to this
+// one in that it makes guesses and then uses strtod() to check them.
+// Their implementation is faster because they use their own code to
+// generate the digits in the first place rather than use snprintf(),
+// thus avoiding format string parsing overhead. However, this makes
+// it considerably more complicated than the following implementation,
+// and it is embedded in a larger library. If speed turns out to be
+// an issue, we could re-implement this in terms of their
+// implementation.
+// ----------------------------------------------------------------------
+
+string SimpleDtoa(double value) {
+ char buffer[kDoubleToBufferSize];
+ return DoubleToBuffer(value, buffer);
+}
+
+string SimpleFtoa(float value) {
+ char buffer[kFloatToBufferSize];
+ return FloatToBuffer(value, buffer);
+}
+
+static inline bool IsValidFloatChar(char c) {
+ return ('0' <= c && c <= '9') ||
+ c == 'e' || c == 'E' ||
+ c == '+' || c == '-';
+}
+
+void DelocalizeRadix(char* buffer) {
+ // Fast check: if the buffer has a normal decimal point, assume no
+ // translation is needed.
+ if (strchr(buffer, '.') != NULL) return;
+
+ // Find the first unknown character.
+ while (IsValidFloatChar(*buffer)) ++buffer;
+
+ if (*buffer == '\0') {
+ // No radix character found.
+ return;
+ }
+
+ // We are now pointing at the locale-specific radix character. Replace it
+ // with '.'.
+ *buffer = '.';
+ ++buffer;
+
+ if (!IsValidFloatChar(*buffer) && *buffer != '\0') {
+ // It appears the radix was a multi-byte character. We need to remove the
+ // extra bytes.
+ char* target = buffer;
+ do { ++buffer; } while (!IsValidFloatChar(*buffer) && *buffer != '\0');
+ memmove(target, buffer, strlen(buffer) + 1);
+ }
+}
+
+char* DoubleToBuffer(double value, char* buffer) {
+ // DBL_DIG is 15 for IEEE-754 doubles, which are used on almost all
+ // platforms these days. Just in case some system exists where DBL_DIG
+ // is significantly larger -- and risks overflowing our buffer -- we have
+ // this assert.
+ GOOGLE_COMPILE_ASSERT(DBL_DIG < 20, DBL_DIG_is_too_big);
+
+ if (value == numeric_limits<double>::infinity()) {
+ strcpy(buffer, "inf");
+ return buffer;
+ } else if (value == -numeric_limits<double>::infinity()) {
+ strcpy(buffer, "-inf");
+ return buffer;
+ } else if (MathLimits<double>::IsNaN(value)) {
+ strcpy(buffer, "nan");
+ return buffer;
+ }
+
+ int snprintf_result =
+ snprintf(buffer, kDoubleToBufferSize, "%.*g", DBL_DIG, value);
+
+ // The snprintf should never overflow because the buffer is significantly
+ // larger than the precision we asked for.
+ GOOGLE_DCHECK(snprintf_result > 0 && snprintf_result < kDoubleToBufferSize);
+
+ // We need to make parsed_value volatile in order to force the compiler to
+ // write it out to the stack. Otherwise, it may keep the value in a
+ // register, and if it does that, it may keep it as a long double instead
+ // of a double. This long double may have extra bits that make it compare
+ // unequal to "value" even though it would be exactly equal if it were
+ // truncated to a double.
+ volatile double parsed_value = strtod(buffer, NULL);
+ if (parsed_value != value) {
+ int snprintf_result =
+ snprintf(buffer, kDoubleToBufferSize, "%.*g", DBL_DIG+2, value);
+
+ // Should never overflow; see above.
+ GOOGLE_DCHECK(snprintf_result > 0 && snprintf_result < kDoubleToBufferSize);
+ }
+
+ DelocalizeRadix(buffer);
+ return buffer;
+}
+
+static int memcasecmp(const char *s1, const char *s2, size_t len) {
+ const unsigned char *us1 = reinterpret_cast<const unsigned char *>(s1);
+ const unsigned char *us2 = reinterpret_cast<const unsigned char *>(s2);
+
+ for ( int i = 0; i < len; i++ ) {
+ const int diff =
+ static_cast<int>(static_cast<unsigned char>(ascii_tolower(us1[i]))) -
+ static_cast<int>(static_cast<unsigned char>(ascii_tolower(us2[i])));
+ if (diff != 0) return diff;
+ }
+ return 0;
+}
+
+inline bool CaseEqual(StringPiece s1, StringPiece s2) {
+ if (s1.size() != s2.size()) return false;
+ return memcasecmp(s1.data(), s2.data(), s1.size()) == 0;
+}
+
+bool safe_strtob(StringPiece str, bool* value) {
+ GOOGLE_CHECK(value != NULL) << "NULL output boolean given.";
+ if (CaseEqual(str, "true") || CaseEqual(str, "t") ||
+ CaseEqual(str, "yes") || CaseEqual(str, "y") ||
+ CaseEqual(str, "1")) {
+ *value = true;
+ return true;
+ }
+ if (CaseEqual(str, "false") || CaseEqual(str, "f") ||
+ CaseEqual(str, "no") || CaseEqual(str, "n") ||
+ CaseEqual(str, "0")) {
+ *value = false;
+ return true;
+ }
+ return false;
+}
+
+bool safe_strtof(const char* str, float* value) {
+ char* endptr;
+ errno = 0; // errno only gets set on errors
+#if defined(_WIN32) || defined (__hpux) // has no strtof()
+ *value = strtod(str, &endptr);
+#else
+ *value = strtof(str, &endptr);
+#endif
+ return *str != 0 && *endptr == 0 && errno == 0;
+}
+
+bool safe_strtod(const char* str, double* value) {
+ char* endptr;
+ *value = strtod(str, &endptr);
+ if (endptr != str) {
+ while (ascii_isspace(*endptr)) ++endptr;
+ }
+ // Ignore range errors from strtod. The values it
+ // returns on underflow and overflow are the right
+ // fallback in a robust setting.
+ return *str != '\0' && *endptr == '\0';
+}
+
+bool safe_strto32(const string& str, int32* value) {
+ return safe_int_internal(str, value);
+}
+
+bool safe_strtou32(const string& str, uint32* value) {
+ return safe_uint_internal(str, value);
+}
+
+bool safe_strto64(const string& str, int64* value) {
+ return safe_int_internal(str, value);
+}
+
+bool safe_strtou64(const string& str, uint64* value) {
+ return safe_uint_internal(str, value);
+}
+
+char* FloatToBuffer(float value, char* buffer) {
+ // FLT_DIG is 6 for IEEE-754 floats, which are used on almost all
+ // platforms these days. Just in case some system exists where FLT_DIG
+ // is significantly larger -- and risks overflowing our buffer -- we have
+ // this assert.
+ GOOGLE_COMPILE_ASSERT(FLT_DIG < 10, FLT_DIG_is_too_big);
+
+ if (value == numeric_limits<double>::infinity()) {
+ strcpy(buffer, "inf");
+ return buffer;
+ } else if (value == -numeric_limits<double>::infinity()) {
+ strcpy(buffer, "-inf");
+ return buffer;
+ } else if (MathLimits<float>::IsNaN(value)) {
+ strcpy(buffer, "nan");
+ return buffer;
+ }
+
+ int snprintf_result =
+ snprintf(buffer, kFloatToBufferSize, "%.*g", FLT_DIG, value);
+
+ // The snprintf should never overflow because the buffer is significantly
+ // larger than the precision we asked for.
+ GOOGLE_DCHECK(snprintf_result > 0 && snprintf_result < kFloatToBufferSize);
+
+ float parsed_value;
+ if (!safe_strtof(buffer, &parsed_value) || parsed_value != value) {
+ int snprintf_result =
+ snprintf(buffer, kFloatToBufferSize, "%.*g", FLT_DIG+2, value);
+
+ // Should never overflow; see above.
+ GOOGLE_DCHECK(snprintf_result > 0 && snprintf_result < kFloatToBufferSize);
+ }
+
+ DelocalizeRadix(buffer);
+ return buffer;
+}
+
+namespace strings {
+
+AlphaNum::AlphaNum(strings::Hex hex) {
+ char *const end = &digits[kFastToBufferSize];
+ char *writer = end;
+ uint64 value = hex.value;
+ uint64 width = hex.spec;
+ // We accomplish minimum width by OR'ing in 0x10000 to the user's value,
+ // where 0x10000 is the smallest hex number that is as wide as the user
+ // asked for.
+ uint64 mask = ((static_cast<uint64>(1) << (width - 1) * 4)) | value;
+ static const char hexdigits[] = "0123456789abcdef";
+ do {
+ *--writer = hexdigits[value & 0xF];
+ value >>= 4;
+ mask >>= 4;
+ } while (mask != 0);
+ piece_data_ = writer;
+ piece_size_ = end - writer;
+}
+
+} // namespace strings
+
+// ----------------------------------------------------------------------
+// StrCat()
+// This merges the given strings or integers, with no delimiter. This
+// is designed to be the fastest possible way to construct a string out
+// of a mix of raw C strings, C++ strings, and integer values.
+// ----------------------------------------------------------------------
+
+// Append is merely a version of memcpy that returns the address of the byte
+// after the area just overwritten. It comes in multiple flavors to minimize
+// call overhead.
+static char *Append1(char *out, const AlphaNum &x) {
+ memcpy(out, x.data(), x.size());
+ return out + x.size();
+}
+
+static char *Append2(char *out, const AlphaNum &x1, const AlphaNum &x2) {
+ memcpy(out, x1.data(), x1.size());
+ out += x1.size();
+
+ memcpy(out, x2.data(), x2.size());
+ return out + x2.size();
+}
+
+static char *Append4(char *out,
+ const AlphaNum &x1, const AlphaNum &x2,
+ const AlphaNum &x3, const AlphaNum &x4) {
+ memcpy(out, x1.data(), x1.size());
+ out += x1.size();
+
+ memcpy(out, x2.data(), x2.size());
+ out += x2.size();
+
+ memcpy(out, x3.data(), x3.size());
+ out += x3.size();
+
+ memcpy(out, x4.data(), x4.size());
+ return out + x4.size();
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b) {
+ string result;
+ result.resize(a.size() + b.size());
+ char *const begin = &*result.begin();
+ char *out = Append2(begin, a, b);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b, const AlphaNum &c) {
+ string result;
+ result.resize(a.size() + b.size() + c.size());
+ char *const begin = &*result.begin();
+ char *out = Append2(begin, a, b);
+ out = Append1(out, c);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b, const AlphaNum &c,
+ const AlphaNum &d) {
+ string result;
+ result.resize(a.size() + b.size() + c.size() + d.size());
+ char *const begin = &*result.begin();
+ char *out = Append4(begin, a, b, c, d);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b, const AlphaNum &c,
+ const AlphaNum &d, const AlphaNum &e) {
+ string result;
+ result.resize(a.size() + b.size() + c.size() + d.size() + e.size());
+ char *const begin = &*result.begin();
+ char *out = Append4(begin, a, b, c, d);
+ out = Append1(out, e);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b, const AlphaNum &c,
+ const AlphaNum &d, const AlphaNum &e, const AlphaNum &f) {
+ string result;
+ result.resize(a.size() + b.size() + c.size() + d.size() + e.size() +
+ f.size());
+ char *const begin = &*result.begin();
+ char *out = Append4(begin, a, b, c, d);
+ out = Append2(out, e, f);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b, const AlphaNum &c,
+ const AlphaNum &d, const AlphaNum &e, const AlphaNum &f,
+ const AlphaNum &g) {
+ string result;
+ result.resize(a.size() + b.size() + c.size() + d.size() + e.size() +
+ f.size() + g.size());
+ char *const begin = &*result.begin();
+ char *out = Append4(begin, a, b, c, d);
+ out = Append2(out, e, f);
+ out = Append1(out, g);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b, const AlphaNum &c,
+ const AlphaNum &d, const AlphaNum &e, const AlphaNum &f,
+ const AlphaNum &g, const AlphaNum &h) {
+ string result;
+ result.resize(a.size() + b.size() + c.size() + d.size() + e.size() +
+ f.size() + g.size() + h.size());
+ char *const begin = &*result.begin();
+ char *out = Append4(begin, a, b, c, d);
+ out = Append4(out, e, f, g, h);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+string StrCat(const AlphaNum &a, const AlphaNum &b, const AlphaNum &c,
+ const AlphaNum &d, const AlphaNum &e, const AlphaNum &f,
+ const AlphaNum &g, const AlphaNum &h, const AlphaNum &i) {
+ string result;
+ result.resize(a.size() + b.size() + c.size() + d.size() + e.size() +
+ f.size() + g.size() + h.size() + i.size());
+ char *const begin = &*result.begin();
+ char *out = Append4(begin, a, b, c, d);
+ out = Append4(out, e, f, g, h);
+ out = Append1(out, i);
+ GOOGLE_DCHECK_EQ(out, begin + result.size());
+ return result;
+}
+
+// It's possible to call StrAppend with a char * pointer that is partway into
+// the string we're appending to. However the results of this are random.
+// Therefore, check for this in debug mode. Use unsigned math so we only have
+// to do one comparison.
+#define GOOGLE_DCHECK_NO_OVERLAP(dest, src) \
+ GOOGLE_DCHECK_GT(uintptr_t((src).data() - (dest).data()), \
+ uintptr_t((dest).size()))
+
+void StrAppend(string *result, const AlphaNum &a) {
+ GOOGLE_DCHECK_NO_OVERLAP(*result, a);
+ result->append(a.data(), a.size());
+}
+
+void StrAppend(string *result, const AlphaNum &a, const AlphaNum &b) {
+ GOOGLE_DCHECK_NO_OVERLAP(*result, a);
+ GOOGLE_DCHECK_NO_OVERLAP(*result, b);
+ string::size_type old_size = result->size();
+ result->resize(old_size + a.size() + b.size());
+ char *const begin = &*result->begin();
+ char *out = Append2(begin + old_size, a, b);
+ GOOGLE_DCHECK_EQ(out, begin + result->size());
+}
+
+void StrAppend(string *result,
+ const AlphaNum &a, const AlphaNum &b, const AlphaNum &c) {
+ GOOGLE_DCHECK_NO_OVERLAP(*result, a);
+ GOOGLE_DCHECK_NO_OVERLAP(*result, b);
+ GOOGLE_DCHECK_NO_OVERLAP(*result, c);
+ string::size_type old_size = result->size();
+ result->resize(old_size + a.size() + b.size() + c.size());
+ char *const begin = &*result->begin();
+ char *out = Append2(begin + old_size, a, b);
+ out = Append1(out, c);
+ GOOGLE_DCHECK_EQ(out, begin + result->size());
+}
+
+void StrAppend(string *result,
+ const AlphaNum &a, const AlphaNum &b,
+ const AlphaNum &c, const AlphaNum &d) {
+ GOOGLE_DCHECK_NO_OVERLAP(*result, a);
+ GOOGLE_DCHECK_NO_OVERLAP(*result, b);
+ GOOGLE_DCHECK_NO_OVERLAP(*result, c);
+ GOOGLE_DCHECK_NO_OVERLAP(*result, d);
+ string::size_type old_size = result->size();
+ result->resize(old_size + a.size() + b.size() + c.size() + d.size());
+ char *const begin = &*result->begin();
+ char *out = Append4(begin + old_size, a, b, c, d);
+ GOOGLE_DCHECK_EQ(out, begin + result->size());
+}
+
+int GlobalReplaceSubstring(const string& substring,
+ const string& replacement,
+ string* s) {
+ GOOGLE_CHECK(s != NULL);
+ if (s->empty() || substring.empty())
+ return 0;
+ string tmp;
+ int num_replacements = 0;
+ int pos = 0;
+ for (int match_pos = s->find(substring.data(), pos, substring.length());
+ match_pos != string::npos;
+ pos = match_pos + substring.length(),
+ match_pos = s->find(substring.data(), pos, substring.length())) {
+ ++num_replacements;
+ // Append the original content before the match.
+ tmp.append(*s, pos, match_pos - pos);
+ // Append the replacement for the match.
+ tmp.append(replacement.begin(), replacement.end());
+ }
+ // Append the content after the last match. If no replacements were made, the
+ // original string is left untouched.
+ if (num_replacements > 0) {
+ tmp.append(*s, pos, s->length() - pos);
+ s->swap(tmp);
+ }
+ return num_replacements;
+}
+
+int CalculateBase64EscapedLen(int input_len, bool do_padding) {
+ // Base64 encodes three bytes of input at a time. If the input is not
+ // divisible by three, we pad as appropriate.
+ //
+ // (from http://tools.ietf.org/html/rfc3548)
+ // Special processing is performed if fewer than 24 bits are available
+ // at the end of the data being encoded. A full encoding quantum is
+ // always completed at the end of a quantity. When fewer than 24 input
+ // bits are available in an input group, zero bits are added (on the
+ // right) to form an integral number of 6-bit groups. Padding at the
+ // end of the data is performed using the '=' character. Since all base
+ // 64 input is an integral number of octets, only the following cases
+ // can arise:
+
+
+ // Base64 encodes each three bytes of input into four bytes of output.
+ int len = (input_len / 3) * 4;
+
+ if (input_len % 3 == 0) {
+ // (from http://tools.ietf.org/html/rfc3548)
+ // (1) the final quantum of encoding input is an integral multiple of 24
+ // bits; here, the final unit of encoded output will be an integral
+ // multiple of 4 characters with no "=" padding,
+ } else if (input_len % 3 == 1) {
+ // (from http://tools.ietf.org/html/rfc3548)
+ // (2) the final quantum of encoding input is exactly 8 bits; here, the
+ // final unit of encoded output will be two characters followed by two
+ // "=" padding characters, or
+ len += 2;
+ if (do_padding) {
+ len += 2;
+ }
+ } else { // (input_len % 3 == 2)
+ // (from http://tools.ietf.org/html/rfc3548)
+ // (3) the final quantum of encoding input is exactly 16 bits; here, the
+ // final unit of encoded output will be three characters followed by one
+ // "=" padding character.
+ len += 3;
+ if (do_padding) {
+ len += 1;
+ }
+ }
+
+ assert(len >= input_len); // make sure we didn't overflow
+ return len;
+}
+
+// Base64Escape does padding, so this calculation includes padding.
+int CalculateBase64EscapedLen(int input_len) {
+ return CalculateBase64EscapedLen(input_len, true);
+}
+
+// ----------------------------------------------------------------------
+// int Base64Unescape() - base64 decoder
+// int Base64Escape() - base64 encoder
+// int WebSafeBase64Unescape() - Google's variation of base64 decoder
+// int WebSafeBase64Escape() - Google's variation of base64 encoder
+//
+// Check out
+// http://tools.ietf.org/html/rfc2045 for formal description, but what we
+// care about is that...
+// Take the encoded stuff in groups of 4 characters and turn each
+// character into a code 0 to 63 thus:
+// A-Z map to 0 to 25
+// a-z map to 26 to 51
+// 0-9 map to 52 to 61
+// +(- for WebSafe) maps to 62
+// /(_ for WebSafe) maps to 63
+// There will be four numbers, all less than 64 which can be represented
+// by a 6 digit binary number (aaaaaa, bbbbbb, cccccc, dddddd respectively).
+// Arrange the 6 digit binary numbers into three bytes as such:
+// aaaaaabb bbbbcccc ccdddddd
+// Equals signs (one or two) are used at the end of the encoded block to
+// indicate that the text was not an integer multiple of three bytes long.
+// ----------------------------------------------------------------------
+
+int Base64UnescapeInternal(const char *src_param, int szsrc,
+ char *dest, int szdest,
+ const signed char* unbase64) {
+ static const char kPad64Equals = '=';
+ static const char kPad64Dot = '.';
+
+ int decode = 0;
+ int destidx = 0;
+ int state = 0;
+ unsigned int ch = 0;
+ unsigned int temp = 0;
+
+ // If "char" is signed by default, using *src as an array index results in
+ // accessing negative array elements. Treat the input as a pointer to
+ // unsigned char to avoid this.
+ const unsigned char *src = reinterpret_cast<const unsigned char*>(src_param);
+
+ // The GET_INPUT macro gets the next input character, skipping
+ // over any whitespace, and stopping when we reach the end of the
+ // string or when we read any non-data character. The arguments are
+ // an arbitrary identifier (used as a label for goto) and the number
+ // of data bytes that must remain in the input to avoid aborting the
+ // loop.
+#define GET_INPUT(label, remain) \
+ label: \
+ --szsrc; \
+ ch = *src++; \
+ decode = unbase64[ch]; \
+ if (decode < 0) { \
+ if (ascii_isspace(ch) && szsrc >= remain) \
+ goto label; \
+ state = 4 - remain; \
+ break; \
+ }
+
+ // if dest is null, we're just checking to see if it's legal input
+ // rather than producing output. (I suspect this could just be done
+ // with a regexp...). We duplicate the loop so this test can be
+ // outside it instead of in every iteration.
+
+ if (dest) {
+ // This loop consumes 4 input bytes and produces 3 output bytes
+ // per iteration. We can't know at the start that there is enough
+ // data left in the string for a full iteration, so the loop may
+ // break out in the middle; if so 'state' will be set to the
+ // number of input bytes read.
+
+ while (szsrc >= 4) {
+ // We'll start by optimistically assuming that the next four
+ // bytes of the string (src[0..3]) are four good data bytes
+ // (that is, no nulls, whitespace, padding chars, or illegal
+ // chars). We need to test src[0..2] for nulls individually
+ // before constructing temp to preserve the property that we
+ // never read past a null in the string (no matter how long
+ // szsrc claims the string is).
+
+ if (!src[0] || !src[1] || !src[2] ||
+ (temp = ((unsigned(unbase64[src[0]]) << 18) |
+ (unsigned(unbase64[src[1]]) << 12) |
+ (unsigned(unbase64[src[2]]) << 6) |
+ (unsigned(unbase64[src[3]])))) & 0x80000000) {
+ // Iff any of those four characters was bad (null, illegal,
+ // whitespace, padding), then temp's high bit will be set
+ // (because unbase64[] is -1 for all bad characters).
+ //
+ // We'll back up and resort to the slower decoder, which knows
+ // how to handle those cases.
+
+ GET_INPUT(first, 4);
+ temp = decode;
+ GET_INPUT(second, 3);
+ temp = (temp << 6) | decode;
+ GET_INPUT(third, 2);
+ temp = (temp << 6) | decode;
+ GET_INPUT(fourth, 1);
+ temp = (temp << 6) | decode;
+ } else {
+ // We really did have four good data bytes, so advance four
+ // characters in the string.
+
+ szsrc -= 4;
+ src += 4;
+ decode = -1;
+ ch = '\0';
+ }
+
+ // temp has 24 bits of input, so write that out as three bytes.
+
+ if (destidx+3 > szdest) return -1;
+ dest[destidx+2] = temp;
+ temp >>= 8;
+ dest[destidx+1] = temp;
+ temp >>= 8;
+ dest[destidx] = temp;
+ destidx += 3;
+ }
+ } else {
+ while (szsrc >= 4) {
+ if (!src[0] || !src[1] || !src[2] ||
+ (temp = ((unsigned(unbase64[src[0]]) << 18) |
+ (unsigned(unbase64[src[1]]) << 12) |
+ (unsigned(unbase64[src[2]]) << 6) |
+ (unsigned(unbase64[src[3]])))) & 0x80000000) {
+ GET_INPUT(first_no_dest, 4);
+ GET_INPUT(second_no_dest, 3);
+ GET_INPUT(third_no_dest, 2);
+ GET_INPUT(fourth_no_dest, 1);
+ } else {
+ szsrc -= 4;
+ src += 4;
+ decode = -1;
+ ch = '\0';
+ }
+ destidx += 3;
+ }
+ }
+
+#undef GET_INPUT
+
+ // if the loop terminated because we read a bad character, return
+ // now.
+ if (decode < 0 && ch != '\0' &&
+ ch != kPad64Equals && ch != kPad64Dot && !ascii_isspace(ch))
+ return -1;
+
+ if (ch == kPad64Equals || ch == kPad64Dot) {
+ // if we stopped by hitting an '=' or '.', un-read that character -- we'll
+ // look at it again when we count to check for the proper number of
+ // equals signs at the end.
+ ++szsrc;
+ --src;
+ } else {
+ // This loop consumes 1 input byte per iteration. It's used to
+ // clean up the 0-3 input bytes remaining when the first, faster
+ // loop finishes. 'temp' contains the data from 'state' input
+ // characters read by the first loop.
+ while (szsrc > 0) {
+ --szsrc;
+ ch = *src++;
+ decode = unbase64[ch];
+ if (decode < 0) {
+ if (ascii_isspace(ch)) {
+ continue;
+ } else if (ch == '\0') {
+ break;
+ } else if (ch == kPad64Equals || ch == kPad64Dot) {
+ // back up one character; we'll read it again when we check
+ // for the correct number of pad characters at the end.
+ ++szsrc;
+ --src;
+ break;
+ } else {
+ return -1;
+ }
+ }
+
+ // Each input character gives us six bits of output.
+ temp = (temp << 6) | decode;
+ ++state;
+ if (state == 4) {
+ // If we've accumulated 24 bits of output, write that out as
+ // three bytes.
+ if (dest) {
+ if (destidx+3 > szdest) return -1;
+ dest[destidx+2] = temp;
+ temp >>= 8;
+ dest[destidx+1] = temp;
+ temp >>= 8;
+ dest[destidx] = temp;
+ }
+ destidx += 3;
+ state = 0;
+ temp = 0;
+ }
+ }
+ }
+
+ // Process the leftover data contained in 'temp' at the end of the input.
+ int expected_equals = 0;
+ switch (state) {
+ case 0:
+ // Nothing left over; output is a multiple of 3 bytes.
+ break;
+
+ case 1:
+ // Bad input; we have 6 bits left over.
+ return -1;
+
+ case 2:
+ // Produce one more output byte from the 12 input bits we have left.
+ if (dest) {
+ if (destidx+1 > szdest) return -1;
+ temp >>= 4;
+ dest[destidx] = temp;
+ }
+ ++destidx;
+ expected_equals = 2;
+ break;
+
+ case 3:
+ // Produce two more output bytes from the 18 input bits we have left.
+ if (dest) {
+ if (destidx+2 > szdest) return -1;
+ temp >>= 2;
+ dest[destidx+1] = temp;
+ temp >>= 8;
+ dest[destidx] = temp;
+ }
+ destidx += 2;
+ expected_equals = 1;
+ break;
+
+ default:
+ // state should have no other values at this point.
+ GOOGLE_LOG(FATAL) << "This can't happen; base64 decoder state = " << state;
+ }
+
+ // The remainder of the string should be all whitespace, mixed with
+ // exactly 0 equals signs, or exactly 'expected_equals' equals
+ // signs. (Always accepting 0 equals signs is a google extension
+ // not covered in the RFC, as is accepting dot as the pad character.)
+
+ int equals = 0;
+ while (szsrc > 0 && *src) {
+ if (*src == kPad64Equals || *src == kPad64Dot)
+ ++equals;
+ else if (!ascii_isspace(*src))
+ return -1;
+ --szsrc;
+ ++src;
+ }
+
+ return (equals == 0 || equals == expected_equals) ? destidx : -1;
+}
+
+// The arrays below were generated by the following code
+// #include <sys/time.h>
+// #include <stdlib.h>
+// #include <string.h>
+// main()
+// {
+// static const char Base64[] =
+// "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+// char *pos;
+// int idx, i, j;
+// printf(" ");
+// for (i = 0; i < 255; i += 8) {
+// for (j = i; j < i + 8; j++) {
+// pos = strchr(Base64, j);
+// if ((pos == NULL) || (j == 0))
+// idx = -1;
+// else
+// idx = pos - Base64;
+// if (idx == -1)
+// printf(" %2d, ", idx);
+// else
+// printf(" %2d/*%c*/,", idx, j);
+// }
+// printf("\n ");
+// }
+// }
+//
+// where the value of "Base64[]" was replaced by one of the base-64 conversion
+// tables from the functions below.
+static const signed char kUnBase64[] = {
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, 62/*+*/, -1, -1, -1, 63/*/ */,
+ 52/*0*/, 53/*1*/, 54/*2*/, 55/*3*/, 56/*4*/, 57/*5*/, 58/*6*/, 59/*7*/,
+ 60/*8*/, 61/*9*/, -1, -1, -1, -1, -1, -1,
+ -1, 0/*A*/, 1/*B*/, 2/*C*/, 3/*D*/, 4/*E*/, 5/*F*/, 6/*G*/,
+ 07/*H*/, 8/*I*/, 9/*J*/, 10/*K*/, 11/*L*/, 12/*M*/, 13/*N*/, 14/*O*/,
+ 15/*P*/, 16/*Q*/, 17/*R*/, 18/*S*/, 19/*T*/, 20/*U*/, 21/*V*/, 22/*W*/,
+ 23/*X*/, 24/*Y*/, 25/*Z*/, -1, -1, -1, -1, -1,
+ -1, 26/*a*/, 27/*b*/, 28/*c*/, 29/*d*/, 30/*e*/, 31/*f*/, 32/*g*/,
+ 33/*h*/, 34/*i*/, 35/*j*/, 36/*k*/, 37/*l*/, 38/*m*/, 39/*n*/, 40/*o*/,
+ 41/*p*/, 42/*q*/, 43/*r*/, 44/*s*/, 45/*t*/, 46/*u*/, 47/*v*/, 48/*w*/,
+ 49/*x*/, 50/*y*/, 51/*z*/, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1
+};
+static const signed char kUnWebSafeBase64[] = {
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, 62/*-*/, -1, -1,
+ 52/*0*/, 53/*1*/, 54/*2*/, 55/*3*/, 56/*4*/, 57/*5*/, 58/*6*/, 59/*7*/,
+ 60/*8*/, 61/*9*/, -1, -1, -1, -1, -1, -1,
+ -1, 0/*A*/, 1/*B*/, 2/*C*/, 3/*D*/, 4/*E*/, 5/*F*/, 6/*G*/,
+ 07/*H*/, 8/*I*/, 9/*J*/, 10/*K*/, 11/*L*/, 12/*M*/, 13/*N*/, 14/*O*/,
+ 15/*P*/, 16/*Q*/, 17/*R*/, 18/*S*/, 19/*T*/, 20/*U*/, 21/*V*/, 22/*W*/,
+ 23/*X*/, 24/*Y*/, 25/*Z*/, -1, -1, -1, -1, 63/*_*/,
+ -1, 26/*a*/, 27/*b*/, 28/*c*/, 29/*d*/, 30/*e*/, 31/*f*/, 32/*g*/,
+ 33/*h*/, 34/*i*/, 35/*j*/, 36/*k*/, 37/*l*/, 38/*m*/, 39/*n*/, 40/*o*/,
+ 41/*p*/, 42/*q*/, 43/*r*/, 44/*s*/, 45/*t*/, 46/*u*/, 47/*v*/, 48/*w*/,
+ 49/*x*/, 50/*y*/, 51/*z*/, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1,
+ -1, -1, -1, -1, -1, -1, -1, -1
+};
+
+int WebSafeBase64Unescape(const char *src, int szsrc, char *dest, int szdest) {
+ return Base64UnescapeInternal(src, szsrc, dest, szdest, kUnWebSafeBase64);
+}
+
+static bool Base64UnescapeInternal(const char* src, int slen, string* dest,
+ const signed char* unbase64) {
+ // Determine the size of the output string. Base64 encodes every 3 bytes into
+ // 4 characters. any leftover chars are added directly for good measure.
+ // This is documented in the base64 RFC: http://tools.ietf.org/html/rfc3548
+ const int dest_len = 3 * (slen / 4) + (slen % 4);
+
+ dest->resize(dest_len);
+
+ // We are getting the destination buffer by getting the beginning of the
+ // string and converting it into a char *.
+ const int len = Base64UnescapeInternal(src, slen, string_as_array(dest),
+ dest_len, unbase64);
+ if (len < 0) {
+ dest->clear();
+ return false;
+ }
+
+ // could be shorter if there was padding
+ GOOGLE_DCHECK_LE(len, dest_len);
+ dest->erase(len);
+
+ return true;
+}
+
+bool Base64Unescape(StringPiece src, string* dest) {
+ return Base64UnescapeInternal(src.data(), src.size(), dest, kUnBase64);
+}
+
+bool WebSafeBase64Unescape(StringPiece src, string* dest) {
+ return Base64UnescapeInternal(src.data(), src.size(), dest, kUnWebSafeBase64);
+}
+
+int Base64EscapeInternal(const unsigned char *src, int szsrc,
+ char *dest, int szdest, const char *base64,
+ bool do_padding) {
+ static const char kPad64 = '=';
+
+ if (szsrc <= 0) return 0;
+
+ if (szsrc * 4 > szdest * 3) return 0;
+
+ char *cur_dest = dest;
+ const unsigned char *cur_src = src;
+
+ char *limit_dest = dest + szdest;
+ const unsigned char *limit_src = src + szsrc;
+
+ // Three bytes of data encodes to four characters of cyphertext.
+ // So we can pump through three-byte chunks atomically.
+ while (cur_src < limit_src - 3) { // keep going as long as we have >= 32 bits
+ uint32 in = BigEndian::Load32(cur_src) >> 8;
+
+ cur_dest[0] = base64[in >> 18];
+ in &= 0x3FFFF;
+ cur_dest[1] = base64[in >> 12];
+ in &= 0xFFF;
+ cur_dest[2] = base64[in >> 6];
+ in &= 0x3F;
+ cur_dest[3] = base64[in];
+
+ cur_dest += 4;
+ cur_src += 3;
+ }
+ // To save time, we didn't update szdest or szsrc in the loop. So do it now.
+ szdest = limit_dest - cur_dest;
+ szsrc = limit_src - cur_src;
+
+ /* now deal with the tail (<=3 bytes) */
+ switch (szsrc) {
+ case 0:
+ // Nothing left; nothing more to do.
+ break;
+ case 1: {
+ // One byte left: this encodes to two characters, and (optionally)
+ // two pad characters to round out the four-character cypherblock.
+ if ((szdest -= 2) < 0) return 0;
+ uint32 in = cur_src[0];
+ cur_dest[0] = base64[in >> 2];
+ in &= 0x3;
+ cur_dest[1] = base64[in << 4];
+ cur_dest += 2;
+ if (do_padding) {
+ if ((szdest -= 2) < 0) return 0;
+ cur_dest[0] = kPad64;
+ cur_dest[1] = kPad64;
+ cur_dest += 2;
+ }
+ break;
+ }
+ case 2: {
+ // Two bytes left: this encodes to three characters, and (optionally)
+ // one pad character to round out the four-character cypherblock.
+ if ((szdest -= 3) < 0) return 0;
+ uint32 in = BigEndian::Load16(cur_src);
+ cur_dest[0] = base64[in >> 10];
+ in &= 0x3FF;
+ cur_dest[1] = base64[in >> 4];
+ in &= 0x00F;
+ cur_dest[2] = base64[in << 2];
+ cur_dest += 3;
+ if (do_padding) {
+ if ((szdest -= 1) < 0) return 0;
+ cur_dest[0] = kPad64;
+ cur_dest += 1;
+ }
+ break;
+ }
+ case 3: {
+ // Three bytes left: same as in the big loop above. We can't do this in
+ // the loop because the loop above always reads 4 bytes, and the fourth
+ // byte is past the end of the input.
+ if ((szdest -= 4) < 0) return 0;
+ uint32 in = (cur_src[0] << 16) + BigEndian::Load16(cur_src + 1);
+ cur_dest[0] = base64[in >> 18];
+ in &= 0x3FFFF;
+ cur_dest[1] = base64[in >> 12];
+ in &= 0xFFF;
+ cur_dest[2] = base64[in >> 6];
+ in &= 0x3F;
+ cur_dest[3] = base64[in];
+ cur_dest += 4;
+ break;
+ }
+ default:
+ // Should not be reached: blocks of 4 bytes are handled
+ // in the while loop before this switch statement.
+ GOOGLE_LOG(FATAL) << "Logic problem? szsrc = " << szsrc;
+ break;
+ }
+ return (cur_dest - dest);
+}
+
+static const char kBase64Chars[] =
+"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+
+static const char kWebSafeBase64Chars[] =
+"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_";
+
+int Base64Escape(const unsigned char *src, int szsrc, char *dest, int szdest) {
+ return Base64EscapeInternal(src, szsrc, dest, szdest, kBase64Chars, true);
+}
+int WebSafeBase64Escape(const unsigned char *src, int szsrc, char *dest,
+ int szdest, bool do_padding) {
+ return Base64EscapeInternal(src, szsrc, dest, szdest,
+ kWebSafeBase64Chars, do_padding);
+}
+
+void Base64EscapeInternal(const unsigned char* src, int szsrc,
+ string* dest, bool do_padding,
+ const char* base64_chars) {
+ const int calc_escaped_size =
+ CalculateBase64EscapedLen(szsrc, do_padding);
+ dest->resize(calc_escaped_size);
+ const int escaped_len = Base64EscapeInternal(src, szsrc,
+ string_as_array(dest),
+ dest->size(),
+ base64_chars,
+ do_padding);
+ GOOGLE_DCHECK_EQ(calc_escaped_size, escaped_len);
+ dest->erase(escaped_len);
+}
+
+void Base64Escape(const unsigned char *src, int szsrc,
+ string* dest, bool do_padding) {
+ Base64EscapeInternal(src, szsrc, dest, do_padding, kBase64Chars);
+}
+
+void WebSafeBase64Escape(const unsigned char *src, int szsrc,
+ string *dest, bool do_padding) {
+ Base64EscapeInternal(src, szsrc, dest, do_padding, kWebSafeBase64Chars);
+}
+
+void Base64Escape(StringPiece src, string* dest) {
+ Base64Escape(reinterpret_cast<const unsigned char*>(src.data()),
+ src.size(), dest, true);
+}
+
+void WebSafeBase64Escape(StringPiece src, string* dest) {
+ WebSafeBase64Escape(reinterpret_cast<const unsigned char*>(src.data()),
+ src.size(), dest, false);
+}
+
+void WebSafeBase64EscapeWithPadding(StringPiece src, string* dest) {
+ WebSafeBase64Escape(reinterpret_cast<const unsigned char*>(src.data()),
+ src.size(), dest, true);
+}
+
+// Helper to append a Unicode code point to a string as UTF8, without bringing
+// in any external dependencies.
+int EncodeAsUTF8Char(uint32 code_point, char* output) {
+ uint32 tmp = 0;
+ int len = 0;
+ if (code_point <= 0x7f) {
+ tmp = code_point;
+ len = 1;
+ } else if (code_point <= 0x07ff) {
+ tmp = 0x0000c080 |
+ ((code_point & 0x07c0) << 2) |
+ (code_point & 0x003f);
+ len = 2;
+ } else if (code_point <= 0xffff) {
+ tmp = 0x00e08080 |
+ ((code_point & 0xf000) << 4) |
+ ((code_point & 0x0fc0) << 2) |
+ (code_point & 0x003f);
+ len = 3;
+ } else {
+ // UTF-16 is only defined for code points up to 0x10FFFF, and UTF-8 is
+ // normally only defined up to there as well.
+ tmp = 0xf0808080 |
+ ((code_point & 0x1c0000) << 6) |
+ ((code_point & 0x03f000) << 4) |
+ ((code_point & 0x000fc0) << 2) |
+ (code_point & 0x003f);
+ len = 4;
+ }
+ tmp = ghtonl(tmp);
+ memcpy(output, reinterpret_cast<const char*>(&tmp) + sizeof(tmp) - len, len);
+ return len;
+}
+
+// Table of UTF-8 character lengths, based on first byte
+static const unsigned char kUTF8LenTbl[256] = {
+ 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,
+
+ 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,
+ 2,2,2,2,2,2,2,2, 2,2,2,2,2,2,2,2, 2,2,2,2,2,2,2,2, 2,2,2,2,2,2,2,2,
+ 3,3,3,3,3,3,3,3, 3,3,3,3,3,3,3,3, 4,4,4,4,4,4,4,4, 4,4,4,4,4,4,4,4
+};
+
+// Return length of a single UTF-8 source character
+int UTF8FirstLetterNumBytes(const char* src, int len) {
+ if (len == 0) {
+ return 0;
+ }
+ return kUTF8LenTbl[*reinterpret_cast<const uint8*>(src)];
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.h
new file mode 100644
index 0000000000..8bdd611030
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil.h
@@ -0,0 +1,876 @@
+// 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.
+
+// from google3/strings/strutil.h
+
+#ifndef GOOGLE_PROTOBUF_STUBS_STRUTIL_H__
+#define GOOGLE_PROTOBUF_STUBS_STRUTIL_H__
+
+#include <stdlib.h>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+
+namespace google {
+namespace protobuf {
+
+#ifdef _MSC_VER
+#define strtoll _strtoi64
+#define strtoull _strtoui64
+#elif defined(__DECCXX) && defined(__osf__)
+// HP C++ on Tru64 does not have strtoll, but strtol is already 64-bit.
+#define strtoll strtol
+#define strtoull strtoul
+#endif
+
+// ----------------------------------------------------------------------
+// ascii_isalnum()
+// Check if an ASCII character is alphanumeric. We can't use ctype's
+// isalnum() because it is affected by locale. This function is applied
+// to identifiers in the protocol buffer language, not to natural-language
+// strings, so locale should not be taken into account.
+// ascii_isdigit()
+// Like above, but only accepts digits.
+// ascii_isspace()
+// Check if the character is a space character.
+// ----------------------------------------------------------------------
+
+inline bool ascii_isalnum(char c) {
+ return ('a' <= c && c <= 'z') ||
+ ('A' <= c && c <= 'Z') ||
+ ('0' <= c && c <= '9');
+}
+
+inline bool ascii_isdigit(char c) {
+ return ('0' <= c && c <= '9');
+}
+
+inline bool ascii_isspace(char c) {
+ return c == ' ' || c == '\t' || c == '\n' || c == '\v' || c == '\f' ||
+ c == '\r';
+}
+
+inline bool ascii_isupper(char c) {
+ return c >= 'A' && c <= 'Z';
+}
+
+inline bool ascii_islower(char c) {
+ return c >= 'a' && c <= 'z';
+}
+
+inline char ascii_toupper(char c) {
+ return ascii_islower(c) ? c - ('a' - 'A') : c;
+}
+
+inline char ascii_tolower(char c) {
+ return ascii_isupper(c) ? c + ('a' - 'A') : c;
+}
+
+inline int hex_digit_to_int(char c) {
+ /* Assume ASCII. */
+ int x = static_cast<unsigned char>(c);
+ if (x > '9') {
+ x += 9;
+ }
+ return x & 0xf;
+}
+
+// ----------------------------------------------------------------------
+// HasPrefixString()
+// Check if a string begins with a given prefix.
+// StripPrefixString()
+// Given a string and a putative prefix, returns the string minus the
+// prefix string if the prefix matches, otherwise the original
+// string.
+// ----------------------------------------------------------------------
+inline bool HasPrefixString(const string& str,
+ const string& prefix) {
+ return str.size() >= prefix.size() &&
+ str.compare(0, prefix.size(), prefix) == 0;
+}
+
+inline string StripPrefixString(const string& str, const string& prefix) {
+ if (HasPrefixString(str, prefix)) {
+ return str.substr(prefix.size());
+ } else {
+ return str;
+ }
+}
+
+// ----------------------------------------------------------------------
+// HasSuffixString()
+// Return true if str ends in suffix.
+// StripSuffixString()
+// Given a string and a putative suffix, returns the string minus the
+// suffix string if the suffix matches, otherwise the original
+// string.
+// ----------------------------------------------------------------------
+inline bool HasSuffixString(const string& str,
+ const string& suffix) {
+ return str.size() >= suffix.size() &&
+ str.compare(str.size() - suffix.size(), suffix.size(), suffix) == 0;
+}
+
+inline string StripSuffixString(const string& str, const string& suffix) {
+ if (HasSuffixString(str, suffix)) {
+ return str.substr(0, str.size() - suffix.size());
+ } else {
+ return str;
+ }
+}
+
+// ----------------------------------------------------------------------
+// StripString
+// Replaces any occurrence of the character 'remove' (or the characters
+// in 'remove') with the character 'replacewith'.
+// Good for keeping html characters or protocol characters (\t) out
+// of places where they might cause a problem.
+// StripWhitespace
+// Removes whitespaces from both ends of the given string.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT void StripString(string* s, const char* remove,
+ char replacewith);
+
+LIBPROTOBUF_EXPORT void StripWhitespace(string* s);
+
+
+// ----------------------------------------------------------------------
+// LowerString()
+// UpperString()
+// ToUpper()
+// Convert the characters in "s" to lowercase or uppercase. ASCII-only:
+// these functions intentionally ignore locale because they are applied to
+// identifiers used in the Protocol Buffer language, not to natural-language
+// strings.
+// ----------------------------------------------------------------------
+
+inline void LowerString(string * s) {
+ string::iterator end = s->end();
+ for (string::iterator i = s->begin(); i != end; ++i) {
+ // tolower() changes based on locale. We don't want this!
+ if ('A' <= *i && *i <= 'Z') *i += 'a' - 'A';
+ }
+}
+
+inline void UpperString(string * s) {
+ string::iterator end = s->end();
+ for (string::iterator i = s->begin(); i != end; ++i) {
+ // toupper() changes based on locale. We don't want this!
+ if ('a' <= *i && *i <= 'z') *i += 'A' - 'a';
+ }
+}
+
+inline string ToUpper(const string& s) {
+ string out = s;
+ UpperString(&out);
+ return out;
+}
+
+// ----------------------------------------------------------------------
+// StringReplace()
+// Give me a string and two patterns "old" and "new", and I replace
+// the first instance of "old" in the string with "new", if it
+// exists. RETURN a new string, regardless of whether the replacement
+// happened or not.
+// ----------------------------------------------------------------------
+
+LIBPROTOBUF_EXPORT string StringReplace(const string& s, const string& oldsub,
+ const string& newsub, bool replace_all);
+
+// ----------------------------------------------------------------------
+// SplitStringUsing()
+// Split a string using a character delimiter. Append the components
+// to 'result'. If there are consecutive delimiters, this function skips
+// over all of them.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT void SplitStringUsing(const string& full, const char* delim,
+ vector<string>* res);
+
+// Split a string using one or more byte delimiters, presented
+// as a nul-terminated c string. Append the components to 'result'.
+// If there are consecutive delimiters, this function will return
+// corresponding empty strings. If you want to drop the empty
+// strings, try SplitStringUsing().
+//
+// If "full" is the empty string, yields an empty string as the only value.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT void SplitStringAllowEmpty(const string& full,
+ const char* delim,
+ vector<string>* result);
+
+// ----------------------------------------------------------------------
+// Split()
+// Split a string using a character delimiter.
+// ----------------------------------------------------------------------
+inline vector<string> Split(
+ const string& full, const char* delim, bool skip_empty = true) {
+ vector<string> result;
+ if (skip_empty) {
+ SplitStringUsing(full, delim, &result);
+ } else {
+ SplitStringAllowEmpty(full, delim, &result);
+ }
+ return result;
+}
+
+// ----------------------------------------------------------------------
+// JoinStrings()
+// These methods concatenate a vector of strings into a C++ string, using
+// the C-string "delim" as a separator between components. There are two
+// flavors of the function, one flavor returns the concatenated string,
+// another takes a pointer to the target string. In the latter case the
+// target string is cleared and overwritten.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT void JoinStrings(const vector<string>& components,
+ const char* delim, string* result);
+
+inline string JoinStrings(const vector<string>& components,
+ const char* delim) {
+ string result;
+ JoinStrings(components, delim, &result);
+ return result;
+}
+
+// ----------------------------------------------------------------------
+// UnescapeCEscapeSequences()
+// Copies "source" to "dest", rewriting C-style escape sequences
+// -- '\n', '\r', '\\', '\ooo', etc -- to their ASCII
+// equivalents. "dest" must be sufficiently large to hold all
+// the characters in the rewritten string (i.e. at least as large
+// as strlen(source) + 1 should be safe, since the replacements
+// are always shorter than the original escaped sequences). It's
+// safe for source and dest to be the same. RETURNS the length
+// of dest.
+//
+// It allows hex sequences \xhh, or generally \xhhhhh with an
+// arbitrary number of hex digits, but all of them together must
+// specify a value of a single byte (e.g. \x0045 is equivalent
+// to \x45, and \x1234 is erroneous).
+//
+// It also allows escape sequences of the form \uhhhh (exactly four
+// hex digits, upper or lower case) or \Uhhhhhhhh (exactly eight
+// hex digits, upper or lower case) to specify a Unicode code
+// point. The dest array will contain the UTF8-encoded version of
+// that code-point (e.g., if source contains \u2019, then dest will
+// contain the three bytes 0xE2, 0x80, and 0x99).
+//
+// Errors: In the first form of the call, errors are reported with
+// LOG(ERROR). The same is true for the second form of the call if
+// the pointer to the string vector is NULL; otherwise, error
+// messages are stored in the vector. In either case, the effect on
+// the dest array is not defined, but rest of the source will be
+// processed.
+// ----------------------------------------------------------------------
+
+LIBPROTOBUF_EXPORT int UnescapeCEscapeSequences(const char* source, char* dest);
+LIBPROTOBUF_EXPORT int UnescapeCEscapeSequences(const char* source, char* dest,
+ vector<string> *errors);
+
+// ----------------------------------------------------------------------
+// UnescapeCEscapeString()
+// This does the same thing as UnescapeCEscapeSequences, but creates
+// a new string. The caller does not need to worry about allocating
+// a dest buffer. This should be used for non performance critical
+// tasks such as printing debug messages. It is safe for src and dest
+// to be the same.
+//
+// The second call stores its errors in a supplied string vector.
+// If the string vector pointer is NULL, it reports the errors with LOG().
+//
+// In the first and second calls, the length of dest is returned. In the
+// the third call, the new string is returned.
+// ----------------------------------------------------------------------
+
+LIBPROTOBUF_EXPORT int UnescapeCEscapeString(const string& src, string* dest);
+LIBPROTOBUF_EXPORT int UnescapeCEscapeString(const string& src, string* dest,
+ vector<string> *errors);
+LIBPROTOBUF_EXPORT string UnescapeCEscapeString(const string& src);
+
+// ----------------------------------------------------------------------
+// CEscape()
+// Escapes 'src' using C-style escape sequences and returns the resulting
+// string.
+//
+// Escaped chars: \n, \r, \t, ", ', \, and !isprint().
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT string CEscape(const string& src);
+
+// ----------------------------------------------------------------------
+// CEscapeAndAppend()
+// Escapes 'src' using C-style escape sequences, and appends the escaped
+// string to 'dest'.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT void CEscapeAndAppend(StringPiece src, string* dest);
+
+namespace strings {
+// Like CEscape() but does not escape bytes with the upper bit set.
+LIBPROTOBUF_EXPORT string Utf8SafeCEscape(const string& src);
+
+// Like CEscape() but uses hex (\x) escapes instead of octals.
+LIBPROTOBUF_EXPORT string CHexEscape(const string& src);
+} // namespace strings
+
+// ----------------------------------------------------------------------
+// strto32()
+// strtou32()
+// strto64()
+// strtou64()
+// Architecture-neutral plug compatible replacements for strtol() and
+// strtoul(). Long's have different lengths on ILP-32 and LP-64
+// platforms, so using these is safer, from the point of view of
+// overflow behavior, than using the standard libc functions.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT int32 strto32_adaptor(const char *nptr, char **endptr,
+ int base);
+LIBPROTOBUF_EXPORT uint32 strtou32_adaptor(const char *nptr, char **endptr,
+ int base);
+
+inline int32 strto32(const char *nptr, char **endptr, int base) {
+ if (sizeof(int32) == sizeof(long))
+ return strtol(nptr, endptr, base);
+ else
+ return strto32_adaptor(nptr, endptr, base);
+}
+
+inline uint32 strtou32(const char *nptr, char **endptr, int base) {
+ if (sizeof(uint32) == sizeof(unsigned long))
+ return strtoul(nptr, endptr, base);
+ else
+ return strtou32_adaptor(nptr, endptr, base);
+}
+
+// For now, long long is 64-bit on all the platforms we care about, so these
+// functions can simply pass the call to strto[u]ll.
+inline int64 strto64(const char *nptr, char **endptr, int base) {
+ GOOGLE_COMPILE_ASSERT(sizeof(int64) == sizeof(long long),
+ sizeof_int64_is_not_sizeof_long_long);
+ return strtoll(nptr, endptr, base);
+}
+
+inline uint64 strtou64(const char *nptr, char **endptr, int base) {
+ GOOGLE_COMPILE_ASSERT(sizeof(uint64) == sizeof(unsigned long long),
+ sizeof_uint64_is_not_sizeof_long_long);
+ return strtoull(nptr, endptr, base);
+}
+
+// ----------------------------------------------------------------------
+// safe_strtob()
+// safe_strto32()
+// safe_strtou32()
+// safe_strto64()
+// safe_strtou64()
+// safe_strtof()
+// safe_strtod()
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT bool safe_strtob(StringPiece str, bool* value);
+
+LIBPROTOBUF_EXPORT bool safe_strto32(const string& str, int32* value);
+LIBPROTOBUF_EXPORT bool safe_strtou32(const string& str, uint32* value);
+inline bool safe_strto32(const char* str, int32* value) {
+ return safe_strto32(string(str), value);
+}
+inline bool safe_strto32(StringPiece str, int32* value) {
+ return safe_strto32(str.ToString(), value);
+}
+inline bool safe_strtou32(const char* str, uint32* value) {
+ return safe_strtou32(string(str), value);
+}
+inline bool safe_strtou32(StringPiece str, uint32* value) {
+ return safe_strtou32(str.ToString(), value);
+}
+
+LIBPROTOBUF_EXPORT bool safe_strto64(const string& str, int64* value);
+LIBPROTOBUF_EXPORT bool safe_strtou64(const string& str, uint64* value);
+inline bool safe_strto64(const char* str, int64* value) {
+ return safe_strto64(string(str), value);
+}
+inline bool safe_strto64(StringPiece str, int64* value) {
+ return safe_strto64(str.ToString(), value);
+}
+inline bool safe_strtou64(const char* str, uint64* value) {
+ return safe_strtou64(string(str), value);
+}
+inline bool safe_strtou64(StringPiece str, uint64* value) {
+ return safe_strtou64(str.ToString(), value);
+}
+
+LIBPROTOBUF_EXPORT bool safe_strtof(const char* str, float* value);
+LIBPROTOBUF_EXPORT bool safe_strtod(const char* str, double* value);
+inline bool safe_strtof(const string& str, float* value) {
+ return safe_strtof(str.c_str(), value);
+}
+inline bool safe_strtod(const string& str, double* value) {
+ return safe_strtod(str.c_str(), value);
+}
+inline bool safe_strtof(StringPiece str, float* value) {
+ return safe_strtof(str.ToString(), value);
+}
+inline bool safe_strtod(StringPiece str, double* value) {
+ return safe_strtod(str.ToString(), value);
+}
+
+// ----------------------------------------------------------------------
+// FastIntToBuffer()
+// FastHexToBuffer()
+// FastHex64ToBuffer()
+// FastHex32ToBuffer()
+// FastTimeToBuffer()
+// These are intended for speed. FastIntToBuffer() assumes the
+// integer is non-negative. FastHexToBuffer() puts output in
+// hex rather than decimal. FastTimeToBuffer() puts the output
+// into RFC822 format.
+//
+// FastHex64ToBuffer() puts a 64-bit unsigned value in hex-format,
+// padded to exactly 16 bytes (plus one byte for '\0')
+//
+// FastHex32ToBuffer() puts a 32-bit unsigned value in hex-format,
+// padded to exactly 8 bytes (plus one byte for '\0')
+//
+// All functions take the output buffer as an arg.
+// They all return a pointer to the beginning of the output,
+// which may not be the beginning of the input buffer.
+// ----------------------------------------------------------------------
+
+// Suggested buffer size for FastToBuffer functions. Also works with
+// DoubleToBuffer() and FloatToBuffer().
+static const int kFastToBufferSize = 32;
+
+LIBPROTOBUF_EXPORT char* FastInt32ToBuffer(int32 i, char* buffer);
+LIBPROTOBUF_EXPORT char* FastInt64ToBuffer(int64 i, char* buffer);
+char* FastUInt32ToBuffer(uint32 i, char* buffer); // inline below
+char* FastUInt64ToBuffer(uint64 i, char* buffer); // inline below
+LIBPROTOBUF_EXPORT char* FastHexToBuffer(int i, char* buffer);
+LIBPROTOBUF_EXPORT char* FastHex64ToBuffer(uint64 i, char* buffer);
+LIBPROTOBUF_EXPORT char* FastHex32ToBuffer(uint32 i, char* buffer);
+
+// at least 22 bytes long
+inline char* FastIntToBuffer(int i, char* buffer) {
+ return (sizeof(i) == 4 ?
+ FastInt32ToBuffer(i, buffer) : FastInt64ToBuffer(i, buffer));
+}
+inline char* FastUIntToBuffer(unsigned int i, char* buffer) {
+ return (sizeof(i) == 4 ?
+ FastUInt32ToBuffer(i, buffer) : FastUInt64ToBuffer(i, buffer));
+}
+inline char* FastLongToBuffer(long i, char* buffer) {
+ return (sizeof(i) == 4 ?
+ FastInt32ToBuffer(i, buffer) : FastInt64ToBuffer(i, buffer));
+}
+inline char* FastULongToBuffer(unsigned long i, char* buffer) {
+ return (sizeof(i) == 4 ?
+ FastUInt32ToBuffer(i, buffer) : FastUInt64ToBuffer(i, buffer));
+}
+
+// ----------------------------------------------------------------------
+// FastInt32ToBufferLeft()
+// FastUInt32ToBufferLeft()
+// FastInt64ToBufferLeft()
+// FastUInt64ToBufferLeft()
+//
+// Like the Fast*ToBuffer() functions above, these are intended for speed.
+// Unlike the Fast*ToBuffer() functions, however, these functions write
+// their output to the beginning of the buffer (hence the name, as the
+// output is left-aligned). The caller is responsible for ensuring that
+// the buffer has enough space to hold the output.
+//
+// Returns a pointer to the end of the string (i.e. the null character
+// terminating the string).
+// ----------------------------------------------------------------------
+
+LIBPROTOBUF_EXPORT char* FastInt32ToBufferLeft(int32 i, char* buffer);
+LIBPROTOBUF_EXPORT char* FastUInt32ToBufferLeft(uint32 i, char* buffer);
+LIBPROTOBUF_EXPORT char* FastInt64ToBufferLeft(int64 i, char* buffer);
+LIBPROTOBUF_EXPORT char* FastUInt64ToBufferLeft(uint64 i, char* buffer);
+
+// Just define these in terms of the above.
+inline char* FastUInt32ToBuffer(uint32 i, char* buffer) {
+ FastUInt32ToBufferLeft(i, buffer);
+ return buffer;
+}
+inline char* FastUInt64ToBuffer(uint64 i, char* buffer) {
+ FastUInt64ToBufferLeft(i, buffer);
+ return buffer;
+}
+
+inline string SimpleBtoa(bool value) {
+ return value ? "true" : "false";
+}
+
+// ----------------------------------------------------------------------
+// SimpleItoa()
+// Description: converts an integer to a string.
+//
+// Return value: string
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT string SimpleItoa(int i);
+LIBPROTOBUF_EXPORT string SimpleItoa(unsigned int i);
+LIBPROTOBUF_EXPORT string SimpleItoa(long i);
+LIBPROTOBUF_EXPORT string SimpleItoa(unsigned long i);
+LIBPROTOBUF_EXPORT string SimpleItoa(long long i);
+LIBPROTOBUF_EXPORT string SimpleItoa(unsigned long long i);
+
+// ----------------------------------------------------------------------
+// SimpleDtoa()
+// SimpleFtoa()
+// DoubleToBuffer()
+// FloatToBuffer()
+// Description: converts a double or float to a string which, if
+// passed to NoLocaleStrtod(), will produce the exact same original double
+// (except in case of NaN; all NaNs are considered the same value).
+// We try to keep the string short but it's not guaranteed to be as
+// short as possible.
+//
+// DoubleToBuffer() and FloatToBuffer() write the text to the given
+// buffer and return it. The buffer must be at least
+// kDoubleToBufferSize bytes for doubles and kFloatToBufferSize
+// bytes for floats. kFastToBufferSize is also guaranteed to be large
+// enough to hold either.
+//
+// Return value: string
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT string SimpleDtoa(double value);
+LIBPROTOBUF_EXPORT string SimpleFtoa(float value);
+
+LIBPROTOBUF_EXPORT char* DoubleToBuffer(double i, char* buffer);
+LIBPROTOBUF_EXPORT char* FloatToBuffer(float i, char* buffer);
+
+// In practice, doubles should never need more than 24 bytes and floats
+// should never need more than 14 (including null terminators), but we
+// overestimate to be safe.
+static const int kDoubleToBufferSize = 32;
+static const int kFloatToBufferSize = 24;
+
+namespace strings {
+
+enum PadSpec {
+ NO_PAD = 1,
+ ZERO_PAD_2,
+ ZERO_PAD_3,
+ ZERO_PAD_4,
+ ZERO_PAD_5,
+ ZERO_PAD_6,
+ ZERO_PAD_7,
+ ZERO_PAD_8,
+ ZERO_PAD_9,
+ ZERO_PAD_10,
+ ZERO_PAD_11,
+ ZERO_PAD_12,
+ ZERO_PAD_13,
+ ZERO_PAD_14,
+ ZERO_PAD_15,
+ ZERO_PAD_16,
+};
+
+struct Hex {
+ uint64 value;
+ enum PadSpec spec;
+ template <class Int>
+ explicit Hex(Int v, PadSpec s = NO_PAD)
+ : spec(s) {
+ // Prevent sign-extension by casting integers to
+ // their unsigned counterparts.
+#ifdef LANG_CXX11
+ static_assert(
+ sizeof(v) == 1 || sizeof(v) == 2 || sizeof(v) == 4 || sizeof(v) == 8,
+ "Unknown integer type");
+#endif
+ value = sizeof(v) == 1 ? static_cast<uint8>(v)
+ : sizeof(v) == 2 ? static_cast<uint16>(v)
+ : sizeof(v) == 4 ? static_cast<uint32>(v)
+ : static_cast<uint64>(v);
+ }
+};
+
+struct LIBPROTOBUF_EXPORT AlphaNum {
+ const char *piece_data_; // move these to string_ref eventually
+ size_t piece_size_; // move these to string_ref eventually
+
+ char digits[kFastToBufferSize];
+
+ // No bool ctor -- bools convert to an integral type.
+ // A bool ctor would also convert incoming pointers (bletch).
+
+ AlphaNum(int32 i32)
+ : piece_data_(digits),
+ piece_size_(FastInt32ToBufferLeft(i32, digits) - &digits[0]) {}
+ AlphaNum(uint32 u32)
+ : piece_data_(digits),
+ piece_size_(FastUInt32ToBufferLeft(u32, digits) - &digits[0]) {}
+ AlphaNum(int64 i64)
+ : piece_data_(digits),
+ piece_size_(FastInt64ToBufferLeft(i64, digits) - &digits[0]) {}
+ AlphaNum(uint64 u64)
+ : piece_data_(digits),
+ piece_size_(FastUInt64ToBufferLeft(u64, digits) - &digits[0]) {}
+
+ AlphaNum(float f)
+ : piece_data_(digits), piece_size_(strlen(FloatToBuffer(f, digits))) {}
+ AlphaNum(double f)
+ : piece_data_(digits), piece_size_(strlen(DoubleToBuffer(f, digits))) {}
+
+ AlphaNum(Hex hex);
+
+ AlphaNum(const char* c_str)
+ : piece_data_(c_str), piece_size_(strlen(c_str)) {}
+ // TODO: Add a string_ref constructor, eventually
+ // AlphaNum(const StringPiece &pc) : piece(pc) {}
+
+ AlphaNum(const string& str)
+ : piece_data_(str.data()), piece_size_(str.size()) {}
+
+ AlphaNum(StringPiece str)
+ : piece_data_(str.data()), piece_size_(str.size()) {}
+
+ AlphaNum(internal::StringPiecePod str)
+ : piece_data_(str.data()), piece_size_(str.size()) {}
+
+ size_t size() const { return piece_size_; }
+ const char *data() const { return piece_data_; }
+
+ private:
+ // Use ":" not ':'
+ AlphaNum(char c); // NOLINT(runtime/explicit)
+
+ // Disallow copy and assign.
+ AlphaNum(const AlphaNum&);
+ void operator=(const AlphaNum&);
+};
+
+} // namespace strings
+
+using strings::AlphaNum;
+
+// ----------------------------------------------------------------------
+// StrCat()
+// This merges the given strings or numbers, with no delimiter. This
+// is designed to be the fastest possible way to construct a string out
+// of a mix of raw C strings, strings, bool values,
+// and numeric values.
+//
+// Don't use this for user-visible strings. The localization process
+// works poorly on strings built up out of fragments.
+//
+// For clarity and performance, don't use StrCat when appending to a
+// string. In particular, avoid using any of these (anti-)patterns:
+// str.append(StrCat(...)
+// str += StrCat(...)
+// str = StrCat(str, ...)
+// where the last is the worse, with the potential to change a loop
+// from a linear time operation with O(1) dynamic allocations into a
+// quadratic time operation with O(n) dynamic allocations. StrAppend
+// is a better choice than any of the above, subject to the restriction
+// of StrAppend(&str, a, b, c, ...) that none of the a, b, c, ... may
+// be a reference into str.
+// ----------------------------------------------------------------------
+
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b);
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b,
+ const AlphaNum& c);
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b,
+ const AlphaNum& c, const AlphaNum& d);
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b,
+ const AlphaNum& c, const AlphaNum& d,
+ const AlphaNum& e);
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b,
+ const AlphaNum& c, const AlphaNum& d,
+ const AlphaNum& e, const AlphaNum& f);
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b,
+ const AlphaNum& c, const AlphaNum& d,
+ const AlphaNum& e, const AlphaNum& f,
+ const AlphaNum& g);
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b,
+ const AlphaNum& c, const AlphaNum& d,
+ const AlphaNum& e, const AlphaNum& f,
+ const AlphaNum& g, const AlphaNum& h);
+LIBPROTOBUF_EXPORT string StrCat(const AlphaNum& a, const AlphaNum& b,
+ const AlphaNum& c, const AlphaNum& d,
+ const AlphaNum& e, const AlphaNum& f,
+ const AlphaNum& g, const AlphaNum& h,
+ const AlphaNum& i);
+
+inline string StrCat(const AlphaNum& a) { return string(a.data(), a.size()); }
+
+// ----------------------------------------------------------------------
+// StrAppend()
+// Same as above, but adds the output to the given string.
+// WARNING: For speed, StrAppend does not try to check each of its input
+// arguments to be sure that they are not a subset of the string being
+// appended to. That is, while this will work:
+//
+// string s = "foo";
+// s += s;
+//
+// This will not (necessarily) work:
+//
+// string s = "foo";
+// StrAppend(&s, s);
+//
+// Note: while StrCat supports appending up to 9 arguments, StrAppend
+// is currently limited to 4. That's rarely an issue except when
+// automatically transforming StrCat to StrAppend, and can easily be
+// worked around as consecutive calls to StrAppend are quite efficient.
+// ----------------------------------------------------------------------
+
+LIBPROTOBUF_EXPORT void StrAppend(string* dest, const AlphaNum& a);
+LIBPROTOBUF_EXPORT void StrAppend(string* dest, const AlphaNum& a,
+ const AlphaNum& b);
+LIBPROTOBUF_EXPORT void StrAppend(string* dest, const AlphaNum& a,
+ const AlphaNum& b, const AlphaNum& c);
+LIBPROTOBUF_EXPORT void StrAppend(string* dest, const AlphaNum& a,
+ const AlphaNum& b, const AlphaNum& c,
+ const AlphaNum& d);
+
+// ----------------------------------------------------------------------
+// Join()
+// These methods concatenate a range of components into a C++ string, using
+// the C-string "delim" as a separator between components.
+// ----------------------------------------------------------------------
+template <typename Iterator>
+void Join(Iterator start, Iterator end,
+ const char* delim, string* result) {
+ for (Iterator it = start; it != end; ++it) {
+ if (it != start) {
+ result->append(delim);
+ }
+ StrAppend(result, *it);
+ }
+}
+
+template <typename Range>
+string Join(const Range& components,
+ const char* delim) {
+ string result;
+ Join(components.begin(), components.end(), delim, &result);
+ return result;
+}
+
+// ----------------------------------------------------------------------
+// ToHex()
+// Return a lower-case hex string representation of the given integer.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT string ToHex(uint64 num);
+
+// ----------------------------------------------------------------------
+// GlobalReplaceSubstring()
+// Replaces all instances of a substring in a string. Does nothing
+// if 'substring' is empty. Returns the number of replacements.
+//
+// NOTE: The string pieces must not overlap s.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT int GlobalReplaceSubstring(const string& substring,
+ const string& replacement,
+ string* s);
+
+// ----------------------------------------------------------------------
+// Base64Unescape()
+// Converts "src" which is encoded in Base64 to its binary equivalent and
+// writes it to "dest". If src contains invalid characters, dest is cleared
+// and the function returns false. Returns true on success.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT bool Base64Unescape(StringPiece src, string* dest);
+
+// ----------------------------------------------------------------------
+// WebSafeBase64Unescape()
+// This is a variation of Base64Unescape which uses '-' instead of '+', and
+// '_' instead of '/'. src is not null terminated, instead specify len. I
+// recommend that slen<szdest, but we honor szdest anyway.
+// RETURNS the length of dest, or -1 if src contains invalid chars.
+
+// The variation that stores into a string clears the string first, and
+// returns false (with dest empty) if src contains invalid chars; for
+// this version src and dest must be different strings.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT int WebSafeBase64Unescape(const char* src, int slen,
+ char* dest, int szdest);
+LIBPROTOBUF_EXPORT bool WebSafeBase64Unescape(StringPiece src, string* dest);
+
+// Return the length to use for the output buffer given to the base64 escape
+// routines. Make sure to use the same value for do_padding in both.
+// This function may return incorrect results if given input_len values that
+// are extremely high, which should happen rarely.
+LIBPROTOBUF_EXPORT int CalculateBase64EscapedLen(int input_len,
+ bool do_padding);
+// Use this version when calling Base64Escape without a do_padding arg.
+LIBPROTOBUF_EXPORT int CalculateBase64EscapedLen(int input_len);
+
+// ----------------------------------------------------------------------
+// Base64Escape()
+// WebSafeBase64Escape()
+// Encode "src" to "dest" using base64 encoding.
+// src is not null terminated, instead specify len.
+// 'dest' should have at least CalculateBase64EscapedLen() length.
+// RETURNS the length of dest.
+// The WebSafe variation use '-' instead of '+' and '_' instead of '/'
+// so that we can place the out in the URL or cookies without having
+// to escape them. It also has an extra parameter "do_padding",
+// which when set to false will prevent padding with "=".
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT int Base64Escape(const unsigned char* src, int slen,
+ char* dest, int szdest);
+LIBPROTOBUF_EXPORT int WebSafeBase64Escape(
+ const unsigned char* src, int slen, char* dest,
+ int szdest, bool do_padding);
+// Encode src into dest with padding.
+LIBPROTOBUF_EXPORT void Base64Escape(StringPiece src, string* dest);
+// Encode src into dest web-safely without padding.
+LIBPROTOBUF_EXPORT void WebSafeBase64Escape(StringPiece src, string* dest);
+// Encode src into dest web-safely with padding.
+LIBPROTOBUF_EXPORT void WebSafeBase64EscapeWithPadding(StringPiece src,
+ string* dest);
+
+LIBPROTOBUF_EXPORT void Base64Escape(const unsigned char* src, int szsrc,
+ string* dest, bool do_padding);
+LIBPROTOBUF_EXPORT void WebSafeBase64Escape(const unsigned char* src, int szsrc,
+ string* dest, bool do_padding);
+
+inline bool IsValidCodePoint(uint32 code_point) {
+ return code_point < 0xD800 ||
+ (code_point >= 0xE000 && code_point <= 0x10FFFF);
+}
+
+static const int UTFmax = 4;
+// ----------------------------------------------------------------------
+// EncodeAsUTF8Char()
+// Helper to append a Unicode code point to a string as UTF8, without bringing
+// in any external dependencies. The output buffer must be as least 4 bytes
+// large.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT int EncodeAsUTF8Char(uint32 code_point, char* output);
+
+// ----------------------------------------------------------------------
+// UTF8FirstLetterNumBytes()
+// Length of the first UTF-8 character.
+// ----------------------------------------------------------------------
+LIBPROTOBUF_EXPORT int UTF8FirstLetterNumBytes(const char* src, int len);
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_STRUTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil_unittest.cc
new file mode 100644
index 0000000000..5d62fc4adf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/strutil_unittest.cc
@@ -0,0 +1,810 @@
+// 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)
+
+#include <google/protobuf/stubs/strutil.h>
+
+#include <locale.h>
+
+#include <google/protobuf/stubs/stl_util.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+#ifdef _WIN32
+#define snprintf _snprintf
+#endif
+
+namespace google {
+namespace protobuf {
+namespace {
+
+// TODO(kenton): Copy strutil tests from google3?
+
+TEST(StringUtilityTest, ImmuneToLocales) {
+ // Remember the old locale.
+ char* old_locale_cstr = setlocale(LC_NUMERIC, NULL);
+ ASSERT_TRUE(old_locale_cstr != NULL);
+ string old_locale = old_locale_cstr;
+
+ // Set the locale to "C".
+ ASSERT_TRUE(setlocale(LC_NUMERIC, "C") != NULL);
+
+ EXPECT_EQ("1.5", SimpleDtoa(1.5));
+ EXPECT_EQ("1.5", SimpleFtoa(1.5));
+
+ if (setlocale(LC_NUMERIC, "es_ES") == NULL &&
+ setlocale(LC_NUMERIC, "es_ES.utf8") == NULL) {
+ // Some systems may not have the desired locale available.
+ GOOGLE_LOG(WARNING)
+ << "Couldn't set locale to es_ES. Skipping this test.";
+ } else {
+ EXPECT_EQ("1.5", SimpleDtoa(1.5));
+ EXPECT_EQ("1.5", SimpleFtoa(1.5));
+ }
+
+ // Return to original locale.
+ setlocale(LC_NUMERIC, old_locale.c_str());
+}
+
+#define EXPECT_EQ_ARRAY(len, x, y, msg) \
+ for (int j = 0; j < len; ++j) { \
+ EXPECT_EQ(x[j], y[j]) << "" # x << " != " # y \
+ << " byte " << j << ": " << msg; \
+ }
+
+static struct {
+ int plain_length;
+ const char* plaintext;
+ const char* cyphertext;
+} base64_tests[] = {
+ // Empty string.
+ { 0, "", ""},
+
+ // Basic bit patterns;
+ // values obtained with "echo -n '...' | uuencode -m test"
+
+ { 1, "\000", "AA==" },
+ { 1, "\001", "AQ==" },
+ { 1, "\002", "Ag==" },
+ { 1, "\004", "BA==" },
+ { 1, "\010", "CA==" },
+ { 1, "\020", "EA==" },
+ { 1, "\040", "IA==" },
+ { 1, "\100", "QA==" },
+ { 1, "\200", "gA==" },
+
+ { 1, "\377", "/w==" },
+ { 1, "\376", "/g==" },
+ { 1, "\375", "/Q==" },
+ { 1, "\373", "+w==" },
+ { 1, "\367", "9w==" },
+ { 1, "\357", "7w==" },
+ { 1, "\337", "3w==" },
+ { 1, "\277", "vw==" },
+ { 1, "\177", "fw==" },
+ { 2, "\000\000", "AAA=" },
+ { 2, "\000\001", "AAE=" },
+ { 2, "\000\002", "AAI=" },
+ { 2, "\000\004", "AAQ=" },
+ { 2, "\000\010", "AAg=" },
+ { 2, "\000\020", "ABA=" },
+ { 2, "\000\040", "ACA=" },
+ { 2, "\000\100", "AEA=" },
+ { 2, "\000\200", "AIA=" },
+ { 2, "\001\000", "AQA=" },
+ { 2, "\002\000", "AgA=" },
+ { 2, "\004\000", "BAA=" },
+ { 2, "\010\000", "CAA=" },
+ { 2, "\020\000", "EAA=" },
+ { 2, "\040\000", "IAA=" },
+ { 2, "\100\000", "QAA=" },
+ { 2, "\200\000", "gAA=" },
+
+ { 2, "\377\377", "//8=" },
+ { 2, "\377\376", "//4=" },
+ { 2, "\377\375", "//0=" },
+ { 2, "\377\373", "//s=" },
+ { 2, "\377\367", "//c=" },
+ { 2, "\377\357", "/+8=" },
+ { 2, "\377\337", "/98=" },
+ { 2, "\377\277", "/78=" },
+ { 2, "\377\177", "/38=" },
+ { 2, "\376\377", "/v8=" },
+ { 2, "\375\377", "/f8=" },
+ { 2, "\373\377", "+/8=" },
+ { 2, "\367\377", "9/8=" },
+ { 2, "\357\377", "7/8=" },
+ { 2, "\337\377", "3/8=" },
+ { 2, "\277\377", "v/8=" },
+ { 2, "\177\377", "f/8=" },
+
+ { 3, "\000\000\000", "AAAA" },
+ { 3, "\000\000\001", "AAAB" },
+ { 3, "\000\000\002", "AAAC" },
+ { 3, "\000\000\004", "AAAE" },
+ { 3, "\000\000\010", "AAAI" },
+ { 3, "\000\000\020", "AAAQ" },
+ { 3, "\000\000\040", "AAAg" },
+ { 3, "\000\000\100", "AABA" },
+ { 3, "\000\000\200", "AACA" },
+ { 3, "\000\001\000", "AAEA" },
+ { 3, "\000\002\000", "AAIA" },
+ { 3, "\000\004\000", "AAQA" },
+ { 3, "\000\010\000", "AAgA" },
+ { 3, "\000\020\000", "ABAA" },
+ { 3, "\000\040\000", "ACAA" },
+ { 3, "\000\100\000", "AEAA" },
+ { 3, "\000\200\000", "AIAA" },
+ { 3, "\001\000\000", "AQAA" },
+ { 3, "\002\000\000", "AgAA" },
+ { 3, "\004\000\000", "BAAA" },
+ { 3, "\010\000\000", "CAAA" },
+ { 3, "\020\000\000", "EAAA" },
+ { 3, "\040\000\000", "IAAA" },
+ { 3, "\100\000\000", "QAAA" },
+ { 3, "\200\000\000", "gAAA" },
+
+ { 3, "\377\377\377", "////" },
+ { 3, "\377\377\376", "///+" },
+ { 3, "\377\377\375", "///9" },
+ { 3, "\377\377\373", "///7" },
+ { 3, "\377\377\367", "///3" },
+ { 3, "\377\377\357", "///v" },
+ { 3, "\377\377\337", "///f" },
+ { 3, "\377\377\277", "//+/" },
+ { 3, "\377\377\177", "//9/" },
+ { 3, "\377\376\377", "//7/" },
+ { 3, "\377\375\377", "//3/" },
+ { 3, "\377\373\377", "//v/" },
+ { 3, "\377\367\377", "//f/" },
+ { 3, "\377\357\377", "/+//" },
+ { 3, "\377\337\377", "/9//" },
+ { 3, "\377\277\377", "/7//" },
+ { 3, "\377\177\377", "/3//" },
+ { 3, "\376\377\377", "/v//" },
+ { 3, "\375\377\377", "/f//" },
+ { 3, "\373\377\377", "+///" },
+ { 3, "\367\377\377", "9///" },
+ { 3, "\357\377\377", "7///" },
+ { 3, "\337\377\377", "3///" },
+ { 3, "\277\377\377", "v///" },
+ { 3, "\177\377\377", "f///" },
+
+ // Random numbers: values obtained with
+ //
+ // #! /bin/bash
+ // dd bs=$1 count=1 if=/dev/random of=/tmp/bar.random
+ // od -N $1 -t o1 /tmp/bar.random
+ // uuencode -m test < /tmp/bar.random
+ //
+ // where $1 is the number of bytes (2, 3)
+
+ { 2, "\243\361", "o/E=" },
+ { 2, "\024\167", "FHc=" },
+ { 2, "\313\252", "y6o=" },
+ { 2, "\046\041", "JiE=" },
+ { 2, "\145\236", "ZZ4=" },
+ { 2, "\254\325", "rNU=" },
+ { 2, "\061\330", "Mdg=" },
+ { 2, "\245\032", "pRo=" },
+ { 2, "\006\000", "BgA=" },
+ { 2, "\375\131", "/Vk=" },
+ { 2, "\303\210", "w4g=" },
+ { 2, "\040\037", "IB8=" },
+ { 2, "\261\372", "sfo=" },
+ { 2, "\335\014", "3Qw=" },
+ { 2, "\233\217", "m48=" },
+ { 2, "\373\056", "+y4=" },
+ { 2, "\247\232", "p5o=" },
+ { 2, "\107\053", "Rys=" },
+ { 2, "\204\077", "hD8=" },
+ { 2, "\276\211", "vok=" },
+ { 2, "\313\110", "y0g=" },
+ { 2, "\363\376", "8/4=" },
+ { 2, "\251\234", "qZw=" },
+ { 2, "\103\262", "Q7I=" },
+ { 2, "\142\312", "Yso=" },
+ { 2, "\067\211", "N4k=" },
+ { 2, "\220\001", "kAE=" },
+ { 2, "\152\240", "aqA=" },
+ { 2, "\367\061", "9zE=" },
+ { 2, "\133\255", "W60=" },
+ { 2, "\176\035", "fh0=" },
+ { 2, "\032\231", "Gpk=" },
+
+ { 3, "\013\007\144", "Cwdk" },
+ { 3, "\030\112\106", "GEpG" },
+ { 3, "\047\325\046", "J9Um" },
+ { 3, "\310\160\022", "yHAS" },
+ { 3, "\131\100\237", "WUCf" },
+ { 3, "\064\342\134", "NOJc" },
+ { 3, "\010\177\004", "CH8E" },
+ { 3, "\345\147\205", "5WeF" },
+ { 3, "\300\343\360", "wOPw" },
+ { 3, "\061\240\201", "MaCB" },
+ { 3, "\225\333\044", "ldsk" },
+ { 3, "\215\137\352", "jV/q" },
+ { 3, "\371\147\160", "+Wdw" },
+ { 3, "\030\320\051", "GNAp" },
+ { 3, "\044\174\241", "JHyh" },
+ { 3, "\260\127\037", "sFcf" },
+ { 3, "\111\045\033", "SSUb" },
+ { 3, "\202\114\107", "gkxH" },
+ { 3, "\057\371\042", "L/ki" },
+ { 3, "\223\247\244", "k6ek" },
+ { 3, "\047\216\144", "J45k" },
+ { 3, "\203\070\327", "gzjX" },
+ { 3, "\247\140\072", "p2A6" },
+ { 3, "\124\115\116", "VE1O" },
+ { 3, "\157\162\050", "b3Io" },
+ { 3, "\357\223\004", "75ME" },
+ { 3, "\052\117\156", "Kk9u" },
+ { 3, "\347\154\000", "52wA" },
+ { 3, "\303\012\142", "wwpi" },
+ { 3, "\060\035\362", "MB3y" },
+ { 3, "\130\226\361", "WJbx" },
+ { 3, "\173\013\071", "ews5" },
+ { 3, "\336\004\027", "3gQX" },
+ { 3, "\357\366\234", "7/ac" },
+ { 3, "\353\304\111", "68RJ" },
+ { 3, "\024\264\131", "FLRZ" },
+ { 3, "\075\114\251", "PUyp" },
+ { 3, "\315\031\225", "zRmV" },
+ { 3, "\154\201\276", "bIG+" },
+ { 3, "\200\066\072", "gDY6" },
+ { 3, "\142\350\267", "Yui3" },
+ { 3, "\033\000\166", "GwB2" },
+ { 3, "\210\055\077", "iC0/" },
+ { 3, "\341\037\124", "4R9U" },
+ { 3, "\161\103\152", "cUNq" },
+ { 3, "\270\142\131", "uGJZ" },
+ { 3, "\337\076\074", "3z48" },
+ { 3, "\375\106\362", "/Uby" },
+ { 3, "\227\301\127", "l8FX" },
+ { 3, "\340\002\234", "4AKc" },
+ { 3, "\121\064\033", "UTQb" },
+ { 3, "\157\134\143", "b1xj" },
+ { 3, "\247\055\327", "py3X" },
+ { 3, "\340\142\005", "4GIF" },
+ { 3, "\060\260\143", "MLBj" },
+ { 3, "\075\203\170", "PYN4" },
+ { 3, "\143\160\016", "Y3AO" },
+ { 3, "\313\013\063", "ywsz" },
+ { 3, "\174\236\135", "fJ5d" },
+ { 3, "\103\047\026", "QycW" },
+ { 3, "\365\005\343", "9QXj" },
+ { 3, "\271\160\223", "uXCT" },
+ { 3, "\362\255\172", "8q16" },
+ { 3, "\113\012\015", "SwoN" },
+
+ // various lengths, generated by this python script:
+ //
+ // from string import lowercase as lc
+ // for i in range(27):
+ // print '{ %2d, "%s",%s "%s" },' % (i, lc[:i], ' ' * (26-i),
+ // lc[:i].encode('base64').strip())
+
+ { 0, "", "" },
+ { 1, "a", "YQ==" },
+ { 2, "ab", "YWI=" },
+ { 3, "abc", "YWJj" },
+ { 4, "abcd", "YWJjZA==" },
+ { 5, "abcde", "YWJjZGU=" },
+ { 6, "abcdef", "YWJjZGVm" },
+ { 7, "abcdefg", "YWJjZGVmZw==" },
+ { 8, "abcdefgh", "YWJjZGVmZ2g=" },
+ { 9, "abcdefghi", "YWJjZGVmZ2hp" },
+ { 10, "abcdefghij", "YWJjZGVmZ2hpag==" },
+ { 11, "abcdefghijk", "YWJjZGVmZ2hpams=" },
+ { 12, "abcdefghijkl", "YWJjZGVmZ2hpamts" },
+ { 13, "abcdefghijklm", "YWJjZGVmZ2hpamtsbQ==" },
+ { 14, "abcdefghijklmn", "YWJjZGVmZ2hpamtsbW4=" },
+ { 15, "abcdefghijklmno", "YWJjZGVmZ2hpamtsbW5v" },
+ { 16, "abcdefghijklmnop", "YWJjZGVmZ2hpamtsbW5vcA==" },
+ { 17, "abcdefghijklmnopq", "YWJjZGVmZ2hpamtsbW5vcHE=" },
+ { 18, "abcdefghijklmnopqr", "YWJjZGVmZ2hpamtsbW5vcHFy" },
+ { 19, "abcdefghijklmnopqrs", "YWJjZGVmZ2hpamtsbW5vcHFycw==" },
+ { 20, "abcdefghijklmnopqrst", "YWJjZGVmZ2hpamtsbW5vcHFyc3Q=" },
+ { 21, "abcdefghijklmnopqrstu", "YWJjZGVmZ2hpamtsbW5vcHFyc3R1" },
+ { 22, "abcdefghijklmnopqrstuv", "YWJjZGVmZ2hpamtsbW5vcHFyc3R1dg==" },
+ { 23, "abcdefghijklmnopqrstuvw", "YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnc=" },
+ { 24, "abcdefghijklmnopqrstuvwx", "YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4" },
+ { 25, "abcdefghijklmnopqrstuvwxy", "YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eQ==" },
+ { 26, "abcdefghijklmnopqrstuvwxyz", "YWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXo=" },
+};
+
+static struct {
+ const char* plaintext;
+ const char* cyphertext;
+} base64_strings[] = {
+ // Some google quotes
+ // Cyphertext created with "uuencode (GNU sharutils) 4.6.3"
+ // (Note that we're testing the websafe encoding, though, so if
+ // you add messages, be sure to run "tr -- '+/' '-_'" on the output)
+ { "I was always good at math and science, and I never realized "
+ "that was unusual or somehow undesirable. So one of the things "
+ "I care a lot about is helping to remove that stigma, "
+ "to show girls that you can be feminine, you can like the things "
+ "that girls like, but you can also be really good at technology. "
+ "You can be really good at building things."
+ " - Marissa Meyer, Newsweek, 2010-12-22" "\n",
+
+ "SSB3YXMgYWx3YXlzIGdvb2QgYXQgbWF0aCBhbmQgc2NpZW5jZSwgYW5kIEkg"
+ "bmV2ZXIgcmVhbGl6ZWQgdGhhdCB3YXMgdW51c3VhbCBvciBzb21laG93IHVu"
+ "ZGVzaXJhYmxlLiBTbyBvbmUgb2YgdGhlIHRoaW5ncyBJIGNhcmUgYSBsb3Qg"
+ "YWJvdXQgaXMgaGVscGluZyB0byByZW1vdmUgdGhhdCBzdGlnbWEsIHRvIHNo"
+ "b3cgZ2lybHMgdGhhdCB5b3UgY2FuIGJlIGZlbWluaW5lLCB5b3UgY2FuIGxp"
+ "a2UgdGhlIHRoaW5ncyB0aGF0IGdpcmxzIGxpa2UsIGJ1dCB5b3UgY2FuIGFs"
+ "c28gYmUgcmVhbGx5IGdvb2QgYXQgdGVjaG5vbG9neS4gWW91IGNhbiBiZSBy"
+ "ZWFsbHkgZ29vZCBhdCBidWlsZGluZyB0aGluZ3MuIC0gTWFyaXNzYSBNZXll"
+ "ciwgTmV3c3dlZWssIDIwMTAtMTItMjIK" },
+
+ { "Typical first year for a new cluster: "
+ "~0.5 overheating "
+ "~1 PDU failure "
+ "~1 rack-move "
+ "~1 network rewiring "
+ "~20 rack failures "
+ "~5 racks go wonky "
+ "~8 network maintenances "
+ "~12 router reloads "
+ "~3 router failures "
+ "~dozens of minor 30-second blips for dns "
+ "~1000 individual machine failures "
+ "~thousands of hard drive failures "
+ "slow disks, bad memory, misconfigured machines, flaky machines, etc."
+ " - Jeff Dean, The Joys of Real Hardware" "\n",
+
+ "VHlwaWNhbCBmaXJzdCB5ZWFyIGZvciBhIG5ldyBjbHVzdGVyOiB-MC41IG92"
+ "ZXJoZWF0aW5nIH4xIFBEVSBmYWlsdXJlIH4xIHJhY2stbW92ZSB-MSBuZXR3"
+ "b3JrIHJld2lyaW5nIH4yMCByYWNrIGZhaWx1cmVzIH41IHJhY2tzIGdvIHdv"
+ "bmt5IH44IG5ldHdvcmsgbWFpbnRlbmFuY2VzIH4xMiByb3V0ZXIgcmVsb2Fk"
+ "cyB-MyByb3V0ZXIgZmFpbHVyZXMgfmRvemVucyBvZiBtaW5vciAzMC1zZWNv"
+ "bmQgYmxpcHMgZm9yIGRucyB-MTAwMCBpbmRpdmlkdWFsIG1hY2hpbmUgZmFp"
+ "bHVyZXMgfnRob3VzYW5kcyBvZiBoYXJkIGRyaXZlIGZhaWx1cmVzIHNsb3cg"
+ "ZGlza3MsIGJhZCBtZW1vcnksIG1pc2NvbmZpZ3VyZWQgbWFjaGluZXMsIGZs"
+ "YWt5IG1hY2hpbmVzLCBldGMuIC0gSmVmZiBEZWFuLCBUaGUgSm95cyBvZiBS"
+ "ZWFsIEhhcmR3YXJlCg" },
+
+ { "I'm the head of the webspam team at Google. "
+ "That means that if you type your name into Google and get porn back, "
+ "it's my fault. Unless you're a porn star, in which case porn is a "
+ "completely reasonable response."
+ " - Matt Cutts, Google Plus" "\n",
+
+ "SSdtIHRoZSBoZWFkIG9mIHRoZSB3ZWJzcGFtIHRlYW0gYXQgR29vZ2xlLiAg"
+ "VGhhdCBtZWFucyB0aGF0IGlmIHlvdSB0eXBlIHlvdXIgbmFtZSBpbnRvIEdv"
+ "b2dsZSBhbmQgZ2V0IHBvcm4gYmFjaywgaXQncyBteSBmYXVsdC4gVW5sZXNz"
+ "IHlvdSdyZSBhIHBvcm4gc3RhciwgaW4gd2hpY2ggY2FzZSBwb3JuIGlzIGEg"
+ "Y29tcGxldGVseSByZWFzb25hYmxlIHJlc3BvbnNlLiAtIE1hdHQgQ3V0dHMs"
+ "IEdvb2dsZSBQbHVzCg" },
+
+ { "It will still be a long time before machines approach human intelligence. "
+ "But luckily, machines don't actually have to be intelligent; "
+ "they just have to fake it. Access to a wealth of information, "
+ "combined with a rudimentary decision-making capacity, "
+ "can often be almost as useful. Of course, the results are better yet "
+ "when coupled with intelligence. A reference librarian with access to "
+ "a good search engine is a formidable tool."
+ " - Craig Silverstein, Siemens Pictures of the Future, Spring 2004" "\n",
+
+ "SXQgd2lsbCBzdGlsbCBiZSBhIGxvbmcgdGltZSBiZWZvcmUgbWFjaGluZXMg"
+ "YXBwcm9hY2ggaHVtYW4gaW50ZWxsaWdlbmNlLiBCdXQgbHVja2lseSwgbWFj"
+ "aGluZXMgZG9uJ3QgYWN0dWFsbHkgaGF2ZSB0byBiZSBpbnRlbGxpZ2VudDsg"
+ "dGhleSBqdXN0IGhhdmUgdG8gZmFrZSBpdC4gQWNjZXNzIHRvIGEgd2VhbHRo"
+ "IG9mIGluZm9ybWF0aW9uLCBjb21iaW5lZCB3aXRoIGEgcnVkaW1lbnRhcnkg"
+ "ZGVjaXNpb24tbWFraW5nIGNhcGFjaXR5LCBjYW4gb2Z0ZW4gYmUgYWxtb3N0"
+ "IGFzIHVzZWZ1bC4gT2YgY291cnNlLCB0aGUgcmVzdWx0cyBhcmUgYmV0dGVy"
+ "IHlldCB3aGVuIGNvdXBsZWQgd2l0aCBpbnRlbGxpZ2VuY2UuIEEgcmVmZXJl"
+ "bmNlIGxpYnJhcmlhbiB3aXRoIGFjY2VzcyB0byBhIGdvb2Qgc2VhcmNoIGVu"
+ "Z2luZSBpcyBhIGZvcm1pZGFibGUgdG9vbC4gLSBDcmFpZyBTaWx2ZXJzdGVp"
+ "biwgU2llbWVucyBQaWN0dXJlcyBvZiB0aGUgRnV0dXJlLCBTcHJpbmcgMjAw"
+ "NAo" },
+
+ // Degenerate edge case
+ { "",
+ "" },
+};
+
+TEST(Base64, EscapeAndUnescape) {
+ // Check the short strings; this tests the math (and boundaries)
+ for (int i = 0; i < sizeof(base64_tests) / sizeof(base64_tests[0]); ++i) {
+ char encode_buffer[100];
+ int encode_length;
+ char decode_buffer[100];
+ int decode_length;
+ int cypher_length;
+ string decode_str;
+
+ const unsigned char* unsigned_plaintext =
+ reinterpret_cast<const unsigned char*>(base64_tests[i].plaintext);
+
+ StringPiece plaintext(base64_tests[i].plaintext,
+ base64_tests[i].plain_length);
+
+ cypher_length = strlen(base64_tests[i].cyphertext);
+
+ // The basic escape function:
+ memset(encode_buffer, 0, sizeof(encode_buffer));
+ encode_length = Base64Escape(unsigned_plaintext,
+ base64_tests[i].plain_length,
+ encode_buffer,
+ sizeof(encode_buffer));
+ // Is it of the expected length?
+ EXPECT_EQ(encode_length, cypher_length);
+ // Would it have been okay to allocate only CalculateBase64EscapeLen()?
+ EXPECT_EQ(CalculateBase64EscapedLen(base64_tests[i].plain_length),
+ encode_length);
+
+ // Is it the expected encoded value?
+ ASSERT_STREQ(encode_buffer, base64_tests[i].cyphertext);
+
+ // If we encode it into a buffer of exactly the right length...
+ memset(encode_buffer, 0, sizeof(encode_buffer));
+ encode_length = Base64Escape(unsigned_plaintext,
+ base64_tests[i].plain_length,
+ encode_buffer,
+ cypher_length);
+ // Is it still of the expected length?
+ EXPECT_EQ(encode_length, cypher_length);
+
+ // And is the value still correct? (i.e., not losing the last byte)
+ EXPECT_STREQ(encode_buffer, base64_tests[i].cyphertext);
+
+ // If we decode it back:
+ decode_str.clear();
+ EXPECT_TRUE(Base64Unescape(
+ StringPiece(encode_buffer, cypher_length), &decode_str));
+
+ // Is it of the expected length?
+ EXPECT_EQ(base64_tests[i].plain_length, decode_str.length());
+
+ // Is it the expected decoded value?
+ EXPECT_EQ(plaintext, decode_str);
+
+ // Let's try with a pre-populated string.
+ string encoded("this junk should be ignored");
+ Base64Escape(string(base64_tests[i].plaintext,
+ base64_tests[i].plain_length),
+ &encoded);
+ EXPECT_EQ(encoded, string(encode_buffer, cypher_length));
+
+ string decoded("this junk should be ignored");
+ EXPECT_TRUE(Base64Unescape(
+ StringPiece(encode_buffer, cypher_length), &decoded));
+ EXPECT_EQ(decoded.size(), base64_tests[i].plain_length);
+ EXPECT_EQ_ARRAY(decoded.size(), decoded, base64_tests[i].plaintext, i);
+
+ // Our decoder treats the padding '=' characters at the end as
+ // optional (but if there are any, there must be the correct
+ // number of them.) If encode_buffer has any, run some additional
+ // tests that fiddle with them.
+ char* first_equals = strchr(encode_buffer, '=');
+ if (first_equals) {
+ // How many equals signs does the string start with?
+ int equals = (*(first_equals+1) == '=') ? 2 : 1;
+
+ // Try chopping off the equals sign(s) entirely. The decoder
+ // should still be okay with this.
+ string decoded2("this junk should also be ignored");
+ *first_equals = '\0';
+ EXPECT_TRUE(Base64Unescape(
+ StringPiece(encode_buffer, first_equals - encode_buffer), &decoded2));
+ EXPECT_EQ(decoded.size(), base64_tests[i].plain_length);
+ EXPECT_EQ_ARRAY(decoded.size(), decoded, base64_tests[i].plaintext, i);
+
+ // Now test chopping off the equals sign(s) and adding
+ // whitespace. Our decoder should still accept this.
+ decoded2.assign("this junk should be ignored");
+ *first_equals = ' ';
+ *(first_equals+1) = '\0';
+ EXPECT_TRUE(Base64Unescape(
+ StringPiece(encode_buffer, first_equals - encode_buffer + 1),
+ &decoded2));
+ EXPECT_EQ(decoded.size(), base64_tests[i].plain_length);
+ EXPECT_EQ_ARRAY(decoded.size(), decoded, base64_tests[i].plaintext, i);
+
+ // Now stick a bad character at the end of the string. The decoder
+ // should refuse this string.
+ decoded2.assign("this junk should be ignored");
+ *first_equals = '?';
+ *(first_equals+1) = '\0';
+ EXPECT_TRUE(
+ !Base64Unescape(
+ StringPiece(encode_buffer, first_equals - encode_buffer + 1),
+ &decoded2));
+
+ int len;
+
+ // Test whitespace mixed with the padding. (eg "AA = = ") The
+ // decoder should accept this.
+ if (equals == 2) {
+ snprintf(first_equals, 6, " = = ");
+ len = first_equals - encode_buffer + 5;
+ } else {
+ snprintf(first_equals, 6, " = ");
+ len = first_equals - encode_buffer + 3;
+ }
+ decoded2.assign("this junk should be ignored");
+ EXPECT_TRUE(
+ Base64Unescape(StringPiece(encode_buffer, len), &decoded2));
+ EXPECT_EQ(decoded.size(), base64_tests[i].plain_length);
+ EXPECT_EQ_ARRAY(decoded.size(), decoded, base64_tests[i].plaintext, i);
+
+ // Test whitespace mixed with the padding, but with the wrong
+ // number of equals signs (eg "AA = "). The decoder should
+ // refuse these strings.
+ if (equals == 1) {
+ snprintf(first_equals, 6, " = = ");
+ len = first_equals - encode_buffer + 5;
+ } else {
+ snprintf(first_equals, 6, " = ");
+ len = first_equals - encode_buffer + 3;
+ }
+ EXPECT_TRUE(
+ !Base64Unescape(StringPiece(encode_buffer, len), &decoded2));
+ }
+
+ // Cool! the basic Base64 encoder/decoder works.
+ // Let's try the alternate alphabet: tr -- '+/' '-_'
+
+ char websafe[100];
+ memset(websafe, 0, sizeof(websafe));
+ strncpy(websafe, base64_tests[i].cyphertext, cypher_length);
+ for (int c = 0; c < sizeof(websafe); ++c) {
+ if ('+' == websafe[c]) { websafe[c] = '-'; }
+ if ('/' == websafe[c]) { websafe[c] = '_'; }
+ }
+
+ // The websafe escape function:
+ memset(encode_buffer, 0, sizeof(encode_buffer));
+ encode_length = WebSafeBase64Escape(unsigned_plaintext,
+ base64_tests[i].plain_length,
+ encode_buffer,
+ sizeof(encode_buffer),
+ true);
+ // Is it of the expected length?
+ EXPECT_EQ(encode_length, cypher_length);
+ EXPECT_EQ(
+ CalculateBase64EscapedLen(base64_tests[i].plain_length, true),
+ encode_length);
+
+ // Is it the expected encoded value?
+ EXPECT_STREQ(encode_buffer, websafe);
+
+ // If we encode it into a buffer of exactly the right length...
+ memset(encode_buffer, 0, sizeof(encode_buffer));
+ encode_length = WebSafeBase64Escape(unsigned_plaintext,
+ base64_tests[i].plain_length,
+ encode_buffer,
+ cypher_length,
+ true);
+ // Is it still of the expected length?
+ EXPECT_EQ(encode_length, cypher_length);
+
+ // And is the value still correct? (i.e., not losing the last byte)
+ EXPECT_STREQ(encode_buffer, websafe);
+
+ // Let's try the string version of the encoder
+ encoded = "this junk should be ignored";
+ WebSafeBase64Escape(
+ unsigned_plaintext, base64_tests[i].plain_length,
+ &encoded, true);
+ EXPECT_EQ(encoded.size(), cypher_length);
+ EXPECT_STREQ(encoded.c_str(), websafe);
+
+ // If we decode it back:
+ memset(decode_buffer, 0, sizeof(decode_buffer));
+ decode_length = WebSafeBase64Unescape(encode_buffer,
+ cypher_length,
+ decode_buffer,
+ sizeof(decode_buffer));
+
+ // Is it of the expected length?
+ EXPECT_EQ(decode_length, base64_tests[i].plain_length);
+
+ // Is it the expected decoded value?
+ EXPECT_EQ(0,
+ memcmp(decode_buffer, base64_tests[i].plaintext, decode_length));
+
+ // If we decode it into a buffer of exactly the right length...
+ memset(decode_buffer, 0, sizeof(decode_buffer));
+ decode_length = WebSafeBase64Unescape(encode_buffer,
+ cypher_length,
+ decode_buffer,
+ decode_length);
+
+ // Is it still of the expected length?
+ EXPECT_EQ(decode_length, base64_tests[i].plain_length);
+
+ // And is it the expected decoded value?
+ EXPECT_EQ(0,
+ memcmp(decode_buffer, base64_tests[i].plaintext, decode_length));
+
+ // Try using '.' for the pad character.
+ for (int c = cypher_length - 1; c >= 0 && '=' == encode_buffer[c]; --c) {
+ encode_buffer[c] = '.';
+ }
+
+ // If we decode it back:
+ memset(decode_buffer, 0, sizeof(decode_buffer));
+ decode_length = WebSafeBase64Unescape(encode_buffer,
+ cypher_length,
+ decode_buffer,
+ sizeof(decode_buffer));
+
+ // Is it of the expected length?
+ EXPECT_EQ(decode_length, base64_tests[i].plain_length);
+
+ // Is it the expected decoded value?
+ EXPECT_EQ(0,
+ memcmp(decode_buffer, base64_tests[i].plaintext, decode_length));
+
+ // If we decode it into a buffer of exactly the right length...
+ memset(decode_buffer, 0, sizeof(decode_buffer));
+ decode_length = WebSafeBase64Unescape(encode_buffer,
+ cypher_length,
+ decode_buffer,
+ decode_length);
+
+ // Is it still of the expected length?
+ EXPECT_EQ(decode_length, base64_tests[i].plain_length);
+
+ // And is it the expected decoded value?
+ EXPECT_EQ(0,
+ memcmp(decode_buffer, base64_tests[i].plaintext, decode_length));
+
+ // Let's try the string version of the decoder
+ decoded = "this junk should be ignored";
+ EXPECT_TRUE(WebSafeBase64Unescape(
+ StringPiece(encode_buffer, cypher_length), &decoded));
+ EXPECT_EQ(decoded.size(), base64_tests[i].plain_length);
+ EXPECT_EQ_ARRAY(decoded.size(), decoded, base64_tests[i].plaintext, i);
+
+ // Okay! the websafe Base64 encoder/decoder works.
+ // Let's try the unpadded version
+
+ for (int c = 0; c < sizeof(websafe); ++c) {
+ if ('=' == websafe[c]) {
+ websafe[c] = '\0';
+ cypher_length = c;
+ break;
+ }
+ }
+
+ // The websafe escape function:
+ memset(encode_buffer, 0, sizeof(encode_buffer));
+ encode_length = WebSafeBase64Escape(unsigned_plaintext,
+ base64_tests[i].plain_length,
+ encode_buffer,
+ sizeof(encode_buffer),
+ false);
+ // Is it of the expected length?
+ EXPECT_EQ(encode_length, cypher_length);
+ EXPECT_EQ(
+ CalculateBase64EscapedLen(base64_tests[i].plain_length, false),
+ encode_length);
+
+ // Is it the expected encoded value?
+ EXPECT_STREQ(encode_buffer, websafe);
+
+ // If we encode it into a buffer of exactly the right length...
+ memset(encode_buffer, 0, sizeof(encode_buffer));
+ encode_length = WebSafeBase64Escape(unsigned_plaintext,
+ base64_tests[i].plain_length,
+ encode_buffer,
+ cypher_length,
+ false);
+ // Is it still of the expected length?
+ EXPECT_EQ(encode_length, cypher_length);
+
+ // And is the value still correct? (i.e., not losing the last byte)
+ EXPECT_STREQ(encode_buffer, websafe);
+
+ // Let's try the (other) string version of the encoder
+ string plain(base64_tests[i].plaintext, base64_tests[i].plain_length);
+ encoded = "this junk should be ignored";
+ WebSafeBase64Escape(plain, &encoded);
+ EXPECT_EQ(encoded.size(), cypher_length);
+ EXPECT_STREQ(encoded.c_str(), websafe);
+
+ // If we decode it back:
+ memset(decode_buffer, 0, sizeof(decode_buffer));
+ decode_length = WebSafeBase64Unescape(encode_buffer,
+ cypher_length,
+ decode_buffer,
+ sizeof(decode_buffer));
+
+ // Is it of the expected length?
+ EXPECT_EQ(decode_length, base64_tests[i].plain_length);
+
+ // Is it the expected decoded value?
+ EXPECT_EQ(0,
+ memcmp(decode_buffer, base64_tests[i].plaintext, decode_length));
+
+ // If we decode it into a buffer of exactly the right length...
+ memset(decode_buffer, 0, sizeof(decode_buffer));
+ decode_length = WebSafeBase64Unescape(encode_buffer,
+ cypher_length,
+ decode_buffer,
+ decode_length);
+
+ // Is it still of the expected length?
+ EXPECT_EQ(decode_length, base64_tests[i].plain_length);
+
+ // And is it the expected decoded value?
+ EXPECT_EQ(0,
+ memcmp(decode_buffer, base64_tests[i].plaintext, decode_length));
+
+
+ // Let's try the string version of the decoder
+ decoded = "this junk should be ignored";
+ EXPECT_TRUE(WebSafeBase64Unescape(
+ StringPiece(encode_buffer, cypher_length), &decoded));
+ EXPECT_EQ(decoded.size(), base64_tests[i].plain_length);
+ EXPECT_EQ_ARRAY(decoded.size(), decoded, base64_tests[i].plaintext, i);
+
+ // This value works. Try the next.
+ }
+
+ // Now try the long strings, this tests the streaming
+ for (int i = 0; i < sizeof(base64_strings) / sizeof(base64_strings[0]);
+ ++i) {
+ const unsigned char* unsigned_plaintext =
+ reinterpret_cast<const unsigned char*>(base64_strings[i].plaintext);
+ int plain_length = strlen(base64_strings[i].plaintext);
+ int cypher_length = strlen(base64_strings[i].cyphertext);
+ vector<char> buffer(cypher_length+1);
+ int encode_length = WebSafeBase64Escape(unsigned_plaintext,
+ plain_length,
+ &buffer[0],
+ buffer.size(),
+ false);
+ EXPECT_EQ(cypher_length, encode_length);
+ EXPECT_EQ(
+ CalculateBase64EscapedLen(plain_length, false), encode_length);
+ buffer[ encode_length ] = '\0';
+ EXPECT_STREQ(base64_strings[i].cyphertext, &buffer[0]);
+ }
+
+ // Verify the behavior when decoding bad data
+ {
+ const char* bad_data = "ab-/";
+ string buf;
+ EXPECT_FALSE(Base64Unescape(StringPiece(bad_data), &buf));
+ EXPECT_TRUE(!WebSafeBase64Unescape(bad_data, &buf));
+ EXPECT_TRUE(buf.empty());
+ }
+}
+
+} // anonymous namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.cc
new file mode 100644
index 0000000000..c9d95899f5
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.cc
@@ -0,0 +1,134 @@
+// 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)
+
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+namespace strings {
+
+using internal::SubstituteArg;
+
+// Returns the number of args in arg_array which were passed explicitly
+// to Substitute().
+static int CountSubstituteArgs(const SubstituteArg* const* args_array) {
+ int count = 0;
+ while (args_array[count] != NULL && args_array[count]->size() != -1) {
+ ++count;
+ }
+ return count;
+}
+
+string Substitute(
+ const char* format,
+ const SubstituteArg& arg0, const SubstituteArg& arg1,
+ const SubstituteArg& arg2, const SubstituteArg& arg3,
+ const SubstituteArg& arg4, const SubstituteArg& arg5,
+ const SubstituteArg& arg6, const SubstituteArg& arg7,
+ const SubstituteArg& arg8, const SubstituteArg& arg9) {
+ string result;
+ SubstituteAndAppend(&result, format, arg0, arg1, arg2, arg3, arg4,
+ arg5, arg6, arg7, arg8, arg9);
+ return result;
+}
+
+void SubstituteAndAppend(
+ string* output, const char* format,
+ const SubstituteArg& arg0, const SubstituteArg& arg1,
+ const SubstituteArg& arg2, const SubstituteArg& arg3,
+ const SubstituteArg& arg4, const SubstituteArg& arg5,
+ const SubstituteArg& arg6, const SubstituteArg& arg7,
+ const SubstituteArg& arg8, const SubstituteArg& arg9) {
+ const SubstituteArg* const args_array[] = {
+ &arg0, &arg1, &arg2, &arg3, &arg4, &arg5, &arg6, &arg7, &arg8, &arg9, NULL
+ };
+
+ // Determine total size needed.
+ int size = 0;
+ for (int i = 0; format[i] != '\0'; i++) {
+ if (format[i] == '$') {
+ if (ascii_isdigit(format[i+1])) {
+ int index = format[i+1] - '0';
+ if (args_array[index]->size() == -1) {
+ GOOGLE_LOG(DFATAL)
+ << "strings::Substitute format string invalid: asked for \"$"
+ << index << "\", but only " << CountSubstituteArgs(args_array)
+ << " args were given. Full format string was: \""
+ << CEscape(format) << "\".";
+ return;
+ }
+ size += args_array[index]->size();
+ ++i; // Skip next char.
+ } else if (format[i+1] == '$') {
+ ++size;
+ ++i; // Skip next char.
+ } else {
+ GOOGLE_LOG(DFATAL)
+ << "Invalid strings::Substitute() format string: \""
+ << CEscape(format) << "\".";
+ return;
+ }
+ } else {
+ ++size;
+ }
+ }
+
+ if (size == 0) return;
+
+ // Build the string.
+ int original_size = output->size();
+ STLStringResizeUninitialized(output, original_size + size);
+ char* target = string_as_array(output) + original_size;
+ for (int i = 0; format[i] != '\0'; i++) {
+ if (format[i] == '$') {
+ if (ascii_isdigit(format[i+1])) {
+ const SubstituteArg* src = args_array[format[i+1] - '0'];
+ memcpy(target, src->data(), src->size());
+ target += src->size();
+ ++i; // Skip next char.
+ } else if (format[i+1] == '$') {
+ *target++ = '$';
+ ++i; // Skip next char.
+ }
+ } else {
+ *target++ = format[i];
+ }
+ }
+
+ GOOGLE_DCHECK_EQ(target - output->data(), output->size());
+}
+
+} // namespace strings
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.h
new file mode 100644
index 0000000000..7ee442af77
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/substitute.h
@@ -0,0 +1,170 @@
+// 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)
+// from google3/strings/substitute.h
+
+#include <string>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+
+#ifndef GOOGLE_PROTOBUF_STUBS_SUBSTITUTE_H_
+#define GOOGLE_PROTOBUF_STUBS_SUBSTITUTE_H_
+
+namespace google {
+namespace protobuf {
+namespace strings {
+
+// ----------------------------------------------------------------------
+// strings::Substitute()
+// strings::SubstituteAndAppend()
+// Kind of like StringPrintf, but different.
+//
+// Example:
+// string GetMessage(string first_name, string last_name, int age) {
+// return strings::Substitute("My name is $0 $1 and I am $2 years old.",
+// first_name, last_name, age);
+// }
+//
+// Differences from StringPrintf:
+// * The format string does not identify the types of arguments.
+// Instead, the magic of C++ deals with this for us. See below
+// for a list of accepted types.
+// * Substitutions in the format string are identified by a '$'
+// followed by a digit. So, you can use arguments out-of-order and
+// use the same argument multiple times.
+// * It's much faster than StringPrintf.
+//
+// Supported types:
+// * Strings (const char*, const string&)
+// * Note that this means you do not have to add .c_str() to all of
+// your strings. In fact, you shouldn't; it will be slower.
+// * int32, int64, uint32, uint64: Formatted using SimpleItoa().
+// * float, double: Formatted using SimpleFtoa() and SimpleDtoa().
+// * bool: Printed as "true" or "false".
+//
+// SubstituteAndAppend() is like Substitute() but appends the result to
+// *output. Example:
+//
+// string str;
+// strings::SubstituteAndAppend(&str,
+// "My name is $0 $1 and I am $2 years old.",
+// first_name, last_name, age);
+//
+// Substitute() is significantly faster than StringPrintf(). For very
+// large strings, it may be orders of magnitude faster.
+// ----------------------------------------------------------------------
+
+namespace internal { // Implementation details.
+
+class SubstituteArg {
+ public:
+ inline SubstituteArg(const char* value)
+ : text_(value), size_(strlen(text_)) {}
+ inline SubstituteArg(const string& value)
+ : text_(value.data()), size_(value.size()) {}
+
+ // Indicates that no argument was given.
+ inline explicit SubstituteArg()
+ : text_(NULL), size_(-1) {}
+
+ // Primitives
+ // We don't overload for signed and unsigned char because if people are
+ // explicitly declaring their chars as signed or unsigned then they are
+ // probably actually using them as 8-bit integers and would probably
+ // prefer an integer representation. But, we don't really know. So, we
+ // make the caller decide what to do.
+ inline SubstituteArg(char value)
+ : text_(scratch_), size_(1) { scratch_[0] = value; }
+ inline SubstituteArg(short value)
+ : text_(FastInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(unsigned short value)
+ : text_(FastUInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(int value)
+ : text_(FastInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(unsigned int value)
+ : text_(FastUInt32ToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(long value)
+ : text_(FastLongToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(unsigned long value)
+ : text_(FastULongToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(long long value)
+ : text_(FastInt64ToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(unsigned long long value)
+ : text_(FastUInt64ToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(float value)
+ : text_(FloatToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(double value)
+ : text_(DoubleToBuffer(value, scratch_)), size_(strlen(text_)) {}
+ inline SubstituteArg(bool value)
+ : text_(value ? "true" : "false"), size_(strlen(text_)) {}
+
+ inline const char* data() const { return text_; }
+ inline int size() const { return size_; }
+
+ private:
+ const char* text_;
+ int size_;
+ char scratch_[kFastToBufferSize];
+};
+
+} // namespace internal
+
+LIBPROTOBUF_EXPORT string Substitute(
+ const char* format,
+ const internal::SubstituteArg& arg0 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg1 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg2 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg3 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg4 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg5 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg6 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg7 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg8 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg9 = internal::SubstituteArg());
+
+LIBPROTOBUF_EXPORT void SubstituteAndAppend(
+ string* output, const char* format,
+ const internal::SubstituteArg& arg0 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg1 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg2 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg3 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg4 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg5 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg6 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg7 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg8 = internal::SubstituteArg(),
+ const internal::SubstituteArg& arg9 = internal::SubstituteArg());
+
+} // namespace strings
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_SUBSTITUTE_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util.h
new file mode 100644
index 0000000000..feef904bea
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util.h
@@ -0,0 +1,138 @@
+// Copyright 2005 Google Inc.
+// All rights reserved.
+//
+// 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: lar@google.com (Laramie Leavitt)
+//
+// Template metaprogramming utility functions.
+//
+// This code is compiled directly on many platforms, including client
+// platforms like Windows, Mac, and embedded systems. Before making
+// any changes here, make sure that you're not breaking any platforms.
+//
+//
+// The names chosen here reflect those used in tr1 and the boost::mpl
+// library, there are similar operations used in the Loki library as
+// well. I prefer the boost names for 2 reasons:
+// 1. I think that portions of the Boost libraries are more likely to
+// be included in the c++ standard.
+// 2. It is not impossible that some of the boost libraries will be
+// included in our own build in the future.
+// Both of these outcomes means that we may be able to directly replace
+// some of these with boost equivalents.
+//
+#ifndef GOOGLE_PROTOBUF_TEMPLATE_UTIL_H_
+#define GOOGLE_PROTOBUF_TEMPLATE_UTIL_H_
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Types small_ and big_ are guaranteed such that sizeof(small_) <
+// sizeof(big_)
+typedef char small_;
+
+struct big_ {
+ char dummy[2];
+};
+
+// Identity metafunction.
+template <class T>
+struct identity_ {
+ typedef T type;
+};
+
+// integral_constant, defined in tr1, is a wrapper for an integer
+// value. We don't really need this generality; we could get away
+// with hardcoding the integer type to bool. We use the fully
+// general integer_constant for compatibility with tr1.
+
+template<class T, T v>
+struct integral_constant {
+ static const T value = v;
+ typedef T value_type;
+ typedef integral_constant<T, v> type;
+};
+
+template <class T, T v> const T integral_constant<T, v>::value;
+
+
+// Abbreviations: true_type and false_type are structs that represent boolean
+// true and false values. Also define the boost::mpl versions of those names,
+// true_ and false_.
+typedef integral_constant<bool, true> true_type;
+typedef integral_constant<bool, false> false_type;
+typedef true_type true_;
+typedef false_type false_;
+
+// if_ is a templatized conditional statement.
+// if_<cond, A, B> is a compile time evaluation of cond.
+// if_<>::type contains A if cond is true, B otherwise.
+template<bool cond, typename A, typename B>
+struct if_{
+ typedef A type;
+};
+
+template<typename A, typename B>
+struct if_<false, A, B> {
+ typedef B type;
+};
+
+
+// type_equals_ is a template type comparator, similar to Loki IsSameType.
+// type_equals_<A, B>::value is true iff "A" is the same type as "B".
+//
+// New code should prefer base::is_same, defined in base/type_traits.h.
+// It is functionally identical, but is_same is the standard spelling.
+template<typename A, typename B>
+struct type_equals_ : public false_ {
+};
+
+template<typename A>
+struct type_equals_<A, A> : public true_ {
+};
+
+// and_ is a template && operator.
+// and_<A, B>::value evaluates "A::value && B::value".
+template<typename A, typename B>
+struct and_ : public integral_constant<bool, (A::value && B::value)> {
+};
+
+// or_ is a template || operator.
+// or_<A, B>::value evaluates "A::value || B::value".
+template<typename A, typename B>
+struct or_ : public integral_constant<bool, (A::value || B::value)> {
+};
+
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_TEMPLATE_UTIL_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util_unittest.cc
new file mode 100644
index 0000000000..b1745e2bf7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/template_util_unittest.cc
@@ -0,0 +1,130 @@
+// Copyright 2005 Google Inc.
+// All rights reserved.
+//
+// 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: lar@google.com (Laramie Leavitt)
+//
+// These tests are really compile time tests.
+// If you try to step through this in a debugger
+// you will not see any evaluations, merely that
+// value is assigned true or false sequentially.
+
+#include <google/protobuf/stubs/template_util.h>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace GOOGLE_NAMESPACE = google::protobuf::internal;
+
+namespace google {
+namespace protobuf {
+namespace internal {
+namespace {
+
+TEST(TemplateUtilTest, TestSize) {
+ EXPECT_GT(sizeof(GOOGLE_NAMESPACE::big_), sizeof(GOOGLE_NAMESPACE::small_));
+}
+
+TEST(TemplateUtilTest, TestIntegralConstants) {
+ // test the built-in types.
+ EXPECT_TRUE(true_type::value);
+ EXPECT_FALSE(false_type::value);
+
+ typedef integral_constant<int, 1> one_type;
+ EXPECT_EQ(1, one_type::value);
+}
+
+TEST(TemplateUtilTest, TestTemplateIf) {
+ typedef if_<true, true_type, false_type>::type if_true;
+ EXPECT_TRUE(if_true::value);
+
+ typedef if_<false, true_type, false_type>::type if_false;
+ EXPECT_FALSE(if_false::value);
+}
+
+TEST(TemplateUtilTest, TestTemplateTypeEquals) {
+ // Check that the TemplateTypeEquals works correctly.
+ bool value = false;
+
+ // Test the same type is true.
+ value = type_equals_<int, int>::value;
+ EXPECT_TRUE(value);
+
+ // Test different types are false.
+ value = type_equals_<float, int>::value;
+ EXPECT_FALSE(value);
+
+ // Test type aliasing.
+ typedef const int foo;
+ value = type_equals_<const foo, const int>::value;
+ EXPECT_TRUE(value);
+}
+
+TEST(TemplateUtilTest, TestTemplateAndOr) {
+ // Check that the TemplateTypeEquals works correctly.
+ bool value = false;
+
+ // Yes && Yes == true.
+ value = and_<true_, true_>::value;
+ EXPECT_TRUE(value);
+ // Yes && No == false.
+ value = and_<true_, false_>::value;
+ EXPECT_FALSE(value);
+ // No && Yes == false.
+ value = and_<false_, true_>::value;
+ EXPECT_FALSE(value);
+ // No && No == false.
+ value = and_<false_, false_>::value;
+ EXPECT_FALSE(value);
+
+ // Yes || Yes == true.
+ value = or_<true_, true_>::value;
+ EXPECT_TRUE(value);
+ // Yes || No == true.
+ value = or_<true_, false_>::value;
+ EXPECT_TRUE(value);
+ // No || Yes == true.
+ value = or_<false_, true_>::value;
+ EXPECT_TRUE(value);
+ // No || No == false.
+ value = or_<false_, false_>::value;
+ EXPECT_FALSE(value);
+}
+
+TEST(TemplateUtilTest, TestIdentity) {
+ EXPECT_TRUE(
+ (type_equals_<GOOGLE_NAMESPACE::identity_<int>::type, int>::value));
+ EXPECT_TRUE(
+ (type_equals_<GOOGLE_NAMESPACE::identity_<void>::type, void>::value));
+}
+
+} // anonymous namespace
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.cc
new file mode 100644
index 0000000000..49c0412c17
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.cc
@@ -0,0 +1,365 @@
+#include <google/protobuf/stubs/time.h>
+
+#include <ctime>
+
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+namespace {
+static const int64 kSecondsPerMinute = 60;
+static const int64 kSecondsPerHour = 3600;
+static const int64 kSecondsPerDay = kSecondsPerHour * 24;
+static const int64 kSecondsPer400Years =
+ kSecondsPerDay * (400 * 365 + 400 / 4 - 3);
+// Seconds from 0001-01-01T00:00:00 to 1970-01-01T:00:00:00
+static const int64 kSecondsFromEraToEpoch = 62135596800LL;
+// The range of timestamp values we support.
+static const int64 kMinTime = -62135596800LL; // 0001-01-01T00:00:00
+static const int64 kMaxTime = 253402300799LL; // 9999-12-31T23:59:59
+
+static const int kNanosPerMillisecond = 1000000;
+static const int kNanosPerMicrosecond = 1000;
+
+// Count the seconds from the given year (start at Jan 1, 00:00) to 100 years
+// after.
+int64 SecondsPer100Years(int year) {
+ if (year % 400 == 0 || year % 400 > 300) {
+ return kSecondsPerDay * (100 * 365 + 100 / 4);
+ } else {
+ return kSecondsPerDay * (100 * 365 + 100 / 4 - 1);
+ }
+}
+
+// Count the seconds from the given year (start at Jan 1, 00:00) to 4 years
+// after.
+int64 SecondsPer4Years(int year) {
+ if ((year % 100 == 0 || year % 100 > 96) &&
+ !(year % 400 == 0 || year % 400 > 396)) {
+ // No leap years.
+ return kSecondsPerDay * (4 * 365);
+ } else {
+ // One leap years.
+ return kSecondsPerDay * (4 * 365 + 1);
+ }
+}
+
+bool IsLeapYear(int year) {
+ return year % 400 == 0 || (year % 4 == 0 && year % 100 != 0);
+}
+
+int64 SecondsPerYear(int year) {
+ return kSecondsPerDay * (IsLeapYear(year) ? 366 : 365);
+}
+
+static const int kDaysInMonth[13] = {
+ 0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
+};
+
+int64 SecondsPerMonth(int month, bool leap) {
+ if (month == 2 && leap) {
+ return kSecondsPerDay * (kDaysInMonth[month] + 1);
+ }
+ return kSecondsPerDay * kDaysInMonth[month];
+}
+
+static const int kDaysSinceJan[13] = {
+ 0, 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334,
+};
+
+bool ValidateDateTime(const DateTime& time) {
+ if (time.year < 1 || time.year > 9999 ||
+ time.month < 1 || time.month > 12 ||
+ time.day < 1 || time.day > 31 ||
+ time.hour < 0 || time.hour > 23 ||
+ time.minute < 0 || time.minute > 59 ||
+ time.second < 0 || time.second > 59) {
+ return false;
+ }
+ if (time.month == 2 && IsLeapYear(time.year)) {
+ return time.month <= kDaysInMonth[time.month] + 1;
+ } else {
+ return time.month <= kDaysInMonth[time.month];
+ }
+}
+
+// Count the number of seconds elapsed from 0001-01-01T00:00:00 to the given
+// time.
+int64 SecondsSinceCommonEra(const DateTime& time) {
+ int64 result = 0;
+ // Years should be between 1 and 9999.
+ assert(time.year >= 1 && time.year <= 9999);
+ int year = 1;
+ if ((time.year - year) >= 400) {
+ int count_400years = (time.year - year) / 400;
+ result += kSecondsPer400Years * count_400years;
+ year += count_400years * 400;
+ }
+ while ((time.year - year) >= 100) {
+ result += SecondsPer100Years(year);
+ year += 100;
+ }
+ while ((time.year - year) >= 4) {
+ result += SecondsPer4Years(year);
+ year += 4;
+ }
+ while (time.year > year) {
+ result += SecondsPerYear(year);
+ ++year;
+ }
+ // Months should be between 1 and 12.
+ assert(time.month >= 1 && time.month <= 12);
+ int month = time.month;
+ result += kSecondsPerDay * kDaysSinceJan[month];
+ if (month > 2 && IsLeapYear(year)) {
+ result += kSecondsPerDay;
+ }
+ assert(time.day >= 1 &&
+ time.day <= (month == 2 && IsLeapYear(year)
+ ? kDaysInMonth[month] + 1
+ : kDaysInMonth[month]));
+ result += kSecondsPerDay * (time.day - 1);
+ result += kSecondsPerHour * time.hour +
+ kSecondsPerMinute * time.minute +
+ time.second;
+ return result;
+}
+
+// Format nanoseconds with either 3, 6, or 9 digits depending on the required
+// precision to represent the exact value.
+string FormatNanos(int32 nanos) {
+ if (nanos % kNanosPerMillisecond == 0) {
+ return StringPrintf("%03d", nanos / kNanosPerMillisecond);
+ } else if (nanos % kNanosPerMicrosecond == 0) {
+ return StringPrintf("%06d", nanos / kNanosPerMicrosecond);
+ } else {
+ return StringPrintf("%09d", nanos);
+ }
+}
+
+// Parses an integer from a null-terminated char sequence. The method
+// consumes at most "width" chars. Returns a pointer after the consumed
+// integer, or NULL if the data does not start with an integer or the
+// integer value does not fall in the range of [min_value, max_value].
+const char* ParseInt(const char* data, int width, int min_value,
+ int max_value, int* result) {
+ if (!ascii_isdigit(*data)) {
+ return NULL;
+ }
+ int value = 0;
+ for (int i = 0; i < width; ++i, ++data) {
+ if (ascii_isdigit(*data)) {
+ value = value * 10 + (*data - '0');
+ } else {
+ break;
+ }
+ }
+ if (value >= min_value && value <= max_value) {
+ *result = value;
+ return data;
+ } else {
+ return NULL;
+ }
+}
+
+// Consumes the fractional parts of a second into nanos. For example,
+// "010" will be parsed to 10000000 nanos.
+const char* ParseNanos(const char* data, int32* nanos) {
+ if (!ascii_isdigit(*data)) {
+ return NULL;
+ }
+ int value = 0;
+ int len = 0;
+ // Consume as many digits as there are but only take the first 9 into
+ // account.
+ while (ascii_isdigit(*data)) {
+ if (len < 9) {
+ value = value * 10 + *data - '0';
+ }
+ ++len;
+ ++data;
+ }
+ while (len < 9) {
+ value = value * 10;
+ ++len;
+ }
+ *nanos = value;
+ return data;
+}
+
+const char* ParseTimezoneOffset(const char* data, int64* offset) {
+ // Accept format "HH:MM". E.g., "08:00"
+ int hour;
+ if ((data = ParseInt(data, 2, 0, 23, &hour)) == NULL) {
+ return NULL;
+ }
+ if (*data++ != ':') {
+ return NULL;
+ }
+ int minute;
+ if ((data = ParseInt(data, 2, 0, 59, &minute)) == NULL) {
+ return NULL;
+ }
+ *offset = (hour * 60 + minute) * 60;
+ return data;
+}
+} // namespace
+
+bool SecondsToDateTime(int64 seconds, DateTime* time) {
+ if (seconds < kMinTime || seconds > kMaxTime) {
+ return false;
+ }
+ // It's easier to calcuate the DateTime starting from 0001-01-01T00:00:00
+ seconds = seconds + kSecondsFromEraToEpoch;
+ int year = 1;
+ if (seconds >= kSecondsPer400Years) {
+ int count_400years = seconds / kSecondsPer400Years;
+ year += 400 * count_400years;
+ seconds %= kSecondsPer400Years;
+ }
+ while (seconds >= SecondsPer100Years(year)) {
+ seconds -= SecondsPer100Years(year);
+ year += 100;
+ }
+ while (seconds >= SecondsPer4Years(year)) {
+ seconds -= SecondsPer4Years(year);
+ year += 4;
+ }
+ while (seconds >= SecondsPerYear(year)) {
+ seconds -= SecondsPerYear(year);
+ year += 1;
+ }
+ bool leap = IsLeapYear(year);
+ int month = 1;
+ while (seconds >= SecondsPerMonth(month, leap)) {
+ seconds -= SecondsPerMonth(month, leap);
+ ++month;
+ }
+ int day = 1 + seconds / kSecondsPerDay;
+ seconds %= kSecondsPerDay;
+ int hour = seconds / kSecondsPerHour;
+ seconds %= kSecondsPerHour;
+ int minute = seconds / kSecondsPerMinute;
+ seconds %= kSecondsPerMinute;
+ time->year = year;
+ time->month = month;
+ time->day = day;
+ time->hour = hour;
+ time->minute = minute;
+ time->second = static_cast<int>(seconds);
+ return true;
+}
+
+bool DateTimeToSeconds(const DateTime& time, int64* seconds) {
+ if (!ValidateDateTime(time)) {
+ return false;
+ }
+ *seconds = SecondsSinceCommonEra(time) - kSecondsFromEraToEpoch;
+ return true;
+}
+
+void GetCurrentTime(int64* seconds, int32* nanos) {
+ // TODO(xiaofeng): Improve the accuracy of this implementation (or just
+ // remove this method from protobuf).
+ *seconds = time(NULL);
+ *nanos = 0;
+}
+
+string FormatTime(int64 seconds, int32 nanos) {
+ DateTime time;
+ if (nanos < 0 || nanos > 999999999 || !SecondsToDateTime(seconds, &time)) {
+ return "InvalidTime";
+ }
+ string result = StringPrintf("%04d-%02d-%02dT%02d:%02d:%02d",
+ time.year, time.month, time.day,
+ time.hour, time.minute, time.second);
+ if (nanos != 0) {
+ result += "." + FormatNanos(nanos);
+ }
+ return result + "Z";
+}
+
+bool ParseTime(const string& value, int64* seconds, int32* nanos) {
+ DateTime time;
+ const char* data = value.c_str();
+ // We only accept:
+ // Z-normalized: 2015-05-20T13:29:35.120Z
+ // With UTC offset: 2015-05-20T13:29:35.120-08:00
+
+ // Parse year
+ if ((data = ParseInt(data, 4, 1, 9999, &time.year)) == NULL) {
+ return false;
+ }
+ // Expect '-'
+ if (*data++ != '-') return false;
+ // Parse month
+ if ((data = ParseInt(data, 2, 1, 12, &time.month)) == NULL) {
+ return false;
+ }
+ // Expect '-'
+ if (*data++ != '-') return false;
+ // Parse day
+ if ((data = ParseInt(data, 2, 1, 31, &time.day)) == NULL) {
+ return false;
+ }
+ // Expect 'T'
+ if (*data++ != 'T') return false;
+ // Parse hour
+ if ((data = ParseInt(data, 2, 0, 23, &time.hour)) == NULL) {
+ return false;
+ }
+ // Expect ':'
+ if (*data++ != ':') return false;
+ // Parse minute
+ if ((data = ParseInt(data, 2, 0, 59, &time.minute)) == NULL) {
+ return false;
+ }
+ // Expect ':'
+ if (*data++ != ':') return false;
+ // Parse second
+ if ((data = ParseInt(data, 2, 0, 59, &time.second)) == NULL) {
+ return false;
+ }
+ if (!DateTimeToSeconds(time, seconds)) {
+ return false;
+ }
+ // Parse nanoseconds.
+ if (*data == '.') {
+ ++data;
+ // Parse nanoseconds.
+ if ((data = ParseNanos(data, nanos)) == NULL) {
+ return false;
+ }
+ } else {
+ *nanos = 0;
+ }
+ // Parse UTC offsets.
+ if (*data == 'Z') {
+ ++data;
+ } else if (*data == '+') {
+ ++data;
+ int64 offset;
+ if ((data = ParseTimezoneOffset(data, &offset)) == NULL) {
+ return false;
+ }
+ *seconds -= offset;
+ } else if (*data == '-') {
+ ++data;
+ int64 offset;
+ if ((data = ParseTimezoneOffset(data, &offset)) == NULL) {
+ return false;
+ }
+ *seconds += offset;
+ } else {
+ return false;
+ }
+ // Done with parsing.
+ return *data == 0;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.h
new file mode 100644
index 0000000000..45607ca9bb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time.h
@@ -0,0 +1,75 @@
+// 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.
+#ifndef GOOGLE_PROTOBUF_STUBS_TIME_H_
+#define GOOGLE_PROTOBUF_STUBS_TIME_H_
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+struct DateTime {
+ int year;
+ int month;
+ int day;
+ int hour;
+ int minute;
+ int second;
+};
+
+// Converts a timestamp (seconds elapsed since 1970-01-01T00:00:00, could be
+// negative to represent time before 1970-01-01) to DateTime. Returns false
+// if the timestamp is not in the range between 0001-01-01T00:00:00 and
+// 9999-12-31T23:59:59.
+bool LIBPROTOBUF_EXPORT SecondsToDateTime(int64 seconds, DateTime* time);
+// Converts DateTime to a timestamp (seconds since 1970-01-01T00:00:00).
+// Returns false if the DateTime is not valid or is not in the valid range.
+bool LIBPROTOBUF_EXPORT DateTimeToSeconds(const DateTime& time, int64* seconds);
+
+void LIBPROTOBUF_EXPORT GetCurrentTime(int64* seconds, int32* nanos);
+
+// Formats a time string in RFC3339 fromat.
+//
+// For example, "2015-05-20T13:29:35.120Z". For nanos, 0, 3, 6 or 9 fractional
+// digits will be used depending on how many are required to represent the exact
+// value.
+//
+// Note that "nanos" must in the range of [0, 999999999].
+string LIBPROTOBUF_EXPORT FormatTime(int64 seconds, int32 nanos);
+// Parses a time string. This method accepts RFC3339 date/time string with UTC
+// offset. For example, "2015-05-20T13:29:35.120-08:00".
+bool LIBPROTOBUF_EXPORT ParseTime(const string& value, int64* seconds, int32* nanos);
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_STUBS_TIME_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time_test.cc
new file mode 100644
index 0000000000..59e9d1c73c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/time_test.cc
@@ -0,0 +1,208 @@
+// 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.
+#include <google/protobuf/stubs/time.h>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+namespace {
+static const int64 kSecondsPerDay = 3600 * 24;
+
+// For DateTime, tests will mostly focuse on the date part because that's
+// the tricky one.
+int64 CreateTimestamp(int year, int month, int day) {
+ DateTime time;
+ time.year = year;
+ time.month = month;
+ time.day = day;
+ time.hour = time.minute = time.second = 0;
+ int64 result;
+ GOOGLE_CHECK(DateTimeToSeconds(time, &result));
+ // Check that a roundtrip produces the same result.
+ GOOGLE_CHECK(SecondsToDateTime(result, &time));
+ GOOGLE_CHECK(time.year == year);
+ GOOGLE_CHECK(time.month == month);
+ GOOGLE_CHECK(time.day == day);
+ return result;
+}
+
+TEST(DateTimeTest, SimpleTime) {
+ DateTime time;
+ ASSERT_TRUE(SecondsToDateTime(1, &time));
+ EXPECT_EQ(1970, time.year);
+ EXPECT_EQ(1, time.month);
+ EXPECT_EQ(1, time.day);
+ EXPECT_EQ(0, time.hour);
+ EXPECT_EQ(0, time.minute);
+ EXPECT_EQ(1, time.second);
+ int64 seconds;
+ ASSERT_TRUE(DateTimeToSeconds(time, &seconds));
+ EXPECT_EQ(1, seconds);
+
+ ASSERT_TRUE(SecondsToDateTime(-1, &time));
+ EXPECT_EQ(1969, time.year);
+ EXPECT_EQ(12, time.month);
+ EXPECT_EQ(31, time.day);
+ EXPECT_EQ(23, time.hour);
+ EXPECT_EQ(59, time.minute);
+ EXPECT_EQ(59, time.second);
+ ASSERT_TRUE(DateTimeToSeconds(time, &seconds));
+ EXPECT_EQ(-1, seconds);
+
+ DateTime start, end;
+ start.year = 1;
+ start.month = 1;
+ start.day = 1;
+ start.hour = 0;
+ start.minute = 0;
+ start.second = 0;
+ end.year = 9999;
+ end.month = 12;
+ end.day = 31;
+ end.hour = 23;
+ end.minute = 59;
+ end.second = 59;
+ int64 start_time, end_time;
+ ASSERT_TRUE(DateTimeToSeconds(start, &start_time));
+ ASSERT_TRUE(DateTimeToSeconds(end, &end_time));
+ EXPECT_EQ(315537897599LL, end_time - start_time);
+ ASSERT_TRUE(SecondsToDateTime(start_time, &time));
+ ASSERT_TRUE(DateTimeToSeconds(time, &seconds));
+ EXPECT_EQ(start_time, seconds);
+ ASSERT_TRUE(SecondsToDateTime(end_time, &time));
+ ASSERT_TRUE(DateTimeToSeconds(time, &seconds));
+ EXPECT_EQ(end_time, seconds);
+}
+
+TEST(DateTimeTest, DayInMonths) {
+ // Check that month boundaries are handled correctly.
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 1, 1) - CreateTimestamp(2014, 12, 31));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 2, 1) - CreateTimestamp(2015, 1, 31));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 3, 1) - CreateTimestamp(2015, 2, 28));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 4, 1) - CreateTimestamp(2015, 3, 31));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 5, 1) - CreateTimestamp(2015, 4, 30));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 6, 1) - CreateTimestamp(2015, 5, 31));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 7, 1) - CreateTimestamp(2015, 6, 30));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 8, 1) - CreateTimestamp(2015, 7, 31));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 9, 1) - CreateTimestamp(2015, 8, 31));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 10, 1) - CreateTimestamp(2015, 9, 30));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 11, 1) - CreateTimestamp(2015, 10, 31));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 12, 1) - CreateTimestamp(2015, 11, 30));
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2016, 1, 1) - CreateTimestamp(2015, 12, 31));
+}
+
+TEST(DateTimeTest, LeapYear) {
+ // Non-leap year.
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2015, 3, 1) - CreateTimestamp(2015, 2, 28));
+ // Leap year.
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2016, 3, 1) - CreateTimestamp(2016, 2, 29));
+ // Non-leap year.
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2100, 3, 1) - CreateTimestamp(2100, 2, 28));
+ // Leap year.
+ EXPECT_EQ(kSecondsPerDay,
+ CreateTimestamp(2400, 3, 1) - CreateTimestamp(2400, 2, 29));
+}
+
+TEST(DateTimeTest, StringFormat) {
+ DateTime start, end;
+ start.year = 1;
+ start.month = 1;
+ start.day = 1;
+ start.hour = 0;
+ start.minute = 0;
+ start.second = 0;
+ end.year = 9999;
+ end.month = 12;
+ end.day = 31;
+ end.hour = 23;
+ end.minute = 59;
+ end.second = 59;
+ int64 start_time, end_time;
+ ASSERT_TRUE(DateTimeToSeconds(start, &start_time));
+ ASSERT_TRUE(DateTimeToSeconds(end, &end_time));
+
+ EXPECT_EQ("0001-01-01T00:00:00Z", FormatTime(start_time, 0));
+ EXPECT_EQ("9999-12-31T23:59:59Z", FormatTime(end_time, 0));
+
+ // Make sure the nanoseconds part is formated correctly.
+ EXPECT_EQ("1970-01-01T00:00:00.010Z", FormatTime(0, 10000000));
+ EXPECT_EQ("1970-01-01T00:00:00.000010Z", FormatTime(0, 10000));
+ EXPECT_EQ("1970-01-01T00:00:00.000000010Z", FormatTime(0, 10));
+}
+
+TEST(DateTimeTest, ParseString) {
+ int64 seconds;
+ int32 nanos;
+ ASSERT_TRUE(ParseTime("0001-01-01T00:00:00Z", &seconds, &nanos));
+ EXPECT_EQ("0001-01-01T00:00:00Z", FormatTime(seconds, nanos));
+ ASSERT_TRUE(ParseTime("9999-12-31T23:59:59.999999999Z", &seconds, &nanos));
+ EXPECT_EQ("9999-12-31T23:59:59.999999999Z", FormatTime(seconds, nanos));
+
+ // Test time zone offsets.
+ ASSERT_TRUE(ParseTime("1970-01-01T00:00:00-08:00", &seconds, &nanos));
+ EXPECT_EQ("1970-01-01T08:00:00Z", FormatTime(seconds, nanos));
+ ASSERT_TRUE(ParseTime("1970-01-01T00:00:00+08:00", &seconds, &nanos));
+ EXPECT_EQ("1969-12-31T16:00:00Z", FormatTime(seconds, nanos));
+
+ // Test nanoseconds.
+ ASSERT_TRUE(ParseTime("1970-01-01T00:00:00.01Z", &seconds, &nanos));
+ EXPECT_EQ("1970-01-01T00:00:00.010Z", FormatTime(seconds, nanos));
+ ASSERT_TRUE(ParseTime("1970-01-01T00:00:00.00001-08:00", &seconds, &nanos));
+ EXPECT_EQ("1970-01-01T08:00:00.000010Z", FormatTime(seconds, nanos));
+ ASSERT_TRUE(ParseTime("1970-01-01T00:00:00.00000001+08:00", &seconds, &nanos));
+ EXPECT_EQ("1969-12-31T16:00:00.000000010Z", FormatTime(seconds, nanos));
+ // Fractional parts less than 1 nanosecond will be ignored.
+ ASSERT_TRUE(ParseTime("1970-01-01T00:00:00.0123456789Z", &seconds, &nanos));
+ EXPECT_EQ("1970-01-01T00:00:00.012345678Z", FormatTime(seconds, nanos));
+}
+
+} // namespace
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits.h b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits.h
new file mode 100644
index 0000000000..0d8127e504
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits.h
@@ -0,0 +1,364 @@
+// Copyright (c) 2006, Google Inc.
+// All rights reserved.
+//
+// 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: Matt Austern
+//
+// This code is compiled directly on many platforms, including client
+// platforms like Windows, Mac, and embedded systems. Before making
+// any changes here, make sure that you're not breaking any platforms.
+//
+// Define a small subset of tr1 type traits. The traits we define are:
+// enable_if
+// is_integral
+// is_floating_point
+// is_pointer
+// is_enum
+// is_reference
+// is_pod
+// has_trivial_constructor
+// has_trivial_copy
+// has_trivial_assign
+// has_trivial_destructor
+// remove_const
+// remove_volatile
+// remove_cv
+// remove_reference
+// add_reference
+// remove_pointer
+// is_same
+// is_convertible
+// We can add more type traits as required.
+
+#ifndef GOOGLE_PROTOBUF_TYPE_TRAITS_H_
+#define GOOGLE_PROTOBUF_TYPE_TRAITS_H_
+
+#include <cstddef> // for NULL
+#include <utility> // For pair
+
+#include <google/protobuf/stubs/template_util.h> // For true_type and false_type
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+template<typename B, typename D>
+struct is_base_of {
+ typedef char (&yes)[1];
+ typedef char (&no)[2];
+
+ // BEGIN GOOGLE LOCAL MODIFICATION -- check is a #define on Mac.
+ #undef check
+ // END GOOGLE LOCAL MODIFICATION
+
+ static yes check(const B*);
+ static no check(const void*);
+
+ enum {
+ value = sizeof(check(static_cast<const D*>(NULL))) == sizeof(yes),
+ };
+};
+
+template <bool cond, class T = void> struct enable_if;
+template <class T> struct is_integral;
+template <class T> struct is_floating_point;
+template <class T> struct is_pointer;
+// MSVC can't compile this correctly, and neither can gcc 3.3.5 (at least)
+#if !defined(_MSC_VER) && !(defined(__GNUC__) && __GNUC__ <= 3)
+// is_enum uses is_convertible, which is not available on MSVC.
+template <class T> struct is_enum;
+#endif
+template <class T> struct is_reference;
+template <class T> struct is_pod;
+template <class T> struct has_trivial_constructor;
+template <class T> struct has_trivial_copy;
+template <class T> struct has_trivial_assign;
+template <class T> struct has_trivial_destructor;
+template <class T> struct remove_const;
+template <class T> struct remove_volatile;
+template <class T> struct remove_cv;
+template <class T> struct remove_reference;
+template <class T> struct add_reference;
+template <class T> struct remove_pointer;
+template <class T, class U> struct is_same;
+#if !(defined(__GNUC__) && __GNUC__ <= 3)
+template <class From, class To> struct is_convertible;
+#endif
+
+// enable_if, equivalent semantics to c++11 std::enable_if, specifically:
+// "If B is true, the member typedef type shall equal T; otherwise, there
+// shall be no member typedef type."
+// Specified by 20.9.7.6 [Other transformations]
+
+template<bool cond, class T> struct enable_if { typedef T type; };
+template<class T> struct enable_if<false, T> {};
+// is_integral is false except for the built-in integer types. A
+// cv-qualified type is integral if and only if the underlying type is.
+template <class T> struct is_integral : false_type { };
+template<> struct is_integral<bool> : true_type { };
+template<> struct is_integral<char> : true_type { };
+template<> struct is_integral<unsigned char> : true_type { };
+template<> struct is_integral<signed char> : true_type { };
+#if defined(_MSC_VER)
+// wchar_t is not by default a distinct type from unsigned short in
+// Microsoft C.
+// See http://msdn2.microsoft.com/en-us/library/dh8che7s(VS.80).aspx
+template<> struct is_integral<__wchar_t> : true_type { };
+#else
+template<> struct is_integral<wchar_t> : true_type { };
+#endif
+template<> struct is_integral<short> : true_type { };
+template<> struct is_integral<unsigned short> : true_type { };
+template<> struct is_integral<int> : true_type { };
+template<> struct is_integral<unsigned int> : true_type { };
+template<> struct is_integral<long> : true_type { };
+template<> struct is_integral<unsigned long> : true_type { };
+#ifdef HAVE_LONG_LONG
+template<> struct is_integral<long long> : true_type { };
+template<> struct is_integral<unsigned long long> : true_type { };
+#endif
+template <class T> struct is_integral<const T> : is_integral<T> { };
+template <class T> struct is_integral<volatile T> : is_integral<T> { };
+template <class T> struct is_integral<const volatile T> : is_integral<T> { };
+
+// is_floating_point is false except for the built-in floating-point types.
+// A cv-qualified type is integral if and only if the underlying type is.
+template <class T> struct is_floating_point : false_type { };
+template<> struct is_floating_point<float> : true_type { };
+template<> struct is_floating_point<double> : true_type { };
+template<> struct is_floating_point<long double> : true_type { };
+template <class T> struct is_floating_point<const T>
+ : is_floating_point<T> { };
+template <class T> struct is_floating_point<volatile T>
+ : is_floating_point<T> { };
+template <class T> struct is_floating_point<const volatile T>
+ : is_floating_point<T> { };
+
+// is_pointer is false except for pointer types. A cv-qualified type (e.g.
+// "int* const", as opposed to "int const*") is cv-qualified if and only if
+// the underlying type is.
+template <class T> struct is_pointer : false_type { };
+template <class T> struct is_pointer<T*> : true_type { };
+template <class T> struct is_pointer<const T> : is_pointer<T> { };
+template <class T> struct is_pointer<volatile T> : is_pointer<T> { };
+template <class T> struct is_pointer<const volatile T> : is_pointer<T> { };
+
+#if !defined(_MSC_VER) && !(defined(__GNUC__) && __GNUC__ <= 3)
+
+namespace type_traits_internal {
+
+template <class T> struct is_class_or_union {
+ template <class U> static small_ tester(void (U::*)());
+ template <class U> static big_ tester(...);
+ static const bool value = sizeof(tester<T>(0)) == sizeof(small_);
+};
+
+// is_convertible chokes if the first argument is an array. That's why
+// we use add_reference here.
+template <bool NotUnum, class T> struct is_enum_impl
+ : is_convertible<typename add_reference<T>::type, int> { };
+
+template <class T> struct is_enum_impl<true, T> : false_type { };
+
+} // namespace type_traits_internal
+
+// Specified by TR1 [4.5.1] primary type categories.
+
+// Implementation note:
+//
+// Each type is either void, integral, floating point, array, pointer,
+// reference, member object pointer, member function pointer, enum,
+// union or class. Out of these, only integral, floating point, reference,
+// class and enum types are potentially convertible to int. Therefore,
+// if a type is not a reference, integral, floating point or class and
+// is convertible to int, it's a enum. Adding cv-qualification to a type
+// does not change whether it's an enum.
+//
+// Is-convertible-to-int check is done only if all other checks pass,
+// because it can't be used with some types (e.g. void or classes with
+// inaccessible conversion operators).
+template <class T> struct is_enum
+ : type_traits_internal::is_enum_impl<
+ is_same<T, void>::value ||
+ is_integral<T>::value ||
+ is_floating_point<T>::value ||
+ is_reference<T>::value ||
+ type_traits_internal::is_class_or_union<T>::value,
+ T> { };
+
+template <class T> struct is_enum<const T> : is_enum<T> { };
+template <class T> struct is_enum<volatile T> : is_enum<T> { };
+template <class T> struct is_enum<const volatile T> : is_enum<T> { };
+
+#endif
+
+// is_reference is false except for reference types.
+template<typename T> struct is_reference : false_type {};
+template<typename T> struct is_reference<T&> : true_type {};
+
+
+// We can't get is_pod right without compiler help, so fail conservatively.
+// We will assume it's false except for arithmetic types, enumerations,
+// pointers and cv-qualified versions thereof. Note that std::pair<T,U>
+// is not a POD even if T and U are PODs.
+template <class T> struct is_pod
+ : integral_constant<bool, (is_integral<T>::value ||
+ is_floating_point<T>::value ||
+#if !defined(_MSC_VER) && !(defined(__GNUC__) && __GNUC__ <= 3)
+ // is_enum is not available on MSVC.
+ is_enum<T>::value ||
+#endif
+ is_pointer<T>::value)> { };
+template <class T> struct is_pod<const T> : is_pod<T> { };
+template <class T> struct is_pod<volatile T> : is_pod<T> { };
+template <class T> struct is_pod<const volatile T> : is_pod<T> { };
+
+
+// We can't get has_trivial_constructor right without compiler help, so
+// fail conservatively. We will assume it's false except for: (1) types
+// for which is_pod is true. (2) std::pair of types with trivial
+// constructors. (3) array of a type with a trivial constructor.
+// (4) const versions thereof.
+template <class T> struct has_trivial_constructor : is_pod<T> { };
+template <class T, class U> struct has_trivial_constructor<std::pair<T, U> >
+ : integral_constant<bool,
+ (has_trivial_constructor<T>::value &&
+ has_trivial_constructor<U>::value)> { };
+template <class A, int N> struct has_trivial_constructor<A[N]>
+ : has_trivial_constructor<A> { };
+template <class T> struct has_trivial_constructor<const T>
+ : has_trivial_constructor<T> { };
+
+// We can't get has_trivial_copy right without compiler help, so fail
+// conservatively. We will assume it's false except for: (1) types
+// for which is_pod is true. (2) std::pair of types with trivial copy
+// constructors. (3) array of a type with a trivial copy constructor.
+// (4) const versions thereof.
+template <class T> struct has_trivial_copy : is_pod<T> { };
+template <class T, class U> struct has_trivial_copy<std::pair<T, U> >
+ : integral_constant<bool,
+ (has_trivial_copy<T>::value &&
+ has_trivial_copy<U>::value)> { };
+template <class A, int N> struct has_trivial_copy<A[N]>
+ : has_trivial_copy<A> { };
+template <class T> struct has_trivial_copy<const T> : has_trivial_copy<T> { };
+
+// We can't get has_trivial_assign right without compiler help, so fail
+// conservatively. We will assume it's false except for: (1) types
+// for which is_pod is true. (2) std::pair of types with trivial copy
+// constructors. (3) array of a type with a trivial assign constructor.
+template <class T> struct has_trivial_assign : is_pod<T> { };
+template <class T, class U> struct has_trivial_assign<std::pair<T, U> >
+ : integral_constant<bool,
+ (has_trivial_assign<T>::value &&
+ has_trivial_assign<U>::value)> { };
+template <class A, int N> struct has_trivial_assign<A[N]>
+ : has_trivial_assign<A> { };
+
+// We can't get has_trivial_destructor right without compiler help, so
+// fail conservatively. We will assume it's false except for: (1) types
+// for which is_pod is true. (2) std::pair of types with trivial
+// destructors. (3) array of a type with a trivial destructor.
+// (4) const versions thereof.
+template <class T> struct has_trivial_destructor : is_pod<T> { };
+template <class T, class U> struct has_trivial_destructor<std::pair<T, U> >
+ : integral_constant<bool,
+ (has_trivial_destructor<T>::value &&
+ has_trivial_destructor<U>::value)> { };
+template <class A, int N> struct has_trivial_destructor<A[N]>
+ : has_trivial_destructor<A> { };
+template <class T> struct has_trivial_destructor<const T>
+ : has_trivial_destructor<T> { };
+
+// Specified by TR1 [4.7.1]
+template<typename T> struct remove_const { typedef T type; };
+template<typename T> struct remove_const<T const> { typedef T type; };
+template<typename T> struct remove_volatile { typedef T type; };
+template<typename T> struct remove_volatile<T volatile> { typedef T type; };
+template<typename T> struct remove_cv {
+ typedef typename remove_const<typename remove_volatile<T>::type>::type type;
+};
+
+
+// Specified by TR1 [4.7.2] Reference modifications.
+template<typename T> struct remove_reference { typedef T type; };
+template<typename T> struct remove_reference<T&> { typedef T type; };
+
+template <typename T> struct add_reference { typedef T& type; };
+template <typename T> struct add_reference<T&> { typedef T& type; };
+
+// Specified by TR1 [4.7.4] Pointer modifications.
+template<typename T> struct remove_pointer { typedef T type; };
+template<typename T> struct remove_pointer<T*> { typedef T type; };
+template<typename T> struct remove_pointer<T* const> { typedef T type; };
+template<typename T> struct remove_pointer<T* volatile> { typedef T type; };
+template<typename T> struct remove_pointer<T* const volatile> {
+ typedef T type; };
+
+// Specified by TR1 [4.6] Relationships between types
+template<typename T, typename U> struct is_same : public false_type { };
+template<typename T> struct is_same<T, T> : public true_type { };
+
+// Specified by TR1 [4.6] Relationships between types
+#if !(defined(__GNUC__) && __GNUC__ <= 3)
+namespace type_traits_internal {
+
+// This class is an implementation detail for is_convertible, and you
+// don't need to know how it works to use is_convertible. For those
+// who care: we declare two different functions, one whose argument is
+// of type To and one with a variadic argument list. We give them
+// return types of different size, so we can use sizeof to trick the
+// compiler into telling us which function it would have chosen if we
+// had called it with an argument of type From. See Alexandrescu's
+// _Modern C++ Design_ for more details on this sort of trick.
+
+template <typename From, typename To>
+struct ConvertHelper {
+ static small_ Test(To);
+ static big_ Test(...);
+ static From Create();
+ enum {
+ value = sizeof(Test(Create())) == sizeof(small_)
+ };
+};
+} // namespace type_traits_internal
+
+// Inherits from true_type if From is convertible to To, false_type otherwise.
+template <typename From, typename To>
+struct is_convertible
+ : integral_constant<bool,
+ type_traits_internal::ConvertHelper<From, To>::value> {
+};
+#endif
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_TYPE_TRAITS_H_
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits_unittest.cc
new file mode 100644
index 0000000000..49c10aced6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/stubs/type_traits_unittest.cc
@@ -0,0 +1,631 @@
+// Copyright (c) 2006, Google Inc.
+// All rights reserved.
+//
+// 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: Matt Austern
+
+#include <google/protobuf/stubs/type_traits.h>
+
+#include <stdlib.h> // for exit()
+#include <stdio.h>
+#include <string>
+#include <vector>
+
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+typedef int int32;
+// IBM AIX typedefs `int64` in `sys/inttypes.h`, included transitively above.
+#ifndef _AIX
+typedef long int64;
+#endif
+
+using std::string;
+using std::vector;
+using std::pair;
+
+
+// This assertion produces errors like "error: invalid use of
+// incomplete type 'struct <unnamed>::AssertTypesEq<const int, int>'"
+// when it fails.
+template<typename T, typename U> struct AssertTypesEq;
+template<typename T> struct AssertTypesEq<T, T> {};
+#define COMPILE_ASSERT_TYPES_EQ(T, U) static_cast<void>(AssertTypesEq<T, U>())
+
+// A user-defined POD type.
+struct A {
+ int n_;
+};
+
+// A user-defined non-POD type with a trivial copy constructor.
+class B {
+ public:
+ explicit B(int n) : n_(n) { }
+ private:
+ int n_;
+};
+
+// Another user-defined non-POD type with a trivial copy constructor.
+// We will explicitly declare C to have a trivial copy constructor
+// by specializing has_trivial_copy.
+class C {
+ public:
+ explicit C(int n) : n_(n) { }
+ private:
+ int n_;
+};
+
+namespace google {
+namespace protobuf {
+namespace internal {
+template<> struct has_trivial_copy<C> : true_type { };
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+// Another user-defined non-POD type with a trivial assignment operator.
+// We will explicitly declare C to have a trivial assignment operator
+// by specializing has_trivial_assign.
+class D {
+ public:
+ explicit D(int n) : n_(n) { }
+ private:
+ int n_;
+};
+
+namespace google {
+namespace protobuf {
+namespace internal {
+template<> struct has_trivial_assign<D> : true_type { };
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+// Another user-defined non-POD type with a trivial constructor.
+// We will explicitly declare E to have a trivial constructor
+// by specializing has_trivial_constructor.
+class E {
+ public:
+ int n_;
+};
+
+namespace google {
+namespace protobuf {
+namespace internal {
+template<> struct has_trivial_constructor<E> : true_type { };
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+// Another user-defined non-POD type with a trivial destructor.
+// We will explicitly declare E to have a trivial destructor
+// by specializing has_trivial_destructor.
+class F {
+ public:
+ explicit F(int n) : n_(n) { }
+ private:
+ int n_;
+};
+
+namespace google {
+namespace protobuf {
+namespace internal {
+template<> struct has_trivial_destructor<F> : true_type { };
+} // namespace internal
+} // namespace protobuf
+} // namespace google
+
+enum G {};
+
+union H {};
+
+class I {
+ public:
+ operator int() const;
+};
+
+class J {
+ private:
+ operator int() const;
+};
+
+namespace google {
+namespace protobuf {
+namespace internal {
+namespace {
+
+// A base class and a derived class that inherits from it, used for
+// testing conversion type traits.
+class Base {
+ public:
+ virtual ~Base() { }
+};
+
+class Derived : public Base {
+};
+
+TEST(TypeTraitsTest, TestIsInteger) {
+ // Verify that is_integral is true for all integer types.
+ EXPECT_TRUE(is_integral<bool>::value);
+ EXPECT_TRUE(is_integral<char>::value);
+ EXPECT_TRUE(is_integral<unsigned char>::value);
+ EXPECT_TRUE(is_integral<signed char>::value);
+ EXPECT_TRUE(is_integral<wchar_t>::value);
+ EXPECT_TRUE(is_integral<int>::value);
+ EXPECT_TRUE(is_integral<unsigned int>::value);
+ EXPECT_TRUE(is_integral<short>::value);
+ EXPECT_TRUE(is_integral<unsigned short>::value);
+ EXPECT_TRUE(is_integral<long>::value);
+ EXPECT_TRUE(is_integral<unsigned long>::value);
+
+ // Verify that is_integral is false for a few non-integer types.
+ EXPECT_FALSE(is_integral<void>::value);
+ EXPECT_FALSE(is_integral<float>::value);
+ EXPECT_FALSE(is_integral<string>::value);
+ EXPECT_FALSE(is_integral<int*>::value);
+ EXPECT_FALSE(is_integral<A>::value);
+ EXPECT_FALSE((is_integral<pair<int, int> >::value));
+
+ // Verify that cv-qualified integral types are still integral, and
+ // cv-qualified non-integral types are still non-integral.
+ EXPECT_TRUE(is_integral<const char>::value);
+ EXPECT_TRUE(is_integral<volatile bool>::value);
+ EXPECT_TRUE(is_integral<const volatile unsigned int>::value);
+ EXPECT_FALSE(is_integral<const float>::value);
+ EXPECT_FALSE(is_integral<int* volatile>::value);
+ EXPECT_FALSE(is_integral<const volatile string>::value);
+}
+
+TEST(TypeTraitsTest, TestIsFloating) {
+ // Verify that is_floating_point is true for all floating-point types.
+ EXPECT_TRUE(is_floating_point<float>::value);
+ EXPECT_TRUE(is_floating_point<double>::value);
+ EXPECT_TRUE(is_floating_point<long double>::value);
+
+ // Verify that is_floating_point is false for a few non-float types.
+ EXPECT_FALSE(is_floating_point<void>::value);
+ EXPECT_FALSE(is_floating_point<long>::value);
+ EXPECT_FALSE(is_floating_point<string>::value);
+ EXPECT_FALSE(is_floating_point<float*>::value);
+ EXPECT_FALSE(is_floating_point<A>::value);
+ EXPECT_FALSE((is_floating_point<pair<int, int> >::value));
+
+ // Verify that cv-qualified floating point types are still floating, and
+ // cv-qualified non-floating types are still non-floating.
+ EXPECT_TRUE(is_floating_point<const float>::value);
+ EXPECT_TRUE(is_floating_point<volatile double>::value);
+ EXPECT_TRUE(is_floating_point<const volatile long double>::value);
+ EXPECT_FALSE(is_floating_point<const int>::value);
+ EXPECT_FALSE(is_floating_point<volatile string>::value);
+ EXPECT_FALSE(is_floating_point<const volatile char>::value);
+}
+
+TEST(TypeTraitsTest, TestIsPointer) {
+ // Verify that is_pointer is true for some pointer types.
+ EXPECT_TRUE(is_pointer<int*>::value);
+ EXPECT_TRUE(is_pointer<void*>::value);
+ EXPECT_TRUE(is_pointer<string*>::value);
+ EXPECT_TRUE(is_pointer<const void*>::value);
+ EXPECT_TRUE(is_pointer<volatile float* const*>::value);
+
+ // Verify that is_pointer is false for some non-pointer types.
+ EXPECT_FALSE(is_pointer<void>::value);
+ EXPECT_FALSE(is_pointer<float&>::value);
+ EXPECT_FALSE(is_pointer<long>::value);
+ EXPECT_FALSE(is_pointer<vector<int*> >::value);
+ EXPECT_FALSE(is_pointer<int[5]>::value);
+
+ // A function pointer is a pointer, but a function type, or a function
+ // reference type, is not.
+ EXPECT_TRUE(is_pointer<int (*)(int x)>::value);
+ EXPECT_FALSE(is_pointer<void(char x)>::value);
+ EXPECT_FALSE(is_pointer<double (&)(string x)>::value);
+
+ // Verify that is_pointer<T> is true for some cv-qualified pointer types,
+ // and false for some cv-qualified non-pointer types.
+ EXPECT_TRUE(is_pointer<int* const>::value);
+ EXPECT_TRUE(is_pointer<const void* volatile>::value);
+ EXPECT_TRUE(is_pointer<char** const volatile>::value);
+ EXPECT_FALSE(is_pointer<const int>::value);
+ EXPECT_FALSE(is_pointer<volatile vector<int*> >::value);
+ EXPECT_FALSE(is_pointer<const volatile double>::value);
+}
+
+TEST(TypeTraitsTest, TestIsEnum) {
+// is_enum isn't supported on MSVC or gcc 3.x
+#if !defined(_MSC_VER) && !(defined(__GNUC__) && __GNUC__ <= 3)
+ // Verify that is_enum is true for enum types.
+ EXPECT_TRUE(is_enum<G>::value);
+ EXPECT_TRUE(is_enum<const G>::value);
+ EXPECT_TRUE(is_enum<volatile G>::value);
+ EXPECT_TRUE(is_enum<const volatile G>::value);
+
+ // Verify that is_enum is false for a few non-enum types.
+ EXPECT_FALSE(is_enum<void>::value);
+ EXPECT_FALSE(is_enum<G&>::value);
+ EXPECT_FALSE(is_enum<G[1]>::value);
+ EXPECT_FALSE(is_enum<const G[1]>::value);
+ EXPECT_FALSE(is_enum<G[]>::value);
+ EXPECT_FALSE(is_enum<int>::value);
+ EXPECT_FALSE(is_enum<float>::value);
+ EXPECT_FALSE(is_enum<A>::value);
+ EXPECT_FALSE(is_enum<A*>::value);
+ EXPECT_FALSE(is_enum<const A>::value);
+ EXPECT_FALSE(is_enum<H>::value);
+ EXPECT_FALSE(is_enum<I>::value);
+ EXPECT_FALSE(is_enum<J>::value);
+ EXPECT_FALSE(is_enum<void()>::value);
+ EXPECT_FALSE(is_enum<void(*)()>::value);
+ EXPECT_FALSE(is_enum<int A::*>::value);
+ EXPECT_FALSE(is_enum<void (A::*)()>::value);
+#endif
+}
+
+TEST(TypeTraitsTest, TestIsReference) {
+ // Verifies that is_reference is true for all reference types.
+ typedef float& RefFloat;
+ EXPECT_TRUE(is_reference<float&>::value);
+ EXPECT_TRUE(is_reference<const int&>::value);
+ EXPECT_TRUE(is_reference<const int*&>::value);
+ EXPECT_TRUE(is_reference<int (&)(bool)>::value);
+ EXPECT_TRUE(is_reference<RefFloat>::value);
+ EXPECT_TRUE(is_reference<const RefFloat>::value);
+ EXPECT_TRUE(is_reference<volatile RefFloat>::value);
+ EXPECT_TRUE(is_reference<const volatile RefFloat>::value);
+
+
+ // Verifies that is_reference is false for all non-reference types.
+ EXPECT_FALSE(is_reference<float>::value);
+ EXPECT_FALSE(is_reference<const float>::value);
+ EXPECT_FALSE(is_reference<volatile float>::value);
+ EXPECT_FALSE(is_reference<const volatile float>::value);
+ EXPECT_FALSE(is_reference<const int*>::value);
+ EXPECT_FALSE(is_reference<int()>::value);
+ EXPECT_FALSE(is_reference<void(*)(const char&)>::value);
+}
+
+TEST(TypeTraitsTest, TestAddReference) {
+ COMPILE_ASSERT_TYPES_EQ(int&, add_reference<int>::type);
+ COMPILE_ASSERT_TYPES_EQ(const int&, add_reference<const int>::type);
+ COMPILE_ASSERT_TYPES_EQ(volatile int&,
+ add_reference<volatile int>::type);
+ COMPILE_ASSERT_TYPES_EQ(const volatile int&,
+ add_reference<const volatile int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int&, add_reference<int&>::type);
+ COMPILE_ASSERT_TYPES_EQ(const int&, add_reference<const int&>::type);
+ COMPILE_ASSERT_TYPES_EQ(volatile int&,
+ add_reference<volatile int&>::type);
+ COMPILE_ASSERT_TYPES_EQ(const volatile int&,
+ add_reference<const volatile int&>::type);
+}
+
+TEST(TypeTraitsTest, TestIsPod) {
+ // Verify that arithmetic types and pointers are marked as PODs.
+ EXPECT_TRUE(is_pod<bool>::value);
+ EXPECT_TRUE(is_pod<char>::value);
+ EXPECT_TRUE(is_pod<unsigned char>::value);
+ EXPECT_TRUE(is_pod<signed char>::value);
+ EXPECT_TRUE(is_pod<wchar_t>::value);
+ EXPECT_TRUE(is_pod<int>::value);
+ EXPECT_TRUE(is_pod<unsigned int>::value);
+ EXPECT_TRUE(is_pod<short>::value);
+ EXPECT_TRUE(is_pod<unsigned short>::value);
+ EXPECT_TRUE(is_pod<long>::value);
+ EXPECT_TRUE(is_pod<unsigned long>::value);
+ EXPECT_TRUE(is_pod<float>::value);
+ EXPECT_TRUE(is_pod<double>::value);
+ EXPECT_TRUE(is_pod<long double>::value);
+ EXPECT_TRUE(is_pod<string*>::value);
+ EXPECT_TRUE(is_pod<A*>::value);
+ EXPECT_TRUE(is_pod<const B*>::value);
+ EXPECT_TRUE(is_pod<C**>::value);
+ EXPECT_TRUE(is_pod<const int>::value);
+ EXPECT_TRUE(is_pod<char* volatile>::value);
+ EXPECT_TRUE(is_pod<const volatile double>::value);
+#if !defined(_MSC_VER) && !(defined(__GNUC__) && __GNUC__ <= 3)
+ EXPECT_TRUE(is_pod<G>::value);
+ EXPECT_TRUE(is_pod<const G>::value);
+ EXPECT_TRUE(is_pod<volatile G>::value);
+ EXPECT_TRUE(is_pod<const volatile G>::value);
+#endif
+
+ // Verify that some non-POD types are not marked as PODs.
+ EXPECT_FALSE(is_pod<void>::value);
+ EXPECT_FALSE(is_pod<string>::value);
+ EXPECT_FALSE((is_pod<pair<int, int> >::value));
+ EXPECT_FALSE(is_pod<A>::value);
+ EXPECT_FALSE(is_pod<B>::value);
+ EXPECT_FALSE(is_pod<C>::value);
+ EXPECT_FALSE(is_pod<const string>::value);
+ EXPECT_FALSE(is_pod<volatile A>::value);
+ EXPECT_FALSE(is_pod<const volatile B>::value);
+}
+
+TEST(TypeTraitsTest, TestHasTrivialConstructor) {
+ // Verify that arithmetic types and pointers have trivial constructors.
+ EXPECT_TRUE(has_trivial_constructor<bool>::value);
+ EXPECT_TRUE(has_trivial_constructor<char>::value);
+ EXPECT_TRUE(has_trivial_constructor<unsigned char>::value);
+ EXPECT_TRUE(has_trivial_constructor<signed char>::value);
+ EXPECT_TRUE(has_trivial_constructor<wchar_t>::value);
+ EXPECT_TRUE(has_trivial_constructor<int>::value);
+ EXPECT_TRUE(has_trivial_constructor<unsigned int>::value);
+ EXPECT_TRUE(has_trivial_constructor<short>::value);
+ EXPECT_TRUE(has_trivial_constructor<unsigned short>::value);
+ EXPECT_TRUE(has_trivial_constructor<long>::value);
+ EXPECT_TRUE(has_trivial_constructor<unsigned long>::value);
+ EXPECT_TRUE(has_trivial_constructor<float>::value);
+ EXPECT_TRUE(has_trivial_constructor<double>::value);
+ EXPECT_TRUE(has_trivial_constructor<long double>::value);
+ EXPECT_TRUE(has_trivial_constructor<string*>::value);
+ EXPECT_TRUE(has_trivial_constructor<A*>::value);
+ EXPECT_TRUE(has_trivial_constructor<const B*>::value);
+ EXPECT_TRUE(has_trivial_constructor<C**>::value);
+
+ // Verify that pairs and arrays of such types have trivial
+ // constructors.
+ typedef int int10[10];
+ EXPECT_TRUE((has_trivial_constructor<pair<int, char*> >::value));
+ EXPECT_TRUE(has_trivial_constructor<int10>::value);
+
+ // Verify that pairs of types without trivial constructors
+ // are not marked as trivial.
+ EXPECT_FALSE((has_trivial_constructor<pair<int, string> >::value));
+ EXPECT_FALSE((has_trivial_constructor<pair<string, int> >::value));
+
+ // Verify that types without trivial constructors are
+ // correctly marked as such.
+ EXPECT_FALSE(has_trivial_constructor<string>::value);
+ EXPECT_FALSE(has_trivial_constructor<vector<int> >::value);
+
+ // Verify that E, which we have declared to have a trivial
+ // constructor, is correctly marked as such.
+ EXPECT_TRUE(has_trivial_constructor<E>::value);
+}
+
+TEST(TypeTraitsTest, TestHasTrivialCopy) {
+ // Verify that arithmetic types and pointers have trivial copy
+ // constructors.
+ EXPECT_TRUE(has_trivial_copy<bool>::value);
+ EXPECT_TRUE(has_trivial_copy<char>::value);
+ EXPECT_TRUE(has_trivial_copy<unsigned char>::value);
+ EXPECT_TRUE(has_trivial_copy<signed char>::value);
+ EXPECT_TRUE(has_trivial_copy<wchar_t>::value);
+ EXPECT_TRUE(has_trivial_copy<int>::value);
+ EXPECT_TRUE(has_trivial_copy<unsigned int>::value);
+ EXPECT_TRUE(has_trivial_copy<short>::value);
+ EXPECT_TRUE(has_trivial_copy<unsigned short>::value);
+ EXPECT_TRUE(has_trivial_copy<long>::value);
+ EXPECT_TRUE(has_trivial_copy<unsigned long>::value);
+ EXPECT_TRUE(has_trivial_copy<float>::value);
+ EXPECT_TRUE(has_trivial_copy<double>::value);
+ EXPECT_TRUE(has_trivial_copy<long double>::value);
+ EXPECT_TRUE(has_trivial_copy<string*>::value);
+ EXPECT_TRUE(has_trivial_copy<A*>::value);
+ EXPECT_TRUE(has_trivial_copy<const B*>::value);
+ EXPECT_TRUE(has_trivial_copy<C**>::value);
+
+ // Verify that pairs and arrays of such types have trivial
+ // copy constructors.
+ typedef int int10[10];
+ EXPECT_TRUE((has_trivial_copy<pair<int, char*> >::value));
+ EXPECT_TRUE(has_trivial_copy<int10>::value);
+
+ // Verify that pairs of types without trivial copy constructors
+ // are not marked as trivial.
+ EXPECT_FALSE((has_trivial_copy<pair<int, string> >::value));
+ EXPECT_FALSE((has_trivial_copy<pair<string, int> >::value));
+
+ // Verify that types without trivial copy constructors are
+ // correctly marked as such.
+ EXPECT_FALSE(has_trivial_copy<string>::value);
+ EXPECT_FALSE(has_trivial_copy<vector<int> >::value);
+
+ // Verify that C, which we have declared to have a trivial
+ // copy constructor, is correctly marked as such.
+ EXPECT_TRUE(has_trivial_copy<C>::value);
+}
+
+TEST(TypeTraitsTest, TestHasTrivialAssign) {
+ // Verify that arithmetic types and pointers have trivial assignment
+ // operators.
+ EXPECT_TRUE(has_trivial_assign<bool>::value);
+ EXPECT_TRUE(has_trivial_assign<char>::value);
+ EXPECT_TRUE(has_trivial_assign<unsigned char>::value);
+ EXPECT_TRUE(has_trivial_assign<signed char>::value);
+ EXPECT_TRUE(has_trivial_assign<wchar_t>::value);
+ EXPECT_TRUE(has_trivial_assign<int>::value);
+ EXPECT_TRUE(has_trivial_assign<unsigned int>::value);
+ EXPECT_TRUE(has_trivial_assign<short>::value);
+ EXPECT_TRUE(has_trivial_assign<unsigned short>::value);
+ EXPECT_TRUE(has_trivial_assign<long>::value);
+ EXPECT_TRUE(has_trivial_assign<unsigned long>::value);
+ EXPECT_TRUE(has_trivial_assign<float>::value);
+ EXPECT_TRUE(has_trivial_assign<double>::value);
+ EXPECT_TRUE(has_trivial_assign<long double>::value);
+ EXPECT_TRUE(has_trivial_assign<string*>::value);
+ EXPECT_TRUE(has_trivial_assign<A*>::value);
+ EXPECT_TRUE(has_trivial_assign<const B*>::value);
+ EXPECT_TRUE(has_trivial_assign<C**>::value);
+
+ // Verify that pairs and arrays of such types have trivial
+ // assignment operators.
+ typedef int int10[10];
+ EXPECT_TRUE((has_trivial_assign<pair<int, char*> >::value));
+ EXPECT_TRUE(has_trivial_assign<int10>::value);
+
+ // Verify that pairs of types without trivial assignment operators
+ // are not marked as trivial.
+ EXPECT_FALSE((has_trivial_assign<pair<int, string> >::value));
+ EXPECT_FALSE((has_trivial_assign<pair<string, int> >::value));
+
+ // Verify that types without trivial assignment operators are
+ // correctly marked as such.
+ EXPECT_FALSE(has_trivial_assign<string>::value);
+ EXPECT_FALSE(has_trivial_assign<vector<int> >::value);
+
+ // Verify that D, which we have declared to have a trivial
+ // assignment operator, is correctly marked as such.
+ EXPECT_TRUE(has_trivial_assign<D>::value);
+}
+
+TEST(TypeTraitsTest, TestHasTrivialDestructor) {
+ // Verify that arithmetic types and pointers have trivial destructors.
+ EXPECT_TRUE(has_trivial_destructor<bool>::value);
+ EXPECT_TRUE(has_trivial_destructor<char>::value);
+ EXPECT_TRUE(has_trivial_destructor<unsigned char>::value);
+ EXPECT_TRUE(has_trivial_destructor<signed char>::value);
+ EXPECT_TRUE(has_trivial_destructor<wchar_t>::value);
+ EXPECT_TRUE(has_trivial_destructor<int>::value);
+ EXPECT_TRUE(has_trivial_destructor<unsigned int>::value);
+ EXPECT_TRUE(has_trivial_destructor<short>::value);
+ EXPECT_TRUE(has_trivial_destructor<unsigned short>::value);
+ EXPECT_TRUE(has_trivial_destructor<long>::value);
+ EXPECT_TRUE(has_trivial_destructor<unsigned long>::value);
+ EXPECT_TRUE(has_trivial_destructor<float>::value);
+ EXPECT_TRUE(has_trivial_destructor<double>::value);
+ EXPECT_TRUE(has_trivial_destructor<long double>::value);
+ EXPECT_TRUE(has_trivial_destructor<string*>::value);
+ EXPECT_TRUE(has_trivial_destructor<A*>::value);
+ EXPECT_TRUE(has_trivial_destructor<const B*>::value);
+ EXPECT_TRUE(has_trivial_destructor<C**>::value);
+
+ // Verify that pairs and arrays of such types have trivial
+ // destructors.
+ typedef int int10[10];
+ EXPECT_TRUE((has_trivial_destructor<pair<int, char*> >::value));
+ EXPECT_TRUE(has_trivial_destructor<int10>::value);
+
+ // Verify that pairs of types without trivial destructors
+ // are not marked as trivial.
+ EXPECT_FALSE((has_trivial_destructor<pair<int, string> >::value));
+ EXPECT_FALSE((has_trivial_destructor<pair<string, int> >::value));
+
+ // Verify that types without trivial destructors are
+ // correctly marked as such.
+ EXPECT_FALSE(has_trivial_destructor<string>::value);
+ EXPECT_FALSE(has_trivial_destructor<vector<int> >::value);
+
+ // Verify that F, which we have declared to have a trivial
+ // destructor, is correctly marked as such.
+ EXPECT_TRUE(has_trivial_destructor<F>::value);
+}
+
+// Tests remove_pointer.
+TEST(TypeTraitsTest, TestRemovePointer) {
+ COMPILE_ASSERT_TYPES_EQ(int, remove_pointer<int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_pointer<int*>::type);
+ COMPILE_ASSERT_TYPES_EQ(const int, remove_pointer<const int*>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_pointer<int* const>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_pointer<int* volatile>::type);
+}
+
+TEST(TypeTraitsTest, TestRemoveConst) {
+ COMPILE_ASSERT_TYPES_EQ(int, remove_const<int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_const<const int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int *, remove_const<int * const>::type);
+ // TR1 examples.
+ COMPILE_ASSERT_TYPES_EQ(const int *, remove_const<const int *>::type);
+ COMPILE_ASSERT_TYPES_EQ(volatile int,
+ remove_const<const volatile int>::type);
+}
+
+TEST(TypeTraitsTest, TestRemoveVolatile) {
+ COMPILE_ASSERT_TYPES_EQ(int, remove_volatile<int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_volatile<volatile int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int *, remove_volatile<int * volatile>::type);
+ // TR1 examples.
+ COMPILE_ASSERT_TYPES_EQ(volatile int *,
+ remove_volatile<volatile int *>::type);
+ COMPILE_ASSERT_TYPES_EQ(const int,
+ remove_volatile<const volatile int>::type);
+}
+
+TEST(TypeTraitsTest, TestRemoveCV) {
+ COMPILE_ASSERT_TYPES_EQ(int, remove_cv<int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_cv<volatile int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_cv<const int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int *, remove_cv<int * const volatile>::type);
+ // TR1 examples.
+ COMPILE_ASSERT_TYPES_EQ(const volatile int *,
+ remove_cv<const volatile int *>::type);
+ COMPILE_ASSERT_TYPES_EQ(int,
+ remove_cv<const volatile int>::type);
+}
+
+TEST(TypeTraitsTest, TestRemoveReference) {
+ COMPILE_ASSERT_TYPES_EQ(int, remove_reference<int>::type);
+ COMPILE_ASSERT_TYPES_EQ(int, remove_reference<int&>::type);
+ COMPILE_ASSERT_TYPES_EQ(const int, remove_reference<const int&>::type);
+ COMPILE_ASSERT_TYPES_EQ(int*, remove_reference<int * &>::type);
+}
+
+TEST(TypeTraitsTest, TestIsSame) {
+ EXPECT_TRUE((is_same<int32, int32>::value));
+ EXPECT_FALSE((is_same<int32, int64>::value));
+ EXPECT_FALSE((is_same<int64, int32>::value));
+ EXPECT_FALSE((is_same<int, const int>::value));
+
+ EXPECT_TRUE((is_same<void, void>::value));
+ EXPECT_FALSE((is_same<void, int>::value));
+ EXPECT_FALSE((is_same<int, void>::value));
+
+ EXPECT_TRUE((is_same<int*, int*>::value));
+ EXPECT_TRUE((is_same<void*, void*>::value));
+ EXPECT_FALSE((is_same<int*, void*>::value));
+ EXPECT_FALSE((is_same<void*, int*>::value));
+ EXPECT_FALSE((is_same<void*, const void*>::value));
+ EXPECT_FALSE((is_same<void*, void* const>::value));
+
+ EXPECT_TRUE((is_same<Base*, Base*>::value));
+ EXPECT_TRUE((is_same<Derived*, Derived*>::value));
+ EXPECT_FALSE((is_same<Base*, Derived*>::value));
+ EXPECT_FALSE((is_same<Derived*, Base*>::value));
+}
+
+TEST(TypeTraitsTest, TestConvertible) {
+#if !(defined(__GNUC__) && __GNUC__ <= 3)
+ EXPECT_TRUE((is_convertible<int, int>::value));
+ EXPECT_TRUE((is_convertible<int, long>::value));
+ EXPECT_TRUE((is_convertible<long, int>::value));
+
+ EXPECT_TRUE((is_convertible<int*, void*>::value));
+ EXPECT_FALSE((is_convertible<void*, int*>::value));
+
+ EXPECT_TRUE((is_convertible<Derived*, Base*>::value));
+ EXPECT_FALSE((is_convertible<Base*, Derived*>::value));
+ EXPECT_TRUE((is_convertible<Derived*, const Base*>::value));
+ EXPECT_FALSE((is_convertible<const Derived*, Base*>::value));
+#endif
+}
+
+} // anonymous namespace
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/test_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/test_util.cc
new file mode 100644
index 0000000000..658c8ee285
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/test_util.cc
@@ -0,0 +1,3350 @@
+// 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.
+
+#ifdef _WIN32
+// Verify that #including windows.h does not break anything (e.g. because
+// windows.h #defines GetMessage() as a macro).
+#include <windows.h>
+#endif
+
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+void TestUtil::SetAllFields(unittest::TestAllTypes* message) {
+ SetOptionalFields(message);
+ AddRepeatedFields1(message);
+ AddRepeatedFields2(message);
+ SetDefaultFields(message);
+ SetOneofFields(message);
+}
+
+void TestUtil::SetOptionalFields(unittest::TestAllTypes* message) {
+ message->set_optional_int32 (101);
+ message->set_optional_int64 (102);
+ message->set_optional_uint32 (103);
+ message->set_optional_uint64 (104);
+ message->set_optional_sint32 (105);
+ message->set_optional_sint64 (106);
+ message->set_optional_fixed32 (107);
+ message->set_optional_fixed64 (108);
+ message->set_optional_sfixed32(109);
+ message->set_optional_sfixed64(110);
+ message->set_optional_float (111);
+ message->set_optional_double (112);
+ message->set_optional_bool (true);
+ message->set_optional_string ("115");
+ message->set_optional_bytes ("116");
+
+ message->mutable_optionalgroup ()->set_a(117);
+ message->mutable_optional_nested_message ()->set_bb(118);
+ message->mutable_optional_foreign_message ()->set_c(119);
+ message->mutable_optional_import_message ()->set_d(120);
+ message->mutable_optional_public_import_message()->set_e(126);
+ message->mutable_optional_lazy_message ()->set_bb(127);
+
+ message->set_optional_nested_enum (unittest::TestAllTypes::BAZ);
+ message->set_optional_foreign_enum(unittest::FOREIGN_BAZ );
+ message->set_optional_import_enum (unittest_import::IMPORT_BAZ);
+
+ // StringPiece and Cord fields are only accessible via reflection in the
+ // open source release; see comments in compiler/cpp/string_field.cc.
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ message->GetReflection()->SetString(
+ message,
+ message->GetDescriptor()->FindFieldByName("optional_string_piece"),
+ "124");
+ message->GetReflection()->SetString(
+ message,
+ message->GetDescriptor()->FindFieldByName("optional_cord"),
+ "125");
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::AddRepeatedFields1(unittest::TestAllTypes* message) {
+ message->add_repeated_int32 (201);
+ message->add_repeated_int64 (202);
+ message->add_repeated_uint32 (203);
+ message->add_repeated_uint64 (204);
+ message->add_repeated_sint32 (205);
+ message->add_repeated_sint64 (206);
+ message->add_repeated_fixed32 (207);
+ message->add_repeated_fixed64 (208);
+ message->add_repeated_sfixed32(209);
+ message->add_repeated_sfixed64(210);
+ message->add_repeated_float (211);
+ message->add_repeated_double (212);
+ message->add_repeated_bool (true);
+ message->add_repeated_string ("215");
+ message->add_repeated_bytes ("216");
+
+ message->add_repeatedgroup ()->set_a(217);
+ message->add_repeated_nested_message ()->set_bb(218);
+ message->add_repeated_foreign_message()->set_c(219);
+ message->add_repeated_import_message ()->set_d(220);
+ message->add_repeated_lazy_message ()->set_bb(227);
+
+ message->add_repeated_nested_enum (unittest::TestAllTypes::BAR);
+ message->add_repeated_foreign_enum(unittest::FOREIGN_BAR );
+ message->add_repeated_import_enum (unittest_import::IMPORT_BAR);
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ message->GetReflection()->AddString(
+ message,
+ message->GetDescriptor()->FindFieldByName("repeated_string_piece"),
+ "224");
+ message->GetReflection()->AddString(
+ message,
+ message->GetDescriptor()->FindFieldByName("repeated_cord"),
+ "225");
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+}
+
+void TestUtil::AddRepeatedFields2(unittest::TestAllTypes* message) {
+ // Add a second one of each field.
+ message->add_repeated_int32 (301);
+ message->add_repeated_int64 (302);
+ message->add_repeated_uint32 (303);
+ message->add_repeated_uint64 (304);
+ message->add_repeated_sint32 (305);
+ message->add_repeated_sint64 (306);
+ message->add_repeated_fixed32 (307);
+ message->add_repeated_fixed64 (308);
+ message->add_repeated_sfixed32(309);
+ message->add_repeated_sfixed64(310);
+ message->add_repeated_float (311);
+ message->add_repeated_double (312);
+ message->add_repeated_bool (false);
+ message->add_repeated_string ("315");
+ message->add_repeated_bytes ("316");
+
+ message->add_repeatedgroup ()->set_a(317);
+ message->add_repeated_nested_message ()->set_bb(318);
+ message->add_repeated_foreign_message()->set_c(319);
+ message->add_repeated_import_message ()->set_d(320);
+ message->add_repeated_lazy_message ()->set_bb(327);
+
+ message->add_repeated_nested_enum (unittest::TestAllTypes::BAZ);
+ message->add_repeated_foreign_enum(unittest::FOREIGN_BAZ );
+ message->add_repeated_import_enum (unittest_import::IMPORT_BAZ);
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ message->GetReflection()->AddString(
+ message,
+ message->GetDescriptor()->FindFieldByName("repeated_string_piece"),
+ "324");
+ message->GetReflection()->AddString(
+ message,
+ message->GetDescriptor()->FindFieldByName("repeated_cord"),
+ "325");
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::SetDefaultFields(unittest::TestAllTypes* message) {
+ message->set_default_int32 (401);
+ message->set_default_int64 (402);
+ message->set_default_uint32 (403);
+ message->set_default_uint64 (404);
+ message->set_default_sint32 (405);
+ message->set_default_sint64 (406);
+ message->set_default_fixed32 (407);
+ message->set_default_fixed64 (408);
+ message->set_default_sfixed32(409);
+ message->set_default_sfixed64(410);
+ message->set_default_float (411);
+ message->set_default_double (412);
+ message->set_default_bool (false);
+ message->set_default_string ("415");
+ message->set_default_bytes ("416");
+
+ message->set_default_nested_enum (unittest::TestAllTypes::FOO);
+ message->set_default_foreign_enum(unittest::FOREIGN_FOO );
+ message->set_default_import_enum (unittest_import::IMPORT_FOO);
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ message->GetReflection()->SetString(
+ message,
+ message->GetDescriptor()->FindFieldByName("default_string_piece"),
+ "424");
+ message->GetReflection()->SetString(
+ message,
+ message->GetDescriptor()->FindFieldByName("default_cord"),
+ "425");
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ModifyRepeatedFields(unittest::TestAllTypes* message) {
+ message->set_repeated_int32 (1, 501);
+ message->set_repeated_int64 (1, 502);
+ message->set_repeated_uint32 (1, 503);
+ message->set_repeated_uint64 (1, 504);
+ message->set_repeated_sint32 (1, 505);
+ message->set_repeated_sint64 (1, 506);
+ message->set_repeated_fixed32 (1, 507);
+ message->set_repeated_fixed64 (1, 508);
+ message->set_repeated_sfixed32(1, 509);
+ message->set_repeated_sfixed64(1, 510);
+ message->set_repeated_float (1, 511);
+ message->set_repeated_double (1, 512);
+ message->set_repeated_bool (1, true);
+ message->set_repeated_string (1, "515");
+ message->set_repeated_bytes (1, "516");
+
+ message->mutable_repeatedgroup (1)->set_a(517);
+ message->mutable_repeated_nested_message (1)->set_bb(518);
+ message->mutable_repeated_foreign_message(1)->set_c(519);
+ message->mutable_repeated_import_message (1)->set_d(520);
+ message->mutable_repeated_lazy_message (1)->set_bb(527);
+
+ message->set_repeated_nested_enum (1, unittest::TestAllTypes::FOO);
+ message->set_repeated_foreign_enum(1, unittest::FOREIGN_FOO );
+ message->set_repeated_import_enum (1, unittest_import::IMPORT_FOO);
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ message->GetReflection()->SetRepeatedString(
+ message,
+ message->GetDescriptor()->FindFieldByName("repeated_string_piece"),
+ 1, "524");
+ message->GetReflection()->SetRepeatedString(
+ message,
+ message->GetDescriptor()->FindFieldByName("repeated_cord"),
+ 1, "525");
+#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
+}
+
+// ------------------------------------------------------------------
+void TestUtil::SetOneofFields(unittest::TestAllTypes* message) {
+ message->set_oneof_uint32(601);
+ message->mutable_oneof_nested_message()->set_bb(602);
+ message->set_oneof_string("603");
+ message->set_oneof_bytes("604");
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectAllFieldsSet(const unittest::TestAllTypes& message) {
+ EXPECT_TRUE(message.has_optional_int32 ());
+ EXPECT_TRUE(message.has_optional_int64 ());
+ EXPECT_TRUE(message.has_optional_uint32 ());
+ EXPECT_TRUE(message.has_optional_uint64 ());
+ EXPECT_TRUE(message.has_optional_sint32 ());
+ EXPECT_TRUE(message.has_optional_sint64 ());
+ EXPECT_TRUE(message.has_optional_fixed32 ());
+ EXPECT_TRUE(message.has_optional_fixed64 ());
+ EXPECT_TRUE(message.has_optional_sfixed32());
+ EXPECT_TRUE(message.has_optional_sfixed64());
+ EXPECT_TRUE(message.has_optional_float ());
+ EXPECT_TRUE(message.has_optional_double ());
+ EXPECT_TRUE(message.has_optional_bool ());
+ EXPECT_TRUE(message.has_optional_string ());
+ EXPECT_TRUE(message.has_optional_bytes ());
+
+ EXPECT_TRUE(message.has_optionalgroup ());
+ EXPECT_TRUE(message.has_optional_nested_message ());
+ EXPECT_TRUE(message.has_optional_foreign_message ());
+ EXPECT_TRUE(message.has_optional_import_message ());
+ EXPECT_TRUE(message.has_optional_public_import_message());
+ EXPECT_TRUE(message.has_optional_lazy_message ());
+
+ EXPECT_TRUE(message.optionalgroup ().has_a());
+ EXPECT_TRUE(message.optional_nested_message ().has_bb());
+ EXPECT_TRUE(message.optional_foreign_message ().has_c());
+ EXPECT_TRUE(message.optional_import_message ().has_d());
+ EXPECT_TRUE(message.optional_public_import_message().has_e());
+ EXPECT_TRUE(message.optional_lazy_message ().has_bb());
+
+ EXPECT_TRUE(message.has_optional_nested_enum ());
+ EXPECT_TRUE(message.has_optional_foreign_enum());
+ EXPECT_TRUE(message.has_optional_import_enum ());
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ EXPECT_TRUE(message.has_optional_string_piece());
+ EXPECT_TRUE(message.has_optional_cord());
+#endif
+
+ EXPECT_EQ(101 , message.optional_int32 ());
+ EXPECT_EQ(102 , message.optional_int64 ());
+ EXPECT_EQ(103 , message.optional_uint32 ());
+ EXPECT_EQ(104 , message.optional_uint64 ());
+ EXPECT_EQ(105 , message.optional_sint32 ());
+ EXPECT_EQ(106 , message.optional_sint64 ());
+ EXPECT_EQ(107 , message.optional_fixed32 ());
+ EXPECT_EQ(108 , message.optional_fixed64 ());
+ EXPECT_EQ(109 , message.optional_sfixed32());
+ EXPECT_EQ(110 , message.optional_sfixed64());
+ EXPECT_EQ(111 , message.optional_float ());
+ EXPECT_EQ(112 , message.optional_double ());
+ EXPECT_TRUE( message.optional_bool ());
+ EXPECT_EQ("115", message.optional_string ());
+ EXPECT_EQ("116", message.optional_bytes ());
+
+ EXPECT_EQ(117, message.optionalgroup ().a());
+ EXPECT_EQ(118, message.optional_nested_message ().bb());
+ EXPECT_EQ(119, message.optional_foreign_message ().c());
+ EXPECT_EQ(120, message.optional_import_message ().d());
+ EXPECT_EQ(126, message.optional_public_import_message ().e());
+ EXPECT_EQ(127, message.optional_lazy_message ().bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, message.optional_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_BAZ , message.optional_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_BAZ, message.optional_import_enum ());
+
+
+ // -----------------------------------------------------------------
+
+ ASSERT_EQ(2, message.repeated_int32_size ());
+ ASSERT_EQ(2, message.repeated_int64_size ());
+ ASSERT_EQ(2, message.repeated_uint32_size ());
+ ASSERT_EQ(2, message.repeated_uint64_size ());
+ ASSERT_EQ(2, message.repeated_sint32_size ());
+ ASSERT_EQ(2, message.repeated_sint64_size ());
+ ASSERT_EQ(2, message.repeated_fixed32_size ());
+ ASSERT_EQ(2, message.repeated_fixed64_size ());
+ ASSERT_EQ(2, message.repeated_sfixed32_size());
+ ASSERT_EQ(2, message.repeated_sfixed64_size());
+ ASSERT_EQ(2, message.repeated_float_size ());
+ ASSERT_EQ(2, message.repeated_double_size ());
+ ASSERT_EQ(2, message.repeated_bool_size ());
+ ASSERT_EQ(2, message.repeated_string_size ());
+ ASSERT_EQ(2, message.repeated_bytes_size ());
+
+ ASSERT_EQ(2, message.repeatedgroup_size ());
+ ASSERT_EQ(2, message.repeated_nested_message_size ());
+ ASSERT_EQ(2, message.repeated_foreign_message_size());
+ ASSERT_EQ(2, message.repeated_import_message_size ());
+ ASSERT_EQ(2, message.repeated_lazy_message_size ());
+ ASSERT_EQ(2, message.repeated_nested_enum_size ());
+ ASSERT_EQ(2, message.repeated_foreign_enum_size ());
+ ASSERT_EQ(2, message.repeated_import_enum_size ());
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ ASSERT_EQ(2, message.repeated_string_piece_size());
+ ASSERT_EQ(2, message.repeated_cord_size());
+#endif
+
+ EXPECT_EQ(201 , message.repeated_int32 (0));
+ EXPECT_EQ(202 , message.repeated_int64 (0));
+ EXPECT_EQ(203 , message.repeated_uint32 (0));
+ EXPECT_EQ(204 , message.repeated_uint64 (0));
+ EXPECT_EQ(205 , message.repeated_sint32 (0));
+ EXPECT_EQ(206 , message.repeated_sint64 (0));
+ EXPECT_EQ(207 , message.repeated_fixed32 (0));
+ EXPECT_EQ(208 , message.repeated_fixed64 (0));
+ EXPECT_EQ(209 , message.repeated_sfixed32(0));
+ EXPECT_EQ(210 , message.repeated_sfixed64(0));
+ EXPECT_EQ(211 , message.repeated_float (0));
+ EXPECT_EQ(212 , message.repeated_double (0));
+ EXPECT_TRUE( message.repeated_bool (0));
+ EXPECT_EQ("215", message.repeated_string (0));
+ EXPECT_EQ("216", message.repeated_bytes (0));
+
+ EXPECT_EQ(217, message.repeatedgroup (0).a());
+ EXPECT_EQ(218, message.repeated_nested_message (0).bb());
+ EXPECT_EQ(219, message.repeated_foreign_message(0).c());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+ EXPECT_EQ(227, message.repeated_lazy_message (0).bb());
+
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.repeated_nested_enum (0));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.repeated_foreign_enum(0));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.repeated_import_enum (0));
+
+ EXPECT_EQ(301 , message.repeated_int32 (1));
+ EXPECT_EQ(302 , message.repeated_int64 (1));
+ EXPECT_EQ(303 , message.repeated_uint32 (1));
+ EXPECT_EQ(304 , message.repeated_uint64 (1));
+ EXPECT_EQ(305 , message.repeated_sint32 (1));
+ EXPECT_EQ(306 , message.repeated_sint64 (1));
+ EXPECT_EQ(307 , message.repeated_fixed32 (1));
+ EXPECT_EQ(308 , message.repeated_fixed64 (1));
+ EXPECT_EQ(309 , message.repeated_sfixed32(1));
+ EXPECT_EQ(310 , message.repeated_sfixed64(1));
+ EXPECT_EQ(311 , message.repeated_float (1));
+ EXPECT_EQ(312 , message.repeated_double (1));
+ EXPECT_FALSE( message.repeated_bool (1));
+ EXPECT_EQ("315", message.repeated_string (1));
+ EXPECT_EQ("316", message.repeated_bytes (1));
+
+ EXPECT_EQ(317, message.repeatedgroup (1).a());
+ EXPECT_EQ(318, message.repeated_nested_message (1).bb());
+ EXPECT_EQ(319, message.repeated_foreign_message(1).c());
+ EXPECT_EQ(320, message.repeated_import_message (1).d());
+ EXPECT_EQ(327, message.repeated_lazy_message (1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, message.repeated_nested_enum (1));
+ EXPECT_EQ(unittest::FOREIGN_BAZ , message.repeated_foreign_enum(1));
+ EXPECT_EQ(unittest_import::IMPORT_BAZ, message.repeated_import_enum (1));
+
+
+ // -----------------------------------------------------------------
+
+ EXPECT_TRUE(message.has_default_int32 ());
+ EXPECT_TRUE(message.has_default_int64 ());
+ EXPECT_TRUE(message.has_default_uint32 ());
+ EXPECT_TRUE(message.has_default_uint64 ());
+ EXPECT_TRUE(message.has_default_sint32 ());
+ EXPECT_TRUE(message.has_default_sint64 ());
+ EXPECT_TRUE(message.has_default_fixed32 ());
+ EXPECT_TRUE(message.has_default_fixed64 ());
+ EXPECT_TRUE(message.has_default_sfixed32());
+ EXPECT_TRUE(message.has_default_sfixed64());
+ EXPECT_TRUE(message.has_default_float ());
+ EXPECT_TRUE(message.has_default_double ());
+ EXPECT_TRUE(message.has_default_bool ());
+ EXPECT_TRUE(message.has_default_string ());
+ EXPECT_TRUE(message.has_default_bytes ());
+
+ EXPECT_TRUE(message.has_default_nested_enum ());
+ EXPECT_TRUE(message.has_default_foreign_enum());
+ EXPECT_TRUE(message.has_default_import_enum ());
+
+
+ EXPECT_EQ(401 , message.default_int32 ());
+ EXPECT_EQ(402 , message.default_int64 ());
+ EXPECT_EQ(403 , message.default_uint32 ());
+ EXPECT_EQ(404 , message.default_uint64 ());
+ EXPECT_EQ(405 , message.default_sint32 ());
+ EXPECT_EQ(406 , message.default_sint64 ());
+ EXPECT_EQ(407 , message.default_fixed32 ());
+ EXPECT_EQ(408 , message.default_fixed64 ());
+ EXPECT_EQ(409 , message.default_sfixed32());
+ EXPECT_EQ(410 , message.default_sfixed64());
+ EXPECT_EQ(411 , message.default_float ());
+ EXPECT_EQ(412 , message.default_double ());
+ EXPECT_FALSE( message.default_bool ());
+ EXPECT_EQ("415", message.default_string ());
+ EXPECT_EQ("416", message.default_bytes ());
+
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message.default_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_FOO , message.default_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_FOO, message.default_import_enum ());
+
+
+ EXPECT_FALSE(message.has_oneof_uint32 ());
+ EXPECT_FALSE(message.has_oneof_nested_message());
+ EXPECT_FALSE(message.has_oneof_string ());
+ EXPECT_TRUE(message.has_oneof_bytes ());
+
+ EXPECT_EQ("604", message.oneof_bytes());
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectClear(const unittest::TestAllTypes& message) {
+ // has_blah() should initially be false for all optional fields.
+ EXPECT_FALSE(message.has_optional_int32 ());
+ EXPECT_FALSE(message.has_optional_int64 ());
+ EXPECT_FALSE(message.has_optional_uint32 ());
+ EXPECT_FALSE(message.has_optional_uint64 ());
+ EXPECT_FALSE(message.has_optional_sint32 ());
+ EXPECT_FALSE(message.has_optional_sint64 ());
+ EXPECT_FALSE(message.has_optional_fixed32 ());
+ EXPECT_FALSE(message.has_optional_fixed64 ());
+ EXPECT_FALSE(message.has_optional_sfixed32());
+ EXPECT_FALSE(message.has_optional_sfixed64());
+ EXPECT_FALSE(message.has_optional_float ());
+ EXPECT_FALSE(message.has_optional_double ());
+ EXPECT_FALSE(message.has_optional_bool ());
+ EXPECT_FALSE(message.has_optional_string ());
+ EXPECT_FALSE(message.has_optional_bytes ());
+
+ EXPECT_FALSE(message.has_optionalgroup ());
+ EXPECT_FALSE(message.has_optional_nested_message ());
+ EXPECT_FALSE(message.has_optional_foreign_message ());
+ EXPECT_FALSE(message.has_optional_import_message ());
+ EXPECT_FALSE(message.has_optional_public_import_message());
+ EXPECT_FALSE(message.has_optional_lazy_message ());
+
+ EXPECT_FALSE(message.has_optional_nested_enum ());
+ EXPECT_FALSE(message.has_optional_foreign_enum());
+ EXPECT_FALSE(message.has_optional_import_enum ());
+
+ EXPECT_FALSE(message.has_optional_string_piece());
+ EXPECT_FALSE(message.has_optional_cord());
+
+ // Optional fields without defaults are set to zero or something like it.
+ EXPECT_EQ(0 , message.optional_int32 ());
+ EXPECT_EQ(0 , message.optional_int64 ());
+ EXPECT_EQ(0 , message.optional_uint32 ());
+ EXPECT_EQ(0 , message.optional_uint64 ());
+ EXPECT_EQ(0 , message.optional_sint32 ());
+ EXPECT_EQ(0 , message.optional_sint64 ());
+ EXPECT_EQ(0 , message.optional_fixed32 ());
+ EXPECT_EQ(0 , message.optional_fixed64 ());
+ EXPECT_EQ(0 , message.optional_sfixed32());
+ EXPECT_EQ(0 , message.optional_sfixed64());
+ EXPECT_EQ(0 , message.optional_float ());
+ EXPECT_EQ(0 , message.optional_double ());
+ EXPECT_FALSE( message.optional_bool ());
+ EXPECT_EQ("" , message.optional_string ());
+ EXPECT_EQ("" , message.optional_bytes ());
+
+ // Embedded messages should also be clear.
+ EXPECT_FALSE(message.optionalgroup ().has_a());
+ EXPECT_FALSE(message.optional_nested_message ().has_bb());
+ EXPECT_FALSE(message.optional_foreign_message ().has_c());
+ EXPECT_FALSE(message.optional_import_message ().has_d());
+ EXPECT_FALSE(message.optional_public_import_message().has_e());
+ EXPECT_FALSE(message.optional_lazy_message ().has_bb());
+
+ EXPECT_EQ(0, message.optionalgroup ().a());
+ EXPECT_EQ(0, message.optional_nested_message ().bb());
+ EXPECT_EQ(0, message.optional_foreign_message ().c());
+ EXPECT_EQ(0, message.optional_import_message ().d());
+ EXPECT_EQ(0, message.optional_public_import_message().e());
+ EXPECT_EQ(0, message.optional_lazy_message ().bb());
+
+ // Enums without defaults are set to the first value in the enum.
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message.optional_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_FOO , message.optional_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_FOO, message.optional_import_enum ());
+
+
+ // Repeated fields are empty.
+ EXPECT_EQ(0, message.repeated_int32_size ());
+ EXPECT_EQ(0, message.repeated_int64_size ());
+ EXPECT_EQ(0, message.repeated_uint32_size ());
+ EXPECT_EQ(0, message.repeated_uint64_size ());
+ EXPECT_EQ(0, message.repeated_sint32_size ());
+ EXPECT_EQ(0, message.repeated_sint64_size ());
+ EXPECT_EQ(0, message.repeated_fixed32_size ());
+ EXPECT_EQ(0, message.repeated_fixed64_size ());
+ EXPECT_EQ(0, message.repeated_sfixed32_size());
+ EXPECT_EQ(0, message.repeated_sfixed64_size());
+ EXPECT_EQ(0, message.repeated_float_size ());
+ EXPECT_EQ(0, message.repeated_double_size ());
+ EXPECT_EQ(0, message.repeated_bool_size ());
+ EXPECT_EQ(0, message.repeated_string_size ());
+ EXPECT_EQ(0, message.repeated_bytes_size ());
+
+ EXPECT_EQ(0, message.repeatedgroup_size ());
+ EXPECT_EQ(0, message.repeated_nested_message_size ());
+ EXPECT_EQ(0, message.repeated_foreign_message_size());
+ EXPECT_EQ(0, message.repeated_import_message_size ());
+ EXPECT_EQ(0, message.repeated_lazy_message_size ());
+ EXPECT_EQ(0, message.repeated_nested_enum_size ());
+ EXPECT_EQ(0, message.repeated_foreign_enum_size ());
+ EXPECT_EQ(0, message.repeated_import_enum_size ());
+
+ EXPECT_EQ(0, message.repeated_string_piece_size());
+ EXPECT_EQ(0, message.repeated_cord_size());
+
+ // has_blah() should also be false for all default fields.
+ EXPECT_FALSE(message.has_default_int32 ());
+ EXPECT_FALSE(message.has_default_int64 ());
+ EXPECT_FALSE(message.has_default_uint32 ());
+ EXPECT_FALSE(message.has_default_uint64 ());
+ EXPECT_FALSE(message.has_default_sint32 ());
+ EXPECT_FALSE(message.has_default_sint64 ());
+ EXPECT_FALSE(message.has_default_fixed32 ());
+ EXPECT_FALSE(message.has_default_fixed64 ());
+ EXPECT_FALSE(message.has_default_sfixed32());
+ EXPECT_FALSE(message.has_default_sfixed64());
+ EXPECT_FALSE(message.has_default_float ());
+ EXPECT_FALSE(message.has_default_double ());
+ EXPECT_FALSE(message.has_default_bool ());
+ EXPECT_FALSE(message.has_default_string ());
+ EXPECT_FALSE(message.has_default_bytes ());
+
+ EXPECT_FALSE(message.has_default_nested_enum ());
+ EXPECT_FALSE(message.has_default_foreign_enum());
+ EXPECT_FALSE(message.has_default_import_enum ());
+
+
+ // Fields with defaults have their default values (duh).
+ EXPECT_EQ( 41 , message.default_int32 ());
+ EXPECT_EQ( 42 , message.default_int64 ());
+ EXPECT_EQ( 43 , message.default_uint32 ());
+ EXPECT_EQ( 44 , message.default_uint64 ());
+ EXPECT_EQ(-45 , message.default_sint32 ());
+ EXPECT_EQ( 46 , message.default_sint64 ());
+ EXPECT_EQ( 47 , message.default_fixed32 ());
+ EXPECT_EQ( 48 , message.default_fixed64 ());
+ EXPECT_EQ( 49 , message.default_sfixed32());
+ EXPECT_EQ(-50 , message.default_sfixed64());
+ EXPECT_EQ( 51.5 , message.default_float ());
+ EXPECT_EQ( 52e3 , message.default_double ());
+ EXPECT_TRUE( message.default_bool ());
+ EXPECT_EQ("hello", message.default_string ());
+ EXPECT_EQ("world", message.default_bytes ());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.default_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.default_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.default_import_enum ());
+
+
+ EXPECT_FALSE(message.has_oneof_uint32 ());
+ EXPECT_FALSE(message.has_oneof_nested_message());
+ EXPECT_FALSE(message.has_oneof_string ());
+ EXPECT_FALSE(message.has_oneof_bytes ());
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectRepeatedFieldsModified(
+ const unittest::TestAllTypes& message) {
+ // ModifyRepeatedFields only sets the second repeated element of each
+ // field. In addition to verifying this, we also verify that the first
+ // element and size were *not* modified.
+ ASSERT_EQ(2, message.repeated_int32_size ());
+ ASSERT_EQ(2, message.repeated_int64_size ());
+ ASSERT_EQ(2, message.repeated_uint32_size ());
+ ASSERT_EQ(2, message.repeated_uint64_size ());
+ ASSERT_EQ(2, message.repeated_sint32_size ());
+ ASSERT_EQ(2, message.repeated_sint64_size ());
+ ASSERT_EQ(2, message.repeated_fixed32_size ());
+ ASSERT_EQ(2, message.repeated_fixed64_size ());
+ ASSERT_EQ(2, message.repeated_sfixed32_size());
+ ASSERT_EQ(2, message.repeated_sfixed64_size());
+ ASSERT_EQ(2, message.repeated_float_size ());
+ ASSERT_EQ(2, message.repeated_double_size ());
+ ASSERT_EQ(2, message.repeated_bool_size ());
+ ASSERT_EQ(2, message.repeated_string_size ());
+ ASSERT_EQ(2, message.repeated_bytes_size ());
+
+ ASSERT_EQ(2, message.repeatedgroup_size ());
+ ASSERT_EQ(2, message.repeated_nested_message_size ());
+ ASSERT_EQ(2, message.repeated_foreign_message_size());
+ ASSERT_EQ(2, message.repeated_import_message_size ());
+ ASSERT_EQ(2, message.repeated_lazy_message_size ());
+ ASSERT_EQ(2, message.repeated_nested_enum_size ());
+ ASSERT_EQ(2, message.repeated_foreign_enum_size ());
+ ASSERT_EQ(2, message.repeated_import_enum_size ());
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ ASSERT_EQ(2, message.repeated_string_piece_size());
+ ASSERT_EQ(2, message.repeated_cord_size());
+#endif
+
+ EXPECT_EQ(201 , message.repeated_int32 (0));
+ EXPECT_EQ(202 , message.repeated_int64 (0));
+ EXPECT_EQ(203 , message.repeated_uint32 (0));
+ EXPECT_EQ(204 , message.repeated_uint64 (0));
+ EXPECT_EQ(205 , message.repeated_sint32 (0));
+ EXPECT_EQ(206 , message.repeated_sint64 (0));
+ EXPECT_EQ(207 , message.repeated_fixed32 (0));
+ EXPECT_EQ(208 , message.repeated_fixed64 (0));
+ EXPECT_EQ(209 , message.repeated_sfixed32(0));
+ EXPECT_EQ(210 , message.repeated_sfixed64(0));
+ EXPECT_EQ(211 , message.repeated_float (0));
+ EXPECT_EQ(212 , message.repeated_double (0));
+ EXPECT_TRUE( message.repeated_bool (0));
+ EXPECT_EQ("215", message.repeated_string (0));
+ EXPECT_EQ("216", message.repeated_bytes (0));
+
+ EXPECT_EQ(217, message.repeatedgroup (0).a());
+ EXPECT_EQ(218, message.repeated_nested_message (0).bb());
+ EXPECT_EQ(219, message.repeated_foreign_message(0).c());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+ EXPECT_EQ(227, message.repeated_lazy_message (0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.repeated_nested_enum (0));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.repeated_foreign_enum(0));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.repeated_import_enum (0));
+
+
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(501 , message.repeated_int32 (1));
+ EXPECT_EQ(502 , message.repeated_int64 (1));
+ EXPECT_EQ(503 , message.repeated_uint32 (1));
+ EXPECT_EQ(504 , message.repeated_uint64 (1));
+ EXPECT_EQ(505 , message.repeated_sint32 (1));
+ EXPECT_EQ(506 , message.repeated_sint64 (1));
+ EXPECT_EQ(507 , message.repeated_fixed32 (1));
+ EXPECT_EQ(508 , message.repeated_fixed64 (1));
+ EXPECT_EQ(509 , message.repeated_sfixed32(1));
+ EXPECT_EQ(510 , message.repeated_sfixed64(1));
+ EXPECT_EQ(511 , message.repeated_float (1));
+ EXPECT_EQ(512 , message.repeated_double (1));
+ EXPECT_TRUE( message.repeated_bool (1));
+ EXPECT_EQ("515", message.repeated_string (1));
+ EXPECT_EQ("516", message.repeated_bytes (1));
+
+ EXPECT_EQ(517, message.repeatedgroup (1).a());
+ EXPECT_EQ(518, message.repeated_nested_message (1).bb());
+ EXPECT_EQ(519, message.repeated_foreign_message(1).c());
+ EXPECT_EQ(520, message.repeated_import_message (1).d());
+ EXPECT_EQ(527, message.repeated_lazy_message (1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message.repeated_nested_enum (1));
+ EXPECT_EQ(unittest::FOREIGN_FOO , message.repeated_foreign_enum(1));
+ EXPECT_EQ(unittest_import::IMPORT_FOO, message.repeated_import_enum (1));
+
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::SetPackedFields(unittest::TestPackedTypes* message) {
+ message->add_packed_int32 (601);
+ message->add_packed_int64 (602);
+ message->add_packed_uint32 (603);
+ message->add_packed_uint64 (604);
+ message->add_packed_sint32 (605);
+ message->add_packed_sint64 (606);
+ message->add_packed_fixed32 (607);
+ message->add_packed_fixed64 (608);
+ message->add_packed_sfixed32(609);
+ message->add_packed_sfixed64(610);
+ message->add_packed_float (611);
+ message->add_packed_double (612);
+ message->add_packed_bool (true);
+ message->add_packed_enum (unittest::FOREIGN_BAR);
+ // add a second one of each field
+ message->add_packed_int32 (701);
+ message->add_packed_int64 (702);
+ message->add_packed_uint32 (703);
+ message->add_packed_uint64 (704);
+ message->add_packed_sint32 (705);
+ message->add_packed_sint64 (706);
+ message->add_packed_fixed32 (707);
+ message->add_packed_fixed64 (708);
+ message->add_packed_sfixed32(709);
+ message->add_packed_sfixed64(710);
+ message->add_packed_float (711);
+ message->add_packed_double (712);
+ message->add_packed_bool (false);
+ message->add_packed_enum (unittest::FOREIGN_BAZ);
+}
+
+void TestUtil::SetUnpackedFields(unittest::TestUnpackedTypes* message) {
+ // The values applied here must match those of SetPackedFields.
+
+ message->add_unpacked_int32 (601);
+ message->add_unpacked_int64 (602);
+ message->add_unpacked_uint32 (603);
+ message->add_unpacked_uint64 (604);
+ message->add_unpacked_sint32 (605);
+ message->add_unpacked_sint64 (606);
+ message->add_unpacked_fixed32 (607);
+ message->add_unpacked_fixed64 (608);
+ message->add_unpacked_sfixed32(609);
+ message->add_unpacked_sfixed64(610);
+ message->add_unpacked_float (611);
+ message->add_unpacked_double (612);
+ message->add_unpacked_bool (true);
+ message->add_unpacked_enum (unittest::FOREIGN_BAR);
+ // add a second one of each field
+ message->add_unpacked_int32 (701);
+ message->add_unpacked_int64 (702);
+ message->add_unpacked_uint32 (703);
+ message->add_unpacked_uint64 (704);
+ message->add_unpacked_sint32 (705);
+ message->add_unpacked_sint64 (706);
+ message->add_unpacked_fixed32 (707);
+ message->add_unpacked_fixed64 (708);
+ message->add_unpacked_sfixed32(709);
+ message->add_unpacked_sfixed64(710);
+ message->add_unpacked_float (711);
+ message->add_unpacked_double (712);
+ message->add_unpacked_bool (false);
+ message->add_unpacked_enum (unittest::FOREIGN_BAZ);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ModifyPackedFields(unittest::TestPackedTypes* message) {
+ message->set_packed_int32 (1, 801);
+ message->set_packed_int64 (1, 802);
+ message->set_packed_uint32 (1, 803);
+ message->set_packed_uint64 (1, 804);
+ message->set_packed_sint32 (1, 805);
+ message->set_packed_sint64 (1, 806);
+ message->set_packed_fixed32 (1, 807);
+ message->set_packed_fixed64 (1, 808);
+ message->set_packed_sfixed32(1, 809);
+ message->set_packed_sfixed64(1, 810);
+ message->set_packed_float (1, 811);
+ message->set_packed_double (1, 812);
+ message->set_packed_bool (1, true);
+ message->set_packed_enum (1, unittest::FOREIGN_FOO);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectPackedFieldsSet(const unittest::TestPackedTypes& message) {
+ ASSERT_EQ(2, message.packed_int32_size ());
+ ASSERT_EQ(2, message.packed_int64_size ());
+ ASSERT_EQ(2, message.packed_uint32_size ());
+ ASSERT_EQ(2, message.packed_uint64_size ());
+ ASSERT_EQ(2, message.packed_sint32_size ());
+ ASSERT_EQ(2, message.packed_sint64_size ());
+ ASSERT_EQ(2, message.packed_fixed32_size ());
+ ASSERT_EQ(2, message.packed_fixed64_size ());
+ ASSERT_EQ(2, message.packed_sfixed32_size());
+ ASSERT_EQ(2, message.packed_sfixed64_size());
+ ASSERT_EQ(2, message.packed_float_size ());
+ ASSERT_EQ(2, message.packed_double_size ());
+ ASSERT_EQ(2, message.packed_bool_size ());
+ ASSERT_EQ(2, message.packed_enum_size ());
+
+ EXPECT_EQ(601 , message.packed_int32 (0));
+ EXPECT_EQ(602 , message.packed_int64 (0));
+ EXPECT_EQ(603 , message.packed_uint32 (0));
+ EXPECT_EQ(604 , message.packed_uint64 (0));
+ EXPECT_EQ(605 , message.packed_sint32 (0));
+ EXPECT_EQ(606 , message.packed_sint64 (0));
+ EXPECT_EQ(607 , message.packed_fixed32 (0));
+ EXPECT_EQ(608 , message.packed_fixed64 (0));
+ EXPECT_EQ(609 , message.packed_sfixed32(0));
+ EXPECT_EQ(610 , message.packed_sfixed64(0));
+ EXPECT_EQ(611 , message.packed_float (0));
+ EXPECT_EQ(612 , message.packed_double (0));
+ EXPECT_TRUE( message.packed_bool (0));
+ EXPECT_EQ(unittest::FOREIGN_BAR, message.packed_enum(0));
+
+ EXPECT_EQ(701 , message.packed_int32 (1));
+ EXPECT_EQ(702 , message.packed_int64 (1));
+ EXPECT_EQ(703 , message.packed_uint32 (1));
+ EXPECT_EQ(704 , message.packed_uint64 (1));
+ EXPECT_EQ(705 , message.packed_sint32 (1));
+ EXPECT_EQ(706 , message.packed_sint64 (1));
+ EXPECT_EQ(707 , message.packed_fixed32 (1));
+ EXPECT_EQ(708 , message.packed_fixed64 (1));
+ EXPECT_EQ(709 , message.packed_sfixed32(1));
+ EXPECT_EQ(710 , message.packed_sfixed64(1));
+ EXPECT_EQ(711 , message.packed_float (1));
+ EXPECT_EQ(712 , message.packed_double (1));
+ EXPECT_FALSE( message.packed_bool (1));
+ EXPECT_EQ(unittest::FOREIGN_BAZ, message.packed_enum(1));
+}
+
+void TestUtil::ExpectUnpackedFieldsSet(
+ const unittest::TestUnpackedTypes& message) {
+ // The values expected here must match those of ExpectPackedFieldsSet.
+
+ ASSERT_EQ(2, message.unpacked_int32_size ());
+ ASSERT_EQ(2, message.unpacked_int64_size ());
+ ASSERT_EQ(2, message.unpacked_uint32_size ());
+ ASSERT_EQ(2, message.unpacked_uint64_size ());
+ ASSERT_EQ(2, message.unpacked_sint32_size ());
+ ASSERT_EQ(2, message.unpacked_sint64_size ());
+ ASSERT_EQ(2, message.unpacked_fixed32_size ());
+ ASSERT_EQ(2, message.unpacked_fixed64_size ());
+ ASSERT_EQ(2, message.unpacked_sfixed32_size());
+ ASSERT_EQ(2, message.unpacked_sfixed64_size());
+ ASSERT_EQ(2, message.unpacked_float_size ());
+ ASSERT_EQ(2, message.unpacked_double_size ());
+ ASSERT_EQ(2, message.unpacked_bool_size ());
+ ASSERT_EQ(2, message.unpacked_enum_size ());
+
+ EXPECT_EQ(601 , message.unpacked_int32 (0));
+ EXPECT_EQ(602 , message.unpacked_int64 (0));
+ EXPECT_EQ(603 , message.unpacked_uint32 (0));
+ EXPECT_EQ(604 , message.unpacked_uint64 (0));
+ EXPECT_EQ(605 , message.unpacked_sint32 (0));
+ EXPECT_EQ(606 , message.unpacked_sint64 (0));
+ EXPECT_EQ(607 , message.unpacked_fixed32 (0));
+ EXPECT_EQ(608 , message.unpacked_fixed64 (0));
+ EXPECT_EQ(609 , message.unpacked_sfixed32(0));
+ EXPECT_EQ(610 , message.unpacked_sfixed64(0));
+ EXPECT_EQ(611 , message.unpacked_float (0));
+ EXPECT_EQ(612 , message.unpacked_double (0));
+ EXPECT_TRUE( message.unpacked_bool (0));
+ EXPECT_EQ(unittest::FOREIGN_BAR, message.unpacked_enum(0));
+
+ EXPECT_EQ(701 , message.unpacked_int32 (1));
+ EXPECT_EQ(702 , message.unpacked_int64 (1));
+ EXPECT_EQ(703 , message.unpacked_uint32 (1));
+ EXPECT_EQ(704 , message.unpacked_uint64 (1));
+ EXPECT_EQ(705 , message.unpacked_sint32 (1));
+ EXPECT_EQ(706 , message.unpacked_sint64 (1));
+ EXPECT_EQ(707 , message.unpacked_fixed32 (1));
+ EXPECT_EQ(708 , message.unpacked_fixed64 (1));
+ EXPECT_EQ(709 , message.unpacked_sfixed32(1));
+ EXPECT_EQ(710 , message.unpacked_sfixed64(1));
+ EXPECT_EQ(711 , message.unpacked_float (1));
+ EXPECT_EQ(712 , message.unpacked_double (1));
+ EXPECT_FALSE( message.unpacked_bool (1));
+ EXPECT_EQ(unittest::FOREIGN_BAZ, message.unpacked_enum(1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectPackedClear(
+ const unittest::TestPackedTypes& message) {
+ // Packed repeated fields are empty.
+ EXPECT_EQ(0, message.packed_int32_size ());
+ EXPECT_EQ(0, message.packed_int64_size ());
+ EXPECT_EQ(0, message.packed_uint32_size ());
+ EXPECT_EQ(0, message.packed_uint64_size ());
+ EXPECT_EQ(0, message.packed_sint32_size ());
+ EXPECT_EQ(0, message.packed_sint64_size ());
+ EXPECT_EQ(0, message.packed_fixed32_size ());
+ EXPECT_EQ(0, message.packed_fixed64_size ());
+ EXPECT_EQ(0, message.packed_sfixed32_size());
+ EXPECT_EQ(0, message.packed_sfixed64_size());
+ EXPECT_EQ(0, message.packed_float_size ());
+ EXPECT_EQ(0, message.packed_double_size ());
+ EXPECT_EQ(0, message.packed_bool_size ());
+ EXPECT_EQ(0, message.packed_enum_size ());
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectPackedFieldsModified(
+ const unittest::TestPackedTypes& message) {
+ // Do the same for packed repeated fields.
+ ASSERT_EQ(2, message.packed_int32_size ());
+ ASSERT_EQ(2, message.packed_int64_size ());
+ ASSERT_EQ(2, message.packed_uint32_size ());
+ ASSERT_EQ(2, message.packed_uint64_size ());
+ ASSERT_EQ(2, message.packed_sint32_size ());
+ ASSERT_EQ(2, message.packed_sint64_size ());
+ ASSERT_EQ(2, message.packed_fixed32_size ());
+ ASSERT_EQ(2, message.packed_fixed64_size ());
+ ASSERT_EQ(2, message.packed_sfixed32_size());
+ ASSERT_EQ(2, message.packed_sfixed64_size());
+ ASSERT_EQ(2, message.packed_float_size ());
+ ASSERT_EQ(2, message.packed_double_size ());
+ ASSERT_EQ(2, message.packed_bool_size ());
+ ASSERT_EQ(2, message.packed_enum_size ());
+
+ EXPECT_EQ(601 , message.packed_int32 (0));
+ EXPECT_EQ(602 , message.packed_int64 (0));
+ EXPECT_EQ(603 , message.packed_uint32 (0));
+ EXPECT_EQ(604 , message.packed_uint64 (0));
+ EXPECT_EQ(605 , message.packed_sint32 (0));
+ EXPECT_EQ(606 , message.packed_sint64 (0));
+ EXPECT_EQ(607 , message.packed_fixed32 (0));
+ EXPECT_EQ(608 , message.packed_fixed64 (0));
+ EXPECT_EQ(609 , message.packed_sfixed32(0));
+ EXPECT_EQ(610 , message.packed_sfixed64(0));
+ EXPECT_EQ(611 , message.packed_float (0));
+ EXPECT_EQ(612 , message.packed_double (0));
+ EXPECT_TRUE( message.packed_bool (0));
+ EXPECT_EQ(unittest::FOREIGN_BAR, message.packed_enum(0));
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(801 , message.packed_int32 (1));
+ EXPECT_EQ(802 , message.packed_int64 (1));
+ EXPECT_EQ(803 , message.packed_uint32 (1));
+ EXPECT_EQ(804 , message.packed_uint64 (1));
+ EXPECT_EQ(805 , message.packed_sint32 (1));
+ EXPECT_EQ(806 , message.packed_sint64 (1));
+ EXPECT_EQ(807 , message.packed_fixed32 (1));
+ EXPECT_EQ(808 , message.packed_fixed64 (1));
+ EXPECT_EQ(809 , message.packed_sfixed32(1));
+ EXPECT_EQ(810 , message.packed_sfixed64(1));
+ EXPECT_EQ(811 , message.packed_float (1));
+ EXPECT_EQ(812 , message.packed_double (1));
+ EXPECT_TRUE( message.packed_bool (1));
+ EXPECT_EQ(unittest::FOREIGN_FOO, message.packed_enum(1));
+}
+
+// ===================================================================
+// Extensions
+//
+// All this code is exactly equivalent to the above code except that it's
+// manipulating extension fields instead of normal ones.
+//
+// I gave up on the 80-char limit here. Sorry.
+
+void TestUtil::SetAllExtensions(unittest::TestAllExtensions* message) {
+ message->SetExtension(unittest::optional_int32_extension , 101);
+ message->SetExtension(unittest::optional_int64_extension , 102);
+ message->SetExtension(unittest::optional_uint32_extension , 103);
+ message->SetExtension(unittest::optional_uint64_extension , 104);
+ message->SetExtension(unittest::optional_sint32_extension , 105);
+ message->SetExtension(unittest::optional_sint64_extension , 106);
+ message->SetExtension(unittest::optional_fixed32_extension , 107);
+ message->SetExtension(unittest::optional_fixed64_extension , 108);
+ message->SetExtension(unittest::optional_sfixed32_extension, 109);
+ message->SetExtension(unittest::optional_sfixed64_extension, 110);
+ message->SetExtension(unittest::optional_float_extension , 111);
+ message->SetExtension(unittest::optional_double_extension , 112);
+ message->SetExtension(unittest::optional_bool_extension , true);
+ message->SetExtension(unittest::optional_string_extension , "115");
+ message->SetExtension(unittest::optional_bytes_extension , "116");
+
+ message->MutableExtension(unittest::optionalgroup_extension )->set_a(117);
+ message->MutableExtension(unittest::optional_nested_message_extension )->set_bb(118);
+ message->MutableExtension(unittest::optional_foreign_message_extension)->set_c(119);
+ message->MutableExtension(unittest::optional_import_message_extension )->set_d(120);
+
+ message->SetExtension(unittest::optional_nested_enum_extension , unittest::TestAllTypes::BAZ);
+ message->SetExtension(unittest::optional_foreign_enum_extension, unittest::FOREIGN_BAZ );
+ message->SetExtension(unittest::optional_import_enum_extension , unittest_import::IMPORT_BAZ);
+
+ message->SetExtension(unittest::optional_string_piece_extension, "124");
+ message->SetExtension(unittest::optional_cord_extension, "125");
+
+ message->MutableExtension(unittest::optional_public_import_message_extension)->set_e(126);
+ message->MutableExtension(unittest::optional_lazy_message_extension)->set_bb(127);
+
+ // -----------------------------------------------------------------
+
+ message->AddExtension(unittest::repeated_int32_extension , 201);
+ message->AddExtension(unittest::repeated_int64_extension , 202);
+ message->AddExtension(unittest::repeated_uint32_extension , 203);
+ message->AddExtension(unittest::repeated_uint64_extension , 204);
+ message->AddExtension(unittest::repeated_sint32_extension , 205);
+ message->AddExtension(unittest::repeated_sint64_extension , 206);
+ message->AddExtension(unittest::repeated_fixed32_extension , 207);
+ message->AddExtension(unittest::repeated_fixed64_extension , 208);
+ message->AddExtension(unittest::repeated_sfixed32_extension, 209);
+ message->AddExtension(unittest::repeated_sfixed64_extension, 210);
+ message->AddExtension(unittest::repeated_float_extension , 211);
+ message->AddExtension(unittest::repeated_double_extension , 212);
+ message->AddExtension(unittest::repeated_bool_extension , true);
+ message->AddExtension(unittest::repeated_string_extension , "215");
+ message->AddExtension(unittest::repeated_bytes_extension , "216");
+
+ message->AddExtension(unittest::repeatedgroup_extension )->set_a(217);
+ message->AddExtension(unittest::repeated_nested_message_extension )->set_bb(218);
+ message->AddExtension(unittest::repeated_foreign_message_extension)->set_c(219);
+ message->AddExtension(unittest::repeated_import_message_extension )->set_d(220);
+ message->AddExtension(unittest::repeated_lazy_message_extension )->set_bb(227);
+
+ message->AddExtension(unittest::repeated_nested_enum_extension , unittest::TestAllTypes::BAR);
+ message->AddExtension(unittest::repeated_foreign_enum_extension, unittest::FOREIGN_BAR );
+ message->AddExtension(unittest::repeated_import_enum_extension , unittest_import::IMPORT_BAR);
+
+ message->AddExtension(unittest::repeated_string_piece_extension, "224");
+ message->AddExtension(unittest::repeated_cord_extension, "225");
+
+ // Add a second one of each field.
+ message->AddExtension(unittest::repeated_int32_extension , 301);
+ message->AddExtension(unittest::repeated_int64_extension , 302);
+ message->AddExtension(unittest::repeated_uint32_extension , 303);
+ message->AddExtension(unittest::repeated_uint64_extension , 304);
+ message->AddExtension(unittest::repeated_sint32_extension , 305);
+ message->AddExtension(unittest::repeated_sint64_extension , 306);
+ message->AddExtension(unittest::repeated_fixed32_extension , 307);
+ message->AddExtension(unittest::repeated_fixed64_extension , 308);
+ message->AddExtension(unittest::repeated_sfixed32_extension, 309);
+ message->AddExtension(unittest::repeated_sfixed64_extension, 310);
+ message->AddExtension(unittest::repeated_float_extension , 311);
+ message->AddExtension(unittest::repeated_double_extension , 312);
+ message->AddExtension(unittest::repeated_bool_extension , false);
+ message->AddExtension(unittest::repeated_string_extension , "315");
+ message->AddExtension(unittest::repeated_bytes_extension , "316");
+
+ message->AddExtension(unittest::repeatedgroup_extension )->set_a(317);
+ message->AddExtension(unittest::repeated_nested_message_extension )->set_bb(318);
+ message->AddExtension(unittest::repeated_foreign_message_extension)->set_c(319);
+ message->AddExtension(unittest::repeated_import_message_extension )->set_d(320);
+ message->AddExtension(unittest::repeated_lazy_message_extension )->set_bb(327);
+
+ message->AddExtension(unittest::repeated_nested_enum_extension , unittest::TestAllTypes::BAZ);
+ message->AddExtension(unittest::repeated_foreign_enum_extension, unittest::FOREIGN_BAZ );
+ message->AddExtension(unittest::repeated_import_enum_extension , unittest_import::IMPORT_BAZ);
+
+ message->AddExtension(unittest::repeated_string_piece_extension, "324");
+ message->AddExtension(unittest::repeated_cord_extension, "325");
+
+ // -----------------------------------------------------------------
+
+ message->SetExtension(unittest::default_int32_extension , 401);
+ message->SetExtension(unittest::default_int64_extension , 402);
+ message->SetExtension(unittest::default_uint32_extension , 403);
+ message->SetExtension(unittest::default_uint64_extension , 404);
+ message->SetExtension(unittest::default_sint32_extension , 405);
+ message->SetExtension(unittest::default_sint64_extension , 406);
+ message->SetExtension(unittest::default_fixed32_extension , 407);
+ message->SetExtension(unittest::default_fixed64_extension , 408);
+ message->SetExtension(unittest::default_sfixed32_extension, 409);
+ message->SetExtension(unittest::default_sfixed64_extension, 410);
+ message->SetExtension(unittest::default_float_extension , 411);
+ message->SetExtension(unittest::default_double_extension , 412);
+ message->SetExtension(unittest::default_bool_extension , false);
+ message->SetExtension(unittest::default_string_extension , "415");
+ message->SetExtension(unittest::default_bytes_extension , "416");
+
+ message->SetExtension(unittest::default_nested_enum_extension , unittest::TestAllTypes::FOO);
+ message->SetExtension(unittest::default_foreign_enum_extension, unittest::FOREIGN_FOO );
+ message->SetExtension(unittest::default_import_enum_extension , unittest_import::IMPORT_FOO);
+
+ message->SetExtension(unittest::default_string_piece_extension, "424");
+ message->SetExtension(unittest::default_cord_extension, "425");
+
+ SetOneofFields(message);
+}
+
+void TestUtil::SetOneofFields(unittest::TestAllExtensions* message) {
+ message->SetExtension(unittest::oneof_uint32_extension, 601);
+ message->MutableExtension(unittest::oneof_nested_message_extension)->set_bb(602);
+ message->SetExtension(unittest::oneof_string_extension, "603");
+ message->SetExtension(unittest::oneof_bytes_extension, "604");
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::SetAllFieldsAndExtensions(
+ unittest::TestFieldOrderings* message) {
+ GOOGLE_CHECK(message);
+ message->set_my_int(1);
+ message->set_my_string("foo");
+ message->set_my_float(1.0);
+ message->SetExtension(unittest::my_extension_int, 23);
+ message->SetExtension(unittest::my_extension_string, "bar");
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ModifyRepeatedExtensions(unittest::TestAllExtensions* message) {
+ message->SetExtension(unittest::repeated_int32_extension , 1, 501);
+ message->SetExtension(unittest::repeated_int64_extension , 1, 502);
+ message->SetExtension(unittest::repeated_uint32_extension , 1, 503);
+ message->SetExtension(unittest::repeated_uint64_extension , 1, 504);
+ message->SetExtension(unittest::repeated_sint32_extension , 1, 505);
+ message->SetExtension(unittest::repeated_sint64_extension , 1, 506);
+ message->SetExtension(unittest::repeated_fixed32_extension , 1, 507);
+ message->SetExtension(unittest::repeated_fixed64_extension , 1, 508);
+ message->SetExtension(unittest::repeated_sfixed32_extension, 1, 509);
+ message->SetExtension(unittest::repeated_sfixed64_extension, 1, 510);
+ message->SetExtension(unittest::repeated_float_extension , 1, 511);
+ message->SetExtension(unittest::repeated_double_extension , 1, 512);
+ message->SetExtension(unittest::repeated_bool_extension , 1, true);
+ message->SetExtension(unittest::repeated_string_extension , 1, "515");
+ message->SetExtension(unittest::repeated_bytes_extension , 1, "516");
+
+ message->MutableExtension(unittest::repeatedgroup_extension , 1)->set_a(517);
+ message->MutableExtension(unittest::repeated_nested_message_extension , 1)->set_bb(518);
+ message->MutableExtension(unittest::repeated_foreign_message_extension, 1)->set_c(519);
+ message->MutableExtension(unittest::repeated_import_message_extension , 1)->set_d(520);
+ message->MutableExtension(unittest::repeated_lazy_message_extension , 1)->set_bb(527);
+
+ message->SetExtension(unittest::repeated_nested_enum_extension , 1, unittest::TestAllTypes::FOO);
+ message->SetExtension(unittest::repeated_foreign_enum_extension, 1, unittest::FOREIGN_FOO );
+ message->SetExtension(unittest::repeated_import_enum_extension , 1, unittest_import::IMPORT_FOO);
+
+ message->SetExtension(unittest::repeated_string_piece_extension, 1, "524");
+ message->SetExtension(unittest::repeated_cord_extension, 1, "525");
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectAllExtensionsSet(
+ const unittest::TestAllExtensions& message) {
+ EXPECT_TRUE(message.HasExtension(unittest::optional_int32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_int64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_uint32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_uint64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sint32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sint64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_fixed32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_fixed64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sfixed32_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sfixed64_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_float_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_double_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_bool_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_string_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_bytes_extension ));
+
+ EXPECT_TRUE(message.HasExtension(unittest::optionalgroup_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_nested_message_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_foreign_message_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_import_message_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_public_import_message_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_lazy_message_extension ));
+
+ EXPECT_TRUE(message.GetExtension(unittest::optionalgroup_extension ).has_a());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_nested_message_extension ).has_bb());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_foreign_message_extension ).has_c());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_import_message_extension ).has_d());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_public_import_message_extension).has_e());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_lazy_message_extension ).has_bb());
+
+ EXPECT_TRUE(message.HasExtension(unittest::optional_nested_enum_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_foreign_enum_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_import_enum_extension ));
+
+ EXPECT_TRUE(message.HasExtension(unittest::optional_string_piece_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_cord_extension));
+
+ EXPECT_EQ(101 , message.GetExtension(unittest::optional_int32_extension ));
+ EXPECT_EQ(102 , message.GetExtension(unittest::optional_int64_extension ));
+ EXPECT_EQ(103 , message.GetExtension(unittest::optional_uint32_extension ));
+ EXPECT_EQ(104 , message.GetExtension(unittest::optional_uint64_extension ));
+ EXPECT_EQ(105 , message.GetExtension(unittest::optional_sint32_extension ));
+ EXPECT_EQ(106 , message.GetExtension(unittest::optional_sint64_extension ));
+ EXPECT_EQ(107 , message.GetExtension(unittest::optional_fixed32_extension ));
+ EXPECT_EQ(108 , message.GetExtension(unittest::optional_fixed64_extension ));
+ EXPECT_EQ(109 , message.GetExtension(unittest::optional_sfixed32_extension));
+ EXPECT_EQ(110 , message.GetExtension(unittest::optional_sfixed64_extension));
+ EXPECT_EQ(111 , message.GetExtension(unittest::optional_float_extension ));
+ EXPECT_EQ(112 , message.GetExtension(unittest::optional_double_extension ));
+ EXPECT_TRUE( message.GetExtension(unittest::optional_bool_extension ));
+ EXPECT_EQ("115", message.GetExtension(unittest::optional_string_extension ));
+ EXPECT_EQ("116", message.GetExtension(unittest::optional_bytes_extension ));
+
+ EXPECT_EQ(117, message.GetExtension(unittest::optionalgroup_extension ).a());
+ EXPECT_EQ(118, message.GetExtension(unittest::optional_nested_message_extension ).bb());
+ EXPECT_EQ(119, message.GetExtension(unittest::optional_foreign_message_extension).c());
+ EXPECT_EQ(120, message.GetExtension(unittest::optional_import_message_extension ).d());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, message.GetExtension(unittest::optional_nested_enum_extension ));
+ EXPECT_EQ(unittest::FOREIGN_BAZ , message.GetExtension(unittest::optional_foreign_enum_extension));
+ EXPECT_EQ(unittest_import::IMPORT_BAZ, message.GetExtension(unittest::optional_import_enum_extension ));
+
+ EXPECT_EQ("124", message.GetExtension(unittest::optional_string_piece_extension));
+ EXPECT_EQ("125", message.GetExtension(unittest::optional_cord_extension));
+ EXPECT_EQ(126, message.GetExtension(unittest::optional_public_import_message_extension ).e());
+ EXPECT_EQ(127, message.GetExtension(unittest::optional_lazy_message_extension).bb());
+
+ // -----------------------------------------------------------------
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed32_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed64_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_float_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_double_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bool_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bytes_extension ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeatedgroup_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_message_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_lazy_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_enum_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_enum_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_enum_extension ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_piece_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_cord_extension));
+
+ EXPECT_EQ(201 , message.GetExtension(unittest::repeated_int32_extension , 0));
+ EXPECT_EQ(202 , message.GetExtension(unittest::repeated_int64_extension , 0));
+ EXPECT_EQ(203 , message.GetExtension(unittest::repeated_uint32_extension , 0));
+ EXPECT_EQ(204 , message.GetExtension(unittest::repeated_uint64_extension , 0));
+ EXPECT_EQ(205 , message.GetExtension(unittest::repeated_sint32_extension , 0));
+ EXPECT_EQ(206 , message.GetExtension(unittest::repeated_sint64_extension , 0));
+ EXPECT_EQ(207 , message.GetExtension(unittest::repeated_fixed32_extension , 0));
+ EXPECT_EQ(208 , message.GetExtension(unittest::repeated_fixed64_extension , 0));
+ EXPECT_EQ(209 , message.GetExtension(unittest::repeated_sfixed32_extension, 0));
+ EXPECT_EQ(210 , message.GetExtension(unittest::repeated_sfixed64_extension, 0));
+ EXPECT_EQ(211 , message.GetExtension(unittest::repeated_float_extension , 0));
+ EXPECT_EQ(212 , message.GetExtension(unittest::repeated_double_extension , 0));
+ EXPECT_TRUE( message.GetExtension(unittest::repeated_bool_extension , 0));
+ EXPECT_EQ("215", message.GetExtension(unittest::repeated_string_extension , 0));
+ EXPECT_EQ("216", message.GetExtension(unittest::repeated_bytes_extension , 0));
+
+ EXPECT_EQ(217, message.GetExtension(unittest::repeatedgroup_extension , 0).a());
+ EXPECT_EQ(218, message.GetExtension(unittest::repeated_nested_message_extension , 0).bb());
+ EXPECT_EQ(219, message.GetExtension(unittest::repeated_foreign_message_extension, 0).c());
+ EXPECT_EQ(220, message.GetExtension(unittest::repeated_import_message_extension , 0).d());
+ EXPECT_EQ(227, message.GetExtension(unittest::repeated_lazy_message_extension , 0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.GetExtension(unittest::repeated_nested_enum_extension , 0));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.GetExtension(unittest::repeated_foreign_enum_extension, 0));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.GetExtension(unittest::repeated_import_enum_extension , 0));
+
+ EXPECT_EQ("224", message.GetExtension(unittest::repeated_string_piece_extension, 0));
+ EXPECT_EQ("225", message.GetExtension(unittest::repeated_cord_extension, 0));
+
+ EXPECT_EQ(301 , message.GetExtension(unittest::repeated_int32_extension , 1));
+ EXPECT_EQ(302 , message.GetExtension(unittest::repeated_int64_extension , 1));
+ EXPECT_EQ(303 , message.GetExtension(unittest::repeated_uint32_extension , 1));
+ EXPECT_EQ(304 , message.GetExtension(unittest::repeated_uint64_extension , 1));
+ EXPECT_EQ(305 , message.GetExtension(unittest::repeated_sint32_extension , 1));
+ EXPECT_EQ(306 , message.GetExtension(unittest::repeated_sint64_extension , 1));
+ EXPECT_EQ(307 , message.GetExtension(unittest::repeated_fixed32_extension , 1));
+ EXPECT_EQ(308 , message.GetExtension(unittest::repeated_fixed64_extension , 1));
+ EXPECT_EQ(309 , message.GetExtension(unittest::repeated_sfixed32_extension, 1));
+ EXPECT_EQ(310 , message.GetExtension(unittest::repeated_sfixed64_extension, 1));
+ EXPECT_EQ(311 , message.GetExtension(unittest::repeated_float_extension , 1));
+ EXPECT_EQ(312 , message.GetExtension(unittest::repeated_double_extension , 1));
+ EXPECT_FALSE( message.GetExtension(unittest::repeated_bool_extension , 1));
+ EXPECT_EQ("315", message.GetExtension(unittest::repeated_string_extension , 1));
+ EXPECT_EQ("316", message.GetExtension(unittest::repeated_bytes_extension , 1));
+
+ EXPECT_EQ(317, message.GetExtension(unittest::repeatedgroup_extension , 1).a());
+ EXPECT_EQ(318, message.GetExtension(unittest::repeated_nested_message_extension , 1).bb());
+ EXPECT_EQ(319, message.GetExtension(unittest::repeated_foreign_message_extension, 1).c());
+ EXPECT_EQ(320, message.GetExtension(unittest::repeated_import_message_extension , 1).d());
+ EXPECT_EQ(327, message.GetExtension(unittest::repeated_lazy_message_extension , 1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, message.GetExtension(unittest::repeated_nested_enum_extension , 1));
+ EXPECT_EQ(unittest::FOREIGN_BAZ , message.GetExtension(unittest::repeated_foreign_enum_extension, 1));
+ EXPECT_EQ(unittest_import::IMPORT_BAZ, message.GetExtension(unittest::repeated_import_enum_extension , 1));
+
+ EXPECT_EQ("324", message.GetExtension(unittest::repeated_string_piece_extension, 1));
+ EXPECT_EQ("325", message.GetExtension(unittest::repeated_cord_extension, 1));
+
+ // -----------------------------------------------------------------
+
+ EXPECT_TRUE(message.HasExtension(unittest::default_int32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_int64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_uint32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_uint64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sint32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sint64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_fixed32_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_fixed64_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sfixed32_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sfixed64_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::default_float_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_double_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_bool_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_string_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_bytes_extension ));
+
+ EXPECT_TRUE(message.HasExtension(unittest::default_nested_enum_extension ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_foreign_enum_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::default_import_enum_extension ));
+
+ EXPECT_TRUE(message.HasExtension(unittest::default_string_piece_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::default_cord_extension));
+
+ EXPECT_EQ(401 , message.GetExtension(unittest::default_int32_extension ));
+ EXPECT_EQ(402 , message.GetExtension(unittest::default_int64_extension ));
+ EXPECT_EQ(403 , message.GetExtension(unittest::default_uint32_extension ));
+ EXPECT_EQ(404 , message.GetExtension(unittest::default_uint64_extension ));
+ EXPECT_EQ(405 , message.GetExtension(unittest::default_sint32_extension ));
+ EXPECT_EQ(406 , message.GetExtension(unittest::default_sint64_extension ));
+ EXPECT_EQ(407 , message.GetExtension(unittest::default_fixed32_extension ));
+ EXPECT_EQ(408 , message.GetExtension(unittest::default_fixed64_extension ));
+ EXPECT_EQ(409 , message.GetExtension(unittest::default_sfixed32_extension));
+ EXPECT_EQ(410 , message.GetExtension(unittest::default_sfixed64_extension));
+ EXPECT_EQ(411 , message.GetExtension(unittest::default_float_extension ));
+ EXPECT_EQ(412 , message.GetExtension(unittest::default_double_extension ));
+ EXPECT_FALSE( message.GetExtension(unittest::default_bool_extension ));
+ EXPECT_EQ("415", message.GetExtension(unittest::default_string_extension ));
+ EXPECT_EQ("416", message.GetExtension(unittest::default_bytes_extension ));
+
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message.GetExtension(unittest::default_nested_enum_extension ));
+ EXPECT_EQ(unittest::FOREIGN_FOO , message.GetExtension(unittest::default_foreign_enum_extension));
+ EXPECT_EQ(unittest_import::IMPORT_FOO, message.GetExtension(unittest::default_import_enum_extension ));
+
+ EXPECT_EQ("424", message.GetExtension(unittest::default_string_piece_extension));
+ EXPECT_EQ("425", message.GetExtension(unittest::default_cord_extension));
+
+ EXPECT_TRUE(message.HasExtension(unittest::oneof_uint32_extension));
+ EXPECT_TRUE(message.GetExtension(unittest::oneof_nested_message_extension).has_bb());
+ EXPECT_TRUE(message.HasExtension(unittest::oneof_string_extension));
+ EXPECT_TRUE(message.HasExtension(unittest::oneof_bytes_extension));
+
+ EXPECT_EQ(601, message.GetExtension(unittest::oneof_uint32_extension));
+ EXPECT_EQ(602, message.GetExtension(unittest::oneof_nested_message_extension).bb());
+ EXPECT_EQ("603", message.GetExtension(unittest::oneof_string_extension));
+ EXPECT_EQ("604", message.GetExtension(unittest::oneof_bytes_extension));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectExtensionsClear(
+ const unittest::TestAllExtensions& message) {
+ string serialized;
+ ASSERT_TRUE(message.SerializeToString(&serialized));
+ EXPECT_EQ("", serialized);
+ EXPECT_EQ(0, message.ByteSize());
+
+ // has_blah() should initially be false for all optional fields.
+ EXPECT_FALSE(message.HasExtension(unittest::optional_int32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_int64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_uint32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_uint64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sint32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sint64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_fixed32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_fixed64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sfixed32_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sfixed64_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_float_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_double_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_bool_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_string_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_bytes_extension ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::optionalgroup_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_nested_message_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_foreign_message_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_import_message_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_public_import_message_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_lazy_message_extension ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::optional_nested_enum_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_foreign_enum_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_import_enum_extension ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::optional_string_piece_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_cord_extension));
+
+ // Optional fields without defaults are set to zero or something like it.
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_int32_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_int64_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_uint32_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_uint64_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sint32_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sint64_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_fixed32_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_fixed64_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sfixed32_extension));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sfixed64_extension));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_float_extension ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_double_extension ));
+ EXPECT_FALSE( message.GetExtension(unittest::optional_bool_extension ));
+ EXPECT_EQ("" , message.GetExtension(unittest::optional_string_extension ));
+ EXPECT_EQ("" , message.GetExtension(unittest::optional_bytes_extension ));
+
+ // Embedded messages should also be clear.
+ EXPECT_FALSE(message.GetExtension(unittest::optionalgroup_extension ).has_a());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_nested_message_extension ).has_bb());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_foreign_message_extension ).has_c());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_import_message_extension ).has_d());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_public_import_message_extension).has_e());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_lazy_message_extension ).has_bb());
+
+ EXPECT_EQ(0, message.GetExtension(unittest::optionalgroup_extension ).a());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_nested_message_extension ).bb());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_foreign_message_extension ).c());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_import_message_extension ).d());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_public_import_message_extension).e());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_lazy_message_extension ).bb());
+
+ // Enums without defaults are set to the first value in the enum.
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message.GetExtension(unittest::optional_nested_enum_extension ));
+ EXPECT_EQ(unittest::FOREIGN_FOO , message.GetExtension(unittest::optional_foreign_enum_extension));
+ EXPECT_EQ(unittest_import::IMPORT_FOO, message.GetExtension(unittest::optional_import_enum_extension ));
+
+ EXPECT_EQ("", message.GetExtension(unittest::optional_string_piece_extension));
+ EXPECT_EQ("", message.GetExtension(unittest::optional_cord_extension));
+
+ // Repeated fields are empty.
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_int32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_int64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_uint32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_uint64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sint32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sint64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_fixed32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_fixed64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sfixed32_extension));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sfixed64_extension));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_float_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_double_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_bool_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_string_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_bytes_extension ));
+
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeatedgroup_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_nested_message_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_foreign_message_extension));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_import_message_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_lazy_message_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_nested_enum_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_foreign_enum_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_import_enum_extension ));
+
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_string_piece_extension));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_cord_extension));
+
+ // has_blah() should also be false for all default fields.
+ EXPECT_FALSE(message.HasExtension(unittest::default_int32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_int64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_uint32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_uint64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sint32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sint64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_fixed32_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_fixed64_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sfixed32_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sfixed64_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::default_float_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_double_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_bool_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_string_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_bytes_extension ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::default_nested_enum_extension ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_foreign_enum_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::default_import_enum_extension ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::default_string_piece_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::default_cord_extension));
+
+ // Fields with defaults have their default values (duh).
+ EXPECT_EQ( 41 , message.GetExtension(unittest::default_int32_extension ));
+ EXPECT_EQ( 42 , message.GetExtension(unittest::default_int64_extension ));
+ EXPECT_EQ( 43 , message.GetExtension(unittest::default_uint32_extension ));
+ EXPECT_EQ( 44 , message.GetExtension(unittest::default_uint64_extension ));
+ EXPECT_EQ(-45 , message.GetExtension(unittest::default_sint32_extension ));
+ EXPECT_EQ( 46 , message.GetExtension(unittest::default_sint64_extension ));
+ EXPECT_EQ( 47 , message.GetExtension(unittest::default_fixed32_extension ));
+ EXPECT_EQ( 48 , message.GetExtension(unittest::default_fixed64_extension ));
+ EXPECT_EQ( 49 , message.GetExtension(unittest::default_sfixed32_extension));
+ EXPECT_EQ(-50 , message.GetExtension(unittest::default_sfixed64_extension));
+ EXPECT_EQ( 51.5 , message.GetExtension(unittest::default_float_extension ));
+ EXPECT_EQ( 52e3 , message.GetExtension(unittest::default_double_extension ));
+ EXPECT_TRUE( message.GetExtension(unittest::default_bool_extension ));
+ EXPECT_EQ("hello", message.GetExtension(unittest::default_string_extension ));
+ EXPECT_EQ("world", message.GetExtension(unittest::default_bytes_extension ));
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.GetExtension(unittest::default_nested_enum_extension ));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.GetExtension(unittest::default_foreign_enum_extension));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.GetExtension(unittest::default_import_enum_extension ));
+
+ EXPECT_EQ("abc", message.GetExtension(unittest::default_string_piece_extension));
+ EXPECT_EQ("123", message.GetExtension(unittest::default_cord_extension));
+
+ EXPECT_FALSE(message.HasExtension(unittest::oneof_uint32_extension));
+ EXPECT_FALSE(message.GetExtension(unittest::oneof_nested_message_extension).has_bb());
+ EXPECT_FALSE(message.HasExtension(unittest::oneof_string_extension));
+ EXPECT_FALSE(message.HasExtension(unittest::oneof_bytes_extension));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectRepeatedExtensionsModified(
+ const unittest::TestAllExtensions& message) {
+ // ModifyRepeatedFields only sets the second repeated element of each
+ // field. In addition to verifying this, we also verify that the first
+ // element and size were *not* modified.
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed32_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed64_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_float_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_double_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bool_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bytes_extension ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeatedgroup_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_message_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_lazy_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_enum_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_enum_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_enum_extension ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_piece_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_cord_extension));
+
+ EXPECT_EQ(201 , message.GetExtension(unittest::repeated_int32_extension , 0));
+ EXPECT_EQ(202 , message.GetExtension(unittest::repeated_int64_extension , 0));
+ EXPECT_EQ(203 , message.GetExtension(unittest::repeated_uint32_extension , 0));
+ EXPECT_EQ(204 , message.GetExtension(unittest::repeated_uint64_extension , 0));
+ EXPECT_EQ(205 , message.GetExtension(unittest::repeated_sint32_extension , 0));
+ EXPECT_EQ(206 , message.GetExtension(unittest::repeated_sint64_extension , 0));
+ EXPECT_EQ(207 , message.GetExtension(unittest::repeated_fixed32_extension , 0));
+ EXPECT_EQ(208 , message.GetExtension(unittest::repeated_fixed64_extension , 0));
+ EXPECT_EQ(209 , message.GetExtension(unittest::repeated_sfixed32_extension, 0));
+ EXPECT_EQ(210 , message.GetExtension(unittest::repeated_sfixed64_extension, 0));
+ EXPECT_EQ(211 , message.GetExtension(unittest::repeated_float_extension , 0));
+ EXPECT_EQ(212 , message.GetExtension(unittest::repeated_double_extension , 0));
+ EXPECT_TRUE( message.GetExtension(unittest::repeated_bool_extension , 0));
+ EXPECT_EQ("215", message.GetExtension(unittest::repeated_string_extension , 0));
+ EXPECT_EQ("216", message.GetExtension(unittest::repeated_bytes_extension , 0));
+
+ EXPECT_EQ(217, message.GetExtension(unittest::repeatedgroup_extension , 0).a());
+ EXPECT_EQ(218, message.GetExtension(unittest::repeated_nested_message_extension , 0).bb());
+ EXPECT_EQ(219, message.GetExtension(unittest::repeated_foreign_message_extension, 0).c());
+ EXPECT_EQ(220, message.GetExtension(unittest::repeated_import_message_extension , 0).d());
+ EXPECT_EQ(227, message.GetExtension(unittest::repeated_lazy_message_extension , 0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.GetExtension(unittest::repeated_nested_enum_extension , 0));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.GetExtension(unittest::repeated_foreign_enum_extension, 0));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.GetExtension(unittest::repeated_import_enum_extension , 0));
+
+ EXPECT_EQ("224", message.GetExtension(unittest::repeated_string_piece_extension, 0));
+ EXPECT_EQ("225", message.GetExtension(unittest::repeated_cord_extension, 0));
+
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(501 , message.GetExtension(unittest::repeated_int32_extension , 1));
+ EXPECT_EQ(502 , message.GetExtension(unittest::repeated_int64_extension , 1));
+ EXPECT_EQ(503 , message.GetExtension(unittest::repeated_uint32_extension , 1));
+ EXPECT_EQ(504 , message.GetExtension(unittest::repeated_uint64_extension , 1));
+ EXPECT_EQ(505 , message.GetExtension(unittest::repeated_sint32_extension , 1));
+ EXPECT_EQ(506 , message.GetExtension(unittest::repeated_sint64_extension , 1));
+ EXPECT_EQ(507 , message.GetExtension(unittest::repeated_fixed32_extension , 1));
+ EXPECT_EQ(508 , message.GetExtension(unittest::repeated_fixed64_extension , 1));
+ EXPECT_EQ(509 , message.GetExtension(unittest::repeated_sfixed32_extension, 1));
+ EXPECT_EQ(510 , message.GetExtension(unittest::repeated_sfixed64_extension, 1));
+ EXPECT_EQ(511 , message.GetExtension(unittest::repeated_float_extension , 1));
+ EXPECT_EQ(512 , message.GetExtension(unittest::repeated_double_extension , 1));
+ EXPECT_TRUE( message.GetExtension(unittest::repeated_bool_extension , 1));
+ EXPECT_EQ("515", message.GetExtension(unittest::repeated_string_extension , 1));
+ EXPECT_EQ("516", message.GetExtension(unittest::repeated_bytes_extension , 1));
+
+ EXPECT_EQ(517, message.GetExtension(unittest::repeatedgroup_extension , 1).a());
+ EXPECT_EQ(518, message.GetExtension(unittest::repeated_nested_message_extension , 1).bb());
+ EXPECT_EQ(519, message.GetExtension(unittest::repeated_foreign_message_extension, 1).c());
+ EXPECT_EQ(520, message.GetExtension(unittest::repeated_import_message_extension , 1).d());
+ EXPECT_EQ(527, message.GetExtension(unittest::repeated_lazy_message_extension , 1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::FOO, message.GetExtension(unittest::repeated_nested_enum_extension , 1));
+ EXPECT_EQ(unittest::FOREIGN_FOO , message.GetExtension(unittest::repeated_foreign_enum_extension, 1));
+ EXPECT_EQ(unittest_import::IMPORT_FOO, message.GetExtension(unittest::repeated_import_enum_extension , 1));
+
+ EXPECT_EQ("524", message.GetExtension(unittest::repeated_string_piece_extension, 1));
+ EXPECT_EQ("525", message.GetExtension(unittest::repeated_cord_extension, 1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::SetPackedExtensions(unittest::TestPackedExtensions* message) {
+ message->AddExtension(unittest::packed_int32_extension , 601);
+ message->AddExtension(unittest::packed_int64_extension , 602);
+ message->AddExtension(unittest::packed_uint32_extension , 603);
+ message->AddExtension(unittest::packed_uint64_extension , 604);
+ message->AddExtension(unittest::packed_sint32_extension , 605);
+ message->AddExtension(unittest::packed_sint64_extension , 606);
+ message->AddExtension(unittest::packed_fixed32_extension , 607);
+ message->AddExtension(unittest::packed_fixed64_extension , 608);
+ message->AddExtension(unittest::packed_sfixed32_extension, 609);
+ message->AddExtension(unittest::packed_sfixed64_extension, 610);
+ message->AddExtension(unittest::packed_float_extension , 611);
+ message->AddExtension(unittest::packed_double_extension , 612);
+ message->AddExtension(unittest::packed_bool_extension , true);
+ message->AddExtension(unittest::packed_enum_extension, unittest::FOREIGN_BAR);
+ // add a second one of each field
+ message->AddExtension(unittest::packed_int32_extension , 701);
+ message->AddExtension(unittest::packed_int64_extension , 702);
+ message->AddExtension(unittest::packed_uint32_extension , 703);
+ message->AddExtension(unittest::packed_uint64_extension , 704);
+ message->AddExtension(unittest::packed_sint32_extension , 705);
+ message->AddExtension(unittest::packed_sint64_extension , 706);
+ message->AddExtension(unittest::packed_fixed32_extension , 707);
+ message->AddExtension(unittest::packed_fixed64_extension , 708);
+ message->AddExtension(unittest::packed_sfixed32_extension, 709);
+ message->AddExtension(unittest::packed_sfixed64_extension, 710);
+ message->AddExtension(unittest::packed_float_extension , 711);
+ message->AddExtension(unittest::packed_double_extension , 712);
+ message->AddExtension(unittest::packed_bool_extension , false);
+ message->AddExtension(unittest::packed_enum_extension, unittest::FOREIGN_BAZ);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ModifyPackedExtensions(unittest::TestPackedExtensions* message) {
+ message->SetExtension(unittest::packed_int32_extension , 1, 801);
+ message->SetExtension(unittest::packed_int64_extension , 1, 802);
+ message->SetExtension(unittest::packed_uint32_extension , 1, 803);
+ message->SetExtension(unittest::packed_uint64_extension , 1, 804);
+ message->SetExtension(unittest::packed_sint32_extension , 1, 805);
+ message->SetExtension(unittest::packed_sint64_extension , 1, 806);
+ message->SetExtension(unittest::packed_fixed32_extension , 1, 807);
+ message->SetExtension(unittest::packed_fixed64_extension , 1, 808);
+ message->SetExtension(unittest::packed_sfixed32_extension, 1, 809);
+ message->SetExtension(unittest::packed_sfixed64_extension, 1, 810);
+ message->SetExtension(unittest::packed_float_extension , 1, 811);
+ message->SetExtension(unittest::packed_double_extension , 1, 812);
+ message->SetExtension(unittest::packed_bool_extension , 1, true);
+ message->SetExtension(unittest::packed_enum_extension , 1,
+ unittest::FOREIGN_FOO);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectPackedExtensionsSet(
+ const unittest::TestPackedExtensions& message) {
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed32_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed64_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_float_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_double_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_bool_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_enum_extension ));
+
+ EXPECT_EQ(601 , message.GetExtension(unittest::packed_int32_extension , 0));
+ EXPECT_EQ(602 , message.GetExtension(unittest::packed_int64_extension , 0));
+ EXPECT_EQ(603 , message.GetExtension(unittest::packed_uint32_extension , 0));
+ EXPECT_EQ(604 , message.GetExtension(unittest::packed_uint64_extension , 0));
+ EXPECT_EQ(605 , message.GetExtension(unittest::packed_sint32_extension , 0));
+ EXPECT_EQ(606 , message.GetExtension(unittest::packed_sint64_extension , 0));
+ EXPECT_EQ(607 , message.GetExtension(unittest::packed_fixed32_extension , 0));
+ EXPECT_EQ(608 , message.GetExtension(unittest::packed_fixed64_extension , 0));
+ EXPECT_EQ(609 , message.GetExtension(unittest::packed_sfixed32_extension, 0));
+ EXPECT_EQ(610 , message.GetExtension(unittest::packed_sfixed64_extension, 0));
+ EXPECT_EQ(611 , message.GetExtension(unittest::packed_float_extension , 0));
+ EXPECT_EQ(612 , message.GetExtension(unittest::packed_double_extension , 0));
+ EXPECT_TRUE( message.GetExtension(unittest::packed_bool_extension , 0));
+ EXPECT_EQ(unittest::FOREIGN_BAR,
+ message.GetExtension(unittest::packed_enum_extension, 0));
+ EXPECT_EQ(701 , message.GetExtension(unittest::packed_int32_extension , 1));
+ EXPECT_EQ(702 , message.GetExtension(unittest::packed_int64_extension , 1));
+ EXPECT_EQ(703 , message.GetExtension(unittest::packed_uint32_extension , 1));
+ EXPECT_EQ(704 , message.GetExtension(unittest::packed_uint64_extension , 1));
+ EXPECT_EQ(705 , message.GetExtension(unittest::packed_sint32_extension , 1));
+ EXPECT_EQ(706 , message.GetExtension(unittest::packed_sint64_extension , 1));
+ EXPECT_EQ(707 , message.GetExtension(unittest::packed_fixed32_extension , 1));
+ EXPECT_EQ(708 , message.GetExtension(unittest::packed_fixed64_extension , 1));
+ EXPECT_EQ(709 , message.GetExtension(unittest::packed_sfixed32_extension, 1));
+ EXPECT_EQ(710 , message.GetExtension(unittest::packed_sfixed64_extension, 1));
+ EXPECT_EQ(711 , message.GetExtension(unittest::packed_float_extension , 1));
+ EXPECT_EQ(712 , message.GetExtension(unittest::packed_double_extension , 1));
+ EXPECT_FALSE( message.GetExtension(unittest::packed_bool_extension , 1));
+ EXPECT_EQ(unittest::FOREIGN_BAZ,
+ message.GetExtension(unittest::packed_enum_extension, 1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectPackedExtensionsClear(
+ const unittest::TestPackedExtensions& message) {
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_int32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_int64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_uint32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_uint64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sint32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sint64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_fixed32_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_fixed64_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sfixed32_extension));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sfixed64_extension));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_float_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_double_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_bool_extension ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_enum_extension ));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectPackedExtensionsModified(
+ const unittest::TestPackedExtensions& message) {
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed32_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed64_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_float_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_double_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_bool_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_enum_extension ));
+ EXPECT_EQ(601 , message.GetExtension(unittest::packed_int32_extension , 0));
+ EXPECT_EQ(602 , message.GetExtension(unittest::packed_int64_extension , 0));
+ EXPECT_EQ(603 , message.GetExtension(unittest::packed_uint32_extension , 0));
+ EXPECT_EQ(604 , message.GetExtension(unittest::packed_uint64_extension , 0));
+ EXPECT_EQ(605 , message.GetExtension(unittest::packed_sint32_extension , 0));
+ EXPECT_EQ(606 , message.GetExtension(unittest::packed_sint64_extension , 0));
+ EXPECT_EQ(607 , message.GetExtension(unittest::packed_fixed32_extension , 0));
+ EXPECT_EQ(608 , message.GetExtension(unittest::packed_fixed64_extension , 0));
+ EXPECT_EQ(609 , message.GetExtension(unittest::packed_sfixed32_extension, 0));
+ EXPECT_EQ(610 , message.GetExtension(unittest::packed_sfixed64_extension, 0));
+ EXPECT_EQ(611 , message.GetExtension(unittest::packed_float_extension , 0));
+ EXPECT_EQ(612 , message.GetExtension(unittest::packed_double_extension , 0));
+ EXPECT_TRUE( message.GetExtension(unittest::packed_bool_extension , 0));
+ EXPECT_EQ(unittest::FOREIGN_BAR,
+ message.GetExtension(unittest::packed_enum_extension, 0));
+
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(801 , message.GetExtension(unittest::packed_int32_extension , 1));
+ EXPECT_EQ(802 , message.GetExtension(unittest::packed_int64_extension , 1));
+ EXPECT_EQ(803 , message.GetExtension(unittest::packed_uint32_extension , 1));
+ EXPECT_EQ(804 , message.GetExtension(unittest::packed_uint64_extension , 1));
+ EXPECT_EQ(805 , message.GetExtension(unittest::packed_sint32_extension , 1));
+ EXPECT_EQ(806 , message.GetExtension(unittest::packed_sint64_extension , 1));
+ EXPECT_EQ(807 , message.GetExtension(unittest::packed_fixed32_extension , 1));
+ EXPECT_EQ(808 , message.GetExtension(unittest::packed_fixed64_extension , 1));
+ EXPECT_EQ(809 , message.GetExtension(unittest::packed_sfixed32_extension, 1));
+ EXPECT_EQ(810 , message.GetExtension(unittest::packed_sfixed64_extension, 1));
+ EXPECT_EQ(811 , message.GetExtension(unittest::packed_float_extension , 1));
+ EXPECT_EQ(812 , message.GetExtension(unittest::packed_double_extension , 1));
+ EXPECT_TRUE( message.GetExtension(unittest::packed_bool_extension , 1));
+ EXPECT_EQ(unittest::FOREIGN_FOO,
+ message.GetExtension(unittest::packed_enum_extension, 1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectUnpackedExtensionsSet(
+ const unittest::TestUnpackedExtensions& message) {
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_int32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_int64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_uint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_uint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_sint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_sint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_fixed32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_fixed64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_sfixed32_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_sfixed64_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_float_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_double_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_bool_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::unpacked_enum_extension ));
+
+ EXPECT_EQ(601 , message.GetExtension(unittest::unpacked_int32_extension , 0));
+ EXPECT_EQ(602 , message.GetExtension(unittest::unpacked_int64_extension , 0));
+ EXPECT_EQ(603 , message.GetExtension(unittest::unpacked_uint32_extension , 0));
+ EXPECT_EQ(604 , message.GetExtension(unittest::unpacked_uint64_extension , 0));
+ EXPECT_EQ(605 , message.GetExtension(unittest::unpacked_sint32_extension , 0));
+ EXPECT_EQ(606 , message.GetExtension(unittest::unpacked_sint64_extension , 0));
+ EXPECT_EQ(607 , message.GetExtension(unittest::unpacked_fixed32_extension , 0));
+ EXPECT_EQ(608 , message.GetExtension(unittest::unpacked_fixed64_extension , 0));
+ EXPECT_EQ(609 , message.GetExtension(unittest::unpacked_sfixed32_extension, 0));
+ EXPECT_EQ(610 , message.GetExtension(unittest::unpacked_sfixed64_extension, 0));
+ EXPECT_EQ(611 , message.GetExtension(unittest::unpacked_float_extension , 0));
+ EXPECT_EQ(612 , message.GetExtension(unittest::unpacked_double_extension , 0));
+ EXPECT_EQ(true , message.GetExtension(unittest::unpacked_bool_extension , 0));
+ EXPECT_EQ(unittest::FOREIGN_BAR,
+ message.GetExtension(unittest::unpacked_enum_extension, 0));
+ EXPECT_EQ(701 , message.GetExtension(unittest::unpacked_int32_extension , 1));
+ EXPECT_EQ(702 , message.GetExtension(unittest::unpacked_int64_extension , 1));
+ EXPECT_EQ(703 , message.GetExtension(unittest::unpacked_uint32_extension , 1));
+ EXPECT_EQ(704 , message.GetExtension(unittest::unpacked_uint64_extension , 1));
+ EXPECT_EQ(705 , message.GetExtension(unittest::unpacked_sint32_extension , 1));
+ EXPECT_EQ(706 , message.GetExtension(unittest::unpacked_sint64_extension , 1));
+ EXPECT_EQ(707 , message.GetExtension(unittest::unpacked_fixed32_extension , 1));
+ EXPECT_EQ(708 , message.GetExtension(unittest::unpacked_fixed64_extension , 1));
+ EXPECT_EQ(709 , message.GetExtension(unittest::unpacked_sfixed32_extension, 1));
+ EXPECT_EQ(710 , message.GetExtension(unittest::unpacked_sfixed64_extension, 1));
+ EXPECT_EQ(711 , message.GetExtension(unittest::unpacked_float_extension , 1));
+ EXPECT_EQ(712 , message.GetExtension(unittest::unpacked_double_extension , 1));
+ EXPECT_EQ(false, message.GetExtension(unittest::unpacked_bool_extension , 1));
+ EXPECT_EQ(unittest::FOREIGN_BAZ,
+ message.GetExtension(unittest::unpacked_enum_extension, 1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ExpectAllFieldsAndExtensionsInOrder(const string& serialized) {
+ // We set each field individually, serialize separately, and concatenate all
+ // the strings in canonical order to determine the expected serialization.
+ string expected;
+ unittest::TestFieldOrderings message;
+ message.set_my_int(1); // Field 1.
+ message.AppendToString(&expected);
+ message.Clear();
+ message.SetExtension(unittest::my_extension_int, 23); // Field 5.
+ message.AppendToString(&expected);
+ message.Clear();
+ message.set_my_string("foo"); // Field 11.
+ message.AppendToString(&expected);
+ message.Clear();
+ message.SetExtension(unittest::my_extension_string, "bar"); // Field 50.
+ message.AppendToString(&expected);
+ message.Clear();
+ message.set_my_float(1.0); // Field 101.
+ message.AppendToString(&expected);
+ message.Clear();
+
+ // We don't EXPECT_EQ() since we don't want to print raw bytes to stdout.
+ EXPECT_TRUE(serialized == expected);
+}
+
+void TestUtil::ExpectLastRepeatedsRemoved(
+ const unittest::TestAllTypes& message) {
+ ASSERT_EQ(1, message.repeated_int32_size ());
+ ASSERT_EQ(1, message.repeated_int64_size ());
+ ASSERT_EQ(1, message.repeated_uint32_size ());
+ ASSERT_EQ(1, message.repeated_uint64_size ());
+ ASSERT_EQ(1, message.repeated_sint32_size ());
+ ASSERT_EQ(1, message.repeated_sint64_size ());
+ ASSERT_EQ(1, message.repeated_fixed32_size ());
+ ASSERT_EQ(1, message.repeated_fixed64_size ());
+ ASSERT_EQ(1, message.repeated_sfixed32_size());
+ ASSERT_EQ(1, message.repeated_sfixed64_size());
+ ASSERT_EQ(1, message.repeated_float_size ());
+ ASSERT_EQ(1, message.repeated_double_size ());
+ ASSERT_EQ(1, message.repeated_bool_size ());
+ ASSERT_EQ(1, message.repeated_string_size ());
+ ASSERT_EQ(1, message.repeated_bytes_size ());
+
+ ASSERT_EQ(1, message.repeatedgroup_size ());
+ ASSERT_EQ(1, message.repeated_nested_message_size ());
+ ASSERT_EQ(1, message.repeated_foreign_message_size());
+ ASSERT_EQ(1, message.repeated_import_message_size ());
+ ASSERT_EQ(1, message.repeated_import_message_size ());
+ ASSERT_EQ(1, message.repeated_nested_enum_size ());
+ ASSERT_EQ(1, message.repeated_foreign_enum_size ());
+ ASSERT_EQ(1, message.repeated_import_enum_size ());
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ ASSERT_EQ(1, message.repeated_string_piece_size());
+ ASSERT_EQ(1, message.repeated_cord_size());
+#endif
+
+ // Test that the remaining element is the correct one.
+ EXPECT_EQ(201 , message.repeated_int32 (0));
+ EXPECT_EQ(202 , message.repeated_int64 (0));
+ EXPECT_EQ(203 , message.repeated_uint32 (0));
+ EXPECT_EQ(204 , message.repeated_uint64 (0));
+ EXPECT_EQ(205 , message.repeated_sint32 (0));
+ EXPECT_EQ(206 , message.repeated_sint64 (0));
+ EXPECT_EQ(207 , message.repeated_fixed32 (0));
+ EXPECT_EQ(208 , message.repeated_fixed64 (0));
+ EXPECT_EQ(209 , message.repeated_sfixed32(0));
+ EXPECT_EQ(210 , message.repeated_sfixed64(0));
+ EXPECT_EQ(211 , message.repeated_float (0));
+ EXPECT_EQ(212 , message.repeated_double (0));
+ EXPECT_TRUE( message.repeated_bool (0));
+ EXPECT_EQ("215", message.repeated_string (0));
+ EXPECT_EQ("216", message.repeated_bytes (0));
+
+ EXPECT_EQ(217, message.repeatedgroup (0).a());
+ EXPECT_EQ(218, message.repeated_nested_message (0).bb());
+ EXPECT_EQ(219, message.repeated_foreign_message(0).c());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.repeated_nested_enum (0));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.repeated_foreign_enum(0));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.repeated_import_enum (0));
+}
+
+void TestUtil::ExpectLastRepeatedExtensionsRemoved(
+ const unittest::TestAllExtensions& message) {
+
+ // Test that one element was removed.
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_int32_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_int64_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_uint32_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_uint64_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_sint32_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_sint64_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_fixed32_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_fixed64_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_sfixed32_extension));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_sfixed64_extension));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_float_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_double_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_bool_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_string_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_bytes_extension ));
+
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeatedgroup_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_nested_message_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_foreign_message_extension));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_import_message_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_lazy_message_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_nested_enum_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_foreign_enum_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_import_enum_extension ));
+
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_string_piece_extension));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_cord_extension));
+
+ // Test that the remaining element is the correct one.
+ EXPECT_EQ(201 , message.GetExtension(unittest::repeated_int32_extension , 0));
+ EXPECT_EQ(202 , message.GetExtension(unittest::repeated_int64_extension , 0));
+ EXPECT_EQ(203 , message.GetExtension(unittest::repeated_uint32_extension , 0));
+ EXPECT_EQ(204 , message.GetExtension(unittest::repeated_uint64_extension , 0));
+ EXPECT_EQ(205 , message.GetExtension(unittest::repeated_sint32_extension , 0));
+ EXPECT_EQ(206 , message.GetExtension(unittest::repeated_sint64_extension , 0));
+ EXPECT_EQ(207 , message.GetExtension(unittest::repeated_fixed32_extension , 0));
+ EXPECT_EQ(208 , message.GetExtension(unittest::repeated_fixed64_extension , 0));
+ EXPECT_EQ(209 , message.GetExtension(unittest::repeated_sfixed32_extension, 0));
+ EXPECT_EQ(210 , message.GetExtension(unittest::repeated_sfixed64_extension, 0));
+ EXPECT_EQ(211 , message.GetExtension(unittest::repeated_float_extension , 0));
+ EXPECT_EQ(212 , message.GetExtension(unittest::repeated_double_extension , 0));
+ EXPECT_TRUE( message.GetExtension(unittest::repeated_bool_extension , 0));
+ EXPECT_EQ("215", message.GetExtension(unittest::repeated_string_extension , 0));
+ EXPECT_EQ("216", message.GetExtension(unittest::repeated_bytes_extension , 0));
+
+ EXPECT_EQ(217, message.GetExtension(unittest::repeatedgroup_extension , 0).a());
+ EXPECT_EQ(218, message.GetExtension(unittest::repeated_nested_message_extension , 0).bb());
+ EXPECT_EQ(219, message.GetExtension(unittest::repeated_foreign_message_extension, 0).c());
+ EXPECT_EQ(220, message.GetExtension(unittest::repeated_import_message_extension , 0).d());
+ EXPECT_EQ(227, message.GetExtension(unittest::repeated_lazy_message_extension , 0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.GetExtension(unittest::repeated_nested_enum_extension , 0));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.GetExtension(unittest::repeated_foreign_enum_extension, 0));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.GetExtension(unittest::repeated_import_enum_extension , 0));
+
+ EXPECT_EQ("224", message.GetExtension(unittest::repeated_string_piece_extension, 0));
+ EXPECT_EQ("225", message.GetExtension(unittest::repeated_cord_extension, 0));
+}
+
+void TestUtil::ExpectLastRepeatedsReleased(
+ const unittest::TestAllTypes& message) {
+ ASSERT_EQ(1, message.repeatedgroup_size ());
+ ASSERT_EQ(1, message.repeated_nested_message_size ());
+ ASSERT_EQ(1, message.repeated_foreign_message_size());
+ ASSERT_EQ(1, message.repeated_import_message_size ());
+ ASSERT_EQ(1, message.repeated_import_message_size ());
+
+ EXPECT_EQ(217, message.repeatedgroup (0).a());
+ EXPECT_EQ(218, message.repeated_nested_message (0).bb());
+ EXPECT_EQ(219, message.repeated_foreign_message(0).c());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+}
+
+void TestUtil::ExpectLastRepeatedExtensionsReleased(
+ const unittest::TestAllExtensions& message) {
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeatedgroup_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_nested_message_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_foreign_message_extension));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_import_message_extension ));
+ ASSERT_EQ(1, message.ExtensionSize(unittest::repeated_lazy_message_extension ));
+
+ EXPECT_EQ(217, message.GetExtension(unittest::repeatedgroup_extension , 0).a());
+ EXPECT_EQ(218, message.GetExtension(unittest::repeated_nested_message_extension , 0).bb());
+ EXPECT_EQ(219, message.GetExtension(unittest::repeated_foreign_message_extension, 0).c());
+ EXPECT_EQ(220, message.GetExtension(unittest::repeated_import_message_extension , 0).d());
+ EXPECT_EQ(227, message.GetExtension(unittest::repeated_lazy_message_extension , 0).bb());
+}
+
+void TestUtil::ExpectRepeatedsSwapped(
+ const unittest::TestAllTypes& message) {
+ ASSERT_EQ(2, message.repeated_int32_size ());
+ ASSERT_EQ(2, message.repeated_int64_size ());
+ ASSERT_EQ(2, message.repeated_uint32_size ());
+ ASSERT_EQ(2, message.repeated_uint64_size ());
+ ASSERT_EQ(2, message.repeated_sint32_size ());
+ ASSERT_EQ(2, message.repeated_sint64_size ());
+ ASSERT_EQ(2, message.repeated_fixed32_size ());
+ ASSERT_EQ(2, message.repeated_fixed64_size ());
+ ASSERT_EQ(2, message.repeated_sfixed32_size());
+ ASSERT_EQ(2, message.repeated_sfixed64_size());
+ ASSERT_EQ(2, message.repeated_float_size ());
+ ASSERT_EQ(2, message.repeated_double_size ());
+ ASSERT_EQ(2, message.repeated_bool_size ());
+ ASSERT_EQ(2, message.repeated_string_size ());
+ ASSERT_EQ(2, message.repeated_bytes_size ());
+
+ ASSERT_EQ(2, message.repeatedgroup_size ());
+ ASSERT_EQ(2, message.repeated_nested_message_size ());
+ ASSERT_EQ(2, message.repeated_foreign_message_size());
+ ASSERT_EQ(2, message.repeated_import_message_size ());
+ ASSERT_EQ(2, message.repeated_import_message_size ());
+ ASSERT_EQ(2, message.repeated_nested_enum_size ());
+ ASSERT_EQ(2, message.repeated_foreign_enum_size ());
+ ASSERT_EQ(2, message.repeated_import_enum_size ());
+
+#ifndef PROTOBUF_TEST_NO_DESCRIPTORS
+ ASSERT_EQ(2, message.repeated_string_piece_size());
+ ASSERT_EQ(2, message.repeated_cord_size());
+#endif
+
+ // Test that the first element and second element are flipped.
+ EXPECT_EQ(201 , message.repeated_int32 (1));
+ EXPECT_EQ(202 , message.repeated_int64 (1));
+ EXPECT_EQ(203 , message.repeated_uint32 (1));
+ EXPECT_EQ(204 , message.repeated_uint64 (1));
+ EXPECT_EQ(205 , message.repeated_sint32 (1));
+ EXPECT_EQ(206 , message.repeated_sint64 (1));
+ EXPECT_EQ(207 , message.repeated_fixed32 (1));
+ EXPECT_EQ(208 , message.repeated_fixed64 (1));
+ EXPECT_EQ(209 , message.repeated_sfixed32(1));
+ EXPECT_EQ(210 , message.repeated_sfixed64(1));
+ EXPECT_EQ(211 , message.repeated_float (1));
+ EXPECT_EQ(212 , message.repeated_double (1));
+ EXPECT_TRUE( message.repeated_bool (1));
+ EXPECT_EQ("215", message.repeated_string (1));
+ EXPECT_EQ("216", message.repeated_bytes (1));
+
+ EXPECT_EQ(217, message.repeatedgroup (1).a());
+ EXPECT_EQ(218, message.repeated_nested_message (1).bb());
+ EXPECT_EQ(219, message.repeated_foreign_message(1).c());
+ EXPECT_EQ(220, message.repeated_import_message (1).d());
+ EXPECT_EQ(220, message.repeated_import_message (1).d());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.repeated_nested_enum (1));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.repeated_foreign_enum(1));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.repeated_import_enum (1));
+
+ EXPECT_EQ(301 , message.repeated_int32 (0));
+ EXPECT_EQ(302 , message.repeated_int64 (0));
+ EXPECT_EQ(303 , message.repeated_uint32 (0));
+ EXPECT_EQ(304 , message.repeated_uint64 (0));
+ EXPECT_EQ(305 , message.repeated_sint32 (0));
+ EXPECT_EQ(306 , message.repeated_sint64 (0));
+ EXPECT_EQ(307 , message.repeated_fixed32 (0));
+ EXPECT_EQ(308 , message.repeated_fixed64 (0));
+ EXPECT_EQ(309 , message.repeated_sfixed32(0));
+ EXPECT_EQ(310 , message.repeated_sfixed64(0));
+ EXPECT_EQ(311 , message.repeated_float (0));
+ EXPECT_EQ(312 , message.repeated_double (0));
+ EXPECT_FALSE( message.repeated_bool (0));
+ EXPECT_EQ("315", message.repeated_string (0));
+ EXPECT_EQ("316", message.repeated_bytes (0));
+
+ EXPECT_EQ(317, message.repeatedgroup (0).a());
+ EXPECT_EQ(318, message.repeated_nested_message (0).bb());
+ EXPECT_EQ(319, message.repeated_foreign_message(0).c());
+ EXPECT_EQ(320, message.repeated_import_message (0).d());
+ EXPECT_EQ(320, message.repeated_import_message (0).d());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, message.repeated_nested_enum (0));
+ EXPECT_EQ(unittest::FOREIGN_BAZ , message.repeated_foreign_enum(0));
+ EXPECT_EQ(unittest_import::IMPORT_BAZ, message.repeated_import_enum (0));
+}
+
+void TestUtil::ExpectRepeatedExtensionsSwapped(
+ const unittest::TestAllExtensions& message) {
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed32_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed64_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed32_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed64_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_float_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_double_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bool_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bytes_extension ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeatedgroup_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_message_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_lazy_message_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_enum_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_enum_extension ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_enum_extension ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_piece_extension));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_cord_extension));
+
+ EXPECT_EQ(201 , message.GetExtension(unittest::repeated_int32_extension , 1));
+ EXPECT_EQ(202 , message.GetExtension(unittest::repeated_int64_extension , 1));
+ EXPECT_EQ(203 , message.GetExtension(unittest::repeated_uint32_extension , 1));
+ EXPECT_EQ(204 , message.GetExtension(unittest::repeated_uint64_extension , 1));
+ EXPECT_EQ(205 , message.GetExtension(unittest::repeated_sint32_extension , 1));
+ EXPECT_EQ(206 , message.GetExtension(unittest::repeated_sint64_extension , 1));
+ EXPECT_EQ(207 , message.GetExtension(unittest::repeated_fixed32_extension , 1));
+ EXPECT_EQ(208 , message.GetExtension(unittest::repeated_fixed64_extension , 1));
+ EXPECT_EQ(209 , message.GetExtension(unittest::repeated_sfixed32_extension, 1));
+ EXPECT_EQ(210 , message.GetExtension(unittest::repeated_sfixed64_extension, 1));
+ EXPECT_EQ(211 , message.GetExtension(unittest::repeated_float_extension , 1));
+ EXPECT_EQ(212 , message.GetExtension(unittest::repeated_double_extension , 1));
+ EXPECT_TRUE( message.GetExtension(unittest::repeated_bool_extension , 1));
+ EXPECT_EQ("215", message.GetExtension(unittest::repeated_string_extension , 1));
+ EXPECT_EQ("216", message.GetExtension(unittest::repeated_bytes_extension , 1));
+
+ EXPECT_EQ(217, message.GetExtension(unittest::repeatedgroup_extension , 1).a());
+ EXPECT_EQ(218, message.GetExtension(unittest::repeated_nested_message_extension , 1).bb());
+ EXPECT_EQ(219, message.GetExtension(unittest::repeated_foreign_message_extension, 1).c());
+ EXPECT_EQ(220, message.GetExtension(unittest::repeated_import_message_extension , 1).d());
+ EXPECT_EQ(227, message.GetExtension(unittest::repeated_lazy_message_extension , 1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAR, message.GetExtension(unittest::repeated_nested_enum_extension , 1));
+ EXPECT_EQ(unittest::FOREIGN_BAR , message.GetExtension(unittest::repeated_foreign_enum_extension, 1));
+ EXPECT_EQ(unittest_import::IMPORT_BAR, message.GetExtension(unittest::repeated_import_enum_extension , 1));
+
+ EXPECT_EQ("224", message.GetExtension(unittest::repeated_string_piece_extension, 1));
+ EXPECT_EQ("225", message.GetExtension(unittest::repeated_cord_extension, 1));
+
+ EXPECT_EQ(301 , message.GetExtension(unittest::repeated_int32_extension , 0));
+ EXPECT_EQ(302 , message.GetExtension(unittest::repeated_int64_extension , 0));
+ EXPECT_EQ(303 , message.GetExtension(unittest::repeated_uint32_extension , 0));
+ EXPECT_EQ(304 , message.GetExtension(unittest::repeated_uint64_extension , 0));
+ EXPECT_EQ(305 , message.GetExtension(unittest::repeated_sint32_extension , 0));
+ EXPECT_EQ(306 , message.GetExtension(unittest::repeated_sint64_extension , 0));
+ EXPECT_EQ(307 , message.GetExtension(unittest::repeated_fixed32_extension , 0));
+ EXPECT_EQ(308 , message.GetExtension(unittest::repeated_fixed64_extension , 0));
+ EXPECT_EQ(309 , message.GetExtension(unittest::repeated_sfixed32_extension, 0));
+ EXPECT_EQ(310 , message.GetExtension(unittest::repeated_sfixed64_extension, 0));
+ EXPECT_EQ(311 , message.GetExtension(unittest::repeated_float_extension , 0));
+ EXPECT_EQ(312 , message.GetExtension(unittest::repeated_double_extension , 0));
+ EXPECT_FALSE( message.GetExtension(unittest::repeated_bool_extension , 0));
+ EXPECT_EQ("315", message.GetExtension(unittest::repeated_string_extension , 0));
+ EXPECT_EQ("316", message.GetExtension(unittest::repeated_bytes_extension , 0));
+
+ EXPECT_EQ(317, message.GetExtension(unittest::repeatedgroup_extension , 0).a());
+ EXPECT_EQ(318, message.GetExtension(unittest::repeated_nested_message_extension , 0).bb());
+ EXPECT_EQ(319, message.GetExtension(unittest::repeated_foreign_message_extension, 0).c());
+ EXPECT_EQ(320, message.GetExtension(unittest::repeated_import_message_extension , 0).d());
+ EXPECT_EQ(327, message.GetExtension(unittest::repeated_lazy_message_extension , 0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, message.GetExtension(unittest::repeated_nested_enum_extension , 0));
+ EXPECT_EQ(unittest::FOREIGN_BAZ , message.GetExtension(unittest::repeated_foreign_enum_extension, 0));
+ EXPECT_EQ(unittest_import::IMPORT_BAZ, message.GetExtension(unittest::repeated_import_enum_extension , 0));
+
+ EXPECT_EQ("324", message.GetExtension(unittest::repeated_string_piece_extension, 0));
+ EXPECT_EQ("325", message.GetExtension(unittest::repeated_cord_extension, 0));
+}
+
+void TestUtil::SetOneof1(unittest::TestOneof2* message) {
+ message->mutable_foo_lazy_message()->set_qux_int(100);
+ message->set_bar_string("101");
+ message->set_baz_int(102);
+ message->set_baz_string("103");
+}
+
+void TestUtil::SetOneof2(unittest::TestOneof2* message) {
+ message->set_foo_int(200);
+ message->set_bar_enum(unittest::TestOneof2::BAZ);
+ message->set_baz_int(202);
+ message->set_baz_string("203");
+}
+
+void TestUtil::ExpectOneofSet1(const unittest::TestOneof2& message) {
+ ExpectAtMostOneFieldSetInOneof(message);
+
+ EXPECT_TRUE(message.has_foo_lazy_message ());
+ EXPECT_TRUE(message.foo_lazy_message().has_qux_int());
+
+ EXPECT_TRUE(message.has_bar_string());
+ EXPECT_TRUE(message.has_baz_int ());
+ EXPECT_TRUE(message.has_baz_string());
+
+ ASSERT_EQ(0, message.foo_lazy_message().corge_int_size());
+
+ EXPECT_EQ(100 , message.foo_lazy_message().qux_int());
+ EXPECT_EQ("101", message.bar_string ());
+ EXPECT_EQ(102 , message.baz_int ());
+ EXPECT_EQ("103", message.baz_string ());
+}
+
+void TestUtil::ExpectOneofSet2(const unittest::TestOneof2& message) {
+ ExpectAtMostOneFieldSetInOneof(message);
+
+ EXPECT_TRUE(message.has_foo_int ());
+ EXPECT_TRUE(message.has_bar_enum ());
+ EXPECT_TRUE(message.has_baz_int ());
+ EXPECT_TRUE(message.has_baz_string());
+
+ EXPECT_EQ(200 , message.foo_int ());
+ EXPECT_EQ(unittest::TestOneof2::BAZ, message.bar_enum ());
+ EXPECT_EQ(202 , message.baz_int ());
+ EXPECT_EQ("203" , message.baz_string());
+}
+
+void TestUtil::ExpectOneofClear(const unittest::TestOneof2& message) {
+ EXPECT_FALSE(message.has_foo_int());
+ EXPECT_FALSE(message.has_foo_string());
+ EXPECT_FALSE(message.has_foo_bytes());
+ EXPECT_FALSE(message.has_foo_enum());
+ EXPECT_FALSE(message.has_foo_message());
+ EXPECT_FALSE(message.has_foogroup());
+ EXPECT_FALSE(message.has_foo_lazy_message());
+
+ EXPECT_FALSE(message.has_bar_int());
+ EXPECT_FALSE(message.has_bar_string());
+ EXPECT_FALSE(message.has_bar_bytes());
+ EXPECT_FALSE(message.has_bar_enum());
+
+ EXPECT_FALSE(message.has_baz_int());
+ EXPECT_FALSE(message.has_baz_string());
+
+ EXPECT_EQ(unittest::TestOneof2::FOO_NOT_SET, message.foo_case());
+ EXPECT_EQ(unittest::TestOneof2::BAR_NOT_SET, message.bar_case());
+}
+
+void TestUtil::ExpectAtMostOneFieldSetInOneof(
+ const unittest::TestOneof2& message) {
+ int count = 0;
+ if (message.has_foo_int()) count++;
+ if (message.has_foo_string()) count++;
+ if (message.has_foo_bytes()) count++;
+ if (message.has_foo_enum()) count++;
+ if (message.has_foo_message()) count++;
+ if (message.has_foogroup()) count++;
+ if (message.has_foo_lazy_message()) count++;
+ EXPECT_LE(count, 1);
+ count = 0;
+ if (message.has_bar_int()) count++;
+ if (message.has_bar_string()) count++;
+ if (message.has_bar_bytes()) count++;
+ if (message.has_bar_enum()) count++;
+ EXPECT_TRUE(count == 0 || count == 1);
+}
+
+// ===================================================================
+
+TestUtil::ReflectionTester::ReflectionTester(
+ const Descriptor* base_descriptor)
+ : base_descriptor_(base_descriptor) {
+
+ const DescriptorPool* pool = base_descriptor->file()->pool();
+
+ nested_b_ =
+ pool->FindFieldByName("protobuf_unittest.TestAllTypes.NestedMessage.bb");
+ foreign_c_ =
+ pool->FindFieldByName("protobuf_unittest.ForeignMessage.c");
+ import_d_ =
+ pool->FindFieldByName("protobuf_unittest_import.ImportMessage.d");
+ import_e_ =
+ pool->FindFieldByName("protobuf_unittest_import.PublicImportMessage.e");
+ nested_foo_ =
+ pool->FindEnumValueByName("protobuf_unittest.TestAllTypes.FOO");
+ nested_bar_ =
+ pool->FindEnumValueByName("protobuf_unittest.TestAllTypes.BAR");
+ nested_baz_ =
+ pool->FindEnumValueByName("protobuf_unittest.TestAllTypes.BAZ");
+ foreign_foo_ =
+ pool->FindEnumValueByName("protobuf_unittest.FOREIGN_FOO");
+ foreign_bar_ =
+ pool->FindEnumValueByName("protobuf_unittest.FOREIGN_BAR");
+ foreign_baz_ =
+ pool->FindEnumValueByName("protobuf_unittest.FOREIGN_BAZ");
+ import_foo_ =
+ pool->FindEnumValueByName("protobuf_unittest_import.IMPORT_FOO");
+ import_bar_ =
+ pool->FindEnumValueByName("protobuf_unittest_import.IMPORT_BAR");
+ import_baz_ =
+ pool->FindEnumValueByName("protobuf_unittest_import.IMPORT_BAZ");
+
+ if (base_descriptor_->name() == "TestAllExtensions") {
+ group_a_ =
+ pool->FindFieldByName("protobuf_unittest.OptionalGroup_extension.a");
+ repeated_group_a_ =
+ pool->FindFieldByName("protobuf_unittest.RepeatedGroup_extension.a");
+ } else {
+ group_a_ =
+ pool->FindFieldByName("protobuf_unittest.TestAllTypes.OptionalGroup.a");
+ repeated_group_a_ =
+ pool->FindFieldByName("protobuf_unittest.TestAllTypes.RepeatedGroup.a");
+ }
+
+ EXPECT_TRUE(group_a_ != NULL);
+ EXPECT_TRUE(repeated_group_a_ != NULL);
+ EXPECT_TRUE(nested_b_ != NULL);
+ EXPECT_TRUE(foreign_c_ != NULL);
+ EXPECT_TRUE(import_d_ != NULL);
+ EXPECT_TRUE(import_e_ != NULL);
+ EXPECT_TRUE(nested_foo_ != NULL);
+ EXPECT_TRUE(nested_bar_ != NULL);
+ EXPECT_TRUE(nested_baz_ != NULL);
+ EXPECT_TRUE(foreign_foo_ != NULL);
+ EXPECT_TRUE(foreign_bar_ != NULL);
+ EXPECT_TRUE(foreign_baz_ != NULL);
+ EXPECT_TRUE(import_foo_ != NULL);
+ EXPECT_TRUE(import_bar_ != NULL);
+ EXPECT_TRUE(import_baz_ != NULL);
+}
+
+// Shorthand to get a FieldDescriptor for a field of unittest::TestAllTypes.
+const FieldDescriptor* TestUtil::ReflectionTester::F(const string& name) {
+ const FieldDescriptor* result = NULL;
+ if (base_descriptor_->name() == "TestAllExtensions" ||
+ base_descriptor_->name() == "TestPackedExtensions") {
+ result = base_descriptor_->file()->FindExtensionByName(name + "_extension");
+ } else {
+ result = base_descriptor_->FindFieldByName(name);
+ }
+ GOOGLE_CHECK(result != NULL);
+ return result;
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ReflectionTester::SetAllFieldsViaReflection(Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ Message* sub_message;
+
+ reflection->SetInt32 (message, F("optional_int32" ), 101);
+ reflection->SetInt64 (message, F("optional_int64" ), 102);
+ reflection->SetUInt32(message, F("optional_uint32" ), 103);
+ reflection->SetUInt64(message, F("optional_uint64" ), 104);
+ reflection->SetInt32 (message, F("optional_sint32" ), 105);
+ reflection->SetInt64 (message, F("optional_sint64" ), 106);
+ reflection->SetUInt32(message, F("optional_fixed32" ), 107);
+ reflection->SetUInt64(message, F("optional_fixed64" ), 108);
+ reflection->SetInt32 (message, F("optional_sfixed32"), 109);
+ reflection->SetInt64 (message, F("optional_sfixed64"), 110);
+ reflection->SetFloat (message, F("optional_float" ), 111);
+ reflection->SetDouble(message, F("optional_double" ), 112);
+ reflection->SetBool (message, F("optional_bool" ), true);
+ reflection->SetString(message, F("optional_string" ), "115");
+ reflection->SetString(message, F("optional_bytes" ), "116");
+
+ sub_message = reflection->MutableMessage(message, F("optionalgroup"));
+ sub_message->GetReflection()->SetInt32(sub_message, group_a_, 117);
+ sub_message = reflection->MutableMessage(message, F("optional_nested_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 118);
+ sub_message = reflection->MutableMessage(message, F("optional_foreign_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, foreign_c_, 119);
+ sub_message = reflection->MutableMessage(message, F("optional_import_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, import_d_, 120);
+
+ reflection->SetEnum(message, F("optional_nested_enum" ), nested_baz_);
+ reflection->SetEnum(message, F("optional_foreign_enum"), foreign_baz_);
+ reflection->SetEnum(message, F("optional_import_enum" ), import_baz_);
+
+ reflection->SetString(message, F("optional_string_piece"), "124");
+ reflection->SetString(message, F("optional_cord"), "125");
+
+ sub_message = reflection->MutableMessage(message, F("optional_public_import_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, import_e_, 126);
+
+ sub_message = reflection->MutableMessage(message, F("optional_lazy_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 127);
+
+ // -----------------------------------------------------------------
+
+ reflection->AddInt32 (message, F("repeated_int32" ), 201);
+ reflection->AddInt64 (message, F("repeated_int64" ), 202);
+ reflection->AddUInt32(message, F("repeated_uint32" ), 203);
+ reflection->AddUInt64(message, F("repeated_uint64" ), 204);
+ reflection->AddInt32 (message, F("repeated_sint32" ), 205);
+ reflection->AddInt64 (message, F("repeated_sint64" ), 206);
+ reflection->AddUInt32(message, F("repeated_fixed32" ), 207);
+ reflection->AddUInt64(message, F("repeated_fixed64" ), 208);
+ reflection->AddInt32 (message, F("repeated_sfixed32"), 209);
+ reflection->AddInt64 (message, F("repeated_sfixed64"), 210);
+ reflection->AddFloat (message, F("repeated_float" ), 211);
+ reflection->AddDouble(message, F("repeated_double" ), 212);
+ reflection->AddBool (message, F("repeated_bool" ), true);
+ reflection->AddString(message, F("repeated_string" ), "215");
+ reflection->AddString(message, F("repeated_bytes" ), "216");
+
+ sub_message = reflection->AddMessage(message, F("repeatedgroup"));
+ sub_message->GetReflection()->SetInt32(sub_message, repeated_group_a_, 217);
+ sub_message = reflection->AddMessage(message, F("repeated_nested_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 218);
+ sub_message = reflection->AddMessage(message, F("repeated_foreign_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, foreign_c_, 219);
+ sub_message = reflection->AddMessage(message, F("repeated_import_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, import_d_, 220);
+ sub_message = reflection->AddMessage(message, F("repeated_lazy_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 227);
+
+ reflection->AddEnum(message, F("repeated_nested_enum" ), nested_bar_);
+ reflection->AddEnum(message, F("repeated_foreign_enum"), foreign_bar_);
+ reflection->AddEnum(message, F("repeated_import_enum" ), import_bar_);
+
+ reflection->AddString(message, F("repeated_string_piece"), "224");
+ reflection->AddString(message, F("repeated_cord"), "225");
+
+ // Add a second one of each field.
+ reflection->AddInt32 (message, F("repeated_int32" ), 301);
+ reflection->AddInt64 (message, F("repeated_int64" ), 302);
+ reflection->AddUInt32(message, F("repeated_uint32" ), 303);
+ reflection->AddUInt64(message, F("repeated_uint64" ), 304);
+ reflection->AddInt32 (message, F("repeated_sint32" ), 305);
+ reflection->AddInt64 (message, F("repeated_sint64" ), 306);
+ reflection->AddUInt32(message, F("repeated_fixed32" ), 307);
+ reflection->AddUInt64(message, F("repeated_fixed64" ), 308);
+ reflection->AddInt32 (message, F("repeated_sfixed32"), 309);
+ reflection->AddInt64 (message, F("repeated_sfixed64"), 310);
+ reflection->AddFloat (message, F("repeated_float" ), 311);
+ reflection->AddDouble(message, F("repeated_double" ), 312);
+ reflection->AddBool (message, F("repeated_bool" ), false);
+ reflection->AddString(message, F("repeated_string" ), "315");
+ reflection->AddString(message, F("repeated_bytes" ), "316");
+
+ sub_message = reflection->AddMessage(message, F("repeatedgroup"));
+ sub_message->GetReflection()->SetInt32(sub_message, repeated_group_a_, 317);
+ sub_message = reflection->AddMessage(message, F("repeated_nested_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 318);
+ sub_message = reflection->AddMessage(message, F("repeated_foreign_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, foreign_c_, 319);
+ sub_message = reflection->AddMessage(message, F("repeated_import_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, import_d_, 320);
+ sub_message = reflection->AddMessage(message, F("repeated_lazy_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 327);
+
+ reflection->AddEnum(message, F("repeated_nested_enum" ), nested_baz_);
+ reflection->AddEnum(message, F("repeated_foreign_enum"), foreign_baz_);
+ reflection->AddEnum(message, F("repeated_import_enum" ), import_baz_);
+
+ reflection->AddString(message, F("repeated_string_piece"), "324");
+ reflection->AddString(message, F("repeated_cord"), "325");
+
+ // -----------------------------------------------------------------
+
+ reflection->SetInt32 (message, F("default_int32" ), 401);
+ reflection->SetInt64 (message, F("default_int64" ), 402);
+ reflection->SetUInt32(message, F("default_uint32" ), 403);
+ reflection->SetUInt64(message, F("default_uint64" ), 404);
+ reflection->SetInt32 (message, F("default_sint32" ), 405);
+ reflection->SetInt64 (message, F("default_sint64" ), 406);
+ reflection->SetUInt32(message, F("default_fixed32" ), 407);
+ reflection->SetUInt64(message, F("default_fixed64" ), 408);
+ reflection->SetInt32 (message, F("default_sfixed32"), 409);
+ reflection->SetInt64 (message, F("default_sfixed64"), 410);
+ reflection->SetFloat (message, F("default_float" ), 411);
+ reflection->SetDouble(message, F("default_double" ), 412);
+ reflection->SetBool (message, F("default_bool" ), false);
+ reflection->SetString(message, F("default_string" ), "415");
+ reflection->SetString(message, F("default_bytes" ), "416");
+
+ reflection->SetEnum(message, F("default_nested_enum" ), nested_foo_);
+ reflection->SetEnum(message, F("default_foreign_enum"), foreign_foo_);
+ reflection->SetEnum(message, F("default_import_enum" ), import_foo_);
+
+ reflection->SetString(message, F("default_string_piece"), "424");
+ reflection->SetString(message, F("default_cord"), "425");
+
+ reflection->SetUInt32(message, F("oneof_uint32" ), 601);
+ sub_message = reflection->MutableMessage(message, F("oneof_nested_message"));
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 602);
+ reflection->SetString(message, F("oneof_string"), "603");
+ reflection->SetString(message, F("oneof_bytes" ), "604");
+}
+
+void TestUtil::ReflectionTester::SetOneofViaReflection(Message* message) {
+ const Descriptor* descriptor = message->GetDescriptor();
+ const Reflection* reflection = message->GetReflection();
+ Message* sub_message = reflection->MutableMessage(
+ message, descriptor->FindFieldByName("foo_lazy_message"));
+ sub_message->GetReflection()->SetInt64(
+ sub_message,
+ descriptor->file()->pool()->FindFieldByName(
+ "protobuf_unittest.TestOneof2.NestedMessage.qux_int"),
+ 100);
+
+ reflection->SetString(message,
+ descriptor->FindFieldByName("bar_cord"),
+ "101");
+ reflection->SetInt32(message,
+ descriptor->FindFieldByName("baz_int"),
+ 102);
+ reflection->SetString(message,
+ descriptor->FindFieldByName("baz_string"),
+ "103");
+}
+
+void TestUtil::ReflectionTester::ExpectOneofSetViaReflection(
+ const Message& message) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ const Reflection* reflection = message.GetReflection();
+ string scratch;
+ EXPECT_TRUE(reflection->HasField(
+ message, descriptor->FindFieldByName("foo_lazy_message")));
+ EXPECT_TRUE(reflection->HasField(
+ message, descriptor->FindFieldByName("bar_cord")));
+ EXPECT_TRUE(reflection->HasField(
+ message, descriptor->FindFieldByName("baz_int")));
+ EXPECT_TRUE(reflection->HasField(
+ message, descriptor->FindFieldByName("baz_string")));
+
+ const Message* sub_message = &reflection->GetMessage(
+ message, descriptor->FindFieldByName("foo_lazy_message"));
+ EXPECT_EQ(100, sub_message->GetReflection()->GetInt64(
+ *sub_message,
+ descriptor->file()->pool()->FindFieldByName(
+ "protobuf_unittest.TestOneof2.NestedMessage.qux_int")));
+
+ EXPECT_EQ("101", reflection->GetString(
+ message, descriptor->FindFieldByName("bar_cord")));
+ EXPECT_EQ("101", reflection->GetStringReference(
+ message, descriptor->FindFieldByName("bar_cord"), &scratch));
+
+ EXPECT_EQ(102, reflection->GetInt32(
+ message, descriptor->FindFieldByName("baz_int")));
+
+ EXPECT_EQ("103", reflection->GetString(
+ message, descriptor->FindFieldByName("baz_string")));
+ EXPECT_EQ("103", reflection->GetStringReference(
+ message, descriptor->FindFieldByName("baz_string"), &scratch));
+}
+
+void TestUtil::ReflectionTester::SetPackedFieldsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ reflection->AddInt32 (message, F("packed_int32" ), 601);
+ reflection->AddInt64 (message, F("packed_int64" ), 602);
+ reflection->AddUInt32(message, F("packed_uint32" ), 603);
+ reflection->AddUInt64(message, F("packed_uint64" ), 604);
+ reflection->AddInt32 (message, F("packed_sint32" ), 605);
+ reflection->AddInt64 (message, F("packed_sint64" ), 606);
+ reflection->AddUInt32(message, F("packed_fixed32" ), 607);
+ reflection->AddUInt64(message, F("packed_fixed64" ), 608);
+ reflection->AddInt32 (message, F("packed_sfixed32"), 609);
+ reflection->AddInt64 (message, F("packed_sfixed64"), 610);
+ reflection->AddFloat (message, F("packed_float" ), 611);
+ reflection->AddDouble(message, F("packed_double" ), 612);
+ reflection->AddBool (message, F("packed_bool" ), true);
+ reflection->AddEnum (message, F("packed_enum" ), foreign_bar_);
+
+ reflection->AddInt32 (message, F("packed_int32" ), 701);
+ reflection->AddInt64 (message, F("packed_int64" ), 702);
+ reflection->AddUInt32(message, F("packed_uint32" ), 703);
+ reflection->AddUInt64(message, F("packed_uint64" ), 704);
+ reflection->AddInt32 (message, F("packed_sint32" ), 705);
+ reflection->AddInt64 (message, F("packed_sint64" ), 706);
+ reflection->AddUInt32(message, F("packed_fixed32" ), 707);
+ reflection->AddUInt64(message, F("packed_fixed64" ), 708);
+ reflection->AddInt32 (message, F("packed_sfixed32"), 709);
+ reflection->AddInt64 (message, F("packed_sfixed64"), 710);
+ reflection->AddFloat (message, F("packed_float" ), 711);
+ reflection->AddDouble(message, F("packed_double" ), 712);
+ reflection->AddBool (message, F("packed_bool" ), false);
+ reflection->AddEnum (message, F("packed_enum" ), foreign_baz_);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ReflectionTester::ExpectAllFieldsSetViaReflection(
+ const Message& message) {
+ // We have to split this into three function otherwise it creates a stack
+ // frame so large that it triggers a warning.
+ ExpectAllFieldsSetViaReflection1(message);
+ ExpectAllFieldsSetViaReflection2(message);
+ ExpectAllFieldsSetViaReflection3(message);
+}
+
+void TestUtil::ReflectionTester::ExpectAllFieldsSetViaReflection1(
+ const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+ string scratch;
+ const Message* sub_message;
+
+ EXPECT_TRUE(reflection->HasField(message, F("optional_int32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_int64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_uint32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_uint64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_sint32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_sint64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_fixed32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_fixed64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_sfixed32")));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_sfixed64")));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_float" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_double" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_bool" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_string" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_bytes" )));
+
+ EXPECT_TRUE(reflection->HasField(message, F("optionalgroup" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_nested_message" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_foreign_message" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_import_message" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_public_import_message")));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_lazy_message" )));
+
+ sub_message = &reflection->GetMessage(message, F("optionalgroup"));
+ EXPECT_TRUE(sub_message->GetReflection()->HasField(*sub_message, group_a_));
+ sub_message = &reflection->GetMessage(message, F("optional_nested_message"));
+ EXPECT_TRUE(sub_message->GetReflection()->HasField(*sub_message, nested_b_));
+ sub_message = &reflection->GetMessage(message, F("optional_foreign_message"));
+ EXPECT_TRUE(sub_message->GetReflection()->HasField(*sub_message, foreign_c_));
+ sub_message = &reflection->GetMessage(message, F("optional_import_message"));
+ EXPECT_TRUE(sub_message->GetReflection()->HasField(*sub_message, import_d_));
+ sub_message = &reflection->GetMessage(message, F("optional_public_import_message"));
+ EXPECT_TRUE(sub_message->GetReflection()->HasField(*sub_message, import_e_));
+ sub_message = &reflection->GetMessage(message, F("optional_lazy_message"));
+ EXPECT_TRUE(sub_message->GetReflection()->HasField(*sub_message, nested_b_));
+
+ EXPECT_TRUE(reflection->HasField(message, F("optional_nested_enum" )));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_foreign_enum")));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_import_enum" )));
+
+ EXPECT_TRUE(reflection->HasField(message, F("optional_string_piece")));
+ EXPECT_TRUE(reflection->HasField(message, F("optional_cord")));
+
+ EXPECT_EQ(101 , reflection->GetInt32 (message, F("optional_int32" )));
+ EXPECT_EQ(102 , reflection->GetInt64 (message, F("optional_int64" )));
+ EXPECT_EQ(103 , reflection->GetUInt32(message, F("optional_uint32" )));
+ EXPECT_EQ(104 , reflection->GetUInt64(message, F("optional_uint64" )));
+ EXPECT_EQ(105 , reflection->GetInt32 (message, F("optional_sint32" )));
+ EXPECT_EQ(106 , reflection->GetInt64 (message, F("optional_sint64" )));
+ EXPECT_EQ(107 , reflection->GetUInt32(message, F("optional_fixed32" )));
+ EXPECT_EQ(108 , reflection->GetUInt64(message, F("optional_fixed64" )));
+ EXPECT_EQ(109 , reflection->GetInt32 (message, F("optional_sfixed32")));
+ EXPECT_EQ(110 , reflection->GetInt64 (message, F("optional_sfixed64")));
+ EXPECT_EQ(111 , reflection->GetFloat (message, F("optional_float" )));
+ EXPECT_EQ(112 , reflection->GetDouble(message, F("optional_double" )));
+ EXPECT_TRUE( reflection->GetBool (message, F("optional_bool" )));
+ EXPECT_EQ("115", reflection->GetString(message, F("optional_string" )));
+ EXPECT_EQ("116", reflection->GetString(message, F("optional_bytes" )));
+
+ EXPECT_EQ("115", reflection->GetStringReference(message, F("optional_string"), &scratch));
+ EXPECT_EQ("116", reflection->GetStringReference(message, F("optional_bytes" ), &scratch));
+
+ sub_message = &reflection->GetMessage(message, F("optionalgroup"));
+ EXPECT_EQ(117, sub_message->GetReflection()->GetInt32(*sub_message, group_a_));
+ sub_message = &reflection->GetMessage(message, F("optional_nested_message"));
+ EXPECT_EQ(118, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+ sub_message = &reflection->GetMessage(message, F("optional_foreign_message"));
+ EXPECT_EQ(119, sub_message->GetReflection()->GetInt32(*sub_message, foreign_c_));
+ sub_message = &reflection->GetMessage(message, F("optional_import_message"));
+ EXPECT_EQ(120, sub_message->GetReflection()->GetInt32(*sub_message, import_d_));
+ sub_message = &reflection->GetMessage(message, F("optional_public_import_message"));
+ EXPECT_EQ(126, sub_message->GetReflection()->GetInt32(*sub_message, import_e_));
+ sub_message = &reflection->GetMessage(message, F("optional_lazy_message"));
+ EXPECT_EQ(127, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+
+ EXPECT_EQ( nested_baz_, reflection->GetEnum(message, F("optional_nested_enum" )));
+ EXPECT_EQ(foreign_baz_, reflection->GetEnum(message, F("optional_foreign_enum")));
+ EXPECT_EQ( import_baz_, reflection->GetEnum(message, F("optional_import_enum" )));
+
+ EXPECT_EQ("124", reflection->GetString(message, F("optional_string_piece")));
+ EXPECT_EQ("124", reflection->GetStringReference(message, F("optional_string_piece"), &scratch));
+
+ EXPECT_EQ("125", reflection->GetString(message, F("optional_cord")));
+ EXPECT_EQ("125", reflection->GetStringReference(message, F("optional_cord"), &scratch));
+
+ EXPECT_TRUE(reflection->HasField(message, F("oneof_bytes" )));
+ EXPECT_EQ("604", reflection->GetString(message, F("oneof_bytes" )));
+
+ if (base_descriptor_->name() == "TestAllTypes") {
+ EXPECT_FALSE(reflection->HasField(message, F("oneof_uint32")));
+ EXPECT_FALSE(reflection->HasField(message, F("oneof_string")));
+ } else {
+ EXPECT_TRUE(reflection->HasField(message, F("oneof_uint32")));
+ EXPECT_TRUE(reflection->HasField(message, F("oneof_string")));
+ EXPECT_EQ(601 , reflection->GetUInt32(message, F("oneof_uint32")));
+ EXPECT_EQ("603", reflection->GetString(message, F("oneof_string")));
+ sub_message = &reflection->GetMessage(message, F("oneof_nested_message"));
+ EXPECT_EQ(602, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+ }
+}
+
+void TestUtil::ReflectionTester::ExpectAllFieldsSetViaReflection2(
+ const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+ string scratch;
+ const Message* sub_message;
+
+ // -----------------------------------------------------------------
+
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_int32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_int64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_uint32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_uint64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_sint32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_sint64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_fixed32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_fixed64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_sfixed32")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_sfixed64")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_float" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_double" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_bool" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_string" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_bytes" )));
+
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeatedgroup" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_nested_message" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_foreign_message")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_import_message" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_lazy_message" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_nested_enum" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_foreign_enum" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_import_enum" )));
+
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_string_piece")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("repeated_cord")));
+
+ EXPECT_EQ(201 , reflection->GetRepeatedInt32 (message, F("repeated_int32" ), 0));
+ EXPECT_EQ(202 , reflection->GetRepeatedInt64 (message, F("repeated_int64" ), 0));
+ EXPECT_EQ(203 , reflection->GetRepeatedUInt32(message, F("repeated_uint32" ), 0));
+ EXPECT_EQ(204 , reflection->GetRepeatedUInt64(message, F("repeated_uint64" ), 0));
+ EXPECT_EQ(205 , reflection->GetRepeatedInt32 (message, F("repeated_sint32" ), 0));
+ EXPECT_EQ(206 , reflection->GetRepeatedInt64 (message, F("repeated_sint64" ), 0));
+ EXPECT_EQ(207 , reflection->GetRepeatedUInt32(message, F("repeated_fixed32" ), 0));
+ EXPECT_EQ(208 , reflection->GetRepeatedUInt64(message, F("repeated_fixed64" ), 0));
+ EXPECT_EQ(209 , reflection->GetRepeatedInt32 (message, F("repeated_sfixed32"), 0));
+ EXPECT_EQ(210 , reflection->GetRepeatedInt64 (message, F("repeated_sfixed64"), 0));
+ EXPECT_EQ(211 , reflection->GetRepeatedFloat (message, F("repeated_float" ), 0));
+ EXPECT_EQ(212 , reflection->GetRepeatedDouble(message, F("repeated_double" ), 0));
+ EXPECT_TRUE( reflection->GetRepeatedBool (message, F("repeated_bool" ), 0));
+ EXPECT_EQ("215", reflection->GetRepeatedString(message, F("repeated_string" ), 0));
+ EXPECT_EQ("216", reflection->GetRepeatedString(message, F("repeated_bytes" ), 0));
+
+ EXPECT_EQ("215", reflection->GetRepeatedStringReference(message, F("repeated_string"), 0, &scratch));
+ EXPECT_EQ("216", reflection->GetRepeatedStringReference(message, F("repeated_bytes"), 0, &scratch));
+
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeatedgroup"), 0);
+ EXPECT_EQ(217, sub_message->GetReflection()->GetInt32(*sub_message, repeated_group_a_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_nested_message"), 0);
+ EXPECT_EQ(218, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_foreign_message"), 0);
+ EXPECT_EQ(219, sub_message->GetReflection()->GetInt32(*sub_message, foreign_c_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_import_message"), 0);
+ EXPECT_EQ(220, sub_message->GetReflection()->GetInt32(*sub_message, import_d_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_lazy_message"), 0);
+ EXPECT_EQ(227, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+
+ EXPECT_EQ( nested_bar_, reflection->GetRepeatedEnum(message, F("repeated_nested_enum" ),0));
+ EXPECT_EQ(foreign_bar_, reflection->GetRepeatedEnum(message, F("repeated_foreign_enum"),0));
+ EXPECT_EQ( import_bar_, reflection->GetRepeatedEnum(message, F("repeated_import_enum" ),0));
+
+ EXPECT_EQ("224", reflection->GetRepeatedString(message, F("repeated_string_piece"), 0));
+ EXPECT_EQ("224", reflection->GetRepeatedStringReference(
+ message, F("repeated_string_piece"), 0, &scratch));
+
+ EXPECT_EQ("225", reflection->GetRepeatedString(message, F("repeated_cord"), 0));
+ EXPECT_EQ("225", reflection->GetRepeatedStringReference(
+ message, F("repeated_cord"), 0, &scratch));
+
+ EXPECT_EQ(301 , reflection->GetRepeatedInt32 (message, F("repeated_int32" ), 1));
+ EXPECT_EQ(302 , reflection->GetRepeatedInt64 (message, F("repeated_int64" ), 1));
+ EXPECT_EQ(303 , reflection->GetRepeatedUInt32(message, F("repeated_uint32" ), 1));
+ EXPECT_EQ(304 , reflection->GetRepeatedUInt64(message, F("repeated_uint64" ), 1));
+ EXPECT_EQ(305 , reflection->GetRepeatedInt32 (message, F("repeated_sint32" ), 1));
+ EXPECT_EQ(306 , reflection->GetRepeatedInt64 (message, F("repeated_sint64" ), 1));
+ EXPECT_EQ(307 , reflection->GetRepeatedUInt32(message, F("repeated_fixed32" ), 1));
+ EXPECT_EQ(308 , reflection->GetRepeatedUInt64(message, F("repeated_fixed64" ), 1));
+ EXPECT_EQ(309 , reflection->GetRepeatedInt32 (message, F("repeated_sfixed32"), 1));
+ EXPECT_EQ(310 , reflection->GetRepeatedInt64 (message, F("repeated_sfixed64"), 1));
+ EXPECT_EQ(311 , reflection->GetRepeatedFloat (message, F("repeated_float" ), 1));
+ EXPECT_EQ(312 , reflection->GetRepeatedDouble(message, F("repeated_double" ), 1));
+ EXPECT_FALSE( reflection->GetRepeatedBool (message, F("repeated_bool" ), 1));
+ EXPECT_EQ("315", reflection->GetRepeatedString(message, F("repeated_string" ), 1));
+ EXPECT_EQ("316", reflection->GetRepeatedString(message, F("repeated_bytes" ), 1));
+
+ EXPECT_EQ("315", reflection->GetRepeatedStringReference(message, F("repeated_string"),
+ 1, &scratch));
+ EXPECT_EQ("316", reflection->GetRepeatedStringReference(message, F("repeated_bytes"),
+ 1, &scratch));
+
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeatedgroup"), 1);
+ EXPECT_EQ(317, sub_message->GetReflection()->GetInt32(*sub_message, repeated_group_a_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_nested_message"), 1);
+ EXPECT_EQ(318, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_foreign_message"), 1);
+ EXPECT_EQ(319, sub_message->GetReflection()->GetInt32(*sub_message, foreign_c_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_import_message"), 1);
+ EXPECT_EQ(320, sub_message->GetReflection()->GetInt32(*sub_message, import_d_));
+ sub_message = &reflection->GetRepeatedMessage(message, F("repeated_lazy_message"), 1);
+ EXPECT_EQ(327, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+
+ EXPECT_EQ( nested_baz_, reflection->GetRepeatedEnum(message, F("repeated_nested_enum" ),1));
+ EXPECT_EQ(foreign_baz_, reflection->GetRepeatedEnum(message, F("repeated_foreign_enum"),1));
+ EXPECT_EQ( import_baz_, reflection->GetRepeatedEnum(message, F("repeated_import_enum" ),1));
+
+ EXPECT_EQ("324", reflection->GetRepeatedString(message, F("repeated_string_piece"), 1));
+ EXPECT_EQ("324", reflection->GetRepeatedStringReference(
+ message, F("repeated_string_piece"), 1, &scratch));
+
+ EXPECT_EQ("325", reflection->GetRepeatedString(message, F("repeated_cord"), 1));
+ EXPECT_EQ("325", reflection->GetRepeatedStringReference(
+ message, F("repeated_cord"), 1, &scratch));
+}
+
+void TestUtil::ReflectionTester::ExpectAllFieldsSetViaReflection3(
+ const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+ string scratch;
+
+ // -----------------------------------------------------------------
+
+ EXPECT_TRUE(reflection->HasField(message, F("default_int32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_int64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_uint32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_uint64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_sint32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_sint64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_fixed32" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_fixed64" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_sfixed32")));
+ EXPECT_TRUE(reflection->HasField(message, F("default_sfixed64")));
+ EXPECT_TRUE(reflection->HasField(message, F("default_float" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_double" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_bool" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_string" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_bytes" )));
+
+ EXPECT_TRUE(reflection->HasField(message, F("default_nested_enum" )));
+ EXPECT_TRUE(reflection->HasField(message, F("default_foreign_enum")));
+ EXPECT_TRUE(reflection->HasField(message, F("default_import_enum" )));
+
+ EXPECT_TRUE(reflection->HasField(message, F("default_string_piece")));
+ EXPECT_TRUE(reflection->HasField(message, F("default_cord")));
+
+ EXPECT_EQ(401 , reflection->GetInt32 (message, F("default_int32" )));
+ EXPECT_EQ(402 , reflection->GetInt64 (message, F("default_int64" )));
+ EXPECT_EQ(403 , reflection->GetUInt32(message, F("default_uint32" )));
+ EXPECT_EQ(404 , reflection->GetUInt64(message, F("default_uint64" )));
+ EXPECT_EQ(405 , reflection->GetInt32 (message, F("default_sint32" )));
+ EXPECT_EQ(406 , reflection->GetInt64 (message, F("default_sint64" )));
+ EXPECT_EQ(407 , reflection->GetUInt32(message, F("default_fixed32" )));
+ EXPECT_EQ(408 , reflection->GetUInt64(message, F("default_fixed64" )));
+ EXPECT_EQ(409 , reflection->GetInt32 (message, F("default_sfixed32")));
+ EXPECT_EQ(410 , reflection->GetInt64 (message, F("default_sfixed64")));
+ EXPECT_EQ(411 , reflection->GetFloat (message, F("default_float" )));
+ EXPECT_EQ(412 , reflection->GetDouble(message, F("default_double" )));
+ EXPECT_FALSE( reflection->GetBool (message, F("default_bool" )));
+ EXPECT_EQ("415", reflection->GetString(message, F("default_string" )));
+ EXPECT_EQ("416", reflection->GetString(message, F("default_bytes" )));
+
+ EXPECT_EQ("415", reflection->GetStringReference(message, F("default_string"), &scratch));
+ EXPECT_EQ("416", reflection->GetStringReference(message, F("default_bytes" ), &scratch));
+
+ EXPECT_EQ( nested_foo_, reflection->GetEnum(message, F("default_nested_enum" )));
+ EXPECT_EQ(foreign_foo_, reflection->GetEnum(message, F("default_foreign_enum")));
+ EXPECT_EQ( import_foo_, reflection->GetEnum(message, F("default_import_enum" )));
+
+ EXPECT_EQ("424", reflection->GetString(message, F("default_string_piece")));
+ EXPECT_EQ("424", reflection->GetStringReference(message, F("default_string_piece"),
+ &scratch));
+
+ EXPECT_EQ("425", reflection->GetString(message, F("default_cord")));
+ EXPECT_EQ("425", reflection->GetStringReference(message, F("default_cord"), &scratch));
+}
+
+void TestUtil::ReflectionTester::ExpectPackedFieldsSetViaReflection(
+ const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_int32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_int64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_uint32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_uint64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_sint32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_sint64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_fixed32" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_fixed64" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_sfixed32")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_sfixed64")));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_float" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_double" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_bool" )));
+ ASSERT_EQ(2, reflection->FieldSize(message, F("packed_enum" )));
+
+ EXPECT_EQ(601 , reflection->GetRepeatedInt32 (message, F("packed_int32" ), 0));
+ EXPECT_EQ(602 , reflection->GetRepeatedInt64 (message, F("packed_int64" ), 0));
+ EXPECT_EQ(603 , reflection->GetRepeatedUInt32(message, F("packed_uint32" ), 0));
+ EXPECT_EQ(604 , reflection->GetRepeatedUInt64(message, F("packed_uint64" ), 0));
+ EXPECT_EQ(605 , reflection->GetRepeatedInt32 (message, F("packed_sint32" ), 0));
+ EXPECT_EQ(606 , reflection->GetRepeatedInt64 (message, F("packed_sint64" ), 0));
+ EXPECT_EQ(607 , reflection->GetRepeatedUInt32(message, F("packed_fixed32" ), 0));
+ EXPECT_EQ(608 , reflection->GetRepeatedUInt64(message, F("packed_fixed64" ), 0));
+ EXPECT_EQ(609 , reflection->GetRepeatedInt32 (message, F("packed_sfixed32"), 0));
+ EXPECT_EQ(610 , reflection->GetRepeatedInt64 (message, F("packed_sfixed64"), 0));
+ EXPECT_EQ(611 , reflection->GetRepeatedFloat (message, F("packed_float" ), 0));
+ EXPECT_EQ(612 , reflection->GetRepeatedDouble(message, F("packed_double" ), 0));
+ EXPECT_TRUE( reflection->GetRepeatedBool (message, F("packed_bool" ), 0));
+ EXPECT_EQ(foreign_bar_,
+ reflection->GetRepeatedEnum(message, F("packed_enum"), 0));
+
+ EXPECT_EQ(701 , reflection->GetRepeatedInt32 (message, F("packed_int32" ), 1));
+ EXPECT_EQ(702 , reflection->GetRepeatedInt64 (message, F("packed_int64" ), 1));
+ EXPECT_EQ(703 , reflection->GetRepeatedUInt32(message, F("packed_uint32" ), 1));
+ EXPECT_EQ(704 , reflection->GetRepeatedUInt64(message, F("packed_uint64" ), 1));
+ EXPECT_EQ(705 , reflection->GetRepeatedInt32 (message, F("packed_sint32" ), 1));
+ EXPECT_EQ(706 , reflection->GetRepeatedInt64 (message, F("packed_sint64" ), 1));
+ EXPECT_EQ(707 , reflection->GetRepeatedUInt32(message, F("packed_fixed32" ), 1));
+ EXPECT_EQ(708 , reflection->GetRepeatedUInt64(message, F("packed_fixed64" ), 1));
+ EXPECT_EQ(709 , reflection->GetRepeatedInt32 (message, F("packed_sfixed32"), 1));
+ EXPECT_EQ(710 , reflection->GetRepeatedInt64 (message, F("packed_sfixed64"), 1));
+ EXPECT_EQ(711 , reflection->GetRepeatedFloat (message, F("packed_float" ), 1));
+ EXPECT_EQ(712 , reflection->GetRepeatedDouble(message, F("packed_double" ), 1));
+ EXPECT_FALSE( reflection->GetRepeatedBool (message, F("packed_bool" ), 1));
+ EXPECT_EQ(foreign_baz_,
+ reflection->GetRepeatedEnum(message, F("packed_enum"), 1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ReflectionTester::ExpectClearViaReflection(
+ const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+ string scratch;
+ const Message* sub_message;
+
+ // has_blah() should initially be false for all optional fields.
+ EXPECT_FALSE(reflection->HasField(message, F("optional_int32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_int64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_uint32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_uint64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_sint32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_sint64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_fixed32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_fixed64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_sfixed32")));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_sfixed64")));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_float" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_double" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_bool" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_string" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_bytes" )));
+
+ EXPECT_FALSE(reflection->HasField(message, F("optionalgroup" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_nested_message" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_foreign_message")));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_import_message" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_public_import_message")));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_lazy_message")));
+
+ EXPECT_FALSE(reflection->HasField(message, F("optional_nested_enum" )));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_foreign_enum")));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_import_enum" )));
+
+ EXPECT_FALSE(reflection->HasField(message, F("optional_string_piece")));
+ EXPECT_FALSE(reflection->HasField(message, F("optional_cord")));
+
+ // Optional fields without defaults are set to zero or something like it.
+ EXPECT_EQ(0 , reflection->GetInt32 (message, F("optional_int32" )));
+ EXPECT_EQ(0 , reflection->GetInt64 (message, F("optional_int64" )));
+ EXPECT_EQ(0 , reflection->GetUInt32(message, F("optional_uint32" )));
+ EXPECT_EQ(0 , reflection->GetUInt64(message, F("optional_uint64" )));
+ EXPECT_EQ(0 , reflection->GetInt32 (message, F("optional_sint32" )));
+ EXPECT_EQ(0 , reflection->GetInt64 (message, F("optional_sint64" )));
+ EXPECT_EQ(0 , reflection->GetUInt32(message, F("optional_fixed32" )));
+ EXPECT_EQ(0 , reflection->GetUInt64(message, F("optional_fixed64" )));
+ EXPECT_EQ(0 , reflection->GetInt32 (message, F("optional_sfixed32")));
+ EXPECT_EQ(0 , reflection->GetInt64 (message, F("optional_sfixed64")));
+ EXPECT_EQ(0 , reflection->GetFloat (message, F("optional_float" )));
+ EXPECT_EQ(0 , reflection->GetDouble(message, F("optional_double" )));
+ EXPECT_FALSE( reflection->GetBool (message, F("optional_bool" )));
+ EXPECT_EQ("" , reflection->GetString(message, F("optional_string" )));
+ EXPECT_EQ("" , reflection->GetString(message, F("optional_bytes" )));
+
+ EXPECT_EQ("", reflection->GetStringReference(message, F("optional_string"), &scratch));
+ EXPECT_EQ("", reflection->GetStringReference(message, F("optional_bytes" ), &scratch));
+
+ // Embedded messages should also be clear.
+ sub_message = &reflection->GetMessage(message, F("optionalgroup"));
+ EXPECT_FALSE(sub_message->GetReflection()->HasField(*sub_message, group_a_));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message, group_a_));
+ sub_message = &reflection->GetMessage(message, F("optional_nested_message"));
+ EXPECT_FALSE(sub_message->GetReflection()->HasField(*sub_message, nested_b_));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+ sub_message = &reflection->GetMessage(message, F("optional_foreign_message"));
+ EXPECT_FALSE(sub_message->GetReflection()->HasField(*sub_message, foreign_c_));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message, foreign_c_));
+ sub_message = &reflection->GetMessage(message, F("optional_import_message"));
+ EXPECT_FALSE(sub_message->GetReflection()->HasField(*sub_message, import_d_));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message, import_d_));
+ sub_message = &reflection->GetMessage(message, F("optional_public_import_message"));
+ EXPECT_FALSE(sub_message->GetReflection()->HasField(*sub_message, import_e_));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message, import_e_));
+ sub_message = &reflection->GetMessage(message, F("optional_lazy_message"));
+ EXPECT_FALSE(sub_message->GetReflection()->HasField(*sub_message, nested_b_));
+ EXPECT_EQ(0, sub_message->GetReflection()->GetInt32(*sub_message, nested_b_));
+
+ // Enums without defaults are set to the first value in the enum.
+ EXPECT_EQ( nested_foo_, reflection->GetEnum(message, F("optional_nested_enum" )));
+ EXPECT_EQ(foreign_foo_, reflection->GetEnum(message, F("optional_foreign_enum")));
+ EXPECT_EQ( import_foo_, reflection->GetEnum(message, F("optional_import_enum" )));
+
+ EXPECT_EQ("", reflection->GetString(message, F("optional_string_piece")));
+ EXPECT_EQ("", reflection->GetStringReference(message, F("optional_string_piece"), &scratch));
+
+ EXPECT_EQ("", reflection->GetString(message, F("optional_cord")));
+ EXPECT_EQ("", reflection->GetStringReference(message, F("optional_cord"), &scratch));
+
+ // Repeated fields are empty.
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_int32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_int64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_uint32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_uint64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_sint32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_sint64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_fixed32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_fixed64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_sfixed32")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_sfixed64")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_float" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_double" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_bool" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_string" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_bytes" )));
+
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeatedgroup" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_nested_message" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_foreign_message")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_import_message" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_lazy_message" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_nested_enum" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_foreign_enum" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_import_enum" )));
+
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_string_piece")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("repeated_cord")));
+
+ // has_blah() should also be false for all default fields.
+ EXPECT_FALSE(reflection->HasField(message, F("default_int32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_int64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_uint32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_uint64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_sint32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_sint64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_fixed32" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_fixed64" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_sfixed32")));
+ EXPECT_FALSE(reflection->HasField(message, F("default_sfixed64")));
+ EXPECT_FALSE(reflection->HasField(message, F("default_float" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_double" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_bool" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_string" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_bytes" )));
+
+ EXPECT_FALSE(reflection->HasField(message, F("default_nested_enum" )));
+ EXPECT_FALSE(reflection->HasField(message, F("default_foreign_enum")));
+ EXPECT_FALSE(reflection->HasField(message, F("default_import_enum" )));
+
+ EXPECT_FALSE(reflection->HasField(message, F("default_string_piece")));
+ EXPECT_FALSE(reflection->HasField(message, F("default_cord")));
+
+ // Fields with defaults have their default values (duh).
+ EXPECT_EQ( 41 , reflection->GetInt32 (message, F("default_int32" )));
+ EXPECT_EQ( 42 , reflection->GetInt64 (message, F("default_int64" )));
+ EXPECT_EQ( 43 , reflection->GetUInt32(message, F("default_uint32" )));
+ EXPECT_EQ( 44 , reflection->GetUInt64(message, F("default_uint64" )));
+ EXPECT_EQ(-45 , reflection->GetInt32 (message, F("default_sint32" )));
+ EXPECT_EQ( 46 , reflection->GetInt64 (message, F("default_sint64" )));
+ EXPECT_EQ( 47 , reflection->GetUInt32(message, F("default_fixed32" )));
+ EXPECT_EQ( 48 , reflection->GetUInt64(message, F("default_fixed64" )));
+ EXPECT_EQ( 49 , reflection->GetInt32 (message, F("default_sfixed32")));
+ EXPECT_EQ(-50 , reflection->GetInt64 (message, F("default_sfixed64")));
+ EXPECT_EQ( 51.5 , reflection->GetFloat (message, F("default_float" )));
+ EXPECT_EQ( 52e3 , reflection->GetDouble(message, F("default_double" )));
+ EXPECT_TRUE( reflection->GetBool (message, F("default_bool" )));
+ EXPECT_EQ("hello", reflection->GetString(message, F("default_string" )));
+ EXPECT_EQ("world", reflection->GetString(message, F("default_bytes" )));
+
+ EXPECT_EQ("hello", reflection->GetStringReference(message, F("default_string"), &scratch));
+ EXPECT_EQ("world", reflection->GetStringReference(message, F("default_bytes" ), &scratch));
+
+ EXPECT_EQ( nested_bar_, reflection->GetEnum(message, F("default_nested_enum" )));
+ EXPECT_EQ(foreign_bar_, reflection->GetEnum(message, F("default_foreign_enum")));
+ EXPECT_EQ( import_bar_, reflection->GetEnum(message, F("default_import_enum" )));
+
+ EXPECT_EQ("abc", reflection->GetString(message, F("default_string_piece")));
+ EXPECT_EQ("abc", reflection->GetStringReference(message, F("default_string_piece"), &scratch));
+
+ EXPECT_EQ("123", reflection->GetString(message, F("default_cord")));
+ EXPECT_EQ("123", reflection->GetStringReference(message, F("default_cord"), &scratch));
+}
+
+void TestUtil::ReflectionTester::ExpectPackedClearViaReflection(
+ const Message& message) {
+ const Reflection* reflection = message.GetReflection();
+
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_int32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_int64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_uint32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_uint64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_sint32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_sint64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_fixed32" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_fixed64" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_sfixed32")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_sfixed64")));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_float" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_double" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_bool" )));
+ EXPECT_EQ(0, reflection->FieldSize(message, F("packed_enum" )));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtil::ReflectionTester::ModifyRepeatedFieldsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ Message* sub_message;
+
+ reflection->SetRepeatedInt32 (message, F("repeated_int32" ), 1, 501);
+ reflection->SetRepeatedInt64 (message, F("repeated_int64" ), 1, 502);
+ reflection->SetRepeatedUInt32(message, F("repeated_uint32" ), 1, 503);
+ reflection->SetRepeatedUInt64(message, F("repeated_uint64" ), 1, 504);
+ reflection->SetRepeatedInt32 (message, F("repeated_sint32" ), 1, 505);
+ reflection->SetRepeatedInt64 (message, F("repeated_sint64" ), 1, 506);
+ reflection->SetRepeatedUInt32(message, F("repeated_fixed32" ), 1, 507);
+ reflection->SetRepeatedUInt64(message, F("repeated_fixed64" ), 1, 508);
+ reflection->SetRepeatedInt32 (message, F("repeated_sfixed32"), 1, 509);
+ reflection->SetRepeatedInt64 (message, F("repeated_sfixed64"), 1, 510);
+ reflection->SetRepeatedFloat (message, F("repeated_float" ), 1, 511);
+ reflection->SetRepeatedDouble(message, F("repeated_double" ), 1, 512);
+ reflection->SetRepeatedBool (message, F("repeated_bool" ), 1, true);
+ reflection->SetRepeatedString(message, F("repeated_string" ), 1, "515");
+ reflection->SetRepeatedString(message, F("repeated_bytes" ), 1, "516");
+
+ sub_message = reflection->MutableRepeatedMessage(message, F("repeatedgroup"), 1);
+ sub_message->GetReflection()->SetInt32(sub_message, repeated_group_a_, 517);
+ sub_message = reflection->MutableRepeatedMessage(message, F("repeated_nested_message"), 1);
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 518);
+ sub_message = reflection->MutableRepeatedMessage(message, F("repeated_foreign_message"), 1);
+ sub_message->GetReflection()->SetInt32(sub_message, foreign_c_, 519);
+ sub_message = reflection->MutableRepeatedMessage(message, F("repeated_import_message"), 1);
+ sub_message->GetReflection()->SetInt32(sub_message, import_d_, 520);
+ sub_message = reflection->MutableRepeatedMessage(message, F("repeated_lazy_message"), 1);
+ sub_message->GetReflection()->SetInt32(sub_message, nested_b_, 527);
+
+ reflection->SetRepeatedEnum(message, F("repeated_nested_enum" ), 1, nested_foo_);
+ reflection->SetRepeatedEnum(message, F("repeated_foreign_enum"), 1, foreign_foo_);
+ reflection->SetRepeatedEnum(message, F("repeated_import_enum" ), 1, import_foo_);
+
+ reflection->SetRepeatedString(message, F("repeated_string_piece"), 1, "524");
+ reflection->SetRepeatedString(message, F("repeated_cord"), 1, "525");
+}
+
+void TestUtil::ReflectionTester::ModifyPackedFieldsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ reflection->SetRepeatedInt32 (message, F("packed_int32" ), 1, 801);
+ reflection->SetRepeatedInt64 (message, F("packed_int64" ), 1, 802);
+ reflection->SetRepeatedUInt32(message, F("packed_uint32" ), 1, 803);
+ reflection->SetRepeatedUInt64(message, F("packed_uint64" ), 1, 804);
+ reflection->SetRepeatedInt32 (message, F("packed_sint32" ), 1, 805);
+ reflection->SetRepeatedInt64 (message, F("packed_sint64" ), 1, 806);
+ reflection->SetRepeatedUInt32(message, F("packed_fixed32" ), 1, 807);
+ reflection->SetRepeatedUInt64(message, F("packed_fixed64" ), 1, 808);
+ reflection->SetRepeatedInt32 (message, F("packed_sfixed32"), 1, 809);
+ reflection->SetRepeatedInt64 (message, F("packed_sfixed64"), 1, 810);
+ reflection->SetRepeatedFloat (message, F("packed_float" ), 1, 811);
+ reflection->SetRepeatedDouble(message, F("packed_double" ), 1, 812);
+ reflection->SetRepeatedBool (message, F("packed_bool" ), 1, true);
+ reflection->SetRepeatedEnum (message, F("packed_enum" ), 1, foreign_foo_);
+}
+
+void TestUtil::ReflectionTester::RemoveLastRepeatedsViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ vector<const FieldDescriptor*> output;
+ reflection->ListFields(*message, &output);
+ for (int i=0; i<output.size(); ++i) {
+ const FieldDescriptor* field = output[i];
+ if (!field->is_repeated()) continue;
+
+ reflection->RemoveLast(message, field);
+ }
+}
+
+void TestUtil::ReflectionTester::ReleaseLastRepeatedsViaReflection(
+ Message* message, bool expect_extensions_notnull) {
+ const Reflection* reflection = message->GetReflection();
+
+ vector<const FieldDescriptor*> output;
+ reflection->ListFields(*message, &output);
+ for (int i=0; i<output.size(); ++i) {
+ const FieldDescriptor* field = output[i];
+ if (!field->is_repeated()) continue;
+ if (field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) continue;
+
+ Message* released = reflection->ReleaseLast(message, field);
+ if (!field->is_extension() || expect_extensions_notnull) {
+ ASSERT_TRUE(released != NULL) << "ReleaseLast returned NULL for: "
+ << field->name();
+ }
+ delete released;
+ }
+}
+
+void TestUtil::ReflectionTester::SwapRepeatedsViaReflection(Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ vector<const FieldDescriptor*> output;
+ reflection->ListFields(*message, &output);
+ for (int i=0; i<output.size(); ++i) {
+ const FieldDescriptor* field = output[i];
+ if (!field->is_repeated()) continue;
+
+ reflection->SwapElements(message, field, 0, 1);
+ }
+}
+
+void TestUtil::ReflectionTester::
+SetAllocatedOptionalMessageFieldsToNullViaReflection(
+ Message* message) {
+ const Reflection* reflection = message->GetReflection();
+
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(*message, &fields);
+
+ for (int i = 0; i < fields.size(); ++i) {
+ const FieldDescriptor* field = fields[i];
+ if (!field->is_optional() ||
+ field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) continue;
+
+ reflection->SetAllocatedMessage(message, NULL, field);
+ }
+}
+
+void TestUtil::ReflectionTester::
+SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ Message* from_message,
+ Message* to_message) {
+ EXPECT_EQ(from_message->GetDescriptor(), to_message->GetDescriptor());
+ const Reflection* from_reflection = from_message->GetReflection();
+ const Reflection* to_reflection = to_message->GetReflection();
+
+ vector<const FieldDescriptor*> fields;
+ from_reflection->ListFields(*from_message, &fields);
+
+ for (int i = 0; i < fields.size(); ++i) {
+ const FieldDescriptor* field = fields[i];
+ if (!field->is_optional() ||
+ field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) continue;
+
+ Message* sub_message =
+ from_reflection->ReleaseMessage(from_message, field);
+ to_reflection->SetAllocatedMessage(to_message, sub_message, field);
+ }
+}
+
+void TestUtil::ReflectionTester::ExpectMessagesReleasedViaReflection(
+ Message* message,
+ TestUtil::ReflectionTester::MessageReleaseState expected_release_state) {
+ const Reflection* reflection = message->GetReflection();
+
+ static const char* fields[] = {
+ "optionalgroup",
+ "optional_nested_message",
+ "optional_foreign_message",
+ "optional_import_message",
+ };
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(fields); i++) {
+ const Message& sub_message = reflection->GetMessage(*message, F(fields[i]));
+ Message* released = reflection->ReleaseMessage(message, F(fields[i]));
+ switch (expected_release_state) {
+ case IS_NULL:
+ EXPECT_TRUE(released == NULL);
+ break;
+ case NOT_NULL:
+ EXPECT_TRUE(released != NULL);
+ if (message->GetArena() == NULL) {
+ // released message must be same as sub_message if source message is
+ // not on arena.
+ EXPECT_EQ(&sub_message, released);
+ }
+ break;
+ case CAN_BE_NULL:
+ break;
+ }
+ delete released;
+ EXPECT_FALSE(reflection->HasField(*message, F(fields[i])));
+ }
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/test_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/test_util.h
new file mode 100644
index 0000000000..1c13a1a7f6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/test_util.h
@@ -0,0 +1,215 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_TEST_UTIL_H__
+#define GOOGLE_PROTOBUF_TEST_UTIL_H__
+
+#include <stack>
+#include <string>
+#include <google/protobuf/message.h>
+#include <google/protobuf/unittest.pb.h>
+
+namespace google {
+namespace protobuf {
+
+namespace unittest = ::protobuf_unittest;
+namespace unittest_import = protobuf_unittest_import;
+
+class TestUtil {
+ public:
+ // Set every field in the message to a unique value.
+ static void SetAllFields(unittest::TestAllTypes* message);
+ static void SetOptionalFields(unittest::TestAllTypes* message);
+ static void AddRepeatedFields1(unittest::TestAllTypes* message);
+ static void AddRepeatedFields2(unittest::TestAllTypes* message);
+ static void SetDefaultFields(unittest::TestAllTypes* message);
+ static void SetOneofFields(unittest::TestAllTypes* message);
+ static void SetAllExtensions(unittest::TestAllExtensions* message);
+ static void SetOneofFields(unittest::TestAllExtensions* message);
+ static void SetAllFieldsAndExtensions(unittest::TestFieldOrderings* message);
+ static void SetPackedFields(unittest::TestPackedTypes* message);
+ static void SetPackedExtensions(unittest::TestPackedExtensions* message);
+ static void SetUnpackedFields(unittest::TestUnpackedTypes* message);
+ static void SetOneof1(unittest::TestOneof2* message);
+ static void SetOneof2(unittest::TestOneof2* message);
+
+ // Use the repeated versions of the set_*() accessors to modify all the
+ // repeated fields of the message (which should already have been
+ // initialized with Set*Fields()). Set*Fields() itself only tests
+ // the add_*() accessors.
+ static void ModifyRepeatedFields(unittest::TestAllTypes* message);
+ static void ModifyRepeatedExtensions(unittest::TestAllExtensions* message);
+ static void ModifyPackedFields(unittest::TestPackedTypes* message);
+ static void ModifyPackedExtensions(unittest::TestPackedExtensions* message);
+
+ // Check that all fields have the values that they should have after
+ // Set*Fields() is called.
+ static void ExpectAllFieldsSet(const unittest::TestAllTypes& message);
+ static void ExpectAllExtensionsSet(
+ const unittest::TestAllExtensions& message);
+ static void ExpectPackedFieldsSet(const unittest::TestPackedTypes& message);
+ static void ExpectPackedExtensionsSet(
+ const unittest::TestPackedExtensions& message);
+ static void ExpectUnpackedFieldsSet(
+ const unittest::TestUnpackedTypes& message);
+ static void ExpectUnpackedExtensionsSet(
+ const unittest::TestUnpackedExtensions& message);
+ static void ExpectOneofSet1(const unittest::TestOneof2& message);
+ static void ExpectOneofSet2(const unittest::TestOneof2& message);
+
+ // Expect that the message is modified as would be expected from
+ // Modify*Fields().
+ static void ExpectRepeatedFieldsModified(
+ const unittest::TestAllTypes& message);
+ static void ExpectRepeatedExtensionsModified(
+ const unittest::TestAllExtensions& message);
+ static void ExpectPackedFieldsModified(
+ const unittest::TestPackedTypes& message);
+ static void ExpectPackedExtensionsModified(
+ const unittest::TestPackedExtensions& message);
+
+ // Check that all fields have their default values.
+ static void ExpectClear(const unittest::TestAllTypes& message);
+ static void ExpectExtensionsClear(const unittest::TestAllExtensions& message);
+ static void ExpectPackedClear(const unittest::TestPackedTypes& message);
+ static void ExpectPackedExtensionsClear(
+ const unittest::TestPackedExtensions& message);
+ static void ExpectOneofClear(const unittest::TestOneof2& message);
+
+ // Check that the passed-in serialization is the canonical serialization we
+ // expect for a TestFieldOrderings message filled in by
+ // SetAllFieldsAndExtensions().
+ static void ExpectAllFieldsAndExtensionsInOrder(const string& serialized);
+
+ // Check that all repeated fields have had their last elements removed.
+ static void ExpectLastRepeatedsRemoved(
+ const unittest::TestAllTypes& message);
+ static void ExpectLastRepeatedExtensionsRemoved(
+ const unittest::TestAllExtensions& message);
+ static void ExpectLastRepeatedsReleased(
+ const unittest::TestAllTypes& message);
+ static void ExpectLastRepeatedExtensionsReleased(
+ const unittest::TestAllExtensions& message);
+
+ // Check that all repeated fields have had their first and last elements
+ // swapped.
+ static void ExpectRepeatedsSwapped(const unittest::TestAllTypes& message);
+ static void ExpectRepeatedExtensionsSwapped(
+ const unittest::TestAllExtensions& message);
+
+ static void ExpectAtMostOneFieldSetInOneof(
+ const unittest::TestOneof2 &message);
+
+ // Like above, but use the reflection interface.
+ class ReflectionTester {
+ public:
+ // base_descriptor must be a descriptor for TestAllTypes or
+ // TestAllExtensions. In the former case, ReflectionTester fetches from
+ // it the FieldDescriptors needed to use the reflection interface. In
+ // the latter case, ReflectionTester searches for extension fields in
+ // its file.
+ explicit ReflectionTester(const Descriptor* base_descriptor);
+
+ void SetAllFieldsViaReflection(Message* message);
+ void ModifyRepeatedFieldsViaReflection(Message* message);
+ void ExpectAllFieldsSetViaReflection(const Message& message);
+ void ExpectClearViaReflection(const Message& message);
+
+ void SetPackedFieldsViaReflection(Message* message);
+ void ModifyPackedFieldsViaReflection(Message* message);
+ void ExpectPackedFieldsSetViaReflection(const Message& message);
+ void ExpectPackedClearViaReflection(const Message& message);
+
+ void RemoveLastRepeatedsViaReflection(Message* message);
+ void ReleaseLastRepeatedsViaReflection(
+ Message* message, bool expect_extensions_notnull);
+ void SwapRepeatedsViaReflection(Message* message);
+ void SetAllocatedOptionalMessageFieldsToNullViaReflection(
+ Message* message);
+ static void SetAllocatedOptionalMessageFieldsToMessageViaReflection(
+ Message* from_message,
+ Message* to_message);
+
+ enum MessageReleaseState {
+ IS_NULL,
+ CAN_BE_NULL,
+ NOT_NULL,
+ };
+ void ExpectMessagesReleasedViaReflection(
+ Message* message, MessageReleaseState expected_release_state);
+
+ // Set and check functions for TestOneof2 messages. No need to construct
+ // the ReflectionTester by TestAllTypes nor TestAllExtensions.
+ static void SetOneofViaReflection(Message* message);
+ static void ExpectOneofSetViaReflection(const Message& message);
+
+ private:
+ const FieldDescriptor* F(const string& name);
+
+ const Descriptor* base_descriptor_;
+
+ const FieldDescriptor* group_a_;
+ const FieldDescriptor* repeated_group_a_;
+ const FieldDescriptor* nested_b_;
+ const FieldDescriptor* foreign_c_;
+ const FieldDescriptor* import_d_;
+ const FieldDescriptor* import_e_;
+
+ const EnumValueDescriptor* nested_foo_;
+ const EnumValueDescriptor* nested_bar_;
+ const EnumValueDescriptor* nested_baz_;
+ const EnumValueDescriptor* foreign_foo_;
+ const EnumValueDescriptor* foreign_bar_;
+ const EnumValueDescriptor* foreign_baz_;
+ const EnumValueDescriptor* import_foo_;
+ const EnumValueDescriptor* import_bar_;
+ const EnumValueDescriptor* import_baz_;
+
+ // We have to split this into three function otherwise it creates a stack
+ // frame so large that it triggers a warning.
+ void ExpectAllFieldsSetViaReflection1(const Message& message);
+ void ExpectAllFieldsSetViaReflection2(const Message& message);
+ void ExpectAllFieldsSetViaReflection3(const Message& message);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ReflectionTester);
+ };
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TestUtil);
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_TEST_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.cc
new file mode 100644
index 0000000000..388c0cbde2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.cc
@@ -0,0 +1,1586 @@
+// 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.
+
+#include <google/protobuf/test_util_lite.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+
+
+#define EXPECT_TRUE GOOGLE_CHECK
+#define ASSERT_TRUE GOOGLE_CHECK
+#define EXPECT_FALSE(COND) GOOGLE_CHECK(!(COND))
+#define EXPECT_EQ GOOGLE_CHECK_EQ
+#define ASSERT_EQ GOOGLE_CHECK_EQ
+
+namespace google {
+namespace protobuf {
+
+void TestUtilLite::SetAllFields(unittest::TestAllTypesLite* message) {
+ message->set_optional_int32 (101);
+ message->set_optional_int64 (102);
+ message->set_optional_uint32 (103);
+ message->set_optional_uint64 (104);
+ message->set_optional_sint32 (105);
+ message->set_optional_sint64 (106);
+ message->set_optional_fixed32 (107);
+ message->set_optional_fixed64 (108);
+ message->set_optional_sfixed32(109);
+ message->set_optional_sfixed64(110);
+ message->set_optional_float (111);
+ message->set_optional_double (112);
+ message->set_optional_bool (true);
+ message->set_optional_string ("115");
+ message->set_optional_bytes ("116");
+
+ message->mutable_optionalgroup ()->set_a(117);
+ message->mutable_optional_nested_message ()->set_bb(118);
+ message->mutable_optional_foreign_message ()->set_c(119);
+ message->mutable_optional_import_message ()->set_d(120);
+ message->mutable_optional_public_import_message()->set_e(126);
+ message->mutable_optional_lazy_message ()->set_bb(127);
+
+ message->set_optional_nested_enum (unittest::TestAllTypesLite::BAZ );
+ message->set_optional_foreign_enum(unittest::FOREIGN_LITE_BAZ );
+ message->set_optional_import_enum (unittest_import::IMPORT_LITE_BAZ);
+
+
+ // -----------------------------------------------------------------
+
+ message->add_repeated_int32 (201);
+ message->add_repeated_int64 (202);
+ message->add_repeated_uint32 (203);
+ message->add_repeated_uint64 (204);
+ message->add_repeated_sint32 (205);
+ message->add_repeated_sint64 (206);
+ message->add_repeated_fixed32 (207);
+ message->add_repeated_fixed64 (208);
+ message->add_repeated_sfixed32(209);
+ message->add_repeated_sfixed64(210);
+ message->add_repeated_float (211);
+ message->add_repeated_double (212);
+ message->add_repeated_bool (true);
+ message->add_repeated_string ("215");
+ message->add_repeated_bytes ("216");
+
+ message->add_repeatedgroup ()->set_a(217);
+ message->add_repeated_nested_message ()->set_bb(218);
+ message->add_repeated_foreign_message()->set_c(219);
+ message->add_repeated_import_message ()->set_d(220);
+ message->add_repeated_lazy_message ()->set_bb(227);
+
+ message->add_repeated_nested_enum (unittest::TestAllTypesLite::BAR );
+ message->add_repeated_foreign_enum(unittest::FOREIGN_LITE_BAR );
+ message->add_repeated_import_enum (unittest_import::IMPORT_LITE_BAR);
+
+
+ // Add a second one of each field.
+ message->add_repeated_int32 (301);
+ message->add_repeated_int64 (302);
+ message->add_repeated_uint32 (303);
+ message->add_repeated_uint64 (304);
+ message->add_repeated_sint32 (305);
+ message->add_repeated_sint64 (306);
+ message->add_repeated_fixed32 (307);
+ message->add_repeated_fixed64 (308);
+ message->add_repeated_sfixed32(309);
+ message->add_repeated_sfixed64(310);
+ message->add_repeated_float (311);
+ message->add_repeated_double (312);
+ message->add_repeated_bool (false);
+ message->add_repeated_string ("315");
+ message->add_repeated_bytes ("316");
+
+ message->add_repeatedgroup ()->set_a(317);
+ message->add_repeated_nested_message ()->set_bb(318);
+ message->add_repeated_foreign_message()->set_c(319);
+ message->add_repeated_import_message ()->set_d(320);
+ message->add_repeated_lazy_message ()->set_bb(327);
+
+ message->add_repeated_nested_enum (unittest::TestAllTypesLite::BAZ );
+ message->add_repeated_foreign_enum(unittest::FOREIGN_LITE_BAZ );
+ message->add_repeated_import_enum (unittest_import::IMPORT_LITE_BAZ);
+
+
+ // -----------------------------------------------------------------
+
+ message->set_default_int32 (401);
+ message->set_default_int64 (402);
+ message->set_default_uint32 (403);
+ message->set_default_uint64 (404);
+ message->set_default_sint32 (405);
+ message->set_default_sint64 (406);
+ message->set_default_fixed32 (407);
+ message->set_default_fixed64 (408);
+ message->set_default_sfixed32(409);
+ message->set_default_sfixed64(410);
+ message->set_default_float (411);
+ message->set_default_double (412);
+ message->set_default_bool (false);
+ message->set_default_string ("415");
+ message->set_default_bytes ("416");
+
+ message->set_default_nested_enum (unittest::TestAllTypesLite::FOO );
+ message->set_default_foreign_enum(unittest::FOREIGN_LITE_FOO );
+ message->set_default_import_enum (unittest_import::IMPORT_LITE_FOO);
+
+
+ message->set_oneof_uint32(601);
+ message->mutable_oneof_nested_message()->set_bb(602);
+ message->set_oneof_string("603");
+ message->set_oneof_bytes("604");
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ModifyRepeatedFields(unittest::TestAllTypesLite* message) {
+ message->set_repeated_int32 (1, 501);
+ message->set_repeated_int64 (1, 502);
+ message->set_repeated_uint32 (1, 503);
+ message->set_repeated_uint64 (1, 504);
+ message->set_repeated_sint32 (1, 505);
+ message->set_repeated_sint64 (1, 506);
+ message->set_repeated_fixed32 (1, 507);
+ message->set_repeated_fixed64 (1, 508);
+ message->set_repeated_sfixed32(1, 509);
+ message->set_repeated_sfixed64(1, 510);
+ message->set_repeated_float (1, 511);
+ message->set_repeated_double (1, 512);
+ message->set_repeated_bool (1, true);
+ message->set_repeated_string (1, "515");
+ message->set_repeated_bytes (1, "516");
+
+ message->mutable_repeatedgroup (1)->set_a(517);
+ message->mutable_repeated_nested_message (1)->set_bb(518);
+ message->mutable_repeated_foreign_message(1)->set_c(519);
+ message->mutable_repeated_import_message (1)->set_d(520);
+ message->mutable_repeated_lazy_message (1)->set_bb(527);
+
+ message->set_repeated_nested_enum (1, unittest::TestAllTypesLite::FOO );
+ message->set_repeated_foreign_enum(1, unittest::FOREIGN_LITE_FOO );
+ message->set_repeated_import_enum (1, unittest_import::IMPORT_LITE_FOO);
+
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectAllFieldsSet(
+ const unittest::TestAllTypesLite& message) {
+ EXPECT_TRUE(message.has_optional_int32 ());
+ EXPECT_TRUE(message.has_optional_int64 ());
+ EXPECT_TRUE(message.has_optional_uint32 ());
+ EXPECT_TRUE(message.has_optional_uint64 ());
+ EXPECT_TRUE(message.has_optional_sint32 ());
+ EXPECT_TRUE(message.has_optional_sint64 ());
+ EXPECT_TRUE(message.has_optional_fixed32 ());
+ EXPECT_TRUE(message.has_optional_fixed64 ());
+ EXPECT_TRUE(message.has_optional_sfixed32());
+ EXPECT_TRUE(message.has_optional_sfixed64());
+ EXPECT_TRUE(message.has_optional_float ());
+ EXPECT_TRUE(message.has_optional_double ());
+ EXPECT_TRUE(message.has_optional_bool ());
+ EXPECT_TRUE(message.has_optional_string ());
+ EXPECT_TRUE(message.has_optional_bytes ());
+
+ EXPECT_TRUE(message.has_optionalgroup ());
+ EXPECT_TRUE(message.has_optional_nested_message ());
+ EXPECT_TRUE(message.has_optional_foreign_message ());
+ EXPECT_TRUE(message.has_optional_import_message ());
+ EXPECT_TRUE(message.has_optional_public_import_message());
+ EXPECT_TRUE(message.has_optional_lazy_message ());
+
+ EXPECT_TRUE(message.optionalgroup ().has_a());
+ EXPECT_TRUE(message.optional_nested_message ().has_bb());
+ EXPECT_TRUE(message.optional_foreign_message ().has_c());
+ EXPECT_TRUE(message.optional_import_message ().has_d());
+ EXPECT_TRUE(message.optional_public_import_message().has_e());
+ EXPECT_TRUE(message.optional_lazy_message ().has_bb());
+
+ EXPECT_TRUE(message.has_optional_nested_enum ());
+ EXPECT_TRUE(message.has_optional_foreign_enum());
+ EXPECT_TRUE(message.has_optional_import_enum ());
+
+
+ EXPECT_EQ(101 , message.optional_int32 ());
+ EXPECT_EQ(102 , message.optional_int64 ());
+ EXPECT_EQ(103 , message.optional_uint32 ());
+ EXPECT_EQ(104 , message.optional_uint64 ());
+ EXPECT_EQ(105 , message.optional_sint32 ());
+ EXPECT_EQ(106 , message.optional_sint64 ());
+ EXPECT_EQ(107 , message.optional_fixed32 ());
+ EXPECT_EQ(108 , message.optional_fixed64 ());
+ EXPECT_EQ(109 , message.optional_sfixed32());
+ EXPECT_EQ(110 , message.optional_sfixed64());
+ EXPECT_EQ(111 , message.optional_float ());
+ EXPECT_EQ(112 , message.optional_double ());
+ EXPECT_EQ(true , message.optional_bool ());
+ EXPECT_EQ("115", message.optional_string ());
+ EXPECT_EQ("116", message.optional_bytes ());
+
+ EXPECT_EQ(117, message.optionalgroup ().a());
+ EXPECT_EQ(118, message.optional_nested_message ().bb());
+ EXPECT_EQ(119, message.optional_foreign_message ().c());
+ EXPECT_EQ(120, message.optional_import_message ().d());
+ EXPECT_EQ(126, message.optional_public_import_message().e());
+ EXPECT_EQ(127, message.optional_lazy_message ().bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAZ , message.optional_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAZ , message.optional_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAZ, message.optional_import_enum ());
+
+
+ // -----------------------------------------------------------------
+
+ ASSERT_EQ(2, message.repeated_int32_size ());
+ ASSERT_EQ(2, message.repeated_int64_size ());
+ ASSERT_EQ(2, message.repeated_uint32_size ());
+ ASSERT_EQ(2, message.repeated_uint64_size ());
+ ASSERT_EQ(2, message.repeated_sint32_size ());
+ ASSERT_EQ(2, message.repeated_sint64_size ());
+ ASSERT_EQ(2, message.repeated_fixed32_size ());
+ ASSERT_EQ(2, message.repeated_fixed64_size ());
+ ASSERT_EQ(2, message.repeated_sfixed32_size());
+ ASSERT_EQ(2, message.repeated_sfixed64_size());
+ ASSERT_EQ(2, message.repeated_float_size ());
+ ASSERT_EQ(2, message.repeated_double_size ());
+ ASSERT_EQ(2, message.repeated_bool_size ());
+ ASSERT_EQ(2, message.repeated_string_size ());
+ ASSERT_EQ(2, message.repeated_bytes_size ());
+
+ ASSERT_EQ(2, message.repeatedgroup_size ());
+ ASSERT_EQ(2, message.repeated_nested_message_size ());
+ ASSERT_EQ(2, message.repeated_foreign_message_size());
+ ASSERT_EQ(2, message.repeated_import_message_size ());
+ ASSERT_EQ(2, message.repeated_lazy_message_size ());
+ ASSERT_EQ(2, message.repeated_nested_enum_size ());
+ ASSERT_EQ(2, message.repeated_foreign_enum_size ());
+ ASSERT_EQ(2, message.repeated_import_enum_size ());
+
+
+ EXPECT_EQ(201 , message.repeated_int32 (0));
+ EXPECT_EQ(202 , message.repeated_int64 (0));
+ EXPECT_EQ(203 , message.repeated_uint32 (0));
+ EXPECT_EQ(204 , message.repeated_uint64 (0));
+ EXPECT_EQ(205 , message.repeated_sint32 (0));
+ EXPECT_EQ(206 , message.repeated_sint64 (0));
+ EXPECT_EQ(207 , message.repeated_fixed32 (0));
+ EXPECT_EQ(208 , message.repeated_fixed64 (0));
+ EXPECT_EQ(209 , message.repeated_sfixed32(0));
+ EXPECT_EQ(210 , message.repeated_sfixed64(0));
+ EXPECT_EQ(211 , message.repeated_float (0));
+ EXPECT_EQ(212 , message.repeated_double (0));
+ EXPECT_EQ(true , message.repeated_bool (0));
+ EXPECT_EQ("215", message.repeated_string (0));
+ EXPECT_EQ("216", message.repeated_bytes (0));
+
+ EXPECT_EQ(217, message.repeatedgroup (0).a());
+ EXPECT_EQ(218, message.repeated_nested_message (0).bb());
+ EXPECT_EQ(219, message.repeated_foreign_message(0).c());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+ EXPECT_EQ(227, message.repeated_lazy_message (0).bb());
+
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAR , message.repeated_nested_enum (0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR , message.repeated_foreign_enum(0));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAR, message.repeated_import_enum (0));
+
+ EXPECT_EQ(301 , message.repeated_int32 (1));
+ EXPECT_EQ(302 , message.repeated_int64 (1));
+ EXPECT_EQ(303 , message.repeated_uint32 (1));
+ EXPECT_EQ(304 , message.repeated_uint64 (1));
+ EXPECT_EQ(305 , message.repeated_sint32 (1));
+ EXPECT_EQ(306 , message.repeated_sint64 (1));
+ EXPECT_EQ(307 , message.repeated_fixed32 (1));
+ EXPECT_EQ(308 , message.repeated_fixed64 (1));
+ EXPECT_EQ(309 , message.repeated_sfixed32(1));
+ EXPECT_EQ(310 , message.repeated_sfixed64(1));
+ EXPECT_EQ(311 , message.repeated_float (1));
+ EXPECT_EQ(312 , message.repeated_double (1));
+ EXPECT_EQ(false, message.repeated_bool (1));
+ EXPECT_EQ("315", message.repeated_string (1));
+ EXPECT_EQ("316", message.repeated_bytes (1));
+
+ EXPECT_EQ(317, message.repeatedgroup (1).a());
+ EXPECT_EQ(318, message.repeated_nested_message (1).bb());
+ EXPECT_EQ(319, message.repeated_foreign_message(1).c());
+ EXPECT_EQ(320, message.repeated_import_message (1).d());
+ EXPECT_EQ(327, message.repeated_lazy_message (1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAZ , message.repeated_nested_enum (1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAZ , message.repeated_foreign_enum(1));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAZ, message.repeated_import_enum (1));
+
+
+ // -----------------------------------------------------------------
+
+ EXPECT_TRUE(message.has_default_int32 ());
+ EXPECT_TRUE(message.has_default_int64 ());
+ EXPECT_TRUE(message.has_default_uint32 ());
+ EXPECT_TRUE(message.has_default_uint64 ());
+ EXPECT_TRUE(message.has_default_sint32 ());
+ EXPECT_TRUE(message.has_default_sint64 ());
+ EXPECT_TRUE(message.has_default_fixed32 ());
+ EXPECT_TRUE(message.has_default_fixed64 ());
+ EXPECT_TRUE(message.has_default_sfixed32());
+ EXPECT_TRUE(message.has_default_sfixed64());
+ EXPECT_TRUE(message.has_default_float ());
+ EXPECT_TRUE(message.has_default_double ());
+ EXPECT_TRUE(message.has_default_bool ());
+ EXPECT_TRUE(message.has_default_string ());
+ EXPECT_TRUE(message.has_default_bytes ());
+
+ EXPECT_TRUE(message.has_default_nested_enum ());
+ EXPECT_TRUE(message.has_default_foreign_enum());
+ EXPECT_TRUE(message.has_default_import_enum ());
+
+
+ EXPECT_EQ(401 , message.default_int32 ());
+ EXPECT_EQ(402 , message.default_int64 ());
+ EXPECT_EQ(403 , message.default_uint32 ());
+ EXPECT_EQ(404 , message.default_uint64 ());
+ EXPECT_EQ(405 , message.default_sint32 ());
+ EXPECT_EQ(406 , message.default_sint64 ());
+ EXPECT_EQ(407 , message.default_fixed32 ());
+ EXPECT_EQ(408 , message.default_fixed64 ());
+ EXPECT_EQ(409 , message.default_sfixed32());
+ EXPECT_EQ(410 , message.default_sfixed64());
+ EXPECT_EQ(411 , message.default_float ());
+ EXPECT_EQ(412 , message.default_double ());
+ EXPECT_EQ(false, message.default_bool ());
+ EXPECT_EQ("415", message.default_string ());
+ EXPECT_EQ("416", message.default_bytes ());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::FOO , message.default_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO , message.default_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_LITE_FOO, message.default_import_enum ());
+
+
+ EXPECT_FALSE(message.has_oneof_uint32 ());
+ EXPECT_FALSE(message.has_oneof_nested_message());
+ EXPECT_FALSE(message.has_oneof_string ());
+ EXPECT_TRUE(message.has_oneof_bytes ());
+
+ EXPECT_EQ("604", message.oneof_bytes());
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectClear(const unittest::TestAllTypesLite& message) {
+ // has_blah() should initially be false for all optional fields.
+ EXPECT_FALSE(message.has_optional_int32 ());
+ EXPECT_FALSE(message.has_optional_int64 ());
+ EXPECT_FALSE(message.has_optional_uint32 ());
+ EXPECT_FALSE(message.has_optional_uint64 ());
+ EXPECT_FALSE(message.has_optional_sint32 ());
+ EXPECT_FALSE(message.has_optional_sint64 ());
+ EXPECT_FALSE(message.has_optional_fixed32 ());
+ EXPECT_FALSE(message.has_optional_fixed64 ());
+ EXPECT_FALSE(message.has_optional_sfixed32());
+ EXPECT_FALSE(message.has_optional_sfixed64());
+ EXPECT_FALSE(message.has_optional_float ());
+ EXPECT_FALSE(message.has_optional_double ());
+ EXPECT_FALSE(message.has_optional_bool ());
+ EXPECT_FALSE(message.has_optional_string ());
+ EXPECT_FALSE(message.has_optional_bytes ());
+
+ EXPECT_FALSE(message.has_optionalgroup ());
+ EXPECT_FALSE(message.has_optional_nested_message ());
+ EXPECT_FALSE(message.has_optional_foreign_message ());
+ EXPECT_FALSE(message.has_optional_import_message ());
+ EXPECT_FALSE(message.has_optional_public_import_message());
+ EXPECT_FALSE(message.has_optional_lazy_message ());
+
+ EXPECT_FALSE(message.has_optional_nested_enum ());
+ EXPECT_FALSE(message.has_optional_foreign_enum());
+ EXPECT_FALSE(message.has_optional_import_enum ());
+
+
+ // Optional fields without defaults are set to zero or something like it.
+ EXPECT_EQ(0 , message.optional_int32 ());
+ EXPECT_EQ(0 , message.optional_int64 ());
+ EXPECT_EQ(0 , message.optional_uint32 ());
+ EXPECT_EQ(0 , message.optional_uint64 ());
+ EXPECT_EQ(0 , message.optional_sint32 ());
+ EXPECT_EQ(0 , message.optional_sint64 ());
+ EXPECT_EQ(0 , message.optional_fixed32 ());
+ EXPECT_EQ(0 , message.optional_fixed64 ());
+ EXPECT_EQ(0 , message.optional_sfixed32());
+ EXPECT_EQ(0 , message.optional_sfixed64());
+ EXPECT_EQ(0 , message.optional_float ());
+ EXPECT_EQ(0 , message.optional_double ());
+ EXPECT_EQ(false, message.optional_bool ());
+ EXPECT_EQ("" , message.optional_string ());
+ EXPECT_EQ("" , message.optional_bytes ());
+
+ // Embedded messages should also be clear.
+ EXPECT_FALSE(message.optionalgroup ().has_a());
+ EXPECT_FALSE(message.optional_nested_message ().has_bb());
+ EXPECT_FALSE(message.optional_foreign_message ().has_c());
+ EXPECT_FALSE(message.optional_import_message ().has_d());
+ EXPECT_FALSE(message.optional_public_import_message().has_e());
+ EXPECT_FALSE(message.optional_lazy_message ().has_bb());
+
+ EXPECT_EQ(0, message.optionalgroup ().a());
+ EXPECT_EQ(0, message.optional_nested_message ().bb());
+ EXPECT_EQ(0, message.optional_foreign_message().c());
+ EXPECT_EQ(0, message.optional_import_message ().d());
+
+ // Enums without defaults are set to the first value in the enum.
+ EXPECT_EQ(unittest::TestAllTypesLite::FOO , message.optional_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO , message.optional_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_LITE_FOO, message.optional_import_enum ());
+
+
+ // Repeated fields are empty.
+ EXPECT_EQ(0, message.repeated_int32_size ());
+ EXPECT_EQ(0, message.repeated_int64_size ());
+ EXPECT_EQ(0, message.repeated_uint32_size ());
+ EXPECT_EQ(0, message.repeated_uint64_size ());
+ EXPECT_EQ(0, message.repeated_sint32_size ());
+ EXPECT_EQ(0, message.repeated_sint64_size ());
+ EXPECT_EQ(0, message.repeated_fixed32_size ());
+ EXPECT_EQ(0, message.repeated_fixed64_size ());
+ EXPECT_EQ(0, message.repeated_sfixed32_size());
+ EXPECT_EQ(0, message.repeated_sfixed64_size());
+ EXPECT_EQ(0, message.repeated_float_size ());
+ EXPECT_EQ(0, message.repeated_double_size ());
+ EXPECT_EQ(0, message.repeated_bool_size ());
+ EXPECT_EQ(0, message.repeated_string_size ());
+ EXPECT_EQ(0, message.repeated_bytes_size ());
+
+ EXPECT_EQ(0, message.repeatedgroup_size ());
+ EXPECT_EQ(0, message.repeated_nested_message_size ());
+ EXPECT_EQ(0, message.repeated_foreign_message_size());
+ EXPECT_EQ(0, message.repeated_import_message_size ());
+ EXPECT_EQ(0, message.repeated_lazy_message_size ());
+ EXPECT_EQ(0, message.repeated_nested_enum_size ());
+ EXPECT_EQ(0, message.repeated_foreign_enum_size ());
+ EXPECT_EQ(0, message.repeated_import_enum_size ());
+
+
+ // has_blah() should also be false for all default fields.
+ EXPECT_FALSE(message.has_default_int32 ());
+ EXPECT_FALSE(message.has_default_int64 ());
+ EXPECT_FALSE(message.has_default_uint32 ());
+ EXPECT_FALSE(message.has_default_uint64 ());
+ EXPECT_FALSE(message.has_default_sint32 ());
+ EXPECT_FALSE(message.has_default_sint64 ());
+ EXPECT_FALSE(message.has_default_fixed32 ());
+ EXPECT_FALSE(message.has_default_fixed64 ());
+ EXPECT_FALSE(message.has_default_sfixed32());
+ EXPECT_FALSE(message.has_default_sfixed64());
+ EXPECT_FALSE(message.has_default_float ());
+ EXPECT_FALSE(message.has_default_double ());
+ EXPECT_FALSE(message.has_default_bool ());
+ EXPECT_FALSE(message.has_default_string ());
+ EXPECT_FALSE(message.has_default_bytes ());
+
+ EXPECT_FALSE(message.has_default_nested_enum ());
+ EXPECT_FALSE(message.has_default_foreign_enum());
+ EXPECT_FALSE(message.has_default_import_enum ());
+
+
+ // Fields with defaults have their default values (duh).
+ EXPECT_EQ( 41 , message.default_int32 ());
+ EXPECT_EQ( 42 , message.default_int64 ());
+ EXPECT_EQ( 43 , message.default_uint32 ());
+ EXPECT_EQ( 44 , message.default_uint64 ());
+ EXPECT_EQ(-45 , message.default_sint32 ());
+ EXPECT_EQ( 46 , message.default_sint64 ());
+ EXPECT_EQ( 47 , message.default_fixed32 ());
+ EXPECT_EQ( 48 , message.default_fixed64 ());
+ EXPECT_EQ( 49 , message.default_sfixed32());
+ EXPECT_EQ(-50 , message.default_sfixed64());
+ EXPECT_EQ( 51.5 , message.default_float ());
+ EXPECT_EQ( 52e3 , message.default_double ());
+ EXPECT_EQ(true , message.default_bool ());
+ EXPECT_EQ("hello", message.default_string ());
+ EXPECT_EQ("world", message.default_bytes ());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAR , message.default_nested_enum ());
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR , message.default_foreign_enum());
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAR, message.default_import_enum ());
+
+
+ EXPECT_FALSE(message.has_oneof_uint32 ());
+ EXPECT_FALSE(message.has_oneof_nested_message());
+ EXPECT_FALSE(message.has_oneof_string ());
+ EXPECT_FALSE(message.has_oneof_bytes ());
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectRepeatedFieldsModified(
+ const unittest::TestAllTypesLite& message) {
+ // ModifyRepeatedFields only sets the second repeated element of each
+ // field. In addition to verifying this, we also verify that the first
+ // element and size were *not* modified.
+ ASSERT_EQ(2, message.repeated_int32_size ());
+ ASSERT_EQ(2, message.repeated_int64_size ());
+ ASSERT_EQ(2, message.repeated_uint32_size ());
+ ASSERT_EQ(2, message.repeated_uint64_size ());
+ ASSERT_EQ(2, message.repeated_sint32_size ());
+ ASSERT_EQ(2, message.repeated_sint64_size ());
+ ASSERT_EQ(2, message.repeated_fixed32_size ());
+ ASSERT_EQ(2, message.repeated_fixed64_size ());
+ ASSERT_EQ(2, message.repeated_sfixed32_size());
+ ASSERT_EQ(2, message.repeated_sfixed64_size());
+ ASSERT_EQ(2, message.repeated_float_size ());
+ ASSERT_EQ(2, message.repeated_double_size ());
+ ASSERT_EQ(2, message.repeated_bool_size ());
+ ASSERT_EQ(2, message.repeated_string_size ());
+ ASSERT_EQ(2, message.repeated_bytes_size ());
+
+ ASSERT_EQ(2, message.repeatedgroup_size ());
+ ASSERT_EQ(2, message.repeated_nested_message_size ());
+ ASSERT_EQ(2, message.repeated_foreign_message_size());
+ ASSERT_EQ(2, message.repeated_import_message_size ());
+ ASSERT_EQ(2, message.repeated_lazy_message_size ());
+ ASSERT_EQ(2, message.repeated_nested_enum_size ());
+ ASSERT_EQ(2, message.repeated_foreign_enum_size ());
+ ASSERT_EQ(2, message.repeated_import_enum_size ());
+
+
+ EXPECT_EQ(201 , message.repeated_int32 (0));
+ EXPECT_EQ(202 , message.repeated_int64 (0));
+ EXPECT_EQ(203 , message.repeated_uint32 (0));
+ EXPECT_EQ(204 , message.repeated_uint64 (0));
+ EXPECT_EQ(205 , message.repeated_sint32 (0));
+ EXPECT_EQ(206 , message.repeated_sint64 (0));
+ EXPECT_EQ(207 , message.repeated_fixed32 (0));
+ EXPECT_EQ(208 , message.repeated_fixed64 (0));
+ EXPECT_EQ(209 , message.repeated_sfixed32(0));
+ EXPECT_EQ(210 , message.repeated_sfixed64(0));
+ EXPECT_EQ(211 , message.repeated_float (0));
+ EXPECT_EQ(212 , message.repeated_double (0));
+ EXPECT_EQ(true , message.repeated_bool (0));
+ EXPECT_EQ("215", message.repeated_string (0));
+ EXPECT_EQ("216", message.repeated_bytes (0));
+
+ EXPECT_EQ(217, message.repeatedgroup (0).a());
+ EXPECT_EQ(218, message.repeated_nested_message (0).bb());
+ EXPECT_EQ(219, message.repeated_foreign_message(0).c());
+ EXPECT_EQ(220, message.repeated_import_message (0).d());
+ EXPECT_EQ(227, message.repeated_lazy_message (0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAR , message.repeated_nested_enum (0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR , message.repeated_foreign_enum(0));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAR, message.repeated_import_enum (0));
+
+
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(501 , message.repeated_int32 (1));
+ EXPECT_EQ(502 , message.repeated_int64 (1));
+ EXPECT_EQ(503 , message.repeated_uint32 (1));
+ EXPECT_EQ(504 , message.repeated_uint64 (1));
+ EXPECT_EQ(505 , message.repeated_sint32 (1));
+ EXPECT_EQ(506 , message.repeated_sint64 (1));
+ EXPECT_EQ(507 , message.repeated_fixed32 (1));
+ EXPECT_EQ(508 , message.repeated_fixed64 (1));
+ EXPECT_EQ(509 , message.repeated_sfixed32(1));
+ EXPECT_EQ(510 , message.repeated_sfixed64(1));
+ EXPECT_EQ(511 , message.repeated_float (1));
+ EXPECT_EQ(512 , message.repeated_double (1));
+ EXPECT_EQ(true , message.repeated_bool (1));
+ EXPECT_EQ("515", message.repeated_string (1));
+ EXPECT_EQ("516", message.repeated_bytes (1));
+
+ EXPECT_EQ(517, message.repeatedgroup (1).a());
+ EXPECT_EQ(518, message.repeated_nested_message (1).bb());
+ EXPECT_EQ(519, message.repeated_foreign_message(1).c());
+ EXPECT_EQ(520, message.repeated_import_message (1).d());
+ EXPECT_EQ(527, message.repeated_lazy_message (1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::FOO , message.repeated_nested_enum (1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO , message.repeated_foreign_enum(1));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_FOO, message.repeated_import_enum (1));
+
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::SetPackedFields(unittest::TestPackedTypesLite* message) {
+ message->add_packed_int32 (601);
+ message->add_packed_int64 (602);
+ message->add_packed_uint32 (603);
+ message->add_packed_uint64 (604);
+ message->add_packed_sint32 (605);
+ message->add_packed_sint64 (606);
+ message->add_packed_fixed32 (607);
+ message->add_packed_fixed64 (608);
+ message->add_packed_sfixed32(609);
+ message->add_packed_sfixed64(610);
+ message->add_packed_float (611);
+ message->add_packed_double (612);
+ message->add_packed_bool (true);
+ message->add_packed_enum (unittest::FOREIGN_LITE_BAR);
+ // add a second one of each field
+ message->add_packed_int32 (701);
+ message->add_packed_int64 (702);
+ message->add_packed_uint32 (703);
+ message->add_packed_uint64 (704);
+ message->add_packed_sint32 (705);
+ message->add_packed_sint64 (706);
+ message->add_packed_fixed32 (707);
+ message->add_packed_fixed64 (708);
+ message->add_packed_sfixed32(709);
+ message->add_packed_sfixed64(710);
+ message->add_packed_float (711);
+ message->add_packed_double (712);
+ message->add_packed_bool (false);
+ message->add_packed_enum (unittest::FOREIGN_LITE_BAZ);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ModifyPackedFields(unittest::TestPackedTypesLite* message) {
+ message->set_packed_int32 (1, 801);
+ message->set_packed_int64 (1, 802);
+ message->set_packed_uint32 (1, 803);
+ message->set_packed_uint64 (1, 804);
+ message->set_packed_sint32 (1, 805);
+ message->set_packed_sint64 (1, 806);
+ message->set_packed_fixed32 (1, 807);
+ message->set_packed_fixed64 (1, 808);
+ message->set_packed_sfixed32(1, 809);
+ message->set_packed_sfixed64(1, 810);
+ message->set_packed_float (1, 811);
+ message->set_packed_double (1, 812);
+ message->set_packed_bool (1, true);
+ message->set_packed_enum (1, unittest::FOREIGN_LITE_FOO);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectPackedFieldsSet(
+ const unittest::TestPackedTypesLite& message) {
+ ASSERT_EQ(2, message.packed_int32_size ());
+ ASSERT_EQ(2, message.packed_int64_size ());
+ ASSERT_EQ(2, message.packed_uint32_size ());
+ ASSERT_EQ(2, message.packed_uint64_size ());
+ ASSERT_EQ(2, message.packed_sint32_size ());
+ ASSERT_EQ(2, message.packed_sint64_size ());
+ ASSERT_EQ(2, message.packed_fixed32_size ());
+ ASSERT_EQ(2, message.packed_fixed64_size ());
+ ASSERT_EQ(2, message.packed_sfixed32_size());
+ ASSERT_EQ(2, message.packed_sfixed64_size());
+ ASSERT_EQ(2, message.packed_float_size ());
+ ASSERT_EQ(2, message.packed_double_size ());
+ ASSERT_EQ(2, message.packed_bool_size ());
+ ASSERT_EQ(2, message.packed_enum_size ());
+
+ EXPECT_EQ(601 , message.packed_int32 (0));
+ EXPECT_EQ(602 , message.packed_int64 (0));
+ EXPECT_EQ(603 , message.packed_uint32 (0));
+ EXPECT_EQ(604 , message.packed_uint64 (0));
+ EXPECT_EQ(605 , message.packed_sint32 (0));
+ EXPECT_EQ(606 , message.packed_sint64 (0));
+ EXPECT_EQ(607 , message.packed_fixed32 (0));
+ EXPECT_EQ(608 , message.packed_fixed64 (0));
+ EXPECT_EQ(609 , message.packed_sfixed32(0));
+ EXPECT_EQ(610 , message.packed_sfixed64(0));
+ EXPECT_EQ(611 , message.packed_float (0));
+ EXPECT_EQ(612 , message.packed_double (0));
+ EXPECT_EQ(true , message.packed_bool (0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR, message.packed_enum(0));
+
+ EXPECT_EQ(701 , message.packed_int32 (1));
+ EXPECT_EQ(702 , message.packed_int64 (1));
+ EXPECT_EQ(703 , message.packed_uint32 (1));
+ EXPECT_EQ(704 , message.packed_uint64 (1));
+ EXPECT_EQ(705 , message.packed_sint32 (1));
+ EXPECT_EQ(706 , message.packed_sint64 (1));
+ EXPECT_EQ(707 , message.packed_fixed32 (1));
+ EXPECT_EQ(708 , message.packed_fixed64 (1));
+ EXPECT_EQ(709 , message.packed_sfixed32(1));
+ EXPECT_EQ(710 , message.packed_sfixed64(1));
+ EXPECT_EQ(711 , message.packed_float (1));
+ EXPECT_EQ(712 , message.packed_double (1));
+ EXPECT_EQ(false, message.packed_bool (1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAZ, message.packed_enum(1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectPackedClear(
+ const unittest::TestPackedTypesLite& message) {
+ // Packed repeated fields are empty.
+ EXPECT_EQ(0, message.packed_int32_size ());
+ EXPECT_EQ(0, message.packed_int64_size ());
+ EXPECT_EQ(0, message.packed_uint32_size ());
+ EXPECT_EQ(0, message.packed_uint64_size ());
+ EXPECT_EQ(0, message.packed_sint32_size ());
+ EXPECT_EQ(0, message.packed_sint64_size ());
+ EXPECT_EQ(0, message.packed_fixed32_size ());
+ EXPECT_EQ(0, message.packed_fixed64_size ());
+ EXPECT_EQ(0, message.packed_sfixed32_size());
+ EXPECT_EQ(0, message.packed_sfixed64_size());
+ EXPECT_EQ(0, message.packed_float_size ());
+ EXPECT_EQ(0, message.packed_double_size ());
+ EXPECT_EQ(0, message.packed_bool_size ());
+ EXPECT_EQ(0, message.packed_enum_size ());
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectPackedFieldsModified(
+ const unittest::TestPackedTypesLite& message) {
+ // Do the same for packed repeated fields.
+ ASSERT_EQ(2, message.packed_int32_size ());
+ ASSERT_EQ(2, message.packed_int64_size ());
+ ASSERT_EQ(2, message.packed_uint32_size ());
+ ASSERT_EQ(2, message.packed_uint64_size ());
+ ASSERT_EQ(2, message.packed_sint32_size ());
+ ASSERT_EQ(2, message.packed_sint64_size ());
+ ASSERT_EQ(2, message.packed_fixed32_size ());
+ ASSERT_EQ(2, message.packed_fixed64_size ());
+ ASSERT_EQ(2, message.packed_sfixed32_size());
+ ASSERT_EQ(2, message.packed_sfixed64_size());
+ ASSERT_EQ(2, message.packed_float_size ());
+ ASSERT_EQ(2, message.packed_double_size ());
+ ASSERT_EQ(2, message.packed_bool_size ());
+ ASSERT_EQ(2, message.packed_enum_size ());
+
+ EXPECT_EQ(601 , message.packed_int32 (0));
+ EXPECT_EQ(602 , message.packed_int64 (0));
+ EXPECT_EQ(603 , message.packed_uint32 (0));
+ EXPECT_EQ(604 , message.packed_uint64 (0));
+ EXPECT_EQ(605 , message.packed_sint32 (0));
+ EXPECT_EQ(606 , message.packed_sint64 (0));
+ EXPECT_EQ(607 , message.packed_fixed32 (0));
+ EXPECT_EQ(608 , message.packed_fixed64 (0));
+ EXPECT_EQ(609 , message.packed_sfixed32(0));
+ EXPECT_EQ(610 , message.packed_sfixed64(0));
+ EXPECT_EQ(611 , message.packed_float (0));
+ EXPECT_EQ(612 , message.packed_double (0));
+ EXPECT_EQ(true , message.packed_bool (0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR, message.packed_enum(0));
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(801 , message.packed_int32 (1));
+ EXPECT_EQ(802 , message.packed_int64 (1));
+ EXPECT_EQ(803 , message.packed_uint32 (1));
+ EXPECT_EQ(804 , message.packed_uint64 (1));
+ EXPECT_EQ(805 , message.packed_sint32 (1));
+ EXPECT_EQ(806 , message.packed_sint64 (1));
+ EXPECT_EQ(807 , message.packed_fixed32 (1));
+ EXPECT_EQ(808 , message.packed_fixed64 (1));
+ EXPECT_EQ(809 , message.packed_sfixed32(1));
+ EXPECT_EQ(810 , message.packed_sfixed64(1));
+ EXPECT_EQ(811 , message.packed_float (1));
+ EXPECT_EQ(812 , message.packed_double (1));
+ EXPECT_EQ(true , message.packed_bool (1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO, message.packed_enum(1));
+}
+
+// ===================================================================
+// Extensions
+//
+// All this code is exactly equivalent to the above code except that it's
+// manipulating extension fields instead of normal ones.
+//
+// I gave up on the 80-char limit here. Sorry.
+
+void TestUtilLite::SetAllExtensions(unittest::TestAllExtensionsLite* message) {
+ message->SetExtension(unittest::optional_int32_extension_lite , 101);
+ message->SetExtension(unittest::optional_int64_extension_lite , 102);
+ message->SetExtension(unittest::optional_uint32_extension_lite , 103);
+ message->SetExtension(unittest::optional_uint64_extension_lite , 104);
+ message->SetExtension(unittest::optional_sint32_extension_lite , 105);
+ message->SetExtension(unittest::optional_sint64_extension_lite , 106);
+ message->SetExtension(unittest::optional_fixed32_extension_lite , 107);
+ message->SetExtension(unittest::optional_fixed64_extension_lite , 108);
+ message->SetExtension(unittest::optional_sfixed32_extension_lite, 109);
+ message->SetExtension(unittest::optional_sfixed64_extension_lite, 110);
+ message->SetExtension(unittest::optional_float_extension_lite , 111);
+ message->SetExtension(unittest::optional_double_extension_lite , 112);
+ message->SetExtension(unittest::optional_bool_extension_lite , true);
+ message->SetExtension(unittest::optional_string_extension_lite , "115");
+ message->SetExtension(unittest::optional_bytes_extension_lite , "116");
+
+ message->MutableExtension(unittest::optionalgroup_extension_lite )->set_a(117);
+ message->MutableExtension(unittest::optional_nested_message_extension_lite )->set_bb(118);
+ message->MutableExtension(unittest::optional_foreign_message_extension_lite )->set_c(119);
+ message->MutableExtension(unittest::optional_import_message_extension_lite )->set_d(120);
+ message->MutableExtension(unittest::optional_public_import_message_extension_lite)->set_e(126);
+ message->MutableExtension(unittest::optional_lazy_message_extension_lite )->set_bb(127);
+
+ message->SetExtension(unittest::optional_nested_enum_extension_lite , unittest::TestAllTypesLite::BAZ );
+ message->SetExtension(unittest::optional_foreign_enum_extension_lite, unittest::FOREIGN_LITE_BAZ );
+ message->SetExtension(unittest::optional_import_enum_extension_lite , unittest_import::IMPORT_LITE_BAZ);
+
+
+ // -----------------------------------------------------------------
+
+ message->AddExtension(unittest::repeated_int32_extension_lite , 201);
+ message->AddExtension(unittest::repeated_int64_extension_lite , 202);
+ message->AddExtension(unittest::repeated_uint32_extension_lite , 203);
+ message->AddExtension(unittest::repeated_uint64_extension_lite , 204);
+ message->AddExtension(unittest::repeated_sint32_extension_lite , 205);
+ message->AddExtension(unittest::repeated_sint64_extension_lite , 206);
+ message->AddExtension(unittest::repeated_fixed32_extension_lite , 207);
+ message->AddExtension(unittest::repeated_fixed64_extension_lite , 208);
+ message->AddExtension(unittest::repeated_sfixed32_extension_lite, 209);
+ message->AddExtension(unittest::repeated_sfixed64_extension_lite, 210);
+ message->AddExtension(unittest::repeated_float_extension_lite , 211);
+ message->AddExtension(unittest::repeated_double_extension_lite , 212);
+ message->AddExtension(unittest::repeated_bool_extension_lite , true);
+ message->AddExtension(unittest::repeated_string_extension_lite , "215");
+ message->AddExtension(unittest::repeated_bytes_extension_lite , "216");
+
+ message->AddExtension(unittest::repeatedgroup_extension_lite )->set_a(217);
+ message->AddExtension(unittest::repeated_nested_message_extension_lite )->set_bb(218);
+ message->AddExtension(unittest::repeated_foreign_message_extension_lite)->set_c(219);
+ message->AddExtension(unittest::repeated_import_message_extension_lite )->set_d(220);
+ message->AddExtension(unittest::repeated_lazy_message_extension_lite )->set_bb(227);
+
+ message->AddExtension(unittest::repeated_nested_enum_extension_lite , unittest::TestAllTypesLite::BAR );
+ message->AddExtension(unittest::repeated_foreign_enum_extension_lite, unittest::FOREIGN_LITE_BAR );
+ message->AddExtension(unittest::repeated_import_enum_extension_lite , unittest_import::IMPORT_LITE_BAR);
+
+
+ // Add a second one of each field.
+ message->AddExtension(unittest::repeated_int32_extension_lite , 301);
+ message->AddExtension(unittest::repeated_int64_extension_lite , 302);
+ message->AddExtension(unittest::repeated_uint32_extension_lite , 303);
+ message->AddExtension(unittest::repeated_uint64_extension_lite , 304);
+ message->AddExtension(unittest::repeated_sint32_extension_lite , 305);
+ message->AddExtension(unittest::repeated_sint64_extension_lite , 306);
+ message->AddExtension(unittest::repeated_fixed32_extension_lite , 307);
+ message->AddExtension(unittest::repeated_fixed64_extension_lite , 308);
+ message->AddExtension(unittest::repeated_sfixed32_extension_lite, 309);
+ message->AddExtension(unittest::repeated_sfixed64_extension_lite, 310);
+ message->AddExtension(unittest::repeated_float_extension_lite , 311);
+ message->AddExtension(unittest::repeated_double_extension_lite , 312);
+ message->AddExtension(unittest::repeated_bool_extension_lite , false);
+ message->AddExtension(unittest::repeated_string_extension_lite , "315");
+ message->AddExtension(unittest::repeated_bytes_extension_lite , "316");
+
+ message->AddExtension(unittest::repeatedgroup_extension_lite )->set_a(317);
+ message->AddExtension(unittest::repeated_nested_message_extension_lite )->set_bb(318);
+ message->AddExtension(unittest::repeated_foreign_message_extension_lite)->set_c(319);
+ message->AddExtension(unittest::repeated_import_message_extension_lite )->set_d(320);
+ message->AddExtension(unittest::repeated_lazy_message_extension_lite )->set_bb(327);
+
+ message->AddExtension(unittest::repeated_nested_enum_extension_lite , unittest::TestAllTypesLite::BAZ );
+ message->AddExtension(unittest::repeated_foreign_enum_extension_lite, unittest::FOREIGN_LITE_BAZ );
+ message->AddExtension(unittest::repeated_import_enum_extension_lite , unittest_import::IMPORT_LITE_BAZ);
+
+
+ // -----------------------------------------------------------------
+
+ message->SetExtension(unittest::default_int32_extension_lite , 401);
+ message->SetExtension(unittest::default_int64_extension_lite , 402);
+ message->SetExtension(unittest::default_uint32_extension_lite , 403);
+ message->SetExtension(unittest::default_uint64_extension_lite , 404);
+ message->SetExtension(unittest::default_sint32_extension_lite , 405);
+ message->SetExtension(unittest::default_sint64_extension_lite , 406);
+ message->SetExtension(unittest::default_fixed32_extension_lite , 407);
+ message->SetExtension(unittest::default_fixed64_extension_lite , 408);
+ message->SetExtension(unittest::default_sfixed32_extension_lite, 409);
+ message->SetExtension(unittest::default_sfixed64_extension_lite, 410);
+ message->SetExtension(unittest::default_float_extension_lite , 411);
+ message->SetExtension(unittest::default_double_extension_lite , 412);
+ message->SetExtension(unittest::default_bool_extension_lite , false);
+ message->SetExtension(unittest::default_string_extension_lite , "415");
+ message->SetExtension(unittest::default_bytes_extension_lite , "416");
+
+ message->SetExtension(unittest::default_nested_enum_extension_lite , unittest::TestAllTypesLite::FOO );
+ message->SetExtension(unittest::default_foreign_enum_extension_lite, unittest::FOREIGN_LITE_FOO );
+ message->SetExtension(unittest::default_import_enum_extension_lite , unittest_import::IMPORT_LITE_FOO);
+
+
+ message->SetExtension(unittest::oneof_uint32_extension_lite, 601);
+ message->MutableExtension(unittest::oneof_nested_message_extension_lite)->set_bb(602);;
+ message->SetExtension(unittest::oneof_string_extension_lite, "603");
+ message->SetExtension(unittest::oneof_bytes_extension_lite, "604");
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ModifyRepeatedExtensions(
+ unittest::TestAllExtensionsLite* message) {
+ message->SetExtension(unittest::repeated_int32_extension_lite , 1, 501);
+ message->SetExtension(unittest::repeated_int64_extension_lite , 1, 502);
+ message->SetExtension(unittest::repeated_uint32_extension_lite , 1, 503);
+ message->SetExtension(unittest::repeated_uint64_extension_lite , 1, 504);
+ message->SetExtension(unittest::repeated_sint32_extension_lite , 1, 505);
+ message->SetExtension(unittest::repeated_sint64_extension_lite , 1, 506);
+ message->SetExtension(unittest::repeated_fixed32_extension_lite , 1, 507);
+ message->SetExtension(unittest::repeated_fixed64_extension_lite , 1, 508);
+ message->SetExtension(unittest::repeated_sfixed32_extension_lite, 1, 509);
+ message->SetExtension(unittest::repeated_sfixed64_extension_lite, 1, 510);
+ message->SetExtension(unittest::repeated_float_extension_lite , 1, 511);
+ message->SetExtension(unittest::repeated_double_extension_lite , 1, 512);
+ message->SetExtension(unittest::repeated_bool_extension_lite , 1, true);
+ message->SetExtension(unittest::repeated_string_extension_lite , 1, "515");
+ message->SetExtension(unittest::repeated_bytes_extension_lite , 1, "516");
+
+ message->MutableExtension(unittest::repeatedgroup_extension_lite , 1)->set_a(517);
+ message->MutableExtension(unittest::repeated_nested_message_extension_lite , 1)->set_bb(518);
+ message->MutableExtension(unittest::repeated_foreign_message_extension_lite, 1)->set_c(519);
+ message->MutableExtension(unittest::repeated_import_message_extension_lite , 1)->set_d(520);
+ message->MutableExtension(unittest::repeated_lazy_message_extension_lite , 1)->set_bb(527);
+
+ message->SetExtension(unittest::repeated_nested_enum_extension_lite , 1, unittest::TestAllTypesLite::FOO );
+ message->SetExtension(unittest::repeated_foreign_enum_extension_lite, 1, unittest::FOREIGN_LITE_FOO );
+ message->SetExtension(unittest::repeated_import_enum_extension_lite , 1, unittest_import::IMPORT_LITE_FOO);
+
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectAllExtensionsSet(
+ const unittest::TestAllExtensionsLite& message) {
+ EXPECT_TRUE(message.HasExtension(unittest::optional_int32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_int64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_uint32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_uint64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sint32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sint64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_fixed32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_fixed64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sfixed32_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_sfixed64_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_float_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_double_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_bool_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_string_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_bytes_extension_lite ));
+
+ EXPECT_TRUE(message.HasExtension(unittest::optionalgroup_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_nested_message_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_foreign_message_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_import_message_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_public_import_message_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_lazy_message_extension_lite ));
+
+ EXPECT_TRUE(message.GetExtension(unittest::optionalgroup_extension_lite ).has_a());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_nested_message_extension_lite ).has_bb());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_foreign_message_extension_lite ).has_c());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_import_message_extension_lite ).has_d());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_public_import_message_extension_lite).has_e());
+ EXPECT_TRUE(message.GetExtension(unittest::optional_lazy_message_extension_lite ).has_bb());
+
+ EXPECT_TRUE(message.HasExtension(unittest::optional_nested_enum_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_foreign_enum_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::optional_import_enum_extension_lite ));
+
+
+ EXPECT_EQ(101 , message.GetExtension(unittest::optional_int32_extension_lite ));
+ EXPECT_EQ(102 , message.GetExtension(unittest::optional_int64_extension_lite ));
+ EXPECT_EQ(103 , message.GetExtension(unittest::optional_uint32_extension_lite ));
+ EXPECT_EQ(104 , message.GetExtension(unittest::optional_uint64_extension_lite ));
+ EXPECT_EQ(105 , message.GetExtension(unittest::optional_sint32_extension_lite ));
+ EXPECT_EQ(106 , message.GetExtension(unittest::optional_sint64_extension_lite ));
+ EXPECT_EQ(107 , message.GetExtension(unittest::optional_fixed32_extension_lite ));
+ EXPECT_EQ(108 , message.GetExtension(unittest::optional_fixed64_extension_lite ));
+ EXPECT_EQ(109 , message.GetExtension(unittest::optional_sfixed32_extension_lite));
+ EXPECT_EQ(110 , message.GetExtension(unittest::optional_sfixed64_extension_lite));
+ EXPECT_EQ(111 , message.GetExtension(unittest::optional_float_extension_lite ));
+ EXPECT_EQ(112 , message.GetExtension(unittest::optional_double_extension_lite ));
+ EXPECT_EQ(true , message.GetExtension(unittest::optional_bool_extension_lite ));
+ EXPECT_EQ("115", message.GetExtension(unittest::optional_string_extension_lite ));
+ EXPECT_EQ("116", message.GetExtension(unittest::optional_bytes_extension_lite ));
+
+ EXPECT_EQ(117, message.GetExtension(unittest::optionalgroup_extension_lite ).a());
+ EXPECT_EQ(118, message.GetExtension(unittest::optional_nested_message_extension_lite ).bb());
+ EXPECT_EQ(119, message.GetExtension(unittest::optional_foreign_message_extension_lite ).c());
+ EXPECT_EQ(120, message.GetExtension(unittest::optional_import_message_extension_lite ).d());
+ EXPECT_EQ(126, message.GetExtension(unittest::optional_public_import_message_extension_lite).e());
+ EXPECT_EQ(127, message.GetExtension(unittest::optional_lazy_message_extension_lite ).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAZ , message.GetExtension(unittest::optional_nested_enum_extension_lite ));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAZ , message.GetExtension(unittest::optional_foreign_enum_extension_lite));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAZ, message.GetExtension(unittest::optional_import_enum_extension_lite ));
+
+
+ // -----------------------------------------------------------------
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed32_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed64_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_float_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_double_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bool_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bytes_extension_lite ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeatedgroup_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_message_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_message_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_message_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_lazy_message_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_enum_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_enum_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_enum_extension_lite ));
+
+
+ EXPECT_EQ(201 , message.GetExtension(unittest::repeated_int32_extension_lite , 0));
+ EXPECT_EQ(202 , message.GetExtension(unittest::repeated_int64_extension_lite , 0));
+ EXPECT_EQ(203 , message.GetExtension(unittest::repeated_uint32_extension_lite , 0));
+ EXPECT_EQ(204 , message.GetExtension(unittest::repeated_uint64_extension_lite , 0));
+ EXPECT_EQ(205 , message.GetExtension(unittest::repeated_sint32_extension_lite , 0));
+ EXPECT_EQ(206 , message.GetExtension(unittest::repeated_sint64_extension_lite , 0));
+ EXPECT_EQ(207 , message.GetExtension(unittest::repeated_fixed32_extension_lite , 0));
+ EXPECT_EQ(208 , message.GetExtension(unittest::repeated_fixed64_extension_lite , 0));
+ EXPECT_EQ(209 , message.GetExtension(unittest::repeated_sfixed32_extension_lite, 0));
+ EXPECT_EQ(210 , message.GetExtension(unittest::repeated_sfixed64_extension_lite, 0));
+ EXPECT_EQ(211 , message.GetExtension(unittest::repeated_float_extension_lite , 0));
+ EXPECT_EQ(212 , message.GetExtension(unittest::repeated_double_extension_lite , 0));
+ EXPECT_EQ(true , message.GetExtension(unittest::repeated_bool_extension_lite , 0));
+ EXPECT_EQ("215", message.GetExtension(unittest::repeated_string_extension_lite , 0));
+ EXPECT_EQ("216", message.GetExtension(unittest::repeated_bytes_extension_lite , 0));
+
+ EXPECT_EQ(217, message.GetExtension(unittest::repeatedgroup_extension_lite , 0).a());
+ EXPECT_EQ(218, message.GetExtension(unittest::repeated_nested_message_extension_lite , 0).bb());
+ EXPECT_EQ(219, message.GetExtension(unittest::repeated_foreign_message_extension_lite, 0).c());
+ EXPECT_EQ(220, message.GetExtension(unittest::repeated_import_message_extension_lite , 0).d());
+ EXPECT_EQ(227, message.GetExtension(unittest::repeated_lazy_message_extension_lite , 0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAR , message.GetExtension(unittest::repeated_nested_enum_extension_lite , 0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR , message.GetExtension(unittest::repeated_foreign_enum_extension_lite, 0));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAR, message.GetExtension(unittest::repeated_import_enum_extension_lite , 0));
+
+
+ EXPECT_EQ(301 , message.GetExtension(unittest::repeated_int32_extension_lite , 1));
+ EXPECT_EQ(302 , message.GetExtension(unittest::repeated_int64_extension_lite , 1));
+ EXPECT_EQ(303 , message.GetExtension(unittest::repeated_uint32_extension_lite , 1));
+ EXPECT_EQ(304 , message.GetExtension(unittest::repeated_uint64_extension_lite , 1));
+ EXPECT_EQ(305 , message.GetExtension(unittest::repeated_sint32_extension_lite , 1));
+ EXPECT_EQ(306 , message.GetExtension(unittest::repeated_sint64_extension_lite , 1));
+ EXPECT_EQ(307 , message.GetExtension(unittest::repeated_fixed32_extension_lite , 1));
+ EXPECT_EQ(308 , message.GetExtension(unittest::repeated_fixed64_extension_lite , 1));
+ EXPECT_EQ(309 , message.GetExtension(unittest::repeated_sfixed32_extension_lite, 1));
+ EXPECT_EQ(310 , message.GetExtension(unittest::repeated_sfixed64_extension_lite, 1));
+ EXPECT_EQ(311 , message.GetExtension(unittest::repeated_float_extension_lite , 1));
+ EXPECT_EQ(312 , message.GetExtension(unittest::repeated_double_extension_lite , 1));
+ EXPECT_EQ(false, message.GetExtension(unittest::repeated_bool_extension_lite , 1));
+ EXPECT_EQ("315", message.GetExtension(unittest::repeated_string_extension_lite , 1));
+ EXPECT_EQ("316", message.GetExtension(unittest::repeated_bytes_extension_lite , 1));
+
+ EXPECT_EQ(317, message.GetExtension(unittest::repeatedgroup_extension_lite , 1).a());
+ EXPECT_EQ(318, message.GetExtension(unittest::repeated_nested_message_extension_lite , 1).bb());
+ EXPECT_EQ(319, message.GetExtension(unittest::repeated_foreign_message_extension_lite, 1).c());
+ EXPECT_EQ(320, message.GetExtension(unittest::repeated_import_message_extension_lite , 1).d());
+ EXPECT_EQ(327, message.GetExtension(unittest::repeated_lazy_message_extension_lite , 1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAZ , message.GetExtension(unittest::repeated_nested_enum_extension_lite , 1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAZ , message.GetExtension(unittest::repeated_foreign_enum_extension_lite, 1));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAZ, message.GetExtension(unittest::repeated_import_enum_extension_lite , 1));
+
+
+ // -----------------------------------------------------------------
+
+ EXPECT_TRUE(message.HasExtension(unittest::default_int32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_int64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_uint32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_uint64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sint32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sint64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_fixed32_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_fixed64_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sfixed32_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::default_sfixed64_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::default_float_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_double_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_bool_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_string_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_bytes_extension_lite ));
+
+ EXPECT_TRUE(message.HasExtension(unittest::default_nested_enum_extension_lite ));
+ EXPECT_TRUE(message.HasExtension(unittest::default_foreign_enum_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::default_import_enum_extension_lite ));
+
+
+ EXPECT_EQ(401 , message.GetExtension(unittest::default_int32_extension_lite ));
+ EXPECT_EQ(402 , message.GetExtension(unittest::default_int64_extension_lite ));
+ EXPECT_EQ(403 , message.GetExtension(unittest::default_uint32_extension_lite ));
+ EXPECT_EQ(404 , message.GetExtension(unittest::default_uint64_extension_lite ));
+ EXPECT_EQ(405 , message.GetExtension(unittest::default_sint32_extension_lite ));
+ EXPECT_EQ(406 , message.GetExtension(unittest::default_sint64_extension_lite ));
+ EXPECT_EQ(407 , message.GetExtension(unittest::default_fixed32_extension_lite ));
+ EXPECT_EQ(408 , message.GetExtension(unittest::default_fixed64_extension_lite ));
+ EXPECT_EQ(409 , message.GetExtension(unittest::default_sfixed32_extension_lite));
+ EXPECT_EQ(410 , message.GetExtension(unittest::default_sfixed64_extension_lite));
+ EXPECT_EQ(411 , message.GetExtension(unittest::default_float_extension_lite ));
+ EXPECT_EQ(412 , message.GetExtension(unittest::default_double_extension_lite ));
+ EXPECT_EQ(false, message.GetExtension(unittest::default_bool_extension_lite ));
+ EXPECT_EQ("415", message.GetExtension(unittest::default_string_extension_lite ));
+ EXPECT_EQ("416", message.GetExtension(unittest::default_bytes_extension_lite ));
+
+ EXPECT_EQ(unittest::TestAllTypesLite::FOO , message.GetExtension(unittest::default_nested_enum_extension_lite ));
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO , message.GetExtension(unittest::default_foreign_enum_extension_lite));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_FOO, message.GetExtension(unittest::default_import_enum_extension_lite ));
+
+
+ EXPECT_TRUE(message.HasExtension(unittest::oneof_uint32_extension_lite));
+ EXPECT_TRUE(message.GetExtension(unittest::oneof_nested_message_extension_lite).has_bb());
+ EXPECT_TRUE(message.HasExtension(unittest::oneof_string_extension_lite));
+ EXPECT_TRUE(message.HasExtension(unittest::oneof_bytes_extension_lite));
+
+ EXPECT_EQ(601, message.GetExtension(unittest::oneof_uint32_extension_lite));
+ EXPECT_EQ(602, message.GetExtension(unittest::oneof_nested_message_extension_lite).bb());
+ EXPECT_EQ("603", message.GetExtension(unittest::oneof_string_extension_lite));
+ EXPECT_EQ("604", message.GetExtension(unittest::oneof_bytes_extension_lite));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectExtensionsClear(
+ const unittest::TestAllExtensionsLite& message) {
+ string serialized;
+ ASSERT_TRUE(message.SerializeToString(&serialized));
+ EXPECT_EQ("", serialized);
+ EXPECT_EQ(0, message.ByteSize());
+
+ // has_blah() should initially be false for all optional fields.
+ EXPECT_FALSE(message.HasExtension(unittest::optional_int32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_int64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_uint32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_uint64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sint32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sint64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_fixed32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_fixed64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sfixed32_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_sfixed64_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_float_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_double_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_bool_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_string_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_bytes_extension_lite ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::optionalgroup_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_nested_message_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_foreign_message_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_import_message_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_public_import_message_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_lazy_message_extension_lite ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::optional_nested_enum_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_foreign_enum_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::optional_import_enum_extension_lite ));
+
+
+ // Optional fields without defaults are set to zero or something like it.
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_int32_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_int64_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_uint32_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_uint64_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sint32_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sint64_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_fixed32_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_fixed64_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sfixed32_extension_lite));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_sfixed64_extension_lite));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_float_extension_lite ));
+ EXPECT_EQ(0 , message.GetExtension(unittest::optional_double_extension_lite ));
+ EXPECT_EQ(false, message.GetExtension(unittest::optional_bool_extension_lite ));
+ EXPECT_EQ("" , message.GetExtension(unittest::optional_string_extension_lite ));
+ EXPECT_EQ("" , message.GetExtension(unittest::optional_bytes_extension_lite ));
+
+ // Embedded messages should also be clear.
+ EXPECT_FALSE(message.GetExtension(unittest::optionalgroup_extension_lite ).has_a());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_nested_message_extension_lite ).has_bb());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_foreign_message_extension_lite ).has_c());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_import_message_extension_lite ).has_d());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_public_import_message_extension_lite).has_e());
+ EXPECT_FALSE(message.GetExtension(unittest::optional_lazy_message_extension_lite ).has_bb());
+
+ EXPECT_EQ(0, message.GetExtension(unittest::optionalgroup_extension_lite ).a());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_nested_message_extension_lite ).bb());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_foreign_message_extension_lite ).c());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_import_message_extension_lite ).d());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_public_import_message_extension_lite).e());
+ EXPECT_EQ(0, message.GetExtension(unittest::optional_lazy_message_extension_lite ).bb());
+
+ // Enums without defaults are set to the first value in the enum.
+ EXPECT_EQ(unittest::TestAllTypesLite::FOO , message.GetExtension(unittest::optional_nested_enum_extension_lite ));
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO , message.GetExtension(unittest::optional_foreign_enum_extension_lite));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_FOO, message.GetExtension(unittest::optional_import_enum_extension_lite ));
+
+
+ // Repeated fields are empty.
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_int32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_int64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_uint32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_uint64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sint32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sint64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_fixed32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_fixed64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sfixed32_extension_lite));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_sfixed64_extension_lite));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_float_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_double_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_bool_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_string_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_bytes_extension_lite ));
+
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeatedgroup_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_nested_message_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_foreign_message_extension_lite));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_import_message_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_lazy_message_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_nested_enum_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_foreign_enum_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::repeated_import_enum_extension_lite ));
+
+
+ // has_blah() should also be false for all default fields.
+ EXPECT_FALSE(message.HasExtension(unittest::default_int32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_int64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_uint32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_uint64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sint32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sint64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_fixed32_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_fixed64_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sfixed32_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::default_sfixed64_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::default_float_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_double_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_bool_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_string_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_bytes_extension_lite ));
+
+ EXPECT_FALSE(message.HasExtension(unittest::default_nested_enum_extension_lite ));
+ EXPECT_FALSE(message.HasExtension(unittest::default_foreign_enum_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::default_import_enum_extension_lite ));
+
+
+ // Fields with defaults have their default values (duh).
+ EXPECT_EQ( 41 , message.GetExtension(unittest::default_int32_extension_lite ));
+ EXPECT_EQ( 42 , message.GetExtension(unittest::default_int64_extension_lite ));
+ EXPECT_EQ( 43 , message.GetExtension(unittest::default_uint32_extension_lite ));
+ EXPECT_EQ( 44 , message.GetExtension(unittest::default_uint64_extension_lite ));
+ EXPECT_EQ(-45 , message.GetExtension(unittest::default_sint32_extension_lite ));
+ EXPECT_EQ( 46 , message.GetExtension(unittest::default_sint64_extension_lite ));
+ EXPECT_EQ( 47 , message.GetExtension(unittest::default_fixed32_extension_lite ));
+ EXPECT_EQ( 48 , message.GetExtension(unittest::default_fixed64_extension_lite ));
+ EXPECT_EQ( 49 , message.GetExtension(unittest::default_sfixed32_extension_lite));
+ EXPECT_EQ(-50 , message.GetExtension(unittest::default_sfixed64_extension_lite));
+ EXPECT_EQ( 51.5 , message.GetExtension(unittest::default_float_extension_lite ));
+ EXPECT_EQ( 52e3 , message.GetExtension(unittest::default_double_extension_lite ));
+ EXPECT_EQ(true , message.GetExtension(unittest::default_bool_extension_lite ));
+ EXPECT_EQ("hello", message.GetExtension(unittest::default_string_extension_lite ));
+ EXPECT_EQ("world", message.GetExtension(unittest::default_bytes_extension_lite ));
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAR , message.GetExtension(unittest::default_nested_enum_extension_lite ));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR , message.GetExtension(unittest::default_foreign_enum_extension_lite));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAR, message.GetExtension(unittest::default_import_enum_extension_lite ));
+
+
+ EXPECT_FALSE(message.HasExtension(unittest::oneof_uint32_extension_lite));
+ EXPECT_FALSE(message.GetExtension(unittest::oneof_nested_message_extension_lite).has_bb());
+ EXPECT_FALSE(message.HasExtension(unittest::oneof_string_extension_lite));
+ EXPECT_FALSE(message.HasExtension(unittest::oneof_bytes_extension_lite));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectRepeatedExtensionsModified(
+ const unittest::TestAllExtensionsLite& message) {
+ // ModifyRepeatedFields only sets the second repeated element of each
+ // field. In addition to verifying this, we also verify that the first
+ // element and size were *not* modified.
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_int64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_uint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_fixed64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed32_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_sfixed64_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_float_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_double_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bool_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_string_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_bytes_extension_lite ));
+
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeatedgroup_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_message_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_message_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_message_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_lazy_message_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_nested_enum_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_foreign_enum_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::repeated_import_enum_extension_lite ));
+
+
+ EXPECT_EQ(201 , message.GetExtension(unittest::repeated_int32_extension_lite , 0));
+ EXPECT_EQ(202 , message.GetExtension(unittest::repeated_int64_extension_lite , 0));
+ EXPECT_EQ(203 , message.GetExtension(unittest::repeated_uint32_extension_lite , 0));
+ EXPECT_EQ(204 , message.GetExtension(unittest::repeated_uint64_extension_lite , 0));
+ EXPECT_EQ(205 , message.GetExtension(unittest::repeated_sint32_extension_lite , 0));
+ EXPECT_EQ(206 , message.GetExtension(unittest::repeated_sint64_extension_lite , 0));
+ EXPECT_EQ(207 , message.GetExtension(unittest::repeated_fixed32_extension_lite , 0));
+ EXPECT_EQ(208 , message.GetExtension(unittest::repeated_fixed64_extension_lite , 0));
+ EXPECT_EQ(209 , message.GetExtension(unittest::repeated_sfixed32_extension_lite, 0));
+ EXPECT_EQ(210 , message.GetExtension(unittest::repeated_sfixed64_extension_lite, 0));
+ EXPECT_EQ(211 , message.GetExtension(unittest::repeated_float_extension_lite , 0));
+ EXPECT_EQ(212 , message.GetExtension(unittest::repeated_double_extension_lite , 0));
+ EXPECT_EQ(true , message.GetExtension(unittest::repeated_bool_extension_lite , 0));
+ EXPECT_EQ("215", message.GetExtension(unittest::repeated_string_extension_lite , 0));
+ EXPECT_EQ("216", message.GetExtension(unittest::repeated_bytes_extension_lite , 0));
+
+ EXPECT_EQ(217, message.GetExtension(unittest::repeatedgroup_extension_lite , 0).a());
+ EXPECT_EQ(218, message.GetExtension(unittest::repeated_nested_message_extension_lite , 0).bb());
+ EXPECT_EQ(219, message.GetExtension(unittest::repeated_foreign_message_extension_lite, 0).c());
+ EXPECT_EQ(220, message.GetExtension(unittest::repeated_import_message_extension_lite , 0).d());
+ EXPECT_EQ(227, message.GetExtension(unittest::repeated_lazy_message_extension_lite , 0).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::BAR , message.GetExtension(unittest::repeated_nested_enum_extension_lite , 0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR , message.GetExtension(unittest::repeated_foreign_enum_extension_lite, 0));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_BAR, message.GetExtension(unittest::repeated_import_enum_extension_lite , 0));
+
+
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(501 , message.GetExtension(unittest::repeated_int32_extension_lite , 1));
+ EXPECT_EQ(502 , message.GetExtension(unittest::repeated_int64_extension_lite , 1));
+ EXPECT_EQ(503 , message.GetExtension(unittest::repeated_uint32_extension_lite , 1));
+ EXPECT_EQ(504 , message.GetExtension(unittest::repeated_uint64_extension_lite , 1));
+ EXPECT_EQ(505 , message.GetExtension(unittest::repeated_sint32_extension_lite , 1));
+ EXPECT_EQ(506 , message.GetExtension(unittest::repeated_sint64_extension_lite , 1));
+ EXPECT_EQ(507 , message.GetExtension(unittest::repeated_fixed32_extension_lite , 1));
+ EXPECT_EQ(508 , message.GetExtension(unittest::repeated_fixed64_extension_lite , 1));
+ EXPECT_EQ(509 , message.GetExtension(unittest::repeated_sfixed32_extension_lite, 1));
+ EXPECT_EQ(510 , message.GetExtension(unittest::repeated_sfixed64_extension_lite, 1));
+ EXPECT_EQ(511 , message.GetExtension(unittest::repeated_float_extension_lite , 1));
+ EXPECT_EQ(512 , message.GetExtension(unittest::repeated_double_extension_lite , 1));
+ EXPECT_EQ(true , message.GetExtension(unittest::repeated_bool_extension_lite , 1));
+ EXPECT_EQ("515", message.GetExtension(unittest::repeated_string_extension_lite , 1));
+ EXPECT_EQ("516", message.GetExtension(unittest::repeated_bytes_extension_lite , 1));
+
+ EXPECT_EQ(517, message.GetExtension(unittest::repeatedgroup_extension_lite , 1).a());
+ EXPECT_EQ(518, message.GetExtension(unittest::repeated_nested_message_extension_lite , 1).bb());
+ EXPECT_EQ(519, message.GetExtension(unittest::repeated_foreign_message_extension_lite, 1).c());
+ EXPECT_EQ(520, message.GetExtension(unittest::repeated_import_message_extension_lite , 1).d());
+ EXPECT_EQ(527, message.GetExtension(unittest::repeated_lazy_message_extension_lite , 1).bb());
+
+ EXPECT_EQ(unittest::TestAllTypesLite::FOO , message.GetExtension(unittest::repeated_nested_enum_extension_lite , 1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO , message.GetExtension(unittest::repeated_foreign_enum_extension_lite, 1));
+ EXPECT_EQ(unittest_import::IMPORT_LITE_FOO, message.GetExtension(unittest::repeated_import_enum_extension_lite , 1));
+
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::SetPackedExtensions(
+ unittest::TestPackedExtensionsLite* message) {
+ message->AddExtension(unittest::packed_int32_extension_lite , 601);
+ message->AddExtension(unittest::packed_int64_extension_lite , 602);
+ message->AddExtension(unittest::packed_uint32_extension_lite , 603);
+ message->AddExtension(unittest::packed_uint64_extension_lite , 604);
+ message->AddExtension(unittest::packed_sint32_extension_lite , 605);
+ message->AddExtension(unittest::packed_sint64_extension_lite , 606);
+ message->AddExtension(unittest::packed_fixed32_extension_lite , 607);
+ message->AddExtension(unittest::packed_fixed64_extension_lite , 608);
+ message->AddExtension(unittest::packed_sfixed32_extension_lite, 609);
+ message->AddExtension(unittest::packed_sfixed64_extension_lite, 610);
+ message->AddExtension(unittest::packed_float_extension_lite , 611);
+ message->AddExtension(unittest::packed_double_extension_lite , 612);
+ message->AddExtension(unittest::packed_bool_extension_lite , true);
+ message->AddExtension(unittest::packed_enum_extension_lite, unittest::FOREIGN_LITE_BAR);
+ // add a second one of each field
+ message->AddExtension(unittest::packed_int32_extension_lite , 701);
+ message->AddExtension(unittest::packed_int64_extension_lite , 702);
+ message->AddExtension(unittest::packed_uint32_extension_lite , 703);
+ message->AddExtension(unittest::packed_uint64_extension_lite , 704);
+ message->AddExtension(unittest::packed_sint32_extension_lite , 705);
+ message->AddExtension(unittest::packed_sint64_extension_lite , 706);
+ message->AddExtension(unittest::packed_fixed32_extension_lite , 707);
+ message->AddExtension(unittest::packed_fixed64_extension_lite , 708);
+ message->AddExtension(unittest::packed_sfixed32_extension_lite, 709);
+ message->AddExtension(unittest::packed_sfixed64_extension_lite, 710);
+ message->AddExtension(unittest::packed_float_extension_lite , 711);
+ message->AddExtension(unittest::packed_double_extension_lite , 712);
+ message->AddExtension(unittest::packed_bool_extension_lite , false);
+ message->AddExtension(unittest::packed_enum_extension_lite, unittest::FOREIGN_LITE_BAZ);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ModifyPackedExtensions(
+ unittest::TestPackedExtensionsLite* message) {
+ message->SetExtension(unittest::packed_int32_extension_lite , 1, 801);
+ message->SetExtension(unittest::packed_int64_extension_lite , 1, 802);
+ message->SetExtension(unittest::packed_uint32_extension_lite , 1, 803);
+ message->SetExtension(unittest::packed_uint64_extension_lite , 1, 804);
+ message->SetExtension(unittest::packed_sint32_extension_lite , 1, 805);
+ message->SetExtension(unittest::packed_sint64_extension_lite , 1, 806);
+ message->SetExtension(unittest::packed_fixed32_extension_lite , 1, 807);
+ message->SetExtension(unittest::packed_fixed64_extension_lite , 1, 808);
+ message->SetExtension(unittest::packed_sfixed32_extension_lite, 1, 809);
+ message->SetExtension(unittest::packed_sfixed64_extension_lite, 1, 810);
+ message->SetExtension(unittest::packed_float_extension_lite , 1, 811);
+ message->SetExtension(unittest::packed_double_extension_lite , 1, 812);
+ message->SetExtension(unittest::packed_bool_extension_lite , 1, true);
+ message->SetExtension(unittest::packed_enum_extension_lite , 1,
+ unittest::FOREIGN_LITE_FOO);
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectPackedExtensionsSet(
+ const unittest::TestPackedExtensionsLite& message) {
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed32_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed64_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_float_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_double_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_bool_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_enum_extension_lite ));
+
+ EXPECT_EQ(601 , message.GetExtension(unittest::packed_int32_extension_lite , 0));
+ EXPECT_EQ(602 , message.GetExtension(unittest::packed_int64_extension_lite , 0));
+ EXPECT_EQ(603 , message.GetExtension(unittest::packed_uint32_extension_lite , 0));
+ EXPECT_EQ(604 , message.GetExtension(unittest::packed_uint64_extension_lite , 0));
+ EXPECT_EQ(605 , message.GetExtension(unittest::packed_sint32_extension_lite , 0));
+ EXPECT_EQ(606 , message.GetExtension(unittest::packed_sint64_extension_lite , 0));
+ EXPECT_EQ(607 , message.GetExtension(unittest::packed_fixed32_extension_lite , 0));
+ EXPECT_EQ(608 , message.GetExtension(unittest::packed_fixed64_extension_lite , 0));
+ EXPECT_EQ(609 , message.GetExtension(unittest::packed_sfixed32_extension_lite, 0));
+ EXPECT_EQ(610 , message.GetExtension(unittest::packed_sfixed64_extension_lite, 0));
+ EXPECT_EQ(611 , message.GetExtension(unittest::packed_float_extension_lite , 0));
+ EXPECT_EQ(612 , message.GetExtension(unittest::packed_double_extension_lite , 0));
+ EXPECT_EQ(true , message.GetExtension(unittest::packed_bool_extension_lite , 0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR,
+ message.GetExtension(unittest::packed_enum_extension_lite, 0));
+ EXPECT_EQ(701 , message.GetExtension(unittest::packed_int32_extension_lite , 1));
+ EXPECT_EQ(702 , message.GetExtension(unittest::packed_int64_extension_lite , 1));
+ EXPECT_EQ(703 , message.GetExtension(unittest::packed_uint32_extension_lite , 1));
+ EXPECT_EQ(704 , message.GetExtension(unittest::packed_uint64_extension_lite , 1));
+ EXPECT_EQ(705 , message.GetExtension(unittest::packed_sint32_extension_lite , 1));
+ EXPECT_EQ(706 , message.GetExtension(unittest::packed_sint64_extension_lite , 1));
+ EXPECT_EQ(707 , message.GetExtension(unittest::packed_fixed32_extension_lite , 1));
+ EXPECT_EQ(708 , message.GetExtension(unittest::packed_fixed64_extension_lite , 1));
+ EXPECT_EQ(709 , message.GetExtension(unittest::packed_sfixed32_extension_lite, 1));
+ EXPECT_EQ(710 , message.GetExtension(unittest::packed_sfixed64_extension_lite, 1));
+ EXPECT_EQ(711 , message.GetExtension(unittest::packed_float_extension_lite , 1));
+ EXPECT_EQ(712 , message.GetExtension(unittest::packed_double_extension_lite , 1));
+ EXPECT_EQ(false, message.GetExtension(unittest::packed_bool_extension_lite , 1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAZ,
+ message.GetExtension(unittest::packed_enum_extension_lite, 1));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectPackedExtensionsClear(
+ const unittest::TestPackedExtensionsLite& message) {
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_int32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_int64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_uint32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_uint64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sint32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sint64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_fixed32_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_fixed64_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sfixed32_extension_lite));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_sfixed64_extension_lite));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_float_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_double_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_bool_extension_lite ));
+ EXPECT_EQ(0, message.ExtensionSize(unittest::packed_enum_extension_lite ));
+}
+
+// -------------------------------------------------------------------
+
+void TestUtilLite::ExpectPackedExtensionsModified(
+ const unittest::TestPackedExtensionsLite& message) {
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_int64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_uint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sint64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed32_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_fixed64_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed32_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_sfixed64_extension_lite));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_float_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_double_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_bool_extension_lite ));
+ ASSERT_EQ(2, message.ExtensionSize(unittest::packed_enum_extension_lite ));
+ EXPECT_EQ(601 , message.GetExtension(unittest::packed_int32_extension_lite , 0));
+ EXPECT_EQ(602 , message.GetExtension(unittest::packed_int64_extension_lite , 0));
+ EXPECT_EQ(603 , message.GetExtension(unittest::packed_uint32_extension_lite , 0));
+ EXPECT_EQ(604 , message.GetExtension(unittest::packed_uint64_extension_lite , 0));
+ EXPECT_EQ(605 , message.GetExtension(unittest::packed_sint32_extension_lite , 0));
+ EXPECT_EQ(606 , message.GetExtension(unittest::packed_sint64_extension_lite , 0));
+ EXPECT_EQ(607 , message.GetExtension(unittest::packed_fixed32_extension_lite , 0));
+ EXPECT_EQ(608 , message.GetExtension(unittest::packed_fixed64_extension_lite , 0));
+ EXPECT_EQ(609 , message.GetExtension(unittest::packed_sfixed32_extension_lite, 0));
+ EXPECT_EQ(610 , message.GetExtension(unittest::packed_sfixed64_extension_lite, 0));
+ EXPECT_EQ(611 , message.GetExtension(unittest::packed_float_extension_lite , 0));
+ EXPECT_EQ(612 , message.GetExtension(unittest::packed_double_extension_lite , 0));
+ EXPECT_EQ(true , message.GetExtension(unittest::packed_bool_extension_lite , 0));
+ EXPECT_EQ(unittest::FOREIGN_LITE_BAR,
+ message.GetExtension(unittest::packed_enum_extension_lite, 0));
+
+ // Actually verify the second (modified) elements now.
+ EXPECT_EQ(801 , message.GetExtension(unittest::packed_int32_extension_lite , 1));
+ EXPECT_EQ(802 , message.GetExtension(unittest::packed_int64_extension_lite , 1));
+ EXPECT_EQ(803 , message.GetExtension(unittest::packed_uint32_extension_lite , 1));
+ EXPECT_EQ(804 , message.GetExtension(unittest::packed_uint64_extension_lite , 1));
+ EXPECT_EQ(805 , message.GetExtension(unittest::packed_sint32_extension_lite , 1));
+ EXPECT_EQ(806 , message.GetExtension(unittest::packed_sint64_extension_lite , 1));
+ EXPECT_EQ(807 , message.GetExtension(unittest::packed_fixed32_extension_lite , 1));
+ EXPECT_EQ(808 , message.GetExtension(unittest::packed_fixed64_extension_lite , 1));
+ EXPECT_EQ(809 , message.GetExtension(unittest::packed_sfixed32_extension_lite, 1));
+ EXPECT_EQ(810 , message.GetExtension(unittest::packed_sfixed64_extension_lite, 1));
+ EXPECT_EQ(811 , message.GetExtension(unittest::packed_float_extension_lite , 1));
+ EXPECT_EQ(812 , message.GetExtension(unittest::packed_double_extension_lite , 1));
+ EXPECT_EQ(true , message.GetExtension(unittest::packed_bool_extension_lite , 1));
+ EXPECT_EQ(unittest::FOREIGN_LITE_FOO,
+ message.GetExtension(unittest::packed_enum_extension_lite, 1));
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.h
new file mode 100644
index 0000000000..47a2269d36
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/test_util_lite.h
@@ -0,0 +1,101 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_TEST_UTIL_LITE_H__
+#define GOOGLE_PROTOBUF_TEST_UTIL_LITE_H__
+
+#include <google/protobuf/unittest_lite.pb.h>
+
+namespace google {
+namespace protobuf {
+
+namespace unittest = protobuf_unittest;
+namespace unittest_import = protobuf_unittest_import;
+
+class TestUtilLite {
+ public:
+ // Set every field in the message to a unique value.
+ static void SetAllFields(unittest::TestAllTypesLite* message);
+ static void SetAllExtensions(unittest::TestAllExtensionsLite* message);
+ static void SetPackedFields(unittest::TestPackedTypesLite* message);
+ static void SetPackedExtensions(unittest::TestPackedExtensionsLite* message);
+
+ // Use the repeated versions of the set_*() accessors to modify all the
+ // repeated fields of the message (which should already have been
+ // initialized with Set*Fields()). Set*Fields() itself only tests
+ // the add_*() accessors.
+ static void ModifyRepeatedFields(unittest::TestAllTypesLite* message);
+ static void ModifyRepeatedExtensions(
+ unittest::TestAllExtensionsLite* message);
+ static void ModifyPackedFields(unittest::TestPackedTypesLite* message);
+ static void ModifyPackedExtensions(
+ unittest::TestPackedExtensionsLite* message);
+
+ // Check that all fields have the values that they should have after
+ // Set*Fields() is called.
+ static void ExpectAllFieldsSet(const unittest::TestAllTypesLite& message);
+ static void ExpectAllExtensionsSet(
+ const unittest::TestAllExtensionsLite& message);
+ static void ExpectPackedFieldsSet(
+ const unittest::TestPackedTypesLite& message);
+ static void ExpectPackedExtensionsSet(
+ const unittest::TestPackedExtensionsLite& message);
+
+ // Expect that the message is modified as would be expected from
+ // Modify*Fields().
+ static void ExpectRepeatedFieldsModified(
+ const unittest::TestAllTypesLite& message);
+ static void ExpectRepeatedExtensionsModified(
+ const unittest::TestAllExtensionsLite& message);
+ static void ExpectPackedFieldsModified(
+ const unittest::TestPackedTypesLite& message);
+ static void ExpectPackedExtensionsModified(
+ const unittest::TestPackedExtensionsLite& message);
+
+ // Check that all fields have their default values.
+ static void ExpectClear(const unittest::TestAllTypesLite& message);
+ static void ExpectExtensionsClear(
+ const unittest::TestAllExtensionsLite& message);
+ static void ExpectPackedClear(const unittest::TestPackedTypesLite& message);
+ static void ExpectPackedExtensionsClear(
+ const unittest::TestPackedExtensionsLite& message);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TestUtilLite);
+};
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_TEST_UTIL_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/bad_utf8_string b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/bad_utf8_string
new file mode 100644
index 0000000000..a1337ec689
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/bad_utf8_string
@@ -0,0 +1 @@
+rÿ \ No newline at end of file
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message
new file mode 100644
index 0000000000..0b7e6552c6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message
Binary files differ
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_maps b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_maps
new file mode 100644
index 0000000000..c70a4d7cde
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_maps
Binary files differ
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_oneof_implemented b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_oneof_implemented
new file mode 100644
index 0000000000..b48c898526
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_oneof_implemented
Binary files differ
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_proto3 b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_proto3
new file mode 100644
index 0000000000..bd646a0dc8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_message_proto3
Binary files differ
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_packed_fields_message b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_packed_fields_message
new file mode 100644
index 0000000000..ee28d38830
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/golden_packed_fields_message
Binary files differ
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/map_test_data.txt b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/map_test_data.txt
new file mode 100644
index 0000000000..bc2723214a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/map_test_data.txt
@@ -0,0 +1,140 @@
+map_int32_int32 {
+ key: 0
+ value: 0
+}
+map_int32_int32 {
+ key: 1
+ value: 1
+}
+map_int64_int64 {
+ key: 0
+ value: 0
+}
+map_int64_int64 {
+ key: 1
+ value: 1
+}
+map_uint32_uint32 {
+ key: 0
+ value: 0
+}
+map_uint32_uint32 {
+ key: 1
+ value: 1
+}
+map_uint64_uint64 {
+ key: 0
+ value: 0
+}
+map_uint64_uint64 {
+ key: 1
+ value: 1
+}
+map_sint32_sint32 {
+ key: 0
+ value: 0
+}
+map_sint32_sint32 {
+ key: 1
+ value: 1
+}
+map_sint64_sint64 {
+ key: 0
+ value: 0
+}
+map_sint64_sint64 {
+ key: 1
+ value: 1
+}
+map_fixed32_fixed32 {
+ key: 0
+ value: 0
+}
+map_fixed32_fixed32 {
+ key: 1
+ value: 1
+}
+map_fixed64_fixed64 {
+ key: 0
+ value: 0
+}
+map_fixed64_fixed64 {
+ key: 1
+ value: 1
+}
+map_sfixed32_sfixed32 {
+ key: 0
+ value: 0
+}
+map_sfixed32_sfixed32 {
+ key: 1
+ value: 1
+}
+map_sfixed64_sfixed64 {
+ key: 0
+ value: 0
+}
+map_sfixed64_sfixed64 {
+ key: 1
+ value: 1
+}
+map_int32_float {
+ key: 0
+ value: 0
+}
+map_int32_float {
+ key: 1
+ value: 1
+}
+map_int32_double {
+ key: 0
+ value: 0
+}
+map_int32_double {
+ key: 1
+ value: 1
+}
+map_bool_bool {
+ key: false
+ value: false
+}
+map_bool_bool {
+ key: true
+ value: true
+}
+map_string_string {
+ key: "0"
+ value: "0"
+}
+map_string_string {
+ key: "1"
+ value: "1"
+}
+map_int32_bytes {
+ key: 0
+ value: "0"
+}
+map_int32_bytes {
+ key: 1
+ value: "1"
+}
+map_int32_enum {
+ key: 0
+ value: MAP_ENUM_BAR
+}
+map_int32_enum {
+ key: 1
+ value: MAP_ENUM_BAZ
+}
+map_int32_foreign_message {
+ key: 0
+ value {
+ c: 0
+ }
+}
+map_int32_foreign_message {
+ key: 1
+ value {
+ c: 1
+ }
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data.txt b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data.txt
new file mode 100644
index 0000000000..7a874b54cd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data.txt
@@ -0,0 +1,134 @@
+optional_int32: 101
+optional_int64: 102
+optional_uint32: 103
+optional_uint64: 104
+optional_sint32: 105
+optional_sint64: 106
+optional_fixed32: 107
+optional_fixed64: 108
+optional_sfixed32: 109
+optional_sfixed64: 110
+optional_float: 111
+optional_double: 112
+optional_bool: true
+optional_string: "115"
+optional_bytes: "116"
+OptionalGroup {
+ a: 117
+}
+optional_nested_message {
+ bb: 118
+}
+optional_foreign_message {
+ c: 119
+}
+optional_import_message {
+ d: 120
+}
+optional_nested_enum: BAZ
+optional_foreign_enum: FOREIGN_BAZ
+optional_import_enum: IMPORT_BAZ
+optional_string_piece: "124"
+optional_cord: "125"
+optional_public_import_message {
+ e: 126
+}
+optional_lazy_message {
+ bb: 127
+}
+repeated_int32: 201
+repeated_int32: 301
+repeated_int64: 202
+repeated_int64: 302
+repeated_uint32: 203
+repeated_uint32: 303
+repeated_uint64: 204
+repeated_uint64: 304
+repeated_sint32: 205
+repeated_sint32: 305
+repeated_sint64: 206
+repeated_sint64: 306
+repeated_fixed32: 207
+repeated_fixed32: 307
+repeated_fixed64: 208
+repeated_fixed64: 308
+repeated_sfixed32: 209
+repeated_sfixed32: 309
+repeated_sfixed64: 210
+repeated_sfixed64: 310
+repeated_float: 211
+repeated_float: 311
+repeated_double: 212
+repeated_double: 312
+repeated_bool: true
+repeated_bool: false
+repeated_string: "215"
+repeated_string: "315"
+repeated_bytes: "216"
+repeated_bytes: "316"
+RepeatedGroup {
+ a: 217
+}
+RepeatedGroup {
+ a: 317
+}
+repeated_nested_message {
+ bb: 218
+}
+repeated_nested_message {
+ bb: 318
+}
+repeated_foreign_message {
+ c: 219
+}
+repeated_foreign_message {
+ c: 319
+}
+repeated_import_message {
+ d: 220
+}
+repeated_import_message {
+ d: 320
+}
+repeated_nested_enum: BAR
+repeated_nested_enum: BAZ
+repeated_foreign_enum: FOREIGN_BAR
+repeated_foreign_enum: FOREIGN_BAZ
+repeated_import_enum: IMPORT_BAR
+repeated_import_enum: IMPORT_BAZ
+repeated_string_piece: "224"
+repeated_string_piece: "324"
+repeated_cord: "225"
+repeated_cord: "325"
+repeated_lazy_message {
+ bb: 227
+}
+repeated_lazy_message {
+ bb: 327
+}
+default_int32: 401
+default_int64: 402
+default_uint32: 403
+default_uint64: 404
+default_sint32: 405
+default_sint64: 406
+default_fixed32: 407
+default_fixed64: 408
+default_sfixed32: 409
+default_sfixed64: 410
+default_float: 411
+default_double: 412
+default_bool: false
+default_string: "415"
+default_bytes: "416"
+default_nested_enum: FOO
+default_foreign_enum: FOREIGN_FOO
+default_import_enum: IMPORT_FOO
+default_string_piece: "424"
+default_cord: "425"
+oneof_uint32: 601
+oneof_nested_message {
+ bb: 602
+}
+oneof_string: "603"
+oneof_bytes: "604"
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_oneof_implemented.txt b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_oneof_implemented.txt
new file mode 100644
index 0000000000..ec95e1e81a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_oneof_implemented.txt
@@ -0,0 +1,129 @@
+optional_int32: 101
+optional_int64: 102
+optional_uint32: 103
+optional_uint64: 104
+optional_sint32: 105
+optional_sint64: 106
+optional_fixed32: 107
+optional_fixed64: 108
+optional_sfixed32: 109
+optional_sfixed64: 110
+optional_float: 111
+optional_double: 112
+optional_bool: true
+optional_string: "115"
+optional_bytes: "116"
+OptionalGroup {
+ a: 117
+}
+optional_nested_message {
+ bb: 118
+}
+optional_foreign_message {
+ c: 119
+}
+optional_import_message {
+ d: 120
+}
+optional_nested_enum: BAZ
+optional_foreign_enum: FOREIGN_BAZ
+optional_import_enum: IMPORT_BAZ
+optional_string_piece: "124"
+optional_cord: "125"
+optional_public_import_message {
+ e: 126
+}
+optional_lazy_message {
+ bb: 127
+}
+repeated_int32: 201
+repeated_int32: 301
+repeated_int64: 202
+repeated_int64: 302
+repeated_uint32: 203
+repeated_uint32: 303
+repeated_uint64: 204
+repeated_uint64: 304
+repeated_sint32: 205
+repeated_sint32: 305
+repeated_sint64: 206
+repeated_sint64: 306
+repeated_fixed32: 207
+repeated_fixed32: 307
+repeated_fixed64: 208
+repeated_fixed64: 308
+repeated_sfixed32: 209
+repeated_sfixed32: 309
+repeated_sfixed64: 210
+repeated_sfixed64: 310
+repeated_float: 211
+repeated_float: 311
+repeated_double: 212
+repeated_double: 312
+repeated_bool: true
+repeated_bool: false
+repeated_string: "215"
+repeated_string: "315"
+repeated_bytes: "216"
+repeated_bytes: "316"
+RepeatedGroup {
+ a: 217
+}
+RepeatedGroup {
+ a: 317
+}
+repeated_nested_message {
+ bb: 218
+}
+repeated_nested_message {
+ bb: 318
+}
+repeated_foreign_message {
+ c: 219
+}
+repeated_foreign_message {
+ c: 319
+}
+repeated_import_message {
+ d: 220
+}
+repeated_import_message {
+ d: 320
+}
+repeated_nested_enum: BAR
+repeated_nested_enum: BAZ
+repeated_foreign_enum: FOREIGN_BAR
+repeated_foreign_enum: FOREIGN_BAZ
+repeated_import_enum: IMPORT_BAR
+repeated_import_enum: IMPORT_BAZ
+repeated_string_piece: "224"
+repeated_string_piece: "324"
+repeated_cord: "225"
+repeated_cord: "325"
+repeated_lazy_message {
+ bb: 227
+}
+repeated_lazy_message {
+ bb: 327
+}
+default_int32: 401
+default_int64: 402
+default_uint32: 403
+default_uint64: 404
+default_sint32: 405
+default_sint64: 406
+default_fixed32: 407
+default_fixed64: 408
+default_sfixed32: 409
+default_sfixed64: 410
+default_float: 411
+default_double: 412
+default_bool: false
+default_string: "415"
+default_bytes: "416"
+default_nested_enum: FOO
+default_foreign_enum: FOREIGN_FOO
+default_import_enum: IMPORT_FOO
+default_string_piece: "424"
+default_cord: "425"
+oneof_bytes: "604"
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy.txt b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy.txt
new file mode 100644
index 0000000000..e1011ebf15
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy.txt
@@ -0,0 +1,134 @@
+optional_int32: 101
+optional_int64: 102
+optional_uint32: 103
+optional_uint64: 104
+optional_sint32: 105
+optional_sint64: 106
+optional_fixed32: 107
+optional_fixed64: 108
+optional_sfixed32: 109
+optional_sfixed64: 110
+optional_float: 111
+optional_double: 112
+optional_bool: true
+optional_string: "115"
+optional_bytes: "116"
+OptionalGroup <
+ a: 117
+>
+optional_nested_message <
+ bb: 118
+>
+optional_foreign_message <
+ c: 119
+>
+optional_import_message <
+ d: 120
+>
+optional_nested_enum: BAZ
+optional_foreign_enum: FOREIGN_BAZ
+optional_import_enum: IMPORT_BAZ
+optional_string_piece: "124"
+optional_cord: "125"
+optional_public_import_message <
+ e: 126
+>
+optional_lazy_message <
+ bb: 127
+>
+repeated_int32: 201
+repeated_int32: 301
+repeated_int64: 202
+repeated_int64: 302
+repeated_uint32: 203
+repeated_uint32: 303
+repeated_uint64: 204
+repeated_uint64: 304
+repeated_sint32: 205
+repeated_sint32: 305
+repeated_sint64: 206
+repeated_sint64: 306
+repeated_fixed32: 207
+repeated_fixed32: 307
+repeated_fixed64: 208
+repeated_fixed64: 308
+repeated_sfixed32: 209
+repeated_sfixed32: 309
+repeated_sfixed64: 210
+repeated_sfixed64: 310
+repeated_float: 211
+repeated_float: 311
+repeated_double: 212
+repeated_double: 312
+repeated_bool: true
+repeated_bool: false
+repeated_string: "215"
+repeated_string: "315"
+repeated_bytes: "216"
+repeated_bytes: "316"
+RepeatedGroup <
+ a: 217
+>
+RepeatedGroup <
+ a: 317
+>
+repeated_nested_message <
+ bb: 218
+>
+repeated_nested_message <
+ bb: 318
+>
+repeated_foreign_message <
+ c: 219
+>
+repeated_foreign_message <
+ c: 319
+>
+repeated_import_message <
+ d: 220
+>
+repeated_import_message <
+ d: 320
+>
+repeated_nested_enum: BAR
+repeated_nested_enum: BAZ
+repeated_foreign_enum: FOREIGN_BAR
+repeated_foreign_enum: FOREIGN_BAZ
+repeated_import_enum: IMPORT_BAR
+repeated_import_enum: IMPORT_BAZ
+repeated_string_piece: "224"
+repeated_string_piece: "324"
+repeated_cord: "225"
+repeated_cord: "325"
+repeated_lazy_message <
+ bb: 227
+>
+repeated_lazy_message <
+ bb: 327
+>
+default_int32: 401
+default_int64: 402
+default_uint32: 403
+default_uint64: 404
+default_sint32: 405
+default_sint64: 406
+default_fixed32: 407
+default_fixed64: 408
+default_sfixed32: 409
+default_sfixed64: 410
+default_float: 411
+default_double: 412
+default_bool: false
+default_string: "415"
+default_bytes: "416"
+default_nested_enum: FOO
+default_foreign_enum: FOREIGN_FOO
+default_import_enum: IMPORT_FOO
+default_string_piece: "424"
+default_cord: "425"
+oneof_uint32: 601
+oneof_nested_message <
+ bb: 602
+>
+oneof_string: "603"
+oneof_bytes: "604"
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy_oneof.txt b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy_oneof.txt
new file mode 100644
index 0000000000..95109f62ab
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_data_pointy_oneof.txt
@@ -0,0 +1,129 @@
+optional_int32: 101
+optional_int64: 102
+optional_uint32: 103
+optional_uint64: 104
+optional_sint32: 105
+optional_sint64: 106
+optional_fixed32: 107
+optional_fixed64: 108
+optional_sfixed32: 109
+optional_sfixed64: 110
+optional_float: 111
+optional_double: 112
+optional_bool: true
+optional_string: "115"
+optional_bytes: "116"
+OptionalGroup <
+ a: 117
+>
+optional_nested_message <
+ bb: 118
+>
+optional_foreign_message <
+ c: 119
+>
+optional_import_message <
+ d: 120
+>
+optional_nested_enum: BAZ
+optional_foreign_enum: FOREIGN_BAZ
+optional_import_enum: IMPORT_BAZ
+optional_string_piece: "124"
+optional_cord: "125"
+optional_public_import_message <
+ e: 126
+>
+optional_lazy_message <
+ bb: 127
+>
+repeated_int32: 201
+repeated_int32: 301
+repeated_int64: 202
+repeated_int64: 302
+repeated_uint32: 203
+repeated_uint32: 303
+repeated_uint64: 204
+repeated_uint64: 304
+repeated_sint32: 205
+repeated_sint32: 305
+repeated_sint64: 206
+repeated_sint64: 306
+repeated_fixed32: 207
+repeated_fixed32: 307
+repeated_fixed64: 208
+repeated_fixed64: 308
+repeated_sfixed32: 209
+repeated_sfixed32: 309
+repeated_sfixed64: 210
+repeated_sfixed64: 310
+repeated_float: 211
+repeated_float: 311
+repeated_double: 212
+repeated_double: 312
+repeated_bool: true
+repeated_bool: false
+repeated_string: "215"
+repeated_string: "315"
+repeated_bytes: "216"
+repeated_bytes: "316"
+RepeatedGroup <
+ a: 217
+>
+RepeatedGroup <
+ a: 317
+>
+repeated_nested_message <
+ bb: 218
+>
+repeated_nested_message <
+ bb: 318
+>
+repeated_foreign_message <
+ c: 219
+>
+repeated_foreign_message <
+ c: 319
+>
+repeated_import_message <
+ d: 220
+>
+repeated_import_message <
+ d: 320
+>
+repeated_nested_enum: BAR
+repeated_nested_enum: BAZ
+repeated_foreign_enum: FOREIGN_BAR
+repeated_foreign_enum: FOREIGN_BAZ
+repeated_import_enum: IMPORT_BAR
+repeated_import_enum: IMPORT_BAZ
+repeated_string_piece: "224"
+repeated_string_piece: "324"
+repeated_cord: "225"
+repeated_cord: "325"
+repeated_lazy_message <
+ bb: 227
+>
+repeated_lazy_message <
+ bb: 327
+>
+default_int32: 401
+default_int64: 402
+default_uint32: 403
+default_uint64: 404
+default_sint32: 405
+default_sint64: 406
+default_fixed32: 407
+default_fixed64: 408
+default_sfixed32: 409
+default_sfixed64: 410
+default_float: 411
+default_double: 412
+default_bool: false
+default_string: "415"
+default_bytes: "416"
+default_nested_enum: FOO
+default_foreign_enum: FOREIGN_FOO
+default_import_enum: IMPORT_FOO
+default_string_piece: "424"
+default_cord: "425"
+oneof_bytes: "604"
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data.txt b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data.txt
new file mode 100644
index 0000000000..8c8b1eb4d8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data.txt
@@ -0,0 +1,134 @@
+[protobuf_unittest.optional_int32_extension]: 101
+[protobuf_unittest.optional_int64_extension]: 102
+[protobuf_unittest.optional_uint32_extension]: 103
+[protobuf_unittest.optional_uint64_extension]: 104
+[protobuf_unittest.optional_sint32_extension]: 105
+[protobuf_unittest.optional_sint64_extension]: 106
+[protobuf_unittest.optional_fixed32_extension]: 107
+[protobuf_unittest.optional_fixed64_extension]: 108
+[protobuf_unittest.optional_sfixed32_extension]: 109
+[protobuf_unittest.optional_sfixed64_extension]: 110
+[protobuf_unittest.optional_float_extension]: 111
+[protobuf_unittest.optional_double_extension]: 112
+[protobuf_unittest.optional_bool_extension]: true
+[protobuf_unittest.optional_string_extension]: "115"
+[protobuf_unittest.optional_bytes_extension]: "116"
+[protobuf_unittest.optionalgroup_extension] {
+ a: 117
+}
+[protobuf_unittest.optional_nested_message_extension] {
+ bb: 118
+}
+[protobuf_unittest.optional_foreign_message_extension] {
+ c: 119
+}
+[protobuf_unittest.optional_import_message_extension] {
+ d: 120
+}
+[protobuf_unittest.optional_nested_enum_extension]: BAZ
+[protobuf_unittest.optional_foreign_enum_extension]: FOREIGN_BAZ
+[protobuf_unittest.optional_import_enum_extension]: IMPORT_BAZ
+[protobuf_unittest.optional_string_piece_extension]: "124"
+[protobuf_unittest.optional_cord_extension]: "125"
+[protobuf_unittest.optional_public_import_message_extension] {
+ e: 126
+}
+[protobuf_unittest.optional_lazy_message_extension] {
+ bb: 127
+}
+[protobuf_unittest.repeated_int32_extension]: 201
+[protobuf_unittest.repeated_int32_extension]: 301
+[protobuf_unittest.repeated_int64_extension]: 202
+[protobuf_unittest.repeated_int64_extension]: 302
+[protobuf_unittest.repeated_uint32_extension]: 203
+[protobuf_unittest.repeated_uint32_extension]: 303
+[protobuf_unittest.repeated_uint64_extension]: 204
+[protobuf_unittest.repeated_uint64_extension]: 304
+[protobuf_unittest.repeated_sint32_extension]: 205
+[protobuf_unittest.repeated_sint32_extension]: 305
+[protobuf_unittest.repeated_sint64_extension]: 206
+[protobuf_unittest.repeated_sint64_extension]: 306
+[protobuf_unittest.repeated_fixed32_extension]: 207
+[protobuf_unittest.repeated_fixed32_extension]: 307
+[protobuf_unittest.repeated_fixed64_extension]: 208
+[protobuf_unittest.repeated_fixed64_extension]: 308
+[protobuf_unittest.repeated_sfixed32_extension]: 209
+[protobuf_unittest.repeated_sfixed32_extension]: 309
+[protobuf_unittest.repeated_sfixed64_extension]: 210
+[protobuf_unittest.repeated_sfixed64_extension]: 310
+[protobuf_unittest.repeated_float_extension]: 211
+[protobuf_unittest.repeated_float_extension]: 311
+[protobuf_unittest.repeated_double_extension]: 212
+[protobuf_unittest.repeated_double_extension]: 312
+[protobuf_unittest.repeated_bool_extension]: true
+[protobuf_unittest.repeated_bool_extension]: false
+[protobuf_unittest.repeated_string_extension]: "215"
+[protobuf_unittest.repeated_string_extension]: "315"
+[protobuf_unittest.repeated_bytes_extension]: "216"
+[protobuf_unittest.repeated_bytes_extension]: "316"
+[protobuf_unittest.repeatedgroup_extension] {
+ a: 217
+}
+[protobuf_unittest.repeatedgroup_extension] {
+ a: 317
+}
+[protobuf_unittest.repeated_nested_message_extension] {
+ bb: 218
+}
+[protobuf_unittest.repeated_nested_message_extension] {
+ bb: 318
+}
+[protobuf_unittest.repeated_foreign_message_extension] {
+ c: 219
+}
+[protobuf_unittest.repeated_foreign_message_extension] {
+ c: 319
+}
+[protobuf_unittest.repeated_import_message_extension] {
+ d: 220
+}
+[protobuf_unittest.repeated_import_message_extension] {
+ d: 320
+}
+[protobuf_unittest.repeated_nested_enum_extension]: BAR
+[protobuf_unittest.repeated_nested_enum_extension]: BAZ
+[protobuf_unittest.repeated_foreign_enum_extension]: FOREIGN_BAR
+[protobuf_unittest.repeated_foreign_enum_extension]: FOREIGN_BAZ
+[protobuf_unittest.repeated_import_enum_extension]: IMPORT_BAR
+[protobuf_unittest.repeated_import_enum_extension]: IMPORT_BAZ
+[protobuf_unittest.repeated_string_piece_extension]: "224"
+[protobuf_unittest.repeated_string_piece_extension]: "324"
+[protobuf_unittest.repeated_cord_extension]: "225"
+[protobuf_unittest.repeated_cord_extension]: "325"
+[protobuf_unittest.repeated_lazy_message_extension] {
+ bb: 227
+}
+[protobuf_unittest.repeated_lazy_message_extension] {
+ bb: 327
+}
+[protobuf_unittest.default_int32_extension]: 401
+[protobuf_unittest.default_int64_extension]: 402
+[protobuf_unittest.default_uint32_extension]: 403
+[protobuf_unittest.default_uint64_extension]: 404
+[protobuf_unittest.default_sint32_extension]: 405
+[protobuf_unittest.default_sint64_extension]: 406
+[protobuf_unittest.default_fixed32_extension]: 407
+[protobuf_unittest.default_fixed64_extension]: 408
+[protobuf_unittest.default_sfixed32_extension]: 409
+[protobuf_unittest.default_sfixed64_extension]: 410
+[protobuf_unittest.default_float_extension]: 411
+[protobuf_unittest.default_double_extension]: 412
+[protobuf_unittest.default_bool_extension]: false
+[protobuf_unittest.default_string_extension]: "415"
+[protobuf_unittest.default_bytes_extension]: "416"
+[protobuf_unittest.default_nested_enum_extension]: FOO
+[protobuf_unittest.default_foreign_enum_extension]: FOREIGN_FOO
+[protobuf_unittest.default_import_enum_extension]: IMPORT_FOO
+[protobuf_unittest.default_string_piece_extension]: "424"
+[protobuf_unittest.default_cord_extension]: "425"
+[protobuf_unittest.oneof_uint32_extension]: 601
+[protobuf_unittest.oneof_nested_message_extension] {
+ bb: 602
+}
+[protobuf_unittest.oneof_string_extension]: "603"
+[protobuf_unittest.oneof_bytes_extension]: "604"
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data_pointy.txt b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data_pointy.txt
new file mode 100644
index 0000000000..132f7445f3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testdata/text_format_unittest_extensions_data_pointy.txt
@@ -0,0 +1,134 @@
+[protobuf_unittest.optional_int32_extension]: 101
+[protobuf_unittest.optional_int64_extension]: 102
+[protobuf_unittest.optional_uint32_extension]: 103
+[protobuf_unittest.optional_uint64_extension]: 104
+[protobuf_unittest.optional_sint32_extension]: 105
+[protobuf_unittest.optional_sint64_extension]: 106
+[protobuf_unittest.optional_fixed32_extension]: 107
+[protobuf_unittest.optional_fixed64_extension]: 108
+[protobuf_unittest.optional_sfixed32_extension]: 109
+[protobuf_unittest.optional_sfixed64_extension]: 110
+[protobuf_unittest.optional_float_extension]: 111
+[protobuf_unittest.optional_double_extension]: 112
+[protobuf_unittest.optional_bool_extension]: true
+[protobuf_unittest.optional_string_extension]: "115"
+[protobuf_unittest.optional_bytes_extension]: "116"
+[protobuf_unittest.optionalgroup_extension] <
+ a: 117
+>
+[protobuf_unittest.optional_nested_message_extension] <
+ bb: 118
+>
+[protobuf_unittest.optional_foreign_message_extension] <
+ c: 119
+>
+[protobuf_unittest.optional_import_message_extension] <
+ d: 120
+>
+[protobuf_unittest.optional_nested_enum_extension]: BAZ
+[protobuf_unittest.optional_foreign_enum_extension]: FOREIGN_BAZ
+[protobuf_unittest.optional_import_enum_extension]: IMPORT_BAZ
+[protobuf_unittest.optional_string_piece_extension]: "124"
+[protobuf_unittest.optional_cord_extension]: "125"
+[protobuf_unittest.optional_public_import_message_extension] <
+ e: 126
+>
+[protobuf_unittest.optional_lazy_message_extension] <
+ bb: 127
+>
+[protobuf_unittest.repeated_int32_extension]: 201
+[protobuf_unittest.repeated_int32_extension]: 301
+[protobuf_unittest.repeated_int64_extension]: 202
+[protobuf_unittest.repeated_int64_extension]: 302
+[protobuf_unittest.repeated_uint32_extension]: 203
+[protobuf_unittest.repeated_uint32_extension]: 303
+[protobuf_unittest.repeated_uint64_extension]: 204
+[protobuf_unittest.repeated_uint64_extension]: 304
+[protobuf_unittest.repeated_sint32_extension]: 205
+[protobuf_unittest.repeated_sint32_extension]: 305
+[protobuf_unittest.repeated_sint64_extension]: 206
+[protobuf_unittest.repeated_sint64_extension]: 306
+[protobuf_unittest.repeated_fixed32_extension]: 207
+[protobuf_unittest.repeated_fixed32_extension]: 307
+[protobuf_unittest.repeated_fixed64_extension]: 208
+[protobuf_unittest.repeated_fixed64_extension]: 308
+[protobuf_unittest.repeated_sfixed32_extension]: 209
+[protobuf_unittest.repeated_sfixed32_extension]: 309
+[protobuf_unittest.repeated_sfixed64_extension]: 210
+[protobuf_unittest.repeated_sfixed64_extension]: 310
+[protobuf_unittest.repeated_float_extension]: 211
+[protobuf_unittest.repeated_float_extension]: 311
+[protobuf_unittest.repeated_double_extension]: 212
+[protobuf_unittest.repeated_double_extension]: 312
+[protobuf_unittest.repeated_bool_extension]: true
+[protobuf_unittest.repeated_bool_extension]: false
+[protobuf_unittest.repeated_string_extension]: "215"
+[protobuf_unittest.repeated_string_extension]: "315"
+[protobuf_unittest.repeated_bytes_extension]: "216"
+[protobuf_unittest.repeated_bytes_extension]: "316"
+[protobuf_unittest.repeatedgroup_extension] <
+ a: 217
+>
+[protobuf_unittest.repeatedgroup_extension] <
+ a: 317
+>
+[protobuf_unittest.repeated_nested_message_extension] <
+ bb: 218
+>
+[protobuf_unittest.repeated_nested_message_extension] <
+ bb: 318
+>
+[protobuf_unittest.repeated_foreign_message_extension] <
+ c: 219
+>
+[protobuf_unittest.repeated_foreign_message_extension] <
+ c: 319
+>
+[protobuf_unittest.repeated_import_message_extension] <
+ d: 220
+>
+[protobuf_unittest.repeated_import_message_extension] <
+ d: 320
+>
+[protobuf_unittest.repeated_nested_enum_extension]: BAR
+[protobuf_unittest.repeated_nested_enum_extension]: BAZ
+[protobuf_unittest.repeated_foreign_enum_extension]: FOREIGN_BAR
+[protobuf_unittest.repeated_foreign_enum_extension]: FOREIGN_BAZ
+[protobuf_unittest.repeated_import_enum_extension]: IMPORT_BAR
+[protobuf_unittest.repeated_import_enum_extension]: IMPORT_BAZ
+[protobuf_unittest.repeated_string_piece_extension]: "224"
+[protobuf_unittest.repeated_string_piece_extension]: "324"
+[protobuf_unittest.repeated_cord_extension]: "225"
+[protobuf_unittest.repeated_cord_extension]: "325"
+[protobuf_unittest.repeated_lazy_message_extension] <
+ bb: 227
+>
+[protobuf_unittest.repeated_lazy_message_extension] <
+ bb: 327
+>
+[protobuf_unittest.default_int32_extension]: 401
+[protobuf_unittest.default_int64_extension]: 402
+[protobuf_unittest.default_uint32_extension]: 403
+[protobuf_unittest.default_uint64_extension]: 404
+[protobuf_unittest.default_sint32_extension]: 405
+[protobuf_unittest.default_sint64_extension]: 406
+[protobuf_unittest.default_fixed32_extension]: 407
+[protobuf_unittest.default_fixed64_extension]: 408
+[protobuf_unittest.default_sfixed32_extension]: 409
+[protobuf_unittest.default_sfixed64_extension]: 410
+[protobuf_unittest.default_float_extension]: 411
+[protobuf_unittest.default_double_extension]: 412
+[protobuf_unittest.default_bool_extension]: false
+[protobuf_unittest.default_string_extension]: "415"
+[protobuf_unittest.default_bytes_extension]: "416"
+[protobuf_unittest.default_nested_enum_extension]: FOO
+[protobuf_unittest.default_foreign_enum_extension]: FOREIGN_FOO
+[protobuf_unittest.default_import_enum_extension]: IMPORT_FOO
+[protobuf_unittest.default_string_piece_extension]: "424"
+[protobuf_unittest.default_cord_extension]: "425"
+[protobuf_unittest.oneof_uint32_extension]: 601
+[protobuf_unittest.oneof_nested_message_extension] <
+ bb: 602
+>
+[protobuf_unittest.oneof_string_extension]: "603"
+[protobuf_unittest.oneof_bytes_extension]: "604"
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testing/file.cc b/third_party/protobuf/3.0.0/src/google/protobuf/testing/file.cc
new file mode 100644
index 0000000000..3d07b1276c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testing/file.cc
@@ -0,0 +1,200 @@
+// 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)
+// emulates google3/file/base/file.cc
+
+#include <google/protobuf/testing/file.h>
+#include <stdio.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#ifdef _MSC_VER
+#define WIN32_LEAN_AND_MEAN // yeah, right
+#include <windows.h> // Find*File(). :(
+#include <io.h>
+#include <direct.h>
+#else
+#include <dirent.h>
+#include <unistd.h>
+#endif
+#include <errno.h>
+
+namespace google {
+namespace protobuf {
+
+#ifdef _WIN32
+#define mkdir(name, mode) mkdir(name)
+// Windows doesn't have symbolic links.
+#define lstat stat
+#ifndef F_OK
+#define F_OK 00 // not defined by MSVC for whatever reason
+#endif
+#endif
+
+bool File::Exists(const string& name) {
+ return access(name.c_str(), F_OK) == 0;
+}
+
+bool File::ReadFileToString(const string& name, string* output) {
+ char buffer[1024];
+ FILE* file = fopen(name.c_str(), "rb");
+ if (file == NULL) return false;
+
+ while (true) {
+ size_t n = fread(buffer, 1, sizeof(buffer), file);
+ if (n <= 0) break;
+ output->append(buffer, n);
+ }
+
+ int error = ferror(file);
+ if (fclose(file) != 0) return false;
+ return error == 0;
+}
+
+void File::ReadFileToStringOrDie(const string& name, string* output) {
+ GOOGLE_CHECK(ReadFileToString(name, output)) << "Could not read: " << name;
+}
+
+bool File::WriteStringToFile(const string& contents, const string& name) {
+ FILE* file = fopen(name.c_str(), "wb");
+ if (file == NULL) {
+ GOOGLE_LOG(ERROR) << "fopen(" << name << ", \"wb\"): " << strerror(errno);
+ return false;
+ }
+
+ if (fwrite(contents.data(), 1, contents.size(), file) != contents.size()) {
+ GOOGLE_LOG(ERROR) << "fwrite(" << name << "): " << strerror(errno);
+ return false;
+ }
+
+ if (fclose(file) != 0) {
+ return false;
+ }
+ return true;
+}
+
+void File::WriteStringToFileOrDie(const string& contents, const string& name) {
+ FILE* file = fopen(name.c_str(), "wb");
+ GOOGLE_CHECK(file != NULL)
+ << "fopen(" << name << ", \"wb\"): " << strerror(errno);
+ GOOGLE_CHECK_EQ(fwrite(contents.data(), 1, contents.size(), file),
+ contents.size())
+ << "fwrite(" << name << "): " << strerror(errno);
+ GOOGLE_CHECK(fclose(file) == 0)
+ << "fclose(" << name << "): " << strerror(errno);
+}
+
+bool File::CreateDir(const string& name, int mode) {
+ return mkdir(name.c_str(), mode) == 0;
+}
+
+bool File::RecursivelyCreateDir(const string& path, int mode) {
+ if (CreateDir(path, mode)) return true;
+
+ if (Exists(path)) return false;
+
+ // Try creating the parent.
+ string::size_type slashpos = path.find_last_of('/');
+ if (slashpos == string::npos) {
+ // No parent given.
+ return false;
+ }
+
+ return RecursivelyCreateDir(path.substr(0, slashpos), mode) &&
+ CreateDir(path, mode);
+}
+
+void File::DeleteRecursively(const string& name,
+ void* dummy1, void* dummy2) {
+ if (name.empty()) return;
+
+ // We don't care too much about error checking here since this is only used
+ // in tests to delete temporary directories that are under /tmp anyway.
+
+#ifdef _MSC_VER
+ // This interface is so weird.
+ WIN32_FIND_DATA find_data;
+ HANDLE find_handle = FindFirstFile((name + "/*").c_str(), &find_data);
+ if (find_handle == INVALID_HANDLE_VALUE) {
+ // Just delete it, whatever it is.
+ DeleteFile(name.c_str());
+ RemoveDirectory(name.c_str());
+ return;
+ }
+
+ do {
+ string entry_name = find_data.cFileName;
+ if (entry_name != "." && entry_name != "..") {
+ string path = name + "/" + entry_name;
+ if (find_data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
+ DeleteRecursively(path, NULL, NULL);
+ RemoveDirectory(path.c_str());
+ } else {
+ DeleteFile(path.c_str());
+ }
+ }
+ } while(FindNextFile(find_handle, &find_data));
+ FindClose(find_handle);
+
+ RemoveDirectory(name.c_str());
+#else
+ // Use opendir()! Yay!
+ // lstat = Don't follow symbolic links.
+ struct stat stats;
+ if (lstat(name.c_str(), &stats) != 0) return;
+
+ if (S_ISDIR(stats.st_mode)) {
+ DIR* dir = opendir(name.c_str());
+ if (dir != NULL) {
+ while (true) {
+ struct dirent* entry = readdir(dir);
+ if (entry == NULL) break;
+ string entry_name = entry->d_name;
+ if (entry_name != "." && entry_name != "..") {
+ DeleteRecursively(name + "/" + entry_name, NULL, NULL);
+ }
+ }
+ }
+
+ closedir(dir);
+ rmdir(name.c_str());
+
+ } else if (S_ISREG(stats.st_mode)) {
+ remove(name.c_str());
+ }
+#endif
+}
+
+bool File::ChangeWorkingDirectory(const string& new_working_directory) {
+ return chdir(new_working_directory.c_str()) == 0;
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testing/file.h b/third_party/protobuf/3.0.0/src/google/protobuf/testing/file.h
new file mode 100644
index 0000000000..2f63f80e7b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testing/file.h
@@ -0,0 +1,100 @@
+// 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)
+// emulates google3/file/base/file.h
+
+#ifndef GOOGLE_PROTOBUF_TESTING_FILE_H__
+#define GOOGLE_PROTOBUF_TESTING_FILE_H__
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+const int DEFAULT_FILE_MODE = 0777;
+
+// Protocol buffer code only uses a couple static methods of File, and only
+// in tests.
+class File {
+ public:
+ // Check if the file exists.
+ static bool Exists(const string& name);
+
+ // Read an entire file to a string. Return true if successful, false
+ // otherwise.
+ static bool ReadFileToString(const string& name, string* output);
+
+ // Same as above, but crash on failure.
+ static void ReadFileToStringOrDie(const string& name, string* output);
+
+ // Create a file and write a string to it.
+ static bool WriteStringToFile(const string& contents,
+ const string& name);
+
+ // Same as above, but crash on failure.
+ static void WriteStringToFileOrDie(const string& contents,
+ const string& name);
+
+ // Create a directory.
+ static bool CreateDir(const string& name, int mode);
+
+ // Create a directory and all parent directories if necessary.
+ static bool RecursivelyCreateDir(const string& path, int mode);
+
+ // If "name" is a file, we delete it. If it is a directory, we
+ // call DeleteRecursively() for each file or directory (other than
+ // dot and double-dot) within it, and then delete the directory itself.
+ // The "dummy" parameters have a meaning in the original version of this
+ // method but they are not used anywhere in protocol buffers.
+ static void DeleteRecursively(const string& name,
+ void* dummy1, void* dummy2);
+
+ // Change working directory to given directory.
+ static bool ChangeWorkingDirectory(const string& new_working_directory);
+
+ static bool GetContents(
+ const string& name, string* output, bool /*is_default*/) {
+ return ReadFileToString(name, output);
+ }
+
+ static bool SetContents(
+ const string& name, const string& contents, bool /*is_default*/) {
+ return WriteStringToFile(contents, name);
+ }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(File);
+};
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_TESTING_FILE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.cc
new file mode 100644
index 0000000000..d45706b654
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.cc
@@ -0,0 +1,271 @@
+// 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)
+// emulates google3/testing/base/public/googletest.cc
+
+#include <google/protobuf/testing/googletest.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <errno.h>
+#include <stdlib.h>
+#ifdef _MSC_VER
+#include <io.h>
+#include <direct.h>
+#else
+#include <unistd.h>
+#endif
+#include <stdio.h>
+#include <fcntl.h>
+#include <iostream>
+#include <fstream>
+
+namespace google {
+namespace protobuf {
+
+#ifdef _WIN32
+#define mkdir(name, mode) mkdir(name)
+#endif
+
+#ifndef O_BINARY
+#ifdef _O_BINARY
+#define O_BINARY _O_BINARY
+#else
+#define O_BINARY 0 // If this isn't defined, the platform doesn't need it.
+#endif
+#endif
+
+string TestSourceDir() {
+#ifndef GOOGLE_THIRD_PARTY_PROTOBUF
+#ifdef GOOGLE_PROTOBUF_TEST_SOURCE_PATH
+ return GOOGLE_PROTOBUF_TEST_SOURCE_PATH;
+#else
+#ifndef _MSC_VER
+ // automake sets the "srcdir" environment variable.
+ char* result = getenv("srcdir");
+ if (result != NULL) {
+ return result;
+ }
+#endif // _MSC_VER
+
+ // Look for the "src" directory.
+ string prefix = ".";
+
+ while (!File::Exists(prefix + "/src/google/protobuf")) {
+ if (!File::Exists(prefix)) {
+ GOOGLE_LOG(FATAL)
+ << "Could not find protobuf source code. Please run tests from "
+ "somewhere within the protobuf source package.";
+ }
+ prefix += "/..";
+ }
+ return prefix + "/src";
+#endif // GOOGLE_PROTOBUF_TEST_SOURCE_PATH
+#else
+ return "third_party/protobuf/src";
+#endif // GOOGLE_THIRD_PARTY_PROTOBUF
+}
+
+namespace {
+
+string GetTemporaryDirectoryName() {
+ // Tests run under Bazel "should not" use /tmp. Bazel sets this environment
+ // variable for tests to use instead.
+ char *from_environment = getenv("TEST_TMPDIR");
+ if (from_environment != NULL && from_environment[0] != '\0') {
+ return string(from_environment) + "/protobuf_tmpdir";
+ }
+
+ // tmpnam() is generally not considered safe but we're only using it for
+ // testing. We cannot use tmpfile() or mkstemp() since we're creating a
+ // directory.
+ char b[L_tmpnam + 1]; // HPUX multithread return 0 if s is 0
+ string result = tmpnam(b);
+#ifdef _WIN32
+ // On Win32, tmpnam() returns a file prefixed with '\', but which is supposed
+ // to be used in the current working directory. WTF?
+ if (HasPrefixString(result, "\\")) {
+ result.erase(0, 1);
+ }
+ // The Win32 API accepts forward slashes as a path delimiter even though
+ // backslashes are standard. Let's avoid confusion and use only forward
+ // slashes.
+ result = StringReplace(result, "\\", "/", true);
+#endif // _WIN32
+ return result;
+}
+
+// Creates a temporary directory on demand and deletes it when the process
+// quits.
+class TempDirDeleter {
+ public:
+ TempDirDeleter() {}
+ ~TempDirDeleter() {
+ if (!name_.empty()) {
+ File::DeleteRecursively(name_, NULL, NULL);
+ }
+ }
+
+ string GetTempDir() {
+ if (name_.empty()) {
+ name_ = GetTemporaryDirectoryName();
+ GOOGLE_CHECK(mkdir(name_.c_str(), 0777) == 0) << strerror(errno);
+
+ // Stick a file in the directory that tells people what this is, in case
+ // we abort and don't get a chance to delete it.
+ File::WriteStringToFileOrDie("", name_ + "/TEMP_DIR_FOR_PROTOBUF_TESTS");
+ }
+ return name_;
+ }
+
+ private:
+ string name_;
+};
+
+TempDirDeleter temp_dir_deleter_;
+
+} // namespace
+
+string TestTempDir() {
+ return temp_dir_deleter_.GetTempDir();
+}
+
+// TODO(kenton): Share duplicated code below. Too busy/lazy for now.
+
+static string stdout_capture_filename_;
+static string stderr_capture_filename_;
+static int original_stdout_ = -1;
+static int original_stderr_ = -1;
+
+void CaptureTestStdout() {
+ GOOGLE_CHECK_EQ(original_stdout_, -1) << "Already capturing.";
+
+ stdout_capture_filename_ = TestTempDir() + "/captured_stdout";
+
+ int fd = open(stdout_capture_filename_.c_str(),
+ O_WRONLY | O_CREAT | O_EXCL | O_BINARY, 0777);
+ GOOGLE_CHECK(fd >= 0) << "open: " << strerror(errno);
+
+ original_stdout_ = dup(1);
+ close(1);
+ dup2(fd, 1);
+ close(fd);
+}
+
+void CaptureTestStderr() {
+ GOOGLE_CHECK_EQ(original_stderr_, -1) << "Already capturing.";
+
+ stderr_capture_filename_ = TestTempDir() + "/captured_stderr";
+
+ int fd = open(stderr_capture_filename_.c_str(),
+ O_WRONLY | O_CREAT | O_EXCL | O_BINARY, 0777);
+ GOOGLE_CHECK(fd >= 0) << "open: " << strerror(errno);
+
+ original_stderr_ = dup(2);
+ close(2);
+ dup2(fd, 2);
+ close(fd);
+}
+
+string GetCapturedTestStdout() {
+ GOOGLE_CHECK_NE(original_stdout_, -1) << "Not capturing.";
+
+ close(1);
+ dup2(original_stdout_, 1);
+ original_stdout_ = -1;
+
+ string result;
+ File::ReadFileToStringOrDie(stdout_capture_filename_, &result);
+
+ remove(stdout_capture_filename_.c_str());
+
+ return result;
+}
+
+string GetCapturedTestStderr() {
+ GOOGLE_CHECK_NE(original_stderr_, -1) << "Not capturing.";
+
+ close(2);
+ dup2(original_stderr_, 2);
+ original_stderr_ = -1;
+
+ string result;
+ File::ReadFileToStringOrDie(stderr_capture_filename_, &result);
+
+ remove(stderr_capture_filename_.c_str());
+
+ return result;
+}
+
+ScopedMemoryLog* ScopedMemoryLog::active_log_ = NULL;
+
+ScopedMemoryLog::ScopedMemoryLog() {
+ GOOGLE_CHECK(active_log_ == NULL);
+ active_log_ = this;
+ old_handler_ = SetLogHandler(&HandleLog);
+}
+
+ScopedMemoryLog::~ScopedMemoryLog() {
+ SetLogHandler(old_handler_);
+ active_log_ = NULL;
+}
+
+const vector<string>& ScopedMemoryLog::GetMessages(LogLevel level) {
+ GOOGLE_CHECK(level == ERROR ||
+ level == WARNING);
+ return messages_[level];
+}
+
+void ScopedMemoryLog::HandleLog(LogLevel level, const char* filename,
+ int line, const string& message) {
+ GOOGLE_CHECK(active_log_ != NULL);
+ if (level == ERROR || level == WARNING) {
+ active_log_->messages_[level].push_back(message);
+ }
+}
+
+namespace {
+
+// Force shutdown at process exit so that we can test for memory leaks. To
+// actually check for leaks, I suggest using the heap checker included with
+// google-perftools. Set it to "draconian" mode to ensure that every last
+// call to malloc() has a corresponding free().
+struct ForceShutdown {
+ ~ForceShutdown() {
+ ShutdownProtobufLibrary();
+ }
+} force_shutdown;
+
+} // namespace
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.h b/third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.h
new file mode 100644
index 0000000000..c0d99e69ac
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testing/googletest.h
@@ -0,0 +1,102 @@
+// 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)
+// emulates google3/testing/base/public/googletest.h
+
+#ifndef GOOGLE_PROTOBUF_GOOGLETEST_H__
+#define GOOGLE_PROTOBUF_GOOGLETEST_H__
+
+#include <map>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+
+// Disable death tests if we use exceptions in CHECK().
+#if !PROTOBUF_USE_EXCEPTIONS && defined(GTEST_HAS_DEATH_TEST)
+#define PROTOBUF_HAS_DEATH_TEST
+#endif
+
+namespace google {
+namespace protobuf {
+
+// When running unittests, get the directory containing the source code.
+string TestSourceDir();
+
+// When running unittests, get a directory where temporary files may be
+// placed.
+string TestTempDir();
+
+// Capture all text written to stdout or stderr.
+void CaptureTestStdout();
+void CaptureTestStderr();
+
+// Stop capturing stdout or stderr and return the text captured.
+string GetCapturedTestStdout();
+string GetCapturedTestStderr();
+
+// For use with ScopedMemoryLog::GetMessages(). Inside Google the LogLevel
+// constants don't have the LOGLEVEL_ prefix, so the code that used
+// ScopedMemoryLog refers to LOGLEVEL_ERROR as just ERROR.
+#undef ERROR // defend against promiscuous windows.h
+static const LogLevel ERROR = LOGLEVEL_ERROR;
+static const LogLevel WARNING = LOGLEVEL_WARNING;
+
+// Receives copies of all LOG(ERROR) messages while in scope. Sample usage:
+// {
+// ScopedMemoryLog log; // constructor registers object as a log sink
+// SomeRoutineThatMayLogMessages();
+// const vector<string>& warnings = log.GetMessages(ERROR);
+// } // destructor unregisters object as a log sink
+// This is a dummy implementation which covers only what is used by protocol
+// buffer unit tests.
+class ScopedMemoryLog {
+ public:
+ ScopedMemoryLog();
+ virtual ~ScopedMemoryLog();
+
+ // Fetches all messages with the given severity level.
+ const vector<string>& GetMessages(LogLevel error);
+
+ private:
+ map<LogLevel, vector<string> > messages_;
+ LogHandler* old_handler_;
+
+ static void HandleLog(LogLevel level, const char* filename, int line,
+ const string& message);
+
+ static ScopedMemoryLog* active_log_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ScopedMemoryLog);
+};
+
+} // namespace protobuf
+} // namespace google
+
+#endif // GOOGLE_PROTOBUF_GOOGLETEST_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgunzip.cc b/third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgunzip.cc
new file mode 100644
index 0000000000..76f8cfe11b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgunzip.cc
@@ -0,0 +1,80 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2009 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: brianolson@google.com (Brian Olson)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// Test program to verify that GzipInputStream is compatible with command line
+// gunzip or java.util.zip.GzipInputStream
+//
+// Reads gzip stream on standard input and writes decompressed data to standard
+// output.
+
+#include <assert.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <fcntl.h>
+
+#ifdef _WIN32
+#ifndef STDIN_FILENO
+#define STDIN_FILENO 0
+#endif
+#ifndef STDOUT_FILENO
+#define STDOUT_FILENO 1
+#endif
+#endif
+
+#include <google/protobuf/io/gzip_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+
+using google::protobuf::io::FileInputStream;
+using google::protobuf::io::GzipInputStream;
+
+int main(int argc, const char** argv) {
+ FileInputStream fin(STDIN_FILENO);
+ GzipInputStream in(&fin);
+
+ while (true) {
+ const void* inptr;
+ int inlen;
+ bool ok;
+ ok = in.Next(&inptr, &inlen);
+ if (!ok) {
+ break;
+ }
+ if (inlen > 0) {
+ int err = write(STDOUT_FILENO, inptr, inlen);
+ assert(err == inlen);
+ }
+ }
+
+ return 0;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgzip.cc b/third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgzip.cc
new file mode 100644
index 0000000000..992ddc6ed6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/testing/zcgzip.cc
@@ -0,0 +1,86 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2009 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: brianolson@google.com (Brian Olson)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// Test program to verify that GzipOutputStream is compatible with command line
+// gzip or java.util.zip.GzipOutputStream
+//
+// Reads data on standard input and writes compressed gzip stream to standard
+// output.
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <fcntl.h>
+
+#ifdef _WIN32
+#ifndef STDIN_FILENO
+#define STDIN_FILENO 0
+#endif
+#ifndef STDOUT_FILENO
+#define STDOUT_FILENO 1
+#endif
+#endif
+
+#include <google/protobuf/io/gzip_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+
+using google::protobuf::io::FileOutputStream;
+using google::protobuf::io::GzipOutputStream;
+
+int main(int argc, const char** argv) {
+ FileOutputStream fout(STDOUT_FILENO);
+ GzipOutputStream out(&fout);
+ int readlen;
+
+ while (true) {
+ void* outptr;
+ int outlen;
+ bool ok;
+ do {
+ ok = out.Next(&outptr, &outlen);
+ if (!ok) {
+ break;
+ }
+ } while (outlen <= 0);
+ readlen = read(STDIN_FILENO, outptr, outlen);
+ if (readlen <= 0) {
+ out.BackUp(outlen);
+ break;
+ }
+ if (readlen < outlen) {
+ out.BackUp(outlen - readlen);
+ }
+ }
+
+ return 0;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/text_format.cc b/third_party/protobuf/3.0.0/src/google/protobuf/text_format.cc
new file mode 100644
index 0000000000..66b2648b7c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/text_format.cc
@@ -0,0 +1,2007 @@
+// 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: jschorr@google.com (Joseph Schorr)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <algorithm>
+#include <float.h>
+#include <math.h>
+#include <stdio.h>
+#include <stack>
+#include <limits>
+#include <vector>
+
+#include <google/protobuf/text_format.h>
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/wire_format_lite.h>
+#include <google/protobuf/io/strtod.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/any.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+inline bool IsHexNumber(const string& str) {
+ return (str.length() >= 2 && str[0] == '0' &&
+ (str[1] == 'x' || str[1] == 'X'));
+}
+
+inline bool IsOctNumber(const string& str) {
+ return (str.length() >= 2 && str[0] == '0' &&
+ (str[1] >= '0' && str[1] < '8'));
+}
+
+inline bool GetAnyFieldDescriptors(const Message& message,
+ const FieldDescriptor** type_url_field,
+ const FieldDescriptor** value_field) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ *type_url_field = descriptor->FindFieldByNumber(1);
+ *value_field = descriptor->FindFieldByNumber(2);
+ return (*type_url_field != NULL &&
+ (*type_url_field)->type() == FieldDescriptor::TYPE_STRING &&
+ *value_field != NULL &&
+ (*value_field)->type() == FieldDescriptor::TYPE_BYTES);
+}
+
+} // namespace
+
+string Message::DebugString() const {
+ string debug_string;
+
+ TextFormat::Printer printer;
+ printer.SetExpandAny(true);
+
+ printer.PrintToString(*this, &debug_string);
+
+ return debug_string;
+}
+
+string Message::ShortDebugString() const {
+ string debug_string;
+
+ TextFormat::Printer printer;
+ printer.SetSingleLineMode(true);
+ printer.SetExpandAny(true);
+
+ printer.PrintToString(*this, &debug_string);
+ // Single line mode currently might have an extra space at the end.
+ if (debug_string.size() > 0 &&
+ debug_string[debug_string.size() - 1] == ' ') {
+ debug_string.resize(debug_string.size() - 1);
+ }
+
+ return debug_string;
+}
+
+string Message::Utf8DebugString() const {
+ string debug_string;
+
+ TextFormat::Printer printer;
+ printer.SetUseUtf8StringEscaping(true);
+ printer.SetExpandAny(true);
+
+ printer.PrintToString(*this, &debug_string);
+
+ return debug_string;
+}
+
+void Message::PrintDebugString() const {
+ printf("%s", DebugString().c_str());
+}
+
+
+// ===========================================================================
+// Implementation of the parse information tree class.
+TextFormat::ParseInfoTree::ParseInfoTree() { }
+
+TextFormat::ParseInfoTree::~ParseInfoTree() {
+ // Remove any nested information trees, as they are owned by this tree.
+ for (NestedMap::iterator it = nested_.begin(); it != nested_.end(); ++it) {
+ STLDeleteElements(&(it->second));
+ }
+}
+
+void TextFormat::ParseInfoTree::RecordLocation(
+ const FieldDescriptor* field,
+ TextFormat::ParseLocation location) {
+ locations_[field].push_back(location);
+}
+
+TextFormat::ParseInfoTree* TextFormat::ParseInfoTree::CreateNested(
+ const FieldDescriptor* field) {
+ // Owned by us in the map.
+ TextFormat::ParseInfoTree* instance = new TextFormat::ParseInfoTree();
+ vector<TextFormat::ParseInfoTree*>* trees = &nested_[field];
+ GOOGLE_CHECK(trees);
+ trees->push_back(instance);
+ return instance;
+}
+
+void CheckFieldIndex(const FieldDescriptor* field, int index) {
+ if (field == NULL) { return; }
+
+ if (field->is_repeated() && index == -1) {
+ GOOGLE_LOG(DFATAL) << "Index must be in range of repeated field values. "
+ << "Field: " << field->name();
+ } else if (!field->is_repeated() && index != -1) {
+ GOOGLE_LOG(DFATAL) << "Index must be -1 for singular fields."
+ << "Field: " << field->name();
+ }
+}
+
+TextFormat::ParseLocation TextFormat::ParseInfoTree::GetLocation(
+ const FieldDescriptor* field, int index) const {
+ CheckFieldIndex(field, index);
+ if (index == -1) { index = 0; }
+
+ const vector<TextFormat::ParseLocation>* locations =
+ FindOrNull(locations_, field);
+ if (locations == NULL || index >= locations->size()) {
+ return TextFormat::ParseLocation();
+ }
+
+ return (*locations)[index];
+}
+
+TextFormat::ParseInfoTree* TextFormat::ParseInfoTree::GetTreeForNested(
+ const FieldDescriptor* field, int index) const {
+ CheckFieldIndex(field, index);
+ if (index == -1) { index = 0; }
+
+ const vector<TextFormat::ParseInfoTree*>* trees = FindOrNull(nested_, field);
+ if (trees == NULL || index >= trees->size()) {
+ return NULL;
+ }
+
+ return (*trees)[index];
+}
+
+
+// ===========================================================================
+// Internal class for parsing an ASCII representation of a Protocol Message.
+// This class makes use of the Protocol Message compiler's tokenizer found
+// in //google/protobuf/io/tokenizer.h. Note that class's Parse
+// method is *not* thread-safe and should only be used in a single thread at
+// a time.
+
+// Makes code slightly more readable. The meaning of "DO(foo)" is
+// "Execute foo and fail if it fails.", where failure is indicated by
+// returning false. Borrowed from parser.cc (Thanks Kenton!).
+#define DO(STATEMENT) if (STATEMENT) {} else return false
+
+class TextFormat::Parser::ParserImpl {
+ public:
+
+ // Determines if repeated values for non-repeated fields and
+ // oneofs are permitted, e.g., the string "foo: 1 foo: 2" for a
+ // required/optional field named "foo", or "baz: 1 qux: 2"
+ // where "baz" and "qux" are members of the same oneof.
+ enum SingularOverwritePolicy {
+ ALLOW_SINGULAR_OVERWRITES = 0, // the last value is retained
+ FORBID_SINGULAR_OVERWRITES = 1, // an error is issued
+ };
+
+ ParserImpl(const Descriptor* root_message_type,
+ io::ZeroCopyInputStream* input_stream,
+ io::ErrorCollector* error_collector,
+ TextFormat::Finder* finder,
+ ParseInfoTree* parse_info_tree,
+ SingularOverwritePolicy singular_overwrite_policy,
+ bool allow_case_insensitive_field,
+ bool allow_unknown_field,
+ bool allow_unknown_enum,
+ bool allow_field_number,
+ bool allow_relaxed_whitespace,
+ bool allow_partial)
+ : error_collector_(error_collector),
+ finder_(finder),
+ parse_info_tree_(parse_info_tree),
+ tokenizer_error_collector_(this),
+ tokenizer_(input_stream, &tokenizer_error_collector_),
+ root_message_type_(root_message_type),
+ singular_overwrite_policy_(singular_overwrite_policy),
+ allow_case_insensitive_field_(allow_case_insensitive_field),
+ allow_unknown_field_(allow_unknown_field),
+ allow_unknown_enum_(allow_unknown_enum),
+ allow_field_number_(allow_field_number),
+ allow_partial_(allow_partial),
+ had_errors_(false) {
+ // For backwards-compatibility with proto1, we need to allow the 'f' suffix
+ // for floats.
+ tokenizer_.set_allow_f_after_float(true);
+
+ // '#' starts a comment.
+ tokenizer_.set_comment_style(io::Tokenizer::SH_COMMENT_STYLE);
+
+ if (allow_relaxed_whitespace) {
+ tokenizer_.set_require_space_after_number(false);
+ tokenizer_.set_allow_multiline_strings(true);
+ }
+
+ // Consume the starting token.
+ tokenizer_.Next();
+ }
+ ~ParserImpl() { }
+
+ // Parses the ASCII representation specified in input and saves the
+ // information into the output pointer (a Message). Returns
+ // false if an error occurs (an error will also be logged to
+ // GOOGLE_LOG(ERROR)).
+ bool Parse(Message* output) {
+ // Consume fields until we cannot do so anymore.
+ while (true) {
+ if (LookingAtType(io::Tokenizer::TYPE_END)) {
+ return !had_errors_;
+ }
+
+ DO(ConsumeField(output));
+ }
+ }
+
+ bool ParseField(const FieldDescriptor* field, Message* output) {
+ bool suc;
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ suc = ConsumeFieldMessage(output, output->GetReflection(), field);
+ } else {
+ suc = ConsumeFieldValue(output, output->GetReflection(), field);
+ }
+ return suc && LookingAtType(io::Tokenizer::TYPE_END);
+ }
+
+ void ReportError(int line, int col, const string& message) {
+ had_errors_ = true;
+ if (error_collector_ == NULL) {
+ if (line >= 0) {
+ GOOGLE_LOG(ERROR) << "Error parsing text-format "
+ << root_message_type_->full_name()
+ << ": " << (line + 1) << ":"
+ << (col + 1) << ": " << message;
+ } else {
+ GOOGLE_LOG(ERROR) << "Error parsing text-format "
+ << root_message_type_->full_name()
+ << ": " << message;
+ }
+ } else {
+ error_collector_->AddError(line, col, message);
+ }
+ }
+
+ void ReportWarning(int line, int col, const string& message) {
+ if (error_collector_ == NULL) {
+ if (line >= 0) {
+ GOOGLE_LOG(WARNING) << "Warning parsing text-format "
+ << root_message_type_->full_name()
+ << ": " << (line + 1) << ":"
+ << (col + 1) << ": " << message;
+ } else {
+ GOOGLE_LOG(WARNING) << "Warning parsing text-format "
+ << root_message_type_->full_name()
+ << ": " << message;
+ }
+ } else {
+ error_collector_->AddWarning(line, col, message);
+ }
+ }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ParserImpl);
+
+ // Reports an error with the given message with information indicating
+ // the position (as derived from the current token).
+ void ReportError(const string& message) {
+ ReportError(tokenizer_.current().line, tokenizer_.current().column,
+ message);
+ }
+
+ // Reports a warning with the given message with information indicating
+ // the position (as derived from the current token).
+ void ReportWarning(const string& message) {
+ ReportWarning(tokenizer_.current().line, tokenizer_.current().column,
+ message);
+ }
+
+ // Consumes the specified message with the given starting delimiter.
+ // This method checks to see that the end delimiter at the conclusion of
+ // the consumption matches the starting delimiter passed in here.
+ bool ConsumeMessage(Message* message, const string delimiter) {
+ while (!LookingAt(">") && !LookingAt("}")) {
+ DO(ConsumeField(message));
+ }
+
+ // Confirm that we have a valid ending delimiter.
+ DO(Consume(delimiter));
+ return true;
+ }
+
+ // Consume either "<" or "{".
+ bool ConsumeMessageDelimiter(string* delimiter) {
+ if (TryConsume("<")) {
+ *delimiter = ">";
+ } else {
+ DO(Consume("{"));
+ *delimiter = "}";
+ }
+ return true;
+ }
+
+
+ // Consumes the current field (as returned by the tokenizer) on the
+ // passed in message.
+ bool ConsumeField(Message* message) {
+ const Reflection* reflection = message->GetReflection();
+ const Descriptor* descriptor = message->GetDescriptor();
+
+ string field_name;
+
+ const FieldDescriptor* field = NULL;
+ int start_line = tokenizer_.current().line;
+ int start_column = tokenizer_.current().column;
+
+ const FieldDescriptor* any_type_url_field;
+ const FieldDescriptor* any_value_field;
+ if (internal::GetAnyFieldDescriptors(*message, &any_type_url_field,
+ &any_value_field) &&
+ TryConsume("[")) {
+ string full_type_name, prefix;
+ DO(ConsumeAnyTypeUrl(&full_type_name, &prefix));
+ DO(Consume("]"));
+ TryConsume(":"); // ':' is optional between message labels and values.
+ string serialized_value;
+ DO(ConsumeAnyValue(full_type_name,
+ message->GetDescriptor()->file()->pool(),
+ &serialized_value));
+ reflection->SetString(
+ message, any_type_url_field,
+ string(prefix + full_type_name));
+ reflection->SetString(message, any_value_field, serialized_value);
+ return true;
+ }
+ if (TryConsume("[")) {
+ // Extension.
+ DO(ConsumeFullTypeName(&field_name));
+ DO(Consume("]"));
+
+ field = (finder_ != NULL
+ ? finder_->FindExtension(message, field_name)
+ : reflection->FindKnownExtensionByName(field_name));
+
+ if (field == NULL) {
+ if (!allow_unknown_field_) {
+ ReportError("Extension \"" + field_name + "\" is not defined or "
+ "is not an extension of \"" +
+ descriptor->full_name() + "\".");
+ return false;
+ } else {
+ ReportWarning("Extension \"" + field_name + "\" is not defined or "
+ "is not an extension of \"" +
+ descriptor->full_name() + "\".");
+ }
+ }
+ } else {
+ DO(ConsumeIdentifier(&field_name));
+
+ int32 field_number;
+ if (allow_field_number_ && safe_strto32(field_name, &field_number)) {
+ if (descriptor->IsExtensionNumber(field_number)) {
+ field = reflection->FindKnownExtensionByNumber(field_number);
+ } else {
+ field = descriptor->FindFieldByNumber(field_number);
+ }
+ } else {
+ field = descriptor->FindFieldByName(field_name);
+ // Group names are expected to be capitalized as they appear in the
+ // .proto file, which actually matches their type names, not their
+ // field names.
+ if (field == NULL) {
+ string lower_field_name = field_name;
+ LowerString(&lower_field_name);
+ field = descriptor->FindFieldByName(lower_field_name);
+ // If the case-insensitive match worked but the field is NOT a group,
+ if (field != NULL && field->type() != FieldDescriptor::TYPE_GROUP) {
+ field = NULL;
+ }
+ }
+ // Again, special-case group names as described above.
+ if (field != NULL && field->type() == FieldDescriptor::TYPE_GROUP
+ && field->message_type()->name() != field_name) {
+ field = NULL;
+ }
+
+ if (field == NULL && allow_case_insensitive_field_) {
+ string lower_field_name = field_name;
+ LowerString(&lower_field_name);
+ field = descriptor->FindFieldByLowercaseName(lower_field_name);
+ }
+ }
+
+ if (field == NULL) {
+ if (!allow_unknown_field_) {
+ ReportError("Message type \"" + descriptor->full_name() +
+ "\" has no field named \"" + field_name + "\".");
+ return false;
+ } else {
+ ReportWarning("Message type \"" + descriptor->full_name() +
+ "\" has no field named \"" + field_name + "\".");
+ }
+ }
+ }
+
+ // Skips unknown field.
+ if (field == NULL) {
+ GOOGLE_CHECK(allow_unknown_field_);
+ // Try to guess the type of this field.
+ // If this field is not a message, there should be a ":" between the
+ // field name and the field value and also the field value should not
+ // start with "{" or "<" which indicates the beginning of a message body.
+ // If there is no ":" or there is a "{" or "<" after ":", this field has
+ // to be a message or the input is ill-formed.
+ if (TryConsume(":") && !LookingAt("{") && !LookingAt("<")) {
+ return SkipFieldValue();
+ } else {
+ return SkipFieldMessage();
+ }
+ }
+
+ if (singular_overwrite_policy_ == FORBID_SINGULAR_OVERWRITES) {
+ // Fail if the field is not repeated and it has already been specified.
+ if (!field->is_repeated() && reflection->HasField(*message, field)) {
+ ReportError("Non-repeated field \"" + field_name +
+ "\" is specified multiple times.");
+ return false;
+ }
+ // Fail if the field is a member of a oneof and another member has already
+ // been specified.
+ const OneofDescriptor* oneof = field->containing_oneof();
+ if (oneof != NULL && reflection->HasOneof(*message, oneof)) {
+ const FieldDescriptor* other_field =
+ reflection->GetOneofFieldDescriptor(*message, oneof);
+ ReportError("Field \"" + field_name + "\" is specified along with "
+ "field \"" + other_field->name() + "\", another member "
+ "of oneof \"" + oneof->name() + "\".");
+ return false;
+ }
+ }
+
+ // Perform special handling for embedded message types.
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // ':' is optional here.
+ TryConsume(":");
+ } else {
+ // ':' is required here.
+ DO(Consume(":"));
+ }
+
+ if (field->is_repeated() && TryConsume("[")) {
+ // Short repeated format, e.g. "foo: [1, 2, 3]"
+ while (true) {
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Perform special handling for embedded message types.
+ DO(ConsumeFieldMessage(message, reflection, field));
+ } else {
+ DO(ConsumeFieldValue(message, reflection, field));
+ }
+ if (TryConsume("]")) {
+ break;
+ }
+ DO(Consume(","));
+ }
+ } else if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ DO(ConsumeFieldMessage(message, reflection, field));
+ } else {
+ DO(ConsumeFieldValue(message, reflection, field));
+ }
+
+ // For historical reasons, fields may optionally be separated by commas or
+ // semicolons.
+ TryConsume(";") || TryConsume(",");
+
+ if (field->options().deprecated()) {
+ ReportWarning("text format contains deprecated field \""
+ + field_name + "\"");
+ }
+
+ // If a parse info tree exists, add the location for the parsed
+ // field.
+ if (parse_info_tree_ != NULL) {
+ RecordLocation(parse_info_tree_, field,
+ ParseLocation(start_line, start_column));
+ }
+
+ return true;
+ }
+
+ // Skips the next field including the field's name and value.
+ bool SkipField() {
+ string field_name;
+ if (TryConsume("[")) {
+ // Extension name.
+ DO(ConsumeFullTypeName(&field_name));
+ DO(Consume("]"));
+ } else {
+ DO(ConsumeIdentifier(&field_name));
+ }
+
+ // Try to guess the type of this field.
+ // If this field is not a message, there should be a ":" between the
+ // field name and the field value and also the field value should not
+ // start with "{" or "<" which indicates the beginning of a message body.
+ // If there is no ":" or there is a "{" or "<" after ":", this field has
+ // to be a message or the input is ill-formed.
+ if (TryConsume(":") && !LookingAt("{") && !LookingAt("<")) {
+ DO(SkipFieldValue());
+ } else {
+ DO(SkipFieldMessage());
+ }
+ // For historical reasons, fields may optionally be separated by commas or
+ // semicolons.
+ TryConsume(";") || TryConsume(",");
+ return true;
+ }
+
+ bool ConsumeFieldMessage(Message* message,
+ const Reflection* reflection,
+ const FieldDescriptor* field) {
+
+ // If the parse information tree is not NULL, create a nested one
+ // for the nested message.
+ ParseInfoTree* parent = parse_info_tree_;
+ if (parent != NULL) {
+ parse_info_tree_ = CreateNested(parent, field);
+ }
+
+ string delimiter;
+ DO(ConsumeMessageDelimiter(&delimiter));
+ if (field->is_repeated()) {
+ DO(ConsumeMessage(reflection->AddMessage(message, field), delimiter));
+ } else {
+ DO(ConsumeMessage(reflection->MutableMessage(message, field),
+ delimiter));
+ }
+
+ // Reset the parse information tree.
+ parse_info_tree_ = parent;
+ return true;
+ }
+
+ // Skips the whole body of a message including the beginning delimiter and
+ // the ending delimiter.
+ bool SkipFieldMessage() {
+ string delimiter;
+ DO(ConsumeMessageDelimiter(&delimiter));
+ while (!LookingAt(">") && !LookingAt("}")) {
+ DO(SkipField());
+ }
+ DO(Consume(delimiter));
+ return true;
+ }
+
+ bool ConsumeFieldValue(Message* message,
+ const Reflection* reflection,
+ const FieldDescriptor* field) {
+
+// Define an easy to use macro for setting fields. This macro checks
+// to see if the field is repeated (in which case we need to use the Add
+// methods or not (in which case we need to use the Set methods).
+#define SET_FIELD(CPPTYPE, VALUE) \
+ if (field->is_repeated()) { \
+ reflection->Add##CPPTYPE(message, field, VALUE); \
+ } else { \
+ reflection->Set##CPPTYPE(message, field, VALUE); \
+ } \
+
+ switch(field->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32: {
+ int64 value;
+ DO(ConsumeSignedInteger(&value, kint32max));
+ SET_FIELD(Int32, static_cast<int32>(value));
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ uint64 value;
+ DO(ConsumeUnsignedInteger(&value, kuint32max));
+ SET_FIELD(UInt32, static_cast<uint32>(value));
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_INT64: {
+ int64 value;
+ DO(ConsumeSignedInteger(&value, kint64max));
+ SET_FIELD(Int64, value);
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ uint64 value;
+ DO(ConsumeUnsignedInteger(&value, kuint64max));
+ SET_FIELD(UInt64, value);
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_FLOAT: {
+ double value;
+ DO(ConsumeDouble(&value));
+ SET_FIELD(Float, io::SafeDoubleToFloat(value));
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_DOUBLE: {
+ double value;
+ DO(ConsumeDouble(&value));
+ SET_FIELD(Double, value);
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string value;
+ DO(ConsumeString(&value));
+ SET_FIELD(String, value);
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ if (LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ uint64 value;
+ DO(ConsumeUnsignedInteger(&value, 1));
+ SET_FIELD(Bool, value);
+ } else {
+ string value;
+ DO(ConsumeIdentifier(&value));
+ if (value == "true" || value == "True" || value == "t") {
+ SET_FIELD(Bool, true);
+ } else if (value == "false" || value == "False" || value == "f") {
+ SET_FIELD(Bool, false);
+ } else {
+ ReportError("Invalid value for boolean field \"" + field->name()
+ + "\". Value: \"" + value + "\".");
+ return false;
+ }
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ string value;
+ const EnumDescriptor* enum_type = field->enum_type();
+ const EnumValueDescriptor* enum_value = NULL;
+
+ if (LookingAtType(io::Tokenizer::TYPE_IDENTIFIER)) {
+ DO(ConsumeIdentifier(&value));
+ // Find the enumeration value.
+ enum_value = enum_type->FindValueByName(value);
+
+ } else if (LookingAt("-") ||
+ LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ int64 int_value;
+ DO(ConsumeSignedInteger(&int_value, kint32max));
+ value = SimpleItoa(int_value); // for error reporting
+ enum_value = enum_type->FindValueByNumber(int_value);
+ } else {
+ ReportError("Expected integer or identifier, got: " +
+ tokenizer_.current().text);
+ return false;
+ }
+
+ if (enum_value == NULL) {
+ if (!allow_unknown_enum_) {
+ ReportError("Unknown enumeration value of \"" + value + "\" for "
+ "field \"" + field->name() + "\".");
+ return false;
+ } else {
+ ReportWarning("Unknown enumeration value of \"" + value + "\" for "
+ "field \"" + field->name() + "\".");
+ return true;
+ }
+ }
+
+ SET_FIELD(Enum, enum_value);
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_MESSAGE: {
+ // We should never get here. Put here instead of a default
+ // so that if new types are added, we get a nice compiler warning.
+ GOOGLE_LOG(FATAL) << "Reached an unintended state: CPPTYPE_MESSAGE";
+ break;
+ }
+ }
+#undef SET_FIELD
+ return true;
+ }
+
+ bool SkipFieldValue() {
+ if (LookingAtType(io::Tokenizer::TYPE_STRING)) {
+ while (LookingAtType(io::Tokenizer::TYPE_STRING)) {
+ tokenizer_.Next();
+ }
+ return true;
+ }
+ if (TryConsume("[")) {
+ while (true) {
+ if (!LookingAt("{") && !LookingAt("<")) {
+ DO(SkipFieldValue());
+ } else {
+ DO(SkipFieldMessage());
+ }
+ if (TryConsume("]")) {
+ break;
+ }
+ DO(Consume(","));
+ }
+ return true;
+ }
+ // Possible field values other than string:
+ // 12345 => TYPE_INTEGER
+ // -12345 => TYPE_SYMBOL + TYPE_INTEGER
+ // 1.2345 => TYPE_FLOAT
+ // -1.2345 => TYPE_SYMBOL + TYPE_FLOAT
+ // inf => TYPE_IDENTIFIER
+ // -inf => TYPE_SYMBOL + TYPE_IDENTIFIER
+ // TYPE_INTEGER => TYPE_IDENTIFIER
+ // Divides them into two group, one with TYPE_SYMBOL
+ // and the other without:
+ // Group one:
+ // 12345 => TYPE_INTEGER
+ // 1.2345 => TYPE_FLOAT
+ // inf => TYPE_IDENTIFIER
+ // TYPE_INTEGER => TYPE_IDENTIFIER
+ // Group two:
+ // -12345 => TYPE_SYMBOL + TYPE_INTEGER
+ // -1.2345 => TYPE_SYMBOL + TYPE_FLOAT
+ // -inf => TYPE_SYMBOL + TYPE_IDENTIFIER
+ // As we can see, the field value consists of an optional '-' and one of
+ // TYPE_INTEGER, TYPE_FLOAT and TYPE_IDENTIFIER.
+ bool has_minus = TryConsume("-");
+ if (!LookingAtType(io::Tokenizer::TYPE_INTEGER) &&
+ !LookingAtType(io::Tokenizer::TYPE_FLOAT) &&
+ !LookingAtType(io::Tokenizer::TYPE_IDENTIFIER)) {
+ return false;
+ }
+ // Combination of '-' and TYPE_IDENTIFIER may result in an invalid field
+ // value while other combinations all generate valid values.
+ // We check if the value of this combination is valid here.
+ // TYPE_IDENTIFIER after a '-' should be one of the float values listed
+ // below:
+ // inf, inff, infinity, nan
+ if (has_minus && LookingAtType(io::Tokenizer::TYPE_IDENTIFIER)) {
+ string text = tokenizer_.current().text;
+ LowerString(&text);
+ if (text != "inf" &&
+ text != "infinity" &&
+ text != "nan") {
+ ReportError("Invalid float number: " + text);
+ return false;
+ }
+ }
+ tokenizer_.Next();
+ return true;
+ }
+
+ // Returns true if the current token's text is equal to that specified.
+ bool LookingAt(const string& text) {
+ return tokenizer_.current().text == text;
+ }
+
+ // Returns true if the current token's type is equal to that specified.
+ bool LookingAtType(io::Tokenizer::TokenType token_type) {
+ return tokenizer_.current().type == token_type;
+ }
+
+ // Consumes an identifier and saves its value in the identifier parameter.
+ // Returns false if the token is not of type IDENTFIER.
+ bool ConsumeIdentifier(string* identifier) {
+ if (LookingAtType(io::Tokenizer::TYPE_IDENTIFIER)) {
+ *identifier = tokenizer_.current().text;
+ tokenizer_.Next();
+ return true;
+ }
+
+ // If allow_field_numer_ or allow_unknown_field_ is true, we should able
+ // to parse integer identifiers.
+ if ((allow_field_number_ || allow_unknown_field_)
+ && LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ *identifier = tokenizer_.current().text;
+ tokenizer_.Next();
+ return true;
+ }
+
+ ReportError("Expected identifier, got: " + tokenizer_.current().text);
+ return false;
+ }
+
+ // Consume a string of form "<id1>.<id2>....<idN>".
+ bool ConsumeFullTypeName(string* name) {
+ DO(ConsumeIdentifier(name));
+ while (TryConsume(".")) {
+ string part;
+ DO(ConsumeIdentifier(&part));
+ *name += ".";
+ *name += part;
+ }
+ return true;
+ }
+
+ // Consumes a string and saves its value in the text parameter.
+ // Returns false if the token is not of type STRING.
+ bool ConsumeString(string* text) {
+ if (!LookingAtType(io::Tokenizer::TYPE_STRING)) {
+ ReportError("Expected string, got: " + tokenizer_.current().text);
+ return false;
+ }
+
+ text->clear();
+ while (LookingAtType(io::Tokenizer::TYPE_STRING)) {
+ io::Tokenizer::ParseStringAppend(tokenizer_.current().text, text);
+
+ tokenizer_.Next();
+ }
+
+ return true;
+ }
+
+ // Consumes a uint64 and saves its value in the value parameter.
+ // Returns false if the token is not of type INTEGER.
+ bool ConsumeUnsignedInteger(uint64* value, uint64 max_value) {
+ if (!LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ ReportError("Expected integer, got: " + tokenizer_.current().text);
+ return false;
+ }
+
+ if (!io::Tokenizer::ParseInteger(tokenizer_.current().text,
+ max_value, value)) {
+ ReportError("Integer out of range (" + tokenizer_.current().text + ")");
+ return false;
+ }
+
+ tokenizer_.Next();
+ return true;
+ }
+
+ // Consumes an int64 and saves its value in the value parameter.
+ // Note that since the tokenizer does not support negative numbers,
+ // we actually may consume an additional token (for the minus sign) in this
+ // method. Returns false if the token is not an integer
+ // (signed or otherwise).
+ bool ConsumeSignedInteger(int64* value, uint64 max_value) {
+ bool negative = false;
+
+ if (TryConsume("-")) {
+ negative = true;
+ // Two's complement always allows one more negative integer than
+ // positive.
+ ++max_value;
+ }
+
+ uint64 unsigned_value;
+
+ DO(ConsumeUnsignedInteger(&unsigned_value, max_value));
+
+ if (negative) {
+ if ((static_cast<uint64>(kint64max) + 1) == unsigned_value) {
+ *value = kint64min;
+ } else {
+ *value = -static_cast<int64>(unsigned_value);
+ }
+ } else {
+ *value = static_cast<int64>(unsigned_value);
+ }
+
+ return true;
+ }
+
+ // Consumes a uint64 and saves its value in the value parameter.
+ // Accepts decimal numbers only, rejects hex or oct numbers.
+ bool ConsumeUnsignedDecimalInteger(uint64* value, uint64 max_value) {
+ if (!LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ ReportError("Expected integer, got: " + tokenizer_.current().text);
+ return false;
+ }
+
+ const string& text = tokenizer_.current().text;
+ if (IsHexNumber(text) || IsOctNumber(text)) {
+ ReportError("Expect a decimal number, got: " + text);
+ return false;
+ }
+
+ if (!io::Tokenizer::ParseInteger(text, max_value, value)) {
+ ReportError("Integer out of range (" + text + ")");
+ return false;
+ }
+
+ tokenizer_.Next();
+ return true;
+ }
+
+ // Consumes a double and saves its value in the value parameter.
+ // Note that since the tokenizer does not support negative numbers,
+ // we actually may consume an additional token (for the minus sign) in this
+ // method. Returns false if the token is not a double
+ // (signed or otherwise).
+ bool ConsumeDouble(double* value) {
+ bool negative = false;
+
+ if (TryConsume("-")) {
+ negative = true;
+ }
+
+ // A double can actually be an integer, according to the tokenizer.
+ // Therefore, we must check both cases here.
+ if (LookingAtType(io::Tokenizer::TYPE_INTEGER)) {
+ // We have found an integer value for the double.
+ uint64 integer_value;
+ DO(ConsumeUnsignedDecimalInteger(&integer_value, kuint64max));
+
+ *value = static_cast<double>(integer_value);
+ } else if (LookingAtType(io::Tokenizer::TYPE_FLOAT)) {
+ // We have found a float value for the double.
+ *value = io::Tokenizer::ParseFloat(tokenizer_.current().text);
+
+ // Mark the current token as consumed.
+ tokenizer_.Next();
+ } else if (LookingAtType(io::Tokenizer::TYPE_IDENTIFIER)) {
+ string text = tokenizer_.current().text;
+ LowerString(&text);
+ if (text == "inf" ||
+ text == "infinity") {
+ *value = std::numeric_limits<double>::infinity();
+ tokenizer_.Next();
+ } else if (text == "nan") {
+ *value = std::numeric_limits<double>::quiet_NaN();
+ tokenizer_.Next();
+ } else {
+ ReportError("Expected double, got: " + text);
+ return false;
+ }
+ } else {
+ ReportError("Expected double, got: " + tokenizer_.current().text);
+ return false;
+ }
+
+ if (negative) {
+ *value = -*value;
+ }
+
+ return true;
+ }
+
+ // Consumes Any::type_url value, of form "type.googleapis.com/full.type.Name"
+ // or "type.googleprod.com/full.type.Name"
+ bool ConsumeAnyTypeUrl(string* full_type_name, string* prefix) {
+ // TODO(saito) Extend Consume() to consume multiple tokens at once, so that
+ // this code can be written as just DO(Consume(kGoogleApisTypePrefix)).
+ string url1, url2, url3;
+ DO(ConsumeIdentifier(&url1)); // type
+ DO(Consume("."));
+ DO(ConsumeIdentifier(&url2)); // googleapis
+ DO(Consume("."));
+ DO(ConsumeIdentifier(&url3)); // com
+ DO(Consume("/"));
+ DO(ConsumeFullTypeName(full_type_name));
+
+ *prefix = url1 + "." + url2 + "." + url3 + "/";
+ if (*prefix != internal::kTypeGoogleApisComPrefix &&
+ *prefix != internal::kTypeGoogleProdComPrefix) {
+ ReportError("TextFormat::Parser for Any supports only "
+ "type.googleapis.com and type.googleprod.com, "
+ "but found \"" + *prefix + "\"");
+ return false;
+ }
+ return true;
+ }
+
+ // A helper function for reconstructing Any::value. Consumes a text of
+ // full_type_name, then serializes it into serialized_value. "pool" is used to
+ // look up and create a temporary object with full_type_name.
+ bool ConsumeAnyValue(const string& full_type_name, const DescriptorPool* pool,
+ string* serialized_value) {
+ const Descriptor* value_descriptor =
+ pool->FindMessageTypeByName(full_type_name);
+ if (value_descriptor == NULL) {
+ ReportError("Could not find type \"" + full_type_name +
+ "\" stored in google.protobuf.Any.");
+ return false;
+ }
+ DynamicMessageFactory factory;
+ const Message* value_prototype = factory.GetPrototype(value_descriptor);
+ if (value_prototype == NULL) {
+ return false;
+ }
+ google::protobuf::scoped_ptr<Message> value(value_prototype->New());
+ string sub_delimiter;
+ DO(ConsumeMessageDelimiter(&sub_delimiter));
+ DO(ConsumeMessage(value.get(), sub_delimiter));
+
+ if (allow_partial_) {
+ value->AppendPartialToString(serialized_value);
+ } else {
+ if (!value->IsInitialized()) {
+ ReportError(
+ "Value of type \"" + full_type_name +
+ "\" stored in google.protobuf.Any has missing required fields");
+ return false;
+ }
+ value->AppendToString(serialized_value);
+ }
+ return true;
+ }
+
+ // Consumes a token and confirms that it matches that specified in the
+ // value parameter. Returns false if the token found does not match that
+ // which was specified.
+ bool Consume(const string& value) {
+ const string& current_value = tokenizer_.current().text;
+
+ if (current_value != value) {
+ ReportError("Expected \"" + value + "\", found \"" + current_value
+ + "\".");
+ return false;
+ }
+
+ tokenizer_.Next();
+
+ return true;
+ }
+
+ // Attempts to consume the supplied value. Returns false if a the
+ // token found does not match the value specified.
+ bool TryConsume(const string& value) {
+ if (tokenizer_.current().text == value) {
+ tokenizer_.Next();
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ // An internal instance of the Tokenizer's error collector, used to
+ // collect any base-level parse errors and feed them to the ParserImpl.
+ class ParserErrorCollector : public io::ErrorCollector {
+ public:
+ explicit ParserErrorCollector(TextFormat::Parser::ParserImpl* parser) :
+ parser_(parser) { }
+
+ virtual ~ParserErrorCollector() { }
+
+ virtual void AddError(int line, int column, const string& message) {
+ parser_->ReportError(line, column, message);
+ }
+
+ virtual void AddWarning(int line, int column, const string& message) {
+ parser_->ReportWarning(line, column, message);
+ }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ParserErrorCollector);
+ TextFormat::Parser::ParserImpl* parser_;
+ };
+
+ io::ErrorCollector* error_collector_;
+ TextFormat::Finder* finder_;
+ ParseInfoTree* parse_info_tree_;
+ ParserErrorCollector tokenizer_error_collector_;
+ io::Tokenizer tokenizer_;
+ const Descriptor* root_message_type_;
+ SingularOverwritePolicy singular_overwrite_policy_;
+ const bool allow_case_insensitive_field_;
+ const bool allow_unknown_field_;
+ const bool allow_unknown_enum_;
+ const bool allow_field_number_;
+ const bool allow_partial_;
+ bool had_errors_;
+};
+
+#undef DO
+
+// ===========================================================================
+// Internal class for writing text to the io::ZeroCopyOutputStream. Adapted
+// from the Printer found in //google/protobuf/io/printer.h
+class TextFormat::Printer::TextGenerator {
+ public:
+ explicit TextGenerator(io::ZeroCopyOutputStream* output,
+ int initial_indent_level)
+ : output_(output),
+ buffer_(NULL),
+ buffer_size_(0),
+ at_start_of_line_(true),
+ failed_(false),
+ indent_(""),
+ initial_indent_level_(initial_indent_level) {
+ indent_.resize(initial_indent_level_ * 2, ' ');
+ }
+
+ ~TextGenerator() {
+ // Only BackUp() if we're sure we've successfully called Next() at least
+ // once.
+ if (!failed_ && buffer_size_ > 0) {
+ output_->BackUp(buffer_size_);
+ }
+ }
+
+ // Indent text by two spaces. After calling Indent(), two spaces will be
+ // inserted at the beginning of each line of text. Indent() may be called
+ // multiple times to produce deeper indents.
+ void Indent() {
+ indent_ += " ";
+ }
+
+ // Reduces the current indent level by two spaces, or crashes if the indent
+ // level is zero.
+ void Outdent() {
+ if (indent_.empty() ||
+ indent_.size() < initial_indent_level_ * 2) {
+ GOOGLE_LOG(DFATAL) << " Outdent() without matching Indent().";
+ return;
+ }
+
+ indent_.resize(indent_.size() - 2);
+ }
+
+ // Print text to the output stream.
+ void Print(const string& str) {
+ Print(str.data(), str.size());
+ }
+
+ // Print text to the output stream.
+ void Print(const char* text) {
+ Print(text, strlen(text));
+ }
+
+ // Print text to the output stream.
+ void Print(const char* text, size_t size) {
+ size_t pos = 0; // The number of bytes we've written so far.
+
+ for (size_t i = 0; i < size; i++) {
+ if (text[i] == '\n') {
+ // Saw newline. If there is more text, we may need to insert an indent
+ // here. So, write what we have so far, including the '\n'.
+ Write(text + pos, i - pos + 1);
+ pos = i + 1;
+
+ // Setting this true will cause the next Write() to insert an indent
+ // first.
+ at_start_of_line_ = true;
+ }
+ }
+
+ // Write the rest.
+ Write(text + pos, size - pos);
+ }
+
+ // True if any write to the underlying stream failed. (We don't just
+ // crash in this case because this is an I/O failure, not a programming
+ // error.)
+ bool failed() const { return failed_; }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TextGenerator);
+
+ void Write(const char* data, size_t size) {
+ if (failed_) return;
+ if (size == 0) return;
+
+ if (at_start_of_line_) {
+ // Insert an indent.
+ at_start_of_line_ = false;
+ Write(indent_.data(), indent_.size());
+ if (failed_) return;
+ }
+
+ while (size > buffer_size_) {
+ // Data exceeds space in the buffer. Copy what we can and request a
+ // new buffer.
+ memcpy(buffer_, data, buffer_size_);
+ data += buffer_size_;
+ size -= buffer_size_;
+ void* void_buffer;
+ failed_ = !output_->Next(&void_buffer, &buffer_size_);
+ if (failed_) return;
+ buffer_ = reinterpret_cast<char*>(void_buffer);
+ }
+
+ // Buffer is big enough to receive the data; copy it.
+ memcpy(buffer_, data, size);
+ buffer_ += size;
+ buffer_size_ -= size;
+ }
+
+ io::ZeroCopyOutputStream* const output_;
+ char* buffer_;
+ int buffer_size_;
+ bool at_start_of_line_;
+ bool failed_;
+
+ string indent_;
+ int initial_indent_level_;
+};
+
+// ===========================================================================
+
+TextFormat::Finder::~Finder() {
+}
+
+TextFormat::Parser::Parser()
+ : error_collector_(NULL),
+ finder_(NULL),
+ parse_info_tree_(NULL),
+ allow_partial_(false),
+ allow_case_insensitive_field_(false),
+ allow_unknown_field_(false),
+ allow_unknown_enum_(false),
+ allow_field_number_(false),
+ allow_relaxed_whitespace_(false),
+ allow_singular_overwrites_(false) {
+}
+
+TextFormat::Parser::~Parser() {}
+
+bool TextFormat::Parser::Parse(io::ZeroCopyInputStream* input,
+ Message* output) {
+ output->Clear();
+
+ ParserImpl::SingularOverwritePolicy overwrites_policy =
+ allow_singular_overwrites_
+ ? ParserImpl::ALLOW_SINGULAR_OVERWRITES
+ : ParserImpl::FORBID_SINGULAR_OVERWRITES;
+
+ ParserImpl parser(output->GetDescriptor(), input, error_collector_,
+ finder_, parse_info_tree_,
+ overwrites_policy,
+ allow_case_insensitive_field_, allow_unknown_field_,
+ allow_unknown_enum_, allow_field_number_,
+ allow_relaxed_whitespace_, allow_partial_);
+ return MergeUsingImpl(input, output, &parser);
+}
+
+bool TextFormat::Parser::ParseFromString(const string& input,
+ Message* output) {
+ io::ArrayInputStream input_stream(input.data(), input.size());
+ return Parse(&input_stream, output);
+}
+
+bool TextFormat::Parser::Merge(io::ZeroCopyInputStream* input,
+ Message* output) {
+ ParserImpl parser(output->GetDescriptor(), input, error_collector_,
+ finder_, parse_info_tree_,
+ ParserImpl::ALLOW_SINGULAR_OVERWRITES,
+ allow_case_insensitive_field_, allow_unknown_field_,
+ allow_unknown_enum_, allow_field_number_,
+ allow_relaxed_whitespace_, allow_partial_);
+ return MergeUsingImpl(input, output, &parser);
+}
+
+bool TextFormat::Parser::MergeFromString(const string& input,
+ Message* output) {
+ io::ArrayInputStream input_stream(input.data(), input.size());
+ return Merge(&input_stream, output);
+}
+
+bool TextFormat::Parser::MergeUsingImpl(io::ZeroCopyInputStream* /* input */,
+ Message* output,
+ ParserImpl* parser_impl) {
+ if (!parser_impl->Parse(output)) return false;
+ if (!allow_partial_ && !output->IsInitialized()) {
+ vector<string> missing_fields;
+ output->FindInitializationErrors(&missing_fields);
+ parser_impl->ReportError(-1, 0, "Message missing required fields: " +
+ Join(missing_fields, ", "));
+ return false;
+ }
+ return true;
+}
+
+bool TextFormat::Parser::ParseFieldValueFromString(
+ const string& input,
+ const FieldDescriptor* field,
+ Message* output) {
+ io::ArrayInputStream input_stream(input.data(), input.size());
+ ParserImpl parser(output->GetDescriptor(), &input_stream, error_collector_,
+ finder_, parse_info_tree_,
+ ParserImpl::ALLOW_SINGULAR_OVERWRITES,
+ allow_case_insensitive_field_, allow_unknown_field_,
+ allow_unknown_enum_, allow_field_number_,
+ allow_relaxed_whitespace_, allow_partial_);
+ return parser.ParseField(field, output);
+}
+
+/* static */ bool TextFormat::Parse(io::ZeroCopyInputStream* input,
+ Message* output) {
+ return Parser().Parse(input, output);
+}
+
+/* static */ bool TextFormat::Merge(io::ZeroCopyInputStream* input,
+ Message* output) {
+ return Parser().Merge(input, output);
+}
+
+/* static */ bool TextFormat::ParseFromString(const string& input,
+ Message* output) {
+ return Parser().ParseFromString(input, output);
+}
+
+/* static */ bool TextFormat::MergeFromString(const string& input,
+ Message* output) {
+ return Parser().MergeFromString(input, output);
+}
+
+// ===========================================================================
+
+// The default implementation for FieldValuePrinter. The base class just
+// does simple formatting. That way, deriving classes could decide to fallback
+// to that behavior.
+TextFormat::FieldValuePrinter::FieldValuePrinter() {}
+TextFormat::FieldValuePrinter::~FieldValuePrinter() {}
+string TextFormat::FieldValuePrinter::PrintBool(bool val) const {
+ return val ? "true" : "false";
+}
+string TextFormat::FieldValuePrinter::PrintInt32(int32 val) const {
+ return SimpleItoa(val);
+}
+string TextFormat::FieldValuePrinter::PrintUInt32(uint32 val) const {
+ return SimpleItoa(val);
+}
+string TextFormat::FieldValuePrinter::PrintInt64(int64 val) const {
+ return SimpleItoa(val);
+}
+string TextFormat::FieldValuePrinter::PrintUInt64(uint64 val) const {
+ return SimpleItoa(val);
+}
+string TextFormat::FieldValuePrinter::PrintFloat(float val) const {
+ return SimpleFtoa(val);
+}
+string TextFormat::FieldValuePrinter::PrintDouble(double val) const {
+ return SimpleDtoa(val);
+}
+string TextFormat::FieldValuePrinter::PrintString(const string& val) const {
+ string printed("\"");
+ CEscapeAndAppend(val, &printed);
+ printed.push_back('\"');
+ return printed;
+}
+string TextFormat::FieldValuePrinter::PrintBytes(const string& val) const {
+ return PrintString(val);
+}
+string TextFormat::FieldValuePrinter::PrintEnum(int32 val,
+ const string& name) const {
+ return name;
+}
+string TextFormat::FieldValuePrinter::PrintFieldName(
+ const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field) const {
+ if (field->is_extension()) {
+ // We special-case MessageSet elements for compatibility with proto1.
+ if (field->containing_type()->options().message_set_wire_format()
+ && field->type() == FieldDescriptor::TYPE_MESSAGE
+ && field->is_optional()
+ && field->extension_scope() == field->message_type()) {
+ return StrCat("[", field->message_type()->full_name(), "]");
+ } else {
+ return StrCat("[", field->full_name(), "]");
+ }
+ } else if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ // Groups must be serialized with their original capitalization.
+ return field->message_type()->name();
+ } else {
+ return field->name();
+ }
+}
+string TextFormat::FieldValuePrinter::PrintMessageStart(
+ const Message& message,
+ int field_index,
+ int field_count,
+ bool single_line_mode) const {
+ return single_line_mode ? " { " : " {\n";
+}
+string TextFormat::FieldValuePrinter::PrintMessageEnd(
+ const Message& message,
+ int field_index,
+ int field_count,
+ bool single_line_mode) const {
+ return single_line_mode ? "} " : "}\n";
+}
+
+namespace {
+// Our own specialization: for UTF8 escaped strings.
+class FieldValuePrinterUtf8Escaping : public TextFormat::FieldValuePrinter {
+ public:
+ virtual string PrintString(const string& val) const {
+ return StrCat("\"", strings::Utf8SafeCEscape(val), "\"");
+ }
+ virtual string PrintBytes(const string& val) const {
+ return TextFormat::FieldValuePrinter::PrintString(val);
+ }
+};
+
+} // namespace
+
+TextFormat::Printer::Printer()
+ : initial_indent_level_(0),
+ single_line_mode_(false),
+ use_field_number_(false),
+ use_short_repeated_primitives_(false),
+ hide_unknown_fields_(false),
+ print_message_fields_in_index_order_(false),
+ expand_any_(false),
+ truncate_string_field_longer_than_(0LL) {
+ SetUseUtf8StringEscaping(false);
+}
+
+TextFormat::Printer::~Printer() {
+ STLDeleteValues(&custom_printers_);
+}
+
+void TextFormat::Printer::SetUseUtf8StringEscaping(bool as_utf8) {
+ SetDefaultFieldValuePrinter(as_utf8
+ ? new FieldValuePrinterUtf8Escaping()
+ : new FieldValuePrinter());
+}
+
+void TextFormat::Printer::SetDefaultFieldValuePrinter(
+ const FieldValuePrinter* printer) {
+ default_field_value_printer_.reset(printer);
+}
+
+bool TextFormat::Printer::RegisterFieldValuePrinter(
+ const FieldDescriptor* field,
+ const FieldValuePrinter* printer) {
+ return field != NULL && printer != NULL &&
+ custom_printers_.insert(std::make_pair(field, printer)).second;
+}
+
+bool TextFormat::Printer::PrintToString(const Message& message,
+ string* output) const {
+ GOOGLE_DCHECK(output) << "output specified is NULL";
+
+ output->clear();
+ io::StringOutputStream output_stream(output);
+
+ return Print(message, &output_stream);
+}
+
+bool TextFormat::Printer::PrintUnknownFieldsToString(
+ const UnknownFieldSet& unknown_fields,
+ string* output) const {
+ GOOGLE_DCHECK(output) << "output specified is NULL";
+
+ output->clear();
+ io::StringOutputStream output_stream(output);
+ return PrintUnknownFields(unknown_fields, &output_stream);
+}
+
+bool TextFormat::Printer::Print(const Message& message,
+ io::ZeroCopyOutputStream* output) const {
+ TextGenerator generator(output, initial_indent_level_);
+
+ Print(message, generator);
+
+ // Output false if the generator failed internally.
+ return !generator.failed();
+}
+
+bool TextFormat::Printer::PrintUnknownFields(
+ const UnknownFieldSet& unknown_fields,
+ io::ZeroCopyOutputStream* output) const {
+ TextGenerator generator(output, initial_indent_level_);
+
+ PrintUnknownFields(unknown_fields, generator);
+
+ // Output false if the generator failed internally.
+ return !generator.failed();
+}
+
+namespace {
+// Comparison functor for sorting FieldDescriptors by field index.
+struct FieldIndexSorter {
+ bool operator()(const FieldDescriptor* left,
+ const FieldDescriptor* right) const {
+ return left->index() < right->index();
+ }
+};
+
+} // namespace
+
+bool TextFormat::Printer::PrintAny(const Message& message,
+ TextGenerator& generator) const {
+ const FieldDescriptor* type_url_field;
+ const FieldDescriptor* value_field;
+ if (!internal::GetAnyFieldDescriptors(message, &type_url_field,
+ &value_field)) {
+ return false;
+ }
+
+ const Reflection* reflection = message.GetReflection();
+
+ // Extract the full type name from the type_url field.
+ const string& type_url = reflection->GetString(message, type_url_field);
+ string full_type_name;
+ if (!internal::ParseAnyTypeUrl(type_url, &full_type_name)) {
+ return false;
+ }
+
+ // Print the "value" in text.
+ const google::protobuf::Descriptor* value_descriptor =
+ message.GetDescriptor()->file()->pool()->FindMessageTypeByName(
+ full_type_name);
+ if (value_descriptor == NULL) {
+ GOOGLE_LOG(WARNING) << "Proto type " << type_url << " not found";
+ return false;
+ }
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<google::protobuf::Message> value_message(
+ factory.GetPrototype(value_descriptor)->New());
+ string serialized_value = reflection->GetString(message, value_field);
+ if (!value_message->ParseFromString(serialized_value)) {
+ GOOGLE_LOG(WARNING) << type_url << ": failed to parse contents";
+ return false;
+ }
+ generator.Print(StrCat("[", type_url, "]"));
+ const FieldValuePrinter* printer = FindWithDefault(
+ custom_printers_, value_field, default_field_value_printer_.get());
+ generator.Print(
+ printer->PrintMessageStart(message, -1, 0, single_line_mode_));
+ generator.Indent();
+ Print(*value_message, generator);
+ generator.Outdent();
+ generator.Print(printer->PrintMessageEnd(message, -1, 0, single_line_mode_));
+ return true;
+}
+
+void TextFormat::Printer::Print(const Message& message,
+ TextGenerator& generator) const {
+ const Descriptor* descriptor = message.GetDescriptor();
+ const Reflection* reflection = message.GetReflection();
+ if (descriptor->full_name() == internal::kAnyFullTypeName && expand_any_ &&
+ PrintAny(message, generator)) {
+ return;
+ }
+ vector<const FieldDescriptor*> fields;
+ reflection->ListFields(message, &fields);
+ if (print_message_fields_in_index_order_) {
+ std::sort(fields.begin(), fields.end(), FieldIndexSorter());
+ }
+ for (int i = 0; i < fields.size(); i++) {
+ PrintField(message, reflection, fields[i], generator);
+ }
+ if (!hide_unknown_fields_) {
+ PrintUnknownFields(reflection->GetUnknownFields(message), generator);
+ }
+}
+
+void TextFormat::Printer::PrintFieldValueToString(
+ const Message& message,
+ const FieldDescriptor* field,
+ int index,
+ string* output) const {
+
+ GOOGLE_DCHECK(output) << "output specified is NULL";
+
+ output->clear();
+ io::StringOutputStream output_stream(output);
+ TextGenerator generator(&output_stream, initial_indent_level_);
+
+ PrintFieldValue(message, message.GetReflection(), field, index, generator);
+}
+
+class MapEntryMessageComparator {
+ public:
+ explicit MapEntryMessageComparator(const Descriptor* descriptor)
+ : field_(descriptor->field(0)) {}
+
+ bool operator()(const Message* a, const Message* b) {
+ const Reflection* reflection = a->GetReflection();
+ switch (field_->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_BOOL: {
+ bool first = reflection->GetBool(*a, field_);
+ bool second = reflection->GetBool(*b, field_);
+ return first < second;
+ }
+ case FieldDescriptor::CPPTYPE_INT32: {
+ int32 first = reflection->GetInt32(*a, field_);
+ int32 second = reflection->GetInt32(*b, field_);
+ return first < second;
+ }
+ case FieldDescriptor::CPPTYPE_INT64: {
+ int64 first = reflection->GetInt64(*a, field_);
+ int64 second = reflection->GetInt64(*b, field_);
+ return first < second;
+ }
+ case FieldDescriptor::CPPTYPE_UINT32: {
+ uint32 first = reflection->GetUInt32(*a, field_);
+ uint32 second = reflection->GetUInt32(*b, field_);
+ return first < second;
+ }
+ case FieldDescriptor::CPPTYPE_UINT64: {
+ uint64 first = reflection->GetUInt64(*a, field_);
+ uint64 second = reflection->GetUInt64(*b, field_);
+ return first < second;
+ }
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string first = reflection->GetString(*a, field_);
+ string second = reflection->GetString(*b, field_);
+ return first < second;
+ }
+ default:
+ GOOGLE_LOG(DFATAL) << "Invalid key for map field.";
+ return true;
+ }
+ }
+
+ private:
+ const FieldDescriptor* field_;
+};
+
+void TextFormat::Printer::PrintField(const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ TextGenerator& generator) const {
+ if (use_short_repeated_primitives_ &&
+ field->is_repeated() &&
+ field->cpp_type() != FieldDescriptor::CPPTYPE_STRING &&
+ field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ PrintShortRepeatedField(message, reflection, field, generator);
+ return;
+ }
+
+ int count = 0;
+
+ if (field->is_repeated()) {
+ count = reflection->FieldSize(message, field);
+ } else if (reflection->HasField(message, field)) {
+ count = 1;
+ }
+
+ std::vector<const Message*> sorted_map_field;
+ if (field->is_map()) {
+ const RepeatedPtrField<Message>& map_field =
+ reflection->GetRepeatedPtrField<Message>(message, field);
+ for (RepeatedPtrField<Message>::const_pointer_iterator it =
+ map_field.pointer_begin();
+ it != map_field.pointer_end(); ++it) {
+ sorted_map_field.push_back(*it);
+ }
+
+ MapEntryMessageComparator comparator(field->message_type());
+ std::stable_sort(sorted_map_field.begin(), sorted_map_field.end(),
+ comparator);
+ }
+
+ for (int j = 0; j < count; ++j) {
+ const int field_index = field->is_repeated() ? j : -1;
+
+ PrintFieldName(message, reflection, field, generator);
+
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ const FieldValuePrinter* printer = FindWithDefault(
+ custom_printers_, field, default_field_value_printer_.get());
+ const Message& sub_message =
+ field->is_repeated()
+ ? (field->is_map()
+ ? *sorted_map_field[j]
+ : reflection->GetRepeatedMessage(message, field, j))
+ : reflection->GetMessage(message, field);
+ generator.Print(
+ printer->PrintMessageStart(
+ sub_message, field_index, count, single_line_mode_));
+ generator.Indent();
+ Print(sub_message, generator);
+ generator.Outdent();
+ generator.Print(
+ printer->PrintMessageEnd(
+ sub_message, field_index, count, single_line_mode_));
+ } else {
+ generator.Print(": ");
+ // Write the field value.
+ PrintFieldValue(message, reflection, field, field_index, generator);
+ if (single_line_mode_) {
+ generator.Print(" ");
+ } else {
+ generator.Print("\n");
+ }
+ }
+ }
+}
+
+void TextFormat::Printer::PrintShortRepeatedField(
+ const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ TextGenerator& generator) const {
+ // Print primitive repeated field in short form.
+ PrintFieldName(message, reflection, field, generator);
+
+ int size = reflection->FieldSize(message, field);
+ generator.Print(": [");
+ for (int i = 0; i < size; i++) {
+ if (i > 0) generator.Print(", ");
+ PrintFieldValue(message, reflection, field, i, generator);
+ }
+ if (single_line_mode_) {
+ generator.Print("] ");
+ } else {
+ generator.Print("]\n");
+ }
+}
+
+void TextFormat::Printer::PrintFieldName(const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ TextGenerator& generator) const {
+ // if use_field_number_ is true, prints field number instead
+ // of field name.
+ if (use_field_number_) {
+ generator.Print(SimpleItoa(field->number()));
+ return;
+ }
+
+ const FieldValuePrinter* printer = FindWithDefault(
+ custom_printers_, field, default_field_value_printer_.get());
+ generator.Print(printer->PrintFieldName(message, reflection, field));
+}
+
+void TextFormat::Printer::PrintFieldValue(
+ const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ int index,
+ TextGenerator& generator) const {
+ GOOGLE_DCHECK(field->is_repeated() || (index == -1))
+ << "Index must be -1 for non-repeated fields";
+
+ const FieldValuePrinter* printer
+ = FindWithDefault(custom_printers_, field,
+ default_field_value_printer_.get());
+
+ switch (field->cpp_type()) {
+#define OUTPUT_FIELD(CPPTYPE, METHOD) \
+ case FieldDescriptor::CPPTYPE_##CPPTYPE: \
+ generator.Print(printer->Print##METHOD(field->is_repeated() \
+ ? reflection->GetRepeated##METHOD(message, field, index) \
+ : reflection->Get##METHOD(message, field))); \
+ break
+
+ OUTPUT_FIELD( INT32, Int32);
+ OUTPUT_FIELD( INT64, Int64);
+ OUTPUT_FIELD(UINT32, UInt32);
+ OUTPUT_FIELD(UINT64, UInt64);
+ OUTPUT_FIELD( FLOAT, Float);
+ OUTPUT_FIELD(DOUBLE, Double);
+ OUTPUT_FIELD( BOOL, Bool);
+#undef OUTPUT_FIELD
+
+ case FieldDescriptor::CPPTYPE_STRING: {
+ string scratch;
+ const string& value = field->is_repeated()
+ ? reflection->GetRepeatedStringReference(
+ message, field, index, &scratch)
+ : reflection->GetStringReference(message, field, &scratch);
+ const string* value_to_print = &value;
+ string truncated_value;
+ if (truncate_string_field_longer_than_ > 0 &&
+ truncate_string_field_longer_than_ < value.size()) {
+ truncated_value = value.substr(0, truncate_string_field_longer_than_) +
+ "...<truncated>...";
+ value_to_print = &truncated_value;
+ }
+ if (field->type() == FieldDescriptor::TYPE_STRING) {
+ generator.Print(printer->PrintString(*value_to_print));
+ } else {
+ GOOGLE_DCHECK_EQ(field->type(), FieldDescriptor::TYPE_BYTES);
+ generator.Print(printer->PrintBytes(*value_to_print));
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_ENUM: {
+ int enum_value = field->is_repeated()
+ ? reflection->GetRepeatedEnumValue(message, field, index)
+ : reflection->GetEnumValue(message, field);
+ const EnumValueDescriptor* enum_desc =
+ field->enum_type()->FindValueByNumber(enum_value);
+ if (enum_desc != NULL) {
+ generator.Print(printer->PrintEnum(enum_value, enum_desc->name()));
+ } else {
+ // Ordinarily, enum_desc should not be null, because proto2 has the
+ // invariant that set enum field values must be in-range, but with the
+ // new integer-based API for enums (or the RepeatedField<int> loophole),
+ // it is possible for the user to force an unknown integer value. So we
+ // simply use the integer value itself as the enum value name in this
+ // case.
+ generator.Print(printer->PrintEnum(enum_value,
+ StringPrintf("%d", enum_value)));
+ }
+ break;
+ }
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ Print(field->is_repeated()
+ ? reflection->GetRepeatedMessage(message, field, index)
+ : reflection->GetMessage(message, field),
+ generator);
+ break;
+ }
+}
+
+/* static */ bool TextFormat::Print(const Message& message,
+ io::ZeroCopyOutputStream* output) {
+ return Printer().Print(message, output);
+}
+
+/* static */ bool TextFormat::PrintUnknownFields(
+ const UnknownFieldSet& unknown_fields,
+ io::ZeroCopyOutputStream* output) {
+ return Printer().PrintUnknownFields(unknown_fields, output);
+}
+
+/* static */ bool TextFormat::PrintToString(
+ const Message& message, string* output) {
+ return Printer().PrintToString(message, output);
+}
+
+/* static */ bool TextFormat::PrintUnknownFieldsToString(
+ const UnknownFieldSet& unknown_fields, string* output) {
+ return Printer().PrintUnknownFieldsToString(unknown_fields, output);
+}
+
+/* static */ void TextFormat::PrintFieldValueToString(
+ const Message& message,
+ const FieldDescriptor* field,
+ int index,
+ string* output) {
+ return Printer().PrintFieldValueToString(message, field, index, output);
+}
+
+/* static */ bool TextFormat::ParseFieldValueFromString(
+ const string& input,
+ const FieldDescriptor* field,
+ Message* message) {
+ return Parser().ParseFieldValueFromString(input, field, message);
+}
+
+// Prints an integer as hex with a fixed number of digits dependent on the
+// integer type.
+template<typename IntType>
+static string PaddedHex(IntType value) {
+ string result;
+ result.reserve(sizeof(value) * 2);
+ for (int i = sizeof(value) * 2 - 1; i >= 0; i--) {
+ result.push_back(int_to_hex_digit(value >> (i*4) & 0x0F));
+ }
+ return result;
+}
+
+void TextFormat::Printer::PrintUnknownFields(
+ const UnknownFieldSet& unknown_fields, TextGenerator& generator) const {
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ const UnknownField& field = unknown_fields.field(i);
+ string field_number = SimpleItoa(field.number());
+
+ switch (field.type()) {
+ case UnknownField::TYPE_VARINT:
+ generator.Print(field_number);
+ generator.Print(": ");
+ generator.Print(SimpleItoa(field.varint()));
+ if (single_line_mode_) {
+ generator.Print(" ");
+ } else {
+ generator.Print("\n");
+ }
+ break;
+ case UnknownField::TYPE_FIXED32: {
+ generator.Print(field_number);
+ generator.Print(": 0x");
+ generator.Print(
+ StrCat(strings::Hex(field.fixed32(), strings::ZERO_PAD_8)));
+ if (single_line_mode_) {
+ generator.Print(" ");
+ } else {
+ generator.Print("\n");
+ }
+ break;
+ }
+ case UnknownField::TYPE_FIXED64: {
+ generator.Print(field_number);
+ generator.Print(": 0x");
+ generator.Print(
+ StrCat(strings::Hex(field.fixed64(), strings::ZERO_PAD_16)));
+ if (single_line_mode_) {
+ generator.Print(" ");
+ } else {
+ generator.Print("\n");
+ }
+ break;
+ }
+ case UnknownField::TYPE_LENGTH_DELIMITED: {
+ generator.Print(field_number);
+ const string& value = field.length_delimited();
+ UnknownFieldSet embedded_unknown_fields;
+ if (!value.empty() && embedded_unknown_fields.ParseFromString(value)) {
+ // This field is parseable as a Message.
+ // So it is probably an embedded message.
+ if (single_line_mode_) {
+ generator.Print(" { ");
+ } else {
+ generator.Print(" {\n");
+ generator.Indent();
+ }
+ PrintUnknownFields(embedded_unknown_fields, generator);
+ if (single_line_mode_) {
+ generator.Print("} ");
+ } else {
+ generator.Outdent();
+ generator.Print("}\n");
+ }
+ } else {
+ // This field is not parseable as a Message.
+ // So it is probably just a plain string.
+ string printed(": \"");
+ CEscapeAndAppend(value, &printed);
+ printed.append(single_line_mode_ ? "\" " : "\"\n");
+ generator.Print(printed);
+ }
+ break;
+ }
+ case UnknownField::TYPE_GROUP:
+ generator.Print(field_number);
+ if (single_line_mode_) {
+ generator.Print(" { ");
+ } else {
+ generator.Print(" {\n");
+ generator.Indent();
+ }
+ PrintUnknownFields(field.group(), generator);
+ if (single_line_mode_) {
+ generator.Print("} ");
+ } else {
+ generator.Outdent();
+ generator.Print("}\n");
+ }
+ break;
+ }
+ }
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/text_format.h b/third_party/protobuf/3.0.0/src/google/protobuf/text_format.h
new file mode 100644
index 0000000000..ef3d4a8fd7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/text_format.h
@@ -0,0 +1,517 @@
+// 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: jschorr@google.com (Joseph Schorr)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// Utilities for printing and parsing protocol messages in a human-readable,
+// text-based format.
+
+#ifndef GOOGLE_PROTOBUF_TEXT_FORMAT_H__
+#define GOOGLE_PROTOBUF_TEXT_FORMAT_H__
+
+#include <map>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+
+namespace google {
+namespace protobuf {
+
+namespace io {
+ class ErrorCollector; // tokenizer.h
+}
+
+// This class implements protocol buffer text format. Printing and parsing
+// protocol messages in text format is useful for debugging and human editing
+// of messages.
+//
+// This class is really a namespace that contains only static methods.
+class LIBPROTOBUF_EXPORT TextFormat {
+ public:
+ // Outputs a textual representation of the given message to the given
+ // output stream.
+ static bool Print(const Message& message, io::ZeroCopyOutputStream* output);
+
+ // Print the fields in an UnknownFieldSet. They are printed by tag number
+ // only. Embedded messages are heuristically identified by attempting to
+ // parse them.
+ static bool PrintUnknownFields(const UnknownFieldSet& unknown_fields,
+ io::ZeroCopyOutputStream* output);
+
+ // Like Print(), but outputs directly to a string.
+ static bool PrintToString(const Message& message, string* output);
+
+ // Like PrintUnknownFields(), but outputs directly to a string.
+ static bool PrintUnknownFieldsToString(const UnknownFieldSet& unknown_fields,
+ string* output);
+
+ // Outputs a textual representation of the value of the field supplied on
+ // the message supplied. For non-repeated fields, an index of -1 must
+ // be supplied. Note that this method will print the default value for a
+ // field if it is not set.
+ static void PrintFieldValueToString(const Message& message,
+ const FieldDescriptor* field,
+ int index,
+ string* output);
+
+ // The default printer that converts scalar values from fields into
+ // their string representation.
+ // You can derive from this FieldValuePrinter if you want to have
+ // fields to be printed in a different way and register it at the
+ // Printer.
+ class LIBPROTOBUF_EXPORT FieldValuePrinter {
+ public:
+ FieldValuePrinter();
+ virtual ~FieldValuePrinter();
+ virtual string PrintBool(bool val) const;
+ virtual string PrintInt32(int32 val) const;
+ virtual string PrintUInt32(uint32 val) const;
+ virtual string PrintInt64(int64 val) const;
+ virtual string PrintUInt64(uint64 val) const;
+ virtual string PrintFloat(float val) const;
+ virtual string PrintDouble(double val) const;
+ virtual string PrintString(const string& val) const;
+ virtual string PrintBytes(const string& val) const;
+ virtual string PrintEnum(int32 val, const string& name) const;
+ virtual string PrintFieldName(const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field) const;
+ virtual string PrintMessageStart(const Message& message,
+ int field_index,
+ int field_count,
+ bool single_line_mode) const;
+ virtual string PrintMessageEnd(const Message& message,
+ int field_index,
+ int field_count,
+ bool single_line_mode) const;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldValuePrinter);
+ };
+
+ // Class for those users which require more fine-grained control over how
+ // a protobuffer message is printed out.
+ class LIBPROTOBUF_EXPORT Printer {
+ public:
+ Printer();
+ ~Printer();
+
+ // Like TextFormat::Print
+ bool Print(const Message& message, io::ZeroCopyOutputStream* output) const;
+ // Like TextFormat::PrintUnknownFields
+ bool PrintUnknownFields(const UnknownFieldSet& unknown_fields,
+ io::ZeroCopyOutputStream* output) const;
+ // Like TextFormat::PrintToString
+ bool PrintToString(const Message& message, string* output) const;
+ // Like TextFormat::PrintUnknownFieldsToString
+ bool PrintUnknownFieldsToString(const UnknownFieldSet& unknown_fields,
+ string* output) const;
+ // Like TextFormat::PrintFieldValueToString
+ void PrintFieldValueToString(const Message& message,
+ const FieldDescriptor* field,
+ int index,
+ string* output) const;
+
+ // Adjust the initial indent level of all output. Each indent level is
+ // equal to two spaces.
+ void SetInitialIndentLevel(int indent_level) {
+ initial_indent_level_ = indent_level;
+ }
+
+ // If printing in single line mode, then the entire message will be output
+ // on a single line with no line breaks.
+ void SetSingleLineMode(bool single_line_mode) {
+ single_line_mode_ = single_line_mode;
+ }
+
+ bool IsInSingleLineMode() {
+ return single_line_mode_;
+ }
+
+ // If use_field_number is true, uses field number instead of field name.
+ void SetUseFieldNumber(bool use_field_number) {
+ use_field_number_ = use_field_number;
+ }
+
+ // Set true to print repeated primitives in a format like:
+ // field_name: [1, 2, 3, 4]
+ // instead of printing each value on its own line. Short format applies
+ // only to primitive values -- i.e. everything except strings and
+ // sub-messages/groups.
+ void SetUseShortRepeatedPrimitives(bool use_short_repeated_primitives) {
+ use_short_repeated_primitives_ = use_short_repeated_primitives;
+ }
+
+ // Set true to output UTF-8 instead of ASCII. The only difference
+ // is that bytes >= 0x80 in string fields will not be escaped,
+ // because they are assumed to be part of UTF-8 multi-byte
+ // sequences. This will change the default FieldValuePrinter.
+ void SetUseUtf8StringEscaping(bool as_utf8);
+
+ // Set the default FieldValuePrinter that is used for all fields that
+ // don't have a field-specific printer registered.
+ // Takes ownership of the printer.
+ void SetDefaultFieldValuePrinter(const FieldValuePrinter* printer);
+
+ // Sets whether we want to hide unknown fields or not.
+ // Usually unknown fields are printed in a generic way that includes the
+ // tag number of the field instead of field name. However, sometimes it
+ // is useful to be able to print the message without unknown fields (e.g.
+ // for the python protobuf version to maintain consistency between its pure
+ // python and c++ implementations).
+ void SetHideUnknownFields(bool hide) {
+ hide_unknown_fields_ = hide;
+ }
+
+ // If print_message_fields_in_index_order is true, print fields of a proto
+ // message using the order defined in source code instead of the field
+ // number. By default, use the field number order.
+ void SetPrintMessageFieldsInIndexOrder(
+ bool print_message_fields_in_index_order) {
+ print_message_fields_in_index_order_ =
+ print_message_fields_in_index_order;
+ }
+
+ // If expand==true, expand google.protobuf.Any payloads. The output
+ // will be of form
+ // [type_url] { <value_printed_in_text> }
+ //
+ // If expand==false, print Any using the default printer. The output will
+ // look like
+ // type_url: "<type_url>" value: "serialized_content"
+ void SetExpandAny(bool expand) {
+ expand_any_ = expand;
+ }
+
+ // If non-zero, we truncate all string fields that are longer than this
+ // threshold. This is useful when the proto message has very long strings,
+ // e.g., dump of encoded image file.
+ //
+ // NOTE(hfgong): Setting a non-zero value breaks round-trip safe
+ // property of TextFormat::Printer. That is, from the printed message, we
+ // cannot fully recover the original string field any more.
+ void SetTruncateStringFieldLongerThan(
+ const int64 truncate_string_field_longer_than) {
+ truncate_string_field_longer_than_ = truncate_string_field_longer_than;
+ }
+
+ // Register a custom field-specific FieldValuePrinter for fields
+ // with a particular FieldDescriptor.
+ // Returns "true" if the registration succeeded, or "false", if there is
+ // already a printer for that FieldDescriptor.
+ // Takes ownership of the printer on successful registration.
+ bool RegisterFieldValuePrinter(const FieldDescriptor* field,
+ const FieldValuePrinter* printer);
+
+ private:
+ // Forward declaration of an internal class used to print the text
+ // output to the OutputStream (see text_format.cc for implementation).
+ class TextGenerator;
+
+ // Internal Print method, used for writing to the OutputStream via
+ // the TextGenerator class.
+ void Print(const Message& message,
+ TextGenerator& generator) const;
+
+ // Print a single field.
+ void PrintField(const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ TextGenerator& generator) const;
+
+ // Print a repeated primitive field in short form.
+ void PrintShortRepeatedField(const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ TextGenerator& generator) const;
+
+ // Print the name of a field -- i.e. everything that comes before the
+ // ':' for a single name/value pair.
+ void PrintFieldName(const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ TextGenerator& generator) const;
+
+ // Outputs a textual representation of the value of the field supplied on
+ // the message supplied or the default value if not set.
+ void PrintFieldValue(const Message& message,
+ const Reflection* reflection,
+ const FieldDescriptor* field,
+ int index,
+ TextGenerator& generator) const;
+
+ // Print the fields in an UnknownFieldSet. They are printed by tag number
+ // only. Embedded messages are heuristically identified by attempting to
+ // parse them.
+ void PrintUnknownFields(const UnknownFieldSet& unknown_fields,
+ TextGenerator& generator) const;
+
+ bool PrintAny(const Message& message, TextGenerator& generator) const;
+
+ int initial_indent_level_;
+
+ bool single_line_mode_;
+
+ bool use_field_number_;
+
+ bool use_short_repeated_primitives_;
+
+ bool hide_unknown_fields_;
+
+ bool print_message_fields_in_index_order_;
+
+ bool expand_any_;
+
+ int64 truncate_string_field_longer_than_;
+
+ google::protobuf::scoped_ptr<const FieldValuePrinter> default_field_value_printer_;
+ typedef map<const FieldDescriptor*,
+ const FieldValuePrinter*> CustomPrinterMap;
+ CustomPrinterMap custom_printers_;
+ };
+
+ // Parses a text-format protocol message from the given input stream to
+ // the given message object. This function parses the human-readable format
+ // written by Print(). Returns true on success. The message is cleared first,
+ // even if the function fails -- See Merge() to avoid this behavior.
+ //
+ // Example input: "user {\n id: 123 extra { gender: MALE language: 'en' }\n}"
+ //
+ // One use for this function is parsing handwritten strings in test code.
+ // Another use is to parse the output from google::protobuf::Message::DebugString()
+ // (or ShortDebugString()), because these functions output using
+ // google::protobuf::TextFormat::Print().
+ //
+ // If you would like to read a protocol buffer serialized in the
+ // (non-human-readable) binary wire format, see
+ // google::protobuf::MessageLite::ParseFromString().
+ static bool Parse(io::ZeroCopyInputStream* input, Message* output);
+ // Like Parse(), but reads directly from a string.
+ static bool ParseFromString(const string& input, Message* output);
+
+ // Like Parse(), but the data is merged into the given message, as if
+ // using Message::MergeFrom().
+ static bool Merge(io::ZeroCopyInputStream* input, Message* output);
+ // Like Merge(), but reads directly from a string.
+ static bool MergeFromString(const string& input, Message* output);
+
+ // Parse the given text as a single field value and store it into the
+ // given field of the given message. If the field is a repeated field,
+ // the new value will be added to the end
+ static bool ParseFieldValueFromString(const string& input,
+ const FieldDescriptor* field,
+ Message* message);
+
+ // Interface that TextFormat::Parser can use to find extensions.
+ // This class may be extended in the future to find more information
+ // like fields, etc.
+ class LIBPROTOBUF_EXPORT Finder {
+ public:
+ virtual ~Finder();
+
+ // Try to find an extension of *message by fully-qualified field
+ // name. Returns NULL if no extension is known for this name or number.
+ virtual const FieldDescriptor* FindExtension(
+ Message* message,
+ const string& name) const = 0;
+ };
+
+ // A location in the parsed text.
+ struct ParseLocation {
+ int line;
+ int column;
+
+ ParseLocation() : line(-1), column(-1) {}
+ ParseLocation(int line_param, int column_param)
+ : line(line_param), column(column_param) {}
+ };
+
+ // Data structure which is populated with the locations of each field
+ // value parsed from the text.
+ class LIBPROTOBUF_EXPORT ParseInfoTree {
+ public:
+ ParseInfoTree();
+ ~ParseInfoTree();
+
+ // Returns the parse location for index-th value of the field in the parsed
+ // text. If none exists, returns a location with line = -1. Index should be
+ // -1 for not-repeated fields.
+ ParseLocation GetLocation(const FieldDescriptor* field, int index) const;
+
+ // Returns the parse info tree for the given field, which must be a message
+ // type. The nested information tree is owned by the root tree and will be
+ // deleted when it is deleted.
+ ParseInfoTree* GetTreeForNested(const FieldDescriptor* field,
+ int index) const;
+
+ private:
+ // Allow the text format parser to record information into the tree.
+ friend class TextFormat;
+
+ // Records the starting location of a single value for a field.
+ void RecordLocation(const FieldDescriptor* field, ParseLocation location);
+
+ // Create and records a nested tree for a nested message field.
+ ParseInfoTree* CreateNested(const FieldDescriptor* field);
+
+ // Defines the map from the index-th field descriptor to its parse location.
+ typedef map<const FieldDescriptor*, vector<ParseLocation> > LocationMap;
+
+ // Defines the map from the index-th field descriptor to the nested parse
+ // info tree.
+ typedef map<const FieldDescriptor*, vector<ParseInfoTree*> > NestedMap;
+
+ LocationMap locations_;
+ NestedMap nested_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ParseInfoTree);
+ };
+
+ // For more control over parsing, use this class.
+ class LIBPROTOBUF_EXPORT Parser {
+ public:
+ Parser();
+ ~Parser();
+
+ // Like TextFormat::Parse().
+ bool Parse(io::ZeroCopyInputStream* input, Message* output);
+ // Like TextFormat::ParseFromString().
+ bool ParseFromString(const string& input, Message* output);
+ // Like TextFormat::Merge().
+ bool Merge(io::ZeroCopyInputStream* input, Message* output);
+ // Like TextFormat::MergeFromString().
+ bool MergeFromString(const string& input, Message* output);
+
+ // Set where to report parse errors. If NULL (the default), errors will
+ // be printed to stderr.
+ void RecordErrorsTo(io::ErrorCollector* error_collector) {
+ error_collector_ = error_collector;
+ }
+
+ // Set how parser finds extensions. If NULL (the default), the
+ // parser will use the standard Reflection object associated with
+ // the message being parsed.
+ void SetFinder(Finder* finder) {
+ finder_ = finder;
+ }
+
+ // Sets where location information about the parse will be written. If NULL
+ // (the default), then no location will be written.
+ void WriteLocationsTo(ParseInfoTree* tree) {
+ parse_info_tree_ = tree;
+ }
+
+ // Normally parsing fails if, after parsing, output->IsInitialized()
+ // returns false. Call AllowPartialMessage(true) to skip this check.
+ void AllowPartialMessage(bool allow) {
+ allow_partial_ = allow;
+ }
+
+ // Allow field names to be matched case-insensitively.
+ // This is not advisable if there are fields that only differ in case, or
+ // if you want to enforce writing in the canonical form.
+ // This is 'false' by default.
+ void AllowCaseInsensitiveField(bool allow) {
+ allow_case_insensitive_field_ = allow;
+ }
+
+ // Like TextFormat::ParseFieldValueFromString
+ bool ParseFieldValueFromString(const string& input,
+ const FieldDescriptor* field,
+ Message* output);
+
+
+ void AllowFieldNumber(bool allow) {
+ allow_field_number_ = allow;
+ }
+
+ private:
+ // Forward declaration of an internal class used to parse text
+ // representations (see text_format.cc for implementation).
+ class ParserImpl;
+
+ // Like TextFormat::Merge(). The provided implementation is used
+ // to do the parsing.
+ bool MergeUsingImpl(io::ZeroCopyInputStream* input,
+ Message* output,
+ ParserImpl* parser_impl);
+
+ io::ErrorCollector* error_collector_;
+ Finder* finder_;
+ ParseInfoTree* parse_info_tree_;
+ bool allow_partial_;
+ bool allow_case_insensitive_field_;
+ bool allow_unknown_field_;
+ bool allow_unknown_enum_;
+ bool allow_field_number_;
+ bool allow_relaxed_whitespace_;
+ bool allow_singular_overwrites_;
+ };
+
+
+ private:
+ // Hack: ParseInfoTree declares TextFormat as a friend which should extend
+ // the friendship to TextFormat::Parser::ParserImpl, but unfortunately some
+ // old compilers (e.g. GCC 3.4.6) don't implement this correctly. We provide
+ // helpers for ParserImpl to call methods of ParseInfoTree.
+ static inline void RecordLocation(ParseInfoTree* info_tree,
+ const FieldDescriptor* field,
+ ParseLocation location);
+ static inline ParseInfoTree* CreateNested(ParseInfoTree* info_tree,
+ const FieldDescriptor* field);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TextFormat);
+};
+
+inline void TextFormat::RecordLocation(ParseInfoTree* info_tree,
+ const FieldDescriptor* field,
+ ParseLocation location) {
+ info_tree->RecordLocation(field, location);
+}
+
+
+inline TextFormat::ParseInfoTree* TextFormat::CreateNested(
+ ParseInfoTree* info_tree, const FieldDescriptor* field) {
+ return info_tree->CreateNested(field);
+}
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_TEXT_FORMAT_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/text_format_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/text_format_unittest.cc
new file mode 100644
index 0000000000..c9521cc31f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/text_format_unittest.cc
@@ -0,0 +1,1493 @@
+// 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: jschorr@google.com (Joseph Schorr)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#include <google/protobuf/text_format.h>
+
+#include <math.h>
+#include <stdlib.h>
+#include <limits>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/testing/file.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_mset.pb.h>
+#include <google/protobuf/unittest_mset_wire_format.pb.h>
+#include <google/protobuf/io/tokenizer.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/stubs/mathlimits.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/substitute.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+
+namespace google {
+namespace protobuf {
+
+// Can't use an anonymous namespace here due to brokenness of Tru64 compiler.
+namespace text_format_unittest {
+
+// A basic string with different escapable characters for testing.
+const string kEscapeTestString =
+ "\"A string with ' characters \n and \r newlines and \t tabs and \001 "
+ "slashes \\ and multiple spaces";
+
+// A representation of the above string with all the characters escaped.
+const string kEscapeTestStringEscaped =
+ "\"\\\"A string with \\' characters \\n and \\r newlines "
+ "and \\t tabs and \\001 slashes \\\\ and multiple spaces\"";
+
+class TextFormatTest : public testing::Test {
+ public:
+ static void SetUpTestCase() {
+ GOOGLE_CHECK_OK(File::GetContents(
+ TestSourceDir() +
+ "/google/protobuf/"
+ "testdata/text_format_unittest_data_oneof_implemented.txt",
+ &static_proto_debug_string_, true));
+ }
+
+ TextFormatTest() : proto_debug_string_(static_proto_debug_string_) {}
+
+ protected:
+ // Debug string read from text_format_unittest_data.txt.
+ const string proto_debug_string_;
+ unittest::TestAllTypes proto_;
+
+ private:
+ static string static_proto_debug_string_;
+};
+string TextFormatTest::static_proto_debug_string_;
+
+class TextFormatExtensionsTest : public testing::Test {
+ public:
+ static void SetUpTestCase() {
+ GOOGLE_CHECK_OK(File::GetContents(TestSourceDir() +
+ "/google/protobuf/testdata/"
+ "text_format_unittest_extensions_data.txt",
+ &static_proto_debug_string_, true));
+ }
+
+ TextFormatExtensionsTest()
+ : proto_debug_string_(static_proto_debug_string_) {}
+
+ protected:
+ // Debug string read from text_format_unittest_data.txt.
+ const string proto_debug_string_;
+ unittest::TestAllExtensions proto_;
+
+ private:
+ static string static_proto_debug_string_;
+};
+string TextFormatExtensionsTest::static_proto_debug_string_;
+
+
+TEST_F(TextFormatTest, Basic) {
+ TestUtil::SetAllFields(&proto_);
+ EXPECT_EQ(proto_debug_string_, proto_.DebugString());
+}
+
+TEST_F(TextFormatExtensionsTest, Extensions) {
+ TestUtil::SetAllExtensions(&proto_);
+ EXPECT_EQ(proto_debug_string_, proto_.DebugString());
+}
+
+TEST_F(TextFormatTest, ShortDebugString) {
+ proto_.set_optional_int32(1);
+ proto_.set_optional_string("hello");
+ proto_.mutable_optional_nested_message()->set_bb(2);
+ proto_.mutable_optional_foreign_message();
+
+ EXPECT_EQ("optional_int32: 1 optional_string: \"hello\" "
+ "optional_nested_message { bb: 2 } "
+ "optional_foreign_message { }",
+ proto_.ShortDebugString());
+}
+
+TEST_F(TextFormatTest, ShortPrimitiveRepeateds) {
+ proto_.set_optional_int32(123);
+ proto_.add_repeated_int32(456);
+ proto_.add_repeated_int32(789);
+ proto_.add_repeated_string("foo");
+ proto_.add_repeated_string("bar");
+ proto_.add_repeated_nested_message()->set_bb(2);
+ proto_.add_repeated_nested_message()->set_bb(3);
+ proto_.add_repeated_nested_enum(unittest::TestAllTypes::FOO);
+ proto_.add_repeated_nested_enum(unittest::TestAllTypes::BAR);
+
+ TextFormat::Printer printer;
+ printer.SetUseShortRepeatedPrimitives(true);
+ string text;
+ printer.PrintToString(proto_, &text);
+
+ EXPECT_EQ("optional_int32: 123\n"
+ "repeated_int32: [456, 789]\n"
+ "repeated_string: \"foo\"\n"
+ "repeated_string: \"bar\"\n"
+ "repeated_nested_message {\n bb: 2\n}\n"
+ "repeated_nested_message {\n bb: 3\n}\n"
+ "repeated_nested_enum: [FOO, BAR]\n",
+ text);
+
+ // Try in single-line mode.
+ printer.SetSingleLineMode(true);
+ printer.PrintToString(proto_, &text);
+
+ EXPECT_EQ("optional_int32: 123 "
+ "repeated_int32: [456, 789] "
+ "repeated_string: \"foo\" "
+ "repeated_string: \"bar\" "
+ "repeated_nested_message { bb: 2 } "
+ "repeated_nested_message { bb: 3 } "
+ "repeated_nested_enum: [FOO, BAR] ",
+ text);
+}
+
+
+TEST_F(TextFormatTest, StringEscape) {
+ // Set the string value to test.
+ proto_.set_optional_string(kEscapeTestString);
+
+ // Get the DebugString from the proto.
+ string debug_string = proto_.DebugString();
+ string utf8_debug_string = proto_.Utf8DebugString();
+
+ // Hardcode a correct value to test against.
+ string correct_string = "optional_string: "
+ + kEscapeTestStringEscaped
+ + "\n";
+
+ // Compare.
+ EXPECT_EQ(correct_string, debug_string);
+ // UTF-8 string is the same as non-UTF-8 because
+ // the protocol buffer contains no UTF-8 text.
+ EXPECT_EQ(correct_string, utf8_debug_string);
+
+ string expected_short_debug_string = "optional_string: "
+ + kEscapeTestStringEscaped;
+ EXPECT_EQ(expected_short_debug_string, proto_.ShortDebugString());
+}
+
+TEST_F(TextFormatTest, Utf8DebugString) {
+ // Set the string value to test.
+ proto_.set_optional_string("\350\260\267\346\255\214");
+ proto_.set_optional_bytes("\350\260\267\346\255\214");
+
+ // Get the DebugString from the proto.
+ string debug_string = proto_.DebugString();
+ string utf8_debug_string = proto_.Utf8DebugString();
+
+ // Hardcode a correct value to test against.
+ string correct_utf8_string =
+ "optional_string: "
+ "\"\350\260\267\346\255\214\""
+ "\n"
+ "optional_bytes: "
+ "\"\\350\\260\\267\\346\\255\\214\""
+ "\n";
+ string correct_string =
+ "optional_string: "
+ "\"\\350\\260\\267\\346\\255\\214\""
+ "\n"
+ "optional_bytes: "
+ "\"\\350\\260\\267\\346\\255\\214\""
+ "\n";
+
+ // Compare.
+ EXPECT_EQ(correct_utf8_string, utf8_debug_string);
+ EXPECT_EQ(correct_string, debug_string);
+}
+
+TEST_F(TextFormatTest, PrintUnknownFields) {
+ // Test printing of unknown fields in a message.
+
+ unittest::TestEmptyMessage message;
+ UnknownFieldSet* unknown_fields = message.mutable_unknown_fields();
+
+ unknown_fields->AddVarint(5, 1);
+ unknown_fields->AddFixed32(5, 2);
+ unknown_fields->AddFixed64(5, 3);
+ unknown_fields->AddLengthDelimited(5, "4");
+ unknown_fields->AddGroup(5)->AddVarint(10, 5);
+
+ unknown_fields->AddVarint(8, 1);
+ unknown_fields->AddVarint(8, 2);
+ unknown_fields->AddVarint(8, 3);
+
+ EXPECT_EQ(
+ "5: 1\n"
+ "5: 0x00000002\n"
+ "5: 0x0000000000000003\n"
+ "5: \"4\"\n"
+ "5 {\n"
+ " 10: 5\n"
+ "}\n"
+ "8: 1\n"
+ "8: 2\n"
+ "8: 3\n",
+ message.DebugString());
+}
+
+TEST_F(TextFormatTest, PrintUnknownFieldsHidden) {
+ // Test printing of unknown fields in a message when suppressed.
+
+ unittest::OneString message;
+ message.set_data("data");
+ UnknownFieldSet* unknown_fields = message.mutable_unknown_fields();
+
+ unknown_fields->AddVarint(5, 1);
+ unknown_fields->AddFixed32(5, 2);
+ unknown_fields->AddFixed64(5, 3);
+ unknown_fields->AddLengthDelimited(5, "4");
+ unknown_fields->AddGroup(5)->AddVarint(10, 5);
+
+ unknown_fields->AddVarint(8, 1);
+ unknown_fields->AddVarint(8, 2);
+ unknown_fields->AddVarint(8, 3);
+
+ TextFormat::Printer printer;
+ printer.SetHideUnknownFields(true);
+ string output;
+ printer.PrintToString(message, &output);
+
+ EXPECT_EQ("data: \"data\"\n", output);
+}
+
+TEST_F(TextFormatTest, PrintUnknownMessage) {
+ // Test heuristic printing of messages in an UnknownFieldSet.
+
+ protobuf_unittest::TestAllTypes message;
+
+ // Cases which should not be interpreted as sub-messages.
+
+ // 'a' is a valid FIXED64 tag, so for the string to be parseable as a message
+ // it should be followed by 8 bytes. Since this string only has two
+ // subsequent bytes, it should be treated as a string.
+ message.add_repeated_string("abc");
+
+ // 'd' happens to be a valid ENDGROUP tag. So,
+ // UnknownFieldSet::MergeFromCodedStream() will successfully parse "def", but
+ // the ConsumedEntireMessage() check should fail.
+ message.add_repeated_string("def");
+
+ // A zero-length string should never be interpreted as a message even though
+ // it is technically valid as one.
+ message.add_repeated_string("");
+
+ // Case which should be interpreted as a sub-message.
+
+ // An actual nested message with content should always be interpreted as a
+ // nested message.
+ message.add_repeated_nested_message()->set_bb(123);
+
+ string data;
+ message.SerializeToString(&data);
+
+ string text;
+ UnknownFieldSet unknown_fields;
+ EXPECT_TRUE(unknown_fields.ParseFromString(data));
+ EXPECT_TRUE(TextFormat::PrintUnknownFieldsToString(unknown_fields, &text));
+ EXPECT_EQ(
+ "44: \"abc\"\n"
+ "44: \"def\"\n"
+ "44: \"\"\n"
+ "48 {\n"
+ " 1: 123\n"
+ "}\n",
+ text);
+}
+
+TEST_F(TextFormatTest, PrintMessageWithIndent) {
+ // Test adding an initial indent to printing.
+
+ protobuf_unittest::TestAllTypes message;
+
+ message.add_repeated_string("abc");
+ message.add_repeated_string("def");
+ message.add_repeated_nested_message()->set_bb(123);
+
+ string text;
+ TextFormat::Printer printer;
+ printer.SetInitialIndentLevel(1);
+ EXPECT_TRUE(printer.PrintToString(message, &text));
+ EXPECT_EQ(
+ " repeated_string: \"abc\"\n"
+ " repeated_string: \"def\"\n"
+ " repeated_nested_message {\n"
+ " bb: 123\n"
+ " }\n",
+ text);
+}
+
+TEST_F(TextFormatTest, PrintMessageSingleLine) {
+ // Test printing a message on a single line.
+
+ protobuf_unittest::TestAllTypes message;
+
+ message.add_repeated_string("abc");
+ message.add_repeated_string("def");
+ message.add_repeated_nested_message()->set_bb(123);
+
+ string text;
+ TextFormat::Printer printer;
+ printer.SetInitialIndentLevel(1);
+ printer.SetSingleLineMode(true);
+ EXPECT_TRUE(printer.PrintToString(message, &text));
+ EXPECT_EQ(
+ " repeated_string: \"abc\" repeated_string: \"def\" "
+ "repeated_nested_message { bb: 123 } ",
+ text);
+}
+
+TEST_F(TextFormatTest, PrintBufferTooSmall) {
+ // Test printing a message to a buffer that is too small.
+
+ protobuf_unittest::TestAllTypes message;
+
+ message.add_repeated_string("abc");
+ message.add_repeated_string("def");
+
+ char buffer[1] = "";
+ io::ArrayOutputStream output_stream(buffer, 1);
+ EXPECT_FALSE(TextFormat::Print(message, &output_stream));
+ EXPECT_EQ(buffer[0], 'r');
+ EXPECT_EQ(output_stream.ByteCount(), 1);
+}
+
+// A printer that appends 'u' to all unsigned int32.
+class CustomUInt32FieldValuePrinter : public TextFormat::FieldValuePrinter {
+ public:
+ virtual string PrintUInt32(uint32 val) const {
+ return StrCat(FieldValuePrinter::PrintUInt32(val), "u");
+ }
+};
+
+TEST_F(TextFormatTest, DefaultCustomFieldPrinter) {
+ protobuf_unittest::TestAllTypes message;
+
+ message.set_optional_uint32(42);
+ message.add_repeated_uint32(1);
+ message.add_repeated_uint32(2);
+ message.add_repeated_uint32(3);
+
+ TextFormat::Printer printer;
+ printer.SetDefaultFieldValuePrinter(new CustomUInt32FieldValuePrinter());
+ // Let's see if that works well together with the repeated primitives:
+ printer.SetUseShortRepeatedPrimitives(true);
+ string text;
+ printer.PrintToString(message, &text);
+ EXPECT_EQ("optional_uint32: 42u\nrepeated_uint32: [1u, 2u, 3u]\n", text);
+}
+
+class CustomInt32FieldValuePrinter : public TextFormat::FieldValuePrinter {
+ public:
+ virtual string PrintInt32(int32 val) const {
+ return StrCat("value-is(", FieldValuePrinter::PrintInt32(val), ")");
+ }
+};
+
+TEST_F(TextFormatTest, FieldSpecificCustomPrinter) {
+ protobuf_unittest::TestAllTypes message;
+
+ message.set_optional_int32(42); // This will be handled by our Printer.
+ message.add_repeated_int32(42); // This will be printed as number.
+
+ TextFormat::Printer printer;
+ EXPECT_TRUE(printer.RegisterFieldValuePrinter(
+ message.GetDescriptor()->FindFieldByName("optional_int32"),
+ new CustomInt32FieldValuePrinter()));
+ string text;
+ printer.PrintToString(message, &text);
+ EXPECT_EQ("optional_int32: value-is(42)\nrepeated_int32: 42\n", text);
+}
+
+TEST_F(TextFormatTest, ErrorCasesRegisteringFieldValuePrinterShouldFail) {
+ protobuf_unittest::TestAllTypes message;
+ TextFormat::Printer printer;
+ // NULL printer.
+ EXPECT_FALSE(printer.RegisterFieldValuePrinter(
+ message.GetDescriptor()->FindFieldByName("optional_int32"),
+ NULL));
+ // Because registration fails, the ownership of this printer is never taken.
+ TextFormat::FieldValuePrinter my_field_printer;
+ // NULL field
+ EXPECT_FALSE(printer.RegisterFieldValuePrinter(NULL, &my_field_printer));
+}
+
+class CustomMessageFieldValuePrinter : public TextFormat::FieldValuePrinter {
+ public:
+ virtual string PrintInt32(int32 v) const {
+ return StrCat(FieldValuePrinter::PrintInt32(v), " # x", strings::Hex(v));
+ }
+
+ virtual string PrintMessageStart(const Message& message,
+ int field_index,
+ int field_count,
+ bool single_line_mode) const {
+ if (single_line_mode) {
+ return " { ";
+ }
+ return StrCat(
+ " { # ", message.GetDescriptor()->name(), ": ", field_index, "\n");
+ }
+};
+
+TEST_F(TextFormatTest, CustomPrinterForComments) {
+ protobuf_unittest::TestAllTypes message;
+ message.mutable_optional_nested_message();
+ message.mutable_optional_import_message()->set_d(42);
+ message.add_repeated_nested_message();
+ message.add_repeated_nested_message();
+ message.add_repeated_import_message()->set_d(43);
+ message.add_repeated_import_message()->set_d(44);
+ TextFormat::Printer printer;
+ CustomMessageFieldValuePrinter my_field_printer;
+ printer.SetDefaultFieldValuePrinter(new CustomMessageFieldValuePrinter());
+ string text;
+ printer.PrintToString(message, &text);
+ EXPECT_EQ(
+ "optional_nested_message { # NestedMessage: -1\n"
+ "}\n"
+ "optional_import_message { # ImportMessage: -1\n"
+ " d: 42 # x2a\n"
+ "}\n"
+ "repeated_nested_message { # NestedMessage: 0\n"
+ "}\n"
+ "repeated_nested_message { # NestedMessage: 1\n"
+ "}\n"
+ "repeated_import_message { # ImportMessage: 0\n"
+ " d: 43 # x2b\n"
+ "}\n"
+ "repeated_import_message { # ImportMessage: 1\n"
+ " d: 44 # x2c\n"
+ "}\n",
+ text);
+}
+
+class CustomMultilineCommentPrinter : public TextFormat::FieldValuePrinter {
+ public:
+ virtual string PrintMessageStart(const Message& message,
+ int field_index,
+ int field_count,
+ bool single_line_comment) const {
+ return StrCat(" { # 1\n", " # 2\n");
+ }
+};
+
+TEST_F(TextFormatTest, CustomPrinterForMultilineComments) {
+ protobuf_unittest::TestAllTypes message;
+ message.mutable_optional_nested_message();
+ message.mutable_optional_import_message()->set_d(42);
+ TextFormat::Printer printer;
+ CustomMessageFieldValuePrinter my_field_printer;
+ printer.SetDefaultFieldValuePrinter(new CustomMultilineCommentPrinter());
+ string text;
+ printer.PrintToString(message, &text);
+ EXPECT_EQ(
+ "optional_nested_message { # 1\n"
+ " # 2\n"
+ "}\n"
+ "optional_import_message { # 1\n"
+ " # 2\n"
+ " d: 42\n"
+ "}\n",
+ text);
+}
+
+TEST_F(TextFormatTest, ParseBasic) {
+ io::ArrayInputStream input_stream(proto_debug_string_.data(),
+ proto_debug_string_.size());
+ TextFormat::Parse(&input_stream, &proto_);
+ TestUtil::ExpectAllFieldsSet(proto_);
+}
+
+TEST_F(TextFormatExtensionsTest, ParseExtensions) {
+ io::ArrayInputStream input_stream(proto_debug_string_.data(),
+ proto_debug_string_.size());
+ TextFormat::Parse(&input_stream, &proto_);
+ TestUtil::ExpectAllExtensionsSet(proto_);
+}
+
+TEST_F(TextFormatTest, ParseEnumFieldFromNumber) {
+ // Create a parse string with a numerical value for an enum field.
+ string parse_string = strings::Substitute("optional_nested_enum: $0",
+ unittest::TestAllTypes::BAZ);
+ EXPECT_TRUE(TextFormat::ParseFromString(parse_string, &proto_));
+ EXPECT_TRUE(proto_.has_optional_nested_enum());
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, proto_.optional_nested_enum());
+}
+
+TEST_F(TextFormatTest, ParseEnumFieldFromNegativeNumber) {
+ ASSERT_LT(unittest::SPARSE_E, 0);
+ string parse_string = strings::Substitute("sparse_enum: $0",
+ unittest::SPARSE_E);
+ unittest::SparseEnumMessage proto;
+ EXPECT_TRUE(TextFormat::ParseFromString(parse_string, &proto));
+ EXPECT_TRUE(proto.has_sparse_enum());
+ EXPECT_EQ(unittest::SPARSE_E, proto.sparse_enum());
+}
+
+TEST_F(TextFormatTest, ParseStringEscape) {
+ // Create a parse string with escpaed characters in it.
+ string parse_string = "optional_string: "
+ + kEscapeTestStringEscaped
+ + "\n";
+
+ io::ArrayInputStream input_stream(parse_string.data(),
+ parse_string.size());
+ TextFormat::Parse(&input_stream, &proto_);
+
+ // Compare.
+ EXPECT_EQ(kEscapeTestString, proto_.optional_string());
+}
+
+TEST_F(TextFormatTest, ParseConcatenatedString) {
+ // Create a parse string with multiple parts on one line.
+ string parse_string = "optional_string: \"foo\" \"bar\"\n";
+
+ io::ArrayInputStream input_stream1(parse_string.data(),
+ parse_string.size());
+ TextFormat::Parse(&input_stream1, &proto_);
+
+ // Compare.
+ EXPECT_EQ("foobar", proto_.optional_string());
+
+ // Create a parse string with multiple parts on separate lines.
+ parse_string = "optional_string: \"foo\"\n"
+ "\"bar\"\n";
+
+ io::ArrayInputStream input_stream2(parse_string.data(),
+ parse_string.size());
+ TextFormat::Parse(&input_stream2, &proto_);
+
+ // Compare.
+ EXPECT_EQ("foobar", proto_.optional_string());
+}
+
+TEST_F(TextFormatTest, ParseFloatWithSuffix) {
+ // Test that we can parse a floating-point value with 'f' appended to the
+ // end. This is needed for backwards-compatibility with proto1.
+
+ // Have it parse a float with the 'f' suffix.
+ string parse_string = "optional_float: 1.0f\n";
+
+ io::ArrayInputStream input_stream(parse_string.data(),
+ parse_string.size());
+
+ TextFormat::Parse(&input_stream, &proto_);
+
+ // Compare.
+ EXPECT_EQ(1.0, proto_.optional_float());
+}
+
+TEST_F(TextFormatTest, ParseShortRepeatedForm) {
+ string parse_string =
+ // Mixed short-form and long-form are simply concatenated.
+ "repeated_int32: 1\n"
+ "repeated_int32: [456, 789]\n"
+ "repeated_nested_enum: [ FOO ,BAR, # comment\n"
+ " 3]\n"
+ // Note that while the printer won't print repeated strings in short-form,
+ // the parser will accept them.
+ "repeated_string: [ \"foo\", 'bar' ]\n"
+ // Repeated message
+ "repeated_nested_message: [ { bb: 1 }, { bb : 2 }]\n"
+ // Repeated group
+ "RepeatedGroup [{ a: 3 },{ a: 4 }]\n";
+
+ ASSERT_TRUE(TextFormat::ParseFromString(parse_string, &proto_));
+
+ ASSERT_EQ(3, proto_.repeated_int32_size());
+ EXPECT_EQ(1, proto_.repeated_int32(0));
+ EXPECT_EQ(456, proto_.repeated_int32(1));
+ EXPECT_EQ(789, proto_.repeated_int32(2));
+
+ ASSERT_EQ(3, proto_.repeated_nested_enum_size());
+ EXPECT_EQ(unittest::TestAllTypes::FOO, proto_.repeated_nested_enum(0));
+ EXPECT_EQ(unittest::TestAllTypes::BAR, proto_.repeated_nested_enum(1));
+ EXPECT_EQ(unittest::TestAllTypes::BAZ, proto_.repeated_nested_enum(2));
+
+ ASSERT_EQ(2, proto_.repeated_string_size());
+ EXPECT_EQ("foo", proto_.repeated_string(0));
+ EXPECT_EQ("bar", proto_.repeated_string(1));
+
+ ASSERT_EQ(2, proto_.repeated_nested_message_size());
+ EXPECT_EQ(1, proto_.repeated_nested_message(0).bb());
+ EXPECT_EQ(2, proto_.repeated_nested_message(1).bb());
+
+ ASSERT_EQ(2, proto_.repeatedgroup_size());
+ EXPECT_EQ(3, proto_.repeatedgroup(0).a());
+ EXPECT_EQ(4, proto_.repeatedgroup(1).a());
+}
+
+
+TEST_F(TextFormatTest, Comments) {
+ // Test that comments are ignored.
+
+ string parse_string = "optional_int32: 1 # a comment\n"
+ "optional_int64: 2 # another comment";
+
+ io::ArrayInputStream input_stream(parse_string.data(),
+ parse_string.size());
+
+ TextFormat::Parse(&input_stream, &proto_);
+
+ // Compare.
+ EXPECT_EQ(1, proto_.optional_int32());
+ EXPECT_EQ(2, proto_.optional_int64());
+}
+
+TEST_F(TextFormatTest, OptionalColon) {
+ // Test that we can place a ':' after the field name of a nested message,
+ // even though we don't have to.
+
+ string parse_string = "optional_nested_message: { bb: 1}\n";
+
+ io::ArrayInputStream input_stream(parse_string.data(),
+ parse_string.size());
+
+ TextFormat::Parse(&input_stream, &proto_);
+
+ // Compare.
+ EXPECT_TRUE(proto_.has_optional_nested_message());
+ EXPECT_EQ(1, proto_.optional_nested_message().bb());
+}
+
+// Some platforms (e.g. Windows) insist on padding the exponent to three
+// digits when one or two would be just fine.
+static string RemoveRedundantZeros(string text) {
+ text = StringReplace(text, "e+0", "e+", true);
+ text = StringReplace(text, "e-0", "e-", true);
+ return text;
+}
+
+TEST_F(TextFormatTest, PrintExotic) {
+ unittest::TestAllTypes message;
+
+ // Note: In C, a negative integer literal is actually the unary negation
+ // operator being applied to a positive integer literal, and
+ // 9223372036854775808 is outside the range of int64. However, it is not
+ // outside the range of uint64. Confusingly, this means that everything
+ // works if we make the literal unsigned, even though we are negating it.
+ message.add_repeated_int64(-GOOGLE_ULONGLONG(9223372036854775808));
+ message.add_repeated_uint64(GOOGLE_ULONGLONG(18446744073709551615));
+ message.add_repeated_double(123.456);
+ message.add_repeated_double(1.23e21);
+ message.add_repeated_double(1.23e-18);
+ message.add_repeated_double(std::numeric_limits<double>::infinity());
+ message.add_repeated_double(-std::numeric_limits<double>::infinity());
+ message.add_repeated_double(std::numeric_limits<double>::quiet_NaN());
+ message.add_repeated_string(string("\000\001\a\b\f\n\r\t\v\\\'\"", 12));
+
+ // Fun story: We used to use 1.23e22 instead of 1.23e21 above, but this
+ // seemed to trigger an odd case on MinGW/GCC 3.4.5 where GCC's parsing of
+ // the value differed from strtod()'s parsing. That is to say, the
+ // following assertion fails on MinGW:
+ // assert(1.23e22 == strtod("1.23e22", NULL));
+ // As a result, SimpleDtoa() would print the value as
+ // "1.2300000000000001e+22" to make sure strtod() produce the exact same
+ // result. Our goal is to test runtime parsing, not compile-time parsing,
+ // so this wasn't our problem. It was found that using 1.23e21 did not
+ // have this problem, so we switched to that instead.
+
+ EXPECT_EQ(
+ "repeated_int64: -9223372036854775808\n"
+ "repeated_uint64: 18446744073709551615\n"
+ "repeated_double: 123.456\n"
+ "repeated_double: 1.23e+21\n"
+ "repeated_double: 1.23e-18\n"
+ "repeated_double: inf\n"
+ "repeated_double: -inf\n"
+ "repeated_double: nan\n"
+ "repeated_string: \"\\000\\001\\007\\010\\014\\n\\r\\t\\013\\\\\\'\\\"\"\n",
+ RemoveRedundantZeros(message.DebugString()));
+}
+
+TEST_F(TextFormatTest, PrintFloatPrecision) {
+ unittest::TestAllTypes message;
+
+ message.add_repeated_float(1.2);
+ message.add_repeated_float(1.23);
+ message.add_repeated_float(1.234);
+ message.add_repeated_float(1.2345);
+ message.add_repeated_float(1.23456);
+ message.add_repeated_float(1.2e10);
+ message.add_repeated_float(1.23e10);
+ message.add_repeated_float(1.234e10);
+ message.add_repeated_float(1.2345e10);
+ message.add_repeated_float(1.23456e10);
+ message.add_repeated_double(1.2);
+ message.add_repeated_double(1.23);
+ message.add_repeated_double(1.234);
+ message.add_repeated_double(1.2345);
+ message.add_repeated_double(1.23456);
+ message.add_repeated_double(1.234567);
+ message.add_repeated_double(1.2345678);
+ message.add_repeated_double(1.23456789);
+ message.add_repeated_double(1.234567898);
+ message.add_repeated_double(1.2345678987);
+ message.add_repeated_double(1.23456789876);
+ message.add_repeated_double(1.234567898765);
+ message.add_repeated_double(1.2345678987654);
+ message.add_repeated_double(1.23456789876543);
+ message.add_repeated_double(1.2e100);
+ message.add_repeated_double(1.23e100);
+ message.add_repeated_double(1.234e100);
+ message.add_repeated_double(1.2345e100);
+ message.add_repeated_double(1.23456e100);
+ message.add_repeated_double(1.234567e100);
+ message.add_repeated_double(1.2345678e100);
+ message.add_repeated_double(1.23456789e100);
+ message.add_repeated_double(1.234567898e100);
+ message.add_repeated_double(1.2345678987e100);
+ message.add_repeated_double(1.23456789876e100);
+ message.add_repeated_double(1.234567898765e100);
+ message.add_repeated_double(1.2345678987654e100);
+ message.add_repeated_double(1.23456789876543e100);
+
+ EXPECT_EQ(
+ "repeated_float: 1.2\n"
+ "repeated_float: 1.23\n"
+ "repeated_float: 1.234\n"
+ "repeated_float: 1.2345\n"
+ "repeated_float: 1.23456\n"
+ "repeated_float: 1.2e+10\n"
+ "repeated_float: 1.23e+10\n"
+ "repeated_float: 1.234e+10\n"
+ "repeated_float: 1.2345e+10\n"
+ "repeated_float: 1.23456e+10\n"
+ "repeated_double: 1.2\n"
+ "repeated_double: 1.23\n"
+ "repeated_double: 1.234\n"
+ "repeated_double: 1.2345\n"
+ "repeated_double: 1.23456\n"
+ "repeated_double: 1.234567\n"
+ "repeated_double: 1.2345678\n"
+ "repeated_double: 1.23456789\n"
+ "repeated_double: 1.234567898\n"
+ "repeated_double: 1.2345678987\n"
+ "repeated_double: 1.23456789876\n"
+ "repeated_double: 1.234567898765\n"
+ "repeated_double: 1.2345678987654\n"
+ "repeated_double: 1.23456789876543\n"
+ "repeated_double: 1.2e+100\n"
+ "repeated_double: 1.23e+100\n"
+ "repeated_double: 1.234e+100\n"
+ "repeated_double: 1.2345e+100\n"
+ "repeated_double: 1.23456e+100\n"
+ "repeated_double: 1.234567e+100\n"
+ "repeated_double: 1.2345678e+100\n"
+ "repeated_double: 1.23456789e+100\n"
+ "repeated_double: 1.234567898e+100\n"
+ "repeated_double: 1.2345678987e+100\n"
+ "repeated_double: 1.23456789876e+100\n"
+ "repeated_double: 1.234567898765e+100\n"
+ "repeated_double: 1.2345678987654e+100\n"
+ "repeated_double: 1.23456789876543e+100\n",
+ RemoveRedundantZeros(message.DebugString()));
+}
+
+
+TEST_F(TextFormatTest, AllowPartial) {
+ unittest::TestRequired message;
+ TextFormat::Parser parser;
+ parser.AllowPartialMessage(true);
+ EXPECT_TRUE(parser.ParseFromString("a: 1", &message));
+ EXPECT_EQ(1, message.a());
+ EXPECT_FALSE(message.has_b());
+ EXPECT_FALSE(message.has_c());
+}
+
+TEST_F(TextFormatTest, ParseExotic) {
+ unittest::TestAllTypes message;
+ ASSERT_TRUE(TextFormat::ParseFromString(
+ "repeated_int32: -1\n"
+ "repeated_int32: -2147483648\n"
+ "repeated_int64: -1\n"
+ "repeated_int64: -9223372036854775808\n"
+ "repeated_uint32: 4294967295\n"
+ "repeated_uint32: 2147483648\n"
+ "repeated_uint64: 18446744073709551615\n"
+ "repeated_uint64: 9223372036854775808\n"
+ "repeated_double: 123.0\n"
+ "repeated_double: 123.5\n"
+ "repeated_double: 0.125\n"
+ "repeated_double: 1.23E17\n"
+ "repeated_double: 1.235E+22\n"
+ "repeated_double: 1.235e-18\n"
+ "repeated_double: 123.456789\n"
+ "repeated_double: inf\n"
+ "repeated_double: Infinity\n"
+ "repeated_double: -inf\n"
+ "repeated_double: -Infinity\n"
+ "repeated_double: nan\n"
+ "repeated_double: NaN\n"
+ "repeated_string: \"\\000\\001\\a\\b\\f\\n\\r\\t\\v\\\\\\'\\\"\"\n",
+ &message));
+
+ ASSERT_EQ(2, message.repeated_int32_size());
+ EXPECT_EQ(-1, message.repeated_int32(0));
+ // Note: In C, a negative integer literal is actually the unary negation
+ // operator being applied to a positive integer literal, and 2147483648 is
+ // outside the range of int32. However, it is not outside the range of
+ // uint32. Confusingly, this means that everything works if we make the
+ // literal unsigned, even though we are negating it.
+ EXPECT_EQ(-2147483648u, message.repeated_int32(1));
+
+ ASSERT_EQ(2, message.repeated_int64_size());
+ EXPECT_EQ(-1, message.repeated_int64(0));
+ // Note: In C, a negative integer literal is actually the unary negation
+ // operator being applied to a positive integer literal, and
+ // 9223372036854775808 is outside the range of int64. However, it is not
+ // outside the range of uint64. Confusingly, this means that everything
+ // works if we make the literal unsigned, even though we are negating it.
+ EXPECT_EQ(-GOOGLE_ULONGLONG(9223372036854775808), message.repeated_int64(1));
+
+ ASSERT_EQ(2, message.repeated_uint32_size());
+ EXPECT_EQ(4294967295u, message.repeated_uint32(0));
+ EXPECT_EQ(2147483648u, message.repeated_uint32(1));
+
+ ASSERT_EQ(2, message.repeated_uint64_size());
+ EXPECT_EQ(GOOGLE_ULONGLONG(18446744073709551615), message.repeated_uint64(0));
+ EXPECT_EQ(GOOGLE_ULONGLONG(9223372036854775808), message.repeated_uint64(1));
+
+ ASSERT_EQ(13, message.repeated_double_size());
+ EXPECT_EQ(123.0 , message.repeated_double(0));
+ EXPECT_EQ(123.5 , message.repeated_double(1));
+ EXPECT_EQ(0.125 , message.repeated_double(2));
+ EXPECT_EQ(1.23E17 , message.repeated_double(3));
+ EXPECT_EQ(1.235E22 , message.repeated_double(4));
+ EXPECT_EQ(1.235E-18 , message.repeated_double(5));
+ EXPECT_EQ(123.456789, message.repeated_double(6));
+ EXPECT_EQ(message.repeated_double(7), numeric_limits<double>::infinity());
+ EXPECT_EQ(message.repeated_double(8), numeric_limits<double>::infinity());
+ EXPECT_EQ(message.repeated_double(9), -numeric_limits<double>::infinity());
+ EXPECT_EQ(message.repeated_double(10), -numeric_limits<double>::infinity());
+ EXPECT_TRUE(MathLimits<double>::IsNaN(message.repeated_double(11)));
+ EXPECT_TRUE(MathLimits<double>::IsNaN(message.repeated_double(12)));
+
+ // Note: Since these string literals have \0's in them, we must explicitly
+ // pass their sizes to string's constructor.
+ ASSERT_EQ(1, message.repeated_string_size());
+ EXPECT_EQ(string("\000\001\a\b\f\n\r\t\v\\\'\"", 12),
+ message.repeated_string(0));
+}
+
+TEST_F(TextFormatTest, PrintFieldsInIndexOrder) {
+ protobuf_unittest::TestFieldOrderings message;
+ // Fields are listed in index order instead of field number.
+ message.set_my_string("Test String"); // Field number 11
+ message.set_my_int(12345); // Field number 1
+ message.set_my_float(0.999); // Field number 101
+ TextFormat::Printer printer;
+ string text;
+
+ // By default, print in field number order.
+ printer.PrintToString(message, &text);
+ EXPECT_EQ("my_int: 12345\nmy_string: \"Test String\"\nmy_float: 0.999\n",
+ text);
+
+ // Print in index order.
+ printer.SetPrintMessageFieldsInIndexOrder(true);
+ printer.PrintToString(message, &text);
+ EXPECT_EQ("my_string: \"Test String\"\nmy_int: 12345\nmy_float: 0.999\n",
+ text);
+}
+
+class TextFormatParserTest : public testing::Test {
+ protected:
+ void ExpectFailure(const string& input, const string& message, int line,
+ int col) {
+ google::protobuf::scoped_ptr<unittest::TestAllTypes> proto(new unittest::TestAllTypes);
+ ExpectFailure(input, message, line, col, proto.get());
+ }
+
+ void ExpectFailure(const string& input, const string& message, int line,
+ int col, Message* proto) {
+ ExpectMessage(input, message, line, col, proto, false);
+ }
+
+ void ExpectMessage(const string& input, const string& message, int line,
+ int col, Message* proto, bool expected_result) {
+ TextFormat::Parser parser;
+ MockErrorCollector error_collector;
+ parser.RecordErrorsTo(&error_collector);
+ EXPECT_EQ(expected_result, parser.ParseFromString(input, proto))
+ << input << " -> " << proto->DebugString();
+ EXPECT_EQ(SimpleItoa(line) + ":" + SimpleItoa(col) + ": " + message + "\n",
+ error_collector.text_);
+ }
+
+ void ExpectSuccessAndTree(const string& input, Message* proto,
+ TextFormat::ParseInfoTree* info_tree) {
+ TextFormat::Parser parser;
+ MockErrorCollector error_collector;
+ parser.RecordErrorsTo(&error_collector);
+ parser.WriteLocationsTo(info_tree);
+
+ EXPECT_TRUE(parser.ParseFromString(input, proto));
+ }
+
+ void ExpectLocation(TextFormat::ParseInfoTree* tree,
+ const Descriptor* d, const string& field_name,
+ int index, int line, int column) {
+ TextFormat::ParseLocation location = tree->GetLocation(
+ d->FindFieldByName(field_name), index);
+ EXPECT_EQ(line, location.line);
+ EXPECT_EQ(column, location.column);
+ }
+
+ // An error collector which simply concatenates all its errors into a big
+ // block of text which can be checked.
+ class MockErrorCollector : public io::ErrorCollector {
+ public:
+ MockErrorCollector() {}
+ ~MockErrorCollector() {}
+
+ string text_;
+
+ // implements ErrorCollector -------------------------------------
+ void AddError(int line, int column, const string& message) {
+ strings::SubstituteAndAppend(&text_, "$0:$1: $2\n",
+ line + 1, column + 1, message);
+ }
+
+ void AddWarning(int line, int column, const string& message) {
+ AddError(line, column, "WARNING:" + message);
+ }
+ };
+};
+
+TEST_F(TextFormatParserTest, ParseInfoTreeBuilding) {
+ google::protobuf::scoped_ptr<unittest::TestAllTypes> message(new unittest::TestAllTypes);
+ const Descriptor* d = message->GetDescriptor();
+
+ string stringData =
+ "optional_int32: 1\n"
+ "optional_int64: 2\n"
+ " optional_double: 2.4\n"
+ "repeated_int32: 5\n"
+ "repeated_int32: 10\n"
+ "optional_nested_message <\n"
+ " bb: 78\n"
+ ">\n"
+ "repeated_nested_message <\n"
+ " bb: 79\n"
+ ">\n"
+ "repeated_nested_message <\n"
+ " bb: 80\n"
+ ">";
+
+
+ TextFormat::ParseInfoTree tree;
+ ExpectSuccessAndTree(stringData, message.get(), &tree);
+
+ // Verify that the tree has the correct positions.
+ ExpectLocation(&tree, d, "optional_int32", -1, 0, 0);
+ ExpectLocation(&tree, d, "optional_int64", -1, 1, 0);
+ ExpectLocation(&tree, d, "optional_double", -1, 2, 2);
+
+ ExpectLocation(&tree, d, "repeated_int32", 0, 3, 0);
+ ExpectLocation(&tree, d, "repeated_int32", 1, 4, 0);
+
+ ExpectLocation(&tree, d, "optional_nested_message", -1, 5, 0);
+ ExpectLocation(&tree, d, "repeated_nested_message", 0, 8, 0);
+ ExpectLocation(&tree, d, "repeated_nested_message", 1, 11, 0);
+
+ // Check for fields not set. For an invalid field, the location returned
+ // should be -1, -1.
+ ExpectLocation(&tree, d, "repeated_int64", 0, -1, -1);
+ ExpectLocation(&tree, d, "repeated_int32", 6, -1, -1);
+ ExpectLocation(&tree, d, "some_unknown_field", -1, -1, -1);
+
+ // Verify inside the nested message.
+ const FieldDescriptor* nested_field =
+ d->FindFieldByName("optional_nested_message");
+
+ TextFormat::ParseInfoTree* nested_tree =
+ tree.GetTreeForNested(nested_field, -1);
+ ExpectLocation(nested_tree, nested_field->message_type(), "bb", -1, 6, 2);
+
+ // Verify inside another nested message.
+ nested_field = d->FindFieldByName("repeated_nested_message");
+ nested_tree = tree.GetTreeForNested(nested_field, 0);
+ ExpectLocation(nested_tree, nested_field->message_type(), "bb", -1, 9, 2);
+
+ nested_tree = tree.GetTreeForNested(nested_field, 1);
+ ExpectLocation(nested_tree, nested_field->message_type(), "bb", -1, 12, 2);
+
+ // Verify a NULL tree for an unknown nested field.
+ TextFormat::ParseInfoTree* unknown_nested_tree =
+ tree.GetTreeForNested(nested_field, 2);
+
+ EXPECT_EQ(NULL, unknown_nested_tree);
+}
+
+TEST_F(TextFormatParserTest, ParseFieldValueFromString) {
+ google::protobuf::scoped_ptr<unittest::TestAllTypes> message(new unittest::TestAllTypes);
+ const Descriptor* d = message->GetDescriptor();
+
+#define EXPECT_FIELD(name, value, valuestring) \
+ EXPECT_TRUE(TextFormat::ParseFieldValueFromString( \
+ valuestring, d->FindFieldByName("optional_" #name), message.get())); \
+ EXPECT_EQ(value, message->optional_##name()); \
+ EXPECT_TRUE(message->has_optional_##name());
+
+#define EXPECT_BOOL_FIELD(name, value, valuestring) \
+ EXPECT_TRUE(TextFormat::ParseFieldValueFromString( \
+ valuestring, d->FindFieldByName("optional_" #name), message.get())); \
+ EXPECT_TRUE(message->optional_##name() == value); \
+ EXPECT_TRUE(message->has_optional_##name());
+
+#define EXPECT_FLOAT_FIELD(name, value, valuestring) \
+ EXPECT_TRUE(TextFormat::ParseFieldValueFromString( \
+ valuestring, d->FindFieldByName("optional_" #name), message.get())); \
+ EXPECT_FLOAT_EQ(value, message->optional_##name()); \
+ EXPECT_TRUE(message->has_optional_##name());
+
+#define EXPECT_DOUBLE_FIELD(name, value, valuestring) \
+ EXPECT_TRUE(TextFormat::ParseFieldValueFromString( \
+ valuestring, d->FindFieldByName("optional_" #name), message.get())); \
+ EXPECT_DOUBLE_EQ(value, message->optional_##name()); \
+ EXPECT_TRUE(message->has_optional_##name());
+
+#define EXPECT_INVALID(name, valuestring) \
+ EXPECT_FALSE(TextFormat::ParseFieldValueFromString( \
+ valuestring, d->FindFieldByName("optional_" #name), message.get()));
+
+ // int32
+ EXPECT_FIELD(int32, 1, "1");
+ EXPECT_FIELD(int32, -1, "-1");
+ EXPECT_FIELD(int32, 0x1234, "0x1234");
+ EXPECT_INVALID(int32, "a");
+ EXPECT_INVALID(int32, "999999999999999999999999999999999999");
+ EXPECT_INVALID(int32, "1,2");
+
+ // int64
+ EXPECT_FIELD(int64, 1, "1");
+ EXPECT_FIELD(int64, -1, "-1");
+ EXPECT_FIELD(int64, 0x1234567812345678LL, "0x1234567812345678");
+ EXPECT_INVALID(int64, "a");
+ EXPECT_INVALID(int64, "999999999999999999999999999999999999");
+ EXPECT_INVALID(int64, "1,2");
+
+ // uint64
+ EXPECT_FIELD(uint64, 1, "1");
+ EXPECT_FIELD(uint64, 0xf234567812345678ULL, "0xf234567812345678");
+ EXPECT_INVALID(uint64, "-1");
+ EXPECT_INVALID(uint64, "a");
+ EXPECT_INVALID(uint64, "999999999999999999999999999999999999");
+ EXPECT_INVALID(uint64, "1,2");
+
+ // fixed32
+ EXPECT_FIELD(fixed32, 1, "1");
+ EXPECT_FIELD(fixed32, 0x12345678, "0x12345678");
+ EXPECT_INVALID(fixed32, "-1");
+ EXPECT_INVALID(fixed32, "a");
+ EXPECT_INVALID(fixed32, "999999999999999999999999999999999999");
+ EXPECT_INVALID(fixed32, "1,2");
+
+ // fixed64
+ EXPECT_FIELD(fixed64, 1, "1");
+ EXPECT_FIELD(fixed64, 0x1234567812345678ULL, "0x1234567812345678");
+ EXPECT_INVALID(fixed64, "-1");
+ EXPECT_INVALID(fixed64, "a");
+ EXPECT_INVALID(fixed64, "999999999999999999999999999999999999");
+ EXPECT_INVALID(fixed64, "1,2");
+
+ // bool
+ EXPECT_BOOL_FIELD(bool, true, "true");
+ EXPECT_BOOL_FIELD(bool, false, "false");
+ EXPECT_BOOL_FIELD(bool, true, "1");
+ EXPECT_BOOL_FIELD(bool, true, "t");
+ EXPECT_BOOL_FIELD(bool, false, "0");
+ EXPECT_BOOL_FIELD(bool, false, "f");
+ EXPECT_FIELD(bool, true, "True");
+ EXPECT_FIELD(bool, false, "False");
+ EXPECT_INVALID(bool, "tRue");
+ EXPECT_INVALID(bool, "faLse");
+ EXPECT_INVALID(bool, "2");
+ EXPECT_INVALID(bool, "-0");
+ EXPECT_INVALID(bool, "on");
+ EXPECT_INVALID(bool, "a");
+
+ // float
+ EXPECT_FIELD(float, 1, "1");
+ EXPECT_FLOAT_FIELD(float, 1.5, "1.5");
+ EXPECT_FLOAT_FIELD(float, 1.5e3, "1.5e3");
+ EXPECT_FLOAT_FIELD(float, -4.55, "-4.55");
+ EXPECT_INVALID(float, "a");
+ EXPECT_INVALID(float, "1,2");
+
+ // double
+ EXPECT_FIELD(double, 1, "1");
+ EXPECT_FIELD(double, -1, "-1");
+ EXPECT_DOUBLE_FIELD(double, 2.3, "2.3");
+ EXPECT_DOUBLE_FIELD(double, 3e5, "3e5");
+ EXPECT_INVALID(double, "a");
+ EXPECT_INVALID(double, "1,2");
+ // Rejects hex and oct numbers for a double field.
+ EXPECT_INVALID(double, "0xf");
+ EXPECT_INVALID(double, "012");
+
+ // string
+ EXPECT_FIELD(string, "hello", "\"hello\"");
+ EXPECT_FIELD(string, "-1.87", "'-1.87'");
+ EXPECT_INVALID(string, "hello"); // without quote for value
+
+ // enum
+ EXPECT_FIELD(nested_enum, unittest::TestAllTypes::BAR, "BAR");
+ EXPECT_FIELD(nested_enum, unittest::TestAllTypes::BAZ,
+ SimpleItoa(unittest::TestAllTypes::BAZ));
+ EXPECT_INVALID(nested_enum, "FOOBAR");
+
+ // message
+ EXPECT_TRUE(TextFormat::ParseFieldValueFromString(
+ "<bb:12>", d->FindFieldByName("optional_nested_message"), message.get()));
+ EXPECT_EQ(12, message->optional_nested_message().bb()); \
+ EXPECT_TRUE(message->has_optional_nested_message());
+ EXPECT_INVALID(nested_message, "any");
+
+#undef EXPECT_FIELD
+#undef EXPECT_BOOL_FIELD
+#undef EXPECT_FLOAT_FIELD
+#undef EXPECT_DOUBLE_FIELD
+#undef EXPECT_INVALID
+}
+
+
+TEST_F(TextFormatParserTest, InvalidToken) {
+ ExpectFailure("optional_bool: true\n-5\n", "Expected identifier, got: -",
+ 2, 1);
+
+ ExpectFailure("optional_bool: true!\n", "Expected identifier, got: !", 1,
+ 20);
+ ExpectFailure("\"some string\"",
+ "Expected identifier, got: \"some string\"", 1, 1);
+}
+
+TEST_F(TextFormatParserTest, InvalidFieldName) {
+ ExpectFailure(
+ "invalid_field: somevalue\n",
+ "Message type \"protobuf_unittest.TestAllTypes\" has no field named "
+ "\"invalid_field\".",
+ 1, 14);
+}
+
+TEST_F(TextFormatParserTest, InvalidCapitalization) {
+ // We require that group names be exactly as they appear in the .proto.
+ ExpectFailure(
+ "optionalgroup {\na: 15\n}\n",
+ "Message type \"protobuf_unittest.TestAllTypes\" has no field named "
+ "\"optionalgroup\".",
+ 1, 15);
+ ExpectFailure(
+ "OPTIONALgroup {\na: 15\n}\n",
+ "Message type \"protobuf_unittest.TestAllTypes\" has no field named "
+ "\"OPTIONALgroup\".",
+ 1, 15);
+ ExpectFailure(
+ "Optional_Double: 10.0\n",
+ "Message type \"protobuf_unittest.TestAllTypes\" has no field named "
+ "\"Optional_Double\".",
+ 1, 16);
+}
+
+TEST_F(TextFormatParserTest, AllowIgnoreCapitalizationError) {
+ TextFormat::Parser parser;
+ protobuf_unittest::TestAllTypes proto;
+
+ // These fields have a mismatching case.
+ EXPECT_FALSE(parser.ParseFromString("Optional_Double: 10.0", &proto));
+ EXPECT_FALSE(parser.ParseFromString("oPtIoNaLgRoUp { a: 15 }", &proto));
+
+ // ... but are parsed correctly if we match case insensitive.
+ parser.AllowCaseInsensitiveField(true);
+ EXPECT_TRUE(parser.ParseFromString("Optional_Double: 10.0", &proto));
+ EXPECT_EQ(10.0, proto.optional_double());
+ EXPECT_TRUE(parser.ParseFromString("oPtIoNaLgRoUp { a: 15 }", &proto));
+ EXPECT_EQ(15, proto.optionalgroup().a());
+}
+
+TEST_F(TextFormatParserTest, InvalidFieldValues) {
+ // Invalid values for a double/float field.
+ ExpectFailure("optional_double: \"hello\"\n",
+ "Expected double, got: \"hello\"", 1, 18);
+ ExpectFailure("optional_double: true\n", "Expected double, got: true", 1,
+ 18);
+ ExpectFailure("optional_double: !\n", "Expected double, got: !", 1, 18);
+ ExpectFailure("optional_double {\n \n}\n", "Expected \":\", found \"{\".",
+ 1, 17);
+
+ // Invalid values for a signed integer field.
+ ExpectFailure("optional_int32: \"hello\"\n",
+ "Expected integer, got: \"hello\"", 1, 17);
+ ExpectFailure("optional_int32: true\n", "Expected integer, got: true", 1, 17);
+ ExpectFailure("optional_int32: 4.5\n", "Expected integer, got: 4.5", 1, 17);
+ ExpectFailure("optional_int32: !\n", "Expected integer, got: !", 1, 17);
+ ExpectFailure("optional_int32 {\n \n}\n", "Expected \":\", found \"{\".",
+ 1, 16);
+ ExpectFailure("optional_int32: 0x80000000\n",
+ "Integer out of range (0x80000000)", 1, 17);
+ ExpectFailure("optional_int64: 0x8000000000000000\n",
+ "Integer out of range (0x8000000000000000)", 1, 17);
+ ExpectFailure("optional_int32: -0x80000001\n",
+ "Integer out of range (0x80000001)", 1, 18);
+ ExpectFailure("optional_int64: -0x8000000000000001\n",
+ "Integer out of range (0x8000000000000001)", 1, 18);
+
+ // Invalid values for an unsigned integer field.
+ ExpectFailure("optional_uint64: \"hello\"\n",
+ "Expected integer, got: \"hello\"", 1, 18);
+ ExpectFailure("optional_uint64: true\n",
+ "Expected integer, got: true", 1, 18);
+ ExpectFailure("optional_uint64: 4.5\n", "Expected integer, got: 4.5", 1, 18);
+ ExpectFailure("optional_uint64: -5\n", "Expected integer, got: -", 1, 18);
+ ExpectFailure("optional_uint64: !\n", "Expected integer, got: !", 1, 18);
+ ExpectFailure("optional_uint64 {\n \n}\n", "Expected \":\", found \"{\".",
+ 1, 17);
+ ExpectFailure("optional_uint32: 0x100000000\n",
+ "Integer out of range (0x100000000)", 1, 18);
+ ExpectFailure("optional_uint64: 0x10000000000000000\n",
+ "Integer out of range (0x10000000000000000)", 1, 18);
+
+ // Invalid values for a boolean field.
+ ExpectFailure("optional_bool: \"hello\"\n",
+ "Expected identifier, got: \"hello\"", 1, 16);
+ ExpectFailure("optional_bool: 5\n", "Integer out of range (5)", 1, 16);
+ ExpectFailure("optional_bool: -7.5\n", "Expected identifier, got: -", 1, 16);
+ ExpectFailure("optional_bool: !\n", "Expected identifier, got: !", 1, 16);
+
+ ExpectFailure(
+ "optional_bool: meh\n",
+ "Invalid value for boolean field \"optional_bool\". Value: \"meh\".",
+ 2, 1);
+
+ ExpectFailure("optional_bool {\n \n}\n", "Expected \":\", found \"{\".",
+ 1, 15);
+
+ // Invalid values for a string field.
+ ExpectFailure("optional_string: true\n", "Expected string, got: true", 1, 18);
+ ExpectFailure("optional_string: 5\n", "Expected string, got: 5", 1, 18);
+ ExpectFailure("optional_string: -7.5\n", "Expected string, got: -", 1, 18);
+ ExpectFailure("optional_string: !\n", "Expected string, got: !", 1, 18);
+ ExpectFailure("optional_string {\n \n}\n", "Expected \":\", found \"{\".",
+ 1, 17);
+
+ // Invalid values for an enumeration field.
+ ExpectFailure("optional_nested_enum: \"hello\"\n",
+ "Expected integer or identifier, got: \"hello\"", 1, 23);
+
+ // Valid token, but enum value is not defined.
+ ExpectFailure("optional_nested_enum: 5\n",
+ "Unknown enumeration value of \"5\" for field "
+ "\"optional_nested_enum\".", 2, 1);
+ // We consume the negative sign, so the error position starts one character
+ // later.
+ ExpectFailure("optional_nested_enum: -7.5\n", "Expected integer, got: 7.5", 1,
+ 24);
+ ExpectFailure("optional_nested_enum: !\n",
+ "Expected integer or identifier, got: !", 1, 23);
+
+ ExpectFailure(
+ "optional_nested_enum: grah\n",
+ "Unknown enumeration value of \"grah\" for field "
+ "\"optional_nested_enum\".", 2, 1);
+
+ ExpectFailure(
+ "optional_nested_enum {\n \n}\n",
+ "Expected \":\", found \"{\".", 1, 22);
+}
+
+TEST_F(TextFormatParserTest, MessageDelimiters) {
+ // Non-matching delimiters.
+ ExpectFailure("OptionalGroup <\n \n}\n", "Expected \">\", found \"}\".",
+ 3, 1);
+
+ // Invalid delimiters.
+ ExpectFailure("OptionalGroup [\n \n]\n", "Expected \"{\", found \"[\".",
+ 1, 15);
+
+ // Unending message.
+ ExpectFailure("optional_nested_message {\n \nbb: 118\n",
+ "Expected identifier, got: ",
+ 4, 1);
+}
+
+TEST_F(TextFormatParserTest, UnknownExtension) {
+ // Non-matching delimiters.
+ ExpectFailure("[blahblah]: 123",
+ "Extension \"blahblah\" is not defined or is not an "
+ "extension of \"protobuf_unittest.TestAllTypes\".",
+ 1, 11);
+}
+
+TEST_F(TextFormatParserTest, MissingRequired) {
+ unittest::TestRequired message;
+ ExpectFailure("a: 1",
+ "Message missing required fields: b, c",
+ 0, 1, &message);
+}
+
+TEST_F(TextFormatParserTest, ParseDuplicateRequired) {
+ unittest::TestRequired message;
+ ExpectFailure("a: 1 b: 2 c: 3 a: 1",
+ "Non-repeated field \"a\" is specified multiple times.",
+ 1, 17, &message);
+}
+
+TEST_F(TextFormatParserTest, ParseDuplicateOptional) {
+ unittest::ForeignMessage message;
+ ExpectFailure("c: 1 c: 2",
+ "Non-repeated field \"c\" is specified multiple times.",
+ 1, 7, &message);
+}
+
+TEST_F(TextFormatParserTest, MergeDuplicateRequired) {
+ unittest::TestRequired message;
+ TextFormat::Parser parser;
+ EXPECT_TRUE(parser.MergeFromString("a: 1 b: 2 c: 3 a: 4", &message));
+ EXPECT_EQ(4, message.a());
+}
+
+TEST_F(TextFormatParserTest, MergeDuplicateOptional) {
+ unittest::ForeignMessage message;
+ TextFormat::Parser parser;
+ EXPECT_TRUE(parser.MergeFromString("c: 1 c: 2", &message));
+ EXPECT_EQ(2, message.c());
+}
+
+TEST_F(TextFormatParserTest, ExplicitDelimiters) {
+ unittest::TestRequired message;
+ EXPECT_TRUE(TextFormat::ParseFromString("a:1,b:2;c:3", &message));
+ EXPECT_EQ(1, message.a());
+ EXPECT_EQ(2, message.b());
+ EXPECT_EQ(3, message.c());
+}
+
+TEST_F(TextFormatParserTest, PrintErrorsToStderr) {
+ vector<string> errors;
+
+ {
+ ScopedMemoryLog log;
+ unittest::TestAllTypes proto;
+ EXPECT_FALSE(TextFormat::ParseFromString("no_such_field: 1", &proto));
+ errors = log.GetMessages(ERROR);
+ }
+
+ ASSERT_EQ(1, errors.size());
+ EXPECT_EQ("Error parsing text-format protobuf_unittest.TestAllTypes: "
+ "1:14: Message type \"protobuf_unittest.TestAllTypes\" has no field "
+ "named \"no_such_field\".",
+ errors[0]);
+}
+
+TEST_F(TextFormatParserTest, FailsOnTokenizationError) {
+ vector<string> errors;
+
+ {
+ ScopedMemoryLog log;
+ unittest::TestAllTypes proto;
+ EXPECT_FALSE(TextFormat::ParseFromString("\020", &proto));
+ errors = log.GetMessages(ERROR);
+ }
+
+ ASSERT_EQ(1, errors.size());
+ EXPECT_EQ("Error parsing text-format protobuf_unittest.TestAllTypes: "
+ "1:1: Invalid control characters encountered in text.",
+ errors[0]);
+}
+
+TEST_F(TextFormatParserTest, ParseDeprecatedField) {
+ unittest::TestDeprecatedFields message;
+ ExpectMessage("deprecated_int32: 42",
+ "WARNING:text format contains deprecated field "
+ "\"deprecated_int32\"", 1, 21, &message, true);
+}
+
+class TextFormatMessageSetTest : public testing::Test {
+ protected:
+ static const char proto_debug_string_[];
+};
+const char TextFormatMessageSetTest::proto_debug_string_[] =
+"message_set {\n"
+" [protobuf_unittest.TestMessageSetExtension1] {\n"
+" i: 23\n"
+" }\n"
+" [protobuf_unittest.TestMessageSetExtension2] {\n"
+" str: \"foo\"\n"
+" }\n"
+"}\n";
+
+
+TEST_F(TextFormatMessageSetTest, Serialize) {
+ protobuf_unittest::TestMessageSetContainer proto;
+ protobuf_unittest::TestMessageSetExtension1* item_a =
+ proto.mutable_message_set()->MutableExtension(
+ protobuf_unittest::TestMessageSetExtension1::message_set_extension);
+ item_a->set_i(23);
+ protobuf_unittest::TestMessageSetExtension2* item_b =
+ proto.mutable_message_set()->MutableExtension(
+ protobuf_unittest::TestMessageSetExtension2::message_set_extension);
+ item_b->set_str("foo");
+ EXPECT_EQ(proto_debug_string_, proto.DebugString());
+}
+
+TEST_F(TextFormatMessageSetTest, Deserialize) {
+ protobuf_unittest::TestMessageSetContainer proto;
+ ASSERT_TRUE(TextFormat::ParseFromString(proto_debug_string_, &proto));
+ EXPECT_EQ(23, proto.message_set().GetExtension(
+ protobuf_unittest::TestMessageSetExtension1::message_set_extension).i());
+ EXPECT_EQ("foo", proto.message_set().GetExtension(
+ protobuf_unittest::TestMessageSetExtension2::message_set_extension).str());
+
+ // Ensure that these are the only entries present.
+ vector<const FieldDescriptor*> descriptors;
+ proto.message_set().GetReflection()->ListFields(
+ proto.message_set(), &descriptors);
+ EXPECT_EQ(2, descriptors.size());
+}
+
+
+} // namespace text_format_unittest
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.cc
new file mode 100644
index 0000000000..542e5ed7e4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.cc
@@ -0,0 +1,448 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/timestamp.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/timestamp.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* Timestamp_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Timestamp_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2ftimestamp_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2ftimestamp_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2ftimestamp_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/timestamp.proto");
+ GOOGLE_CHECK(file != NULL);
+ Timestamp_descriptor_ = file->message_type(0);
+ static const int Timestamp_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Timestamp, seconds_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Timestamp, nanos_),
+ };
+ Timestamp_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Timestamp_descriptor_,
+ Timestamp::default_instance_,
+ Timestamp_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Timestamp),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Timestamp, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Timestamp, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2ftimestamp_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Timestamp_descriptor_, &Timestamp::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2ftimestamp_2eproto() {
+ delete Timestamp::default_instance_;
+ delete Timestamp_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2ftimestamp_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2ftimestamp_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n\037google/protobuf/timestamp.proto\022\017googl"
+ "e.protobuf\"+\n\tTimestamp\022\017\n\007seconds\030\001 \001(\003"
+ "\022\r\n\005nanos\030\002 \001(\005B\201\001\n\023com.google.protobufB"
+ "\016TimestampProtoP\001Z+github.com/golang/pro"
+ "tobuf/ptypes/timestamp\240\001\001\370\001\001\242\002\003GPB\252\002\036Goo"
+ "gle.Protobuf.WellKnownTypesb\006proto3", 235);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/timestamp.proto", &protobuf_RegisterTypes);
+ Timestamp::default_instance_ = new Timestamp();
+ Timestamp::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2ftimestamp_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2ftimestamp_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2ftimestamp_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2ftimestamp_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2ftimestamp_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Timestamp::kSecondsFieldNumber;
+const int Timestamp::kNanosFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Timestamp::Timestamp()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Timestamp)
+}
+
+Timestamp::Timestamp(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.Timestamp)
+}
+
+void Timestamp::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Timestamp::Timestamp(const Timestamp& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Timestamp)
+}
+
+void Timestamp::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ seconds_ = GOOGLE_LONGLONG(0);
+ nanos_ = 0;
+}
+
+Timestamp::~Timestamp() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Timestamp)
+ SharedDtor();
+}
+
+void Timestamp::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void Timestamp::ArenaDtor(void* object) {
+ Timestamp* _this = reinterpret_cast< Timestamp* >(object);
+ (void)_this;
+}
+void Timestamp::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void Timestamp::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Timestamp::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Timestamp_descriptor_;
+}
+
+const Timestamp& Timestamp::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2ftimestamp_2eproto();
+ return *default_instance_;
+}
+
+Timestamp* Timestamp::default_instance_ = NULL;
+
+Timestamp* Timestamp::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<Timestamp>(arena);
+}
+
+void Timestamp::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Timestamp)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(Timestamp, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<Timestamp*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(seconds_, nanos_);
+
+#undef ZR_HELPER_
+#undef ZR_
+
+}
+
+bool Timestamp::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Timestamp)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional int64 seconds = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int64, ::google::protobuf::internal::WireFormatLite::TYPE_INT64>(
+ input, &seconds_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_nanos;
+ break;
+ }
+
+ // optional int32 nanos = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_nanos:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &nanos_)));
+
+ } 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Timestamp)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Timestamp)
+ return false;
+#undef DO_
+}
+
+void Timestamp::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Timestamp)
+ // optional int64 seconds = 1;
+ if (this->seconds() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt64(1, this->seconds(), output);
+ }
+
+ // optional int32 nanos = 2;
+ if (this->nanos() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(2, this->nanos(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Timestamp)
+}
+
+::google::protobuf::uint8* Timestamp::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Timestamp)
+ // optional int64 seconds = 1;
+ if (this->seconds() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt64ToArray(1, this->seconds(), target);
+ }
+
+ // optional int32 nanos = 2;
+ if (this->nanos() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(2, this->nanos(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Timestamp)
+ return target;
+}
+
+int Timestamp::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Timestamp)
+ int total_size = 0;
+
+ // optional int64 seconds = 1;
+ if (this->seconds() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int64Size(
+ this->seconds());
+ }
+
+ // optional int32 nanos = 2;
+ if (this->nanos() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->nanos());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Timestamp::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Timestamp)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Timestamp* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Timestamp>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Timestamp)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Timestamp)
+ MergeFrom(*source);
+ }
+}
+
+void Timestamp::MergeFrom(const Timestamp& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Timestamp)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.seconds() != 0) {
+ set_seconds(from.seconds());
+ }
+ if (from.nanos() != 0) {
+ set_nanos(from.nanos());
+ }
+}
+
+void Timestamp::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Timestamp)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Timestamp::CopyFrom(const Timestamp& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Timestamp)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Timestamp::IsInitialized() const {
+
+ return true;
+}
+
+void Timestamp::Swap(Timestamp* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ Timestamp temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void Timestamp::UnsafeArenaSwap(Timestamp* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void Timestamp::InternalSwap(Timestamp* other) {
+ std::swap(seconds_, other->seconds_);
+ std::swap(nanos_, other->nanos_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Timestamp::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Timestamp_descriptor_;
+ metadata.reflection = Timestamp_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Timestamp
+
+// optional int64 seconds = 1;
+void Timestamp::clear_seconds() {
+ seconds_ = GOOGLE_LONGLONG(0);
+}
+ ::google::protobuf::int64 Timestamp::seconds() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Timestamp.seconds)
+ return seconds_;
+}
+ void Timestamp::set_seconds(::google::protobuf::int64 value) {
+
+ seconds_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Timestamp.seconds)
+}
+
+// optional int32 nanos = 2;
+void Timestamp::clear_nanos() {
+ nanos_ = 0;
+}
+ ::google::protobuf::int32 Timestamp::nanos() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Timestamp.nanos)
+ return nanos_;
+}
+ void Timestamp::set_nanos(::google::protobuf::int32 value) {
+
+ nanos_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Timestamp.nanos)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.h
new file mode 100644
index 0000000000..19f4f86f70
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.pb.h
@@ -0,0 +1,189 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/timestamp.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2ftimestamp_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2ftimestamp_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftimestamp_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2ftimestamp_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2ftimestamp_2eproto();
+
+class Timestamp;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT Timestamp : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Timestamp) */ {
+ public:
+ Timestamp();
+ virtual ~Timestamp();
+
+ Timestamp(const Timestamp& from);
+
+ inline Timestamp& operator=(const Timestamp& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Timestamp& default_instance();
+
+ void UnsafeArenaSwap(Timestamp* other);
+ void Swap(Timestamp* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Timestamp* New() const { return New(NULL); }
+
+ Timestamp* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Timestamp& from);
+ void MergeFrom(const Timestamp& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Timestamp* other);
+ protected:
+ explicit Timestamp(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional int64 seconds = 1;
+ void clear_seconds();
+ static const int kSecondsFieldNumber = 1;
+ ::google::protobuf::int64 seconds() const;
+ void set_seconds(::google::protobuf::int64 value);
+
+ // optional int32 nanos = 2;
+ void clear_nanos();
+ static const int kNanosFieldNumber = 2;
+ ::google::protobuf::int32 nanos() const;
+ void set_nanos(::google::protobuf::int32 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Timestamp)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ ::google::protobuf::int64 seconds_;
+ ::google::protobuf::int32 nanos_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftimestamp_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2ftimestamp_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2ftimestamp_2eproto();
+
+ void InitAsDefaultInstance();
+ static Timestamp* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// Timestamp
+
+// optional int64 seconds = 1;
+inline void Timestamp::clear_seconds() {
+ seconds_ = GOOGLE_LONGLONG(0);
+}
+inline ::google::protobuf::int64 Timestamp::seconds() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Timestamp.seconds)
+ return seconds_;
+}
+inline void Timestamp::set_seconds(::google::protobuf::int64 value) {
+
+ seconds_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Timestamp.seconds)
+}
+
+// optional int32 nanos = 2;
+inline void Timestamp::clear_nanos() {
+ nanos_ = 0;
+}
+inline ::google::protobuf::int32 Timestamp::nanos() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Timestamp.nanos)
+ return nanos_;
+}
+inline void Timestamp::set_nanos(::google::protobuf::int32 value) {
+
+ nanos_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Timestamp.nanos)
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2ftimestamp_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.proto b/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.proto
new file mode 100644
index 0000000000..7992a85886
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/timestamp.proto
@@ -0,0 +1,111 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option cc_enable_arenas = true;
+option go_package = "github.com/golang/protobuf/ptypes/timestamp";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "TimestampProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+// A Timestamp represents a point in time independent of any time zone
+// or calendar, represented as seconds and fractions of seconds at
+// nanosecond resolution in UTC Epoch time. It is encoded using the
+// Proleptic Gregorian Calendar which extends the Gregorian calendar
+// backwards to year one. It is encoded assuming all minutes are 60
+// seconds long, i.e. leap seconds are "smeared" so that no leap second
+// table is needed for interpretation. Range is from
+// 0001-01-01T00:00:00Z to 9999-12-31T23:59:59.999999999Z.
+// By restricting to that range, we ensure that we can convert to
+// and from RFC 3339 date strings.
+// See [https://www.ietf.org/rfc/rfc3339.txt](https://www.ietf.org/rfc/rfc3339.txt).
+//
+// Example 1: Compute Timestamp from POSIX `time()`.
+//
+// Timestamp timestamp;
+// timestamp.set_seconds(time(NULL));
+// timestamp.set_nanos(0);
+//
+// Example 2: Compute Timestamp from POSIX `gettimeofday()`.
+//
+// struct timeval tv;
+// gettimeofday(&tv, NULL);
+//
+// Timestamp timestamp;
+// timestamp.set_seconds(tv.tv_sec);
+// timestamp.set_nanos(tv.tv_usec * 1000);
+//
+// Example 3: Compute Timestamp from Win32 `GetSystemTimeAsFileTime()`.
+//
+// FILETIME ft;
+// GetSystemTimeAsFileTime(&ft);
+// UINT64 ticks = (((UINT64)ft.dwHighDateTime) << 32) | ft.dwLowDateTime;
+//
+// // A Windows tick is 100 nanoseconds. Windows epoch 1601-01-01T00:00:00Z
+// // is 11644473600 seconds before Unix epoch 1970-01-01T00:00:00Z.
+// Timestamp timestamp;
+// timestamp.set_seconds((INT64) ((ticks / 10000000) - 11644473600LL));
+// timestamp.set_nanos((INT32) ((ticks % 10000000) * 100));
+//
+// Example 4: Compute Timestamp from Java `System.currentTimeMillis()`.
+//
+// long millis = System.currentTimeMillis();
+//
+// Timestamp timestamp = Timestamp.newBuilder().setSeconds(millis / 1000)
+// .setNanos((int) ((millis % 1000) * 1000000)).build();
+//
+//
+// Example 5: Compute Timestamp from current time in Python.
+//
+// now = time.time()
+// seconds = int(now)
+// nanos = int((now - seconds) * 10**9)
+// timestamp = Timestamp(seconds=seconds, nanos=nanos)
+//
+//
+message Timestamp {
+
+ // Represents seconds of UTC time since Unix epoch
+ // 1970-01-01T00:00:00Z. Must be from from 0001-01-01T00:00:00Z to
+ // 9999-12-31T23:59:59Z inclusive.
+ int64 seconds = 1;
+
+ // Non-negative fractions of a second at nanosecond resolution. Negative
+ // second values with fractions must still have non-negative nanos values
+ // that count forward in time. Must be from 0 to 999,999,999
+ // inclusive.
+ int32 nanos = 2;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/type.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/type.pb.cc
new file mode 100644
index 0000000000..7ba909ef1c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/type.pb.cc
@@ -0,0 +1,3304 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/type.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/type.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* Type_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Type_reflection_ = NULL;
+const ::google::protobuf::Descriptor* Field_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Field_reflection_ = NULL;
+const ::google::protobuf::EnumDescriptor* Field_Kind_descriptor_ = NULL;
+const ::google::protobuf::EnumDescriptor* Field_Cardinality_descriptor_ = NULL;
+const ::google::protobuf::Descriptor* Enum_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Enum_reflection_ = NULL;
+const ::google::protobuf::Descriptor* EnumValue_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ EnumValue_reflection_ = NULL;
+const ::google::protobuf::Descriptor* Option_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Option_reflection_ = NULL;
+const ::google::protobuf::EnumDescriptor* Syntax_descriptor_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/type.proto");
+ GOOGLE_CHECK(file != NULL);
+ Type_descriptor_ = file->message_type(0);
+ static const int Type_offsets_[6] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, fields_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, oneofs_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, source_context_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, syntax_),
+ };
+ Type_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Type_descriptor_,
+ Type::default_instance_,
+ Type_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Type),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Type, _is_default_instance_));
+ Field_descriptor_ = file->message_type(1);
+ static const int Field_offsets_[10] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, kind_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, cardinality_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, number_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, type_url_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, oneof_index_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, packed_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, json_name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, default_value_),
+ };
+ Field_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Field_descriptor_,
+ Field::default_instance_,
+ Field_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Field),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Field, _is_default_instance_));
+ Field_Kind_descriptor_ = Field_descriptor_->enum_type(0);
+ Field_Cardinality_descriptor_ = Field_descriptor_->enum_type(1);
+ Enum_descriptor_ = file->message_type(2);
+ static const int Enum_offsets_[5] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Enum, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Enum, enumvalue_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Enum, options_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Enum, source_context_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Enum, syntax_),
+ };
+ Enum_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Enum_descriptor_,
+ Enum::default_instance_,
+ Enum_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Enum),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Enum, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Enum, _is_default_instance_));
+ EnumValue_descriptor_ = file->message_type(3);
+ static const int EnumValue_offsets_[3] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValue, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValue, number_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValue, options_),
+ };
+ EnumValue_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ EnumValue_descriptor_,
+ EnumValue::default_instance_,
+ EnumValue_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(EnumValue),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValue, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(EnumValue, _is_default_instance_));
+ Option_descriptor_ = file->message_type(4);
+ static const int Option_offsets_[2] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Option, name_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Option, value_),
+ };
+ Option_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Option_descriptor_,
+ Option::default_instance_,
+ Option_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Option),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Option, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Option, _is_default_instance_));
+ Syntax_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_2ftype_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Type_descriptor_, &Type::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Field_descriptor_, &Field::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Enum_descriptor_, &Enum::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ EnumValue_descriptor_, &EnumValue::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Option_descriptor_, &Option::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto() {
+ delete Type::default_instance_;
+ delete Type_reflection_;
+ delete Field::default_instance_;
+ delete Field_reflection_;
+ delete Enum::default_instance_;
+ delete Enum_reflection_;
+ delete EnumValue::default_instance_;
+ delete EnumValue_reflection_;
+ delete Option::default_instance_;
+ delete Option_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::protobuf_AddDesc_google_2fprotobuf_2fany_2eproto();
+ ::google::protobuf::protobuf_AddDesc_google_2fprotobuf_2fsource_5fcontext_2eproto();
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n\032google/protobuf/type.proto\022\017google.pro"
+ "tobuf\032\031google/protobuf/any.proto\032$google"
+ "/protobuf/source_context.proto\"\327\001\n\004Type\022"
+ "\014\n\004name\030\001 \001(\t\022&\n\006fields\030\002 \003(\0132\026.google.p"
+ "rotobuf.Field\022\016\n\006oneofs\030\003 \003(\t\022(\n\007options"
+ "\030\004 \003(\0132\027.google.protobuf.Option\0226\n\016sourc"
+ "e_context\030\005 \001(\0132\036.google.protobuf.Source"
+ "Context\022\'\n\006syntax\030\006 \001(\0162\027.google.protobu"
+ "f.Syntax\"\325\005\n\005Field\022)\n\004kind\030\001 \001(\0162\033.googl"
+ "e.protobuf.Field.Kind\0227\n\013cardinality\030\002 \001"
+ "(\0162\".google.protobuf.Field.Cardinality\022\016"
+ "\n\006number\030\003 \001(\005\022\014\n\004name\030\004 \001(\t\022\020\n\010type_url"
+ "\030\006 \001(\t\022\023\n\013oneof_index\030\007 \001(\005\022\016\n\006packed\030\010 "
+ "\001(\010\022(\n\007options\030\t \003(\0132\027.google.protobuf.O"
+ "ption\022\021\n\tjson_name\030\n \001(\t\022\025\n\rdefault_valu"
+ "e\030\013 \001(\t\"\310\002\n\004Kind\022\020\n\014TYPE_UNKNOWN\020\000\022\017\n\013TY"
+ "PE_DOUBLE\020\001\022\016\n\nTYPE_FLOAT\020\002\022\016\n\nTYPE_INT6"
+ "4\020\003\022\017\n\013TYPE_UINT64\020\004\022\016\n\nTYPE_INT32\020\005\022\020\n\014"
+ "TYPE_FIXED64\020\006\022\020\n\014TYPE_FIXED32\020\007\022\r\n\tTYPE"
+ "_BOOL\020\010\022\017\n\013TYPE_STRING\020\t\022\016\n\nTYPE_GROUP\020\n"
+ "\022\020\n\014TYPE_MESSAGE\020\013\022\016\n\nTYPE_BYTES\020\014\022\017\n\013TY"
+ "PE_UINT32\020\r\022\r\n\tTYPE_ENUM\020\016\022\021\n\rTYPE_SFIXE"
+ "D32\020\017\022\021\n\rTYPE_SFIXED64\020\020\022\017\n\013TYPE_SINT32\020"
+ "\021\022\017\n\013TYPE_SINT64\020\022\"t\n\013Cardinality\022\027\n\023CAR"
+ "DINALITY_UNKNOWN\020\000\022\030\n\024CARDINALITY_OPTION"
+ "AL\020\001\022\030\n\024CARDINALITY_REQUIRED\020\002\022\030\n\024CARDIN"
+ "ALITY_REPEATED\020\003\"\316\001\n\004Enum\022\014\n\004name\030\001 \001(\t\022"
+ "-\n\tenumvalue\030\002 \003(\0132\032.google.protobuf.Enu"
+ "mValue\022(\n\007options\030\003 \003(\0132\027.google.protobu"
+ "f.Option\0226\n\016source_context\030\004 \001(\0132\036.googl"
+ "e.protobuf.SourceContext\022\'\n\006syntax\030\005 \001(\016"
+ "2\027.google.protobuf.Syntax\"S\n\tEnumValue\022\014"
+ "\n\004name\030\001 \001(\t\022\016\n\006number\030\002 \001(\005\022(\n\007options\030"
+ "\003 \003(\0132\027.google.protobuf.Option\";\n\006Option"
+ "\022\014\n\004name\030\001 \001(\t\022#\n\005value\030\002 \001(\0132\024.google.p"
+ "rotobuf.Any*.\n\006Syntax\022\021\n\rSYNTAX_PROTO2\020\000"
+ "\022\021\n\rSYNTAX_PROTO3\020\001BL\n\023com.google.protob"
+ "ufB\tTypeProtoP\001\240\001\001\242\002\003GPB\252\002\036Google.Protob"
+ "uf.WellKnownTypesb\006proto3", 1545);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/type.proto", &protobuf_RegisterTypes);
+ Type::default_instance_ = new Type();
+ Field::default_instance_ = new Field();
+ Enum::default_instance_ = new Enum();
+ EnumValue::default_instance_ = new EnumValue();
+ Option::default_instance_ = new Option();
+ Type::default_instance_->InitAsDefaultInstance();
+ Field::default_instance_->InitAsDefaultInstance();
+ Enum::default_instance_->InitAsDefaultInstance();
+ EnumValue::default_instance_->InitAsDefaultInstance();
+ Option::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2ftype_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2ftype_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2ftype_2eproto_;
+const ::google::protobuf::EnumDescriptor* Syntax_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Syntax_descriptor_;
+}
+bool Syntax_IsValid(int value) {
+ switch(value) {
+ case 0:
+ case 1:
+ return true;
+ default:
+ return false;
+ }
+}
+
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Type::kNameFieldNumber;
+const int Type::kFieldsFieldNumber;
+const int Type::kOneofsFieldNumber;
+const int Type::kOptionsFieldNumber;
+const int Type::kSourceContextFieldNumber;
+const int Type::kSyntaxFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Type::Type()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Type)
+}
+
+void Type::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+ source_context_ = const_cast< ::google::protobuf::SourceContext*>(&::google::protobuf::SourceContext::default_instance());
+}
+
+Type::Type(const Type& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Type)
+}
+
+void Type::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ source_context_ = NULL;
+ syntax_ = 0;
+}
+
+Type::~Type() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Type)
+ SharedDtor();
+}
+
+void Type::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete source_context_;
+ }
+}
+
+void Type::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Type::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Type_descriptor_;
+}
+
+const Type& Type::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ return *default_instance_;
+}
+
+Type* Type::default_instance_ = NULL;
+
+Type* Type::New(::google::protobuf::Arena* arena) const {
+ Type* n = new Type;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Type::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Type)
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+ syntax_ = 0;
+ fields_.Clear();
+ oneofs_.Clear();
+ options_.Clear();
+}
+
+bool Type::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Type)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Type.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_fields;
+ break;
+ }
+
+ // repeated .google.protobuf.Field fields = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_fields:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_fields:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_fields()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_loop_fields;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(26)) goto parse_oneofs;
+ break;
+ }
+
+ // repeated string oneofs = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_oneofs:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->add_oneofs()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->oneofs(this->oneofs_size() - 1).data(),
+ this->oneofs(this->oneofs_size() - 1).length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Type.oneofs"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_oneofs;
+ if (input->ExpectTag(34)) goto parse_options;
+ break;
+ }
+
+ // repeated .google.protobuf.Option options = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_options:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(34)) goto parse_loop_options;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(42)) goto parse_source_context;
+ break;
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ case 5: {
+ if (tag == 42) {
+ parse_source_context:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_source_context()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(48)) goto parse_syntax;
+ break;
+ }
+
+ // optional .google.protobuf.Syntax syntax = 6;
+ case 6: {
+ if (tag == 48) {
+ parse_syntax:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ set_syntax(static_cast< ::google::protobuf::Syntax >(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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Type)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Type)
+ return false;
+#undef DO_
+}
+
+void Type::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Type)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Type.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // repeated .google.protobuf.Field fields = 2;
+ for (unsigned int i = 0, n = this->fields_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, this->fields(i), output);
+ }
+
+ // repeated string oneofs = 3;
+ for (int i = 0; i < this->oneofs_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->oneofs(i).data(), this->oneofs(i).length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Type.oneofs");
+ ::google::protobuf::internal::WireFormatLite::WriteString(
+ 3, this->oneofs(i), output);
+ }
+
+ // repeated .google.protobuf.Option options = 4;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 4, this->options(i), output);
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ if (this->has_source_context()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 5, *this->source_context_, output);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 6;
+ if (this->syntax() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 6, this->syntax(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Type)
+}
+
+::google::protobuf::uint8* Type::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Type)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Type.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // repeated .google.protobuf.Field fields = 2;
+ for (unsigned int i = 0, n = this->fields_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, this->fields(i), false, target);
+ }
+
+ // repeated string oneofs = 3;
+ for (int i = 0; i < this->oneofs_size(); i++) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->oneofs(i).data(), this->oneofs(i).length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Type.oneofs");
+ target = ::google::protobuf::internal::WireFormatLite::
+ WriteStringToArray(3, this->oneofs(i), target);
+ }
+
+ // repeated .google.protobuf.Option options = 4;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 4, this->options(i), false, target);
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ if (this->has_source_context()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 5, *this->source_context_, false, target);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 6;
+ if (this->syntax() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 6, this->syntax(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Type)
+ return target;
+}
+
+int Type::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Type)
+ int total_size = 0;
+
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ if (this->has_source_context()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->source_context_);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 6;
+ if (this->syntax() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->syntax());
+ }
+
+ // repeated .google.protobuf.Field fields = 2;
+ total_size += 1 * this->fields_size();
+ for (int i = 0; i < this->fields_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->fields(i));
+ }
+
+ // repeated string oneofs = 3;
+ total_size += 1 * this->oneofs_size();
+ for (int i = 0; i < this->oneofs_size(); i++) {
+ total_size += ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->oneofs(i));
+ }
+
+ // repeated .google.protobuf.Option options = 4;
+ total_size += 1 * this->options_size();
+ for (int i = 0; i < this->options_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->options(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Type::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Type)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Type* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Type>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Type)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Type)
+ MergeFrom(*source);
+ }
+}
+
+void Type::MergeFrom(const Type& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Type)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ fields_.MergeFrom(from.fields_);
+ oneofs_.MergeFrom(from.oneofs_);
+ options_.MergeFrom(from.options_);
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_source_context()) {
+ mutable_source_context()->::google::protobuf::SourceContext::MergeFrom(from.source_context());
+ }
+ if (from.syntax() != 0) {
+ set_syntax(from.syntax());
+ }
+}
+
+void Type::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Type)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Type::CopyFrom(const Type& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Type)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Type::IsInitialized() const {
+
+ return true;
+}
+
+void Type::Swap(Type* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Type::InternalSwap(Type* other) {
+ name_.Swap(&other->name_);
+ fields_.UnsafeArenaSwap(&other->fields_);
+ oneofs_.UnsafeArenaSwap(&other->oneofs_);
+ options_.UnsafeArenaSwap(&other->options_);
+ std::swap(source_context_, other->source_context_);
+ std::swap(syntax_, other->syntax_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Type::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Type_descriptor_;
+ metadata.reflection = Type_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Type
+
+// optional string name = 1;
+void Type::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Type::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Type::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Type.name)
+}
+ void Type::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Type.name)
+}
+ void Type::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Type.name)
+}
+ ::std::string* Type::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Type::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Type.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Type::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Type.name)
+}
+
+// repeated .google.protobuf.Field fields = 2;
+int Type::fields_size() const {
+ return fields_.size();
+}
+void Type::clear_fields() {
+ fields_.Clear();
+}
+const ::google::protobuf::Field& Type::fields(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.fields)
+ return fields_.Get(index);
+}
+::google::protobuf::Field* Type::mutable_fields(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.fields)
+ return fields_.Mutable(index);
+}
+::google::protobuf::Field* Type::add_fields() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Type.fields)
+ return fields_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Field >*
+Type::mutable_fields() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Type.fields)
+ return &fields_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Field >&
+Type::fields() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Type.fields)
+ return fields_;
+}
+
+// repeated string oneofs = 3;
+int Type::oneofs_size() const {
+ return oneofs_.size();
+}
+void Type::clear_oneofs() {
+ oneofs_.Clear();
+}
+ const ::std::string& Type::oneofs(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.oneofs)
+ return oneofs_.Get(index);
+}
+ ::std::string* Type::mutable_oneofs(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.oneofs)
+ return oneofs_.Mutable(index);
+}
+ void Type::set_oneofs(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.Type.oneofs)
+ oneofs_.Mutable(index)->assign(value);
+}
+ void Type::set_oneofs(int index, const char* value) {
+ oneofs_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Type.oneofs)
+}
+ void Type::set_oneofs(int index, const char* value, size_t size) {
+ oneofs_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Type.oneofs)
+}
+ ::std::string* Type::add_oneofs() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.Type.oneofs)
+ return oneofs_.Add();
+}
+ void Type::add_oneofs(const ::std::string& value) {
+ oneofs_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.Type.oneofs)
+}
+ void Type::add_oneofs(const char* value) {
+ oneofs_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.Type.oneofs)
+}
+ void Type::add_oneofs(const char* value, size_t size) {
+ oneofs_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.Type.oneofs)
+}
+ const ::google::protobuf::RepeatedPtrField< ::std::string>&
+Type::oneofs() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Type.oneofs)
+ return oneofs_;
+}
+ ::google::protobuf::RepeatedPtrField< ::std::string>*
+Type::mutable_oneofs() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Type.oneofs)
+ return &oneofs_;
+}
+
+// repeated .google.protobuf.Option options = 4;
+int Type::options_size() const {
+ return options_.size();
+}
+void Type::clear_options() {
+ options_.Clear();
+}
+const ::google::protobuf::Option& Type::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.options)
+ return options_.Get(index);
+}
+::google::protobuf::Option* Type::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.options)
+ return options_.Mutable(index);
+}
+::google::protobuf::Option* Type::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Type.options)
+ return options_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Type::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Type.options)
+ return &options_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Type::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Type.options)
+ return options_;
+}
+
+// optional .google.protobuf.SourceContext source_context = 5;
+bool Type::has_source_context() const {
+ return !_is_default_instance_ && source_context_ != NULL;
+}
+void Type::clear_source_context() {
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+}
+const ::google::protobuf::SourceContext& Type::source_context() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.source_context)
+ return source_context_ != NULL ? *source_context_ : *default_instance_->source_context_;
+}
+::google::protobuf::SourceContext* Type::mutable_source_context() {
+
+ if (source_context_ == NULL) {
+ source_context_ = new ::google::protobuf::SourceContext;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.source_context)
+ return source_context_;
+}
+::google::protobuf::SourceContext* Type::release_source_context() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Type.source_context)
+
+ ::google::protobuf::SourceContext* temp = source_context_;
+ source_context_ = NULL;
+ return temp;
+}
+void Type::set_allocated_source_context(::google::protobuf::SourceContext* source_context) {
+ delete source_context_;
+ source_context_ = source_context;
+ if (source_context) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Type.source_context)
+}
+
+// optional .google.protobuf.Syntax syntax = 6;
+void Type::clear_syntax() {
+ syntax_ = 0;
+}
+ ::google::protobuf::Syntax Type::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+ void Type::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Type.syntax)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+const ::google::protobuf::EnumDescriptor* Field_Kind_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Field_Kind_descriptor_;
+}
+bool Field_Kind_IsValid(int value) {
+ switch(value) {
+ case 0:
+ case 1:
+ case 2:
+ case 3:
+ case 4:
+ case 5:
+ case 6:
+ case 7:
+ case 8:
+ case 9:
+ case 10:
+ case 11:
+ case 12:
+ case 13:
+ case 14:
+ case 15:
+ case 16:
+ case 17:
+ case 18:
+ return true;
+ default:
+ return false;
+ }
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const Field_Kind Field::TYPE_UNKNOWN;
+const Field_Kind Field::TYPE_DOUBLE;
+const Field_Kind Field::TYPE_FLOAT;
+const Field_Kind Field::TYPE_INT64;
+const Field_Kind Field::TYPE_UINT64;
+const Field_Kind Field::TYPE_INT32;
+const Field_Kind Field::TYPE_FIXED64;
+const Field_Kind Field::TYPE_FIXED32;
+const Field_Kind Field::TYPE_BOOL;
+const Field_Kind Field::TYPE_STRING;
+const Field_Kind Field::TYPE_GROUP;
+const Field_Kind Field::TYPE_MESSAGE;
+const Field_Kind Field::TYPE_BYTES;
+const Field_Kind Field::TYPE_UINT32;
+const Field_Kind Field::TYPE_ENUM;
+const Field_Kind Field::TYPE_SFIXED32;
+const Field_Kind Field::TYPE_SFIXED64;
+const Field_Kind Field::TYPE_SINT32;
+const Field_Kind Field::TYPE_SINT64;
+const Field_Kind Field::Kind_MIN;
+const Field_Kind Field::Kind_MAX;
+const int Field::Kind_ARRAYSIZE;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+const ::google::protobuf::EnumDescriptor* Field_Cardinality_descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Field_Cardinality_descriptor_;
+}
+bool Field_Cardinality_IsValid(int value) {
+ switch(value) {
+ case 0:
+ case 1:
+ case 2:
+ case 3:
+ return true;
+ default:
+ return false;
+ }
+}
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const Field_Cardinality Field::CARDINALITY_UNKNOWN;
+const Field_Cardinality Field::CARDINALITY_OPTIONAL;
+const Field_Cardinality Field::CARDINALITY_REQUIRED;
+const Field_Cardinality Field::CARDINALITY_REPEATED;
+const Field_Cardinality Field::Cardinality_MIN;
+const Field_Cardinality Field::Cardinality_MAX;
+const int Field::Cardinality_ARRAYSIZE;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Field::kKindFieldNumber;
+const int Field::kCardinalityFieldNumber;
+const int Field::kNumberFieldNumber;
+const int Field::kNameFieldNumber;
+const int Field::kTypeUrlFieldNumber;
+const int Field::kOneofIndexFieldNumber;
+const int Field::kPackedFieldNumber;
+const int Field::kOptionsFieldNumber;
+const int Field::kJsonNameFieldNumber;
+const int Field::kDefaultValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Field::Field()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Field)
+}
+
+void Field::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Field::Field(const Field& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Field)
+}
+
+void Field::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ kind_ = 0;
+ cardinality_ = 0;
+ number_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ type_url_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ oneof_index_ = 0;
+ packed_ = false;
+ json_name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ default_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+Field::~Field() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Field)
+ SharedDtor();
+}
+
+void Field::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ type_url_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ json_name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ default_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void Field::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Field::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Field_descriptor_;
+}
+
+const Field& Field::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ return *default_instance_;
+}
+
+Field* Field::default_instance_ = NULL;
+
+Field* Field::New(::google::protobuf::Arena* arena) const {
+ Field* n = new Field;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Field::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Field)
+#if defined(__clang__)
+#define ZR_HELPER_(f) \
+ _Pragma("clang diagnostic push") \
+ _Pragma("clang diagnostic ignored \"-Winvalid-offsetof\"") \
+ __builtin_offsetof(Field, f) \
+ _Pragma("clang diagnostic pop")
+#else
+#define ZR_HELPER_(f) reinterpret_cast<char*>(\
+ &reinterpret_cast<Field*>(16)->f)
+#endif
+
+#define ZR_(first, last) do {\
+ ::memset(&first, 0,\
+ ZR_HELPER_(last) - ZR_HELPER_(first) + sizeof(last));\
+} while (0)
+
+ ZR_(kind_, cardinality_);
+ ZR_(number_, oneof_index_);
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ packed_ = false;
+ json_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ default_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+
+#undef ZR_HELPER_
+#undef ZR_
+
+ options_.Clear();
+}
+
+bool Field::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Field)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional .google.protobuf.Field.Kind kind = 1;
+ case 1: {
+ if (tag == 8) {
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ set_kind(static_cast< ::google::protobuf::Field_Kind >(value));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_cardinality;
+ break;
+ }
+
+ // optional .google.protobuf.Field.Cardinality cardinality = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_cardinality:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ set_cardinality(static_cast< ::google::protobuf::Field_Cardinality >(value));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(24)) goto parse_number;
+ break;
+ }
+
+ // optional int32 number = 3;
+ case 3: {
+ if (tag == 24) {
+ parse_number:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &number_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(34)) goto parse_name;
+ break;
+ }
+
+ // optional string name = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_name:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Field.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(50)) goto parse_type_url;
+ break;
+ }
+
+ // optional string type_url = 6;
+ case 6: {
+ if (tag == 50) {
+ parse_type_url:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_type_url()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->type_url().data(), this->type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Field.type_url"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(56)) goto parse_oneof_index;
+ break;
+ }
+
+ // optional int32 oneof_index = 7;
+ case 7: {
+ if (tag == 56) {
+ parse_oneof_index:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &oneof_index_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(64)) goto parse_packed;
+ break;
+ }
+
+ // optional bool packed = 8;
+ case 8: {
+ if (tag == 64) {
+ parse_packed:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &packed_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(74)) goto parse_options;
+ break;
+ }
+
+ // repeated .google.protobuf.Option options = 9;
+ case 9: {
+ if (tag == 74) {
+ parse_options:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(74)) goto parse_loop_options;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(82)) goto parse_json_name;
+ break;
+ }
+
+ // optional string json_name = 10;
+ case 10: {
+ if (tag == 82) {
+ parse_json_name:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_json_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->json_name().data(), this->json_name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Field.json_name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(90)) goto parse_default_value;
+ break;
+ }
+
+ // optional string default_value = 11;
+ case 11: {
+ if (tag == 90) {
+ parse_default_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_default_value()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->default_value().data(), this->default_value().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Field.default_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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Field)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Field)
+ return false;
+#undef DO_
+}
+
+void Field::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Field)
+ // optional .google.protobuf.Field.Kind kind = 1;
+ if (this->kind() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 1, this->kind(), output);
+ }
+
+ // optional .google.protobuf.Field.Cardinality cardinality = 2;
+ if (this->cardinality() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 2, this->cardinality(), output);
+ }
+
+ // optional int32 number = 3;
+ if (this->number() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(3, this->number(), output);
+ }
+
+ // optional string name = 4;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 4, this->name(), output);
+ }
+
+ // optional string type_url = 6;
+ if (this->type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->type_url().data(), this->type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.type_url");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 6, this->type_url(), output);
+ }
+
+ // optional int32 oneof_index = 7;
+ if (this->oneof_index() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(7, this->oneof_index(), output);
+ }
+
+ // optional bool packed = 8;
+ if (this->packed() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(8, this->packed(), output);
+ }
+
+ // repeated .google.protobuf.Option options = 9;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 9, this->options(i), output);
+ }
+
+ // optional string json_name = 10;
+ if (this->json_name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->json_name().data(), this->json_name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.json_name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 10, this->json_name(), output);
+ }
+
+ // optional string default_value = 11;
+ if (this->default_value().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->default_value().data(), this->default_value().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.default_value");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 11, this->default_value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Field)
+}
+
+::google::protobuf::uint8* Field::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Field)
+ // optional .google.protobuf.Field.Kind kind = 1;
+ if (this->kind() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 1, this->kind(), target);
+ }
+
+ // optional .google.protobuf.Field.Cardinality cardinality = 2;
+ if (this->cardinality() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 2, this->cardinality(), target);
+ }
+
+ // optional int32 number = 3;
+ if (this->number() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(3, this->number(), target);
+ }
+
+ // optional string name = 4;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 4, this->name(), target);
+ }
+
+ // optional string type_url = 6;
+ if (this->type_url().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->type_url().data(), this->type_url().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.type_url");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 6, this->type_url(), target);
+ }
+
+ // optional int32 oneof_index = 7;
+ if (this->oneof_index() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(7, this->oneof_index(), target);
+ }
+
+ // optional bool packed = 8;
+ if (this->packed() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(8, this->packed(), target);
+ }
+
+ // repeated .google.protobuf.Option options = 9;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 9, this->options(i), false, target);
+ }
+
+ // optional string json_name = 10;
+ if (this->json_name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->json_name().data(), this->json_name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.json_name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 10, this->json_name(), target);
+ }
+
+ // optional string default_value = 11;
+ if (this->default_value().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->default_value().data(), this->default_value().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Field.default_value");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 11, this->default_value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Field)
+ return target;
+}
+
+int Field::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Field)
+ int total_size = 0;
+
+ // optional .google.protobuf.Field.Kind kind = 1;
+ if (this->kind() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->kind());
+ }
+
+ // optional .google.protobuf.Field.Cardinality cardinality = 2;
+ if (this->cardinality() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->cardinality());
+ }
+
+ // optional int32 number = 3;
+ if (this->number() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->number());
+ }
+
+ // optional string name = 4;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional string type_url = 6;
+ if (this->type_url().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->type_url());
+ }
+
+ // optional int32 oneof_index = 7;
+ if (this->oneof_index() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->oneof_index());
+ }
+
+ // optional bool packed = 8;
+ if (this->packed() != 0) {
+ total_size += 1 + 1;
+ }
+
+ // optional string json_name = 10;
+ if (this->json_name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->json_name());
+ }
+
+ // optional string default_value = 11;
+ if (this->default_value().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->default_value());
+ }
+
+ // repeated .google.protobuf.Option options = 9;
+ total_size += 1 * this->options_size();
+ for (int i = 0; i < this->options_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->options(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Field::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Field)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Field* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Field>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Field)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Field)
+ MergeFrom(*source);
+ }
+}
+
+void Field::MergeFrom(const Field& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Field)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ options_.MergeFrom(from.options_);
+ if (from.kind() != 0) {
+ set_kind(from.kind());
+ }
+ if (from.cardinality() != 0) {
+ set_cardinality(from.cardinality());
+ }
+ if (from.number() != 0) {
+ set_number(from.number());
+ }
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.type_url().size() > 0) {
+
+ type_url_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.type_url_);
+ }
+ if (from.oneof_index() != 0) {
+ set_oneof_index(from.oneof_index());
+ }
+ if (from.packed() != 0) {
+ set_packed(from.packed());
+ }
+ if (from.json_name().size() > 0) {
+
+ json_name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.json_name_);
+ }
+ if (from.default_value().size() > 0) {
+
+ default_value_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.default_value_);
+ }
+}
+
+void Field::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Field)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Field::CopyFrom(const Field& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Field)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Field::IsInitialized() const {
+
+ return true;
+}
+
+void Field::Swap(Field* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Field::InternalSwap(Field* other) {
+ std::swap(kind_, other->kind_);
+ std::swap(cardinality_, other->cardinality_);
+ std::swap(number_, other->number_);
+ name_.Swap(&other->name_);
+ type_url_.Swap(&other->type_url_);
+ std::swap(oneof_index_, other->oneof_index_);
+ std::swap(packed_, other->packed_);
+ options_.UnsafeArenaSwap(&other->options_);
+ json_name_.Swap(&other->json_name_);
+ default_value_.Swap(&other->default_value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Field::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Field_descriptor_;
+ metadata.reflection = Field_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Field
+
+// optional .google.protobuf.Field.Kind kind = 1;
+void Field::clear_kind() {
+ kind_ = 0;
+}
+ ::google::protobuf::Field_Kind Field::kind() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.kind)
+ return static_cast< ::google::protobuf::Field_Kind >(kind_);
+}
+ void Field::set_kind(::google::protobuf::Field_Kind value) {
+
+ kind_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.kind)
+}
+
+// optional .google.protobuf.Field.Cardinality cardinality = 2;
+void Field::clear_cardinality() {
+ cardinality_ = 0;
+}
+ ::google::protobuf::Field_Cardinality Field::cardinality() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.cardinality)
+ return static_cast< ::google::protobuf::Field_Cardinality >(cardinality_);
+}
+ void Field::set_cardinality(::google::protobuf::Field_Cardinality value) {
+
+ cardinality_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.cardinality)
+}
+
+// optional int32 number = 3;
+void Field::clear_number() {
+ number_ = 0;
+}
+ ::google::protobuf::int32 Field::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.number)
+ return number_;
+}
+ void Field::set_number(::google::protobuf::int32 value) {
+
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.number)
+}
+
+// optional string name = 4;
+void Field::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Field::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.name)
+}
+ void Field::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.name)
+}
+ void Field::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.name)
+}
+ ::std::string* Field::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Field::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.name)
+}
+
+// optional string type_url = 6;
+void Field::clear_type_url() {
+ type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Field::type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.type_url)
+ return type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_type_url(const ::std::string& value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.type_url)
+}
+ void Field::set_type_url(const char* value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.type_url)
+}
+ void Field::set_type_url(const char* value, size_t size) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.type_url)
+}
+ ::std::string* Field::mutable_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.type_url)
+ return type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Field::release_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.type_url)
+
+ return type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_allocated_type_url(::std::string* type_url) {
+ if (type_url != NULL) {
+
+ } else {
+
+ }
+ type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.type_url)
+}
+
+// optional int32 oneof_index = 7;
+void Field::clear_oneof_index() {
+ oneof_index_ = 0;
+}
+ ::google::protobuf::int32 Field::oneof_index() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.oneof_index)
+ return oneof_index_;
+}
+ void Field::set_oneof_index(::google::protobuf::int32 value) {
+
+ oneof_index_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.oneof_index)
+}
+
+// optional bool packed = 8;
+void Field::clear_packed() {
+ packed_ = false;
+}
+ bool Field::packed() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.packed)
+ return packed_;
+}
+ void Field::set_packed(bool value) {
+
+ packed_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.packed)
+}
+
+// repeated .google.protobuf.Option options = 9;
+int Field::options_size() const {
+ return options_.size();
+}
+void Field::clear_options() {
+ options_.Clear();
+}
+const ::google::protobuf::Option& Field::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.options)
+ return options_.Get(index);
+}
+::google::protobuf::Option* Field::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.options)
+ return options_.Mutable(index);
+}
+::google::protobuf::Option* Field::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Field.options)
+ return options_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Field::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Field.options)
+ return &options_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Field::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Field.options)
+ return options_;
+}
+
+// optional string json_name = 10;
+void Field::clear_json_name() {
+ json_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Field::json_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.json_name)
+ return json_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_json_name(const ::std::string& value) {
+
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.json_name)
+}
+ void Field::set_json_name(const char* value) {
+
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.json_name)
+}
+ void Field::set_json_name(const char* value, size_t size) {
+
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.json_name)
+}
+ ::std::string* Field::mutable_json_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.json_name)
+ return json_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Field::release_json_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.json_name)
+
+ return json_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_allocated_json_name(::std::string* json_name) {
+ if (json_name != NULL) {
+
+ } else {
+
+ }
+ json_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), json_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.json_name)
+}
+
+// optional string default_value = 11;
+void Field::clear_default_value() {
+ default_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Field::default_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.default_value)
+ return default_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_default_value(const ::std::string& value) {
+
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.default_value)
+}
+ void Field::set_default_value(const char* value) {
+
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.default_value)
+}
+ void Field::set_default_value(const char* value, size_t size) {
+
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.default_value)
+}
+ ::std::string* Field::mutable_default_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.default_value)
+ return default_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Field::release_default_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.default_value)
+
+ return default_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Field::set_allocated_default_value(::std::string* default_value) {
+ if (default_value != NULL) {
+
+ } else {
+
+ }
+ default_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), default_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.default_value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Enum::kNameFieldNumber;
+const int Enum::kEnumvalueFieldNumber;
+const int Enum::kOptionsFieldNumber;
+const int Enum::kSourceContextFieldNumber;
+const int Enum::kSyntaxFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Enum::Enum()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Enum)
+}
+
+void Enum::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+ source_context_ = const_cast< ::google::protobuf::SourceContext*>(&::google::protobuf::SourceContext::default_instance());
+}
+
+Enum::Enum(const Enum& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Enum)
+}
+
+void Enum::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ source_context_ = NULL;
+ syntax_ = 0;
+}
+
+Enum::~Enum() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Enum)
+ SharedDtor();
+}
+
+void Enum::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete source_context_;
+ }
+}
+
+void Enum::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Enum::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Enum_descriptor_;
+}
+
+const Enum& Enum::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ return *default_instance_;
+}
+
+Enum* Enum::default_instance_ = NULL;
+
+Enum* Enum::New(::google::protobuf::Arena* arena) const {
+ Enum* n = new Enum;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Enum::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Enum)
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+ syntax_ = 0;
+ enumvalue_.Clear();
+ options_.Clear();
+}
+
+bool Enum::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Enum)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Enum.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_enumvalue;
+ break;
+ }
+
+ // repeated .google.protobuf.EnumValue enumvalue = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_enumvalue:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_enumvalue:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_enumvalue()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_loop_enumvalue;
+ if (input->ExpectTag(26)) goto parse_loop_options;
+ input->UnsafeDecrementRecursionDepth();
+ break;
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ case 3: {
+ if (tag == 26) {
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_loop_options;
+ input->UnsafeDecrementRecursionDepth();
+ if (input->ExpectTag(34)) goto parse_source_context;
+ break;
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 4;
+ case 4: {
+ if (tag == 34) {
+ parse_source_context:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_source_context()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(40)) goto parse_syntax;
+ break;
+ }
+
+ // optional .google.protobuf.Syntax syntax = 5;
+ case 5: {
+ if (tag == 40) {
+ parse_syntax:
+ int value;
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
+ input, &value)));
+ set_syntax(static_cast< ::google::protobuf::Syntax >(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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Enum)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Enum)
+ return false;
+#undef DO_
+}
+
+void Enum::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Enum)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Enum.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // repeated .google.protobuf.EnumValue enumvalue = 2;
+ for (unsigned int i = 0, n = this->enumvalue_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, this->enumvalue(i), output);
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 3, this->options(i), output);
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 4;
+ if (this->has_source_context()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 4, *this->source_context_, output);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 5;
+ if (this->syntax() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteEnum(
+ 5, this->syntax(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Enum)
+}
+
+::google::protobuf::uint8* Enum::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Enum)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Enum.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // repeated .google.protobuf.EnumValue enumvalue = 2;
+ for (unsigned int i = 0, n = this->enumvalue_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, this->enumvalue(i), false, target);
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 3, this->options(i), false, target);
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 4;
+ if (this->has_source_context()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 4, *this->source_context_, false, target);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 5;
+ if (this->syntax() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
+ 5, this->syntax(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Enum)
+ return target;
+}
+
+int Enum::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Enum)
+ int total_size = 0;
+
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional .google.protobuf.SourceContext source_context = 4;
+ if (this->has_source_context()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->source_context_);
+ }
+
+ // optional .google.protobuf.Syntax syntax = 5;
+ if (this->syntax() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::EnumSize(this->syntax());
+ }
+
+ // repeated .google.protobuf.EnumValue enumvalue = 2;
+ total_size += 1 * this->enumvalue_size();
+ for (int i = 0; i < this->enumvalue_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->enumvalue(i));
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ total_size += 1 * this->options_size();
+ for (int i = 0; i < this->options_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->options(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Enum::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Enum)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Enum* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Enum>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Enum)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Enum)
+ MergeFrom(*source);
+ }
+}
+
+void Enum::MergeFrom(const Enum& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Enum)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ enumvalue_.MergeFrom(from.enumvalue_);
+ options_.MergeFrom(from.options_);
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_source_context()) {
+ mutable_source_context()->::google::protobuf::SourceContext::MergeFrom(from.source_context());
+ }
+ if (from.syntax() != 0) {
+ set_syntax(from.syntax());
+ }
+}
+
+void Enum::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Enum)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Enum::CopyFrom(const Enum& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Enum)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Enum::IsInitialized() const {
+
+ return true;
+}
+
+void Enum::Swap(Enum* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Enum::InternalSwap(Enum* other) {
+ name_.Swap(&other->name_);
+ enumvalue_.UnsafeArenaSwap(&other->enumvalue_);
+ options_.UnsafeArenaSwap(&other->options_);
+ std::swap(source_context_, other->source_context_);
+ std::swap(syntax_, other->syntax_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Enum::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Enum_descriptor_;
+ metadata.reflection = Enum_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Enum
+
+// optional string name = 1;
+void Enum::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Enum::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Enum::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Enum.name)
+}
+ void Enum::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Enum.name)
+}
+ void Enum::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Enum.name)
+}
+ ::std::string* Enum::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Enum::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Enum.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Enum::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Enum.name)
+}
+
+// repeated .google.protobuf.EnumValue enumvalue = 2;
+int Enum::enumvalue_size() const {
+ return enumvalue_.size();
+}
+void Enum::clear_enumvalue() {
+ enumvalue_.Clear();
+}
+const ::google::protobuf::EnumValue& Enum::enumvalue(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.enumvalue)
+ return enumvalue_.Get(index);
+}
+::google::protobuf::EnumValue* Enum::mutable_enumvalue(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.enumvalue)
+ return enumvalue_.Mutable(index);
+}
+::google::protobuf::EnumValue* Enum::add_enumvalue() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Enum.enumvalue)
+ return enumvalue_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValue >*
+Enum::mutable_enumvalue() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Enum.enumvalue)
+ return &enumvalue_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValue >&
+Enum::enumvalue() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Enum.enumvalue)
+ return enumvalue_;
+}
+
+// repeated .google.protobuf.Option options = 3;
+int Enum::options_size() const {
+ return options_.size();
+}
+void Enum::clear_options() {
+ options_.Clear();
+}
+const ::google::protobuf::Option& Enum::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.options)
+ return options_.Get(index);
+}
+::google::protobuf::Option* Enum::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.options)
+ return options_.Mutable(index);
+}
+::google::protobuf::Option* Enum::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Enum.options)
+ return options_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Enum::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Enum.options)
+ return &options_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Enum::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Enum.options)
+ return options_;
+}
+
+// optional .google.protobuf.SourceContext source_context = 4;
+bool Enum::has_source_context() const {
+ return !_is_default_instance_ && source_context_ != NULL;
+}
+void Enum::clear_source_context() {
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+}
+const ::google::protobuf::SourceContext& Enum::source_context() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.source_context)
+ return source_context_ != NULL ? *source_context_ : *default_instance_->source_context_;
+}
+::google::protobuf::SourceContext* Enum::mutable_source_context() {
+
+ if (source_context_ == NULL) {
+ source_context_ = new ::google::protobuf::SourceContext;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.source_context)
+ return source_context_;
+}
+::google::protobuf::SourceContext* Enum::release_source_context() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Enum.source_context)
+
+ ::google::protobuf::SourceContext* temp = source_context_;
+ source_context_ = NULL;
+ return temp;
+}
+void Enum::set_allocated_source_context(::google::protobuf::SourceContext* source_context) {
+ delete source_context_;
+ source_context_ = source_context;
+ if (source_context) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Enum.source_context)
+}
+
+// optional .google.protobuf.Syntax syntax = 5;
+void Enum::clear_syntax() {
+ syntax_ = 0;
+}
+ ::google::protobuf::Syntax Enum::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+ void Enum::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Enum.syntax)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int EnumValue::kNameFieldNumber;
+const int EnumValue::kNumberFieldNumber;
+const int EnumValue::kOptionsFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+EnumValue::EnumValue()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.EnumValue)
+}
+
+void EnumValue::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+EnumValue::EnumValue(const EnumValue& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.EnumValue)
+}
+
+void EnumValue::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ number_ = 0;
+}
+
+EnumValue::~EnumValue() {
+ // @@protoc_insertion_point(destructor:google.protobuf.EnumValue)
+ SharedDtor();
+}
+
+void EnumValue::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ }
+}
+
+void EnumValue::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* EnumValue::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return EnumValue_descriptor_;
+}
+
+const EnumValue& EnumValue::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ return *default_instance_;
+}
+
+EnumValue* EnumValue::default_instance_ = NULL;
+
+EnumValue* EnumValue::New(::google::protobuf::Arena* arena) const {
+ EnumValue* n = new EnumValue;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void EnumValue::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.EnumValue)
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ number_ = 0;
+ options_.Clear();
+}
+
+bool EnumValue::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.EnumValue)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.EnumValue.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(16)) goto parse_number;
+ break;
+ }
+
+ // optional int32 number = 2;
+ case 2: {
+ if (tag == 16) {
+ parse_number:
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &number_)));
+
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_options;
+ break;
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ case 3: {
+ if (tag == 26) {
+ parse_options:
+ DO_(input->IncrementRecursionDepth());
+ parse_loop_options:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ input, add_options()));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(26)) goto parse_loop_options;
+ 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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.EnumValue)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.EnumValue)
+ return false;
+#undef DO_
+}
+
+void EnumValue::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.EnumValue)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.EnumValue.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional int32 number = 2;
+ if (this->number() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(2, this->number(), output);
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 3, this->options(i), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.EnumValue)
+}
+
+::google::protobuf::uint8* EnumValue::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.EnumValue)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.EnumValue.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional int32 number = 2;
+ if (this->number() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(2, this->number(), target);
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ for (unsigned int i = 0, n = this->options_size(); i < n; i++) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 3, this->options(i), false, target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.EnumValue)
+ return target;
+}
+
+int EnumValue::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.EnumValue)
+ int total_size = 0;
+
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional int32 number = 2;
+ if (this->number() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->number());
+ }
+
+ // repeated .google.protobuf.Option options = 3;
+ total_size += 1 * this->options_size();
+ for (int i = 0; i < this->options_size(); i++) {
+ total_size +=
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ this->options(i));
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void EnumValue::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.EnumValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const EnumValue* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const EnumValue>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.EnumValue)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.EnumValue)
+ MergeFrom(*source);
+ }
+}
+
+void EnumValue::MergeFrom(const EnumValue& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.EnumValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ options_.MergeFrom(from.options_);
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.number() != 0) {
+ set_number(from.number());
+ }
+}
+
+void EnumValue::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.EnumValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void EnumValue::CopyFrom(const EnumValue& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.EnumValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool EnumValue::IsInitialized() const {
+
+ return true;
+}
+
+void EnumValue::Swap(EnumValue* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void EnumValue::InternalSwap(EnumValue* other) {
+ name_.Swap(&other->name_);
+ std::swap(number_, other->number_);
+ options_.UnsafeArenaSwap(&other->options_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata EnumValue::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = EnumValue_descriptor_;
+ metadata.reflection = EnumValue_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// EnumValue
+
+// optional string name = 1;
+void EnumValue::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& EnumValue::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValue.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void EnumValue::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValue.name)
+}
+ void EnumValue::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.EnumValue.name)
+}
+ void EnumValue::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.EnumValue.name)
+}
+ ::std::string* EnumValue::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValue.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* EnumValue::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumValue.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void EnumValue::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumValue.name)
+}
+
+// optional int32 number = 2;
+void EnumValue::clear_number() {
+ number_ = 0;
+}
+ ::google::protobuf::int32 EnumValue::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValue.number)
+ return number_;
+}
+ void EnumValue::set_number(::google::protobuf::int32 value) {
+
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValue.number)
+}
+
+// repeated .google.protobuf.Option options = 3;
+int EnumValue::options_size() const {
+ return options_.size();
+}
+void EnumValue::clear_options() {
+ options_.Clear();
+}
+const ::google::protobuf::Option& EnumValue::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValue.options)
+ return options_.Get(index);
+}
+::google::protobuf::Option* EnumValue::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValue.options)
+ return options_.Mutable(index);
+}
+::google::protobuf::Option* EnumValue::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumValue.options)
+ return options_.Add();
+}
+::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+EnumValue::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumValue.options)
+ return &options_;
+}
+const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+EnumValue::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumValue.options)
+ return options_;
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Option::kNameFieldNumber;
+const int Option::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Option::Option()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Option)
+}
+
+void Option::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+ value_ = const_cast< ::google::protobuf::Any*>(&::google::protobuf::Any::default_instance());
+}
+
+Option::Option(const Option& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Option)
+}
+
+void Option::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ name_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ value_ = NULL;
+}
+
+Option::~Option() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Option)
+ SharedDtor();
+}
+
+void Option::SharedDtor() {
+ name_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (this != default_instance_) {
+ delete value_;
+ }
+}
+
+void Option::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Option::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Option_descriptor_;
+}
+
+const Option& Option::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ return *default_instance_;
+}
+
+Option* Option::default_instance_ = NULL;
+
+Option* Option::New(::google::protobuf::Arena* arena) const {
+ Option* n = new Option;
+ if (arena != NULL) {
+ arena->Own(n);
+ }
+ return n;
+}
+
+void Option::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Option)
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+ if (GetArenaNoVirtual() == NULL && value_ != NULL) delete value_;
+ value_ = NULL;
+}
+
+bool Option::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Option)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string name = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_name()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.Option.name"));
+ } else {
+ goto handle_unusual;
+ }
+ if (input->ExpectTag(18)) goto parse_value;
+ break;
+ }
+
+ // optional .google.protobuf.Any value = 2;
+ case 2: {
+ if (tag == 18) {
+ parse_value:
+ DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+ input, mutable_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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Option)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Option)
+ return false;
+#undef DO_
+}
+
+void Option::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Option)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Option.name");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->name(), output);
+ }
+
+ // optional .google.protobuf.Any value = 2;
+ if (this->has_value()) {
+ ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+ 2, *this->value_, output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Option)
+}
+
+::google::protobuf::uint8* Option::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Option)
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->name().data(), this->name().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.Option.name");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->name(), target);
+ }
+
+ // optional .google.protobuf.Any value = 2;
+ if (this->has_value()) {
+ target = ::google::protobuf::internal::WireFormatLite::
+ InternalWriteMessageNoVirtualToArray(
+ 2, *this->value_, false, target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Option)
+ return target;
+}
+
+int Option::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Option)
+ int total_size = 0;
+
+ // optional string name = 1;
+ if (this->name().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->name());
+ }
+
+ // optional .google.protobuf.Any value = 2;
+ if (this->has_value()) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+ *this->value_);
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Option::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Option)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Option* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Option>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Option)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Option)
+ MergeFrom(*source);
+ }
+}
+
+void Option::MergeFrom(const Option& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Option)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.name().size() > 0) {
+
+ name_.AssignWithDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), from.name_);
+ }
+ if (from.has_value()) {
+ mutable_value()->::google::protobuf::Any::MergeFrom(from.value());
+ }
+}
+
+void Option::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Option)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Option::CopyFrom(const Option& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Option)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Option::IsInitialized() const {
+
+ return true;
+}
+
+void Option::Swap(Option* other) {
+ if (other == this) return;
+ InternalSwap(other);
+}
+void Option::InternalSwap(Option* other) {
+ name_.Swap(&other->name_);
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Option::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Option_descriptor_;
+ metadata.reflection = Option_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Option
+
+// optional string name = 1;
+void Option::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ const ::std::string& Option::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Option.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Option::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Option.name)
+}
+ void Option::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Option.name)
+}
+ void Option::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Option.name)
+}
+ ::std::string* Option::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Option.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ ::std::string* Option::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Option.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void Option::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Option.name)
+}
+
+// optional .google.protobuf.Any value = 2;
+bool Option::has_value() const {
+ return !_is_default_instance_ && value_ != NULL;
+}
+void Option::clear_value() {
+ if (GetArenaNoVirtual() == NULL && value_ != NULL) delete value_;
+ value_ = NULL;
+}
+const ::google::protobuf::Any& Option::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Option.value)
+ return value_ != NULL ? *value_ : *default_instance_->value_;
+}
+::google::protobuf::Any* Option::mutable_value() {
+
+ if (value_ == NULL) {
+ value_ = new ::google::protobuf::Any;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Option.value)
+ return value_;
+}
+::google::protobuf::Any* Option::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Option.value)
+
+ ::google::protobuf::Any* temp = value_;
+ value_ = NULL;
+ return temp;
+}
+void Option::set_allocated_value(::google::protobuf::Any* value) {
+ delete value_;
+ value_ = value;
+ if (value) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Option.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/type.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/type.pb.h
new file mode 100644
index 0000000000..ce29c2817f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/type.pb.h
@@ -0,0 +1,1751 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/type.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2ftype_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2ftype_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/generated_enum_reflection.h>
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/any.pb.h>
+#include <google/protobuf/source_context.pb.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto();
+
+class Enum;
+class EnumValue;
+class Field;
+class Option;
+class Type;
+
+enum Field_Kind {
+ Field_Kind_TYPE_UNKNOWN = 0,
+ Field_Kind_TYPE_DOUBLE = 1,
+ Field_Kind_TYPE_FLOAT = 2,
+ Field_Kind_TYPE_INT64 = 3,
+ Field_Kind_TYPE_UINT64 = 4,
+ Field_Kind_TYPE_INT32 = 5,
+ Field_Kind_TYPE_FIXED64 = 6,
+ Field_Kind_TYPE_FIXED32 = 7,
+ Field_Kind_TYPE_BOOL = 8,
+ Field_Kind_TYPE_STRING = 9,
+ Field_Kind_TYPE_GROUP = 10,
+ Field_Kind_TYPE_MESSAGE = 11,
+ Field_Kind_TYPE_BYTES = 12,
+ Field_Kind_TYPE_UINT32 = 13,
+ Field_Kind_TYPE_ENUM = 14,
+ Field_Kind_TYPE_SFIXED32 = 15,
+ Field_Kind_TYPE_SFIXED64 = 16,
+ Field_Kind_TYPE_SINT32 = 17,
+ Field_Kind_TYPE_SINT64 = 18,
+ Field_Kind_Field_Kind_INT_MIN_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32min,
+ Field_Kind_Field_Kind_INT_MAX_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32max
+};
+LIBPROTOBUF_EXPORT bool Field_Kind_IsValid(int value);
+const Field_Kind Field_Kind_Kind_MIN = Field_Kind_TYPE_UNKNOWN;
+const Field_Kind Field_Kind_Kind_MAX = Field_Kind_TYPE_SINT64;
+const int Field_Kind_Kind_ARRAYSIZE = Field_Kind_Kind_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* Field_Kind_descriptor();
+inline const ::std::string& Field_Kind_Name(Field_Kind value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ Field_Kind_descriptor(), value);
+}
+inline bool Field_Kind_Parse(
+ const ::std::string& name, Field_Kind* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<Field_Kind>(
+ Field_Kind_descriptor(), name, value);
+}
+enum Field_Cardinality {
+ Field_Cardinality_CARDINALITY_UNKNOWN = 0,
+ Field_Cardinality_CARDINALITY_OPTIONAL = 1,
+ Field_Cardinality_CARDINALITY_REQUIRED = 2,
+ Field_Cardinality_CARDINALITY_REPEATED = 3,
+ Field_Cardinality_Field_Cardinality_INT_MIN_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32min,
+ Field_Cardinality_Field_Cardinality_INT_MAX_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32max
+};
+LIBPROTOBUF_EXPORT bool Field_Cardinality_IsValid(int value);
+const Field_Cardinality Field_Cardinality_Cardinality_MIN = Field_Cardinality_CARDINALITY_UNKNOWN;
+const Field_Cardinality Field_Cardinality_Cardinality_MAX = Field_Cardinality_CARDINALITY_REPEATED;
+const int Field_Cardinality_Cardinality_ARRAYSIZE = Field_Cardinality_Cardinality_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* Field_Cardinality_descriptor();
+inline const ::std::string& Field_Cardinality_Name(Field_Cardinality value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ Field_Cardinality_descriptor(), value);
+}
+inline bool Field_Cardinality_Parse(
+ const ::std::string& name, Field_Cardinality* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<Field_Cardinality>(
+ Field_Cardinality_descriptor(), name, value);
+}
+enum Syntax {
+ SYNTAX_PROTO2 = 0,
+ SYNTAX_PROTO3 = 1,
+ Syntax_INT_MIN_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32min,
+ Syntax_INT_MAX_SENTINEL_DO_NOT_USE_ = ::google::protobuf::kint32max
+};
+LIBPROTOBUF_EXPORT bool Syntax_IsValid(int value);
+const Syntax Syntax_MIN = SYNTAX_PROTO2;
+const Syntax Syntax_MAX = SYNTAX_PROTO3;
+const int Syntax_ARRAYSIZE = Syntax_MAX + 1;
+
+LIBPROTOBUF_EXPORT const ::google::protobuf::EnumDescriptor* Syntax_descriptor();
+inline const ::std::string& Syntax_Name(Syntax value) {
+ return ::google::protobuf::internal::NameOfEnum(
+ Syntax_descriptor(), value);
+}
+inline bool Syntax_Parse(
+ const ::std::string& name, Syntax* value) {
+ return ::google::protobuf::internal::ParseNamedEnum<Syntax>(
+ Syntax_descriptor(), name, value);
+}
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT Type : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Type) */ {
+ public:
+ Type();
+ virtual ~Type();
+
+ Type(const Type& from);
+
+ inline Type& operator=(const Type& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Type& default_instance();
+
+ void Swap(Type* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Type* New() const { return New(NULL); }
+
+ Type* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Type& from);
+ void MergeFrom(const Type& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Type* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // repeated .google.protobuf.Field fields = 2;
+ int fields_size() const;
+ void clear_fields();
+ static const int kFieldsFieldNumber = 2;
+ const ::google::protobuf::Field& fields(int index) const;
+ ::google::protobuf::Field* mutable_fields(int index);
+ ::google::protobuf::Field* add_fields();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Field >*
+ mutable_fields();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Field >&
+ fields() const;
+
+ // repeated string oneofs = 3;
+ int oneofs_size() const;
+ void clear_oneofs();
+ static const int kOneofsFieldNumber = 3;
+ const ::std::string& oneofs(int index) const;
+ ::std::string* mutable_oneofs(int index);
+ void set_oneofs(int index, const ::std::string& value);
+ void set_oneofs(int index, const char* value);
+ void set_oneofs(int index, const char* value, size_t size);
+ ::std::string* add_oneofs();
+ void add_oneofs(const ::std::string& value);
+ void add_oneofs(const char* value);
+ void add_oneofs(const char* value, size_t size);
+ const ::google::protobuf::RepeatedPtrField< ::std::string>& oneofs() const;
+ ::google::protobuf::RepeatedPtrField< ::std::string>* mutable_oneofs();
+
+ // repeated .google.protobuf.Option options = 4;
+ int options_size() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 4;
+ const ::google::protobuf::Option& options(int index) const;
+ ::google::protobuf::Option* mutable_options(int index);
+ ::google::protobuf::Option* add_options();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+ mutable_options();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+ options() const;
+
+ // optional .google.protobuf.SourceContext source_context = 5;
+ bool has_source_context() const;
+ void clear_source_context();
+ static const int kSourceContextFieldNumber = 5;
+ const ::google::protobuf::SourceContext& source_context() const;
+ ::google::protobuf::SourceContext* mutable_source_context();
+ ::google::protobuf::SourceContext* release_source_context();
+ void set_allocated_source_context(::google::protobuf::SourceContext* source_context);
+
+ // optional .google.protobuf.Syntax syntax = 6;
+ void clear_syntax();
+ static const int kSyntaxFieldNumber = 6;
+ ::google::protobuf::Syntax syntax() const;
+ void set_syntax(::google::protobuf::Syntax value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Type)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Field > fields_;
+ ::google::protobuf::RepeatedPtrField< ::std::string> oneofs_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option > options_;
+ ::google::protobuf::SourceContext* source_context_;
+ int syntax_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto();
+
+ void InitAsDefaultInstance();
+ static Type* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Field : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Field) */ {
+ public:
+ Field();
+ virtual ~Field();
+
+ Field(const Field& from);
+
+ inline Field& operator=(const Field& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Field& default_instance();
+
+ void Swap(Field* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Field* New() const { return New(NULL); }
+
+ Field* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Field& from);
+ void MergeFrom(const Field& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Field* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ typedef Field_Kind Kind;
+ static const Kind TYPE_UNKNOWN =
+ Field_Kind_TYPE_UNKNOWN;
+ static const Kind TYPE_DOUBLE =
+ Field_Kind_TYPE_DOUBLE;
+ static const Kind TYPE_FLOAT =
+ Field_Kind_TYPE_FLOAT;
+ static const Kind TYPE_INT64 =
+ Field_Kind_TYPE_INT64;
+ static const Kind TYPE_UINT64 =
+ Field_Kind_TYPE_UINT64;
+ static const Kind TYPE_INT32 =
+ Field_Kind_TYPE_INT32;
+ static const Kind TYPE_FIXED64 =
+ Field_Kind_TYPE_FIXED64;
+ static const Kind TYPE_FIXED32 =
+ Field_Kind_TYPE_FIXED32;
+ static const Kind TYPE_BOOL =
+ Field_Kind_TYPE_BOOL;
+ static const Kind TYPE_STRING =
+ Field_Kind_TYPE_STRING;
+ static const Kind TYPE_GROUP =
+ Field_Kind_TYPE_GROUP;
+ static const Kind TYPE_MESSAGE =
+ Field_Kind_TYPE_MESSAGE;
+ static const Kind TYPE_BYTES =
+ Field_Kind_TYPE_BYTES;
+ static const Kind TYPE_UINT32 =
+ Field_Kind_TYPE_UINT32;
+ static const Kind TYPE_ENUM =
+ Field_Kind_TYPE_ENUM;
+ static const Kind TYPE_SFIXED32 =
+ Field_Kind_TYPE_SFIXED32;
+ static const Kind TYPE_SFIXED64 =
+ Field_Kind_TYPE_SFIXED64;
+ static const Kind TYPE_SINT32 =
+ Field_Kind_TYPE_SINT32;
+ static const Kind TYPE_SINT64 =
+ Field_Kind_TYPE_SINT64;
+ static inline bool Kind_IsValid(int value) {
+ return Field_Kind_IsValid(value);
+ }
+ static const Kind Kind_MIN =
+ Field_Kind_Kind_MIN;
+ static const Kind Kind_MAX =
+ Field_Kind_Kind_MAX;
+ static const int Kind_ARRAYSIZE =
+ Field_Kind_Kind_ARRAYSIZE;
+ static inline const ::google::protobuf::EnumDescriptor*
+ Kind_descriptor() {
+ return Field_Kind_descriptor();
+ }
+ static inline const ::std::string& Kind_Name(Kind value) {
+ return Field_Kind_Name(value);
+ }
+ static inline bool Kind_Parse(const ::std::string& name,
+ Kind* value) {
+ return Field_Kind_Parse(name, value);
+ }
+
+ typedef Field_Cardinality Cardinality;
+ static const Cardinality CARDINALITY_UNKNOWN =
+ Field_Cardinality_CARDINALITY_UNKNOWN;
+ static const Cardinality CARDINALITY_OPTIONAL =
+ Field_Cardinality_CARDINALITY_OPTIONAL;
+ static const Cardinality CARDINALITY_REQUIRED =
+ Field_Cardinality_CARDINALITY_REQUIRED;
+ static const Cardinality CARDINALITY_REPEATED =
+ Field_Cardinality_CARDINALITY_REPEATED;
+ static inline bool Cardinality_IsValid(int value) {
+ return Field_Cardinality_IsValid(value);
+ }
+ static const Cardinality Cardinality_MIN =
+ Field_Cardinality_Cardinality_MIN;
+ static const Cardinality Cardinality_MAX =
+ Field_Cardinality_Cardinality_MAX;
+ static const int Cardinality_ARRAYSIZE =
+ Field_Cardinality_Cardinality_ARRAYSIZE;
+ static inline const ::google::protobuf::EnumDescriptor*
+ Cardinality_descriptor() {
+ return Field_Cardinality_descriptor();
+ }
+ static inline const ::std::string& Cardinality_Name(Cardinality value) {
+ return Field_Cardinality_Name(value);
+ }
+ static inline bool Cardinality_Parse(const ::std::string& name,
+ Cardinality* value) {
+ return Field_Cardinality_Parse(name, value);
+ }
+
+ // accessors -------------------------------------------------------
+
+ // optional .google.protobuf.Field.Kind kind = 1;
+ void clear_kind();
+ static const int kKindFieldNumber = 1;
+ ::google::protobuf::Field_Kind kind() const;
+ void set_kind(::google::protobuf::Field_Kind value);
+
+ // optional .google.protobuf.Field.Cardinality cardinality = 2;
+ void clear_cardinality();
+ static const int kCardinalityFieldNumber = 2;
+ ::google::protobuf::Field_Cardinality cardinality() const;
+ void set_cardinality(::google::protobuf::Field_Cardinality value);
+
+ // optional int32 number = 3;
+ void clear_number();
+ static const int kNumberFieldNumber = 3;
+ ::google::protobuf::int32 number() const;
+ void set_number(::google::protobuf::int32 value);
+
+ // optional string name = 4;
+ void clear_name();
+ static const int kNameFieldNumber = 4;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional string type_url = 6;
+ void clear_type_url();
+ static const int kTypeUrlFieldNumber = 6;
+ const ::std::string& type_url() const;
+ void set_type_url(const ::std::string& value);
+ void set_type_url(const char* value);
+ void set_type_url(const char* value, size_t size);
+ ::std::string* mutable_type_url();
+ ::std::string* release_type_url();
+ void set_allocated_type_url(::std::string* type_url);
+
+ // optional int32 oneof_index = 7;
+ void clear_oneof_index();
+ static const int kOneofIndexFieldNumber = 7;
+ ::google::protobuf::int32 oneof_index() const;
+ void set_oneof_index(::google::protobuf::int32 value);
+
+ // optional bool packed = 8;
+ void clear_packed();
+ static const int kPackedFieldNumber = 8;
+ bool packed() const;
+ void set_packed(bool value);
+
+ // repeated .google.protobuf.Option options = 9;
+ int options_size() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 9;
+ const ::google::protobuf::Option& options(int index) const;
+ ::google::protobuf::Option* mutable_options(int index);
+ ::google::protobuf::Option* add_options();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+ mutable_options();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+ options() const;
+
+ // optional string json_name = 10;
+ void clear_json_name();
+ static const int kJsonNameFieldNumber = 10;
+ const ::std::string& json_name() const;
+ void set_json_name(const ::std::string& value);
+ void set_json_name(const char* value);
+ void set_json_name(const char* value, size_t size);
+ ::std::string* mutable_json_name();
+ ::std::string* release_json_name();
+ void set_allocated_json_name(::std::string* json_name);
+
+ // optional string default_value = 11;
+ void clear_default_value();
+ static const int kDefaultValueFieldNumber = 11;
+ const ::std::string& default_value() const;
+ void set_default_value(const ::std::string& value);
+ void set_default_value(const char* value);
+ void set_default_value(const char* value, size_t size);
+ ::std::string* mutable_default_value();
+ ::std::string* release_default_value();
+ void set_allocated_default_value(::std::string* default_value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Field)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ int kind_;
+ int cardinality_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::int32 number_;
+ ::google::protobuf::int32 oneof_index_;
+ ::google::protobuf::internal::ArenaStringPtr type_url_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option > options_;
+ ::google::protobuf::internal::ArenaStringPtr json_name_;
+ ::google::protobuf::internal::ArenaStringPtr default_value_;
+ bool packed_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto();
+
+ void InitAsDefaultInstance();
+ static Field* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Enum : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Enum) */ {
+ public:
+ Enum();
+ virtual ~Enum();
+
+ Enum(const Enum& from);
+
+ inline Enum& operator=(const Enum& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Enum& default_instance();
+
+ void Swap(Enum* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Enum* New() const { return New(NULL); }
+
+ Enum* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Enum& from);
+ void MergeFrom(const Enum& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Enum* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // repeated .google.protobuf.EnumValue enumvalue = 2;
+ int enumvalue_size() const;
+ void clear_enumvalue();
+ static const int kEnumvalueFieldNumber = 2;
+ const ::google::protobuf::EnumValue& enumvalue(int index) const;
+ ::google::protobuf::EnumValue* mutable_enumvalue(int index);
+ ::google::protobuf::EnumValue* add_enumvalue();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValue >*
+ mutable_enumvalue();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValue >&
+ enumvalue() const;
+
+ // repeated .google.protobuf.Option options = 3;
+ int options_size() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 3;
+ const ::google::protobuf::Option& options(int index) const;
+ ::google::protobuf::Option* mutable_options(int index);
+ ::google::protobuf::Option* add_options();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+ mutable_options();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+ options() const;
+
+ // optional .google.protobuf.SourceContext source_context = 4;
+ bool has_source_context() const;
+ void clear_source_context();
+ static const int kSourceContextFieldNumber = 4;
+ const ::google::protobuf::SourceContext& source_context() const;
+ ::google::protobuf::SourceContext* mutable_source_context();
+ ::google::protobuf::SourceContext* release_source_context();
+ void set_allocated_source_context(::google::protobuf::SourceContext* source_context);
+
+ // optional .google.protobuf.Syntax syntax = 5;
+ void clear_syntax();
+ static const int kSyntaxFieldNumber = 5;
+ ::google::protobuf::Syntax syntax() const;
+ void set_syntax(::google::protobuf::Syntax value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Enum)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValue > enumvalue_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option > options_;
+ ::google::protobuf::SourceContext* source_context_;
+ int syntax_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto();
+
+ void InitAsDefaultInstance();
+ static Enum* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT EnumValue : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.EnumValue) */ {
+ public:
+ EnumValue();
+ virtual ~EnumValue();
+
+ EnumValue(const EnumValue& from);
+
+ inline EnumValue& operator=(const EnumValue& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const EnumValue& default_instance();
+
+ void Swap(EnumValue* other);
+
+ // implements Message ----------------------------------------------
+
+ inline EnumValue* New() const { return New(NULL); }
+
+ EnumValue* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const EnumValue& from);
+ void MergeFrom(const EnumValue& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(EnumValue* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional int32 number = 2;
+ void clear_number();
+ static const int kNumberFieldNumber = 2;
+ ::google::protobuf::int32 number() const;
+ void set_number(::google::protobuf::int32 value);
+
+ // repeated .google.protobuf.Option options = 3;
+ int options_size() const;
+ void clear_options();
+ static const int kOptionsFieldNumber = 3;
+ const ::google::protobuf::Option& options(int index) const;
+ ::google::protobuf::Option* mutable_options(int index);
+ ::google::protobuf::Option* add_options();
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+ mutable_options();
+ const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+ options() const;
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.EnumValue)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option > options_;
+ ::google::protobuf::int32 number_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto();
+
+ void InitAsDefaultInstance();
+ static EnumValue* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Option : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Option) */ {
+ public:
+ Option();
+ virtual ~Option();
+
+ Option(const Option& from);
+
+ inline Option& operator=(const Option& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Option& default_instance();
+
+ void Swap(Option* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Option* New() const { return New(NULL); }
+
+ Option* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Option& from);
+ void MergeFrom(const Option& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Option* other);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string name = 1;
+ void clear_name();
+ static const int kNameFieldNumber = 1;
+ const ::std::string& name() const;
+ void set_name(const ::std::string& value);
+ void set_name(const char* value);
+ void set_name(const char* value, size_t size);
+ ::std::string* mutable_name();
+ ::std::string* release_name();
+ void set_allocated_name(::std::string* name);
+
+ // optional .google.protobuf.Any value = 2;
+ bool has_value() const;
+ void clear_value();
+ static const int kValueFieldNumber = 2;
+ const ::google::protobuf::Any& value() const;
+ ::google::protobuf::Any* mutable_value();
+ ::google::protobuf::Any* release_value();
+ void set_allocated_value(::google::protobuf::Any* value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Option)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr name_;
+ ::google::protobuf::Any* value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2ftype_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2ftype_2eproto();
+
+ void InitAsDefaultInstance();
+ static Option* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// Type
+
+// optional string name = 1;
+inline void Type::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Type::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Type::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Type.name)
+}
+inline void Type::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Type.name)
+}
+inline void Type::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Type.name)
+}
+inline ::std::string* Type::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Type::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Type.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Type::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Type.name)
+}
+
+// repeated .google.protobuf.Field fields = 2;
+inline int Type::fields_size() const {
+ return fields_.size();
+}
+inline void Type::clear_fields() {
+ fields_.Clear();
+}
+inline const ::google::protobuf::Field& Type::fields(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.fields)
+ return fields_.Get(index);
+}
+inline ::google::protobuf::Field* Type::mutable_fields(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.fields)
+ return fields_.Mutable(index);
+}
+inline ::google::protobuf::Field* Type::add_fields() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Type.fields)
+ return fields_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Field >*
+Type::mutable_fields() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Type.fields)
+ return &fields_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Field >&
+Type::fields() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Type.fields)
+ return fields_;
+}
+
+// repeated string oneofs = 3;
+inline int Type::oneofs_size() const {
+ return oneofs_.size();
+}
+inline void Type::clear_oneofs() {
+ oneofs_.Clear();
+}
+inline const ::std::string& Type::oneofs(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.oneofs)
+ return oneofs_.Get(index);
+}
+inline ::std::string* Type::mutable_oneofs(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.oneofs)
+ return oneofs_.Mutable(index);
+}
+inline void Type::set_oneofs(int index, const ::std::string& value) {
+ // @@protoc_insertion_point(field_set:google.protobuf.Type.oneofs)
+ oneofs_.Mutable(index)->assign(value);
+}
+inline void Type::set_oneofs(int index, const char* value) {
+ oneofs_.Mutable(index)->assign(value);
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Type.oneofs)
+}
+inline void Type::set_oneofs(int index, const char* value, size_t size) {
+ oneofs_.Mutable(index)->assign(
+ reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Type.oneofs)
+}
+inline ::std::string* Type::add_oneofs() {
+ // @@protoc_insertion_point(field_add_mutable:google.protobuf.Type.oneofs)
+ return oneofs_.Add();
+}
+inline void Type::add_oneofs(const ::std::string& value) {
+ oneofs_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add:google.protobuf.Type.oneofs)
+}
+inline void Type::add_oneofs(const char* value) {
+ oneofs_.Add()->assign(value);
+ // @@protoc_insertion_point(field_add_char:google.protobuf.Type.oneofs)
+}
+inline void Type::add_oneofs(const char* value, size_t size) {
+ oneofs_.Add()->assign(reinterpret_cast<const char*>(value), size);
+ // @@protoc_insertion_point(field_add_pointer:google.protobuf.Type.oneofs)
+}
+inline const ::google::protobuf::RepeatedPtrField< ::std::string>&
+Type::oneofs() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Type.oneofs)
+ return oneofs_;
+}
+inline ::google::protobuf::RepeatedPtrField< ::std::string>*
+Type::mutable_oneofs() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Type.oneofs)
+ return &oneofs_;
+}
+
+// repeated .google.protobuf.Option options = 4;
+inline int Type::options_size() const {
+ return options_.size();
+}
+inline void Type::clear_options() {
+ options_.Clear();
+}
+inline const ::google::protobuf::Option& Type::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.options)
+ return options_.Get(index);
+}
+inline ::google::protobuf::Option* Type::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.options)
+ return options_.Mutable(index);
+}
+inline ::google::protobuf::Option* Type::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Type.options)
+ return options_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Type::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Type.options)
+ return &options_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Type::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Type.options)
+ return options_;
+}
+
+// optional .google.protobuf.SourceContext source_context = 5;
+inline bool Type::has_source_context() const {
+ return !_is_default_instance_ && source_context_ != NULL;
+}
+inline void Type::clear_source_context() {
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+}
+inline const ::google::protobuf::SourceContext& Type::source_context() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.source_context)
+ return source_context_ != NULL ? *source_context_ : *default_instance_->source_context_;
+}
+inline ::google::protobuf::SourceContext* Type::mutable_source_context() {
+
+ if (source_context_ == NULL) {
+ source_context_ = new ::google::protobuf::SourceContext;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Type.source_context)
+ return source_context_;
+}
+inline ::google::protobuf::SourceContext* Type::release_source_context() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Type.source_context)
+
+ ::google::protobuf::SourceContext* temp = source_context_;
+ source_context_ = NULL;
+ return temp;
+}
+inline void Type::set_allocated_source_context(::google::protobuf::SourceContext* source_context) {
+ delete source_context_;
+ source_context_ = source_context;
+ if (source_context) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Type.source_context)
+}
+
+// optional .google.protobuf.Syntax syntax = 6;
+inline void Type::clear_syntax() {
+ syntax_ = 0;
+}
+inline ::google::protobuf::Syntax Type::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Type.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+inline void Type::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Type.syntax)
+}
+
+// -------------------------------------------------------------------
+
+// Field
+
+// optional .google.protobuf.Field.Kind kind = 1;
+inline void Field::clear_kind() {
+ kind_ = 0;
+}
+inline ::google::protobuf::Field_Kind Field::kind() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.kind)
+ return static_cast< ::google::protobuf::Field_Kind >(kind_);
+}
+inline void Field::set_kind(::google::protobuf::Field_Kind value) {
+
+ kind_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.kind)
+}
+
+// optional .google.protobuf.Field.Cardinality cardinality = 2;
+inline void Field::clear_cardinality() {
+ cardinality_ = 0;
+}
+inline ::google::protobuf::Field_Cardinality Field::cardinality() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.cardinality)
+ return static_cast< ::google::protobuf::Field_Cardinality >(cardinality_);
+}
+inline void Field::set_cardinality(::google::protobuf::Field_Cardinality value) {
+
+ cardinality_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.cardinality)
+}
+
+// optional int32 number = 3;
+inline void Field::clear_number() {
+ number_ = 0;
+}
+inline ::google::protobuf::int32 Field::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.number)
+ return number_;
+}
+inline void Field::set_number(::google::protobuf::int32 value) {
+
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.number)
+}
+
+// optional string name = 4;
+inline void Field::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Field::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.name)
+}
+inline void Field::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.name)
+}
+inline void Field::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.name)
+}
+inline ::std::string* Field::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Field::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.name)
+}
+
+// optional string type_url = 6;
+inline void Field::clear_type_url() {
+ type_url_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Field::type_url() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.type_url)
+ return type_url_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_type_url(const ::std::string& value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.type_url)
+}
+inline void Field::set_type_url(const char* value) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.type_url)
+}
+inline void Field::set_type_url(const char* value, size_t size) {
+
+ type_url_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.type_url)
+}
+inline ::std::string* Field::mutable_type_url() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.type_url)
+ return type_url_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Field::release_type_url() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.type_url)
+
+ return type_url_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_allocated_type_url(::std::string* type_url) {
+ if (type_url != NULL) {
+
+ } else {
+
+ }
+ type_url_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), type_url);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.type_url)
+}
+
+// optional int32 oneof_index = 7;
+inline void Field::clear_oneof_index() {
+ oneof_index_ = 0;
+}
+inline ::google::protobuf::int32 Field::oneof_index() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.oneof_index)
+ return oneof_index_;
+}
+inline void Field::set_oneof_index(::google::protobuf::int32 value) {
+
+ oneof_index_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.oneof_index)
+}
+
+// optional bool packed = 8;
+inline void Field::clear_packed() {
+ packed_ = false;
+}
+inline bool Field::packed() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.packed)
+ return packed_;
+}
+inline void Field::set_packed(bool value) {
+
+ packed_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.packed)
+}
+
+// repeated .google.protobuf.Option options = 9;
+inline int Field::options_size() const {
+ return options_.size();
+}
+inline void Field::clear_options() {
+ options_.Clear();
+}
+inline const ::google::protobuf::Option& Field::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.options)
+ return options_.Get(index);
+}
+inline ::google::protobuf::Option* Field::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.options)
+ return options_.Mutable(index);
+}
+inline ::google::protobuf::Option* Field::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Field.options)
+ return options_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Field::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Field.options)
+ return &options_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Field::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Field.options)
+ return options_;
+}
+
+// optional string json_name = 10;
+inline void Field::clear_json_name() {
+ json_name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Field::json_name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.json_name)
+ return json_name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_json_name(const ::std::string& value) {
+
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.json_name)
+}
+inline void Field::set_json_name(const char* value) {
+
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.json_name)
+}
+inline void Field::set_json_name(const char* value, size_t size) {
+
+ json_name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.json_name)
+}
+inline ::std::string* Field::mutable_json_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.json_name)
+ return json_name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Field::release_json_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.json_name)
+
+ return json_name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_allocated_json_name(::std::string* json_name) {
+ if (json_name != NULL) {
+
+ } else {
+
+ }
+ json_name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), json_name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.json_name)
+}
+
+// optional string default_value = 11;
+inline void Field::clear_default_value() {
+ default_value_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Field::default_value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Field.default_value)
+ return default_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_default_value(const ::std::string& value) {
+
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Field.default_value)
+}
+inline void Field::set_default_value(const char* value) {
+
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Field.default_value)
+}
+inline void Field::set_default_value(const char* value, size_t size) {
+
+ default_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Field.default_value)
+}
+inline ::std::string* Field::mutable_default_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Field.default_value)
+ return default_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Field::release_default_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Field.default_value)
+
+ return default_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Field::set_allocated_default_value(::std::string* default_value) {
+ if (default_value != NULL) {
+
+ } else {
+
+ }
+ default_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), default_value);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Field.default_value)
+}
+
+// -------------------------------------------------------------------
+
+// Enum
+
+// optional string name = 1;
+inline void Enum::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Enum::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Enum::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Enum.name)
+}
+inline void Enum::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Enum.name)
+}
+inline void Enum::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Enum.name)
+}
+inline ::std::string* Enum::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Enum::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Enum.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Enum::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Enum.name)
+}
+
+// repeated .google.protobuf.EnumValue enumvalue = 2;
+inline int Enum::enumvalue_size() const {
+ return enumvalue_.size();
+}
+inline void Enum::clear_enumvalue() {
+ enumvalue_.Clear();
+}
+inline const ::google::protobuf::EnumValue& Enum::enumvalue(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.enumvalue)
+ return enumvalue_.Get(index);
+}
+inline ::google::protobuf::EnumValue* Enum::mutable_enumvalue(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.enumvalue)
+ return enumvalue_.Mutable(index);
+}
+inline ::google::protobuf::EnumValue* Enum::add_enumvalue() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Enum.enumvalue)
+ return enumvalue_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValue >*
+Enum::mutable_enumvalue() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Enum.enumvalue)
+ return &enumvalue_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::EnumValue >&
+Enum::enumvalue() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Enum.enumvalue)
+ return enumvalue_;
+}
+
+// repeated .google.protobuf.Option options = 3;
+inline int Enum::options_size() const {
+ return options_.size();
+}
+inline void Enum::clear_options() {
+ options_.Clear();
+}
+inline const ::google::protobuf::Option& Enum::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.options)
+ return options_.Get(index);
+}
+inline ::google::protobuf::Option* Enum::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.options)
+ return options_.Mutable(index);
+}
+inline ::google::protobuf::Option* Enum::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.Enum.options)
+ return options_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+Enum::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.Enum.options)
+ return &options_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+Enum::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.Enum.options)
+ return options_;
+}
+
+// optional .google.protobuf.SourceContext source_context = 4;
+inline bool Enum::has_source_context() const {
+ return !_is_default_instance_ && source_context_ != NULL;
+}
+inline void Enum::clear_source_context() {
+ if (GetArenaNoVirtual() == NULL && source_context_ != NULL) delete source_context_;
+ source_context_ = NULL;
+}
+inline const ::google::protobuf::SourceContext& Enum::source_context() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.source_context)
+ return source_context_ != NULL ? *source_context_ : *default_instance_->source_context_;
+}
+inline ::google::protobuf::SourceContext* Enum::mutable_source_context() {
+
+ if (source_context_ == NULL) {
+ source_context_ = new ::google::protobuf::SourceContext;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Enum.source_context)
+ return source_context_;
+}
+inline ::google::protobuf::SourceContext* Enum::release_source_context() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Enum.source_context)
+
+ ::google::protobuf::SourceContext* temp = source_context_;
+ source_context_ = NULL;
+ return temp;
+}
+inline void Enum::set_allocated_source_context(::google::protobuf::SourceContext* source_context) {
+ delete source_context_;
+ source_context_ = source_context;
+ if (source_context) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Enum.source_context)
+}
+
+// optional .google.protobuf.Syntax syntax = 5;
+inline void Enum::clear_syntax() {
+ syntax_ = 0;
+}
+inline ::google::protobuf::Syntax Enum::syntax() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Enum.syntax)
+ return static_cast< ::google::protobuf::Syntax >(syntax_);
+}
+inline void Enum::set_syntax(::google::protobuf::Syntax value) {
+
+ syntax_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Enum.syntax)
+}
+
+// -------------------------------------------------------------------
+
+// EnumValue
+
+// optional string name = 1;
+inline void EnumValue::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& EnumValue::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValue.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void EnumValue::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValue.name)
+}
+inline void EnumValue::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.EnumValue.name)
+}
+inline void EnumValue::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.EnumValue.name)
+}
+inline ::std::string* EnumValue::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValue.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* EnumValue::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.EnumValue.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void EnumValue::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.EnumValue.name)
+}
+
+// optional int32 number = 2;
+inline void EnumValue::clear_number() {
+ number_ = 0;
+}
+inline ::google::protobuf::int32 EnumValue::number() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValue.number)
+ return number_;
+}
+inline void EnumValue::set_number(::google::protobuf::int32 value) {
+
+ number_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.EnumValue.number)
+}
+
+// repeated .google.protobuf.Option options = 3;
+inline int EnumValue::options_size() const {
+ return options_.size();
+}
+inline void EnumValue::clear_options() {
+ options_.Clear();
+}
+inline const ::google::protobuf::Option& EnumValue::options(int index) const {
+ // @@protoc_insertion_point(field_get:google.protobuf.EnumValue.options)
+ return options_.Get(index);
+}
+inline ::google::protobuf::Option* EnumValue::mutable_options(int index) {
+ // @@protoc_insertion_point(field_mutable:google.protobuf.EnumValue.options)
+ return options_.Mutable(index);
+}
+inline ::google::protobuf::Option* EnumValue::add_options() {
+ // @@protoc_insertion_point(field_add:google.protobuf.EnumValue.options)
+ return options_.Add();
+}
+inline ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >*
+EnumValue::mutable_options() {
+ // @@protoc_insertion_point(field_mutable_list:google.protobuf.EnumValue.options)
+ return &options_;
+}
+inline const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Option >&
+EnumValue::options() const {
+ // @@protoc_insertion_point(field_list:google.protobuf.EnumValue.options)
+ return options_;
+}
+
+// -------------------------------------------------------------------
+
+// Option
+
+// optional string name = 1;
+inline void Option::clear_name() {
+ name_.ClearToEmptyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline const ::std::string& Option::name() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Option.name)
+ return name_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Option::set_name(const ::std::string& value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
+ // @@protoc_insertion_point(field_set:google.protobuf.Option.name)
+}
+inline void Option::set_name(const char* value) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value));
+ // @@protoc_insertion_point(field_set_char:google.protobuf.Option.name)
+}
+inline void Option::set_name(const char* value, size_t size) {
+
+ name_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ ::std::string(reinterpret_cast<const char*>(value), size));
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.Option.name)
+}
+inline ::std::string* Option::mutable_name() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Option.name)
+ return name_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline ::std::string* Option::release_name() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Option.name)
+
+ return name_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void Option::set_allocated_name(::std::string* name) {
+ if (name != NULL) {
+
+ } else {
+
+ }
+ name_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), name);
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Option.name)
+}
+
+// optional .google.protobuf.Any value = 2;
+inline bool Option::has_value() const {
+ return !_is_default_instance_ && value_ != NULL;
+}
+inline void Option::clear_value() {
+ if (GetArenaNoVirtual() == NULL && value_ != NULL) delete value_;
+ value_ = NULL;
+}
+inline const ::google::protobuf::Any& Option::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Option.value)
+ return value_ != NULL ? *value_ : *default_instance_->value_;
+}
+inline ::google::protobuf::Any* Option::mutable_value() {
+
+ if (value_ == NULL) {
+ value_ = new ::google::protobuf::Any;
+ }
+ // @@protoc_insertion_point(field_mutable:google.protobuf.Option.value)
+ return value_;
+}
+inline ::google::protobuf::Any* Option::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.Option.value)
+
+ ::google::protobuf::Any* temp = value_;
+ value_ = NULL;
+ return temp;
+}
+inline void Option::set_allocated_value(::google::protobuf::Any* value) {
+ delete value_;
+ value_ = value;
+ if (value) {
+
+ } else {
+
+ }
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.Option.value)
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+#ifndef SWIG
+namespace google {
+namespace protobuf {
+
+template <> struct is_proto_enum< ::google::protobuf::Field_Kind> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::Field_Kind>() {
+ return ::google::protobuf::Field_Kind_descriptor();
+}
+template <> struct is_proto_enum< ::google::protobuf::Field_Cardinality> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::Field_Cardinality>() {
+ return ::google::protobuf::Field_Cardinality_descriptor();
+}
+template <> struct is_proto_enum< ::google::protobuf::Syntax> : ::google::protobuf::internal::true_type {};
+template <>
+inline const EnumDescriptor* GetEnumDescriptor< ::google::protobuf::Syntax>() {
+ return ::google::protobuf::Syntax_descriptor();
+}
+
+} // namespace protobuf
+} // namespace google
+#endif // SWIG
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2ftype_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/type.proto b/third_party/protobuf/3.0.0/src/google/protobuf/type.proto
new file mode 100644
index 0000000000..1c9cf53da8
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/type.proto
@@ -0,0 +1,180 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+import "google/protobuf/any.proto";
+import "google/protobuf/source_context.proto";
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "TypeProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+// A protocol buffer message type.
+message Type {
+ // The fully qualified message name.
+ string name = 1;
+ // The list of fields.
+ repeated Field fields = 2;
+ // The list of types appearing in `oneof` definitions in this type.
+ repeated string oneofs = 3;
+ // The protocol buffer options.
+ repeated Option options = 4;
+ // The source context.
+ SourceContext source_context = 5;
+ // The source syntax.
+ Syntax syntax = 6;
+}
+
+// A single field of a message type.
+message Field {
+ // Basic field types.
+ enum Kind {
+ // Field type unknown.
+ TYPE_UNKNOWN = 0;
+ // Field type double.
+ TYPE_DOUBLE = 1;
+ // Field type float.
+ TYPE_FLOAT = 2;
+ // Field type int64.
+ TYPE_INT64 = 3;
+ // Field type uint64.
+ TYPE_UINT64 = 4;
+ // Field type int32.
+ TYPE_INT32 = 5;
+ // Field type fixed64.
+ TYPE_FIXED64 = 6;
+ // Field type fixed32.
+ TYPE_FIXED32 = 7;
+ // Field type bool.
+ TYPE_BOOL = 8;
+ // Field type string.
+ TYPE_STRING = 9;
+ // Field type group. Proto2 syntax only, and deprecated.
+ TYPE_GROUP = 10;
+ // Field type message.
+ TYPE_MESSAGE = 11;
+ // Field type bytes.
+ TYPE_BYTES = 12;
+ // Field type uint32.
+ TYPE_UINT32 = 13;
+ // Field type enum.
+ TYPE_ENUM = 14;
+ // Field type sfixed32.
+ TYPE_SFIXED32 = 15;
+ // Field type sfixed64.
+ TYPE_SFIXED64 = 16;
+ // Field type sint32.
+ TYPE_SINT32 = 17;
+ // Field type sint64.
+ TYPE_SINT64 = 18;
+ };
+
+ // Whether a field is optional, required, or repeated.
+ enum Cardinality {
+ // For fields with unknown cardinality.
+ CARDINALITY_UNKNOWN = 0;
+ // For optional fields.
+ CARDINALITY_OPTIONAL = 1;
+ // For required fields. Proto2 syntax only.
+ CARDINALITY_REQUIRED = 2;
+ // For repeated fields.
+ CARDINALITY_REPEATED = 3;
+ };
+
+ // The field type.
+ Kind kind = 1;
+ // The field cardinality.
+ Cardinality cardinality = 2;
+ // The field number.
+ int32 number = 3;
+ // The field name.
+ string name = 4;
+ // The field type URL, without the scheme, for message or enumeration
+ // types. Example: `"type.googleapis.com/google.protobuf.Timestamp"`.
+ string type_url = 6;
+ // The index of the field type in `Type.oneofs`, for message or enumeration
+ // types. The first type has index 1; zero means the type is not in the list.
+ int32 oneof_index = 7;
+ // Whether to use alternative packed wire representation.
+ bool packed = 8;
+ // The protocol buffer options.
+ repeated Option options = 9;
+ // The field JSON name.
+ string json_name = 10;
+ // The string value of the default value of this field. Proto2 syntax only.
+ string default_value = 11;
+}
+
+// Enum type definition.
+message Enum {
+ // Enum type name.
+ string name = 1;
+ // Enum value definitions.
+ repeated EnumValue enumvalue = 2;
+ // Protocol buffer options.
+ repeated Option options = 3;
+ // The source context.
+ SourceContext source_context = 4;
+ // The source syntax.
+ Syntax syntax = 5;
+}
+
+// Enum value definition.
+message EnumValue {
+ // Enum value name.
+ string name = 1;
+ // Enum value number.
+ int32 number = 2;
+ // Protocol buffer options.
+ repeated Option options = 3;
+}
+
+// A protocol buffer option, which can be attached to a message, field,
+// enumeration, etc.
+message Option {
+ // The option's name. For example, `"java_package"`.
+ string name = 1;
+ // The option's value. For example, `"com.google.protobuf"`.
+ Any value = 2;
+}
+
+// The syntax in which a protocol buffer element is defined.
+enum Syntax {
+ // Syntax `proto2`.
+ SYNTAX_PROTO2 = 0;
+ // Syntax `proto3`.
+ SYNTAX_PROTO3 = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest.proto
new file mode 100644
index 0000000000..d5206d2463
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest.proto
@@ -0,0 +1,880 @@
+// 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.
+//
+// A proto file we will use for unit testing.
+
+syntax = "proto2";
+
+// Some generic_services option(s) added automatically.
+// See: http://go/proto2-generic-services-default
+option cc_generic_services = true; // auto-added
+option java_generic_services = true; // auto-added
+option py_generic_services = true; // auto-added
+option cc_enable_arenas = true;
+
+import "google/protobuf/unittest_import.proto";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In test_util.h we do "using namespace unittest = protobuf_unittest".
+package protobuf_unittest;
+
+// Protos optimized for SPEED use a strict superset of the generated code
+// of equivalent ones optimized for CODE_SIZE, so we should optimize all our
+// tests for speed unless explicitly testing code size optimization.
+option optimize_for = SPEED;
+
+option java_outer_classname = "UnittestProto";
+
+// This proto includes every type of field in both singular and repeated
+// forms.
+message TestAllTypes {
+ message NestedMessage {
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ optional int32 bb = 1;
+ }
+
+ enum NestedEnum {
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ NEG = -1; // Intentionally negative.
+ }
+
+ // Singular
+ optional int32 optional_int32 = 1;
+ optional int64 optional_int64 = 2;
+ optional uint32 optional_uint32 = 3;
+ optional uint64 optional_uint64 = 4;
+ optional sint32 optional_sint32 = 5;
+ optional sint64 optional_sint64 = 6;
+ optional fixed32 optional_fixed32 = 7;
+ optional fixed64 optional_fixed64 = 8;
+ optional sfixed32 optional_sfixed32 = 9;
+ optional sfixed64 optional_sfixed64 = 10;
+ optional float optional_float = 11;
+ optional double optional_double = 12;
+ optional bool optional_bool = 13;
+ optional string optional_string = 14;
+ optional bytes optional_bytes = 15;
+
+ optional group OptionalGroup = 16 {
+ optional int32 a = 17;
+ }
+
+ optional NestedMessage optional_nested_message = 18;
+ optional ForeignMessage optional_foreign_message = 19;
+ optional protobuf_unittest_import.ImportMessage optional_import_message = 20;
+
+ optional NestedEnum optional_nested_enum = 21;
+ optional ForeignEnum optional_foreign_enum = 22;
+ optional protobuf_unittest_import.ImportEnum optional_import_enum = 23;
+
+ optional string optional_string_piece = 24 [ctype=STRING_PIECE];
+ optional string optional_cord = 25 [ctype=CORD];
+
+ // Defined in unittest_import_public.proto
+ optional protobuf_unittest_import.PublicImportMessage
+ optional_public_import_message = 26;
+
+ optional NestedMessage optional_lazy_message = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ repeated group RepeatedGroup = 46 {
+ optional int32 a = 47;
+ }
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessage repeated_foreign_message = 49;
+ repeated protobuf_unittest_import.ImportMessage repeated_import_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnum repeated_foreign_enum = 52;
+ repeated protobuf_unittest_import.ImportEnum repeated_import_enum = 53;
+
+ repeated string repeated_string_piece = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord = 55 [ctype=CORD];
+
+ repeated NestedMessage repeated_lazy_message = 57 [lazy=true];
+
+ // Singular with defaults
+ optional int32 default_int32 = 61 [default = 41 ];
+ optional int64 default_int64 = 62 [default = 42 ];
+ optional uint32 default_uint32 = 63 [default = 43 ];
+ optional uint64 default_uint64 = 64 [default = 44 ];
+ optional sint32 default_sint32 = 65 [default = -45 ];
+ optional sint64 default_sint64 = 66 [default = 46 ];
+ optional fixed32 default_fixed32 = 67 [default = 47 ];
+ optional fixed64 default_fixed64 = 68 [default = 48 ];
+ optional sfixed32 default_sfixed32 = 69 [default = 49 ];
+ optional sfixed64 default_sfixed64 = 70 [default = -50 ];
+ optional float default_float = 71 [default = 51.5 ];
+ optional double default_double = 72 [default = 52e3 ];
+ optional bool default_bool = 73 [default = true ];
+ optional string default_string = 74 [default = "hello"];
+ optional bytes default_bytes = 75 [default = "world"];
+
+ optional NestedEnum default_nested_enum = 81 [default = BAR ];
+ optional ForeignEnum default_foreign_enum = 82 [default = FOREIGN_BAR];
+ optional protobuf_unittest_import.ImportEnum
+ default_import_enum = 83 [default = IMPORT_BAR];
+
+ optional string default_string_piece = 84 [ctype=STRING_PIECE,default="abc"];
+ optional string default_cord = 85 [ctype=CORD,default="123"];
+
+ // For oneof test
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ bytes oneof_bytes = 114;
+ }
+}
+
+// This proto includes a recusively nested message.
+message NestedTestAllTypes {
+ optional NestedTestAllTypes child = 1;
+ optional TestAllTypes payload = 2;
+ repeated NestedTestAllTypes repeated_child = 3;
+}
+
+message TestDeprecatedFields {
+ optional int32 deprecated_int32 = 1 [deprecated=true];
+}
+
+// Define these after TestAllTypes to make sure the compiler can handle
+// that.
+message ForeignMessage {
+ optional int32 c = 1;
+ optional int32 d = 2;
+}
+
+enum ForeignEnum {
+ FOREIGN_FOO = 4;
+ FOREIGN_BAR = 5;
+ FOREIGN_BAZ = 6;
+}
+
+message TestReservedFields {
+ reserved 2, 15, 9 to 11;
+ reserved "bar", "baz";
+}
+
+message TestAllExtensions {
+ extensions 1 to max;
+}
+
+extend TestAllExtensions {
+ // Singular
+ optional int32 optional_int32_extension = 1;
+ optional int64 optional_int64_extension = 2;
+ optional uint32 optional_uint32_extension = 3;
+ optional uint64 optional_uint64_extension = 4;
+ optional sint32 optional_sint32_extension = 5;
+ optional sint64 optional_sint64_extension = 6;
+ optional fixed32 optional_fixed32_extension = 7;
+ optional fixed64 optional_fixed64_extension = 8;
+ optional sfixed32 optional_sfixed32_extension = 9;
+ optional sfixed64 optional_sfixed64_extension = 10;
+ optional float optional_float_extension = 11;
+ optional double optional_double_extension = 12;
+ optional bool optional_bool_extension = 13;
+ optional string optional_string_extension = 14;
+ optional bytes optional_bytes_extension = 15;
+
+ optional group OptionalGroup_extension = 16 {
+ optional int32 a = 17;
+ }
+
+ optional TestAllTypes.NestedMessage optional_nested_message_extension = 18;
+ optional ForeignMessage optional_foreign_message_extension = 19;
+ optional protobuf_unittest_import.ImportMessage
+ optional_import_message_extension = 20;
+
+ optional TestAllTypes.NestedEnum optional_nested_enum_extension = 21;
+ optional ForeignEnum optional_foreign_enum_extension = 22;
+ optional protobuf_unittest_import.ImportEnum
+ optional_import_enum_extension = 23;
+
+ optional string optional_string_piece_extension = 24 [ctype=STRING_PIECE];
+ optional string optional_cord_extension = 25 [ctype=CORD];
+
+ optional protobuf_unittest_import.PublicImportMessage
+ optional_public_import_message_extension = 26;
+
+ optional TestAllTypes.NestedMessage
+ optional_lazy_message_extension = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32_extension = 31;
+ repeated int64 repeated_int64_extension = 32;
+ repeated uint32 repeated_uint32_extension = 33;
+ repeated uint64 repeated_uint64_extension = 34;
+ repeated sint32 repeated_sint32_extension = 35;
+ repeated sint64 repeated_sint64_extension = 36;
+ repeated fixed32 repeated_fixed32_extension = 37;
+ repeated fixed64 repeated_fixed64_extension = 38;
+ repeated sfixed32 repeated_sfixed32_extension = 39;
+ repeated sfixed64 repeated_sfixed64_extension = 40;
+ repeated float repeated_float_extension = 41;
+ repeated double repeated_double_extension = 42;
+ repeated bool repeated_bool_extension = 43;
+ repeated string repeated_string_extension = 44;
+ repeated bytes repeated_bytes_extension = 45;
+
+ repeated group RepeatedGroup_extension = 46 {
+ optional int32 a = 47;
+ }
+
+ repeated TestAllTypes.NestedMessage repeated_nested_message_extension = 48;
+ repeated ForeignMessage repeated_foreign_message_extension = 49;
+ repeated protobuf_unittest_import.ImportMessage
+ repeated_import_message_extension = 50;
+
+ repeated TestAllTypes.NestedEnum repeated_nested_enum_extension = 51;
+ repeated ForeignEnum repeated_foreign_enum_extension = 52;
+ repeated protobuf_unittest_import.ImportEnum
+ repeated_import_enum_extension = 53;
+
+ repeated string repeated_string_piece_extension = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord_extension = 55 [ctype=CORD];
+
+ repeated TestAllTypes.NestedMessage
+ repeated_lazy_message_extension = 57 [lazy=true];
+
+ // Singular with defaults
+ optional int32 default_int32_extension = 61 [default = 41 ];
+ optional int64 default_int64_extension = 62 [default = 42 ];
+ optional uint32 default_uint32_extension = 63 [default = 43 ];
+ optional uint64 default_uint64_extension = 64 [default = 44 ];
+ optional sint32 default_sint32_extension = 65 [default = -45 ];
+ optional sint64 default_sint64_extension = 66 [default = 46 ];
+ optional fixed32 default_fixed32_extension = 67 [default = 47 ];
+ optional fixed64 default_fixed64_extension = 68 [default = 48 ];
+ optional sfixed32 default_sfixed32_extension = 69 [default = 49 ];
+ optional sfixed64 default_sfixed64_extension = 70 [default = -50 ];
+ optional float default_float_extension = 71 [default = 51.5 ];
+ optional double default_double_extension = 72 [default = 52e3 ];
+ optional bool default_bool_extension = 73 [default = true ];
+ optional string default_string_extension = 74 [default = "hello"];
+ optional bytes default_bytes_extension = 75 [default = "world"];
+
+ optional TestAllTypes.NestedEnum
+ default_nested_enum_extension = 81 [default = BAR];
+ optional ForeignEnum
+ default_foreign_enum_extension = 82 [default = FOREIGN_BAR];
+ optional protobuf_unittest_import.ImportEnum
+ default_import_enum_extension = 83 [default = IMPORT_BAR];
+
+ optional string default_string_piece_extension = 84 [ctype=STRING_PIECE,
+ default="abc"];
+ optional string default_cord_extension = 85 [ctype=CORD, default="123"];
+
+ // For oneof test
+ optional uint32 oneof_uint32_extension = 111;
+ optional TestAllTypes.NestedMessage oneof_nested_message_extension = 112;
+ optional string oneof_string_extension = 113;
+ optional bytes oneof_bytes_extension = 114;
+}
+
+message TestNestedExtension {
+ extend TestAllExtensions {
+ // Check for bug where string extensions declared in tested scope did not
+ // compile.
+ optional string test = 1002 [default="test"];
+ // Used to test if generated extension name is correct when there are
+ // underscores.
+ optional string nested_string_extension = 1003;
+ }
+}
+
+// We have separate messages for testing required fields because it's
+// annoying to have to fill in required fields in TestProto in order to
+// do anything with it. Note that we don't need to test every type of
+// required filed because the code output is basically identical to
+// optional fields for all types.
+message TestRequired {
+ required int32 a = 1;
+ optional int32 dummy2 = 2;
+ required int32 b = 3;
+
+ extend TestAllExtensions {
+ optional TestRequired single = 1000;
+ repeated TestRequired multi = 1001;
+ }
+
+ // Pad the field count to 32 so that we can test that IsInitialized()
+ // properly checks multiple elements of has_bits_.
+ optional int32 dummy4 = 4;
+ optional int32 dummy5 = 5;
+ optional int32 dummy6 = 6;
+ optional int32 dummy7 = 7;
+ optional int32 dummy8 = 8;
+ optional int32 dummy9 = 9;
+ optional int32 dummy10 = 10;
+ optional int32 dummy11 = 11;
+ optional int32 dummy12 = 12;
+ optional int32 dummy13 = 13;
+ optional int32 dummy14 = 14;
+ optional int32 dummy15 = 15;
+ optional int32 dummy16 = 16;
+ optional int32 dummy17 = 17;
+ optional int32 dummy18 = 18;
+ optional int32 dummy19 = 19;
+ optional int32 dummy20 = 20;
+ optional int32 dummy21 = 21;
+ optional int32 dummy22 = 22;
+ optional int32 dummy23 = 23;
+ optional int32 dummy24 = 24;
+ optional int32 dummy25 = 25;
+ optional int32 dummy26 = 26;
+ optional int32 dummy27 = 27;
+ optional int32 dummy28 = 28;
+ optional int32 dummy29 = 29;
+ optional int32 dummy30 = 30;
+ optional int32 dummy31 = 31;
+ optional int32 dummy32 = 32;
+
+ required int32 c = 33;
+}
+
+message TestRequiredForeign {
+ optional TestRequired optional_message = 1;
+ repeated TestRequired repeated_message = 2;
+ optional int32 dummy = 3;
+}
+
+// Test that we can use NestedMessage from outside TestAllTypes.
+message TestForeignNested {
+ optional TestAllTypes.NestedMessage foreign_nested = 1;
+}
+
+// TestEmptyMessage is used to test unknown field support.
+message TestEmptyMessage {
+}
+
+// Like above, but declare all field numbers as potential extensions. No
+// actual extensions should ever be defined for this type.
+message TestEmptyMessageWithExtensions {
+ extensions 1 to max;
+}
+
+message TestMultipleExtensionRanges {
+ extensions 42;
+ extensions 4143 to 4243;
+ extensions 65536 to max;
+}
+
+// Test that really large tag numbers don't break anything.
+message TestReallyLargeTagNumber {
+ // The largest possible tag number is 2^28 - 1, since the wire format uses
+ // three bits to communicate wire type.
+ optional int32 a = 1;
+ optional int32 bb = 268435455;
+}
+
+message TestRecursiveMessage {
+ optional TestRecursiveMessage a = 1;
+ optional int32 i = 2;
+}
+
+// Test that mutual recursion works.
+message TestMutualRecursionA {
+ optional TestMutualRecursionB bb = 1;
+}
+
+message TestMutualRecursionB {
+ optional TestMutualRecursionA a = 1;
+ optional int32 optional_int32 = 2;
+}
+
+// Test that groups have disjoint field numbers from their siblings and
+// parents. This is NOT possible in proto1; only google.protobuf. When attempting
+// to compile with proto1, this will emit an error; so we only include it
+// in protobuf_unittest_proto.
+message TestDupFieldNumber { // NO_PROTO1
+ optional int32 a = 1; // NO_PROTO1
+ optional group Foo = 2 { optional int32 a = 1; } // NO_PROTO1
+ optional group Bar = 3 { optional int32 a = 1; } // NO_PROTO1
+} // NO_PROTO1
+
+// Additional messages for testing lazy fields.
+message TestEagerMessage {
+ optional TestAllTypes sub_message = 1 [lazy=false];
+}
+message TestLazyMessage {
+ optional TestAllTypes sub_message = 1 [lazy=true];
+}
+
+// Needed for a Python test.
+message TestNestedMessageHasBits {
+ message NestedMessage {
+ repeated int32 nestedmessage_repeated_int32 = 1;
+ repeated ForeignMessage nestedmessage_repeated_foreignmessage = 2;
+ }
+ optional NestedMessage optional_nested_message = 1;
+}
+
+
+// Test an enum that has multiple values with the same number.
+enum TestEnumWithDupValue {
+ option allow_alias = true;
+
+ FOO1 = 1;
+ BAR1 = 2;
+ BAZ = 3;
+ FOO2 = 1;
+ BAR2 = 2;
+}
+
+// Test an enum with large, unordered values.
+enum TestSparseEnum {
+ SPARSE_A = 123;
+ SPARSE_B = 62374;
+ SPARSE_C = 12589234;
+ SPARSE_D = -15;
+ SPARSE_E = -53452;
+ SPARSE_F = 0;
+ SPARSE_G = 2;
+}
+
+// Test message with CamelCase field names. This violates Protocol Buffer
+// standard style.
+message TestCamelCaseFieldNames {
+ optional int32 PrimitiveField = 1;
+ optional string StringField = 2;
+ optional ForeignEnum EnumField = 3;
+ optional ForeignMessage MessageField = 4;
+ optional string StringPieceField = 5 [ctype=STRING_PIECE];
+ optional string CordField = 6 [ctype=CORD];
+
+ repeated int32 RepeatedPrimitiveField = 7;
+ repeated string RepeatedStringField = 8;
+ repeated ForeignEnum RepeatedEnumField = 9;
+ repeated ForeignMessage RepeatedMessageField = 10;
+ repeated string RepeatedStringPieceField = 11 [ctype=STRING_PIECE];
+ repeated string RepeatedCordField = 12 [ctype=CORD];
+}
+
+
+// We list fields out of order, to ensure that we're using field number and not
+// field index to determine serialization order.
+message TestFieldOrderings {
+ optional string my_string = 11;
+ extensions 2 to 10;
+ optional int64 my_int = 1;
+ extensions 12 to 100;
+ optional float my_float = 101;
+ message NestedMessage {
+ optional int64 oo = 2;
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ optional int32 bb = 1;
+ }
+
+ optional NestedMessage optional_nested_message = 200;
+}
+
+
+extend TestFieldOrderings {
+ optional string my_extension_string = 50;
+ optional int32 my_extension_int = 5;
+}
+
+
+message TestExtremeDefaultValues {
+ optional bytes escaped_bytes = 1 [default = "\0\001\a\b\f\n\r\t\v\\\'\"\xfe"];
+ optional uint32 large_uint32 = 2 [default = 0xFFFFFFFF];
+ optional uint64 large_uint64 = 3 [default = 0xFFFFFFFFFFFFFFFF];
+ optional int32 small_int32 = 4 [default = -0x7FFFFFFF];
+ optional int64 small_int64 = 5 [default = -0x7FFFFFFFFFFFFFFF];
+ optional int32 really_small_int32 = 21 [default = -0x80000000];
+ optional int64 really_small_int64 = 22 [default = -0x8000000000000000];
+
+ // The default value here is UTF-8 for "\u1234". (We could also just type
+ // the UTF-8 text directly into this text file rather than escape it, but
+ // lots of people use editors that would be confused by this.)
+ optional string utf8_string = 6 [default = "\341\210\264"];
+
+ // Tests for single-precision floating-point values.
+ optional float zero_float = 7 [default = 0];
+ optional float one_float = 8 [default = 1];
+ optional float small_float = 9 [default = 1.5];
+ optional float negative_one_float = 10 [default = -1];
+ optional float negative_float = 11 [default = -1.5];
+ // Using exponents
+ optional float large_float = 12 [default = 2E8];
+ optional float small_negative_float = 13 [default = -8e-28];
+
+ // Text for nonfinite floating-point values.
+ optional double inf_double = 14 [default = inf];
+ optional double neg_inf_double = 15 [default = -inf];
+ optional double nan_double = 16 [default = nan];
+ optional float inf_float = 17 [default = inf];
+ optional float neg_inf_float = 18 [default = -inf];
+ optional float nan_float = 19 [default = nan];
+
+ // Tests for C++ trigraphs.
+ // Trigraphs should be escaped in C++ generated files, but they should not be
+ // escaped for other languages.
+ // Note that in .proto file, "\?" is a valid way to escape ? in string
+ // literals.
+ optional string cpp_trigraph = 20 [default = "? \? ?? \?? \??? ??/ ?\?-"];
+
+ // String defaults containing the character '\000'
+ optional string string_with_zero = 23 [default = "hel\000lo"];
+ optional bytes bytes_with_zero = 24 [default = "wor\000ld"];
+ optional string string_piece_with_zero = 25 [ctype=STRING_PIECE,
+ default="ab\000c"];
+ optional string cord_with_zero = 26 [ctype=CORD,
+ default="12\0003"];
+ optional string replacement_string = 27 [default="${unknown}"];
+}
+
+message SparseEnumMessage {
+ optional TestSparseEnum sparse_enum = 1;
+}
+
+// Test String and Bytes: string is for valid UTF-8 strings
+message OneString {
+ optional string data = 1;
+}
+
+message MoreString {
+ repeated string data = 1;
+}
+
+message OneBytes {
+ optional bytes data = 1;
+}
+
+message MoreBytes {
+ repeated bytes data = 1;
+}
+
+// Test int32, uint32, int64, uint64, and bool are all compatible
+message Int32Message {
+ optional int32 data = 1;
+}
+
+message Uint32Message {
+ optional uint32 data = 1;
+}
+
+message Int64Message {
+ optional int64 data = 1;
+}
+
+message Uint64Message {
+ optional uint64 data = 1;
+}
+
+message BoolMessage {
+ optional bool data = 1;
+}
+
+// Test oneofs.
+message TestOneof {
+ oneof foo {
+ int32 foo_int = 1;
+ string foo_string = 2;
+ TestAllTypes foo_message = 3;
+ group FooGroup = 4 {
+ optional int32 a = 5;
+ optional string b = 6;
+ }
+ }
+}
+
+message TestOneofBackwardsCompatible {
+ optional int32 foo_int = 1;
+ optional string foo_string = 2;
+ optional TestAllTypes foo_message = 3;
+ optional group FooGroup = 4 {
+ optional int32 a = 5;
+ optional string b = 6;
+ }
+}
+
+message TestOneof2 {
+ oneof foo {
+ int32 foo_int = 1;
+ string foo_string = 2;
+ string foo_cord = 3 [ctype=CORD];
+ string foo_string_piece = 4 [ctype=STRING_PIECE];
+ bytes foo_bytes = 5;
+ NestedEnum foo_enum = 6;
+ NestedMessage foo_message = 7;
+ group FooGroup = 8 {
+ optional int32 a = 9;
+ optional string b = 10;
+ }
+ NestedMessage foo_lazy_message = 11 [lazy=true];
+ }
+
+ oneof bar {
+ int32 bar_int = 12 [default = 5];
+ string bar_string = 13 [default = "STRING"];
+ string bar_cord = 14 [ctype=CORD, default = "CORD"];
+ string bar_string_piece = 15 [ctype=STRING_PIECE, default = "SPIECE"];
+ bytes bar_bytes = 16 [default = "BYTES"];
+ NestedEnum bar_enum = 17 [default = BAR];
+ }
+
+ optional int32 baz_int = 18;
+ optional string baz_string = 19 [default = "BAZ"];
+
+ message NestedMessage {
+ optional int64 qux_int = 1;
+ repeated int32 corge_int = 2;
+ }
+
+ enum NestedEnum {
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ }
+}
+
+message TestRequiredOneof {
+ oneof foo {
+ int32 foo_int = 1;
+ string foo_string = 2;
+ NestedMessage foo_message = 3;
+ }
+ message NestedMessage {
+ required double required_double = 1;
+ }
+}
+
+
+// Test messages for packed fields
+
+message TestPackedTypes {
+ repeated int32 packed_int32 = 90 [packed = true];
+ repeated int64 packed_int64 = 91 [packed = true];
+ repeated uint32 packed_uint32 = 92 [packed = true];
+ repeated uint64 packed_uint64 = 93 [packed = true];
+ repeated sint32 packed_sint32 = 94 [packed = true];
+ repeated sint64 packed_sint64 = 95 [packed = true];
+ repeated fixed32 packed_fixed32 = 96 [packed = true];
+ repeated fixed64 packed_fixed64 = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32 = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64 = 99 [packed = true];
+ repeated float packed_float = 100 [packed = true];
+ repeated double packed_double = 101 [packed = true];
+ repeated bool packed_bool = 102 [packed = true];
+ repeated ForeignEnum packed_enum = 103 [packed = true];
+}
+
+// A message with the same fields as TestPackedTypes, but without packing. Used
+// to test packed <-> unpacked wire compatibility.
+message TestUnpackedTypes {
+ repeated int32 unpacked_int32 = 90 [packed = false];
+ repeated int64 unpacked_int64 = 91 [packed = false];
+ repeated uint32 unpacked_uint32 = 92 [packed = false];
+ repeated uint64 unpacked_uint64 = 93 [packed = false];
+ repeated sint32 unpacked_sint32 = 94 [packed = false];
+ repeated sint64 unpacked_sint64 = 95 [packed = false];
+ repeated fixed32 unpacked_fixed32 = 96 [packed = false];
+ repeated fixed64 unpacked_fixed64 = 97 [packed = false];
+ repeated sfixed32 unpacked_sfixed32 = 98 [packed = false];
+ repeated sfixed64 unpacked_sfixed64 = 99 [packed = false];
+ repeated float unpacked_float = 100 [packed = false];
+ repeated double unpacked_double = 101 [packed = false];
+ repeated bool unpacked_bool = 102 [packed = false];
+ repeated ForeignEnum unpacked_enum = 103 [packed = false];
+}
+
+message TestPackedExtensions {
+ extensions 1 to max;
+}
+
+extend TestPackedExtensions {
+ repeated int32 packed_int32_extension = 90 [packed = true];
+ repeated int64 packed_int64_extension = 91 [packed = true];
+ repeated uint32 packed_uint32_extension = 92 [packed = true];
+ repeated uint64 packed_uint64_extension = 93 [packed = true];
+ repeated sint32 packed_sint32_extension = 94 [packed = true];
+ repeated sint64 packed_sint64_extension = 95 [packed = true];
+ repeated fixed32 packed_fixed32_extension = 96 [packed = true];
+ repeated fixed64 packed_fixed64_extension = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32_extension = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64_extension = 99 [packed = true];
+ repeated float packed_float_extension = 100 [packed = true];
+ repeated double packed_double_extension = 101 [packed = true];
+ repeated bool packed_bool_extension = 102 [packed = true];
+ repeated ForeignEnum packed_enum_extension = 103 [packed = true];
+}
+
+message TestUnpackedExtensions {
+ extensions 1 to max;
+}
+
+extend TestUnpackedExtensions {
+ repeated int32 unpacked_int32_extension = 90 [packed = false];
+ repeated int64 unpacked_int64_extension = 91 [packed = false];
+ repeated uint32 unpacked_uint32_extension = 92 [packed = false];
+ repeated uint64 unpacked_uint64_extension = 93 [packed = false];
+ repeated sint32 unpacked_sint32_extension = 94 [packed = false];
+ repeated sint64 unpacked_sint64_extension = 95 [packed = false];
+ repeated fixed32 unpacked_fixed32_extension = 96 [packed = false];
+ repeated fixed64 unpacked_fixed64_extension = 97 [packed = false];
+ repeated sfixed32 unpacked_sfixed32_extension = 98 [packed = false];
+ repeated sfixed64 unpacked_sfixed64_extension = 99 [packed = false];
+ repeated float unpacked_float_extension = 100 [packed = false];
+ repeated double unpacked_double_extension = 101 [packed = false];
+ repeated bool unpacked_bool_extension = 102 [packed = false];
+ repeated ForeignEnum unpacked_enum_extension = 103 [packed = false];
+}
+
+// Used by ExtensionSetTest/DynamicExtensions. The test actually builds
+// a set of extensions to TestAllExtensions dynamically, based on the fields
+// of this message type.
+message TestDynamicExtensions {
+ enum DynamicEnumType {
+ DYNAMIC_FOO = 2200;
+ DYNAMIC_BAR = 2201;
+ DYNAMIC_BAZ = 2202;
+ }
+ message DynamicMessageType {
+ optional int32 dynamic_field = 2100;
+ }
+
+ optional fixed32 scalar_extension = 2000;
+ optional ForeignEnum enum_extension = 2001;
+ optional DynamicEnumType dynamic_enum_extension = 2002;
+
+ optional ForeignMessage message_extension = 2003;
+ optional DynamicMessageType dynamic_message_extension = 2004;
+
+ repeated string repeated_extension = 2005;
+ repeated sint32 packed_extension = 2006 [packed = true];
+}
+
+message TestRepeatedScalarDifferentTagSizes {
+ // Parsing repeated fixed size values used to fail. This message needs to be
+ // used in order to get a tag of the right size; all of the repeated fields
+ // in TestAllTypes didn't trigger the check.
+ repeated fixed32 repeated_fixed32 = 12;
+ // Check for a varint type, just for good measure.
+ repeated int32 repeated_int32 = 13;
+
+ // These have two-byte tags.
+ repeated fixed64 repeated_fixed64 = 2046;
+ repeated int64 repeated_int64 = 2047;
+
+ // Three byte tags.
+ repeated float repeated_float = 262142;
+ repeated uint64 repeated_uint64 = 262143;
+}
+
+// Test that if an optional or required message/group field appears multiple
+// times in the input, they need to be merged.
+message TestParsingMerge {
+ // RepeatedFieldsGenerator defines matching field types as TestParsingMerge,
+ // except that all fields are repeated. In the tests, we will serialize the
+ // RepeatedFieldsGenerator to bytes, and parse the bytes to TestParsingMerge.
+ // Repeated fields in RepeatedFieldsGenerator are expected to be merged into
+ // the corresponding required/optional fields in TestParsingMerge.
+ message RepeatedFieldsGenerator {
+ repeated TestAllTypes field1 = 1;
+ repeated TestAllTypes field2 = 2;
+ repeated TestAllTypes field3 = 3;
+ repeated group Group1 = 10 {
+ optional TestAllTypes field1 = 11;
+ }
+ repeated group Group2 = 20 {
+ optional TestAllTypes field1 = 21;
+ }
+ repeated TestAllTypes ext1 = 1000;
+ repeated TestAllTypes ext2 = 1001;
+ }
+ required TestAllTypes required_all_types = 1;
+ optional TestAllTypes optional_all_types = 2;
+ repeated TestAllTypes repeated_all_types = 3;
+ optional group OptionalGroup = 10 {
+ optional TestAllTypes optional_group_all_types = 11;
+ }
+ repeated group RepeatedGroup = 20 {
+ optional TestAllTypes repeated_group_all_types = 21;
+ }
+ extensions 1000 to max;
+ extend TestParsingMerge {
+ optional TestAllTypes optional_ext = 1000;
+ repeated TestAllTypes repeated_ext = 1001;
+ }
+}
+
+message TestCommentInjectionMessage {
+ // */ <- This should not close the generated doc comment
+ optional string a = 1 [default="*/ <- Neither should this."];
+}
+
+
+// Test that RPC services work.
+message FooRequest {}
+message FooResponse {}
+
+message FooClientMessage {}
+message FooServerMessage{}
+
+service TestService {
+ rpc Foo(FooRequest) returns (FooResponse);
+ rpc Bar(BarRequest) returns (BarResponse);
+}
+
+
+message BarRequest {}
+message BarResponse {}
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_arena.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_arena.proto
new file mode 100644
index 0000000000..cd7e437e16
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_arena.proto
@@ -0,0 +1,46 @@
+// 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.
+
+syntax = "proto2";
+
+import "google/protobuf/unittest_no_arena_import.proto";
+
+package proto2_arena_unittest;
+
+option cc_enable_arenas = true;
+
+message NestedMessage {
+ optional int32 d = 1;
+}
+
+message ArenaMessage {
+ repeated NestedMessage repeated_nested_message = 1;
+ repeated ImportNoArenaNestedMessage repeated_import_no_arena_message = 2;
+};
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_custom_options.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_custom_options.proto
new file mode 100644
index 0000000000..218447e9aa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_custom_options.proto
@@ -0,0 +1,430 @@
+// 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: benjy@google.com (Benjy Weinberger)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// A proto file used to test the "custom options" feature of google.protobuf.
+
+syntax = "proto2";
+
+// Some generic_services option(s) added automatically.
+// See: http://go/proto2-generic-services-default
+option cc_generic_services = true; // auto-added
+option java_generic_services = true; // auto-added
+option py_generic_services = true;
+
+// A custom file option (defined below).
+option (file_opt1) = 9876543210;
+
+import "google/protobuf/descriptor.proto";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+package protobuf_unittest;
+
+
+// Some simple test custom options of various types.
+
+extend google.protobuf.FileOptions {
+ optional uint64 file_opt1 = 7736974;
+}
+
+extend google.protobuf.MessageOptions {
+ optional int32 message_opt1 = 7739036;
+}
+
+extend google.protobuf.FieldOptions {
+ optional fixed64 field_opt1 = 7740936;
+ // This is useful for testing that we correctly register default values for
+ // extension options.
+ optional int32 field_opt2 = 7753913 [default=42];
+}
+
+extend google.protobuf.OneofOptions {
+ optional int32 oneof_opt1 = 7740111;
+}
+
+extend google.protobuf.EnumOptions {
+ optional sfixed32 enum_opt1 = 7753576;
+}
+
+extend google.protobuf.EnumValueOptions {
+ optional int32 enum_value_opt1 = 1560678;
+}
+
+extend google.protobuf.ServiceOptions {
+ optional sint64 service_opt1 = 7887650;
+}
+
+enum MethodOpt1 {
+ METHODOPT1_VAL1 = 1;
+ METHODOPT1_VAL2 = 2;
+}
+
+extend google.protobuf.MethodOptions {
+ optional MethodOpt1 method_opt1 = 7890860;
+}
+
+// A test message with custom options at all possible locations (and also some
+// regular options, to make sure they interact nicely).
+message TestMessageWithCustomOptions {
+ option message_set_wire_format = false;
+
+ option (message_opt1) = -56;
+
+ optional string field1 = 1 [ctype=CORD,
+ (field_opt1)=8765432109];
+
+ oneof AnOneof {
+ option (oneof_opt1) = -99;
+ int32 oneof_field = 2;
+ }
+
+ enum AnEnum {
+ option (enum_opt1) = -789;
+
+ ANENUM_VAL1 = 1;
+ ANENUM_VAL2 = 2 [(enum_value_opt1) = 123];
+ }
+}
+
+
+// A test RPC service with custom options at all possible locations (and also
+// some regular options, to make sure they interact nicely).
+message CustomOptionFooRequest {
+}
+
+message CustomOptionFooResponse {
+}
+
+message CustomOptionFooClientMessage {
+}
+
+message CustomOptionFooServerMessage {
+}
+
+service TestServiceWithCustomOptions {
+ option (service_opt1) = -9876543210;
+
+ rpc Foo(CustomOptionFooRequest) returns (CustomOptionFooResponse) {
+ option (method_opt1) = METHODOPT1_VAL2;
+ }
+}
+
+
+
+// Options of every possible field type, so we can test them all exhaustively.
+
+message DummyMessageContainingEnum {
+ enum TestEnumType {
+ TEST_OPTION_ENUM_TYPE1 = 22;
+ TEST_OPTION_ENUM_TYPE2 = -23;
+ }
+}
+
+message DummyMessageInvalidAsOptionType {
+}
+
+extend google.protobuf.MessageOptions {
+ optional bool bool_opt = 7706090;
+ optional int32 int32_opt = 7705709;
+ optional int64 int64_opt = 7705542;
+ optional uint32 uint32_opt = 7704880;
+ optional uint64 uint64_opt = 7702367;
+ optional sint32 sint32_opt = 7701568;
+ optional sint64 sint64_opt = 7700863;
+ optional fixed32 fixed32_opt = 7700307;
+ optional fixed64 fixed64_opt = 7700194;
+ optional sfixed32 sfixed32_opt = 7698645;
+ optional sfixed64 sfixed64_opt = 7685475;
+ optional float float_opt = 7675390;
+ optional double double_opt = 7673293;
+ optional string string_opt = 7673285;
+ optional bytes bytes_opt = 7673238;
+ optional DummyMessageContainingEnum.TestEnumType enum_opt = 7673233;
+ optional DummyMessageInvalidAsOptionType message_type_opt = 7665967;
+}
+
+message CustomOptionMinIntegerValues {
+ option (bool_opt) = false;
+ option (int32_opt) = -0x80000000;
+ option (int64_opt) = -0x8000000000000000;
+ option (uint32_opt) = 0;
+ option (uint64_opt) = 0;
+ option (sint32_opt) = -0x80000000;
+ option (sint64_opt) = -0x8000000000000000;
+ option (fixed32_opt) = 0;
+ option (fixed64_opt) = 0;
+ option (sfixed32_opt) = -0x80000000;
+ option (sfixed64_opt) = -0x8000000000000000;
+}
+
+message CustomOptionMaxIntegerValues {
+ option (bool_opt) = true;
+ option (int32_opt) = 0x7FFFFFFF;
+ option (int64_opt) = 0x7FFFFFFFFFFFFFFF;
+ option (uint32_opt) = 0xFFFFFFFF;
+ option (uint64_opt) = 0xFFFFFFFFFFFFFFFF;
+ option (sint32_opt) = 0x7FFFFFFF;
+ option (sint64_opt) = 0x7FFFFFFFFFFFFFFF;
+ option (fixed32_opt) = 0xFFFFFFFF;
+ option (fixed64_opt) = 0xFFFFFFFFFFFFFFFF;
+ option (sfixed32_opt) = 0x7FFFFFFF;
+ option (sfixed64_opt) = 0x7FFFFFFFFFFFFFFF;
+}
+
+message CustomOptionOtherValues {
+ option (int32_opt) = -100; // To test sign-extension.
+ option (float_opt) = 12.3456789;
+ option (double_opt) = 1.234567890123456789;
+ option (string_opt) = "Hello, \"World\"";
+ option (bytes_opt) = "Hello\0World";
+ option (enum_opt) = TEST_OPTION_ENUM_TYPE2;
+}
+
+message SettingRealsFromPositiveInts {
+ option (float_opt) = 12;
+ option (double_opt) = 154;
+}
+
+message SettingRealsFromNegativeInts {
+ option (float_opt) = -12;
+ option (double_opt) = -154;
+}
+
+// Options of complex message types, themselves combined and extended in
+// various ways.
+
+message ComplexOptionType1 {
+ optional int32 foo = 1;
+ optional int32 foo2 = 2;
+ optional int32 foo3 = 3;
+ repeated int32 foo4 = 4;
+
+ extensions 100 to max;
+}
+
+message ComplexOptionType2 {
+ optional ComplexOptionType1 bar = 1;
+ optional int32 baz = 2;
+
+ message ComplexOptionType4 {
+ optional int32 waldo = 1;
+
+ extend google.protobuf.MessageOptions {
+ optional ComplexOptionType4 complex_opt4 = 7633546;
+ }
+ }
+
+ optional ComplexOptionType4 fred = 3;
+ repeated ComplexOptionType4 barney = 4;
+
+ extensions 100 to max;
+}
+
+message ComplexOptionType3 {
+ optional int32 qux = 1;
+
+ optional group ComplexOptionType5 = 2 {
+ optional int32 plugh = 3;
+ }
+}
+
+extend ComplexOptionType1 {
+ optional int32 quux = 7663707;
+ optional ComplexOptionType3 corge = 7663442;
+}
+
+extend ComplexOptionType2 {
+ optional int32 grault = 7650927;
+ optional ComplexOptionType1 garply = 7649992;
+}
+
+extend google.protobuf.MessageOptions {
+ optional protobuf_unittest.ComplexOptionType1 complex_opt1 = 7646756;
+ optional ComplexOptionType2 complex_opt2 = 7636949;
+ optional ComplexOptionType3 complex_opt3 = 7636463;
+ optional group ComplexOpt6 = 7595468 {
+ optional int32 xyzzy = 7593951;
+ }
+}
+
+// Note that we try various different ways of naming the same extension.
+message VariousComplexOptions {
+ option (.protobuf_unittest.complex_opt1).foo = 42;
+ option (protobuf_unittest.complex_opt1).(.protobuf_unittest.quux) = 324;
+ option (.protobuf_unittest.complex_opt1).(protobuf_unittest.corge).qux = 876;
+ option (protobuf_unittest.complex_opt1).foo4 = 99;
+ option (protobuf_unittest.complex_opt1).foo4 = 88;
+ option (complex_opt2).baz = 987;
+ option (complex_opt2).(grault) = 654;
+ option (complex_opt2).bar.foo = 743;
+ option (complex_opt2).bar.(quux) = 1999;
+ option (complex_opt2).bar.(protobuf_unittest.corge).qux = 2008;
+ option (complex_opt2).(garply).foo = 741;
+ option (complex_opt2).(garply).(.protobuf_unittest.quux) = 1998;
+ option (complex_opt2).(protobuf_unittest.garply).(corge).qux = 2121;
+ option (ComplexOptionType2.ComplexOptionType4.complex_opt4).waldo = 1971;
+ option (complex_opt2).fred.waldo = 321;
+ option (complex_opt2).barney = { waldo: 101 };
+ option (complex_opt2).barney = { waldo: 212 };
+ option (protobuf_unittest.complex_opt3).qux = 9;
+ option (complex_opt3).complexoptiontype5.plugh = 22;
+ option (complexopt6).xyzzy = 24;
+}
+
+// ------------------------------------------------------
+// Definitions for testing aggregate option parsing.
+// See descriptor_unittest.cc.
+
+message AggregateMessageSet {
+ option message_set_wire_format = true;
+ extensions 4 to max;
+}
+
+message AggregateMessageSetElement {
+ extend AggregateMessageSet {
+ optional AggregateMessageSetElement message_set_extension = 15447542;
+ }
+ optional string s = 1;
+}
+
+// A helper type used to test aggregate option parsing
+message Aggregate {
+ optional int32 i = 1;
+ optional string s = 2;
+
+ // A nested object
+ optional Aggregate sub = 3;
+
+ // To test the parsing of extensions inside aggregate values
+ optional google.protobuf.FileOptions file = 4;
+ extend google.protobuf.FileOptions {
+ optional Aggregate nested = 15476903;
+ }
+
+ // An embedded message set
+ optional AggregateMessageSet mset = 5;
+}
+
+// Allow Aggregate to be used as an option at all possible locations
+// in the .proto grammer.
+extend google.protobuf.FileOptions { optional Aggregate fileopt = 15478479; }
+extend google.protobuf.MessageOptions { optional Aggregate msgopt = 15480088; }
+extend google.protobuf.FieldOptions { optional Aggregate fieldopt = 15481374; }
+extend google.protobuf.EnumOptions { optional Aggregate enumopt = 15483218; }
+extend google.protobuf.EnumValueOptions { optional Aggregate enumvalopt = 15486921; }
+extend google.protobuf.ServiceOptions { optional Aggregate serviceopt = 15497145; }
+extend google.protobuf.MethodOptions { optional Aggregate methodopt = 15512713; }
+
+// Try using AggregateOption at different points in the proto grammar
+option (fileopt) = {
+ s: 'FileAnnotation'
+ // Also test the handling of comments
+ /* of both types */ i: 100
+
+ sub { s: 'NestedFileAnnotation' }
+
+ // Include a google.protobuf.FileOptions and recursively extend it with
+ // another fileopt.
+ file {
+ [protobuf_unittest.fileopt] {
+ s:'FileExtensionAnnotation'
+ }
+ }
+
+ // A message set inside an option value
+ mset {
+ [protobuf_unittest.AggregateMessageSetElement.message_set_extension] {
+ s: 'EmbeddedMessageSetElement'
+ }
+ }
+};
+
+message AggregateMessage {
+ option (msgopt) = { i:101 s:'MessageAnnotation' };
+ optional int32 fieldname = 1 [(fieldopt) = { s:'FieldAnnotation' }];
+}
+
+service AggregateService {
+ option (serviceopt) = { s:'ServiceAnnotation' };
+ rpc Method (AggregateMessage) returns (AggregateMessage) {
+ option (methodopt) = { s:'MethodAnnotation' };
+ }
+}
+
+enum AggregateEnum {
+ option (enumopt) = { s:'EnumAnnotation' };
+ VALUE = 1 [(enumvalopt) = { s:'EnumValueAnnotation' }];
+}
+
+// Test custom options for nested type.
+message NestedOptionType {
+ message NestedMessage {
+ option (message_opt1) = 1001;
+ optional int32 nested_field = 1 [(field_opt1) = 1002];
+ }
+ enum NestedEnum {
+ option (enum_opt1) = 1003;
+ NESTED_ENUM_VALUE = 1 [(enum_value_opt1) = 1004];
+ }
+ extend google.protobuf.FileOptions {
+ optional int32 nested_extension = 7912573 [(field_opt2) = 1005];
+ }
+}
+
+// Custom message option that has a required enum field.
+// WARNING: this is strongly discouraged!
+message OldOptionType {
+ enum TestEnum {
+ OLD_VALUE = 0;
+ }
+ required TestEnum value = 1;
+}
+
+// Updated version of the custom option above.
+message NewOptionType {
+ enum TestEnum {
+ OLD_VALUE = 0;
+ NEW_VALUE = 1;
+ }
+ required TestEnum value = 1;
+}
+
+extend google.protobuf.MessageOptions {
+ optional OldOptionType required_enum_opt = 106161807;
+}
+
+// Test message using the "required_enum_opt" option defined above.
+message TestMessageWithRequiredEnumOption {
+ option (required_enum_opt) = { value: OLD_VALUE };
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_drop_unknown_fields.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_drop_unknown_fields.proto
new file mode 100644
index 0000000000..8aa3a37b8e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_drop_unknown_fields.proto
@@ -0,0 +1,58 @@
+// 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.
+
+syntax = "proto3";
+
+package unittest_drop_unknown_fields;
+option objc_class_prefix = "DropUnknowns";
+
+option csharp_namespace = "Google.Protobuf.TestProtos";
+
+message Foo {
+ enum NestedEnum {
+ FOO = 0;
+ BAR = 1;
+ BAZ = 2;
+ }
+ int32 int32_value = 1;
+ NestedEnum enum_value = 2;
+}
+
+message FooWithExtraFields {
+ enum NestedEnum {
+ FOO = 0;
+ BAR = 1;
+ BAZ = 2;
+ QUX = 3;
+ }
+ int32 int32_value = 1;
+ NestedEnum enum_value = 2;
+ int32 extra_int32_value = 3;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_embed_optimize_for.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_embed_optimize_for.proto
new file mode 100644
index 0000000000..d8b0f9b94f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_embed_optimize_for.proto
@@ -0,0 +1,51 @@
+// 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.
+//
+// A proto file which imports a proto file that uses optimize_for = CODE_SIZE.
+
+syntax = "proto2";
+import "google/protobuf/unittest_optimize_for.proto";
+
+package protobuf_unittest;
+
+// We optimize for speed here, but we are importing a proto that is optimized
+// for code size.
+option optimize_for = SPEED;
+
+message TestEmbedOptimizedForSize {
+ // Test that embedding a message which has optimize_for = CODE_SIZE into
+ // one optimized for speed works.
+ optional TestOptimizedForSize optional_message = 1;
+ repeated TestOptimizedForSize repeated_message = 2;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_empty.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_empty.proto
new file mode 100644
index 0000000000..36443e7e01
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_empty.proto
@@ -0,0 +1,38 @@
+// 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 intentionally left blank. (At one point this wouldn't compile
+// correctly.)
+
+syntax = "proto2";
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_enormous_descriptor.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_enormous_descriptor.proto
new file mode 100644
index 0000000000..6e65dc18b7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_enormous_descriptor.proto
@@ -0,0 +1,1048 @@
+// 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.
+//
+// A proto file that has an extremely large descriptor. Used to test that
+// descriptors over 64k don't break language-specific limits in generated code,
+// such as the string literal length limit in Java.
+
+syntax = "proto2";
+
+package google.protobuf;
+option java_package = "com.google.protobuf";
+
+// Avoid generating insanely long methods.
+option optimize_for = CODE_SIZE;
+
+message TestEnormousDescriptor {
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_1 = 1 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_2 = 2 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_3 = 3 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_4 = 4 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_5 = 5 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_6 = 6 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_7 = 7 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_8 = 8 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_9 = 9 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_10 = 10 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_11 = 11 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_12 = 12 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_13 = 13 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_14 = 14 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_15 = 15 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_16 = 16 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_17 = 17 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_18 = 18 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_19 = 19 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_20 = 20 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_21 = 21 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_22 = 22 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_23 = 23 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_24 = 24 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_25 = 25 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_26 = 26 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_27 = 27 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_28 = 28 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_29 = 29 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_30 = 30 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_31 = 31 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_32 = 32 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_33 = 33 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_34 = 34 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_35 = 35 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_36 = 36 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_37 = 37 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_38 = 38 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_39 = 39 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_40 = 40 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_41 = 41 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_42 = 42 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_43 = 43 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_44 = 44 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_45 = 45 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_46 = 46 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_47 = 47 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_48 = 48 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_49 = 49 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_50 = 50 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_51 = 51 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_52 = 52 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_53 = 53 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_54 = 54 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_55 = 55 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_56 = 56 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_57 = 57 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_58 = 58 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_59 = 59 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_60 = 60 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_61 = 61 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_62 = 62 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_63 = 63 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_64 = 64 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_65 = 65 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_66 = 66 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_67 = 67 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_68 = 68 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_69 = 69 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_70 = 70 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_71 = 71 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_72 = 72 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_73 = 73 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_74 = 74 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_75 = 75 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_76 = 76 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_77 = 77 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_78 = 78 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_79 = 79 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_80 = 80 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_81 = 81 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_82 = 82 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_83 = 83 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_84 = 84 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_85 = 85 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_86 = 86 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_87 = 87 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_88 = 88 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_89 = 89 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_90 = 90 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_91 = 91 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_92 = 92 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_93 = 93 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_94 = 94 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_95 = 95 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_96 = 96 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_97 = 97 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_98 = 98 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_99 = 99 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_100 = 100 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_101 = 101 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_102 = 102 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_103 = 103 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_104 = 104 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_105 = 105 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_106 = 106 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_107 = 107 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_108 = 108 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_109 = 109 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_110 = 110 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_111 = 111 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_112 = 112 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_113 = 113 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_114 = 114 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_115 = 115 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_116 = 116 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_117 = 117 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_118 = 118 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_119 = 119 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_120 = 120 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_121 = 121 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_122 = 122 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_123 = 123 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_124 = 124 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_125 = 125 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_126 = 126 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_127 = 127 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_128 = 128 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_129 = 129 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_130 = 130 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_131 = 131 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_132 = 132 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_133 = 133 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_134 = 134 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_135 = 135 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_136 = 136 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_137 = 137 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_138 = 138 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_139 = 139 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_140 = 140 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_141 = 141 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_142 = 142 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_143 = 143 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_144 = 144 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_145 = 145 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_146 = 146 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_147 = 147 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_148 = 148 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_149 = 149 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_150 = 150 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_151 = 151 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_152 = 152 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_153 = 153 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_154 = 154 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_155 = 155 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_156 = 156 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_157 = 157 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_158 = 158 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_159 = 159 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_160 = 160 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_161 = 161 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_162 = 162 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_163 = 163 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_164 = 164 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_165 = 165 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_166 = 166 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_167 = 167 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_168 = 168 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_169 = 169 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_170 = 170 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_171 = 171 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_172 = 172 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_173 = 173 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_174 = 174 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_175 = 175 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_176 = 176 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_177 = 177 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_178 = 178 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_179 = 179 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_180 = 180 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_181 = 181 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_182 = 182 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_183 = 183 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_184 = 184 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_185 = 185 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_186 = 186 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_187 = 187 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_188 = 188 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_189 = 189 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_190 = 190 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_191 = 191 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_192 = 192 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_193 = 193 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_194 = 194 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_195 = 195 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_196 = 196 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_197 = 197 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_198 = 198 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_199 = 199 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_200 = 200 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_201 = 201 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_202 = 202 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_203 = 203 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_204 = 204 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_205 = 205 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_206 = 206 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_207 = 207 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_208 = 208 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_209 = 209 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_210 = 210 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_211 = 211 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_212 = 212 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_213 = 213 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_214 = 214 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_215 = 215 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_216 = 216 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_217 = 217 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_218 = 218 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_219 = 219 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_220 = 220 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_221 = 221 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_222 = 222 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_223 = 223 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_224 = 224 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_225 = 225 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_226 = 226 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_227 = 227 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_228 = 228 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_229 = 229 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_230 = 230 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_231 = 231 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_232 = 232 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_233 = 233 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_234 = 234 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_235 = 235 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_236 = 236 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_237 = 237 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_238 = 238 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_239 = 239 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_240 = 240 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_241 = 241 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_242 = 242 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_243 = 243 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_244 = 244 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_245 = 245 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_246 = 246 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_247 = 247 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_248 = 248 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_249 = 249 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_250 = 250 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_251 = 251 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_252 = 252 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_253 = 253 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_254 = 254 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_255 = 255 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_256 = 256 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_257 = 257 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_258 = 258 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_259 = 259 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_260 = 260 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_261 = 261 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_262 = 262 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_263 = 263 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_264 = 264 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_265 = 265 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_266 = 266 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_267 = 267 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_268 = 268 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_269 = 269 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_270 = 270 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_271 = 271 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_272 = 272 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_273 = 273 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_274 = 274 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_275 = 275 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_276 = 276 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_277 = 277 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_278 = 278 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_279 = 279 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_280 = 280 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_281 = 281 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_282 = 282 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_283 = 283 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_284 = 284 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_285 = 285 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_286 = 286 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_287 = 287 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_288 = 288 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_289 = 289 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_290 = 290 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_291 = 291 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_292 = 292 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_293 = 293 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_294 = 294 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_295 = 295 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_296 = 296 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_297 = 297 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_298 = 298 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_299 = 299 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_300 = 300 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_301 = 301 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_302 = 302 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_303 = 303 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_304 = 304 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_305 = 305 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_306 = 306 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_307 = 307 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_308 = 308 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_309 = 309 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_310 = 310 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_311 = 311 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_312 = 312 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_313 = 313 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_314 = 314 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_315 = 315 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_316 = 316 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_317 = 317 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_318 = 318 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_319 = 319 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_320 = 320 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_321 = 321 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_322 = 322 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_323 = 323 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_324 = 324 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_325 = 325 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_326 = 326 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_327 = 327 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_328 = 328 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_329 = 329 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_330 = 330 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_331 = 331 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_332 = 332 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_333 = 333 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_334 = 334 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_335 = 335 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_336 = 336 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_337 = 337 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_338 = 338 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_339 = 339 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_340 = 340 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_341 = 341 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_342 = 342 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_343 = 343 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_344 = 344 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_345 = 345 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_346 = 346 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_347 = 347 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_348 = 348 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_349 = 349 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_350 = 350 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_351 = 351 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_352 = 352 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_353 = 353 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_354 = 354 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_355 = 355 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_356 = 356 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_357 = 357 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_358 = 358 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_359 = 359 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_360 = 360 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_361 = 361 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_362 = 362 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_363 = 363 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_364 = 364 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_365 = 365 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_366 = 366 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_367 = 367 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_368 = 368 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_369 = 369 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_370 = 370 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_371 = 371 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_372 = 372 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_373 = 373 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_374 = 374 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_375 = 375 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_376 = 376 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_377 = 377 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_378 = 378 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_379 = 379 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_380 = 380 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_381 = 381 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_382 = 382 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_383 = 383 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_384 = 384 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_385 = 385 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_386 = 386 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_387 = 387 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_388 = 388 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_389 = 389 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_390 = 390 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_391 = 391 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_392 = 392 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_393 = 393 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_394 = 394 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_395 = 395 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_396 = 396 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_397 = 397 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_398 = 398 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_399 = 399 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_400 = 400 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_401 = 401 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_402 = 402 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_403 = 403 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_404 = 404 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_405 = 405 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_406 = 406 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_407 = 407 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_408 = 408 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_409 = 409 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_410 = 410 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_411 = 411 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_412 = 412 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_413 = 413 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_414 = 414 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_415 = 415 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_416 = 416 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_417 = 417 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_418 = 418 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_419 = 419 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_420 = 420 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_421 = 421 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_422 = 422 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_423 = 423 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_424 = 424 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_425 = 425 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_426 = 426 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_427 = 427 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_428 = 428 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_429 = 429 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_430 = 430 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_431 = 431 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_432 = 432 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_433 = 433 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_434 = 434 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_435 = 435 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_436 = 436 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_437 = 437 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_438 = 438 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_439 = 439 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_440 = 440 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_441 = 441 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_442 = 442 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_443 = 443 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_444 = 444 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_445 = 445 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_446 = 446 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_447 = 447 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_448 = 448 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_449 = 449 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_450 = 450 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_451 = 451 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_452 = 452 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_453 = 453 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_454 = 454 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_455 = 455 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_456 = 456 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_457 = 457 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_458 = 458 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_459 = 459 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_460 = 460 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_461 = 461 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_462 = 462 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_463 = 463 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_464 = 464 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_465 = 465 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_466 = 466 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_467 = 467 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_468 = 468 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_469 = 469 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_470 = 470 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_471 = 471 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_472 = 472 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_473 = 473 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_474 = 474 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_475 = 475 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_476 = 476 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_477 = 477 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_478 = 478 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_479 = 479 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_480 = 480 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_481 = 481 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_482 = 482 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_483 = 483 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_484 = 484 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_485 = 485 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_486 = 486 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_487 = 487 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_488 = 488 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_489 = 489 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_490 = 490 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_491 = 491 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_492 = 492 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_493 = 493 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_494 = 494 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_495 = 495 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_496 = 496 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_497 = 497 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_498 = 498 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_499 = 499 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_500 = 500 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_501 = 501 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_502 = 502 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_503 = 503 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_504 = 504 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_505 = 505 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_506 = 506 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_507 = 507 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_508 = 508 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_509 = 509 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_510 = 510 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_511 = 511 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_512 = 512 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_513 = 513 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_514 = 514 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_515 = 515 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_516 = 516 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_517 = 517 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_518 = 518 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_519 = 519 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_520 = 520 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_521 = 521 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_522 = 522 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_523 = 523 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_524 = 524 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_525 = 525 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_526 = 526 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_527 = 527 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_528 = 528 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_529 = 529 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_530 = 530 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_531 = 531 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_532 = 532 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_533 = 533 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_534 = 534 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_535 = 535 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_536 = 536 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_537 = 537 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_538 = 538 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_539 = 539 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_540 = 540 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_541 = 541 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_542 = 542 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_543 = 543 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_544 = 544 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_545 = 545 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_546 = 546 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_547 = 547 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_548 = 548 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_549 = 549 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_550 = 550 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_551 = 551 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_552 = 552 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_553 = 553 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_554 = 554 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_555 = 555 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_556 = 556 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_557 = 557 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_558 = 558 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_559 = 559 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_560 = 560 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_561 = 561 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_562 = 562 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_563 = 563 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_564 = 564 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_565 = 565 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_566 = 566 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_567 = 567 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_568 = 568 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_569 = 569 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_570 = 570 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_571 = 571 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_572 = 572 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_573 = 573 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_574 = 574 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_575 = 575 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_576 = 576 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_577 = 577 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_578 = 578 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_579 = 579 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_580 = 580 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_581 = 581 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_582 = 582 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_583 = 583 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_584 = 584 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_585 = 585 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_586 = 586 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_587 = 587 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_588 = 588 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_589 = 589 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_590 = 590 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_591 = 591 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_592 = 592 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_593 = 593 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_594 = 594 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_595 = 595 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_596 = 596 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_597 = 597 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_598 = 598 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_599 = 599 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_600 = 600 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_601 = 601 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_602 = 602 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_603 = 603 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_604 = 604 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_605 = 605 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_606 = 606 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_607 = 607 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_608 = 608 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_609 = 609 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_610 = 610 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_611 = 611 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_612 = 612 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_613 = 613 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_614 = 614 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_615 = 615 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_616 = 616 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_617 = 617 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_618 = 618 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_619 = 619 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_620 = 620 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_621 = 621 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_622 = 622 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_623 = 623 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_624 = 624 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_625 = 625 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_626 = 626 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_627 = 627 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_628 = 628 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_629 = 629 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_630 = 630 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_631 = 631 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_632 = 632 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_633 = 633 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_634 = 634 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_635 = 635 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_636 = 636 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_637 = 637 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_638 = 638 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_639 = 639 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_640 = 640 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_641 = 641 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_642 = 642 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_643 = 643 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_644 = 644 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_645 = 645 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_646 = 646 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_647 = 647 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_648 = 648 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_649 = 649 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_650 = 650 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_651 = 651 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_652 = 652 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_653 = 653 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_654 = 654 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_655 = 655 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_656 = 656 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_657 = 657 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_658 = 658 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_659 = 659 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_660 = 660 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_661 = 661 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_662 = 662 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_663 = 663 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_664 = 664 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_665 = 665 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_666 = 666 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_667 = 667 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_668 = 668 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_669 = 669 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_670 = 670 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_671 = 671 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_672 = 672 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_673 = 673 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_674 = 674 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_675 = 675 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_676 = 676 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_677 = 677 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_678 = 678 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_679 = 679 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_680 = 680 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_681 = 681 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_682 = 682 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_683 = 683 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_684 = 684 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_685 = 685 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_686 = 686 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_687 = 687 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_688 = 688 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_689 = 689 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_690 = 690 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_691 = 691 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_692 = 692 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_693 = 693 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_694 = 694 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_695 = 695 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_696 = 696 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_697 = 697 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_698 = 698 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_699 = 699 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_700 = 700 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_701 = 701 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_702 = 702 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_703 = 703 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_704 = 704 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_705 = 705 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_706 = 706 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_707 = 707 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_708 = 708 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_709 = 709 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_710 = 710 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_711 = 711 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_712 = 712 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_713 = 713 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_714 = 714 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_715 = 715 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_716 = 716 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_717 = 717 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_718 = 718 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_719 = 719 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_720 = 720 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_721 = 721 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_722 = 722 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_723 = 723 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_724 = 724 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_725 = 725 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_726 = 726 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_727 = 727 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_728 = 728 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_729 = 729 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_730 = 730 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_731 = 731 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_732 = 732 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_733 = 733 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_734 = 734 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_735 = 735 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_736 = 736 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_737 = 737 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_738 = 738 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_739 = 739 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_740 = 740 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_741 = 741 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_742 = 742 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_743 = 743 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_744 = 744 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_745 = 745 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_746 = 746 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_747 = 747 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_748 = 748 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_749 = 749 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_750 = 750 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_751 = 751 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_752 = 752 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_753 = 753 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_754 = 754 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_755 = 755 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_756 = 756 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_757 = 757 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_758 = 758 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_759 = 759 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_760 = 760 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_761 = 761 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_762 = 762 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_763 = 763 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_764 = 764 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_765 = 765 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_766 = 766 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_767 = 767 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_768 = 768 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_769 = 769 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_770 = 770 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_771 = 771 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_772 = 772 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_773 = 773 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_774 = 774 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_775 = 775 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_776 = 776 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_777 = 777 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_778 = 778 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_779 = 779 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_780 = 780 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_781 = 781 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_782 = 782 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_783 = 783 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_784 = 784 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_785 = 785 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_786 = 786 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_787 = 787 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_788 = 788 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_789 = 789 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_790 = 790 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_791 = 791 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_792 = 792 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_793 = 793 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_794 = 794 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_795 = 795 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_796 = 796 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_797 = 797 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_798 = 798 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_799 = 799 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_800 = 800 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_801 = 801 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_802 = 802 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_803 = 803 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_804 = 804 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_805 = 805 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_806 = 806 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_807 = 807 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_808 = 808 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_809 = 809 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_810 = 810 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_811 = 811 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_812 = 812 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_813 = 813 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_814 = 814 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_815 = 815 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_816 = 816 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_817 = 817 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_818 = 818 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_819 = 819 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_820 = 820 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_821 = 821 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_822 = 822 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_823 = 823 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_824 = 824 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_825 = 825 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_826 = 826 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_827 = 827 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_828 = 828 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_829 = 829 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_830 = 830 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_831 = 831 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_832 = 832 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_833 = 833 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_834 = 834 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_835 = 835 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_836 = 836 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_837 = 837 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_838 = 838 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_839 = 839 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_840 = 840 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_841 = 841 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_842 = 842 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_843 = 843 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_844 = 844 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_845 = 845 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_846 = 846 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_847 = 847 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_848 = 848 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_849 = 849 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_850 = 850 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_851 = 851 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_852 = 852 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_853 = 853 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_854 = 854 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_855 = 855 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_856 = 856 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_857 = 857 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_858 = 858 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_859 = 859 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_860 = 860 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_861 = 861 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_862 = 862 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_863 = 863 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_864 = 864 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_865 = 865 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_866 = 866 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_867 = 867 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_868 = 868 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_869 = 869 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_870 = 870 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_871 = 871 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_872 = 872 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_873 = 873 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_874 = 874 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_875 = 875 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_876 = 876 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_877 = 877 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_878 = 878 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_879 = 879 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_880 = 880 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_881 = 881 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_882 = 882 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_883 = 883 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_884 = 884 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_885 = 885 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_886 = 886 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_887 = 887 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_888 = 888 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_889 = 889 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_890 = 890 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_891 = 891 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_892 = 892 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_893 = 893 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_894 = 894 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_895 = 895 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_896 = 896 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_897 = 897 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_898 = 898 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_899 = 899 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_900 = 900 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_901 = 901 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_902 = 902 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_903 = 903 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_904 = 904 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_905 = 905 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_906 = 906 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_907 = 907 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_908 = 908 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_909 = 909 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_910 = 910 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_911 = 911 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_912 = 912 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_913 = 913 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_914 = 914 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_915 = 915 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_916 = 916 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_917 = 917 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_918 = 918 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_919 = 919 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_920 = 920 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_921 = 921 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_922 = 922 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_923 = 923 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_924 = 924 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_925 = 925 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_926 = 926 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_927 = 927 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_928 = 928 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_929 = 929 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_930 = 930 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_931 = 931 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_932 = 932 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_933 = 933 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_934 = 934 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_935 = 935 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_936 = 936 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_937 = 937 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_938 = 938 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_939 = 939 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_940 = 940 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_941 = 941 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_942 = 942 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_943 = 943 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_944 = 944 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_945 = 945 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_946 = 946 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_947 = 947 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_948 = 948 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_949 = 949 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_950 = 950 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_951 = 951 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_952 = 952 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_953 = 953 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_954 = 954 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_955 = 955 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_956 = 956 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_957 = 957 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_958 = 958 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_959 = 959 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_960 = 960 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_961 = 961 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_962 = 962 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_963 = 963 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_964 = 964 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_965 = 965 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_966 = 966 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_967 = 967 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_968 = 968 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_969 = 969 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_970 = 970 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_971 = 971 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_972 = 972 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_973 = 973 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_974 = 974 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_975 = 975 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_976 = 976 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_977 = 977 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_978 = 978 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_979 = 979 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_980 = 980 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_981 = 981 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_982 = 982 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_983 = 983 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_984 = 984 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_985 = 985 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_986 = 986 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_987 = 987 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_988 = 988 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_989 = 989 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_990 = 990 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_991 = 991 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_992 = 992 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_993 = 993 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_994 = 994 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_995 = 995 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_996 = 996 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_997 = 997 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_998 = 998 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_999 = 999 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+ optional string long_field_name_is_looooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong_1000 = 1000 [default="long default value is also loooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooong"];
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import.proto
new file mode 100644
index 0000000000..8d03e3888b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import.proto
@@ -0,0 +1,73 @@
+// 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.
+//
+// A proto file which is imported by unittest.proto to test importing.
+
+syntax = "proto2";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In test_util.h we do
+// "using namespace unittest_import = protobuf_unittest_import".
+package protobuf_unittest_import;
+
+option optimize_for = SPEED;
+option cc_enable_arenas = true;
+
+// Exercise the java_package option.
+option java_package = "com.google.protobuf.test";
+
+// Do not set a java_outer_classname here to verify that Proto2 works without
+// one.
+
+// Test public import
+import public "google/protobuf/unittest_import_public.proto";
+
+message ImportMessage {
+ optional int32 d = 1;
+}
+
+enum ImportEnum {
+ IMPORT_FOO = 7;
+ IMPORT_BAR = 8;
+ IMPORT_BAZ = 9;
+}
+
+
+// To use an enum in a map, it must has the first value as 0.
+enum ImportEnumForMap {
+ UNKNOWN = 0;
+ FOO = 1;
+ BAR = 2;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_lite.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_lite.proto
new file mode 100644
index 0000000000..a7afa45233
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_lite.proto
@@ -0,0 +1,52 @@
+// 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)
+//
+// This is like unittest_import.proto but with optimize_for = LITE_RUNTIME.
+
+syntax = "proto2";
+package protobuf_unittest_import;
+
+option optimize_for = LITE_RUNTIME;
+
+option java_package = "com.google.protobuf";
+
+import public "google/protobuf/unittest_import_public_lite.proto";
+
+message ImportMessageLite {
+ optional int32 d = 1;
+}
+
+enum ImportEnumLite {
+ IMPORT_LITE_FOO = 7;
+ IMPORT_LITE_BAR = 8;
+ IMPORT_LITE_BAZ = 9;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_proto3.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_proto3.proto
new file mode 100644
index 0000000000..59673eaf9d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_proto3.proto
@@ -0,0 +1,68 @@
+// 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.
+//
+// A proto file which is imported by unittest_proto3.proto to test importing.
+
+syntax = "proto3";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In test_util.h we do
+// "using namespace unittest_import = protobuf_unittest_import".
+package protobuf_unittest_import;
+
+option optimize_for = SPEED;
+option cc_enable_arenas = true;
+
+// Exercise the java_package option.
+option java_package = "com.google.protobuf.test";
+option csharp_namespace = "Google.Protobuf.TestProtos";
+
+// Do not set a java_outer_classname here to verify that Proto2 works without
+// one.
+
+// Test public import
+import public "google/protobuf/unittest_import_public_proto3.proto";
+
+message ImportMessage {
+ int32 d = 1;
+}
+
+enum ImportEnum {
+ IMPORT_ENUM_UNSPECIFIED = 0;
+ IMPORT_FOO = 7;
+ IMPORT_BAR = 8;
+ IMPORT_BAZ = 9;
+}
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public.proto
new file mode 100644
index 0000000000..ffaf773698
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public.proto
@@ -0,0 +1,41 @@
+// 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: liujisi@google.com (Pherl Liu)
+
+syntax = "proto2";
+
+package protobuf_unittest_import;
+
+option java_package = "com.google.protobuf.test";
+
+message PublicImportMessage {
+ optional int32 e = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_lite.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_lite.proto
new file mode 100644
index 0000000000..33549c2279
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_lite.proto
@@ -0,0 +1,43 @@
+// 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: liujisi@google.com (Pherl Liu)
+
+syntax = "proto2";
+
+package protobuf_unittest_import;
+
+option optimize_for = LITE_RUNTIME;
+
+option java_package = "com.google.protobuf";
+
+message PublicImportMessageLite {
+ optional int32 e = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_proto3.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_proto3.proto
new file mode 100644
index 0000000000..d6f11e28bd
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_import_public_proto3.proto
@@ -0,0 +1,42 @@
+// 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: liujisi@google.com (Pherl Liu)
+
+syntax = "proto3";
+
+package protobuf_unittest_import;
+
+option java_package = "com.google.protobuf.test";
+option csharp_namespace = "Google.Protobuf.TestProtos";
+
+message PublicImportMessage {
+ int32 e = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite.proto
new file mode 100644
index 0000000000..878ec7c1d2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite.proto
@@ -0,0 +1,407 @@
+// 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)
+//
+// This is like unittest.proto but with optimize_for = LITE_RUNTIME.
+
+syntax = "proto2";
+package protobuf_unittest;
+
+import "google/protobuf/unittest_import_lite.proto";
+
+option optimize_for = LITE_RUNTIME;
+
+option java_package = "com.google.protobuf";
+
+// Same as TestAllTypes but with the lite runtime.
+message TestAllTypesLite {
+
+ message NestedMessage {
+ optional int32 bb = 1;
+ optional int64 cc = 2;
+ }
+
+ enum NestedEnum {
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ }
+
+ // Singular
+ optional int32 optional_int32 = 1;
+ optional int64 optional_int64 = 2;
+ optional uint32 optional_uint32 = 3;
+ optional uint64 optional_uint64 = 4;
+ optional sint32 optional_sint32 = 5;
+ optional sint64 optional_sint64 = 6;
+ optional fixed32 optional_fixed32 = 7;
+ optional fixed64 optional_fixed64 = 8;
+ optional sfixed32 optional_sfixed32 = 9;
+ optional sfixed64 optional_sfixed64 = 10;
+ optional float optional_float = 11;
+ optional double optional_double = 12;
+ optional bool optional_bool = 13;
+ optional string optional_string = 14;
+ optional bytes optional_bytes = 15;
+
+ optional group OptionalGroup = 16 {
+ optional int32 a = 17;
+ }
+
+ optional NestedMessage optional_nested_message = 18;
+ optional ForeignMessageLite optional_foreign_message = 19;
+ optional protobuf_unittest_import.ImportMessageLite
+ optional_import_message = 20;
+
+ optional NestedEnum optional_nested_enum = 21;
+ optional ForeignEnumLite optional_foreign_enum = 22;
+ optional protobuf_unittest_import.ImportEnumLite optional_import_enum = 23;
+
+ optional string optional_string_piece = 24 [ctype=STRING_PIECE];
+ optional string optional_cord = 25 [ctype=CORD];
+
+ // Defined in unittest_import_public.proto
+ optional protobuf_unittest_import.PublicImportMessageLite
+ optional_public_import_message = 26;
+
+ optional NestedMessage optional_lazy_message = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ repeated group RepeatedGroup = 46 {
+ optional int32 a = 47;
+ }
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessageLite repeated_foreign_message = 49;
+ repeated protobuf_unittest_import.ImportMessageLite
+ repeated_import_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnumLite repeated_foreign_enum = 52;
+ repeated protobuf_unittest_import.ImportEnumLite repeated_import_enum = 53;
+
+ repeated string repeated_string_piece = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord = 55 [ctype=CORD];
+
+ repeated NestedMessage repeated_lazy_message = 57 [lazy=true];
+
+ // Singular with defaults
+ optional int32 default_int32 = 61 [default = 41 ];
+ optional int64 default_int64 = 62 [default = 42 ];
+ optional uint32 default_uint32 = 63 [default = 43 ];
+ optional uint64 default_uint64 = 64 [default = 44 ];
+ optional sint32 default_sint32 = 65 [default = -45 ];
+ optional sint64 default_sint64 = 66 [default = 46 ];
+ optional fixed32 default_fixed32 = 67 [default = 47 ];
+ optional fixed64 default_fixed64 = 68 [default = 48 ];
+ optional sfixed32 default_sfixed32 = 69 [default = 49 ];
+ optional sfixed64 default_sfixed64 = 70 [default = -50 ];
+ optional float default_float = 71 [default = 51.5 ];
+ optional double default_double = 72 [default = 52e3 ];
+ optional bool default_bool = 73 [default = true ];
+ optional string default_string = 74 [default = "hello"];
+ optional bytes default_bytes = 75 [default = "world"];
+
+ optional NestedEnum default_nested_enum = 81 [default = BAR];
+ optional ForeignEnumLite default_foreign_enum = 82
+ [default = FOREIGN_LITE_BAR];
+ optional protobuf_unittest_import.ImportEnumLite
+ default_import_enum = 83 [default = IMPORT_LITE_BAR];
+
+ optional string default_string_piece = 84 [ctype=STRING_PIECE,default="abc"];
+ optional string default_cord = 85 [ctype=CORD,default="123"];
+
+ // For oneof test
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ bytes oneof_bytes = 114;
+ NestedMessage oneof_lazy_nested_message = 115 [lazy = true];
+ }
+}
+
+message ForeignMessageLite {
+ optional int32 c = 1;
+}
+
+enum ForeignEnumLite {
+ FOREIGN_LITE_FOO = 4;
+ FOREIGN_LITE_BAR = 5;
+ FOREIGN_LITE_BAZ = 6;
+}
+
+message TestPackedTypesLite {
+ repeated int32 packed_int32 = 90 [packed = true];
+ repeated int64 packed_int64 = 91 [packed = true];
+ repeated uint32 packed_uint32 = 92 [packed = true];
+ repeated uint64 packed_uint64 = 93 [packed = true];
+ repeated sint32 packed_sint32 = 94 [packed = true];
+ repeated sint64 packed_sint64 = 95 [packed = true];
+ repeated fixed32 packed_fixed32 = 96 [packed = true];
+ repeated fixed64 packed_fixed64 = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32 = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64 = 99 [packed = true];
+ repeated float packed_float = 100 [packed = true];
+ repeated double packed_double = 101 [packed = true];
+ repeated bool packed_bool = 102 [packed = true];
+ repeated ForeignEnumLite packed_enum = 103 [packed = true];
+}
+
+message TestAllExtensionsLite {
+ extensions 1 to max;
+}
+
+extend TestAllExtensionsLite {
+ // Singular
+ optional int32 optional_int32_extension_lite = 1;
+ optional int64 optional_int64_extension_lite = 2;
+ optional uint32 optional_uint32_extension_lite = 3;
+ optional uint64 optional_uint64_extension_lite = 4;
+ optional sint32 optional_sint32_extension_lite = 5;
+ optional sint64 optional_sint64_extension_lite = 6;
+ optional fixed32 optional_fixed32_extension_lite = 7;
+ optional fixed64 optional_fixed64_extension_lite = 8;
+ optional sfixed32 optional_sfixed32_extension_lite = 9;
+ optional sfixed64 optional_sfixed64_extension_lite = 10;
+ optional float optional_float_extension_lite = 11;
+ optional double optional_double_extension_lite = 12;
+ optional bool optional_bool_extension_lite = 13;
+ optional string optional_string_extension_lite = 14;
+ optional bytes optional_bytes_extension_lite = 15;
+
+ optional group OptionalGroup_extension_lite = 16 {
+ optional int32 a = 17;
+ }
+
+ optional TestAllTypesLite.NestedMessage optional_nested_message_extension_lite
+ = 18;
+ optional ForeignMessageLite optional_foreign_message_extension_lite = 19;
+ optional protobuf_unittest_import.ImportMessageLite
+ optional_import_message_extension_lite = 20;
+
+ optional TestAllTypesLite.NestedEnum optional_nested_enum_extension_lite = 21;
+ optional ForeignEnumLite optional_foreign_enum_extension_lite = 22;
+ optional protobuf_unittest_import.ImportEnumLite
+ optional_import_enum_extension_lite = 23;
+
+ optional string optional_string_piece_extension_lite = 24
+ [ctype=STRING_PIECE];
+ optional string optional_cord_extension_lite = 25 [ctype=CORD];
+
+ optional protobuf_unittest_import.PublicImportMessageLite
+ optional_public_import_message_extension_lite = 26;
+
+ optional TestAllTypesLite.NestedMessage
+ optional_lazy_message_extension_lite = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32_extension_lite = 31;
+ repeated int64 repeated_int64_extension_lite = 32;
+ repeated uint32 repeated_uint32_extension_lite = 33;
+ repeated uint64 repeated_uint64_extension_lite = 34;
+ repeated sint32 repeated_sint32_extension_lite = 35;
+ repeated sint64 repeated_sint64_extension_lite = 36;
+ repeated fixed32 repeated_fixed32_extension_lite = 37;
+ repeated fixed64 repeated_fixed64_extension_lite = 38;
+ repeated sfixed32 repeated_sfixed32_extension_lite = 39;
+ repeated sfixed64 repeated_sfixed64_extension_lite = 40;
+ repeated float repeated_float_extension_lite = 41;
+ repeated double repeated_double_extension_lite = 42;
+ repeated bool repeated_bool_extension_lite = 43;
+ repeated string repeated_string_extension_lite = 44;
+ repeated bytes repeated_bytes_extension_lite = 45;
+
+ repeated group RepeatedGroup_extension_lite = 46 {
+ optional int32 a = 47;
+ }
+
+ repeated TestAllTypesLite.NestedMessage repeated_nested_message_extension_lite
+ = 48;
+ repeated ForeignMessageLite repeated_foreign_message_extension_lite = 49;
+ repeated protobuf_unittest_import.ImportMessageLite
+ repeated_import_message_extension_lite = 50;
+
+ repeated TestAllTypesLite.NestedEnum repeated_nested_enum_extension_lite = 51;
+ repeated ForeignEnumLite repeated_foreign_enum_extension_lite = 52;
+ repeated protobuf_unittest_import.ImportEnumLite
+ repeated_import_enum_extension_lite = 53;
+
+ repeated string repeated_string_piece_extension_lite = 54
+ [ctype=STRING_PIECE];
+ repeated string repeated_cord_extension_lite = 55 [ctype=CORD];
+
+ repeated TestAllTypesLite.NestedMessage
+ repeated_lazy_message_extension_lite = 57 [lazy=true];
+
+ // Singular with defaults
+ optional int32 default_int32_extension_lite = 61 [default = 41 ];
+ optional int64 default_int64_extension_lite = 62 [default = 42 ];
+ optional uint32 default_uint32_extension_lite = 63 [default = 43 ];
+ optional uint64 default_uint64_extension_lite = 64 [default = 44 ];
+ optional sint32 default_sint32_extension_lite = 65 [default = -45 ];
+ optional sint64 default_sint64_extension_lite = 66 [default = 46 ];
+ optional fixed32 default_fixed32_extension_lite = 67 [default = 47 ];
+ optional fixed64 default_fixed64_extension_lite = 68 [default = 48 ];
+ optional sfixed32 default_sfixed32_extension_lite = 69 [default = 49 ];
+ optional sfixed64 default_sfixed64_extension_lite = 70 [default = -50 ];
+ optional float default_float_extension_lite = 71 [default = 51.5 ];
+ optional double default_double_extension_lite = 72 [default = 52e3 ];
+ optional bool default_bool_extension_lite = 73 [default = true ];
+ optional string default_string_extension_lite = 74 [default = "hello"];
+ optional bytes default_bytes_extension_lite = 75 [default = "world"];
+
+ optional TestAllTypesLite.NestedEnum
+ default_nested_enum_extension_lite = 81 [default = BAR];
+ optional ForeignEnumLite
+ default_foreign_enum_extension_lite = 82 [default = FOREIGN_LITE_BAR];
+ optional protobuf_unittest_import.ImportEnumLite
+ default_import_enum_extension_lite = 83 [default = IMPORT_LITE_BAR];
+
+ optional string default_string_piece_extension_lite = 84 [ctype=STRING_PIECE,
+ default="abc"];
+ optional string default_cord_extension_lite = 85 [ctype=CORD, default="123"];
+
+ // For oneof test
+ optional uint32 oneof_uint32_extension_lite = 111;
+ optional TestAllTypesLite.NestedMessage oneof_nested_message_extension_lite = 112;
+ optional string oneof_string_extension_lite = 113;
+ optional bytes oneof_bytes_extension_lite = 114;
+}
+
+message TestPackedExtensionsLite {
+ extensions 1 to max;
+}
+
+extend TestPackedExtensionsLite {
+ repeated int32 packed_int32_extension_lite = 90 [packed = true];
+ repeated int64 packed_int64_extension_lite = 91 [packed = true];
+ repeated uint32 packed_uint32_extension_lite = 92 [packed = true];
+ repeated uint64 packed_uint64_extension_lite = 93 [packed = true];
+ repeated sint32 packed_sint32_extension_lite = 94 [packed = true];
+ repeated sint64 packed_sint64_extension_lite = 95 [packed = true];
+ repeated fixed32 packed_fixed32_extension_lite = 96 [packed = true];
+ repeated fixed64 packed_fixed64_extension_lite = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32_extension_lite = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64_extension_lite = 99 [packed = true];
+ repeated float packed_float_extension_lite = 100 [packed = true];
+ repeated double packed_double_extension_lite = 101 [packed = true];
+ repeated bool packed_bool_extension_lite = 102 [packed = true];
+ repeated ForeignEnumLite packed_enum_extension_lite = 103 [packed = true];
+}
+
+message TestNestedExtensionLite {
+ extend TestAllExtensionsLite {
+ optional int32 nested_extension = 12345;
+ }
+}
+
+// Test that deprecated fields work. We only verify that they compile (at one
+// point this failed).
+message TestDeprecatedLite {
+ optional int32 deprecated_field = 1 [deprecated = true];
+}
+
+// See the comments of the same type in unittest.proto.
+message TestParsingMergeLite {
+ message RepeatedFieldsGenerator {
+ repeated TestAllTypesLite field1 = 1;
+ repeated TestAllTypesLite field2 = 2;
+ repeated TestAllTypesLite field3 = 3;
+ repeated group Group1 = 10 {
+ optional TestAllTypesLite field1 = 11;
+ }
+ repeated group Group2 = 20 {
+ optional TestAllTypesLite field1 = 21;
+ }
+ repeated TestAllTypesLite ext1 = 1000;
+ repeated TestAllTypesLite ext2 = 1001;
+ }
+ required TestAllTypesLite required_all_types = 1;
+ optional TestAllTypesLite optional_all_types = 2;
+ repeated TestAllTypesLite repeated_all_types = 3;
+ optional group OptionalGroup = 10 {
+ optional TestAllTypesLite optional_group_all_types = 11;
+ }
+ repeated group RepeatedGroup = 20 {
+ optional TestAllTypesLite repeated_group_all_types = 21;
+ }
+ extensions 1000 to max;
+ extend TestParsingMergeLite {
+ optional TestAllTypesLite optional_ext = 1000;
+ repeated TestAllTypesLite repeated_ext = 1001;
+ }
+}
+
+// TestEmptyMessageLite is used to test unknown fields support in lite mode.
+message TestEmptyMessageLite{
+}
+
+// Like above, but declare all field numbers as potential extensions. No
+// actual extensions should ever be defined for this type.
+message TestEmptyMessageWithExtensionsLite {
+ extensions 1 to max;
+}
+
+enum V1EnumLite {
+ V1_FIRST = 1;
+}
+
+enum V2EnumLite {
+ V2_FIRST = 1;
+ V2_SECOND = 2;
+}
+
+message V1MessageLite {
+ required int32 int_field = 1;
+ optional V1EnumLite enum_field = 2 [ default = V1_FIRST ];
+}
+
+message V2MessageLite {
+ required int32 int_field = 1;
+ optional V2EnumLite enum_field = 2 [ default = V2_FIRST ];
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite_imports_nonlite.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite_imports_nonlite.proto
new file mode 100644
index 0000000000..132d6a82d2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_lite_imports_nonlite.proto
@@ -0,0 +1,44 @@
+// 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)
+//
+// Tests that a "lite" message can import a regular message.
+
+syntax = "proto2";
+package protobuf_unittest;
+
+import "google/protobuf/unittest.proto";
+
+option optimize_for = LITE_RUNTIME;
+
+message TestLiteImportsNonlite {
+ optional TestAllTypes message = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset.proto
new file mode 100644
index 0000000000..49d9adad0b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset.proto
@@ -0,0 +1,82 @@
+// 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 is similar to unittest_mset_wire_format.proto, but does not
+// have a TestMessageSet, so it can be downgraded to proto1.
+
+syntax = "proto2";
+
+import "google/protobuf/unittest_mset_wire_format.proto";
+
+package protobuf_unittest;
+
+option cc_enable_arenas = true;
+option optimize_for = SPEED;
+
+message TestMessageSetContainer {
+ optional proto2_wireformat_unittest.TestMessageSet message_set = 1;
+}
+
+message TestMessageSetExtension1 {
+ extend proto2_wireformat_unittest.TestMessageSet {
+ optional TestMessageSetExtension1 message_set_extension = 1545008;
+ }
+ optional int32 i = 15;
+}
+
+message TestMessageSetExtension2 {
+ extend proto2_wireformat_unittest.TestMessageSet {
+ optional TestMessageSetExtension2 message_set_extension = 1547769;
+ }
+ optional string str = 25;
+}
+
+// This message was used to generate
+// //net/proto2/python/internal/testdata/message_set_message, but is commented
+// out since it must not actually exist in code, to simulate an "unknown"
+// extension.
+// message TestMessageSetUnknownExtension {
+// extend TestMessageSet {
+// optional TestMessageSetUnknownExtension message_set_extension = 56141421;
+// }
+// optional int64 a = 1;
+// }
+
+// MessageSet wire format is equivalent to this.
+message RawMessageSet {
+ repeated group Item = 1 {
+ required int32 type_id = 2;
+ required bytes message = 3;
+ }
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset_wire_format.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset_wire_format.proto
new file mode 100644
index 0000000000..04e4352e06
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_mset_wire_format.proto
@@ -0,0 +1,52 @@
+// 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 messages for testing message_set_wire_format.
+
+syntax = "proto2";
+package proto2_wireformat_unittest;
+
+option cc_enable_arenas = true;
+option optimize_for = SPEED;
+option csharp_namespace = "Google.ProtocolBuffers.TestProtos";
+
+// A message with message_set_wire_format.
+message TestMessageSet {
+ option message_set_wire_format = true;
+ extensions 4 to max;
+}
+
+message TestMessageSetWireFormatContainer {
+ optional TestMessageSet message_set = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena.proto
new file mode 100644
index 0000000000..41518df297
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena.proto
@@ -0,0 +1,202 @@
+// 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 proto file contains copies of TestAllTypes and friends, but with arena
+// support disabled in code generation. It allows us to test the performance
+// impact against baseline (non-arena) google.protobuf.
+
+syntax = "proto2";
+
+// Some generic_services option(s) added automatically.
+// See: http://go/proto2-generic-services-default
+option cc_generic_services = true; // auto-added
+option java_generic_services = true; // auto-added
+option py_generic_services = true; // auto-added
+option cc_enable_arenas = false;
+option objc_class_prefix = "NOARN";
+
+import "google/protobuf/unittest_import.proto";
+import "google/protobuf/unittest_arena.proto";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In test_util.h we do "using namespace unittest = protobuf_unittest".
+package protobuf_unittest_no_arena;
+
+// Protos optimized for SPEED use a strict superset of the generated code
+// of equivalent ones optimized for CODE_SIZE, so we should optimize all our
+// tests for speed unless explicitly testing code size optimization.
+option optimize_for = SPEED;
+
+option java_outer_classname = "UnittestProto";
+
+// This proto includes every type of field in both singular and repeated
+// forms.
+message TestAllTypes {
+ message NestedMessage {
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ optional int32 bb = 1;
+ }
+
+ enum NestedEnum {
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ NEG = -1; // Intentionally negative.
+ }
+
+ // Singular
+ optional int32 optional_int32 = 1;
+ optional int64 optional_int64 = 2;
+ optional uint32 optional_uint32 = 3;
+ optional uint64 optional_uint64 = 4;
+ optional sint32 optional_sint32 = 5;
+ optional sint64 optional_sint64 = 6;
+ optional fixed32 optional_fixed32 = 7;
+ optional fixed64 optional_fixed64 = 8;
+ optional sfixed32 optional_sfixed32 = 9;
+ optional sfixed64 optional_sfixed64 = 10;
+ optional float optional_float = 11;
+ optional double optional_double = 12;
+ optional bool optional_bool = 13;
+ optional string optional_string = 14;
+ optional bytes optional_bytes = 15;
+
+ optional group OptionalGroup = 16 {
+ optional int32 a = 17;
+ }
+
+ optional NestedMessage optional_nested_message = 18;
+ optional ForeignMessage optional_foreign_message = 19;
+ optional protobuf_unittest_import.ImportMessage optional_import_message = 20;
+
+ optional NestedEnum optional_nested_enum = 21;
+ optional ForeignEnum optional_foreign_enum = 22;
+ optional protobuf_unittest_import.ImportEnum optional_import_enum = 23;
+
+ optional string optional_string_piece = 24 [ctype=STRING_PIECE];
+ optional string optional_cord = 25 [ctype=CORD];
+
+ // Defined in unittest_import_public.proto
+ optional protobuf_unittest_import.PublicImportMessage
+ optional_public_import_message = 26;
+
+ optional NestedMessage optional_message = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ repeated group RepeatedGroup = 46 {
+ optional int32 a = 47;
+ }
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessage repeated_foreign_message = 49;
+ repeated protobuf_unittest_import.ImportMessage repeated_import_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnum repeated_foreign_enum = 52;
+ repeated protobuf_unittest_import.ImportEnum repeated_import_enum = 53;
+
+ repeated string repeated_string_piece = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord = 55 [ctype=CORD];
+
+ repeated NestedMessage repeated_lazy_message = 57 [lazy=true];
+
+ // Singular with defaults
+ optional int32 default_int32 = 61 [default = 41 ];
+ optional int64 default_int64 = 62 [default = 42 ];
+ optional uint32 default_uint32 = 63 [default = 43 ];
+ optional uint64 default_uint64 = 64 [default = 44 ];
+ optional sint32 default_sint32 = 65 [default = -45 ];
+ optional sint64 default_sint64 = 66 [default = 46 ];
+ optional fixed32 default_fixed32 = 67 [default = 47 ];
+ optional fixed64 default_fixed64 = 68 [default = 48 ];
+ optional sfixed32 default_sfixed32 = 69 [default = 49 ];
+ optional sfixed64 default_sfixed64 = 70 [default = -50 ];
+ optional float default_float = 71 [default = 51.5 ];
+ optional double default_double = 72 [default = 52e3 ];
+ optional bool default_bool = 73 [default = true ];
+ optional string default_string = 74 [default = "hello"];
+ optional bytes default_bytes = 75 [default = "world"];
+
+ optional NestedEnum default_nested_enum = 81 [default = BAR ];
+ optional ForeignEnum default_foreign_enum = 82 [default = FOREIGN_BAR];
+ optional protobuf_unittest_import.ImportEnum
+ default_import_enum = 83 [default = IMPORT_BAR];
+
+ optional string default_string_piece = 84 [ctype=STRING_PIECE,default="abc"];
+ optional string default_cord = 85 [ctype=CORD,default="123"];
+
+ // For oneof test
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ bytes oneof_bytes = 114;
+ NestedMessage lazy_oneof_nested_message = 115 [lazy=true];
+ }
+}
+
+// Define these after TestAllTypes to make sure the compiler can handle
+// that.
+message ForeignMessage {
+ optional int32 c = 1;
+}
+
+enum ForeignEnum {
+ FOREIGN_FOO = 4;
+ FOREIGN_BAR = 5;
+ FOREIGN_BAZ = 6;
+}
+
+message TestNoArenaMessage {
+ optional proto2_arena_unittest.ArenaMessage arena_message = 1;
+};
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_import.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_import.proto
new file mode 100644
index 0000000000..072af49e3c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_import.proto
@@ -0,0 +1,37 @@
+// 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.
+
+syntax = "proto2";
+
+package proto2_arena_unittest;
+
+message ImportNoArenaNestedMessage {
+ optional int32 d = 1;
+};
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_lite.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_lite.proto
new file mode 100644
index 0000000000..34c7b7ce99
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_arena_lite.proto
@@ -0,0 +1,42 @@
+// 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.
+
+syntax = "proto2";
+
+option optimize_for = LITE_RUNTIME;
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In test_util.h we do "using namespace unittest = protobuf_unittest".
+package protobuf_unittest_no_arena;
+
+message ForeignMessageLite {
+ optional int32 c = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_field_presence.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_field_presence.proto
new file mode 100644
index 0000000000..994afff42d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_field_presence.proto
@@ -0,0 +1,138 @@
+// 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.
+
+// A proto file used to test a message type with no explicit field presence.
+
+syntax = "proto3";
+
+// We want to test embedded proto2 messages, so include some proto2 types.
+import "google/protobuf/unittest.proto";
+
+package proto2_nofieldpresence_unittest;
+
+// This proto includes every type of field in both singular and repeated
+// forms.
+message TestAllTypes {
+ message NestedMessage {
+ int32 bb = 1;
+ }
+
+ enum NestedEnum {
+ FOO = 0;
+ BAR = 1;
+ BAZ = 2;
+ }
+
+ // Singular
+ // TODO: remove 'optional' labels as soon as CL 69188077 is LGTM'd to make
+ // 'optional' optional.
+ int32 optional_int32 = 1;
+ int64 optional_int64 = 2;
+ uint32 optional_uint32 = 3;
+ uint64 optional_uint64 = 4;
+ sint32 optional_sint32 = 5;
+ sint64 optional_sint64 = 6;
+ fixed32 optional_fixed32 = 7;
+ fixed64 optional_fixed64 = 8;
+ sfixed32 optional_sfixed32 = 9;
+ sfixed64 optional_sfixed64 = 10;
+ float optional_float = 11;
+ double optional_double = 12;
+ bool optional_bool = 13;
+ string optional_string = 14;
+ bytes optional_bytes = 15;
+
+ NestedMessage optional_nested_message = 18;
+ ForeignMessage optional_foreign_message = 19;
+ protobuf_unittest.TestAllTypes optional_proto2_message = 20;
+
+ NestedEnum optional_nested_enum = 21;
+ ForeignEnum optional_foreign_enum = 22;
+ // N.B.: proto2-enum-type fields not allowed, because their default values
+ // might not be zero.
+ //optional protobuf_unittest.ForeignEnum optional_proto2_enum = 23;
+
+ string optional_string_piece = 24 [ctype=STRING_PIECE];
+ string optional_cord = 25 [ctype=CORD];
+
+ NestedMessage optional_lazy_message = 30 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessage repeated_foreign_message = 49;
+ repeated protobuf_unittest.TestAllTypes repeated_proto2_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnum repeated_foreign_enum = 52;
+
+ repeated string repeated_string_piece = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord = 55 [ctype=CORD];
+
+ repeated NestedMessage repeated_lazy_message = 57 [lazy=true];
+
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ NestedEnum oneof_enum = 114;
+ }
+}
+
+message TestProto2Required {
+ protobuf_unittest.TestRequired proto2 = 1;
+}
+
+// Define these after TestAllTypes to make sure the compiler can handle
+// that.
+message ForeignMessage {
+ int32 c = 1;
+}
+
+enum ForeignEnum {
+ FOREIGN_FOO = 0;
+ FOREIGN_BAR = 1;
+ FOREIGN_BAZ = 2;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_generic_services.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_generic_services.proto
new file mode 100644
index 0000000000..8fc7713c9e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_no_generic_services.proto
@@ -0,0 +1,54 @@
+// 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)
+
+syntax = "proto2";
+package google.protobuf.no_generic_services_test;
+
+
+// *_generic_services are false by default.
+
+message TestMessage {
+ optional int32 a = 1;
+ extensions 1000 to max;
+}
+
+enum TestEnum {
+ FOO = 1;
+}
+
+extend TestMessage {
+ optional int32 test_extension = 1000;
+}
+
+service TestService {
+ rpc Foo(TestMessage) returns(TestMessage);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_optimize_for.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_optimize_for.proto
new file mode 100644
index 0000000000..ee9cc7bd49
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_optimize_for.proto
@@ -0,0 +1,67 @@
+// 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.
+//
+// A proto file which uses optimize_for = CODE_SIZE.
+
+syntax = "proto2";
+import "google/protobuf/unittest.proto";
+
+package protobuf_unittest;
+
+option optimize_for = CODE_SIZE;
+
+message TestOptimizedForSize {
+ optional int32 i = 1;
+ optional ForeignMessage msg = 19;
+
+ extensions 1000 to max;
+
+ extend TestOptimizedForSize {
+ optional int32 test_extension = 1234;
+ optional TestRequiredOptimizedForSize test_extension2 = 1235;
+ }
+
+ oneof foo {
+ int32 integer_field = 2;
+ string string_field = 3;
+ }
+}
+
+message TestRequiredOptimizedForSize {
+ required int32 x = 1;
+}
+
+message TestOptionalOptimizedForSize {
+ optional TestRequiredOptimizedForSize o = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum.proto
new file mode 100644
index 0000000000..2f91332c9e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum.proto
@@ -0,0 +1,71 @@
+// 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.
+
+syntax = "proto3";
+
+package proto3_preserve_unknown_enum_unittest;
+option objc_class_prefix = "UnknownEnums";
+
+option csharp_namespace = "Google.Protobuf.TestProtos";
+
+enum MyEnum {
+ FOO = 0;
+ BAR = 1;
+ BAZ = 2;
+}
+
+enum MyEnumPlusExtra {
+ E_FOO = 0;
+ E_BAR = 1;
+ E_BAZ = 2;
+ E_EXTRA = 3;
+}
+
+message MyMessage {
+ MyEnum e = 1;
+ repeated MyEnum repeated_e = 2;
+ repeated MyEnum repeated_packed_e = 3 [packed=true];
+ repeated MyEnumPlusExtra repeated_packed_unexpected_e = 4; // not packed
+ oneof o {
+ MyEnum oneof_e_1 = 5;
+ MyEnum oneof_e_2 = 6;
+ }
+}
+
+message MyMessagePlusExtra {
+ MyEnumPlusExtra e = 1;
+ repeated MyEnumPlusExtra repeated_e = 2;
+ repeated MyEnumPlusExtra repeated_packed_e = 3 [packed=true];
+ repeated MyEnumPlusExtra repeated_packed_unexpected_e = 4 [packed=true];
+ oneof o {
+ MyEnumPlusExtra oneof_e_1 = 5;
+ MyEnumPlusExtra oneof_e_2 = 6;
+ }
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum2.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum2.proto
new file mode 100644
index 0000000000..adf42968aa
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_preserve_unknown_enum2.proto
@@ -0,0 +1,50 @@
+// 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.
+
+syntax = "proto2";
+
+package proto2_preserve_unknown_enum_unittest;
+
+enum MyEnum {
+ FOO = 0;
+ BAR = 1;
+ BAZ = 2;
+}
+
+message MyMessage {
+ optional MyEnum e = 1;
+ repeated MyEnum repeated_e = 2;
+ repeated MyEnum repeated_packed_e = 3 [packed=true];
+ repeated MyEnum repeated_packed_unexpected_e = 4; // not packed
+ oneof o {
+ MyEnum oneof_e_1 = 5;
+ MyEnum oneof_e_2 = 6;
+ }
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3.proto
new file mode 100644
index 0000000000..f59d217864
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3.proto
@@ -0,0 +1,388 @@
+// 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.
+//
+// A proto file we will use for unit testing.
+
+syntax = "proto3";
+
+// Some generic_services option(s) added automatically.
+// See: http://go/proto2-generic-services-default
+option cc_generic_services = true; // auto-added
+option java_generic_services = true; // auto-added
+option py_generic_services = true; // auto-added
+option cc_enable_arenas = true;
+option csharp_namespace = "Google.Protobuf.TestProtos";
+
+import "google/protobuf/unittest_import_proto3.proto";
+
+// We don't put this in a package within proto2 because we need to make sure
+// that the generated code doesn't depend on being in the proto2 namespace.
+// In test_util.h we do "using namespace unittest = protobuf_unittest".
+package protobuf_unittest;
+
+// Protos optimized for SPEED use a strict superset of the generated code
+// of equivalent ones optimized for CODE_SIZE, so we should optimize all our
+// tests for speed unless explicitly testing code size optimization.
+option optimize_for = SPEED;
+
+option java_outer_classname = "UnittestProto";
+
+// This proto includes every type of field in both singular and repeated
+// forms.
+message TestAllTypes {
+ message NestedMessage {
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ int32 bb = 1;
+ }
+
+ enum NestedEnum {
+ NESTED_ENUM_UNSPECIFIED = 0;
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ NEG = -1; // Intentionally negative.
+ }
+
+ // Singular
+ int32 single_int32 = 1;
+ int64 single_int64 = 2;
+ uint32 single_uint32 = 3;
+ uint64 single_uint64 = 4;
+ sint32 single_sint32 = 5;
+ sint64 single_sint64 = 6;
+ fixed32 single_fixed32 = 7;
+ fixed64 single_fixed64 = 8;
+ sfixed32 single_sfixed32 = 9;
+ sfixed64 single_sfixed64 = 10;
+ float single_float = 11;
+ double single_double = 12;
+ bool single_bool = 13;
+ string single_string = 14;
+ bytes single_bytes = 15;
+
+ NestedMessage single_nested_message = 18;
+ ForeignMessage single_foreign_message = 19;
+ protobuf_unittest_import.ImportMessage single_import_message = 20;
+
+ NestedEnum single_nested_enum = 21;
+ ForeignEnum single_foreign_enum = 22;
+ protobuf_unittest_import.ImportEnum single_import_enum = 23;
+
+ // Defined in unittest_import_public.proto
+ protobuf_unittest_import.PublicImportMessage
+ single_public_import_message = 26;
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessage repeated_foreign_message = 49;
+ repeated protobuf_unittest_import.ImportMessage repeated_import_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnum repeated_foreign_enum = 52;
+ repeated protobuf_unittest_import.ImportEnum repeated_import_enum = 53;
+ // Defined in unittest_import_public.proto
+ repeated protobuf_unittest_import.PublicImportMessage
+ repeated_public_import_message = 54;
+
+ // For oneof test
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ bytes oneof_bytes = 114;
+ }
+}
+
+// This proto includes a recusively nested message.
+message NestedTestAllTypes {
+ NestedTestAllTypes child = 1;
+ TestAllTypes payload = 2;
+ repeated NestedTestAllTypes repeated_child = 3;
+}
+
+message TestDeprecatedFields {
+ int32 deprecated_int32 = 1 [deprecated=true];
+}
+
+// Define these after TestAllTypes to make sure the compiler can handle
+// that.
+message ForeignMessage {
+ int32 c = 1;
+}
+
+enum ForeignEnum {
+ FOREIGN_UNSPECIFIED = 0;
+ FOREIGN_FOO = 4;
+ FOREIGN_BAR = 5;
+ FOREIGN_BAZ = 6;
+}
+
+message TestReservedFields {
+ reserved 2, 15, 9 to 11;
+ reserved "bar", "baz";
+}
+
+
+// Test that we can use NestedMessage from outside TestAllTypes.
+message TestForeignNested {
+ TestAllTypes.NestedMessage foreign_nested = 1;
+}
+
+// Test that really large tag numbers don't break anything.
+message TestReallyLargeTagNumber {
+ // The largest possible tag number is 2^28 - 1, since the wire format uses
+ // three bits to communicate wire type.
+ int32 a = 1;
+ int32 bb = 268435455;
+}
+
+message TestRecursiveMessage {
+ TestRecursiveMessage a = 1;
+ int32 i = 2;
+}
+
+// Test that mutual recursion works.
+message TestMutualRecursionA {
+ TestMutualRecursionB bb = 1;
+}
+
+message TestMutualRecursionB {
+ TestMutualRecursionA a = 1;
+ int32 optional_int32 = 2;
+}
+
+
+// Test an enum that has multiple values with the same number.
+enum TestEnumWithDupValue {
+ TEST_ENUM_WITH_DUP_VALUE_UNSPECIFIED = 0;
+ option allow_alias = true;
+
+ FOO1 = 1;
+ BAR1 = 2;
+ BAZ = 3;
+ FOO2 = 1;
+ BAR2 = 2;
+}
+
+// Test an enum with large, unordered values.
+enum TestSparseEnum {
+ TEST_SPARSE_ENUM_UNSPECIFIED = 0;
+ SPARSE_A = 123;
+ SPARSE_B = 62374;
+ SPARSE_C = 12589234;
+ SPARSE_D = -15;
+ SPARSE_E = -53452;
+ // In proto3, value 0 must be the first one specified
+ // SPARSE_F = 0;
+ SPARSE_G = 2;
+}
+
+// Test message with CamelCase field names. This violates Protocol Buffer
+// standard style.
+message TestCamelCaseFieldNames {
+ int32 PrimitiveField = 1;
+ string StringField = 2;
+ ForeignEnum EnumField = 3;
+ ForeignMessage MessageField = 4;
+
+ repeated int32 RepeatedPrimitiveField = 7;
+ repeated string RepeatedStringField = 8;
+ repeated ForeignEnum RepeatedEnumField = 9;
+ repeated ForeignMessage RepeatedMessageField = 10;
+}
+
+
+// We list fields out of order, to ensure that we're using field number and not
+// field index to determine serialization order.
+message TestFieldOrderings {
+ string my_string = 11;
+ int64 my_int = 1;
+ float my_float = 101;
+ message NestedMessage {
+ int64 oo = 2;
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ int32 bb = 1;
+ }
+
+ NestedMessage single_nested_message = 200;
+}
+
+message SparseEnumMessage {
+ TestSparseEnum sparse_enum = 1;
+}
+
+// Test String and Bytes: string is for valid UTF-8 strings
+message OneString {
+ string data = 1;
+}
+
+message MoreString {
+ repeated string data = 1;
+}
+
+message OneBytes {
+ bytes data = 1;
+}
+
+message MoreBytes {
+ bytes data = 1;
+}
+
+// Test int32, uint32, int64, uint64, and bool are all compatible
+message Int32Message {
+ int32 data = 1;
+}
+
+message Uint32Message {
+ uint32 data = 1;
+}
+
+message Int64Message {
+ int64 data = 1;
+}
+
+message Uint64Message {
+ uint64 data = 1;
+}
+
+message BoolMessage {
+ bool data = 1;
+}
+
+// Test oneofs.
+message TestOneof {
+ oneof foo {
+ int32 foo_int = 1;
+ string foo_string = 2;
+ TestAllTypes foo_message = 3;
+ }
+}
+
+// Test messages for packed fields
+
+message TestPackedTypes {
+ repeated int32 packed_int32 = 90 [packed = true];
+ repeated int64 packed_int64 = 91 [packed = true];
+ repeated uint32 packed_uint32 = 92 [packed = true];
+ repeated uint64 packed_uint64 = 93 [packed = true];
+ repeated sint32 packed_sint32 = 94 [packed = true];
+ repeated sint64 packed_sint64 = 95 [packed = true];
+ repeated fixed32 packed_fixed32 = 96 [packed = true];
+ repeated fixed64 packed_fixed64 = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32 = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64 = 99 [packed = true];
+ repeated float packed_float = 100 [packed = true];
+ repeated double packed_double = 101 [packed = true];
+ repeated bool packed_bool = 102 [packed = true];
+ repeated ForeignEnum packed_enum = 103 [packed = true];
+}
+
+// A message with the same fields as TestPackedTypes, but without packing. Used
+// to test packed <-> unpacked wire compatibility.
+message TestUnpackedTypes {
+ repeated int32 unpacked_int32 = 90 [packed = false];
+ repeated int64 unpacked_int64 = 91 [packed = false];
+ repeated uint32 unpacked_uint32 = 92 [packed = false];
+ repeated uint64 unpacked_uint64 = 93 [packed = false];
+ repeated sint32 unpacked_sint32 = 94 [packed = false];
+ repeated sint64 unpacked_sint64 = 95 [packed = false];
+ repeated fixed32 unpacked_fixed32 = 96 [packed = false];
+ repeated fixed64 unpacked_fixed64 = 97 [packed = false];
+ repeated sfixed32 unpacked_sfixed32 = 98 [packed = false];
+ repeated sfixed64 unpacked_sfixed64 = 99 [packed = false];
+ repeated float unpacked_float = 100 [packed = false];
+ repeated double unpacked_double = 101 [packed = false];
+ repeated bool unpacked_bool = 102 [packed = false];
+ repeated ForeignEnum unpacked_enum = 103 [packed = false];
+}
+
+message TestRepeatedScalarDifferentTagSizes {
+ // Parsing repeated fixed size values used to fail. This message needs to be
+ // used in order to get a tag of the right size; all of the repeated fields
+ // in TestAllTypes didn't trigger the check.
+ repeated fixed32 repeated_fixed32 = 12;
+ // Check for a varint type, just for good measure.
+ repeated int32 repeated_int32 = 13;
+
+ // These have two-byte tags.
+ repeated fixed64 repeated_fixed64 = 2046;
+ repeated int64 repeated_int64 = 2047;
+
+ // Three byte tags.
+ repeated float repeated_float = 262142;
+ repeated uint64 repeated_uint64 = 262143;
+}
+
+message TestCommentInjectionMessage {
+ // */ <- This should not close the generated doc comment
+ string a = 1;
+}
+
+
+// Test that RPC services work.
+message FooRequest {}
+message FooResponse {}
+
+message FooClientMessage {}
+message FooServerMessage{}
+
+service TestService {
+ rpc Foo(FooRequest) returns (FooResponse);
+ rpc Bar(BarRequest) returns (BarResponse);
+}
+
+
+message BarRequest {}
+message BarResponse {}
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena.proto
new file mode 100644
index 0000000000..b835a6ba36
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena.proto
@@ -0,0 +1,206 @@
+// 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.
+
+syntax = "proto3";
+
+option cc_enable_arenas = true;
+
+import "google/protobuf/unittest_import.proto";
+
+package proto3_arena_unittest;
+
+// This proto includes every type of field in both singular and repeated
+// forms.
+message TestAllTypes {
+ message NestedMessage {
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ int32 bb = 1;
+ }
+
+ enum NestedEnum {
+ ZERO = 0;
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ NEG = -1; // Intentionally negative.
+ }
+
+ // Singular
+ int32 optional_int32 = 1;
+ int64 optional_int64 = 2;
+ uint32 optional_uint32 = 3;
+ uint64 optional_uint64 = 4;
+ sint32 optional_sint32 = 5;
+ sint64 optional_sint64 = 6;
+ fixed32 optional_fixed32 = 7;
+ fixed64 optional_fixed64 = 8;
+ sfixed32 optional_sfixed32 = 9;
+ sfixed64 optional_sfixed64 = 10;
+ float optional_float = 11;
+ double optional_double = 12;
+ bool optional_bool = 13;
+ string optional_string = 14;
+ bytes optional_bytes = 15;
+
+ // Groups are not allowed in proto3.
+ // optional group OptionalGroup = 16 {
+ // optional int32 a = 17;
+ // }
+
+ NestedMessage optional_nested_message = 18;
+ ForeignMessage optional_foreign_message = 19;
+ protobuf_unittest_import.ImportMessage optional_import_message = 20;
+
+ NestedEnum optional_nested_enum = 21;
+ ForeignEnum optional_foreign_enum = 22;
+
+ // Omitted (compared to unittest.proto) because proto2 enums are not allowed
+ // inside proto2 messages.
+ //
+ // optional protobuf_unittest_import.ImportEnum optional_import_enum = 23;
+
+ string optional_string_piece = 24 [ctype=STRING_PIECE];
+ string optional_cord = 25 [ctype=CORD];
+
+ // Defined in unittest_import_public.proto
+ protobuf_unittest_import.PublicImportMessage
+ optional_public_import_message = 26;
+
+ NestedMessage optional_lazy_message = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ // Groups are not allowed in proto3.
+ // repeated group RepeatedGroup = 46 {
+ // optional int32 a = 47;
+ // }
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessage repeated_foreign_message = 49;
+ repeated protobuf_unittest_import.ImportMessage repeated_import_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnum repeated_foreign_enum = 52;
+
+ // Omitted (compared to unittest.proto) because proto2 enums are not allowed
+ // inside proto2 messages.
+ //
+ // repeated protobuf_unittest_import.ImportEnum repeated_import_enum = 53;
+
+ repeated string repeated_string_piece = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord = 55 [ctype=CORD];
+
+ repeated NestedMessage repeated_lazy_message = 57 [lazy=true];
+
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ bytes oneof_bytes = 114;
+ }
+}
+
+// Test messages for packed fields
+
+message TestPackedTypes {
+ repeated int32 packed_int32 = 90 [packed = true];
+ repeated int64 packed_int64 = 91 [packed = true];
+ repeated uint32 packed_uint32 = 92 [packed = true];
+ repeated uint64 packed_uint64 = 93 [packed = true];
+ repeated sint32 packed_sint32 = 94 [packed = true];
+ repeated sint64 packed_sint64 = 95 [packed = true];
+ repeated fixed32 packed_fixed32 = 96 [packed = true];
+ repeated fixed64 packed_fixed64 = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32 = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64 = 99 [packed = true];
+ repeated float packed_float = 100 [packed = true];
+ repeated double packed_double = 101 [packed = true];
+ repeated bool packed_bool = 102 [packed = true];
+ repeated ForeignEnum packed_enum = 103 [packed = true];
+}
+
+// Explicitly set packed to false
+message TestUnpackedTypes {
+ repeated int32 repeated_int32 = 1 [packed = false];
+ repeated int64 repeated_int64 = 2 [packed = false];
+ repeated uint32 repeated_uint32 = 3 [packed = false];
+ repeated uint64 repeated_uint64 = 4 [packed = false];
+ repeated sint32 repeated_sint32 = 5 [packed = false];
+ repeated sint64 repeated_sint64 = 6 [packed = false];
+ repeated fixed32 repeated_fixed32 = 7 [packed = false];
+ repeated fixed64 repeated_fixed64 = 8 [packed = false];
+ repeated sfixed32 repeated_sfixed32 = 9 [packed = false];
+ repeated sfixed64 repeated_sfixed64 = 10 [packed = false];
+ repeated float repeated_float = 11 [packed = false];
+ repeated double repeated_double = 12 [packed = false];
+ repeated bool repeated_bool = 13 [packed = false];
+ repeated TestAllTypes.NestedEnum repeated_nested_enum = 14 [packed = false];
+}
+
+// This proto includes a recusively nested message.
+message NestedTestAllTypes {
+ NestedTestAllTypes child = 1;
+ TestAllTypes payload = 2;
+}
+
+// Define these after TestAllTypes to make sure the compiler can handle
+// that.
+message ForeignMessage {
+ int32 c = 1;
+}
+
+enum ForeignEnum {
+ FOREIGN_ZERO = 0;
+ FOREIGN_FOO = 4;
+ FOREIGN_BAR = 5;
+ FOREIGN_BAZ = 6;
+}
+
+// TestEmptyMessage is used to test behavior of unknown fields.
+message TestEmptyMessage {
+}
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena_lite.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena_lite.proto
new file mode 100644
index 0000000000..5a60b90f5c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_arena_lite.proto
@@ -0,0 +1,207 @@
+// 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.
+
+syntax = "proto3";
+
+option cc_enable_arenas = true;
+option optimize_for = LITE_RUNTIME;
+
+import "google/protobuf/unittest_import.proto";
+
+package proto3_arena_lite_unittest;
+
+// This proto includes every type of field in both singular and repeated
+// forms.
+message TestAllTypes {
+ message NestedMessage {
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ int32 bb = 1;
+ }
+
+ enum NestedEnum {
+ ZERO = 0;
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ NEG = -1; // Intentionally negative.
+ }
+
+ // Singular
+ int32 optional_int32 = 1;
+ int64 optional_int64 = 2;
+ uint32 optional_uint32 = 3;
+ uint64 optional_uint64 = 4;
+ sint32 optional_sint32 = 5;
+ sint64 optional_sint64 = 6;
+ fixed32 optional_fixed32 = 7;
+ fixed64 optional_fixed64 = 8;
+ sfixed32 optional_sfixed32 = 9;
+ sfixed64 optional_sfixed64 = 10;
+ float optional_float = 11;
+ double optional_double = 12;
+ bool optional_bool = 13;
+ string optional_string = 14;
+ bytes optional_bytes = 15;
+
+ // Groups are not allowed in proto3.
+ // optional group OptionalGroup = 16 {
+ // optional int32 a = 17;
+ // }
+
+ NestedMessage optional_nested_message = 18;
+ ForeignMessage optional_foreign_message = 19;
+ protobuf_unittest_import.ImportMessage optional_import_message = 20;
+
+ NestedEnum optional_nested_enum = 21;
+ ForeignEnum optional_foreign_enum = 22;
+
+ // Omitted (compared to unittest.proto) because proto2 enums are not allowed
+ // inside proto2 messages.
+ //
+ // optional protobuf_unittest_import.ImportEnum optional_import_enum = 23;
+
+ string optional_string_piece = 24 [ctype=STRING_PIECE];
+ string optional_cord = 25 [ctype=CORD];
+
+ // Defined in unittest_import_public.proto
+ protobuf_unittest_import.PublicImportMessage
+ optional_public_import_message = 26;
+
+ NestedMessage optional_lazy_message = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ // Groups are not allowed in proto3.
+ // repeated group RepeatedGroup = 46 {
+ // optional int32 a = 47;
+ // }
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessage repeated_foreign_message = 49;
+ repeated protobuf_unittest_import.ImportMessage repeated_import_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnum repeated_foreign_enum = 52;
+
+ // Omitted (compared to unittest.proto) because proto2 enums are not allowed
+ // inside proto2 messages.
+ //
+ // repeated protobuf_unittest_import.ImportEnum repeated_import_enum = 53;
+
+ repeated string repeated_string_piece = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord = 55 [ctype=CORD];
+
+ repeated NestedMessage repeated_lazy_message = 57 [lazy=true];
+
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ bytes oneof_bytes = 114;
+ }
+}
+
+// Test messages for packed fields
+
+message TestPackedTypes {
+ repeated int32 packed_int32 = 90 [packed = true];
+ repeated int64 packed_int64 = 91 [packed = true];
+ repeated uint32 packed_uint32 = 92 [packed = true];
+ repeated uint64 packed_uint64 = 93 [packed = true];
+ repeated sint32 packed_sint32 = 94 [packed = true];
+ repeated sint64 packed_sint64 = 95 [packed = true];
+ repeated fixed32 packed_fixed32 = 96 [packed = true];
+ repeated fixed64 packed_fixed64 = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32 = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64 = 99 [packed = true];
+ repeated float packed_float = 100 [packed = true];
+ repeated double packed_double = 101 [packed = true];
+ repeated bool packed_bool = 102 [packed = true];
+ repeated ForeignEnum packed_enum = 103 [packed = true];
+}
+
+// Explicitly set packed to false
+message TestUnpackedTypes {
+ repeated int32 repeated_int32 = 1 [packed = false];
+ repeated int64 repeated_int64 = 2 [packed = false];
+ repeated uint32 repeated_uint32 = 3 [packed = false];
+ repeated uint64 repeated_uint64 = 4 [packed = false];
+ repeated sint32 repeated_sint32 = 5 [packed = false];
+ repeated sint64 repeated_sint64 = 6 [packed = false];
+ repeated fixed32 repeated_fixed32 = 7 [packed = false];
+ repeated fixed64 repeated_fixed64 = 8 [packed = false];
+ repeated sfixed32 repeated_sfixed32 = 9 [packed = false];
+ repeated sfixed64 repeated_sfixed64 = 10 [packed = false];
+ repeated float repeated_float = 11 [packed = false];
+ repeated double repeated_double = 12 [packed = false];
+ repeated bool repeated_bool = 13 [packed = false];
+ repeated TestAllTypes.NestedEnum repeated_nested_enum = 14 [packed = false];
+}
+
+// This proto includes a recusively nested message.
+message NestedTestAllTypes {
+ NestedTestAllTypes child = 1;
+ TestAllTypes payload = 2;
+}
+
+// Define these after TestAllTypes to make sure the compiler can handle
+// that.
+message ForeignMessage {
+ int32 c = 1;
+}
+
+enum ForeignEnum {
+ FOREIGN_ZERO = 0;
+ FOREIGN_FOO = 4;
+ FOREIGN_BAR = 5;
+ FOREIGN_BAZ = 6;
+}
+
+// TestEmptyMessage is used to test behavior of unknown fields.
+message TestEmptyMessage {
+}
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_lite.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_lite.proto
new file mode 100644
index 0000000000..874ade6c0e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_proto3_lite.proto
@@ -0,0 +1,206 @@
+// 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.
+
+syntax = "proto3";
+
+option optimize_for = LITE_RUNTIME;
+
+import "google/protobuf/unittest_import.proto";
+
+package proto3_lite_unittest;
+
+// This proto includes every type of field in both singular and repeated
+// forms.
+message TestAllTypes {
+ message NestedMessage {
+ // The field name "b" fails to compile in proto1 because it conflicts with
+ // a local variable named "b" in one of the generated methods. Doh.
+ // This file needs to compile in proto1 to test backwards-compatibility.
+ int32 bb = 1;
+ }
+
+ enum NestedEnum {
+ ZERO = 0;
+ FOO = 1;
+ BAR = 2;
+ BAZ = 3;
+ NEG = -1; // Intentionally negative.
+ }
+
+ // Singular
+ int32 optional_int32 = 1;
+ int64 optional_int64 = 2;
+ uint32 optional_uint32 = 3;
+ uint64 optional_uint64 = 4;
+ sint32 optional_sint32 = 5;
+ sint64 optional_sint64 = 6;
+ fixed32 optional_fixed32 = 7;
+ fixed64 optional_fixed64 = 8;
+ sfixed32 optional_sfixed32 = 9;
+ sfixed64 optional_sfixed64 = 10;
+ float optional_float = 11;
+ double optional_double = 12;
+ bool optional_bool = 13;
+ string optional_string = 14;
+ bytes optional_bytes = 15;
+
+ // Groups are not allowed in proto3.
+ // optional group OptionalGroup = 16 {
+ // optional int32 a = 17;
+ // }
+
+ NestedMessage optional_nested_message = 18;
+ ForeignMessage optional_foreign_message = 19;
+ protobuf_unittest_import.ImportMessage optional_import_message = 20;
+
+ NestedEnum optional_nested_enum = 21;
+ ForeignEnum optional_foreign_enum = 22;
+
+ // Omitted (compared to unittest.proto) because proto2 enums are not allowed
+ // inside proto2 messages.
+ //
+ // optional protobuf_unittest_import.ImportEnum optional_import_enum = 23;
+
+ string optional_string_piece = 24 [ctype=STRING_PIECE];
+ string optional_cord = 25 [ctype=CORD];
+
+ // Defined in unittest_import_public.proto
+ protobuf_unittest_import.PublicImportMessage
+ optional_public_import_message = 26;
+
+ NestedMessage optional_lazy_message = 27 [lazy=true];
+
+ // Repeated
+ repeated int32 repeated_int32 = 31;
+ repeated int64 repeated_int64 = 32;
+ repeated uint32 repeated_uint32 = 33;
+ repeated uint64 repeated_uint64 = 34;
+ repeated sint32 repeated_sint32 = 35;
+ repeated sint64 repeated_sint64 = 36;
+ repeated fixed32 repeated_fixed32 = 37;
+ repeated fixed64 repeated_fixed64 = 38;
+ repeated sfixed32 repeated_sfixed32 = 39;
+ repeated sfixed64 repeated_sfixed64 = 40;
+ repeated float repeated_float = 41;
+ repeated double repeated_double = 42;
+ repeated bool repeated_bool = 43;
+ repeated string repeated_string = 44;
+ repeated bytes repeated_bytes = 45;
+
+ // Groups are not allowed in proto3.
+ // repeated group RepeatedGroup = 46 {
+ // optional int32 a = 47;
+ // }
+
+ repeated NestedMessage repeated_nested_message = 48;
+ repeated ForeignMessage repeated_foreign_message = 49;
+ repeated protobuf_unittest_import.ImportMessage repeated_import_message = 50;
+
+ repeated NestedEnum repeated_nested_enum = 51;
+ repeated ForeignEnum repeated_foreign_enum = 52;
+
+ // Omitted (compared to unittest.proto) because proto2 enums are not allowed
+ // inside proto2 messages.
+ //
+ // repeated protobuf_unittest_import.ImportEnum repeated_import_enum = 53;
+
+ repeated string repeated_string_piece = 54 [ctype=STRING_PIECE];
+ repeated string repeated_cord = 55 [ctype=CORD];
+
+ repeated NestedMessage repeated_lazy_message = 57 [lazy=true];
+
+ oneof oneof_field {
+ uint32 oneof_uint32 = 111;
+ NestedMessage oneof_nested_message = 112;
+ string oneof_string = 113;
+ bytes oneof_bytes = 114;
+ }
+}
+
+// Test messages for packed fields
+
+message TestPackedTypes {
+ repeated int32 packed_int32 = 90 [packed = true];
+ repeated int64 packed_int64 = 91 [packed = true];
+ repeated uint32 packed_uint32 = 92 [packed = true];
+ repeated uint64 packed_uint64 = 93 [packed = true];
+ repeated sint32 packed_sint32 = 94 [packed = true];
+ repeated sint64 packed_sint64 = 95 [packed = true];
+ repeated fixed32 packed_fixed32 = 96 [packed = true];
+ repeated fixed64 packed_fixed64 = 97 [packed = true];
+ repeated sfixed32 packed_sfixed32 = 98 [packed = true];
+ repeated sfixed64 packed_sfixed64 = 99 [packed = true];
+ repeated float packed_float = 100 [packed = true];
+ repeated double packed_double = 101 [packed = true];
+ repeated bool packed_bool = 102 [packed = true];
+ repeated ForeignEnum packed_enum = 103 [packed = true];
+}
+
+// Explicitly set packed to false
+message TestUnpackedTypes {
+ repeated int32 repeated_int32 = 1 [packed = false];
+ repeated int64 repeated_int64 = 2 [packed = false];
+ repeated uint32 repeated_uint32 = 3 [packed = false];
+ repeated uint64 repeated_uint64 = 4 [packed = false];
+ repeated sint32 repeated_sint32 = 5 [packed = false];
+ repeated sint64 repeated_sint64 = 6 [packed = false];
+ repeated fixed32 repeated_fixed32 = 7 [packed = false];
+ repeated fixed64 repeated_fixed64 = 8 [packed = false];
+ repeated sfixed32 repeated_sfixed32 = 9 [packed = false];
+ repeated sfixed64 repeated_sfixed64 = 10 [packed = false];
+ repeated float repeated_float = 11 [packed = false];
+ repeated double repeated_double = 12 [packed = false];
+ repeated bool repeated_bool = 13 [packed = false];
+ repeated TestAllTypes.NestedEnum repeated_nested_enum = 14 [packed = false];
+}
+
+// This proto includes a recusively nested message.
+message NestedTestAllTypes {
+ NestedTestAllTypes child = 1;
+ TestAllTypes payload = 2;
+}
+
+// Define these after TestAllTypes to make sure the compiler can handle
+// that.
+message ForeignMessage {
+ int32 c = 1;
+}
+
+enum ForeignEnum {
+ FOREIGN_ZERO = 0;
+ FOREIGN_FOO = 4;
+ FOREIGN_BAR = 5;
+ FOREIGN_BAZ = 6;
+}
+
+// TestEmptyMessage is used to test behavior of unknown fields.
+message TestEmptyMessage {
+}
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unittest_well_known_types.proto b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_well_known_types.proto
new file mode 100644
index 0000000000..c90752440b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unittest_well_known_types.proto
@@ -0,0 +1,114 @@
+syntax = "proto3";
+
+package protobuf_unittest;
+
+option csharp_namespace = "Google.Protobuf.TestProtos";
+option java_multiple_files = true;
+option java_package = "com.google.protobuf.test";
+
+import "google/protobuf/any.proto";
+import "google/protobuf/api.proto";
+import "google/protobuf/duration.proto";
+import "google/protobuf/empty.proto";
+import "google/protobuf/field_mask.proto";
+import "google/protobuf/source_context.proto";
+import "google/protobuf/struct.proto";
+import "google/protobuf/timestamp.proto";
+import "google/protobuf/type.proto";
+import "google/protobuf/wrappers.proto";
+
+// Test that we can include all well-known types.
+// Each wrapper type is included separately, as languages
+// map handle different wrappers in different ways.
+message TestWellKnownTypes {
+ google.protobuf.Any any_field = 1;
+ google.protobuf.Api api_field = 2;
+ google.protobuf.Duration duration_field = 3;
+ google.protobuf.Empty empty_field = 4;
+ google.protobuf.FieldMask field_mask_field = 5;
+ google.protobuf.SourceContext source_context_field = 6;
+ google.protobuf.Struct struct_field = 7;
+ google.protobuf.Timestamp timestamp_field = 8;
+ google.protobuf.Type type_field = 9;
+ google.protobuf.DoubleValue double_field = 10;
+ google.protobuf.FloatValue float_field = 11;
+ google.protobuf.Int64Value int64_field = 12;
+ google.protobuf.UInt64Value uint64_field = 13;
+ google.protobuf.Int32Value int32_field = 14;
+ google.protobuf.UInt32Value uint32_field = 15;
+ google.protobuf.BoolValue bool_field = 16;
+ google.protobuf.StringValue string_field = 17;
+ google.protobuf.BytesValue bytes_field = 18;
+ // Part of struct, but useful to be able to test separately
+ google.protobuf.Value value_field = 19;
+}
+
+// A repeated field for each well-known type.
+message RepeatedWellKnownTypes {
+ repeated google.protobuf.Any any_field = 1;
+ repeated google.protobuf.Api api_field = 2;
+ repeated google.protobuf.Duration duration_field = 3;
+ repeated google.protobuf.Empty empty_field = 4;
+ repeated google.protobuf.FieldMask field_mask_field = 5;
+ repeated google.protobuf.SourceContext source_context_field = 6;
+ repeated google.protobuf.Struct struct_field = 7;
+ repeated google.protobuf.Timestamp timestamp_field = 8;
+ repeated google.protobuf.Type type_field = 9;
+ // These don't actually make a lot of sense, but they're not prohibited...
+ repeated google.protobuf.DoubleValue double_field = 10;
+ repeated google.protobuf.FloatValue float_field = 11;
+ repeated google.protobuf.Int64Value int64_field = 12;
+ repeated google.protobuf.UInt64Value uint64_field = 13;
+ repeated google.protobuf.Int32Value int32_field = 14;
+ repeated google.protobuf.UInt32Value uint32_field = 15;
+ repeated google.protobuf.BoolValue bool_field = 16;
+ repeated google.protobuf.StringValue string_field = 17;
+ repeated google.protobuf.BytesValue bytes_field = 18;
+}
+
+message OneofWellKnownTypes {
+ oneof oneof_field {
+ google.protobuf.Any any_field = 1;
+ google.protobuf.Api api_field = 2;
+ google.protobuf.Duration duration_field = 3;
+ google.protobuf.Empty empty_field = 4;
+ google.protobuf.FieldMask field_mask_field = 5;
+ google.protobuf.SourceContext source_context_field = 6;
+ google.protobuf.Struct struct_field = 7;
+ google.protobuf.Timestamp timestamp_field = 8;
+ google.protobuf.Type type_field = 9;
+ google.protobuf.DoubleValue double_field = 10;
+ google.protobuf.FloatValue float_field = 11;
+ google.protobuf.Int64Value int64_field = 12;
+ google.protobuf.UInt64Value uint64_field = 13;
+ google.protobuf.Int32Value int32_field = 14;
+ google.protobuf.UInt32Value uint32_field = 15;
+ google.protobuf.BoolValue bool_field = 16;
+ google.protobuf.StringValue string_field = 17;
+ google.protobuf.BytesValue bytes_field = 18;
+ }
+}
+
+// A map field for each well-known type. We only
+// need to worry about the value part of the map being the
+// well-known types, as messages can't be map keys.
+message MapWellKnownTypes {
+ map<int32,google.protobuf.Any> any_field = 1;
+ map<int32,google.protobuf.Api> api_field = 2;
+ map<int32,google.protobuf.Duration> duration_field = 3;
+ map<int32,google.protobuf.Empty> empty_field = 4;
+ map<int32,google.protobuf.FieldMask> field_mask_field = 5;
+ map<int32,google.protobuf.SourceContext> source_context_field = 6;
+ map<int32,google.protobuf.Struct> struct_field = 7;
+ map<int32,google.protobuf.Timestamp> timestamp_field = 8;
+ map<int32,google.protobuf.Type> type_field = 9;
+ map<int32,google.protobuf.DoubleValue> double_field = 10;
+ map<int32,google.protobuf.FloatValue> float_field = 11;
+ map<int32,google.protobuf.Int64Value> int64_field = 12;
+ map<int32,google.protobuf.UInt64Value> uint64_field = 13;
+ map<int32,google.protobuf.Int32Value> int32_field = 14;
+ map<int32,google.protobuf.UInt32Value> uint32_field = 15;
+ map<int32,google.protobuf.BoolValue> bool_field = 16;
+ map<int32,google.protobuf.StringValue> string_field = 17;
+ map<int32,google.protobuf.BytesValue> bytes_field = 18;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.cc b/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.cc
new file mode 100644
index 0000000000..8ee99d48b1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.cc
@@ -0,0 +1,333 @@
+// 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.
+
+#include <google/protobuf/unknown_field_set.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+
+namespace {
+// This global instance is returned by unknown_fields() on any message class
+// when the object has no unknown fields. This is necessary because we now
+// instantiate the UnknownFieldSet dynamically only when required.
+UnknownFieldSet* default_unknown_field_set_instance_ = NULL;
+
+void DeleteDefaultUnknownFieldSet() {
+ delete default_unknown_field_set_instance_;
+}
+
+void InitDefaultUnknownFieldSet() {
+ default_unknown_field_set_instance_ = new UnknownFieldSet();
+ internal::OnShutdown(&DeleteDefaultUnknownFieldSet);
+}
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(default_unknown_field_set_once_init_);
+}
+
+const UnknownFieldSet* UnknownFieldSet::default_instance() {
+ ::google::protobuf::GoogleOnceInit(&default_unknown_field_set_once_init_,
+ &InitDefaultUnknownFieldSet);
+ return default_unknown_field_set_instance_;
+}
+
+void UnknownFieldSet::ClearFallback() {
+ GOOGLE_DCHECK(fields_ != NULL && fields_->size() > 0);
+ int n = fields_->size();
+ do {
+ (*fields_)[--n].Delete();
+ } while (n > 0);
+ delete fields_;
+ fields_ = NULL;
+}
+
+void UnknownFieldSet::InternalMergeFrom(const UnknownFieldSet& other) {
+ int other_field_count = other.field_count();
+ if (other_field_count > 0) {
+ fields_ = new vector<UnknownField>();
+ for (int i = 0; i < other_field_count; i++) {
+ fields_->push_back((*other.fields_)[i]);
+ fields_->back().DeepCopy((*other.fields_)[i]);
+ }
+ }
+}
+
+void UnknownFieldSet::MergeFrom(const UnknownFieldSet& other) {
+ int other_field_count = other.field_count();
+ if (other_field_count > 0) {
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ for (int i = 0; i < other_field_count; i++) {
+ fields_->push_back((*other.fields_)[i]);
+ fields_->back().DeepCopy((*other.fields_)[i]);
+ }
+ }
+}
+
+// A specialized MergeFrom for performance when we are merging from an UFS that
+// is temporary and can be destroyed in the process.
+void UnknownFieldSet::MergeFromAndDestroy(UnknownFieldSet* other) {
+ int other_field_count = other->field_count();
+ if (other_field_count > 0) {
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ for (int i = 0; i < other_field_count; i++) {
+ fields_->push_back((*other->fields_)[i]);
+ (*other->fields_)[i].Reset();
+ }
+ }
+ delete other->fields_;
+ other->fields_ = NULL;
+}
+
+int UnknownFieldSet::SpaceUsedExcludingSelf() const {
+ if (fields_ == NULL) return 0;
+
+ int total_size = sizeof(*fields_) + sizeof(UnknownField) * fields_->size();
+
+ for (int i = 0; i < fields_->size(); i++) {
+ const UnknownField& field = (*fields_)[i];
+ switch (field.type()) {
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ total_size += sizeof(*field.length_delimited_.string_value_) +
+ internal::StringSpaceUsedExcludingSelf(
+ *field.length_delimited_.string_value_);
+ break;
+ case UnknownField::TYPE_GROUP:
+ total_size += field.group_->SpaceUsed();
+ break;
+ default:
+ break;
+ }
+ }
+ return total_size;
+}
+
+int UnknownFieldSet::SpaceUsed() const {
+ return sizeof(*this) + SpaceUsedExcludingSelf();
+}
+
+void UnknownFieldSet::AddVarint(int number, uint64 value) {
+ UnknownField field;
+ field.number_ = number;
+ field.SetType(UnknownField::TYPE_VARINT);
+ field.varint_ = value;
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ fields_->push_back(field);
+}
+
+void UnknownFieldSet::AddFixed32(int number, uint32 value) {
+ UnknownField field;
+ field.number_ = number;
+ field.SetType(UnknownField::TYPE_FIXED32);
+ field.fixed32_ = value;
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ fields_->push_back(field);
+}
+
+void UnknownFieldSet::AddFixed64(int number, uint64 value) {
+ UnknownField field;
+ field.number_ = number;
+ field.SetType(UnknownField::TYPE_FIXED64);
+ field.fixed64_ = value;
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ fields_->push_back(field);
+}
+
+string* UnknownFieldSet::AddLengthDelimited(int number) {
+ UnknownField field;
+ field.number_ = number;
+ field.SetType(UnknownField::TYPE_LENGTH_DELIMITED);
+ field.length_delimited_.string_value_ = new string;
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ fields_->push_back(field);
+ return field.length_delimited_.string_value_;
+}
+
+
+UnknownFieldSet* UnknownFieldSet::AddGroup(int number) {
+ UnknownField field;
+ field.number_ = number;
+ field.SetType(UnknownField::TYPE_GROUP);
+ field.group_ = new UnknownFieldSet;
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ fields_->push_back(field);
+ return field.group_;
+}
+
+void UnknownFieldSet::AddField(const UnknownField& field) {
+ if (fields_ == NULL) fields_ = new vector<UnknownField>();
+ fields_->push_back(field);
+ fields_->back().DeepCopy(field);
+}
+
+void UnknownFieldSet::DeleteSubrange(int start, int num) {
+ // Delete the specified fields.
+ for (int i = 0; i < num; ++i) {
+ (*fields_)[i + start].Delete();
+ }
+ // Slide down the remaining fields.
+ for (int i = start + num; i < fields_->size(); ++i) {
+ (*fields_)[i - num] = (*fields_)[i];
+ }
+ // Pop off the # of deleted fields.
+ for (int i = 0; i < num; ++i) {
+ fields_->pop_back();
+ }
+ if (fields_ && fields_->size() == 0) {
+ // maintain invariant: never hold fields_ if empty.
+ delete fields_;
+ fields_ = NULL;
+ }
+}
+
+void UnknownFieldSet::DeleteByNumber(int number) {
+ if (fields_ == NULL) return;
+ int left = 0; // The number of fields left after deletion.
+ for (int i = 0; i < fields_->size(); ++i) {
+ UnknownField* field = &(*fields_)[i];
+ if (field->number() == number) {
+ field->Delete();
+ } else {
+ if (i != left) {
+ (*fields_)[left] = (*fields_)[i];
+ }
+ ++left;
+ }
+ }
+ fields_->resize(left);
+ if (left == 0) {
+ // maintain invariant: never hold fields_ if empty.
+ delete fields_;
+ fields_ = NULL;
+ }
+}
+
+bool UnknownFieldSet::MergeFromCodedStream(io::CodedInputStream* input) {
+ UnknownFieldSet other;
+ if (internal::WireFormat::SkipMessage(input, &other) &&
+ input->ConsumedEntireMessage()) {
+ MergeFromAndDestroy(&other);
+ return true;
+ } else {
+ return false;
+ }
+}
+
+bool UnknownFieldSet::ParseFromCodedStream(io::CodedInputStream* input) {
+ Clear();
+ return MergeFromCodedStream(input);
+}
+
+bool UnknownFieldSet::ParseFromZeroCopyStream(io::ZeroCopyInputStream* input) {
+ io::CodedInputStream coded_input(input);
+ return (ParseFromCodedStream(&coded_input) &&
+ coded_input.ConsumedEntireMessage());
+}
+
+bool UnknownFieldSet::ParseFromArray(const void* data, int size) {
+ io::ArrayInputStream input(data, size);
+ return ParseFromZeroCopyStream(&input);
+}
+
+void UnknownField::Delete() {
+ switch (type()) {
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ delete length_delimited_.string_value_;
+ break;
+ case UnknownField::TYPE_GROUP:
+ delete group_;
+ break;
+ default:
+ break;
+ }
+}
+
+// Reset all owned ptrs, a special function for performance, to avoid double
+// owning the ptrs, when we merge from a temporary UnknownFieldSet objects.
+void UnknownField::Reset() {
+ switch (type()) {
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ length_delimited_.string_value_ = NULL;
+ break;
+ case UnknownField::TYPE_GROUP: {
+ group_ = NULL;
+ break;
+ }
+ default:
+ break;
+ }
+}
+
+void UnknownField::DeepCopy(const UnknownField& other) {
+ switch (type()) {
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ length_delimited_.string_value_ = new string(
+ *length_delimited_.string_value_);
+ break;
+ case UnknownField::TYPE_GROUP: {
+ UnknownFieldSet* group = new UnknownFieldSet();
+ group->InternalMergeFrom(*group_);
+ group_ = group;
+ break;
+ }
+ default:
+ break;
+ }
+}
+
+
+void UnknownField::SerializeLengthDelimitedNoTag(
+ io::CodedOutputStream* output) const {
+ GOOGLE_DCHECK_EQ(TYPE_LENGTH_DELIMITED, type());
+ const string& data = *length_delimited_.string_value_;
+ output->WriteVarint32(data.size());
+ output->WriteRawMaybeAliased(data.data(), data.size());
+}
+
+uint8* UnknownField::SerializeLengthDelimitedNoTagToArray(uint8* target) const {
+ GOOGLE_DCHECK_EQ(TYPE_LENGTH_DELIMITED, type());
+ const string& data = *length_delimited_.string_value_;
+ target = io::CodedOutputStream::WriteVarint32ToArray(data.size(), target);
+ target = io::CodedOutputStream::WriteStringToArray(data, target);
+ return target;
+}
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.h b/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.h
new file mode 100644
index 0000000000..aa7529165b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set.h
@@ -0,0 +1,346 @@
+// 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.
+//
+// Contains classes used to keep track of unrecognized fields seen while
+// parsing a protocol message.
+
+#ifndef GOOGLE_PROTOBUF_UNKNOWN_FIELD_SET_H__
+#define GOOGLE_PROTOBUF_UNKNOWN_FIELD_SET_H__
+
+#include <assert.h>
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class CodedInputStream; // coded_stream.h
+ class CodedOutputStream; // coded_stream.h
+ class ZeroCopyInputStream; // zero_copy_stream.h
+ }
+ namespace internal {
+ class WireFormat; // wire_format.h
+ class MessageSetFieldSkipperUsingCord;
+ // extension_set_heavy.cc
+ }
+
+class Message; // message.h
+class UnknownField; // below
+
+// An UnknownFieldSet contains fields that were encountered while parsing a
+// message but were not defined by its type. Keeping track of these can be
+// useful, especially in that they may be written if the message is serialized
+// again without being cleared in between. This means that software which
+// simply receives messages and forwards them to other servers does not need
+// to be updated every time a new field is added to the message definition.
+//
+// To get the UnknownFieldSet attached to any message, call
+// Reflection::GetUnknownFields().
+//
+// This class is necessarily tied to the protocol buffer wire format, unlike
+// the Reflection interface which is independent of any serialization scheme.
+class LIBPROTOBUF_EXPORT UnknownFieldSet {
+ public:
+ UnknownFieldSet();
+ ~UnknownFieldSet();
+
+ // Remove all fields.
+ inline void Clear();
+
+ // Remove all fields and deallocate internal data objects
+ void ClearAndFreeMemory();
+
+ // Is this set empty?
+ inline bool empty() const;
+
+ // Merge the contents of some other UnknownFieldSet with this one.
+ void MergeFrom(const UnknownFieldSet& other);
+
+ // Similar to above, but this function will destroy the contents of other.
+ void MergeFromAndDestroy(UnknownFieldSet* other);
+
+ // Swaps the contents of some other UnknownFieldSet with this one.
+ inline void Swap(UnknownFieldSet* x);
+
+ // Computes (an estimate of) the total number of bytes currently used for
+ // storing the unknown fields in memory. Does NOT include
+ // sizeof(*this) in the calculation.
+ int SpaceUsedExcludingSelf() const;
+
+ // Version of SpaceUsed() including sizeof(*this).
+ int SpaceUsed() const;
+
+ // Returns the number of fields present in the UnknownFieldSet.
+ inline int field_count() const;
+ // Get a field in the set, where 0 <= index < field_count(). The fields
+ // appear in the order in which they were added.
+ inline const UnknownField& field(int index) const;
+ // Get a mutable pointer to a field in the set, where
+ // 0 <= index < field_count(). The fields appear in the order in which
+ // they were added.
+ inline UnknownField* mutable_field(int index);
+
+ // Adding fields ---------------------------------------------------
+
+ void AddVarint(int number, uint64 value);
+ void AddFixed32(int number, uint32 value);
+ void AddFixed64(int number, uint64 value);
+ void AddLengthDelimited(int number, const string& value);
+ string* AddLengthDelimited(int number);
+ UnknownFieldSet* AddGroup(int number);
+
+ // Adds an unknown field from another set.
+ void AddField(const UnknownField& field);
+
+ // Delete fields with indices in the range [start .. start+num-1].
+ // Caution: implementation moves all fields with indices [start+num .. ].
+ void DeleteSubrange(int start, int num);
+
+ // Delete all fields with a specific field number. The order of left fields
+ // is preserved.
+ // Caution: implementation moves all fields after the first deleted field.
+ void DeleteByNumber(int number);
+
+ // Parsing helpers -------------------------------------------------
+ // These work exactly like the similarly-named methods of Message.
+
+ bool MergeFromCodedStream(io::CodedInputStream* input);
+ bool ParseFromCodedStream(io::CodedInputStream* input);
+ bool ParseFromZeroCopyStream(io::ZeroCopyInputStream* input);
+ bool ParseFromArray(const void* data, int size);
+ inline bool ParseFromString(const string& data) {
+ return ParseFromArray(data.data(), static_cast<int>(data.size()));
+ }
+
+ static const UnknownFieldSet* default_instance();
+ private:
+ // For InternalMergeFrom
+ friend class UnknownField;
+ // Merges from other UnknownFieldSet. This method assumes, that this object
+ // is newly created and has fields_ == NULL;
+ void InternalMergeFrom(const UnknownFieldSet& other);
+ void ClearFallback();
+
+ // fields_ is either NULL, or a pointer to a vector that is *non-empty*. We
+ // never hold the empty vector because we want the 'do we have any unknown
+ // fields' check to be fast, and avoid a cache miss: the UFS instance gets
+ // embedded in the message object, so 'fields_ != NULL' tests a member
+ // variable hot in the cache, without the need to go touch a vector somewhere
+ // else in memory.
+ std::vector<UnknownField>* fields_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(UnknownFieldSet);
+};
+
+// Represents one field in an UnknownFieldSet.
+class LIBPROTOBUF_EXPORT UnknownField {
+ public:
+ enum Type {
+ TYPE_VARINT,
+ TYPE_FIXED32,
+ TYPE_FIXED64,
+ TYPE_LENGTH_DELIMITED,
+ TYPE_GROUP
+ };
+
+ // The field's tag number, as seen on the wire.
+ inline int number() const;
+
+ // The field type.
+ inline Type type() const;
+
+ // Accessors -------------------------------------------------------
+ // Each method works only for UnknownFields of the corresponding type.
+
+ inline uint64 varint() const;
+ inline uint32 fixed32() const;
+ inline uint64 fixed64() const;
+ inline const string& length_delimited() const;
+ inline const UnknownFieldSet& group() const;
+
+ inline void set_varint(uint64 value);
+ inline void set_fixed32(uint32 value);
+ inline void set_fixed64(uint64 value);
+ inline void set_length_delimited(const string& value);
+ inline string* mutable_length_delimited();
+ inline UnknownFieldSet* mutable_group();
+
+ // Serialization API.
+ // These methods can take advantage of the underlying implementation and may
+ // archieve a better performance than using getters to retrieve the data and
+ // do the serialization yourself.
+ void SerializeLengthDelimitedNoTag(io::CodedOutputStream* output) const;
+ uint8* SerializeLengthDelimitedNoTagToArray(uint8* target) const;
+
+ inline int GetLengthDelimitedSize() const;
+
+ private:
+ friend class UnknownFieldSet;
+
+ // If this UnknownField contains a pointer, delete it.
+ void Delete();
+
+ // Reset all the underlying pointers to NULL. A special function to be only
+ // used while merging from a temporary UFS.
+ void Reset();
+
+ // Make a deep copy of any pointers in this UnknownField.
+ void DeepCopy(const UnknownField& other);
+
+ // Set the wire type of this UnknownField. Should only be used when this
+ // UnknownField is being created.
+ inline void SetType(Type type);
+
+ union LengthDelimited {
+ string* string_value_;
+ };
+
+ uint32 number_;
+ uint32 type_;
+ union {
+ uint64 varint_;
+ uint32 fixed32_;
+ uint64 fixed64_;
+ mutable union LengthDelimited length_delimited_;
+ UnknownFieldSet* group_;
+ };
+};
+
+// ===================================================================
+// inline implementations
+
+inline UnknownFieldSet::UnknownFieldSet() : fields_(NULL) {}
+
+inline UnknownFieldSet::~UnknownFieldSet() { Clear(); }
+
+inline void UnknownFieldSet::ClearAndFreeMemory() { Clear(); }
+
+inline void UnknownFieldSet::Clear() {
+ if (fields_ != NULL) {
+ ClearFallback();
+ }
+}
+
+inline bool UnknownFieldSet::empty() const {
+ // Invariant: fields_ is never empty if present.
+ return !fields_;
+}
+
+inline void UnknownFieldSet::Swap(UnknownFieldSet* x) {
+ std::swap(fields_, x->fields_);
+}
+
+inline int UnknownFieldSet::field_count() const {
+ return fields_ ? static_cast<int>(fields_->size()) : 0;
+}
+inline const UnknownField& UnknownFieldSet::field(int index) const {
+ GOOGLE_DCHECK(fields_ != NULL);
+ return (*fields_)[index];
+}
+inline UnknownField* UnknownFieldSet::mutable_field(int index) {
+ return &(*fields_)[index];
+}
+
+inline void UnknownFieldSet::AddLengthDelimited(
+ int number, const string& value) {
+ AddLengthDelimited(number)->assign(value);
+}
+
+
+inline int UnknownField::number() const { return number_; }
+inline UnknownField::Type UnknownField::type() const {
+ return static_cast<Type>(type_);
+}
+
+inline uint64 UnknownField::varint() const {
+ assert(type() == TYPE_VARINT);
+ return varint_;
+}
+inline uint32 UnknownField::fixed32() const {
+ assert(type() == TYPE_FIXED32);
+ return fixed32_;
+}
+inline uint64 UnknownField::fixed64() const {
+ assert(type() == TYPE_FIXED64);
+ return fixed64_;
+}
+inline const string& UnknownField::length_delimited() const {
+ assert(type() == TYPE_LENGTH_DELIMITED);
+ return *length_delimited_.string_value_;
+}
+inline const UnknownFieldSet& UnknownField::group() const {
+ assert(type() == TYPE_GROUP);
+ return *group_;
+}
+
+inline void UnknownField::set_varint(uint64 value) {
+ assert(type() == TYPE_VARINT);
+ varint_ = value;
+}
+inline void UnknownField::set_fixed32(uint32 value) {
+ assert(type() == TYPE_FIXED32);
+ fixed32_ = value;
+}
+inline void UnknownField::set_fixed64(uint64 value) {
+ assert(type() == TYPE_FIXED64);
+ fixed64_ = value;
+}
+inline void UnknownField::set_length_delimited(const string& value) {
+ assert(type() == TYPE_LENGTH_DELIMITED);
+ length_delimited_.string_value_->assign(value);
+}
+inline string* UnknownField::mutable_length_delimited() {
+ assert(type() == TYPE_LENGTH_DELIMITED);
+ return length_delimited_.string_value_;
+}
+inline UnknownFieldSet* UnknownField::mutable_group() {
+ assert(type() == TYPE_GROUP);
+ return group_;
+}
+
+inline int UnknownField::GetLengthDelimitedSize() const {
+ GOOGLE_DCHECK_EQ(TYPE_LENGTH_DELIMITED, type());
+ return static_cast<int>(length_delimited_.string_value_->size());
+}
+
+inline void UnknownField::SetType(Type type) {
+ type_ = type;
+}
+
+
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UNKNOWN_FIELD_SET_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set_unittest.cc
new file mode 100644
index 0000000000..5de72630a6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/unknown_field_set_unittest.cc
@@ -0,0 +1,609 @@
+// 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 test is testing a lot more than just the UnknownFieldSet class. It
+// tests handling of unknown fields throughout the system.
+
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/test_util.h>
+
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/mutex.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+
+using internal::WireFormat;
+
+class UnknownFieldSetTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ descriptor_ = unittest::TestAllTypes::descriptor();
+ TestUtil::SetAllFields(&all_fields_);
+ all_fields_.SerializeToString(&all_fields_data_);
+ ASSERT_TRUE(empty_message_.ParseFromString(all_fields_data_));
+ unknown_fields_ = empty_message_.mutable_unknown_fields();
+ }
+
+ const UnknownField* GetField(const string& name) {
+ const FieldDescriptor* field = descriptor_->FindFieldByName(name);
+ if (field == NULL) return NULL;
+ for (int i = 0; i < unknown_fields_->field_count(); i++) {
+ if (unknown_fields_->field(i).number() == field->number()) {
+ return &unknown_fields_->field(i);
+ }
+ }
+ return NULL;
+ }
+
+ // Constructs a protocol buffer which contains fields with all the same
+ // numbers as all_fields_data_ except that each field is some other wire
+ // type.
+ string GetBizarroData() {
+ unittest::TestEmptyMessage bizarro_message;
+ UnknownFieldSet* bizarro_unknown_fields =
+ bizarro_message.mutable_unknown_fields();
+ for (int i = 0; i < unknown_fields_->field_count(); i++) {
+ const UnknownField& unknown_field = unknown_fields_->field(i);
+ if (unknown_field.type() == UnknownField::TYPE_VARINT) {
+ bizarro_unknown_fields->AddFixed32(unknown_field.number(), 1);
+ } else {
+ bizarro_unknown_fields->AddVarint(unknown_field.number(), 1);
+ }
+ }
+
+ string data;
+ EXPECT_TRUE(bizarro_message.SerializeToString(&data));
+ return data;
+ }
+
+ const Descriptor* descriptor_;
+ unittest::TestAllTypes all_fields_;
+ string all_fields_data_;
+
+ // An empty message that has been parsed from all_fields_data_. So, it has
+ // unknown fields of every type.
+ unittest::TestEmptyMessage empty_message_;
+ UnknownFieldSet* unknown_fields_;
+};
+
+namespace {
+
+TEST_F(UnknownFieldSetTest, AllFieldsPresent) {
+ // All fields of TestAllTypes should be present, in numeric order (because
+ // that's the order we parsed them in). Fields that are not valid field
+ // numbers of TestAllTypes should NOT be present.
+
+ int pos = 0;
+
+ for (int i = 0; i < 1000; i++) {
+ const FieldDescriptor* field = descriptor_->FindFieldByNumber(i);
+ if (field != NULL) {
+ ASSERT_LT(pos, unknown_fields_->field_count());
+ // Do not check oneof field if it is not set.
+ if (field->containing_oneof() == NULL) {
+ EXPECT_EQ(i, unknown_fields_->field(pos++).number());
+ } else if (i == unknown_fields_->field(pos).number()) {
+ pos++;
+ }
+ if (field->is_repeated()) {
+ // Should have a second instance.
+ ASSERT_LT(pos, unknown_fields_->field_count());
+ EXPECT_EQ(i, unknown_fields_->field(pos++).number());
+ }
+ }
+ }
+ EXPECT_EQ(unknown_fields_->field_count(), pos);
+}
+
+TEST_F(UnknownFieldSetTest, Varint) {
+ const UnknownField* field = GetField("optional_int32");
+ ASSERT_TRUE(field != NULL);
+
+ ASSERT_EQ(UnknownField::TYPE_VARINT, field->type());
+ EXPECT_EQ(all_fields_.optional_int32(), field->varint());
+}
+
+TEST_F(UnknownFieldSetTest, Fixed32) {
+ const UnknownField* field = GetField("optional_fixed32");
+ ASSERT_TRUE(field != NULL);
+
+ ASSERT_EQ(UnknownField::TYPE_FIXED32, field->type());
+ EXPECT_EQ(all_fields_.optional_fixed32(), field->fixed32());
+}
+
+TEST_F(UnknownFieldSetTest, Fixed64) {
+ const UnknownField* field = GetField("optional_fixed64");
+ ASSERT_TRUE(field != NULL);
+
+ ASSERT_EQ(UnknownField::TYPE_FIXED64, field->type());
+ EXPECT_EQ(all_fields_.optional_fixed64(), field->fixed64());
+}
+
+TEST_F(UnknownFieldSetTest, LengthDelimited) {
+ const UnknownField* field = GetField("optional_string");
+ ASSERT_TRUE(field != NULL);
+
+ ASSERT_EQ(UnknownField::TYPE_LENGTH_DELIMITED, field->type());
+ EXPECT_EQ(all_fields_.optional_string(), field->length_delimited());
+}
+
+TEST_F(UnknownFieldSetTest, Group) {
+ const UnknownField* field = GetField("optionalgroup");
+ ASSERT_TRUE(field != NULL);
+
+ ASSERT_EQ(UnknownField::TYPE_GROUP, field->type());
+ ASSERT_EQ(1, field->group().field_count());
+
+ const UnknownField& nested_field = field->group().field(0);
+ const FieldDescriptor* nested_field_descriptor =
+ unittest::TestAllTypes::OptionalGroup::descriptor()->FindFieldByName("a");
+ ASSERT_TRUE(nested_field_descriptor != NULL);
+
+ EXPECT_EQ(nested_field_descriptor->number(), nested_field.number());
+ ASSERT_EQ(UnknownField::TYPE_VARINT, nested_field.type());
+ EXPECT_EQ(all_fields_.optionalgroup().a(), nested_field.varint());
+}
+
+TEST_F(UnknownFieldSetTest, SerializeFastAndSlowAreEquivalent) {
+ int size = WireFormat::ComputeUnknownFieldsSize(
+ empty_message_.unknown_fields());
+ string slow_buffer;
+ string fast_buffer;
+ slow_buffer.resize(size);
+ fast_buffer.resize(size);
+
+ uint8* target = reinterpret_cast<uint8*>(string_as_array(&fast_buffer));
+ uint8* result = WireFormat::SerializeUnknownFieldsToArray(
+ empty_message_.unknown_fields(), target);
+ EXPECT_EQ(size, result - target);
+
+ {
+ io::ArrayOutputStream raw_stream(string_as_array(&slow_buffer), size, 1);
+ io::CodedOutputStream output_stream(&raw_stream);
+ WireFormat::SerializeUnknownFields(empty_message_.unknown_fields(),
+ &output_stream);
+ ASSERT_FALSE(output_stream.HadError());
+ }
+ EXPECT_TRUE(fast_buffer == slow_buffer);
+}
+
+TEST_F(UnknownFieldSetTest, Serialize) {
+ // Check that serializing the UnknownFieldSet produces the original data
+ // again.
+
+ string data;
+ empty_message_.SerializeToString(&data);
+
+ // Don't use EXPECT_EQ because we don't want to dump raw binary data to
+ // stdout.
+ EXPECT_TRUE(data == all_fields_data_);
+}
+
+TEST_F(UnknownFieldSetTest, ParseViaReflection) {
+ // Make sure fields are properly parsed to the UnknownFieldSet when parsing
+ // via reflection.
+
+ unittest::TestEmptyMessage message;
+ io::ArrayInputStream raw_input(all_fields_data_.data(),
+ all_fields_data_.size());
+ io::CodedInputStream input(&raw_input);
+ ASSERT_TRUE(WireFormat::ParseAndMergePartial(&input, &message));
+
+ EXPECT_EQ(message.DebugString(), empty_message_.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, SerializeViaReflection) {
+ // Make sure fields are properly written from the UnknownFieldSet when
+ // serializing via reflection.
+
+ string data;
+
+ {
+ io::StringOutputStream raw_output(&data);
+ io::CodedOutputStream output(&raw_output);
+ int size = WireFormat::ByteSize(empty_message_);
+ WireFormat::SerializeWithCachedSizes(empty_message_, size, &output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Don't use EXPECT_EQ because we don't want to dump raw binary data to
+ // stdout.
+ EXPECT_TRUE(data == all_fields_data_);
+}
+
+TEST_F(UnknownFieldSetTest, CopyFrom) {
+ unittest::TestEmptyMessage message;
+
+ message.CopyFrom(empty_message_);
+
+ EXPECT_EQ(empty_message_.DebugString(), message.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, Swap) {
+ unittest::TestEmptyMessage other_message;
+ ASSERT_TRUE(other_message.ParseFromString(GetBizarroData()));
+
+ EXPECT_GT(empty_message_.unknown_fields().field_count(), 0);
+ EXPECT_GT(other_message.unknown_fields().field_count(), 0);
+ const string debug_string = empty_message_.DebugString();
+ const string other_debug_string = other_message.DebugString();
+ EXPECT_NE(debug_string, other_debug_string);
+
+ empty_message_.Swap(&other_message);
+ EXPECT_EQ(debug_string, other_message.DebugString());
+ EXPECT_EQ(other_debug_string, empty_message_.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, SwapWithSelf) {
+ const string debug_string = empty_message_.DebugString();
+ EXPECT_GT(empty_message_.unknown_fields().field_count(), 0);
+
+ empty_message_.Swap(&empty_message_);
+ EXPECT_GT(empty_message_.unknown_fields().field_count(), 0);
+ EXPECT_EQ(debug_string, empty_message_.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, MergeFrom) {
+ unittest::TestEmptyMessage source, destination;
+
+ destination.mutable_unknown_fields()->AddVarint(1, 1);
+ destination.mutable_unknown_fields()->AddVarint(3, 2);
+ source.mutable_unknown_fields()->AddVarint(2, 3);
+ source.mutable_unknown_fields()->AddVarint(3, 4);
+
+ destination.MergeFrom(source);
+
+ EXPECT_EQ(
+ // Note: The ordering of fields here depends on the ordering of adds
+ // and merging, above.
+ "1: 1\n"
+ "3: 2\n"
+ "2: 3\n"
+ "3: 4\n",
+ destination.DebugString());
+}
+
+
+TEST_F(UnknownFieldSetTest, Clear) {
+ // Clear the set.
+ empty_message_.Clear();
+ EXPECT_EQ(0, unknown_fields_->field_count());
+}
+
+TEST_F(UnknownFieldSetTest, ClearAndFreeMemory) {
+ EXPECT_GT(unknown_fields_->field_count(), 0);
+ unknown_fields_->ClearAndFreeMemory();
+ EXPECT_EQ(0, unknown_fields_->field_count());
+ unknown_fields_->AddVarint(123456, 654321);
+ EXPECT_EQ(1, unknown_fields_->field_count());
+}
+
+TEST_F(UnknownFieldSetTest, ParseKnownAndUnknown) {
+ // Test mixing known and unknown fields when parsing.
+
+ unittest::TestEmptyMessage source;
+ source.mutable_unknown_fields()->AddVarint(123456, 654321);
+ string data;
+ ASSERT_TRUE(source.SerializeToString(&data));
+
+ unittest::TestAllTypes destination;
+ ASSERT_TRUE(destination.ParseFromString(all_fields_data_ + data));
+
+ TestUtil::ExpectAllFieldsSet(destination);
+ ASSERT_EQ(1, destination.unknown_fields().field_count());
+ ASSERT_EQ(UnknownField::TYPE_VARINT,
+ destination.unknown_fields().field(0).type());
+ EXPECT_EQ(654321, destination.unknown_fields().field(0).varint());
+}
+
+TEST_F(UnknownFieldSetTest, WrongTypeTreatedAsUnknown) {
+ // Test that fields of the wrong wire type are treated like unknown fields
+ // when parsing.
+
+ unittest::TestAllTypes all_types_message;
+ unittest::TestEmptyMessage empty_message;
+ string bizarro_data = GetBizarroData();
+ ASSERT_TRUE(all_types_message.ParseFromString(bizarro_data));
+ ASSERT_TRUE(empty_message.ParseFromString(bizarro_data));
+
+ // All fields should have been interpreted as unknown, so the debug strings
+ // should be the same.
+ EXPECT_EQ(empty_message.DebugString(), all_types_message.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, WrongTypeTreatedAsUnknownViaReflection) {
+ // Same as WrongTypeTreatedAsUnknown but via the reflection interface.
+
+ unittest::TestAllTypes all_types_message;
+ unittest::TestEmptyMessage empty_message;
+ string bizarro_data = GetBizarroData();
+ io::ArrayInputStream raw_input(bizarro_data.data(), bizarro_data.size());
+ io::CodedInputStream input(&raw_input);
+ ASSERT_TRUE(WireFormat::ParseAndMergePartial(&input, &all_types_message));
+ ASSERT_TRUE(empty_message.ParseFromString(bizarro_data));
+
+ EXPECT_EQ(empty_message.DebugString(), all_types_message.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, UnknownExtensions) {
+ // Make sure fields are properly parsed to the UnknownFieldSet even when
+ // they are declared as extension numbers.
+
+ unittest::TestEmptyMessageWithExtensions message;
+ ASSERT_TRUE(message.ParseFromString(all_fields_data_));
+
+ EXPECT_EQ(message.DebugString(), empty_message_.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, UnknownExtensionsReflection) {
+ // Same as UnknownExtensions except parsing via reflection.
+
+ unittest::TestEmptyMessageWithExtensions message;
+ io::ArrayInputStream raw_input(all_fields_data_.data(),
+ all_fields_data_.size());
+ io::CodedInputStream input(&raw_input);
+ ASSERT_TRUE(WireFormat::ParseAndMergePartial(&input, &message));
+
+ EXPECT_EQ(message.DebugString(), empty_message_.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, WrongExtensionTypeTreatedAsUnknown) {
+ // Test that fields of the wrong wire type are treated like unknown fields
+ // when parsing extensions.
+
+ unittest::TestAllExtensions all_extensions_message;
+ unittest::TestEmptyMessage empty_message;
+ string bizarro_data = GetBizarroData();
+ ASSERT_TRUE(all_extensions_message.ParseFromString(bizarro_data));
+ ASSERT_TRUE(empty_message.ParseFromString(bizarro_data));
+
+ // All fields should have been interpreted as unknown, so the debug strings
+ // should be the same.
+ EXPECT_EQ(empty_message.DebugString(), all_extensions_message.DebugString());
+}
+
+TEST_F(UnknownFieldSetTest, UnknownEnumValue) {
+ using unittest::TestAllTypes;
+ using unittest::TestAllExtensions;
+ using unittest::TestEmptyMessage;
+
+ const FieldDescriptor* singular_field =
+ TestAllTypes::descriptor()->FindFieldByName("optional_nested_enum");
+ const FieldDescriptor* repeated_field =
+ TestAllTypes::descriptor()->FindFieldByName("repeated_nested_enum");
+ ASSERT_TRUE(singular_field != NULL);
+ ASSERT_TRUE(repeated_field != NULL);
+
+ string data;
+
+ {
+ TestEmptyMessage empty_message;
+ UnknownFieldSet* unknown_fields = empty_message.mutable_unknown_fields();
+ unknown_fields->AddVarint(singular_field->number(), TestAllTypes::BAR);
+ unknown_fields->AddVarint(singular_field->number(), 5); // not valid
+ unknown_fields->AddVarint(repeated_field->number(), TestAllTypes::FOO);
+ unknown_fields->AddVarint(repeated_field->number(), 4); // not valid
+ unknown_fields->AddVarint(repeated_field->number(), TestAllTypes::BAZ);
+ unknown_fields->AddVarint(repeated_field->number(), 6); // not valid
+ empty_message.SerializeToString(&data);
+ }
+
+ {
+ TestAllTypes message;
+ ASSERT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(TestAllTypes::BAR, message.optional_nested_enum());
+ ASSERT_EQ(2, message.repeated_nested_enum_size());
+ EXPECT_EQ(TestAllTypes::FOO, message.repeated_nested_enum(0));
+ EXPECT_EQ(TestAllTypes::BAZ, message.repeated_nested_enum(1));
+
+ const UnknownFieldSet& unknown_fields = message.unknown_fields();
+ ASSERT_EQ(3, unknown_fields.field_count());
+
+ EXPECT_EQ(singular_field->number(), unknown_fields.field(0).number());
+ ASSERT_EQ(UnknownField::TYPE_VARINT, unknown_fields.field(0).type());
+ EXPECT_EQ(5, unknown_fields.field(0).varint());
+
+ EXPECT_EQ(repeated_field->number(), unknown_fields.field(1).number());
+ ASSERT_EQ(UnknownField::TYPE_VARINT, unknown_fields.field(1).type());
+ EXPECT_EQ(4, unknown_fields.field(1).varint());
+
+ EXPECT_EQ(repeated_field->number(), unknown_fields.field(2).number());
+ ASSERT_EQ(UnknownField::TYPE_VARINT, unknown_fields.field(2).type());
+ EXPECT_EQ(6, unknown_fields.field(2).varint());
+ }
+
+ {
+ using unittest::optional_nested_enum_extension;
+ using unittest::repeated_nested_enum_extension;
+
+ TestAllExtensions message;
+ ASSERT_TRUE(message.ParseFromString(data));
+ EXPECT_EQ(TestAllTypes::BAR,
+ message.GetExtension(optional_nested_enum_extension));
+ ASSERT_EQ(2, message.ExtensionSize(repeated_nested_enum_extension));
+ EXPECT_EQ(TestAllTypes::FOO,
+ message.GetExtension(repeated_nested_enum_extension, 0));
+ EXPECT_EQ(TestAllTypes::BAZ,
+ message.GetExtension(repeated_nested_enum_extension, 1));
+
+ const UnknownFieldSet& unknown_fields = message.unknown_fields();
+ ASSERT_EQ(3, unknown_fields.field_count());
+
+ EXPECT_EQ(singular_field->number(), unknown_fields.field(0).number());
+ ASSERT_EQ(UnknownField::TYPE_VARINT, unknown_fields.field(0).type());
+ EXPECT_EQ(5, unknown_fields.field(0).varint());
+
+ EXPECT_EQ(repeated_field->number(), unknown_fields.field(1).number());
+ ASSERT_EQ(UnknownField::TYPE_VARINT, unknown_fields.field(1).type());
+ EXPECT_EQ(4, unknown_fields.field(1).varint());
+
+ EXPECT_EQ(repeated_field->number(), unknown_fields.field(2).number());
+ ASSERT_EQ(UnknownField::TYPE_VARINT, unknown_fields.field(2).type());
+ EXPECT_EQ(6, unknown_fields.field(2).varint());
+ }
+}
+
+TEST_F(UnknownFieldSetTest, SpaceUsedExcludingSelf) {
+ UnknownFieldSet empty;
+ empty.AddVarint(1, 0);
+ EXPECT_EQ(sizeof(vector<UnknownField>) + sizeof(UnknownField),
+ empty.SpaceUsedExcludingSelf());
+}
+
+TEST_F(UnknownFieldSetTest, SpaceUsed) {
+ unittest::TestEmptyMessage empty_message;
+
+ // Make sure an unknown field set has zero space used until a field is
+ // actually added.
+ int base_size = empty_message.SpaceUsed();
+ UnknownFieldSet* unknown_fields = empty_message.mutable_unknown_fields();
+ EXPECT_EQ(base_size, empty_message.SpaceUsed());
+
+ // Make sure each thing we add to the set increases the SpaceUsed().
+ unknown_fields->AddVarint(1, 0);
+ EXPECT_LT(base_size, empty_message.SpaceUsed());
+ base_size = empty_message.SpaceUsed();
+
+ string* str = unknown_fields->AddLengthDelimited(1);
+ EXPECT_LT(base_size, empty_message.SpaceUsed());
+ base_size = empty_message.SpaceUsed();
+
+ str->assign(sizeof(string) + 1, 'x');
+ EXPECT_LT(base_size, empty_message.SpaceUsed());
+ base_size = empty_message.SpaceUsed();
+
+ UnknownFieldSet* group = unknown_fields->AddGroup(1);
+ EXPECT_LT(base_size, empty_message.SpaceUsed());
+ base_size = empty_message.SpaceUsed();
+
+ group->AddVarint(1, 0);
+ EXPECT_LT(base_size, empty_message.SpaceUsed());
+}
+
+
+TEST_F(UnknownFieldSetTest, Empty) {
+ UnknownFieldSet unknown_fields;
+ EXPECT_TRUE(unknown_fields.empty());
+ unknown_fields.AddVarint(6, 123);
+ EXPECT_FALSE(unknown_fields.empty());
+ unknown_fields.Clear();
+ EXPECT_TRUE(unknown_fields.empty());
+}
+
+TEST_F(UnknownFieldSetTest, DeleteSubrange) {
+ // Exhaustively test the deletion of every possible subrange in arrays of all
+ // sizes from 0 through 9.
+ for (int size = 0; size < 10; ++size) {
+ for (int num = 0; num <= size; ++num) {
+ for (int start = 0; start < size - num; ++start) {
+ // Create a set with "size" fields.
+ UnknownFieldSet unknown;
+ for (int i = 0; i < size; ++i) {
+ unknown.AddFixed32(i, i);
+ }
+ // Delete the specified subrange.
+ unknown.DeleteSubrange(start, num);
+ // Make sure the resulting field values are still correct.
+ EXPECT_EQ(size - num, unknown.field_count());
+ for (int i = 0; i < unknown.field_count(); ++i) {
+ if (i < start) {
+ EXPECT_EQ(i, unknown.field(i).fixed32());
+ } else {
+ EXPECT_EQ(i + num, unknown.field(i).fixed32());
+ }
+ }
+ }
+ }
+ }
+}
+
+void CheckDeleteByNumber(const vector<int>& field_numbers, int deleted_number,
+ const vector<int>& expected_field_nubmers) {
+ UnknownFieldSet unknown_fields;
+ for (int i = 0; i < field_numbers.size(); ++i) {
+ unknown_fields.AddFixed32(field_numbers[i], i);
+ }
+ unknown_fields.DeleteByNumber(deleted_number);
+ ASSERT_EQ(expected_field_nubmers.size(), unknown_fields.field_count());
+ for (int i = 0; i < expected_field_nubmers.size(); ++i) {
+ EXPECT_EQ(expected_field_nubmers[i],
+ unknown_fields.field(i).number());
+ }
+}
+
+#define MAKE_VECTOR(x) vector<int>(x, x + GOOGLE_ARRAYSIZE(x))
+TEST_F(UnknownFieldSetTest, DeleteByNumber) {
+ CheckDeleteByNumber(vector<int>(), 1, vector<int>());
+ static const int kTestFieldNumbers1[] = {1, 2, 3};
+ static const int kFieldNumberToDelete1 = 1;
+ static const int kExpectedFieldNumbers1[] = {2, 3};
+ CheckDeleteByNumber(MAKE_VECTOR(kTestFieldNumbers1), kFieldNumberToDelete1,
+ MAKE_VECTOR(kExpectedFieldNumbers1));
+ static const int kTestFieldNumbers2[] = {1, 2, 3};
+ static const int kFieldNumberToDelete2 = 2;
+ static const int kExpectedFieldNumbers2[] = {1, 3};
+ CheckDeleteByNumber(MAKE_VECTOR(kTestFieldNumbers2), kFieldNumberToDelete2,
+ MAKE_VECTOR(kExpectedFieldNumbers2));
+ static const int kTestFieldNumbers3[] = {1, 2, 3};
+ static const int kFieldNumberToDelete3 = 3;
+ static const int kExpectedFieldNumbers3[] = {1, 2};
+ CheckDeleteByNumber(MAKE_VECTOR(kTestFieldNumbers3), kFieldNumberToDelete3,
+ MAKE_VECTOR(kExpectedFieldNumbers3));
+ static const int kTestFieldNumbers4[] = {1, 2, 1, 4, 1};
+ static const int kFieldNumberToDelete4 = 1;
+ static const int kExpectedFieldNumbers4[] = {2, 4};
+ CheckDeleteByNumber(MAKE_VECTOR(kTestFieldNumbers4), kFieldNumberToDelete4,
+ MAKE_VECTOR(kExpectedFieldNumbers4));
+ static const int kTestFieldNumbers5[] = {1, 2, 3, 4, 5};
+ static const int kFieldNumberToDelete5 = 6;
+ static const int kExpectedFieldNumbers5[] = {1, 2, 3, 4, 5};
+ CheckDeleteByNumber(MAKE_VECTOR(kTestFieldNumbers5), kFieldNumberToDelete5,
+ MAKE_VECTOR(kExpectedFieldNumbers5));
+}
+#undef MAKE_VECTOR
+} // namespace
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.cc
new file mode 100644
index 0000000000..a1a56ee674
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.cc
@@ -0,0 +1,208 @@
+// 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: ksroka@google.com (Krzysztof Sroka)
+
+#include <google/protobuf/util/field_comparator.h>
+
+#include <string>
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/mathlimits.h>
+#include <google/protobuf/stubs/mathutil.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+FieldComparator::FieldComparator() {}
+FieldComparator::~FieldComparator() {}
+
+DefaultFieldComparator::DefaultFieldComparator()
+ : float_comparison_(EXACT),
+ treat_nan_as_equal_(false),
+ has_default_tolerance_(false) {
+}
+
+DefaultFieldComparator::~DefaultFieldComparator() {}
+
+FieldComparator::ComparisonResult DefaultFieldComparator::Compare(
+ const google::protobuf::Message& message_1,
+ const google::protobuf::Message& message_2,
+ const google::protobuf::FieldDescriptor* field,
+ int index_1, int index_2,
+ const google::protobuf::util::FieldContext* field_context) {
+ const Reflection* reflection_1 = message_1.GetReflection();
+ const Reflection* reflection_2 = message_2.GetReflection();
+
+ switch (field->cpp_type()) {
+#define COMPARE_FIELD(METHOD) \
+ if (field->is_repeated()) { \
+ return ResultFromBoolean(Compare##METHOD( \
+ *field, \
+ reflection_1->GetRepeated##METHOD(message_1, field, index_1), \
+ reflection_2->GetRepeated##METHOD(message_2, field, index_2))); \
+ } else { \
+ return ResultFromBoolean(Compare##METHOD( \
+ *field, \
+ reflection_1->Get##METHOD(message_1, field), \
+ reflection_2->Get##METHOD(message_2, field))); \
+ } \
+ break; // Make sure no fall-through is introduced.
+
+ case FieldDescriptor::CPPTYPE_BOOL:
+ COMPARE_FIELD(Bool);
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ COMPARE_FIELD(Double);
+ case FieldDescriptor::CPPTYPE_ENUM:
+ COMPARE_FIELD(Enum);
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ COMPARE_FIELD(Float);
+ case FieldDescriptor::CPPTYPE_INT32:
+ COMPARE_FIELD(Int32);
+ case FieldDescriptor::CPPTYPE_INT64:
+ COMPARE_FIELD(Int64);
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (field->is_repeated()) {
+ // Allocate scratch strings to store the result if a conversion is
+ // needed.
+ string scratch1;
+ string scratch2;
+ return ResultFromBoolean(
+ CompareString(*field, reflection_1->GetRepeatedStringReference(
+ message_1, field, index_1, &scratch1),
+ reflection_2->GetRepeatedStringReference(
+ message_2, field, index_2, &scratch2)));
+ } else {
+ // Allocate scratch strings to store the result if a conversion is
+ // needed.
+ string scratch1;
+ string scratch2;
+ return ResultFromBoolean(CompareString(
+ *field,
+ reflection_1->GetStringReference(message_1, field, &scratch1),
+ reflection_2->GetStringReference(message_2, field, &scratch2)));
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ COMPARE_FIELD(UInt32);
+ case FieldDescriptor::CPPTYPE_UINT64:
+ COMPARE_FIELD(UInt64);
+
+#undef COMPARE_FIELD
+
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ return RECURSE;
+
+ default:
+ GOOGLE_LOG(FATAL) << "No comparison code for field " << field->full_name()
+ << " of CppType = " << field->cpp_type();
+ return DIFFERENT;
+ }
+}
+
+void DefaultFieldComparator::SetDefaultFractionAndMargin(double fraction,
+ double margin) {
+ default_tolerance_ = Tolerance(fraction, margin);
+ has_default_tolerance_ = true;
+}
+
+void DefaultFieldComparator::SetFractionAndMargin(const FieldDescriptor* field,
+ double fraction,
+ double margin) {
+ GOOGLE_CHECK(FieldDescriptor::CPPTYPE_FLOAT == field->cpp_type() ||
+ FieldDescriptor::CPPTYPE_DOUBLE == field->cpp_type())
+ << "Field has to be float or double type. Field name is: "
+ << field->full_name();
+ map_tolerance_[field] = Tolerance(fraction, margin);
+}
+
+bool DefaultFieldComparator::CompareDouble(const FieldDescriptor& field,
+ double value_1, double value_2) {
+ return CompareDoubleOrFloat(field, value_1, value_2);
+}
+
+bool DefaultFieldComparator::CompareEnum(const FieldDescriptor& field,
+ const EnumValueDescriptor* value_1,
+ const EnumValueDescriptor* value_2) {
+ return value_1->number() == value_2->number();
+}
+
+bool DefaultFieldComparator::CompareFloat(const FieldDescriptor& field,
+ float value_1, float value_2) {
+ return CompareDoubleOrFloat(field, value_1, value_2);
+}
+
+template<typename T>
+bool DefaultFieldComparator::CompareDoubleOrFloat(const FieldDescriptor& field,
+ T value_1, T value_2) {
+ if (value_1 == value_2) {
+ // Covers +inf and -inf (which are not within margin or fraction of
+ // themselves), and is a shortcut for finite values.
+ return true;
+ } else if (float_comparison_ == EXACT) {
+ if (treat_nan_as_equal_ &&
+ MathLimits<T>::IsNaN(value_1) && MathLimits<T>::IsNaN(value_2)) {
+ return true;
+ }
+ return false;
+ } else {
+ if (treat_nan_as_equal_ &&
+ MathLimits<T>::IsNaN(value_1) && MathLimits<T>::IsNaN(value_2)) {
+ return true;
+ }
+ // float_comparison_ == APPROXIMATE covers two use cases.
+ Tolerance* tolerance = FindOrNull(map_tolerance_, &field);
+ if (tolerance == NULL && has_default_tolerance_) {
+ tolerance = &default_tolerance_;
+ }
+ if (tolerance == NULL) {
+ return MathUtil::AlmostEquals(value_1, value_2);
+ } else {
+ // Use user-provided fraction and margin. Since they are stored as
+ // doubles, we explicitly cast them to types of values provided. This
+ // is very likely to fail if provided values are not numeric.
+ return MathUtil::WithinFractionOrMargin(
+ value_1, value_2, static_cast<T>(tolerance->fraction),
+ static_cast<T>(tolerance->margin));
+ }
+ }
+}
+
+FieldComparator::ComparisonResult DefaultFieldComparator::ResultFromBoolean(
+ bool boolean_result) const {
+ return boolean_result ? FieldComparator::SAME : FieldComparator::DIFFERENT;
+}
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.h
new file mode 100644
index 0000000000..1b4d65b0e6
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator.h
@@ -0,0 +1,259 @@
+// 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: ksroka@google.com (Krzysztof Sroka)
+
+#ifndef GOOGLE_PROTOBUF_UTIL_FIELD_COMPARATOR_H__
+#define GOOGLE_PROTOBUF_UTIL_FIELD_COMPARATOR_H__
+
+#include <map>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+
+class Message;
+class EnumValueDescriptor;
+class FieldDescriptor;
+
+namespace util {
+
+class FieldContext;
+
+// Base class specifying the interface for comparing protocol buffer fields.
+// Regular users should consider using or subclassing DefaultFieldComparator
+// rather than this interface.
+// Currently, this does not support comparing unknown fields.
+class LIBPROTOBUF_EXPORT FieldComparator {
+ public:
+ FieldComparator();
+ virtual ~FieldComparator();
+
+ enum ComparisonResult {
+ SAME, // Compared fields are equal. In case of comparing submessages,
+ // user should not recursively compare their contents.
+ DIFFERENT, // Compared fields are different. In case of comparing
+ // submessages, user should not recursively compare their
+ // contents.
+ RECURSE, // Compared submessages need to be compared recursively.
+ // FieldComparator does not specify the semantics of recursive
+ // comparison. This value should not be returned for simple
+ // values.
+ };
+
+ // Compares the values of a field in two protocol buffer messages.
+ // Returns SAME or DIFFERENT for simple values, and SAME, DIFFERENT or RECURSE
+ // for submessages. Returning RECURSE for fields not being submessages is
+ // illegal.
+ // In case the given FieldDescriptor points to a repeated field, the indices
+ // need to be valid. Otherwise they should be ignored.
+ //
+ // FieldContext contains information about the specific instances of the
+ // fields being compared, versus FieldDescriptor which only contains general
+ // type information about the fields.
+ virtual ComparisonResult Compare(
+ const google::protobuf::Message& message_1,
+ const google::protobuf::Message& message_2,
+ const google::protobuf::FieldDescriptor* field,
+ int index_1, int index_2,
+ const google::protobuf::util::FieldContext* field_context) = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldComparator);
+};
+
+// Basic implementation of FieldComparator. Supports three modes of floating
+// point value comparison: exact, approximate using MathUtil::AlmostEqual
+// method, and arbitrarily precise using MathUtil::WithinFractionOrMargin.
+class LIBPROTOBUF_EXPORT DefaultFieldComparator : public FieldComparator {
+ public:
+ enum FloatComparison {
+ EXACT, // Floats and doubles are compared exactly.
+ APPROXIMATE, // Floats and doubles are compared using the
+ // MathUtil::AlmostEqual method or
+ // MathUtil::WithinFractionOrMargin method.
+ // TODO(ksroka): Introduce third value to differenciate uses of AlmostEqual
+ // and WithinFractionOrMargin.
+ };
+
+ // Creates new comparator with float comparison set to EXACT.
+ DefaultFieldComparator();
+
+ virtual ~DefaultFieldComparator();
+
+ virtual ComparisonResult Compare(
+ const google::protobuf::Message& message_1,
+ const google::protobuf::Message& message_2,
+ const google::protobuf::FieldDescriptor* field,
+ int index_1, int index_2,
+ const google::protobuf::util::FieldContext* field_context);
+
+ void set_float_comparison(FloatComparison float_comparison) {
+ float_comparison_ = float_comparison;
+ }
+
+ FloatComparison float_comparison() const {
+ return float_comparison_;
+ }
+
+ // Set whether the FieldComparator shall treat floats or doubles that are both
+ // NaN as equal (treat_nan_as_equal = true) or as different
+ // (treat_nan_as_equal = false). Default is treating NaNs always as different.
+ void set_treat_nan_as_equal(bool treat_nan_as_equal) {
+ treat_nan_as_equal_ = treat_nan_as_equal;
+ }
+
+ bool treat_nan_as_equal() const {
+ return treat_nan_as_equal_;
+ }
+
+ // Sets the fraction and margin for the float comparison of a given field.
+ // Uses MathUtil::WithinFractionOrMargin to compare the values.
+ //
+ // REQUIRES: field->cpp_type == FieldDescriptor::CPPTYPE_DOUBLE or
+ // field->cpp_type == FieldDescriptor::CPPTYPE_FLOAT
+ // REQUIRES: float_comparison_ == APPROXIMATE
+ void SetFractionAndMargin(const FieldDescriptor* field, double fraction,
+ double margin);
+
+ // Sets the fraction and margin for the float comparison of all float and
+ // double fields, unless a field has been given a specific setting via
+ // SetFractionAndMargin() above.
+ // Uses MathUtil::WithinFractionOrMargin to compare the values.
+ //
+ // REQUIRES: float_comparison_ == APPROXIMATE
+ void SetDefaultFractionAndMargin(double fraction, double margin);
+
+ private:
+ // Defines the tolerance for floating point comparison (fraction and margin).
+ struct Tolerance {
+ double fraction;
+ double margin;
+ Tolerance()
+ : fraction(0.0),
+ margin(0.0) {}
+ Tolerance(double f, double m)
+ : fraction(f),
+ margin(m) {}
+ };
+
+ // Defines the map to store the tolerances for floating point comparison.
+ typedef map<const FieldDescriptor*, Tolerance> ToleranceMap;
+
+ // The following methods get executed when CompareFields is called for the
+ // basic types (instead of submessages). They return true on success. One
+ // can use ResultFromBoolean() to convert that boolean to a ComparisonResult
+ // value.
+ bool CompareBool(const google::protobuf::FieldDescriptor& field,
+ bool value_1, bool value_2) {
+ return value_1 == value_2;
+ }
+
+ // Uses CompareDoubleOrFloat, a helper function used by both CompareDouble and
+ // CompareFloat.
+ bool CompareDouble(const google::protobuf::FieldDescriptor& field,
+ double value_1, double value_2);
+
+ bool CompareEnum(const google::protobuf::FieldDescriptor& field,
+ const EnumValueDescriptor* value_1,
+ const EnumValueDescriptor* value_2);
+
+ // Uses CompareDoubleOrFloat, a helper function used by both CompareDouble and
+ // CompareFloat.
+ bool CompareFloat(const google::protobuf::FieldDescriptor& field,
+ float value_1, float value_2);
+
+ bool CompareInt32(const google::protobuf::FieldDescriptor& field,
+ int32 value_1, int32 value_2) {
+ return value_1 == value_2;
+ }
+
+ bool CompareInt64(const google::protobuf::FieldDescriptor& field,
+ int64 value_1, int64 value_2) {
+ return value_1 == value_2;
+ }
+
+ bool CompareString(const google::protobuf::FieldDescriptor& field,
+ const string& value_1, const string& value_2) {
+ return value_1 == value_2;
+ }
+
+ bool CompareUInt32(const google::protobuf::FieldDescriptor& field,
+ uint32 value_1, uint32 value_2) {
+ return value_1 == value_2;
+ }
+
+ bool CompareUInt64(const google::protobuf::FieldDescriptor& field,
+ uint64 value_1, uint64 value_2) {
+ return value_1 == value_2;
+ }
+
+ // This function is used by CompareDouble and CompareFloat to avoid code
+ // duplication. There are no checks done against types of the values passed,
+ // but it's likely to fail if passed non-numeric arguments.
+ template<typename T>
+ bool CompareDoubleOrFloat(const google::protobuf::FieldDescriptor& field,
+ T value_1, T value_2);
+
+ // Returns FieldComparator::SAME if boolean_result is true and
+ // FieldComparator::DIFFERENT otherwise.
+ ComparisonResult ResultFromBoolean(bool boolean_result) const;
+
+ FloatComparison float_comparison_;
+
+ // If true, floats and doubles that are both NaN are considered to be
+ // equal. Otherwise, two floats or doubles that are NaN are considered to be
+ // different.
+ bool treat_nan_as_equal_;
+
+ // True iff default_tolerance_ has been explicitly set.
+ //
+ // If false, then the default tolerance for flaots and doubles is that which
+ // is used by MathUtil::AlmostEquals().
+ bool has_default_tolerance_;
+
+ // Default float/double tolerance. Only meaningful if
+ // has_default_tolerance_ == true.
+ Tolerance default_tolerance_;
+
+ // Field-specific float/double tolerances, which override any default for
+ // those particular fields.
+ ToleranceMap map_tolerance_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DefaultFieldComparator);
+};
+
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_FIELD_COMPARATOR_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator_test.cc
new file mode 100644
index 0000000000..6fd631d860
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_comparator_test.cc
@@ -0,0 +1,488 @@
+// 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: ksroka@google.com (Krzysztof Sroka)
+
+#include <google/protobuf/util/field_comparator.h>
+
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/stubs/mathutil.h>
+// This gtest header is put after mathutil.h intentionally. We have to do
+// this because mathutil.h includes mathlimits.h which requires cmath not
+// being included to compile on some versions of gcc:
+// https://github.com/google/protobuf/blob/818c5eee08840355d70d2f3bdf1a2f17986a5e70/src/google/protobuf/stubs/mathlimits.h#L48
+// and the opensource version gtest.h header includes cmath transitively
+// somehow.
+#include <gtest/gtest.h>
+namespace google {
+namespace protobuf {
+namespace util {
+namespace {
+
+using protobuf_unittest::TestAllTypes;
+
+class DefaultFieldComparatorTest : public ::testing::Test {
+ protected:
+ void SetUp() {
+ descriptor_ = TestAllTypes::descriptor();
+ }
+
+ const Descriptor* descriptor_;
+ DefaultFieldComparator comparator_;
+ TestAllTypes message_1_;
+ TestAllTypes message_2_;
+};
+
+TEST_F(DefaultFieldComparatorTest, RecursesIntoGroup) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optionalgroup");
+ EXPECT_EQ(FieldComparator::RECURSE,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, RecursesIntoNestedMessage) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optional_nested_message");
+ EXPECT_EQ(FieldComparator::RECURSE,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, RecursesIntoForeignMessage) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optional_foreign_message");
+ EXPECT_EQ(FieldComparator::RECURSE,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, Int32Comparison) {
+ const FieldDescriptor* field = descriptor_->FindFieldByName("optional_int32");
+ message_1_.set_optional_int32(1);
+ message_2_.set_optional_int32(1);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+
+ message_2_.set_optional_int32(-1);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, Int64Comparison) {
+ const FieldDescriptor* field = descriptor_->FindFieldByName("optional_int64");
+ message_1_.set_optional_int64(1L);
+ message_2_.set_optional_int64(1L);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+
+ message_2_.set_optional_int64(-1L);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, UInt32Comparison) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optional_uint32");
+ message_1_.set_optional_uint32(1);
+ message_2_.set_optional_uint32(1);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+
+ message_2_.set_optional_uint32(2);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, UInt64Comparison) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optional_uint64");
+ message_1_.set_optional_uint64(1L);
+ message_2_.set_optional_uint64(1L);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+
+ message_2_.set_optional_uint64(2L);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, BooleanComparison) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optional_bool");
+ message_1_.set_optional_bool(true);
+ message_2_.set_optional_bool(true);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+
+ message_2_.set_optional_bool(false);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, EnumComparison) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optional_nested_enum");
+ message_1_.set_optional_nested_enum(TestAllTypes::BAR);
+ message_2_.set_optional_nested_enum(TestAllTypes::BAR);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+
+ message_2_.set_optional_nested_enum(TestAllTypes::BAZ);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, StringComparison) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("optional_string");
+ message_1_.set_optional_string("foo");
+ message_2_.set_optional_string("foo");
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+
+ message_2_.set_optional_string("bar");
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, FloatingPointComparisonExact) {
+ const FieldDescriptor* field_float =
+ descriptor_->FindFieldByName("optional_float");
+ const FieldDescriptor* field_double =
+ descriptor_->FindFieldByName("optional_double");
+
+ message_1_.set_optional_float(0.1f);
+ message_2_.set_optional_float(0.1f);
+ message_1_.set_optional_double(0.1);
+ message_2_.set_optional_double(0.1);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ message_2_.set_optional_float(0.2f);
+ message_2_.set_optional_double(0.2);
+
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, FloatingPointComparisonApproximate) {
+ const FieldDescriptor* field_float =
+ descriptor_->FindFieldByName("optional_float");
+ const FieldDescriptor* field_double =
+ descriptor_->FindFieldByName("optional_double");
+
+ message_1_.set_optional_float(2.300005f);
+ message_2_.set_optional_float(2.300006f);
+ message_1_.set_optional_double(2.3000000000000003);
+ message_2_.set_optional_double(2.3000000000000007);
+
+ // Approximate comparison depends on MathUtil, so we assert on MathUtil
+ // results first to check if that's where the failure was introduced.
+ ASSERT_NE(message_1_.optional_float(), message_2_.optional_float());
+ ASSERT_NE(message_1_.optional_double(), message_2_.optional_double());
+ ASSERT_TRUE(MathUtil::AlmostEquals(message_1_.optional_float(),
+ message_2_.optional_float()));
+ ASSERT_TRUE(MathUtil::AlmostEquals(message_1_.optional_double(),
+ message_2_.optional_double()));
+
+ // DefaultFieldComparator's default float comparison mode is EXACT.
+ ASSERT_EQ(DefaultFieldComparator::EXACT, comparator_.float_comparison());
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ comparator_.set_float_comparison(DefaultFieldComparator::APPROXIMATE);
+
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest, FloatingPointComparisonTreatNaNsAsEqual) {
+ const FieldDescriptor* field_float =
+ descriptor_->FindFieldByName("optional_float");
+ const FieldDescriptor* field_double =
+ descriptor_->FindFieldByName("optional_double");
+
+ message_1_.set_optional_float(MathLimits<float>::kNaN);
+ message_2_.set_optional_float(MathLimits<float>::kNaN);
+ message_1_.set_optional_double(MathLimits<double>::kNaN);
+ message_2_.set_optional_double(MathLimits<double>::kNaN);
+
+ // DefaultFieldComparator's default float comparison mode is EXACT with
+ // treating NaNs as different.
+ ASSERT_EQ(DefaultFieldComparator::EXACT, comparator_.float_comparison());
+ ASSERT_EQ(false, comparator_.treat_nan_as_equal());
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+ comparator_.set_float_comparison(DefaultFieldComparator::APPROXIMATE);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ comparator_.set_treat_nan_as_equal(true);
+ ASSERT_EQ(true, comparator_.treat_nan_as_equal());
+ comparator_.set_float_comparison(DefaultFieldComparator::EXACT);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+ comparator_.set_float_comparison(DefaultFieldComparator::APPROXIMATE);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest,
+ FloatingPointComparisonWithinFractionOrMargin) {
+ const FieldDescriptor* field_float =
+ descriptor_->FindFieldByName("optional_float");
+ const FieldDescriptor* field_double =
+ descriptor_->FindFieldByName("optional_double");
+
+ message_1_.set_optional_float(100.0f);
+ message_2_.set_optional_float(109.9f);
+ message_1_.set_optional_double(100.0);
+ message_2_.set_optional_double(109.9);
+
+ comparator_.set_float_comparison(DefaultFieldComparator::APPROXIMATE);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Should fail since the fraction is too low.
+ comparator_.SetFractionAndMargin(field_float, 0.01, 0.0);
+ comparator_.SetFractionAndMargin(field_double, 0.01, 0.0);
+
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Should fail since the margin is too low.
+ comparator_.SetFractionAndMargin(field_float, 0.0, 9.0);
+ comparator_.SetFractionAndMargin(field_double, 0.0, 9.0);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Should succeed since the fraction is high enough.
+ comparator_.SetFractionAndMargin(field_float, 0.2, 0.0);
+ comparator_.SetFractionAndMargin(field_double, 0.2, 0.0);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Should succeed since the margin is high enough.
+ comparator_.SetFractionAndMargin(field_float, 0.0, 10.0);
+ comparator_.SetFractionAndMargin(field_double, 0.0, 10.0);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Setting values for one of the fields should not affect the other.
+ comparator_.SetFractionAndMargin(field_double, 0.0, 0.0);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // +inf should be equal even though they are not technically within margin or
+ // fraction.
+ message_1_.set_optional_float(numeric_limits<float>::infinity());
+ message_2_.set_optional_float(numeric_limits<float>::infinity());
+ message_1_.set_optional_double(numeric_limits<double>::infinity());
+ message_2_.set_optional_double(numeric_limits<double>::infinity());
+ comparator_.SetFractionAndMargin(field_float, 0.0, 0.0);
+ comparator_.SetFractionAndMargin(field_double, 0.0, 0.0);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // -inf should be equal even though they are not technically within margin or
+ // fraction.
+ message_1_.set_optional_float(-numeric_limits<float>::infinity());
+ message_2_.set_optional_float(-numeric_limits<float>::infinity());
+ message_1_.set_optional_double(-numeric_limits<double>::infinity());
+ message_2_.set_optional_double(-numeric_limits<double>::infinity());
+ comparator_.SetFractionAndMargin(field_float, 0.0, 0.0);
+ comparator_.SetFractionAndMargin(field_double, 0.0, 0.0);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+}
+
+TEST_F(DefaultFieldComparatorTest,
+ FloatingPointComparisonWithinDefaultFractionOrMargin) {
+ const FieldDescriptor* field_float =
+ descriptor_->FindFieldByName("optional_float");
+ const FieldDescriptor* field_double =
+ descriptor_->FindFieldByName("optional_double");
+
+ message_1_.set_optional_float(100.0f);
+ message_2_.set_optional_float(109.9f);
+ message_1_.set_optional_double(100.0);
+ message_2_.set_optional_double(109.9);
+
+ comparator_.set_float_comparison(DefaultFieldComparator::APPROXIMATE);
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Set default fraction and margin.
+ comparator_.SetDefaultFractionAndMargin(0.01, 0.0);
+
+ // Float comparisons should fail since the fraction is too low.
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Set field-specific fraction and margin for one field (field_float) but not
+ // the other (field_double)
+ comparator_.SetFractionAndMargin(field_float, 0.2, 0.0);
+
+ // The field with the override should succeed, since its field-specific
+ // fraction is high enough.
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ // The field with no override should fail, since the default fraction is too
+ // low
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // Set the default fraction and margin high enough so that fields that use
+ // the default should succeed
+ comparator_.SetDefaultFractionAndMargin(0.2, 0.0);
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+
+ // The field with an override should still be OK
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+
+ // Set fraction and margin for the field with an override to be too low
+ comparator_.SetFractionAndMargin(field_float, 0.01, 0.0);
+
+ // Now our default is high enough but field_float's override is too low.
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_,
+ field_float, -1, -1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_,
+ field_double, -1, -1, NULL));
+}
+
+// Simple test checking whether we compare values at correct indices.
+TEST_F(DefaultFieldComparatorTest, RepeatedFieldComparison) {
+ const FieldDescriptor* field =
+ descriptor_->FindFieldByName("repeated_string");
+
+ message_1_.add_repeated_string("foo");
+ message_1_.add_repeated_string("bar");
+ message_2_.add_repeated_string("bar");
+ message_2_.add_repeated_string("baz");
+
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, 0, 0, NULL));
+ EXPECT_EQ(FieldComparator::DIFFERENT,
+ comparator_.Compare(message_1_, message_2_, field, 1, 1, NULL));
+ EXPECT_EQ(FieldComparator::SAME,
+ comparator_.Compare(message_1_, message_2_, field, 1, 0, NULL));
+}
+
+} // namespace util
+} // namespace protobuf
+} // namespace
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.cc
new file mode 100644
index 0000000000..409010a075
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.cc
@@ -0,0 +1,538 @@
+// 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.
+
+#include <google/protobuf/util/field_mask_util.h>
+
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+using google::protobuf::FieldMask;
+
+string FieldMaskUtil::ToString(const FieldMask& mask) {
+ return Join(mask.paths(), ",");
+}
+
+void FieldMaskUtil::FromString(StringPiece str, FieldMask* out) {
+ out->Clear();
+ vector<string> paths = Split(str, ",");
+ for (int i = 0; i < paths.size(); ++i) {
+ if (paths[i].empty()) continue;
+ out->add_paths(paths[i]);
+ }
+}
+
+bool FieldMaskUtil::SnakeCaseToCamelCase(StringPiece input, string* output) {
+ output->clear();
+ bool after_underscore = false;
+ for (int i = 0; i < input.size(); ++i) {
+ if (input[i] >= 'A' && input[i] <= 'Z') {
+ // The field name must not contain uppercase letters.
+ return false;
+ }
+ if (after_underscore) {
+ if (input[i] >= 'a' && input[i] <= 'z') {
+ output->push_back(input[i] + 'A' - 'a');
+ after_underscore = false;
+ } else {
+ // The character after a "_" must be a lowercase letter.
+ return false;
+ }
+ } else if (input[i] == '_') {
+ after_underscore = true;
+ } else {
+ output->push_back(input[i]);
+ }
+ }
+ if (after_underscore) {
+ // Trailing "_".
+ return false;
+ }
+ return true;
+}
+
+bool FieldMaskUtil::CamelCaseToSnakeCase(StringPiece input, string* output) {
+ output->clear();
+ for (int i = 0; i < input.size(); ++i) {
+ if (input[i] == '_') {
+ // The field name must not contain "_"s.
+ return false;
+ }
+ if (input[i] >= 'A' && input[i] <= 'Z') {
+ output->push_back('_');
+ output->push_back(input[i] + 'a' - 'A');
+ } else {
+ output->push_back(input[i]);
+ }
+ }
+ return true;
+}
+
+bool FieldMaskUtil::ToJsonString(const FieldMask& mask, string* out) {
+ out->clear();
+ for (int i = 0; i < mask.paths_size(); ++i) {
+ const string& path = mask.paths(i);
+ string camelcase_path;
+ if (!SnakeCaseToCamelCase(path, &camelcase_path)) {
+ return false;
+ }
+ if (i > 0) {
+ out->push_back(',');
+ }
+ out->append(camelcase_path);
+ }
+ return true;
+}
+
+bool FieldMaskUtil::FromJsonString(StringPiece str, FieldMask* out) {
+ out->Clear();
+ vector<string> paths = Split(str, ",");
+ for (int i = 0; i < paths.size(); ++i) {
+ if (paths[i].empty()) continue;
+ string snakecase_path;
+ if (!CamelCaseToSnakeCase(paths[i], &snakecase_path)) {
+ return false;
+ }
+ out->add_paths(snakecase_path);
+ }
+ return true;
+}
+
+bool FieldMaskUtil::InternalIsValidPath(const Descriptor* descriptor,
+ StringPiece path) {
+ vector<string> parts = Split(path, ".");
+ for (int i = 0; i < parts.size(); ++i) {
+ const string& field_name = parts[i];
+ if (descriptor == NULL) {
+ return false;
+ }
+ const FieldDescriptor* field = descriptor->FindFieldByName(field_name);
+ if (field == NULL) {
+ return false;
+ }
+ if (!field->is_repeated() &&
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ descriptor = field->message_type();
+ } else {
+ descriptor = NULL;
+ }
+ }
+ return true;
+}
+
+void FieldMaskUtil::InternalGetFieldMaskForAllFields(
+ const Descriptor* descriptor, FieldMask* out) {
+ for (int i = 0; i < descriptor->field_count(); ++i) {
+ out->add_paths(descriptor->field(i)->name());
+ }
+}
+
+namespace {
+// A FieldMaskTree represents a FieldMask in a tree structure. For example,
+// given a FieldMask "foo.bar,foo.baz,bar.baz", the FieldMaskTree will be:
+//
+// [root] -+- foo -+- bar
+// | |
+// | +- baz
+// |
+// +- bar --- baz
+//
+// In the tree, each leaf node represents a field path.
+class FieldMaskTree {
+ public:
+ FieldMaskTree();
+ ~FieldMaskTree();
+
+ void MergeFromFieldMask(const FieldMask& mask);
+ void MergeToFieldMask(FieldMask* mask);
+
+ // Add a field path into the tree. In a FieldMask, each field path matches
+ // the specified field and also all its sub-fields. If the field path to
+ // add is a sub-path of an existing field path in the tree (i.e., a leaf
+ // node), it means the tree already matches the given path so nothing will
+ // be added to the tree. If the path matches an existing non-leaf node in the
+ // tree, that non-leaf node will be turned into a leaf node with all its
+ // children removed because the path matches all the node's children.
+ void AddPath(const string& path);
+
+ // Calculate the intersection part of a field path with this tree and add
+ // the intersection field path into out.
+ void IntersectPath(const string& path, FieldMaskTree* out);
+
+ // Merge all fields specified by this tree from one message to another.
+ void MergeMessage(const Message& source,
+ const FieldMaskUtil::MergeOptions& options,
+ Message* destination) {
+ // Do nothing if the tree is empty.
+ if (root_.children.empty()) {
+ return;
+ }
+ MergeMessage(&root_, source, options, destination);
+ }
+
+ // Trims all fields not specified by this tree from the given message.
+ void TrimMessage(Message* message) {
+ // Do nothing if the tree is empty.
+ if (root_.children.empty()) {
+ return;
+ }
+ TrimMessage(&root_, message);
+ }
+
+ private:
+ struct Node {
+ Node() {}
+
+ ~Node() { ClearChildren(); }
+
+ void ClearChildren() {
+ for (map<string, Node*>::iterator it = children.begin();
+ it != children.end(); ++it) {
+ delete it->second;
+ }
+ children.clear();
+ }
+
+ map<string, Node*> children;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Node);
+ };
+
+ // Merge a sub-tree to mask. This method adds the field paths represented
+ // by all leaf nodes descended from "node" to mask.
+ void MergeToFieldMask(const string& prefix, const Node* node, FieldMask* out);
+
+ // Merge all leaf nodes of a sub-tree to another tree.
+ void MergeLeafNodesToTree(const string& prefix, const Node* node,
+ FieldMaskTree* out);
+
+ // Merge all fields specified by a sub-tree from one message to another.
+ void MergeMessage(const Node* node, const Message& source,
+ const FieldMaskUtil::MergeOptions& options,
+ Message* destination);
+
+ // Trims all fields not specified by this sub-tree from the given message.
+ void TrimMessage(const Node* node, Message* message);
+
+ Node root_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldMaskTree);
+};
+
+FieldMaskTree::FieldMaskTree() {}
+
+FieldMaskTree::~FieldMaskTree() {}
+
+void FieldMaskTree::MergeFromFieldMask(const FieldMask& mask) {
+ for (int i = 0; i < mask.paths_size(); ++i) {
+ AddPath(mask.paths(i));
+ }
+}
+
+void FieldMaskTree::MergeToFieldMask(FieldMask* mask) {
+ MergeToFieldMask("", &root_, mask);
+}
+
+void FieldMaskTree::MergeToFieldMask(const string& prefix, const Node* node,
+ FieldMask* out) {
+ if (node->children.empty()) {
+ if (prefix.empty()) {
+ // This is the root node.
+ return;
+ }
+ out->add_paths(prefix);
+ return;
+ }
+ for (map<string, Node*>::const_iterator it = node->children.begin();
+ it != node->children.end(); ++it) {
+ string current_path = prefix.empty() ? it->first : prefix + "." + it->first;
+ MergeToFieldMask(current_path, it->second, out);
+ }
+}
+
+void FieldMaskTree::AddPath(const string& path) {
+ vector<string> parts = Split(path, ".");
+ if (parts.empty()) {
+ return;
+ }
+ bool new_branch = false;
+ Node* node = &root_;
+ for (int i = 0; i < parts.size(); ++i) {
+ if (!new_branch && node != &root_ && node->children.empty()) {
+ // Path matches an existing leaf node. This means the path is already
+ // coverred by this tree (for example, adding "foo.bar.baz" to a tree
+ // which already contains "foo.bar").
+ return;
+ }
+ const string& node_name = parts[i];
+ Node*& child = node->children[node_name];
+ if (child == NULL) {
+ new_branch = true;
+ child = new Node();
+ }
+ node = child;
+ }
+ if (!node->children.empty()) {
+ node->ClearChildren();
+ }
+}
+
+void FieldMaskTree::IntersectPath(const string& path, FieldMaskTree* out) {
+ vector<string> parts = Split(path, ".");
+ if (parts.empty()) {
+ return;
+ }
+ const Node* node = &root_;
+ for (int i = 0; i < parts.size(); ++i) {
+ if (node->children.empty()) {
+ if (node != &root_) {
+ out->AddPath(path);
+ }
+ return;
+ }
+ const string& node_name = parts[i];
+ const Node* result = FindPtrOrNull(node->children, node_name);
+ if (result == NULL) {
+ // No intersection found.
+ return;
+ }
+ node = result;
+ }
+ // Now we found a matching node with the given path. Add all leaf nodes
+ // to out.
+ MergeLeafNodesToTree(path, node, out);
+}
+
+void FieldMaskTree::MergeLeafNodesToTree(const string& prefix, const Node* node,
+ FieldMaskTree* out) {
+ if (node->children.empty()) {
+ out->AddPath(prefix);
+ }
+ for (map<string, Node*>::const_iterator it = node->children.begin();
+ it != node->children.end(); ++it) {
+ string current_path = prefix.empty() ? it->first : prefix + "." + it->first;
+ MergeLeafNodesToTree(current_path, it->second, out);
+ }
+}
+
+void FieldMaskTree::MergeMessage(const Node* node, const Message& source,
+ const FieldMaskUtil::MergeOptions& options,
+ Message* destination) {
+ GOOGLE_DCHECK(!node->children.empty());
+ const Reflection* source_reflection = source.GetReflection();
+ const Reflection* destination_reflection = destination->GetReflection();
+ const Descriptor* descriptor = source.GetDescriptor();
+ for (map<string, Node*>::const_iterator it = node->children.begin();
+ it != node->children.end(); ++it) {
+ const string& field_name = it->first;
+ const Node* child = it->second;
+ const FieldDescriptor* field = descriptor->FindFieldByName(field_name);
+ if (field == NULL) {
+ GOOGLE_LOG(ERROR) << "Cannot find field \"" << field_name << "\" in message "
+ << descriptor->full_name();
+ continue;
+ }
+ if (!child->children.empty()) {
+ // Sub-paths are only allowed for singular message fields.
+ if (field->is_repeated() ||
+ field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ GOOGLE_LOG(ERROR) << "Field \"" << field_name << "\" in message "
+ << descriptor->full_name()
+ << " is not a singular message field and cannot "
+ << "have sub-fields.";
+ continue;
+ }
+ MergeMessage(child, source_reflection->GetMessage(source, field), options,
+ destination_reflection->MutableMessage(destination, field));
+ continue;
+ }
+ if (!field->is_repeated()) {
+ switch (field->cpp_type()) {
+#define COPY_VALUE(TYPE, Name) \
+ case FieldDescriptor::CPPTYPE_##TYPE: { \
+ if (source_reflection->HasField(source, field)) { \
+ destination_reflection->Set##Name( \
+ destination, field, source_reflection->Get##Name(source, field)); \
+ } else { \
+ destination_reflection->ClearField(destination, field); \
+ } \
+ break; \
+ }
+ COPY_VALUE(BOOL, Bool)
+ COPY_VALUE(INT32, Int32)
+ COPY_VALUE(INT64, Int64)
+ COPY_VALUE(UINT32, UInt32)
+ COPY_VALUE(UINT64, UInt64)
+ COPY_VALUE(FLOAT, Float)
+ COPY_VALUE(DOUBLE, Double)
+ COPY_VALUE(ENUM, Enum)
+ COPY_VALUE(STRING, String)
+#undef COPY_VALUE
+ case FieldDescriptor::CPPTYPE_MESSAGE: {
+ if (options.replace_message_fields()) {
+ destination_reflection->ClearField(destination, field);
+ }
+ if (source_reflection->HasField(source, field)) {
+ destination_reflection->MutableMessage(destination, field)
+ ->MergeFrom(source_reflection->GetMessage(source, field));
+ }
+ break;
+ }
+ }
+ } else {
+ if (options.replace_repeated_fields()) {
+ destination_reflection->ClearField(destination, field);
+ }
+ switch (field->cpp_type()) {
+#define COPY_REPEATED_VALUE(TYPE, Name) \
+ case FieldDescriptor::CPPTYPE_##TYPE: { \
+ int size = source_reflection->FieldSize(source, field); \
+ for (int i = 0; i < size; ++i) { \
+ destination_reflection->Add##Name( \
+ destination, field, \
+ source_reflection->GetRepeated##Name(source, field, i)); \
+ } \
+ break; \
+ }
+ COPY_REPEATED_VALUE(BOOL, Bool)
+ COPY_REPEATED_VALUE(INT32, Int32)
+ COPY_REPEATED_VALUE(INT64, Int64)
+ COPY_REPEATED_VALUE(UINT32, UInt32)
+ COPY_REPEATED_VALUE(UINT64, UInt64)
+ COPY_REPEATED_VALUE(FLOAT, Float)
+ COPY_REPEATED_VALUE(DOUBLE, Double)
+ COPY_REPEATED_VALUE(ENUM, Enum)
+ COPY_REPEATED_VALUE(STRING, String)
+#undef COPY_REPEATED_VALUE
+ case FieldDescriptor::CPPTYPE_MESSAGE: {
+ int size = source_reflection->FieldSize(source, field);
+ for (int i = 0; i < size; ++i) {
+ destination_reflection->AddMessage(destination, field)
+ ->MergeFrom(
+ source_reflection->GetRepeatedMessage(source, field, i));
+ }
+ break;
+ }
+ }
+ }
+ }
+}
+
+void FieldMaskTree::TrimMessage(const Node* node, Message* message) {
+ GOOGLE_DCHECK(!node->children.empty());
+ const Reflection* reflection = message->GetReflection();
+ const Descriptor* descriptor = message->GetDescriptor();
+ const int32 field_count = descriptor->field_count();
+ for (int index = 0; index < field_count; ++index) {
+ const FieldDescriptor* field = descriptor->field(index);
+ if (!ContainsKey(node->children, field->name())) {
+ reflection->ClearField(message, field);
+ } else {
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ Node* child = node->children.at(field->name());
+ if (!child->children.empty()) {
+ TrimMessage(child, reflection->MutableMessage(message, field));
+ }
+ }
+ }
+ }
+}
+
+} // namespace
+
+void FieldMaskUtil::ToCanonicalForm(const FieldMask& mask, FieldMask* out) {
+ FieldMaskTree tree;
+ tree.MergeFromFieldMask(mask);
+ out->Clear();
+ tree.MergeToFieldMask(out);
+}
+
+void FieldMaskUtil::Union(const FieldMask& mask1, const FieldMask& mask2,
+ FieldMask* out) {
+ FieldMaskTree tree;
+ tree.MergeFromFieldMask(mask1);
+ tree.MergeFromFieldMask(mask2);
+ out->Clear();
+ tree.MergeToFieldMask(out);
+}
+
+void FieldMaskUtil::Intersect(const FieldMask& mask1, const FieldMask& mask2,
+ FieldMask* out) {
+ FieldMaskTree tree, intersection;
+ tree.MergeFromFieldMask(mask1);
+ for (int i = 0; i < mask2.paths_size(); ++i) {
+ tree.IntersectPath(mask2.paths(i), &intersection);
+ }
+ out->Clear();
+ intersection.MergeToFieldMask(out);
+}
+
+bool FieldMaskUtil::IsPathInFieldMask(StringPiece path, const FieldMask& mask) {
+ for (int i = 0; i < mask.paths_size(); ++i) {
+ const string& mask_path = mask.paths(i);
+ if (path == mask_path) {
+ return true;
+ } else if (mask_path.length() < path.length()) {
+ // Also check whether mask.paths(i) is a prefix of path.
+ if (path.substr(0, mask_path.length() + 1).compare(mask_path + ".") ==
+ 0) {
+ return true;
+ }
+ }
+ }
+ return false;
+}
+
+void FieldMaskUtil::MergeMessageTo(const Message& source, const FieldMask& mask,
+ const MergeOptions& options,
+ Message* destination) {
+ GOOGLE_CHECK(source.GetDescriptor() == destination->GetDescriptor());
+ // Build a FieldMaskTree and walk through the tree to merge all specified
+ // fields.
+ FieldMaskTree tree;
+ tree.MergeFromFieldMask(mask);
+ tree.MergeMessage(source, options, destination);
+}
+
+void FieldMaskUtil::TrimMessage(const FieldMask& mask, Message* destination) {
+ // Build a FieldMaskTree and walk through the tree to merge all specified
+ // fields.
+ FieldMaskTree tree;
+ tree.MergeFromFieldMask(mask);
+ tree.TrimMessage(GOOGLE_CHECK_NOTNULL(destination));
+}
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.h
new file mode 100644
index 0000000000..e79b65e94e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util.h
@@ -0,0 +1,193 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_FIELD_MASK_UTIL_H__
+#define GOOGLE_PROTOBUF_UTIL_FIELD_MASK_UTIL_H__
+
+#include <string>
+
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/field_mask.pb.h>
+#include <google/protobuf/stubs/stringpiece.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+class LIBPROTOBUF_EXPORT FieldMaskUtil {
+ typedef google::protobuf::FieldMask FieldMask;
+
+ public:
+ // Converts FieldMask to/from string, formatted by separating each path
+ // with a comma (e.g., "foo_bar,baz.quz").
+ static string ToString(const FieldMask& mask);
+ static void FromString(StringPiece str, FieldMask* out);
+
+ // Converts FieldMask to/from string, formatted according to proto3 JSON
+ // spec for FieldMask (e.g., "fooBar,baz.quz"). If the field name is not
+ // style conforming (i.e., not snake_case when converted to string, or not
+ // camelCase when converted from string), the conversion will fail.
+ static bool ToJsonString(const FieldMask& mask, string* out);
+ static bool FromJsonString(StringPiece str, FieldMask* out);
+
+ // Checks whether the given path is valid for type T.
+ template <typename T>
+ static bool IsValidPath(StringPiece path) {
+ return InternalIsValidPath(T::descriptor(), path);
+ }
+
+ // Checks whether the given FieldMask is valid for type T.
+ template <typename T>
+ static bool IsValidFieldMask(const FieldMask& mask) {
+ for (int i = 0; i < mask.paths_size(); ++i) {
+ if (!InternalIsValidPath(T::descriptor(), mask.paths(i))) return false;
+ }
+ return true;
+ }
+
+ // Adds a path to FieldMask after checking whether the given path is valid.
+ // This method check-fails if the path is not a valid path for type T.
+ template <typename T>
+ static void AddPathToFieldMask(StringPiece path, FieldMask* mask) {
+ GOOGLE_CHECK(IsValidPath<T>(path));
+ mask->add_paths(path);
+ }
+
+ // Creates a FieldMask with all fields of type T. This FieldMask only
+ // contains fields of T but not any sub-message fields.
+ template <typename T>
+ static void GetFieldMaskForAllFields(FieldMask* out) {
+ InternalGetFieldMaskForAllFields(T::descriptor(), out);
+ }
+
+ // Converts a FieldMask to the canonical form. It will:
+ // 1. Remove paths that are covered by another path. For example,
+ // "foo.bar" is covered by "foo" and will be removed if "foo"
+ // is also in the FieldMask.
+ // 2. Sort all paths in alphabetical order.
+ static void ToCanonicalForm(const FieldMask& mask, FieldMask* out);
+
+ // Creates an union of two FieldMasks.
+ static void Union(const FieldMask& mask1, const FieldMask& mask2,
+ FieldMask* out);
+
+ // Creates an intersection of two FieldMasks.
+ static void Intersect(const FieldMask& mask1, const FieldMask& mask2,
+ FieldMask* out);
+
+ // Returns true if path is covered by the given FieldMask. Note that path
+ // "foo.bar" covers all paths like "foo.bar.baz", "foo.bar.quz.x", etc.
+ static bool IsPathInFieldMask(StringPiece path, const FieldMask& mask);
+
+ class MergeOptions;
+ // Merges fields specified in a FieldMask into another message. See the
+ // comments in MergeOptions regarding compatibility with
+ // google/protobuf/field_mask.proto
+ static void MergeMessageTo(const Message& source, const FieldMask& mask,
+ const MergeOptions& options, Message* destination);
+
+ // Removes from 'message' any field that is not represented in the given
+ // FieldMask. If the FieldMask is empty, does nothing.
+ static void TrimMessage(const FieldMask& mask, Message* message);
+
+ private:
+ friend class SnakeCaseCamelCaseTest;
+ // Converts a field name from snake_case to camelCase:
+ // 1. Every character after "_" will be converted to uppercase.
+ // 2. All "_"s are removed.
+ // The conversion will fail if:
+ // 1. The field name contains uppercase letters.
+ // 2. Any character after a "_" is not a lowercase letter.
+ // If the conversion succeeds, it's guaranteed that the resulted
+ // camelCase name will yield the original snake_case name when
+ // converted using CamelCaseToSnakeCase().
+ //
+ // Note that the input can contain characters not allowed in C identifiers.
+ // For example, "foo_bar,baz_quz" will be converted to "fooBar,bazQuz"
+ // successfully.
+ static bool SnakeCaseToCamelCase(StringPiece input, string* output);
+ // Converts a field name from camelCase to snake_case:
+ // 1. Every uppercase letter is converted to lowercase with a additional
+ // preceding "-".
+ // The conversion will fail if:
+ // 1. The field name contains "_"s.
+ // If the conversion succeeds, it's guaranteed that the resulted
+ // snake_case name will yield the original camelCase name when
+ // converted using SnakeCaseToCamelCase().
+ //
+ // Note that the input can contain characters not allowed in C identifiers.
+ // For example, "fooBar,bazQuz" will be converted to "foo_bar,baz_quz"
+ // successfully.
+ static bool CamelCaseToSnakeCase(StringPiece input, string* output);
+
+ static bool InternalIsValidPath(const Descriptor* descriptor,
+ StringPiece path);
+
+ static void InternalGetFieldMaskForAllFields(const Descriptor* descriptor,
+ FieldMask* out);
+};
+
+// Note that for compatibility with the defined behaviour for FieldMask in
+// google/protobuf/field_mask.proto, set replace_message_fields and
+// replace_repeated_fields to 'true'. The default options are not compatible
+// with google/protobuf/field_mask.proto.
+class LIBPROTOBUF_EXPORT FieldMaskUtil::MergeOptions {
+ public:
+ MergeOptions()
+ : replace_message_fields_(false), replace_repeated_fields_(false) {}
+ // When merging message fields, the default behavior is to merge the
+ // content of two message fields together. If you instead want to use
+ // the field from the source message to replace the corresponding field
+ // in the destination message, set this flag to true. When this flag is set,
+ // specified submessage fields that are missing in source will be cleared in
+ // destination.
+ void set_replace_message_fields(bool value) {
+ replace_message_fields_ = value;
+ }
+ bool replace_message_fields() const { return replace_message_fields_; }
+ // The default merging behavior will append entries from the source
+ // repeated field to the destination repeated field. If you only want
+ // to keep the entries from the source repeated field, set this flag
+ // to true.
+ void set_replace_repeated_fields(bool value) {
+ replace_repeated_fields_ = value;
+ }
+ bool replace_repeated_fields() const { return replace_repeated_fields_; }
+
+ private:
+ bool replace_message_fields_;
+ bool replace_repeated_fields_;
+};
+
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_FIELD_MASK_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util_test.cc
new file mode 100644
index 0000000000..43fb79057a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/field_mask_util_test.cc
@@ -0,0 +1,606 @@
+// 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.
+
+#include <google/protobuf/util/field_mask_util.h>
+
+#include <algorithm>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/field_mask.pb.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/test_util.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+class SnakeCaseCamelCaseTest : public ::testing::Test {
+ protected:
+ string SnakeCaseToCamelCase(const string& input) {
+ string output;
+ if (FieldMaskUtil::SnakeCaseToCamelCase(input, &output)) {
+ return output;
+ } else {
+ return "#FAIL#";
+ }
+ }
+
+ string CamelCaseToSnakeCase(const string& input) {
+ string output;
+ if (FieldMaskUtil::CamelCaseToSnakeCase(input, &output)) {
+ return output;
+ } else {
+ return "#FAIL#";
+ }
+ }
+};
+
+namespace {
+
+TEST_F(SnakeCaseCamelCaseTest, SnakeToCamel) {
+ EXPECT_EQ("fooBar", SnakeCaseToCamelCase("foo_bar"));
+ EXPECT_EQ("FooBar", SnakeCaseToCamelCase("_foo_bar"));
+ EXPECT_EQ("foo3Bar", SnakeCaseToCamelCase("foo3_bar"));
+ // No uppercase letter is allowed.
+ EXPECT_EQ("#FAIL#", SnakeCaseToCamelCase("Foo"));
+ // Any character after a "_" must be a lowercase letter.
+ // 1. "_" cannot be followed by another "_".
+ // 2. "_" cannot be followed by a digit.
+ // 3. "_" cannot appear as the last character.
+ EXPECT_EQ("#FAIL#", SnakeCaseToCamelCase("foo__bar"));
+ EXPECT_EQ("#FAIL#", SnakeCaseToCamelCase("foo_3bar"));
+ EXPECT_EQ("#FAIL#", SnakeCaseToCamelCase("foo_bar_"));
+}
+
+TEST_F(SnakeCaseCamelCaseTest, CamelToSnake) {
+ EXPECT_EQ("foo_bar", CamelCaseToSnakeCase("fooBar"));
+ EXPECT_EQ("_foo_bar", CamelCaseToSnakeCase("FooBar"));
+ EXPECT_EQ("foo3_bar", CamelCaseToSnakeCase("foo3Bar"));
+ // "_"s are not allowed.
+ EXPECT_EQ("#FAIL#", CamelCaseToSnakeCase("foo_bar"));
+}
+
+TEST_F(SnakeCaseCamelCaseTest, RoundTripTest) {
+ // Enumerates all possible snake_case names and test that converting it to
+ // camelCase and then to snake_case again will yield the original name.
+ string name = "___abc123";
+ std::sort(name.begin(), name.end());
+ do {
+ string camelName = SnakeCaseToCamelCase(name);
+ if (camelName != "#FAIL#") {
+ EXPECT_EQ(name, CamelCaseToSnakeCase(camelName));
+ }
+ } while (std::next_permutation(name.begin(), name.end()));
+
+ // Enumerates all possible camelCase names and test that converting it to
+ // snake_case and then to camelCase again will yield the original name.
+ name = "abcABC123";
+ std::sort(name.begin(), name.end());
+ do {
+ string camelName = CamelCaseToSnakeCase(name);
+ if (camelName != "#FAIL#") {
+ EXPECT_EQ(name, SnakeCaseToCamelCase(camelName));
+ }
+ } while (std::next_permutation(name.begin(), name.end()));
+}
+
+using protobuf_unittest::TestAllTypes;
+using protobuf_unittest::NestedTestAllTypes;
+using google::protobuf::FieldMask;
+
+TEST(FieldMaskUtilTest, StringFormat) {
+ FieldMask mask;
+ EXPECT_EQ("", FieldMaskUtil::ToString(mask));
+ mask.add_paths("foo_bar");
+ EXPECT_EQ("foo_bar", FieldMaskUtil::ToString(mask));
+ mask.add_paths("baz_quz");
+ EXPECT_EQ("foo_bar,baz_quz", FieldMaskUtil::ToString(mask));
+
+ FieldMaskUtil::FromString("", &mask);
+ EXPECT_EQ(0, mask.paths_size());
+ FieldMaskUtil::FromString("fooBar", &mask);
+ EXPECT_EQ(1, mask.paths_size());
+ EXPECT_EQ("fooBar", mask.paths(0));
+ FieldMaskUtil::FromString("fooBar,bazQuz", &mask);
+ EXPECT_EQ(2, mask.paths_size());
+ EXPECT_EQ("fooBar", mask.paths(0));
+ EXPECT_EQ("bazQuz", mask.paths(1));
+}
+
+TEST(FieldMaskUtilTest, JsonStringFormat) {
+ FieldMask mask;
+ string value;
+ EXPECT_TRUE(FieldMaskUtil::ToJsonString(mask, &value));
+ EXPECT_EQ("", value);
+ mask.add_paths("foo_bar");
+ EXPECT_TRUE(FieldMaskUtil::ToJsonString(mask, &value));
+ EXPECT_EQ("fooBar", value);
+ mask.add_paths("bar_quz");
+ EXPECT_TRUE(FieldMaskUtil::ToJsonString(mask, &value));
+ EXPECT_EQ("fooBar,barQuz", value);
+
+ FieldMaskUtil::FromJsonString("", &mask);
+ EXPECT_EQ(0, mask.paths_size());
+ FieldMaskUtil::FromJsonString("fooBar", &mask);
+ EXPECT_EQ(1, mask.paths_size());
+ EXPECT_EQ("foo_bar", mask.paths(0));
+ FieldMaskUtil::FromJsonString("fooBar,bazQuz", &mask);
+ EXPECT_EQ(2, mask.paths_size());
+ EXPECT_EQ("foo_bar", mask.paths(0));
+ EXPECT_EQ("baz_quz", mask.paths(1));
+}
+
+TEST(FieldMaskUtilTest, TestIsVaildPath) {
+ EXPECT_TRUE(FieldMaskUtil::IsValidPath<TestAllTypes>("optional_int32"));
+ EXPECT_FALSE(FieldMaskUtil::IsValidPath<TestAllTypes>("optional_nonexist"));
+ EXPECT_TRUE(
+ FieldMaskUtil::IsValidPath<TestAllTypes>("optional_nested_message.bb"));
+ EXPECT_FALSE(FieldMaskUtil::IsValidPath<TestAllTypes>(
+ "optional_nested_message.nonexist"));
+ // FieldMask cannot be used to specify sub-fields of a repeated message.
+ EXPECT_FALSE(
+ FieldMaskUtil::IsValidPath<TestAllTypes>("repeated_nested_message.bb"));
+}
+
+TEST(FieldMaskUtilTest, TestIsValidFieldMask) {
+ FieldMask mask;
+ FieldMaskUtil::FromString("optional_int32,optional_nested_message.bb", &mask);
+ EXPECT_TRUE(FieldMaskUtil::IsValidFieldMask<TestAllTypes>(mask));
+
+ FieldMaskUtil::FromString(
+ "optional_int32,optional_nested_message.bb,optional_nonexist", &mask);
+ EXPECT_FALSE(FieldMaskUtil::IsValidFieldMask<TestAllTypes>(mask));
+}
+
+TEST(FieldMaskUtilTest, TestGetFieldMaskForAllFields) {
+ FieldMask mask;
+ FieldMaskUtil::GetFieldMaskForAllFields<TestAllTypes::NestedMessage>(&mask);
+ EXPECT_EQ(1, mask.paths_size());
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("bb", mask));
+
+ FieldMaskUtil::GetFieldMaskForAllFields<TestAllTypes>(&mask);
+ EXPECT_EQ(76, mask.paths_size());
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_int32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_int64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_uint32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_uint64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_sint32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_sint64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_fixed32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_fixed64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_sfixed32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_sfixed64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_float", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_double", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_bool", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_string", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_bytes", mask));
+ EXPECT_TRUE(
+ FieldMaskUtil::IsPathInFieldMask("optional_nested_message", mask));
+ EXPECT_TRUE(
+ FieldMaskUtil::IsPathInFieldMask("optional_foreign_message", mask));
+ EXPECT_TRUE(
+ FieldMaskUtil::IsPathInFieldMask("optional_import_message", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_nested_enum", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_foreign_enum", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("optional_import_enum", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_int32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_int64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_uint32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_uint64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_sint32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_sint64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_fixed32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_fixed64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_sfixed32", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_sfixed64", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_float", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_double", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_bool", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_string", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_bytes", mask));
+ EXPECT_TRUE(
+ FieldMaskUtil::IsPathInFieldMask("repeated_nested_message", mask));
+ EXPECT_TRUE(
+ FieldMaskUtil::IsPathInFieldMask("repeated_foreign_message", mask));
+ EXPECT_TRUE(
+ FieldMaskUtil::IsPathInFieldMask("repeated_import_message", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_nested_enum", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_foreign_enum", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("repeated_import_enum", mask));
+}
+
+TEST(FieldMaskUtilTest, TestToCanonicalForm) {
+ FieldMask in, out;
+ // Paths will be sorted.
+ FieldMaskUtil::FromString("baz.quz,bar,foo", &in);
+ FieldMaskUtil::ToCanonicalForm(in, &out);
+ EXPECT_EQ("bar,baz.quz,foo", FieldMaskUtil::ToString(out));
+ // Duplicated paths will be removed.
+ FieldMaskUtil::FromString("foo,bar,foo", &in);
+ FieldMaskUtil::ToCanonicalForm(in, &out);
+ EXPECT_EQ("bar,foo", FieldMaskUtil::ToString(out));
+ // Sub-paths of other paths will be removed.
+ FieldMaskUtil::FromString("foo.b1,bar.b1,foo.b2,bar", &in);
+ FieldMaskUtil::ToCanonicalForm(in, &out);
+ EXPECT_EQ("bar,foo.b1,foo.b2", FieldMaskUtil::ToString(out));
+
+ // Test more deeply nested cases.
+ FieldMaskUtil::FromString(
+ "foo.bar.baz1,"
+ "foo.bar.baz2.quz,"
+ "foo.bar.baz2",
+ &in);
+ FieldMaskUtil::ToCanonicalForm(in, &out);
+ EXPECT_EQ("foo.bar.baz1,foo.bar.baz2", FieldMaskUtil::ToString(out));
+ FieldMaskUtil::FromString(
+ "foo.bar.baz1,"
+ "foo.bar.baz2,"
+ "foo.bar.baz2.quz",
+ &in);
+ FieldMaskUtil::ToCanonicalForm(in, &out);
+ EXPECT_EQ("foo.bar.baz1,foo.bar.baz2", FieldMaskUtil::ToString(out));
+ FieldMaskUtil::FromString(
+ "foo.bar.baz1,"
+ "foo.bar.baz2,"
+ "foo.bar.baz2.quz,"
+ "foo.bar",
+ &in);
+ FieldMaskUtil::ToCanonicalForm(in, &out);
+ EXPECT_EQ("foo.bar", FieldMaskUtil::ToString(out));
+ FieldMaskUtil::FromString(
+ "foo.bar.baz1,"
+ "foo.bar.baz2,"
+ "foo.bar.baz2.quz,"
+ "foo",
+ &in);
+ FieldMaskUtil::ToCanonicalForm(in, &out);
+ EXPECT_EQ("foo", FieldMaskUtil::ToString(out));
+}
+
+TEST(FieldMaskUtilTest, TestUnion) {
+ FieldMask mask1, mask2, out;
+ // Test cases without overlapping.
+ FieldMaskUtil::FromString("foo,baz", &mask1);
+ FieldMaskUtil::FromString("bar,quz", &mask2);
+ FieldMaskUtil::Union(mask1, mask2, &out);
+ EXPECT_EQ("bar,baz,foo,quz", FieldMaskUtil::ToString(out));
+ // Overlap with duplicated paths.
+ FieldMaskUtil::FromString("foo,baz.bb", &mask1);
+ FieldMaskUtil::FromString("baz.bb,quz", &mask2);
+ FieldMaskUtil::Union(mask1, mask2, &out);
+ EXPECT_EQ("baz.bb,foo,quz", FieldMaskUtil::ToString(out));
+ // Overlap with paths covering some other paths.
+ FieldMaskUtil::FromString("foo.bar.baz,quz", &mask1);
+ FieldMaskUtil::FromString("foo.bar,bar", &mask2);
+ FieldMaskUtil::Union(mask1, mask2, &out);
+ EXPECT_EQ("bar,foo.bar,quz", FieldMaskUtil::ToString(out));
+}
+
+TEST(FieldMaskUtilTest, TestIntersect) {
+ FieldMask mask1, mask2, out;
+ // Test cases without overlapping.
+ FieldMaskUtil::FromString("foo,baz", &mask1);
+ FieldMaskUtil::FromString("bar,quz", &mask2);
+ FieldMaskUtil::Intersect(mask1, mask2, &out);
+ EXPECT_EQ("", FieldMaskUtil::ToString(out));
+ // Overlap with duplicated paths.
+ FieldMaskUtil::FromString("foo,baz.bb", &mask1);
+ FieldMaskUtil::FromString("baz.bb,quz", &mask2);
+ FieldMaskUtil::Intersect(mask1, mask2, &out);
+ EXPECT_EQ("baz.bb", FieldMaskUtil::ToString(out));
+ // Overlap with paths covering some other paths.
+ FieldMaskUtil::FromString("foo.bar.baz,quz", &mask1);
+ FieldMaskUtil::FromString("foo.bar,bar", &mask2);
+ FieldMaskUtil::Intersect(mask1, mask2, &out);
+ EXPECT_EQ("foo.bar.baz", FieldMaskUtil::ToString(out));
+}
+
+TEST(FieldMaskUtilTest, TestIspathInFieldMask) {
+ FieldMask mask;
+ FieldMaskUtil::FromString("foo.bar", &mask);
+ EXPECT_FALSE(FieldMaskUtil::IsPathInFieldMask("", mask));
+ EXPECT_FALSE(FieldMaskUtil::IsPathInFieldMask("foo", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("foo.bar", mask));
+ EXPECT_TRUE(FieldMaskUtil::IsPathInFieldMask("foo.bar.baz", mask));
+ EXPECT_FALSE(FieldMaskUtil::IsPathInFieldMask("foo.bar0.baz", mask));
+}
+
+TEST(FieldMaskUtilTest, MergeMessage) {
+ TestAllTypes src, dst;
+ TestUtil::SetAllFields(&src);
+ FieldMaskUtil::MergeOptions options;
+
+#define TEST_MERGE_ONE_PRIMITIVE_FIELD(field_name) \
+ { \
+ TestAllTypes tmp; \
+ tmp.set_##field_name(src.field_name()); \
+ FieldMask mask; \
+ mask.add_paths(#field_name); \
+ dst.Clear(); \
+ FieldMaskUtil::MergeMessageTo(src, mask, options, &dst); \
+ EXPECT_EQ(tmp.DebugString(), dst.DebugString()); \
+ src.clear_##field_name(); \
+ tmp.clear_##field_name(); \
+ FieldMaskUtil::MergeMessageTo(src, mask, options, &dst); \
+ EXPECT_EQ(tmp.DebugString(), dst.DebugString()); \
+ }
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_int32)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_int64)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_uint32)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_uint64)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_sint32)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_sint64)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_fixed32)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_fixed64)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_sfixed32)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_sfixed64)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_float)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_double)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_bool)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_string)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_bytes)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_nested_enum)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_foreign_enum)
+ TEST_MERGE_ONE_PRIMITIVE_FIELD(optional_import_enum)
+#undef TEST_MERGE_ONE_PRIMITIVE_FIELD
+
+#define TEST_MERGE_ONE_FIELD(field_name) \
+ { \
+ TestAllTypes tmp; \
+ *tmp.mutable_##field_name() = src.field_name(); \
+ FieldMask mask; \
+ mask.add_paths(#field_name); \
+ dst.Clear(); \
+ FieldMaskUtil::MergeMessageTo(src, mask, options, &dst); \
+ EXPECT_EQ(tmp.DebugString(), dst.DebugString()); \
+ }
+ TEST_MERGE_ONE_FIELD(optional_nested_message)
+ TEST_MERGE_ONE_FIELD(optional_foreign_message)
+ TEST_MERGE_ONE_FIELD(optional_import_message)
+
+ TEST_MERGE_ONE_FIELD(repeated_int32)
+ TEST_MERGE_ONE_FIELD(repeated_int64)
+ TEST_MERGE_ONE_FIELD(repeated_uint32)
+ TEST_MERGE_ONE_FIELD(repeated_uint64)
+ TEST_MERGE_ONE_FIELD(repeated_sint32)
+ TEST_MERGE_ONE_FIELD(repeated_sint64)
+ TEST_MERGE_ONE_FIELD(repeated_fixed32)
+ TEST_MERGE_ONE_FIELD(repeated_fixed64)
+ TEST_MERGE_ONE_FIELD(repeated_sfixed32)
+ TEST_MERGE_ONE_FIELD(repeated_sfixed64)
+ TEST_MERGE_ONE_FIELD(repeated_float)
+ TEST_MERGE_ONE_FIELD(repeated_double)
+ TEST_MERGE_ONE_FIELD(repeated_bool)
+ TEST_MERGE_ONE_FIELD(repeated_string)
+ TEST_MERGE_ONE_FIELD(repeated_bytes)
+ TEST_MERGE_ONE_FIELD(repeated_nested_message)
+ TEST_MERGE_ONE_FIELD(repeated_foreign_message)
+ TEST_MERGE_ONE_FIELD(repeated_import_message)
+ TEST_MERGE_ONE_FIELD(repeated_nested_enum)
+ TEST_MERGE_ONE_FIELD(repeated_foreign_enum)
+ TEST_MERGE_ONE_FIELD(repeated_import_enum)
+#undef TEST_MERGE_ONE_FIELD
+
+ // Test merge nested fields.
+ NestedTestAllTypes nested_src, nested_dst;
+ nested_src.mutable_child()->mutable_payload()->set_optional_int32(1234);
+ nested_src.mutable_child()
+ ->mutable_child()
+ ->mutable_payload()
+ ->set_optional_int32(5678);
+ FieldMask mask;
+ FieldMaskUtil::FromString("child.payload", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_EQ(1234, nested_dst.child().payload().optional_int32());
+ EXPECT_EQ(0, nested_dst.child().child().payload().optional_int32());
+
+ FieldMaskUtil::FromString("child.child.payload", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_EQ(1234, nested_dst.child().payload().optional_int32());
+ EXPECT_EQ(5678, nested_dst.child().child().payload().optional_int32());
+
+ nested_dst.Clear();
+ FieldMaskUtil::FromString("child.child.payload", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_EQ(0, nested_dst.child().payload().optional_int32());
+ EXPECT_EQ(5678, nested_dst.child().child().payload().optional_int32());
+
+ nested_dst.Clear();
+ FieldMaskUtil::FromString("child", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_EQ(1234, nested_dst.child().payload().optional_int32());
+ EXPECT_EQ(5678, nested_dst.child().child().payload().optional_int32());
+
+ // Test MergeOptions.
+
+ nested_dst.Clear();
+ nested_dst.mutable_child()->mutable_payload()->set_optional_int64(4321);
+ // Message fields will be merged by default.
+ FieldMaskUtil::FromString("child.payload", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_EQ(1234, nested_dst.child().payload().optional_int32());
+ EXPECT_EQ(4321, nested_dst.child().payload().optional_int64());
+ // Change the behavior to replace message fields.
+ options.set_replace_message_fields(true);
+ FieldMaskUtil::FromString("child.payload", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_EQ(1234, nested_dst.child().payload().optional_int32());
+ EXPECT_EQ(0, nested_dst.child().payload().optional_int64());
+
+ // By default, fields missing in source are not cleared in destination.
+ options.set_replace_message_fields(false);
+ nested_dst.mutable_payload();
+ EXPECT_TRUE(nested_dst.has_payload());
+ FieldMaskUtil::FromString("payload", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_TRUE(nested_dst.has_payload());
+ // But they are cleared when replacing message fields.
+ options.set_replace_message_fields(true);
+ nested_dst.Clear();
+ nested_dst.mutable_payload();
+ FieldMaskUtil::FromString("payload", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ EXPECT_FALSE(nested_dst.has_payload());
+
+ nested_src.mutable_payload()->add_repeated_int32(1234);
+ nested_dst.mutable_payload()->add_repeated_int32(5678);
+ // Repeated fields will be appended by default.
+ FieldMaskUtil::FromString("payload.repeated_int32", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ ASSERT_EQ(2, nested_dst.payload().repeated_int32_size());
+ EXPECT_EQ(5678, nested_dst.payload().repeated_int32(0));
+ EXPECT_EQ(1234, nested_dst.payload().repeated_int32(1));
+ // Change the behavior to replace repeated fields.
+ options.set_replace_repeated_fields(true);
+ FieldMaskUtil::FromString("payload.repeated_int32", &mask);
+ FieldMaskUtil::MergeMessageTo(nested_src, mask, options, &nested_dst);
+ ASSERT_EQ(1, nested_dst.payload().repeated_int32_size());
+ EXPECT_EQ(1234, nested_dst.payload().repeated_int32(0));
+}
+
+TEST(FieldMaskUtilTest, TrimMessage) {
+#define TEST_TRIM_ONE_PRIMITIVE_FIELD(field_name) \
+ { \
+ TestAllTypes msg; \
+ TestUtil::SetAllFields(&msg); \
+ TestAllTypes tmp; \
+ tmp.set_##field_name(msg.field_name()); \
+ FieldMask mask; \
+ mask.add_paths(#field_name); \
+ FieldMaskUtil::TrimMessage(mask, &msg); \
+ EXPECT_EQ(tmp.DebugString(), msg.DebugString()); \
+ }
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_int32)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_int64)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_uint32)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_uint64)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_sint32)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_sint64)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_fixed32)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_fixed64)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_sfixed32)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_sfixed64)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_float)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_double)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_bool)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_string)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_bytes)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_nested_enum)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_foreign_enum)
+ TEST_TRIM_ONE_PRIMITIVE_FIELD(optional_import_enum)
+#undef TEST_TRIM_ONE_PRIMITIVE_FIELD
+
+#define TEST_TRIM_ONE_FIELD(field_name) \
+ { \
+ TestAllTypes msg; \
+ TestUtil::SetAllFields(&msg); \
+ TestAllTypes tmp; \
+ *tmp.mutable_##field_name() = msg.field_name(); \
+ FieldMask mask; \
+ mask.add_paths(#field_name); \
+ FieldMaskUtil::TrimMessage(mask, &msg); \
+ EXPECT_EQ(tmp.DebugString(), msg.DebugString()); \
+ }
+ TEST_TRIM_ONE_FIELD(optional_nested_message)
+ TEST_TRIM_ONE_FIELD(optional_foreign_message)
+ TEST_TRIM_ONE_FIELD(optional_import_message)
+
+ TEST_TRIM_ONE_FIELD(repeated_int32)
+ TEST_TRIM_ONE_FIELD(repeated_int64)
+ TEST_TRIM_ONE_FIELD(repeated_uint32)
+ TEST_TRIM_ONE_FIELD(repeated_uint64)
+ TEST_TRIM_ONE_FIELD(repeated_sint32)
+ TEST_TRIM_ONE_FIELD(repeated_sint64)
+ TEST_TRIM_ONE_FIELD(repeated_fixed32)
+ TEST_TRIM_ONE_FIELD(repeated_fixed64)
+ TEST_TRIM_ONE_FIELD(repeated_sfixed32)
+ TEST_TRIM_ONE_FIELD(repeated_sfixed64)
+ TEST_TRIM_ONE_FIELD(repeated_float)
+ TEST_TRIM_ONE_FIELD(repeated_double)
+ TEST_TRIM_ONE_FIELD(repeated_bool)
+ TEST_TRIM_ONE_FIELD(repeated_string)
+ TEST_TRIM_ONE_FIELD(repeated_bytes)
+ TEST_TRIM_ONE_FIELD(repeated_nested_message)
+ TEST_TRIM_ONE_FIELD(repeated_foreign_message)
+ TEST_TRIM_ONE_FIELD(repeated_import_message)
+ TEST_TRIM_ONE_FIELD(repeated_nested_enum)
+ TEST_TRIM_ONE_FIELD(repeated_foreign_enum)
+ TEST_TRIM_ONE_FIELD(repeated_import_enum)
+#undef TEST_TRIM_ONE_FIELD
+
+ // Test trim nested fields.
+ NestedTestAllTypes nested_msg;
+ nested_msg.mutable_child()->mutable_payload()->set_optional_int32(1234);
+ nested_msg.mutable_child()
+ ->mutable_child()
+ ->mutable_payload()
+ ->set_optional_int32(5678);
+ NestedTestAllTypes trimmed_msg(nested_msg);
+ FieldMask mask;
+ FieldMaskUtil::FromString("child.payload", &mask);
+ FieldMaskUtil::TrimMessage(mask, &trimmed_msg);
+ EXPECT_EQ(1234, trimmed_msg.child().payload().optional_int32());
+ EXPECT_EQ(0, trimmed_msg.child().child().payload().optional_int32());
+
+ trimmed_msg = nested_msg;
+ FieldMaskUtil::FromString("child.child.payload", &mask);
+ FieldMaskUtil::TrimMessage(mask, &trimmed_msg);
+ EXPECT_EQ(0, trimmed_msg.child().payload().optional_int32());
+ EXPECT_EQ(5678, trimmed_msg.child().child().payload().optional_int32());
+
+ trimmed_msg = nested_msg;
+ FieldMaskUtil::FromString("child", &mask);
+ FieldMaskUtil::TrimMessage(mask, &trimmed_msg);
+ EXPECT_EQ(1234, trimmed_msg.child().payload().optional_int32());
+ EXPECT_EQ(5678, trimmed_msg.child().child().payload().optional_int32());
+
+ trimmed_msg = nested_msg;
+ FieldMaskUtil::FromString("child.child", &mask);
+ FieldMaskUtil::TrimMessage(mask, &trimmed_msg);
+ EXPECT_EQ(0, trimmed_msg.child().payload().optional_int32());
+ EXPECT_EQ(5678, trimmed_msg.child().child().payload().optional_int32());
+
+ // Verify than an empty FieldMask trims nothing
+ TestAllTypes all_types_msg;
+ TestUtil::SetAllFields(&all_types_msg);
+ TestAllTypes trimmed_all_types(all_types_msg);
+ FieldMask empty_mask;
+ FieldMaskUtil::TrimMessage(empty_mask, &trimmed_all_types);
+ EXPECT_EQ(trimmed_all_types.DebugString(), all_types_msg.DebugString());
+}
+
+
+} // namespace
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/constants.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/constants.h
new file mode 100644
index 0000000000..e556888cca
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/constants.h
@@ -0,0 +1,103 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_CONSTANTS_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_CONSTANTS_H__
+
+#include <google/protobuf/stubs/common.h>
+
+// This file contains constants used by //net/proto2/util/converter.
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+// Prefix for type URLs.
+const char kTypeServiceBaseUrl[] = "type.googleapis.com";
+
+// Format string for RFC3339 timestamp formatting.
+const char kRfc3339TimeFormat[] = "%E4Y-%m-%dT%H:%M:%S";
+
+// Same as above, but the year value is not zero-padded i.e. this accepts
+// timestamps like "1-01-0001T23:59:59Z" instead of "0001-01-0001T23:59:59Z".
+const char kRfc3339TimeFormatNoPadding[] = "%Y-%m-%dT%H:%M:%S";
+
+// Minimun seconds allowed in a google.protobuf.Timestamp value.
+const int64 kTimestampMinSeconds = -62135596800;
+
+// Maximum seconds allowed in a google.protobuf.Timestamp value.
+const int64 kTimestampMaxSeconds = 253402300799;
+
+// Minimum seconds allowed in a google.protobuf.Duration value.
+const int64 kDurationMinSeconds = -315576000000;
+
+// Maximum seconds allowed in a google.protobuf.Duration value.
+const int64 kDurationMaxSeconds = 315576000000;
+
+// Nano seconds in a second.
+const int32 kNanosPerSecond = 1000000000;
+
+// Type url representing NULL values in google.protobuf.Struct type.
+const char kStructNullValueTypeUrl[] =
+ "type.googleapis.com/google.protobuf.NullValue";
+
+// Type string for google.protobuf.Struct
+const char kStructType[] = "google.protobuf.Struct";
+
+// Type string for struct.proto's google.protobuf.Value value type.
+const char kStructValueType[] = "google.protobuf.Value";
+
+// Type string for struct.proto's google.protobuf.ListValue value type.
+const char kStructListValueType[] = "google.protobuf.ListValue";
+
+// Type string for google.protobuf.Timestamp
+const char kTimestampType[] = "google.protobuf.Timestamp";
+
+// Type string for google.protobuf.Duration
+const char kDurationType[] = "google.protobuf.Duration";
+
+// Type URL for struct value type google.protobuf.Value
+const char kStructValueTypeUrl[] = "type.googleapis.com/google.protobuf.Value";
+
+// Type URL for struct value type google.protobuf.Value
+const char kStructTypeUrl[] = "type.googleapis.com/google.protobuf.Struct";
+
+// Type string for google.protobuf.Any
+const char kAnyType[] = "google.protobuf.Any";
+
+// The type URL of google.protobuf.FieldMask;
+const char kFieldMaskTypeUrl[] =
+ "type.googleapis.com/google.protobuf.FieldMask";
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_CONSTANTS_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.cc
new file mode 100644
index 0000000000..ef8da4279f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.cc
@@ -0,0 +1,378 @@
+// 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.
+
+#include <google/protobuf/util/internal/datapiece.h>
+
+#include <google/protobuf/struct.pb.h>
+#include <google/protobuf/type.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/mathlimits.h>
+#include <google/protobuf/stubs/mathutil.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using google::protobuf::EnumDescriptor;
+using google::protobuf::EnumValueDescriptor;
+;
+;
+;
+using util::error::Code;
+using util::Status;
+using util::StatusOr;
+
+namespace {
+
+inline Status InvalidArgument(StringPiece value_str) {
+ return Status(util::error::INVALID_ARGUMENT, value_str);
+}
+
+template <typename To, typename From>
+StatusOr<To> ValidateNumberConversion(To after, From before) {
+ if (after == before &&
+ MathUtil::Sign<From>(before) == MathUtil::Sign<To>(after)) {
+ return after;
+ } else {
+ return InvalidArgument(::google::protobuf::internal::is_integral<From>::value
+ ? ValueAsString(before)
+ : ::google::protobuf::internal::is_same<From, double>::value
+ ? DoubleAsString(before)
+ : FloatAsString(before));
+ }
+}
+
+// For general conversion between
+// int32, int64, uint32, uint64, double and float
+// except conversion between double and float.
+template <typename To, typename From>
+StatusOr<To> NumberConvertAndCheck(From before) {
+ if (::google::protobuf::internal::is_same<From, To>::value) return before;
+
+ To after = static_cast<To>(before);
+ return ValidateNumberConversion(after, before);
+}
+
+// For conversion to integer types (int32, int64, uint32, uint64) from floating
+// point types (double, float) only.
+template <typename To, typename From>
+StatusOr<To> FloatingPointToIntConvertAndCheck(From before) {
+ if (::google::protobuf::internal::is_same<From, To>::value) return before;
+
+ To after = static_cast<To>(before);
+ return ValidateNumberConversion(after, before);
+}
+
+// For conversion between double and float only.
+template <typename To, typename From>
+StatusOr<To> FloatingPointConvertAndCheck(From before) {
+ if (MathLimits<From>::IsNaN(before)) {
+ return std::numeric_limits<To>::quiet_NaN();
+ }
+
+ To after = static_cast<To>(before);
+ if (MathUtil::AlmostEquals<To>(after, before)) {
+ return after;
+ } else {
+ return InvalidArgument(::google::protobuf::internal::is_same<From, double>::value
+ ? DoubleAsString(before)
+ : FloatAsString(before));
+ }
+}
+
+} // namespace
+
+StatusOr<int32> DataPiece::ToInt32() const {
+ if (type_ == TYPE_STRING) return StringToNumber<int32>(safe_strto32);
+
+ if (type_ == TYPE_DOUBLE)
+ return FloatingPointToIntConvertAndCheck<int32, double>(double_);
+
+ if (type_ == TYPE_FLOAT)
+ return FloatingPointToIntConvertAndCheck<int32, float>(float_);
+
+ return GenericConvert<int32>();
+}
+
+StatusOr<uint32> DataPiece::ToUint32() const {
+ if (type_ == TYPE_STRING) return StringToNumber<uint32>(safe_strtou32);
+
+ if (type_ == TYPE_DOUBLE)
+ return FloatingPointToIntConvertAndCheck<uint32, double>(double_);
+
+ if (type_ == TYPE_FLOAT)
+ return FloatingPointToIntConvertAndCheck<uint32, float>(float_);
+
+ return GenericConvert<uint32>();
+}
+
+StatusOr<int64> DataPiece::ToInt64() const {
+ if (type_ == TYPE_STRING) return StringToNumber<int64>(safe_strto64);
+
+ if (type_ == TYPE_DOUBLE)
+ return FloatingPointToIntConvertAndCheck<int64, double>(double_);
+
+ if (type_ == TYPE_FLOAT)
+ return FloatingPointToIntConvertAndCheck<int64, float>(float_);
+
+ return GenericConvert<int64>();
+}
+
+StatusOr<uint64> DataPiece::ToUint64() const {
+ if (type_ == TYPE_STRING) return StringToNumber<uint64>(safe_strtou64);
+
+ if (type_ == TYPE_DOUBLE)
+ return FloatingPointToIntConvertAndCheck<uint64, double>(double_);
+
+ if (type_ == TYPE_FLOAT)
+ return FloatingPointToIntConvertAndCheck<uint64, float>(float_);
+
+ return GenericConvert<uint64>();
+}
+
+StatusOr<double> DataPiece::ToDouble() const {
+ if (type_ == TYPE_FLOAT) {
+ return FloatingPointConvertAndCheck<double, float>(float_);
+ }
+ if (type_ == TYPE_STRING) {
+ if (str_ == "Infinity") return std::numeric_limits<double>::infinity();
+ if (str_ == "-Infinity") return -std::numeric_limits<double>::infinity();
+ if (str_ == "NaN") return std::numeric_limits<double>::quiet_NaN();
+ return StringToNumber<double>(safe_strtod);
+ }
+ return GenericConvert<double>();
+}
+
+StatusOr<float> DataPiece::ToFloat() const {
+ if (type_ == TYPE_DOUBLE) {
+ return FloatingPointConvertAndCheck<float, double>(double_);
+ }
+ if (type_ == TYPE_STRING) {
+ if (str_ == "Infinity") return std::numeric_limits<float>::infinity();
+ if (str_ == "-Infinity") return -std::numeric_limits<float>::infinity();
+ if (str_ == "NaN") return std::numeric_limits<float>::quiet_NaN();
+ // SafeStrToFloat() is used instead of safe_strtof() because the later
+ // does not fail on inputs like SimpleDtoa(DBL_MAX).
+ return StringToNumber<float>(SafeStrToFloat);
+ }
+ return GenericConvert<float>();
+}
+
+StatusOr<bool> DataPiece::ToBool() const {
+ switch (type_) {
+ case TYPE_BOOL:
+ return bool_;
+ case TYPE_STRING:
+ return StringToNumber<bool>(safe_strtob);
+ default:
+ return InvalidArgument(
+ ValueAsStringOrDefault("Wrong type. Cannot convert to Bool."));
+ }
+}
+
+StatusOr<string> DataPiece::ToString() const {
+ switch (type_) {
+ case TYPE_STRING:
+ return str_.ToString();
+ case TYPE_BYTES: {
+ string base64;
+ Base64Escape(str_, &base64);
+ return base64;
+ }
+ default:
+ return InvalidArgument(
+ ValueAsStringOrDefault("Cannot convert to string."));
+ }
+}
+
+string DataPiece::ValueAsStringOrDefault(StringPiece default_string) const {
+ switch (type_) {
+ case TYPE_INT32:
+ return SimpleItoa(i32_);
+ case TYPE_INT64:
+ return SimpleItoa(i64_);
+ case TYPE_UINT32:
+ return SimpleItoa(u32_);
+ case TYPE_UINT64:
+ return SimpleItoa(u64_);
+ case TYPE_DOUBLE:
+ return DoubleAsString(double_);
+ case TYPE_FLOAT:
+ return FloatAsString(float_);
+ case TYPE_BOOL:
+ return SimpleBtoa(bool_);
+ case TYPE_STRING:
+ return StrCat("\"", str_.ToString(), "\"");
+ case TYPE_BYTES: {
+ string base64;
+ WebSafeBase64Escape(str_, &base64);
+ return StrCat("\"", base64, "\"");
+ }
+ case TYPE_NULL:
+ return "null";
+ default:
+ return default_string.ToString();
+ }
+}
+
+StatusOr<string> DataPiece::ToBytes() const {
+ if (type_ == TYPE_BYTES) return str_.ToString();
+ if (type_ == TYPE_STRING) {
+ string decoded;
+ if (!DecodeBase64(str_, &decoded)) {
+ return InvalidArgument(ValueAsStringOrDefault("Invalid data in input."));
+ }
+ return decoded;
+ } else {
+ return InvalidArgument(ValueAsStringOrDefault(
+ "Wrong type. Only String or Bytes can be converted to Bytes."));
+ }
+}
+
+StatusOr<int> DataPiece::ToEnum(const google::protobuf::Enum* enum_type) const {
+ if (type_ == TYPE_NULL) return google::protobuf::NULL_VALUE;
+
+ if (type_ == TYPE_STRING) {
+ // First try the given value as a name.
+ string enum_name = str_.ToString();
+ const google::protobuf::EnumValue* value =
+ FindEnumValueByNameOrNull(enum_type, enum_name);
+ if (value != NULL) return value->number();
+ // Next try a normalized name.
+ for (string::iterator it = enum_name.begin(); it != enum_name.end(); ++it) {
+ *it = *it == '-' ? '_' : ascii_toupper(*it);
+ }
+ value = FindEnumValueByNameOrNull(enum_type, enum_name);
+ if (value != NULL) return value->number();
+ } else {
+ StatusOr<int32> value = ToInt32();
+ if (value.ok()) {
+ if (const google::protobuf::EnumValue* enum_value =
+ FindEnumValueByNumberOrNull(enum_type, value.ValueOrDie())) {
+ return enum_value->number();
+ }
+ }
+ }
+ return InvalidArgument(
+ ValueAsStringOrDefault("Cannot find enum with given value."));
+}
+
+template <typename To>
+StatusOr<To> DataPiece::GenericConvert() const {
+ switch (type_) {
+ case TYPE_INT32:
+ return NumberConvertAndCheck<To, int32>(i32_);
+ case TYPE_INT64:
+ return NumberConvertAndCheck<To, int64>(i64_);
+ case TYPE_UINT32:
+ return NumberConvertAndCheck<To, uint32>(u32_);
+ case TYPE_UINT64:
+ return NumberConvertAndCheck<To, uint64>(u64_);
+ case TYPE_DOUBLE:
+ return NumberConvertAndCheck<To, double>(double_);
+ case TYPE_FLOAT:
+ return NumberConvertAndCheck<To, float>(float_);
+ default: // TYPE_ENUM, TYPE_STRING, TYPE_CORD, TYPE_BOOL
+ return InvalidArgument(ValueAsStringOrDefault(
+ "Wrong type. Bool, Enum, String and Cord not supported in "
+ "GenericConvert."));
+ }
+}
+
+template <typename To>
+StatusOr<To> DataPiece::StringToNumber(bool (*func)(StringPiece, To*)) const {
+ if (str_.size() > 0 && (str_[0] == ' ' || str_[str_.size() - 1] == ' ')) {
+ return InvalidArgument(StrCat("\"", str_, "\""));
+ }
+ To result;
+ if (func(str_, &result)) return result;
+ return InvalidArgument(StrCat("\"", str_.ToString(), "\""));
+}
+
+bool DataPiece::DecodeBase64(StringPiece src, string* dest) const {
+ // Try web-safe decode first, if it fails, try the non-web-safe decode.
+ if (WebSafeBase64Unescape(src, dest)) {
+ if (use_strict_base64_decoding_) {
+ // In strict mode, check if the escaped version gives us the same value as
+ // unescaped.
+ string encoded;
+ // WebSafeBase64Escape does no padding by default.
+ WebSafeBase64Escape(*dest, &encoded);
+ // Remove trailing padding '=' characters before comparison.
+ StringPiece src_no_padding = StringPiece(src).substr(
+ 0, src.ends_with("=") ? src.find_last_not_of('=') + 1 : src.length());
+ return encoded == src_no_padding;
+ }
+ return true;
+ }
+
+ if (Base64Unescape(src, dest)) {
+ if (use_strict_base64_decoding_) {
+ string encoded;
+ Base64Escape(
+ reinterpret_cast<const unsigned char*>(dest->data()), dest->length(),
+ &encoded, false);
+ StringPiece src_no_padding = StringPiece(src).substr(
+ 0, src.ends_with("=") ? src.find_last_not_of('=') + 1 : src.length());
+ return encoded == src_no_padding;
+ }
+ return true;
+ }
+
+ return false;
+}
+
+void DataPiece::InternalCopy(const DataPiece& other) {
+ type_ = other.type_;
+ switch (type_) {
+ case TYPE_INT32:
+ case TYPE_INT64:
+ case TYPE_UINT32:
+ case TYPE_UINT64:
+ case TYPE_DOUBLE:
+ case TYPE_FLOAT:
+ case TYPE_BOOL:
+ case TYPE_ENUM:
+ case TYPE_NULL:
+ case TYPE_BYTES:
+ case TYPE_STRING: {
+ str_ = other.str_;
+ break;
+ }
+ }
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.h
new file mode 100644
index 0000000000..e82cdbacbf
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/datapiece.h
@@ -0,0 +1,204 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_DATAPIECE_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_DATAPIECE_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/statusor.h>
+
+
+namespace google {
+namespace protobuf {
+class Enum;
+} // namespace protobuf
+
+
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// Container for a single piece of data together with its data type.
+//
+// For primitive types (int32, int64, uint32, uint64, double, float, bool),
+// the data is stored by value.
+//
+// For string, a StringPiece is stored. For Cord, a pointer to Cord is stored.
+// Just like StringPiece, the DataPiece class does not own the storage for
+// the actual string or Cord, so it is the user's responsiblity to guarantee
+// that the underlying storage is still valid when the DataPiece is accessed.
+class LIBPROTOBUF_EXPORT DataPiece {
+ public:
+ // Identifies data type of the value.
+ // These are the types supported by DataPiece.
+ enum Type {
+ TYPE_INT32 = 1,
+ TYPE_INT64 = 2,
+ TYPE_UINT32 = 3,
+ TYPE_UINT64 = 4,
+ TYPE_DOUBLE = 5,
+ TYPE_FLOAT = 6,
+ TYPE_BOOL = 7,
+ TYPE_ENUM = 8,
+ TYPE_STRING = 9,
+ TYPE_BYTES = 10,
+ TYPE_NULL = 11, // explicit NULL type
+ };
+
+ // Constructors and Destructor
+ explicit DataPiece(const int32 value) : type_(TYPE_INT32), i32_(value) {}
+ explicit DataPiece(const int64 value) : type_(TYPE_INT64), i64_(value) {}
+ explicit DataPiece(const uint32 value) : type_(TYPE_UINT32), u32_(value) {}
+ explicit DataPiece(const uint64 value) : type_(TYPE_UINT64), u64_(value) {}
+ explicit DataPiece(const double value) : type_(TYPE_DOUBLE), double_(value) {}
+ explicit DataPiece(const float value) : type_(TYPE_FLOAT), float_(value) {}
+ explicit DataPiece(const bool value) : type_(TYPE_BOOL), bool_(value) {}
+ DataPiece(StringPiece value, bool use_strict_base64_decoding)
+ : type_(TYPE_STRING),
+ str_(StringPiecePod::CreateFromStringPiece(value)),
+ use_strict_base64_decoding_(use_strict_base64_decoding) {}
+ // Constructor for bytes. The second parameter is not used.
+ DataPiece(StringPiece value, bool dummy, bool use_strict_base64_decoding)
+ : type_(TYPE_BYTES),
+ str_(StringPiecePod::CreateFromStringPiece(value)),
+ use_strict_base64_decoding_(use_strict_base64_decoding) {}
+
+ DataPiece(const DataPiece& r) : type_(r.type_) { InternalCopy(r); }
+
+ DataPiece& operator=(const DataPiece& x) {
+ InternalCopy(x);
+ return *this;
+ }
+
+ static DataPiece NullData() { return DataPiece(TYPE_NULL, 0); }
+
+ virtual ~DataPiece() {
+ }
+
+ // Accessors
+ Type type() const { return type_; }
+
+ StringPiece str() const {
+ GOOGLE_LOG_IF(DFATAL, type_ != TYPE_STRING) << "Not a string type.";
+ return str_;
+ }
+
+
+ // Parses, casts or converts the value stored in the DataPiece into an int32.
+ util::StatusOr<int32> ToInt32() const;
+
+ // Parses, casts or converts the value stored in the DataPiece into a uint32.
+ util::StatusOr<uint32> ToUint32() const;
+
+ // Parses, casts or converts the value stored in the DataPiece into an int64.
+ util::StatusOr<int64> ToInt64() const;
+
+ // Parses, casts or converts the value stored in the DataPiece into a uint64.
+ util::StatusOr<uint64> ToUint64() const;
+
+ // Parses, casts or converts the value stored in the DataPiece into a double.
+ util::StatusOr<double> ToDouble() const;
+
+ // Parses, casts or converts the value stored in the DataPiece into a float.
+ util::StatusOr<float> ToFloat() const;
+
+ // Parses, casts or converts the value stored in the DataPiece into a bool.
+ util::StatusOr<bool> ToBool() const;
+
+ // Parses, casts or converts the value stored in the DataPiece into a string.
+ util::StatusOr<string> ToString() const;
+
+ // Tries to convert the value contained in this datapiece to string. If the
+ // conversion fails, it returns the default_string.
+ string ValueAsStringOrDefault(StringPiece default_string) const;
+
+ util::StatusOr<string> ToBytes() const;
+
+ // Converts a value into protocol buffer enum number. If the value is a
+ // string, first attempts conversion by name, trying names as follows:
+ // 1) the directly provided string value.
+ // 2) the value upper-cased and replacing '-' by '_'
+ // If the value is not a string, attempts to convert to a 32-bit integer.
+ // If none of these succeeds, returns a conversion error status.
+ util::StatusOr<int> ToEnum(const google::protobuf::Enum* enum_type) const;
+
+ private:
+ // Disallow implicit constructor.
+ DataPiece();
+
+ // Helper to create NULL or ENUM types.
+ DataPiece(Type type, int32 val) : type_(type), i32_(val) {}
+
+ // For numeric conversion between
+ // int32, int64, uint32, uint64, double, float and bool
+ template <typename To>
+ util::StatusOr<To> GenericConvert() const;
+
+ // For conversion from string to
+ // int32, int64, uint32, uint64, double, float and bool
+ template <typename To>
+ util::StatusOr<To> StringToNumber(bool (*func)(StringPiece, To*)) const;
+
+ // Decodes a base64 string. Returns true on success.
+ bool DecodeBase64(StringPiece src, string* dest) const;
+
+ // Helper function to initialize this DataPiece with 'other'.
+ void InternalCopy(const DataPiece& other);
+
+ // Data type for this piece of data.
+ Type type_;
+
+ typedef ::google::protobuf::internal::StringPiecePod StringPiecePod;
+
+ // Stored piece of data.
+ union {
+ int32 i32_;
+ int64 i64_;
+ uint32 u32_;
+ uint64 u64_;
+ double double_;
+ float float_;
+ bool bool_;
+ StringPiecePod str_;
+ };
+
+ // Uses a stricter version of base64 decoding for byte fields.
+ bool use_strict_base64_decoding_;
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_DATAPIECE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.cc
new file mode 100644
index 0000000000..1e8dab701a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.cc
@@ -0,0 +1,596 @@
+// 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.
+
+#include <google/protobuf/util/internal/default_value_objectwriter.h>
+
+#include <google/protobuf/stubs/hash.h>
+
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/stubs/map_util.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+using util::Status;
+using util::StatusOr;
+namespace converter {
+
+namespace {
+// Helper function to convert string value to given data type by calling the
+// passed converter function on the DataPiece created from "value" argument.
+// If value is empty or if conversion fails, the default_value is returned.
+template <typename T>
+T ConvertTo(StringPiece value, StatusOr<T> (DataPiece::*converter_fn)() const,
+ T default_value) {
+ if (value.empty()) return default_value;
+ StatusOr<T> result = (DataPiece(value, true).*converter_fn)();
+ return result.ok() ? result.ValueOrDie() : default_value;
+}
+} // namespace
+
+DefaultValueObjectWriter::DefaultValueObjectWriter(
+ TypeResolver* type_resolver, const google::protobuf::Type& type,
+ ObjectWriter* ow)
+ : typeinfo_(TypeInfo::NewTypeInfo(type_resolver)),
+ own_typeinfo_(true),
+ type_(type),
+ current_(NULL),
+ root_(NULL),
+ suppress_empty_list_(false),
+ field_scrub_callback_(NULL),
+ ow_(ow) {}
+
+DefaultValueObjectWriter::~DefaultValueObjectWriter() {
+ for (int i = 0; i < string_values_.size(); ++i) {
+ delete string_values_[i];
+ }
+ if (own_typeinfo_) {
+ delete typeinfo_;
+ }
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderBool(StringPiece name,
+ bool value) {
+ if (current_ == NULL) {
+ ow_->RenderBool(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderInt32(
+ StringPiece name, int32 value) {
+ if (current_ == NULL) {
+ ow_->RenderInt32(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderUint32(
+ StringPiece name, uint32 value) {
+ if (current_ == NULL) {
+ ow_->RenderUint32(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderInt64(
+ StringPiece name, int64 value) {
+ if (current_ == NULL) {
+ ow_->RenderInt64(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderUint64(
+ StringPiece name, uint64 value) {
+ if (current_ == NULL) {
+ ow_->RenderUint64(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderDouble(
+ StringPiece name, double value) {
+ if (current_ == NULL) {
+ ow_->RenderDouble(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderFloat(
+ StringPiece name, float value) {
+ if (current_ == NULL) {
+ ow_->RenderBool(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderString(
+ StringPiece name, StringPiece value) {
+ if (current_ == NULL) {
+ ow_->RenderString(name, value);
+ } else {
+ // Since StringPiece is essentially a pointer, takes a copy of "value" to
+ // avoid ownership issues.
+ string_values_.push_back(new string(value.ToString()));
+ RenderDataPiece(name, DataPiece(*string_values_.back(), true));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderBytes(
+ StringPiece name, StringPiece value) {
+ if (current_ == NULL) {
+ ow_->RenderBytes(name, value);
+ } else {
+ RenderDataPiece(name, DataPiece(value, false, true));
+ }
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::RenderNull(
+ StringPiece name) {
+ if (current_ == NULL) {
+ ow_->RenderNull(name);
+ } else {
+ RenderDataPiece(name, DataPiece::NullData());
+ }
+ return this;
+}
+
+void DefaultValueObjectWriter::RegisterFieldScrubCallBack(
+ FieldScrubCallBackPtr field_scrub_callback) {
+ field_scrub_callback_.reset(field_scrub_callback.release());
+}
+
+DefaultValueObjectWriter::Node::Node(
+ const string& name, const google::protobuf::Type* type, NodeKind kind,
+ const DataPiece& data, bool is_placeholder, const vector<string>& path,
+ bool suppress_empty_list, FieldScrubCallBack* field_scrub_callback)
+ : name_(name),
+ type_(type),
+ kind_(kind),
+ is_any_(false),
+ data_(data),
+ is_placeholder_(is_placeholder),
+ path_(path),
+ suppress_empty_list_(suppress_empty_list),
+ field_scrub_callback_(field_scrub_callback) {}
+
+DefaultValueObjectWriter::Node* DefaultValueObjectWriter::Node::FindChild(
+ StringPiece name) {
+ if (name.empty() || kind_ != OBJECT) {
+ return NULL;
+ }
+ for (int i = 0; i < children_.size(); ++i) {
+ Node* child = children_[i];
+ if (child->name() == name) {
+ return child;
+ }
+ }
+ return NULL;
+}
+
+void DefaultValueObjectWriter::Node::WriteTo(ObjectWriter* ow) {
+ if (kind_ == PRIMITIVE) {
+ ObjectWriter::RenderDataPieceTo(data_, name_, ow);
+ return;
+ }
+
+ // Render maps. Empty maps are rendered as "{}".
+ if (kind_ == MAP) {
+ ow->StartObject(name_);
+ WriteChildren(ow);
+ ow->EndObject();
+ return;
+ }
+
+ // Write out lists. If we didn't have any list in response, write out empty
+ // list.
+ if (kind_ == LIST) {
+ // Suppress empty lists if requested.
+ if (suppress_empty_list_ && is_placeholder_) return;
+
+ ow->StartList(name_);
+ WriteChildren(ow);
+ ow->EndList();
+ return;
+ }
+
+ // If is_placeholder_ = true, we didn't see this node in the response, so
+ // skip output.
+ if (is_placeholder_) return;
+
+ ow->StartObject(name_);
+ WriteChildren(ow);
+ ow->EndObject();
+}
+
+void DefaultValueObjectWriter::Node::WriteChildren(ObjectWriter* ow) {
+ for (int i = 0; i < children_.size(); ++i) {
+ Node* child = children_[i];
+ child->WriteTo(ow);
+ }
+}
+
+const google::protobuf::Type* DefaultValueObjectWriter::Node::GetMapValueType(
+ const google::protobuf::Type& found_type, const TypeInfo* typeinfo) {
+ // If this field is a map, we should use the type of its "Value" as
+ // the type of the child node.
+ for (int i = 0; i < found_type.fields_size(); ++i) {
+ const google::protobuf::Field& sub_field = found_type.fields(i);
+ if (sub_field.number() != 2) {
+ continue;
+ }
+ if (sub_field.kind() != google::protobuf::Field_Kind_TYPE_MESSAGE) {
+ // This map's value type is not a message type. We don't need to
+ // get the field_type in this case.
+ break;
+ }
+ util::StatusOr<const google::protobuf::Type*> sub_type =
+ typeinfo->ResolveTypeUrl(sub_field.type_url());
+ if (!sub_type.ok()) {
+ GOOGLE_LOG(WARNING) << "Cannot resolve type '" << sub_field.type_url() << "'.";
+ } else {
+ return sub_type.ValueOrDie();
+ }
+ break;
+ }
+ return NULL;
+}
+
+void DefaultValueObjectWriter::Node::PopulateChildren(
+ const TypeInfo* typeinfo) {
+ // Ignores well known types that don't require automatically populating their
+ // primitive children. For type "Any", we only populate its children when the
+ // "@type" field is set.
+ // TODO(tsun): remove "kStructValueType" from the list. It's being checked
+ // now because of a bug in the tool-chain that causes the "oneof_index"
+ // of kStructValueType to not be set correctly.
+ if (type_ == NULL || type_->name() == kAnyType ||
+ type_->name() == kStructType || type_->name() == kTimestampType ||
+ type_->name() == kDurationType || type_->name() == kStructValueType) {
+ return;
+ }
+ std::vector<Node*> new_children;
+ hash_map<string, int> orig_children_map;
+
+ // Creates a map of child nodes to speed up lookup.
+ for (int i = 0; i < children_.size(); ++i) {
+ InsertIfNotPresent(&orig_children_map, children_[i]->name_, i);
+ }
+
+ for (int i = 0; i < type_->fields_size(); ++i) {
+ const google::protobuf::Field& field = type_->fields(i);
+
+ // This code is checking if the field to be added to the tree should be
+ // scrubbed or not by calling the field_scrub_callback_ callback function.
+ vector<string> path;
+ if (!path_.empty()) {
+ path.insert(path.begin(), path_.begin(), path_.end());
+ }
+ path.push_back(field.name());
+ if (field_scrub_callback_ != NULL &&
+ field_scrub_callback_->Run(path, &field)) {
+ continue;
+ }
+
+ hash_map<string, int>::iterator found =
+ orig_children_map.find(field.name());
+ // If the child field has already been set, we just add it to the new list
+ // of children.
+ if (found != orig_children_map.end()) {
+ new_children.push_back(children_[found->second]);
+ children_[found->second] = NULL;
+ continue;
+ }
+
+ const google::protobuf::Type* field_type = NULL;
+ bool is_map = false;
+ NodeKind kind = PRIMITIVE;
+
+ if (field.kind() == google::protobuf::Field_Kind_TYPE_MESSAGE) {
+ kind = OBJECT;
+ util::StatusOr<const google::protobuf::Type*> found_result =
+ typeinfo->ResolveTypeUrl(field.type_url());
+ if (!found_result.ok()) {
+ // "field" is of an unknown type.
+ GOOGLE_LOG(WARNING) << "Cannot resolve type '" << field.type_url() << "'.";
+ } else {
+ const google::protobuf::Type* found_type = found_result.ValueOrDie();
+ is_map = IsMap(field, *found_type);
+
+ if (!is_map) {
+ field_type = found_type;
+ } else {
+ // If this field is a map, we should use the type of its "Value" as
+ // the type of the child node.
+ field_type = GetMapValueType(*found_type, typeinfo);
+ kind = MAP;
+ }
+ }
+ }
+
+ if (!is_map &&
+ field.cardinality() ==
+ google::protobuf::Field_Cardinality_CARDINALITY_REPEATED) {
+ kind = LIST;
+ }
+
+ // If oneof_index() != 0, the child field is part of a "oneof", which means
+ // the child field is optional and we shouldn't populate its default value.
+ if (field.oneof_index() != 0) continue;
+
+ // If the child field is of primitive type, sets its data to the default
+ // value of its type.
+ google::protobuf::scoped_ptr<Node> child(new Node(
+ field.json_name(), field_type, kind,
+ kind == PRIMITIVE ? CreateDefaultDataPieceForField(field, typeinfo)
+ : DataPiece::NullData(),
+ true, path, suppress_empty_list_, field_scrub_callback_));
+ new_children.push_back(child.release());
+ }
+ // Adds all leftover nodes in children_ to the beginning of new_child.
+ for (int i = 0; i < children_.size(); ++i) {
+ if (children_[i] == NULL) {
+ continue;
+ }
+ new_children.insert(new_children.begin(), children_[i]);
+ children_[i] = NULL;
+ }
+ children_.swap(new_children);
+}
+
+void DefaultValueObjectWriter::MaybePopulateChildrenOfAny(Node* node) {
+ // If this is an "Any" node with "@type" already given and no other children
+ // have been added, populates its children.
+ if (node != NULL && node->is_any() && node->type() != NULL &&
+ node->type()->name() != kAnyType && node->number_of_children() == 1) {
+ node->PopulateChildren(typeinfo_);
+ }
+}
+
+DataPiece DefaultValueObjectWriter::FindEnumDefault(
+ const google::protobuf::Field& field, const TypeInfo* typeinfo) {
+ if (!field.default_value().empty())
+ return DataPiece(field.default_value(), true);
+
+ const google::protobuf::Enum* enum_type =
+ typeinfo->GetEnumByTypeUrl(field.type_url());
+ if (!enum_type) {
+ GOOGLE_LOG(WARNING) << "Could not find enum with type '" << field.type_url()
+ << "'";
+ return DataPiece::NullData();
+ }
+ // We treat the first value as the default if none is specified.
+ return enum_type->enumvalue_size() > 0
+ ? DataPiece(enum_type->enumvalue(0).name(), true)
+ : DataPiece::NullData();
+}
+
+DataPiece DefaultValueObjectWriter::CreateDefaultDataPieceForField(
+ const google::protobuf::Field& field, const TypeInfo* typeinfo) {
+ switch (field.kind()) {
+ case google::protobuf::Field_Kind_TYPE_DOUBLE: {
+ return DataPiece(ConvertTo<double>(
+ field.default_value(), &DataPiece::ToDouble, static_cast<double>(0)));
+ }
+ case google::protobuf::Field_Kind_TYPE_FLOAT: {
+ return DataPiece(ConvertTo<float>(
+ field.default_value(), &DataPiece::ToFloat, static_cast<float>(0)));
+ }
+ case google::protobuf::Field_Kind_TYPE_INT64:
+ case google::protobuf::Field_Kind_TYPE_SINT64:
+ case google::protobuf::Field_Kind_TYPE_SFIXED64: {
+ return DataPiece(ConvertTo<int64>(
+ field.default_value(), &DataPiece::ToInt64, static_cast<int64>(0)));
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT64:
+ case google::protobuf::Field_Kind_TYPE_FIXED64: {
+ return DataPiece(ConvertTo<uint64>(
+ field.default_value(), &DataPiece::ToUint64, static_cast<uint64>(0)));
+ }
+ case google::protobuf::Field_Kind_TYPE_INT32:
+ case google::protobuf::Field_Kind_TYPE_SINT32:
+ case google::protobuf::Field_Kind_TYPE_SFIXED32: {
+ return DataPiece(ConvertTo<int32>(
+ field.default_value(), &DataPiece::ToInt32, static_cast<int32>(0)));
+ }
+ case google::protobuf::Field_Kind_TYPE_BOOL: {
+ return DataPiece(
+ ConvertTo<bool>(field.default_value(), &DataPiece::ToBool, false));
+ }
+ case google::protobuf::Field_Kind_TYPE_STRING: {
+ return DataPiece(field.default_value(), true);
+ }
+ case google::protobuf::Field_Kind_TYPE_BYTES: {
+ return DataPiece(field.default_value(), false, true);
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT32:
+ case google::protobuf::Field_Kind_TYPE_FIXED32: {
+ return DataPiece(ConvertTo<uint32>(
+ field.default_value(), &DataPiece::ToUint32, static_cast<uint32>(0)));
+ }
+ case google::protobuf::Field_Kind_TYPE_ENUM: {
+ return FindEnumDefault(field, typeinfo);
+ }
+ default: { return DataPiece::NullData(); }
+ }
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::StartObject(
+ StringPiece name) {
+ if (current_ == NULL) {
+ vector<string> path;
+ root_.reset(new Node(name.ToString(), &type_, OBJECT, DataPiece::NullData(),
+ false, path, suppress_empty_list_,
+ field_scrub_callback_.get()));
+ root_->PopulateChildren(typeinfo_);
+ current_ = root_.get();
+ return this;
+ }
+ MaybePopulateChildrenOfAny(current_);
+ Node* child = current_->FindChild(name);
+ if (current_->kind() == LIST || current_->kind() == MAP || child == NULL) {
+ // If current_ is a list or a map node, we should create a new child and use
+ // the type of current_ as the type of the new child.
+ google::protobuf::scoped_ptr<Node> node(new Node(
+ name.ToString(), ((current_->kind() == LIST || current_->kind() == MAP)
+ ? current_->type()
+ : NULL),
+ OBJECT, DataPiece::NullData(), false,
+ child == NULL ? current_->path() : child->path(),
+ suppress_empty_list_, field_scrub_callback_.get()));
+ child = node.get();
+ current_->AddChild(node.release());
+ }
+
+ child->set_is_placeholder(false);
+ if (child->kind() == OBJECT && child->number_of_children() == 0) {
+ child->PopulateChildren(typeinfo_);
+ }
+
+ stack_.push(current_);
+ current_ = child;
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::EndObject() {
+ if (stack_.empty()) {
+ // The root object ends here. Writes out the tree.
+ WriteRoot();
+ return this;
+ }
+ current_ = stack_.top();
+ stack_.pop();
+ return this;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::StartList(
+ StringPiece name) {
+ if (current_ == NULL) {
+ vector<string> path;
+ root_.reset(new Node(name.ToString(), &type_, LIST, DataPiece::NullData(),
+ false, path, suppress_empty_list_,
+ field_scrub_callback_.get()));
+ current_ = root_.get();
+ return this;
+ }
+ MaybePopulateChildrenOfAny(current_);
+ Node* child = current_->FindChild(name);
+ if (child == NULL || child->kind() != LIST) {
+ google::protobuf::scoped_ptr<Node> node(
+ new Node(name.ToString(), NULL, LIST, DataPiece::NullData(), false,
+ child == NULL ? current_->path() : child->path(),
+ suppress_empty_list_, field_scrub_callback_.get()));
+ child = node.get();
+ current_->AddChild(node.release());
+ }
+ child->set_is_placeholder(false);
+
+ stack_.push(current_);
+ current_ = child;
+ return this;
+}
+
+void DefaultValueObjectWriter::WriteRoot() {
+ root_->WriteTo(ow_);
+ root_.reset(NULL);
+ current_ = NULL;
+}
+
+DefaultValueObjectWriter* DefaultValueObjectWriter::EndList() {
+ if (stack_.empty()) {
+ WriteRoot();
+ return this;
+ }
+ current_ = stack_.top();
+ stack_.pop();
+ return this;
+}
+
+void DefaultValueObjectWriter::RenderDataPiece(StringPiece name,
+ const DataPiece& data) {
+ MaybePopulateChildrenOfAny(current_);
+ util::StatusOr<string> data_string = data.ToString();
+ if (current_->type() != NULL && current_->type()->name() == kAnyType &&
+ name == "@type" && data_string.ok()) {
+ const string& string_value = data_string.ValueOrDie();
+ // If the type of current_ is "Any" and its "@type" field is being set here,
+ // sets the type of current_ to be the type specified by the "@type".
+ util::StatusOr<const google::protobuf::Type*> found_type =
+ typeinfo_->ResolveTypeUrl(string_value);
+ if (!found_type.ok()) {
+ GOOGLE_LOG(WARNING) << "Failed to resolve type '" << string_value << "'.";
+ } else {
+ current_->set_type(found_type.ValueOrDie());
+ }
+ current_->set_is_any(true);
+ // If the "@type" field is placed after other fields, we should populate
+ // other children of primitive type now. Otherwise, we should wait until the
+ // first value field is rendered before we populate the children, because
+ // the "value" field of a Any message could be omitted.
+ if (current_->number_of_children() > 1 && current_->type() != NULL) {
+ current_->PopulateChildren(typeinfo_);
+ }
+ }
+ Node* child = current_->FindChild(name);
+ if (child == NULL || child->kind() != PRIMITIVE) {
+ // No children are found, creates a new child.
+ google::protobuf::scoped_ptr<Node> node(
+ new Node(name.ToString(), NULL, PRIMITIVE, data, false,
+ child == NULL ? current_->path() : child->path(),
+ suppress_empty_list_, field_scrub_callback_.get()));
+ child = node.get();
+ current_->AddChild(node.release());
+ } else {
+ child->set_data(data);
+ }
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.h
new file mode 100644
index 0000000000..5f3b25f378
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter.h
@@ -0,0 +1,284 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_DEFAULT_VALUE_OBJECTWRITER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_DEFAULT_VALUE_OBJECTWRITER_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <stack>
+#include <vector>
+
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/util/internal/type_info.h>
+#include <google/protobuf/util/internal/datapiece.h>
+#include <google/protobuf/util/internal/object_writer.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/stubs/stringpiece.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// An ObjectWriter that renders non-repeated primitive fields of proto messages
+// with their default values. DefaultValueObjectWriter holds objects, lists and
+// fields it receives in a tree structure and writes them out to another
+// ObjectWriter when EndObject() is called on the root object. It also writes
+// out all non-repeated primitive fields that haven't been explicitly rendered
+// with their default values (0 for numbers, "" for strings, etc).
+class LIBPROTOBUF_EXPORT DefaultValueObjectWriter : public ObjectWriter {
+ public:
+ // A Callback function to check whether a field needs to be scrubbed.
+ //
+ // Returns true if the field should not be present in the output. Returns
+ // false otherwise.
+ //
+ // The 'path' parameter is a vector of path to the field from root. For
+ // example: if a nested field "a.b.c" (b is the parent message field of c and
+ // a is the parent message field of b), then the vector should contain { "a",
+ // "b", "c" }.
+ //
+ // The Field* should point to the google::protobuf::Field of "c".
+ typedef ResultCallback2<bool /*return*/,
+ const std::vector<string>& /*path of the field*/,
+ const google::protobuf::Field* /*field*/>
+ FieldScrubCallBack;
+
+ // A unique pointer to a DefaultValueObjectWriter::FieldScrubCallBack.
+ typedef google::protobuf::scoped_ptr<FieldScrubCallBack> FieldScrubCallBackPtr;
+
+ DefaultValueObjectWriter(TypeResolver* type_resolver,
+ const google::protobuf::Type& type,
+ ObjectWriter* ow);
+
+ virtual ~DefaultValueObjectWriter();
+
+ // ObjectWriter methods.
+ virtual DefaultValueObjectWriter* StartObject(StringPiece name);
+
+ virtual DefaultValueObjectWriter* EndObject();
+
+ virtual DefaultValueObjectWriter* StartList(StringPiece name);
+
+ virtual DefaultValueObjectWriter* EndList();
+
+ virtual DefaultValueObjectWriter* RenderBool(StringPiece name, bool value);
+
+ virtual DefaultValueObjectWriter* RenderInt32(StringPiece name, int32 value);
+
+ virtual DefaultValueObjectWriter* RenderUint32(StringPiece name,
+ uint32 value);
+
+ virtual DefaultValueObjectWriter* RenderInt64(StringPiece name, int64 value);
+
+ virtual DefaultValueObjectWriter* RenderUint64(StringPiece name,
+ uint64 value);
+
+ virtual DefaultValueObjectWriter* RenderDouble(StringPiece name,
+ double value);
+
+ virtual DefaultValueObjectWriter* RenderFloat(StringPiece name, float value);
+
+ virtual DefaultValueObjectWriter* RenderString(StringPiece name,
+ StringPiece value);
+ virtual DefaultValueObjectWriter* RenderBytes(StringPiece name,
+ StringPiece value);
+
+ virtual DefaultValueObjectWriter* RenderNull(StringPiece name);
+
+ // Register the callback for scrubbing of fields. Owership of
+ // field_scrub_callback pointer is also transferred to this class
+ void RegisterFieldScrubCallBack(FieldScrubCallBackPtr field_scrub_callback);
+
+ // If set to true, empty lists are suppressed from output when default values
+ // are written.
+ void set_suppress_empty_list(bool value) { suppress_empty_list_ = value; }
+
+ private:
+ enum NodeKind {
+ PRIMITIVE = 0,
+ OBJECT = 1,
+ LIST = 2,
+ MAP = 3,
+ };
+
+ // "Node" represents a node in the tree that holds the input of
+ // DefaultValueObjectWriter.
+ class LIBPROTOBUF_EXPORT Node {
+ public:
+ Node(const string& name, const google::protobuf::Type* type, NodeKind kind,
+ const DataPiece& data, bool is_placeholder, const vector<string>& path,
+ bool suppress_empty_list, FieldScrubCallBack* field_scrub_callback);
+ virtual ~Node() {
+ for (int i = 0; i < children_.size(); ++i) {
+ delete children_[i];
+ }
+ }
+
+ // Adds a child to this node. Takes ownership of this child.
+ void AddChild(Node* child) { children_.push_back(child); }
+
+ // Finds the child given its name.
+ Node* FindChild(StringPiece name);
+
+ // Populates children of this Node based on its type. If there are already
+ // children created, they will be merged to the result. Caller should pass
+ // in TypeInfo for looking up types of the children.
+ void PopulateChildren(const TypeInfo* typeinfo);
+
+ // If this node is a leaf (has data), writes the current node to the
+ // ObjectWriter; if not, then recursively writes the children to the
+ // ObjectWriter.
+ void WriteTo(ObjectWriter* ow);
+
+ // Accessors
+ const string& name() const { return name_; }
+
+ const vector<string>& path() const { return path_; }
+
+ const google::protobuf::Type* type() const { return type_; }
+
+ void set_type(const google::protobuf::Type* type) { type_ = type; }
+
+ NodeKind kind() const { return kind_; }
+
+ int number_of_children() const { return children_.size(); }
+
+ void set_data(const DataPiece& data) { data_ = data; }
+
+ bool is_any() const { return is_any_; }
+
+ void set_is_any(bool is_any) { is_any_ = is_any; }
+
+ void set_is_placeholder(bool is_placeholder) {
+ is_placeholder_ = is_placeholder;
+ }
+
+ private:
+ // Returns the Value Type of a map given the Type of the map entry and a
+ // TypeInfo instance.
+ const google::protobuf::Type* GetMapValueType(
+ const google::protobuf::Type& entry_type, const TypeInfo* typeinfo);
+
+ // Calls WriteTo() on every child in children_.
+ void WriteChildren(ObjectWriter* ow);
+
+ // The name of this node.
+ string name_;
+ // google::protobuf::Type of this node. Owned by TypeInfo.
+ const google::protobuf::Type* type_;
+ // The kind of this node.
+ NodeKind kind_;
+ // Whether this is a node for "Any".
+ bool is_any_;
+ // The data of this node when it is a leaf node.
+ DataPiece data_;
+ // Children of this node.
+ std::vector<Node*> children_;
+ // Whether this node is a placeholder for an object or list automatically
+ // generated when creating the parent node. Should be set to false after
+ // the parent node's StartObject()/StartList() method is called with this
+ // node's name.
+ bool is_placeholder_;
+
+ // Path of the field of this node
+ std::vector<string> path_;
+
+ // Whether to suppress empty list output.
+ bool suppress_empty_list_;
+
+ // Pointer to function for determining whether a field needs to be scrubbed
+ // or not. This callback is owned by the creator of this node.
+ FieldScrubCallBack* field_scrub_callback_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Node);
+ };
+
+ // Populates children of "node" if it is an "any" Node and its real type has
+ // been given.
+ void MaybePopulateChildrenOfAny(Node* node);
+
+ // Writes the root_ node to ow_ and resets the root_ and current_ pointer to
+ // NULL.
+ void WriteRoot();
+
+ // Creates a DataPiece containing the default value of the type of the field.
+ static DataPiece CreateDefaultDataPieceForField(
+ const google::protobuf::Field& field, const TypeInfo* typeinfo);
+
+ // Adds or replaces the data_ of a primitive child node.
+ void RenderDataPiece(StringPiece name, const DataPiece& data);
+
+ // Returns the default enum value as a DataPiece, or the first enum value if
+ // there is no default. For proto3, where we cannot specify an explicit
+ // default, a zero value will always be returned.
+ static DataPiece FindEnumDefault(const google::protobuf::Field& field,
+ const TypeInfo* typeinfo);
+
+ // Type information for all the types used in the descriptor. Used to find
+ // google::protobuf::Type of nested messages/enums.
+ const TypeInfo* typeinfo_;
+ // Whether the TypeInfo object is owned by this class.
+ bool own_typeinfo_;
+ // google::protobuf::Type of the root message type.
+ const google::protobuf::Type& type_;
+ // Holds copies of strings passed to RenderString.
+ vector<string*> string_values_;
+
+ // The current Node. Owned by its parents.
+ Node* current_;
+ // The root Node.
+ google::protobuf::scoped_ptr<Node> root_;
+ // The stack to hold the path of Nodes from current_ to root_;
+ std::stack<Node*> stack_;
+
+ // Whether to suppress output of empty lists.
+ bool suppress_empty_list_;
+
+ // Unique Pointer to function for determining whether a field needs to be
+ // scrubbed or not.
+ FieldScrubCallBackPtr field_scrub_callback_;
+
+ ObjectWriter* ow_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(DefaultValueObjectWriter);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_DEFAULT_VALUE_OBJECTWRITER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter_test.cc
new file mode 100644
index 0000000000..e1dd697aec
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/default_value_objectwriter_test.cc
@@ -0,0 +1,189 @@
+// 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.
+
+#include <google/protobuf/util/internal/default_value_objectwriter.h>
+#include <google/protobuf/util/internal/expecting_objectwriter.h>
+#include <google/protobuf/util/internal/testdata/default_value_test.pb.h>
+#include <google/protobuf/util/internal/type_info_test_helper.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+namespace testing {
+
+using google::protobuf::testing::DefaultValueTest;
+
+// Base class for setting up required state for running default values tests on
+// different descriptors.
+class BaseDefaultValueObjectWriterTest
+ : public ::testing::TestWithParam<testing::TypeInfoSource> {
+ protected:
+ explicit BaseDefaultValueObjectWriterTest(const Descriptor* descriptor)
+ : helper_(GetParam()), mock_(), expects_(&mock_) {
+ helper_.ResetTypeInfo(descriptor);
+ testing_.reset(helper_.NewDefaultValueWriter(
+ string(kTypeServiceBaseUrl) + "/" + descriptor->full_name(), &mock_));
+ }
+
+ virtual ~BaseDefaultValueObjectWriterTest() {}
+
+ TypeInfoTestHelper helper_;
+ MockObjectWriter mock_;
+ ExpectingObjectWriter expects_;
+ google::protobuf::scoped_ptr<DefaultValueObjectWriter> testing_;
+};
+
+// Tests to cover some basic DefaultValueObjectWriter use cases. More tests are
+// in the marshalling_test.cc and translator_integration_test.cc.
+class DefaultValueObjectWriterTest : public BaseDefaultValueObjectWriterTest {
+ protected:
+ DefaultValueObjectWriterTest()
+ : BaseDefaultValueObjectWriterTest(DefaultValueTest::descriptor()) {}
+ virtual ~DefaultValueObjectWriterTest() {}
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ DefaultValueObjectWriterTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(DefaultValueObjectWriterTest, Empty) {
+ // Set expectation
+ expects_.StartObject("")
+ ->RenderDouble("doubleValue", 0.0)
+ ->StartList("repeatedDouble")
+ ->EndList()
+ ->RenderFloat("floatValue", 0.0)
+ ->RenderInt64("int64Value", 0)
+ ->RenderUint64("uint64Value", 0)
+ ->RenderInt32("int32Value", 0)
+ ->RenderUint32("uint32Value", 0)
+ ->RenderBool("boolValue", false)
+ ->RenderString("stringValue", "")
+ ->RenderBytes("bytesValue", "")
+ ->RenderString("enumValue", "ENUM_FIRST")
+ ->EndObject();
+
+ // Actual testing
+ testing_->StartObject("")->EndObject();
+}
+
+TEST_P(DefaultValueObjectWriterTest, NonDefaultDouble) {
+ // Set expectation
+ expects_.StartObject("")
+ ->RenderDouble("doubleValue", 1.0)
+ ->StartList("repeatedDouble")
+ ->EndList()
+ ->RenderFloat("floatValue", 0.0)
+ ->RenderInt64("int64Value", 0)
+ ->RenderUint64("uint64Value", 0)
+ ->RenderInt32("int32Value", 0)
+ ->RenderUint32("uint32Value", 0)
+ ->RenderBool("boolValue", false)
+ ->RenderString("stringValue", "")
+ ->RenderString("enumValue", "ENUM_FIRST")
+ ->EndObject();
+
+ // Actual testing
+ testing_->StartObject("")->RenderDouble("doubleValue", 1.0)->EndObject();
+}
+
+TEST_P(DefaultValueObjectWriterTest, ShouldRetainUnknownField) {
+ // Set expectation
+ expects_.StartObject("")
+ ->RenderDouble("doubleValue", 1.0)
+ ->StartList("repeatedDouble")
+ ->EndList()
+ ->RenderFloat("floatValue", 0.0)
+ ->RenderInt64("int64Value", 0)
+ ->RenderUint64("uint64Value", 0)
+ ->RenderInt32("int32Value", 0)
+ ->RenderUint32("uint32Value", 0)
+ ->RenderBool("boolValue", false)
+ ->RenderString("stringValue", "")
+ ->RenderString("unknown", "abc")
+ ->StartObject("unknownObject")
+ ->RenderString("unknown", "def")
+ ->EndObject()
+ ->RenderString("enumValue", "ENUM_FIRST")
+ ->EndObject();
+
+ // Actual testing
+ testing_->StartObject("")
+ ->RenderDouble("doubleValue", 1.0)
+ ->RenderString("unknown", "abc")
+ ->StartObject("unknownObject")
+ ->RenderString("unknown", "def")
+ ->EndObject()
+ ->EndObject();
+}
+
+
+class DefaultValueObjectWriterSuppressListTest
+ : public BaseDefaultValueObjectWriterTest {
+ protected:
+ DefaultValueObjectWriterSuppressListTest()
+ : BaseDefaultValueObjectWriterTest(DefaultValueTest::descriptor()) {
+ testing_->set_suppress_empty_list(true);
+ }
+ ~DefaultValueObjectWriterSuppressListTest() {}
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ DefaultValueObjectWriterSuppressListTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(DefaultValueObjectWriterSuppressListTest, Empty) {
+ // Set expectation. Emtpy lists should be suppressed.
+ expects_.StartObject("")
+ ->RenderDouble("doubleValue", 0.0)
+ ->RenderFloat("floatValue", 0.0)
+ ->RenderInt64("int64Value", 0)
+ ->RenderUint64("uint64Value", 0)
+ ->RenderInt32("int32Value", 0)
+ ->RenderUint32("uint32Value", 0)
+ ->RenderBool("boolValue", false)
+ ->RenderString("stringValue", "")
+ ->RenderBytes("bytesValue", "")
+ ->RenderString("enumValue", "ENUM_FIRST")
+ ->EndObject();
+
+ // Actual testing
+ testing_->StartObject("")->EndObject();
+}
+} // namespace testing
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.cc
new file mode 100644
index 0000000000..538307bae2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.cc
@@ -0,0 +1,42 @@
+// 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.
+
+#include <google/protobuf/util/internal/error_listener.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.h
new file mode 100644
index 0000000000..3f0639364c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/error_listener.h
@@ -0,0 +1,103 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_ERROR_LISTENER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_ERROR_LISTENER_H__
+
+#include <algorithm>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/util/internal/location_tracker.h>
+#include <google/protobuf/stubs/stringpiece.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// Interface for error listener.
+class LIBPROTOBUF_EXPORT ErrorListener {
+ public:
+ virtual ~ErrorListener() {}
+
+ // Reports an invalid name at the given location.
+ virtual void InvalidName(const LocationTrackerInterface& loc,
+ StringPiece unknown_name, StringPiece message) = 0;
+
+ // Reports an invalid value for a field.
+ virtual void InvalidValue(const LocationTrackerInterface& loc,
+ StringPiece type_name, StringPiece value) = 0;
+
+ // Reports a missing required field.
+ virtual void MissingField(const LocationTrackerInterface& loc,
+ StringPiece missing_name) = 0;
+
+ protected:
+ ErrorListener() {}
+
+ private:
+ // Do not add any data members to this class.
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ErrorListener);
+};
+
+// An error listener that ignores all errors.
+class LIBPROTOBUF_EXPORT NoopErrorListener : public ErrorListener {
+ public:
+ NoopErrorListener() {}
+ virtual ~NoopErrorListener() {}
+
+ virtual void InvalidName(const LocationTrackerInterface& loc,
+ StringPiece unknown_name, StringPiece message) {}
+
+ virtual void InvalidValue(const LocationTrackerInterface& loc,
+ StringPiece type_name, StringPiece value) {}
+
+ virtual void MissingField(const LocationTrackerInterface& loc,
+ StringPiece missing_name) {}
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(NoopErrorListener);
+};
+
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_ERROR_LISTENER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/expecting_objectwriter.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/expecting_objectwriter.h
new file mode 100644
index 0000000000..ae98ddd86a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/expecting_objectwriter.h
@@ -0,0 +1,238 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_EXPECTING_OBJECTWRITER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_EXPECTING_OBJECTWRITER_H__
+
+// An implementation of ObjectWriter that automatically sets the
+// gmock expectations for the response to a method. Every method
+// returns the object itself for chaining.
+//
+// Usage:
+// // Setup
+// MockObjectWriter mock;
+// ExpectingObjectWriter ow(&mock);
+//
+// // Set expectation
+// ow.StartObject("")
+// ->RenderString("key", "value")
+// ->EndObject();
+//
+// // Actual testing
+// mock.StartObject(StringPiece())
+// ->RenderString("key", "value")
+// ->EndObject();
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/util/internal/object_writer.h>
+#include <gmock/gmock.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using testing::IsEmpty;
+using testing::NanSensitiveDoubleEq;
+using testing::NanSensitiveFloatEq;
+using testing::Return;
+using testing::StrEq;
+using testing::TypedEq;
+
+class MockObjectWriter : public ObjectWriter {
+ public:
+ MockObjectWriter() {}
+
+ MOCK_METHOD1(StartObject, ObjectWriter*(StringPiece));
+ MOCK_METHOD0(EndObject, ObjectWriter*());
+ MOCK_METHOD1(StartList, ObjectWriter*(StringPiece));
+ MOCK_METHOD0(EndList, ObjectWriter*());
+ MOCK_METHOD2(RenderBool, ObjectWriter*(StringPiece, bool));
+ MOCK_METHOD2(RenderInt32, ObjectWriter*(StringPiece, int32));
+ MOCK_METHOD2(RenderUint32, ObjectWriter*(StringPiece, uint32));
+ MOCK_METHOD2(RenderInt64, ObjectWriter*(StringPiece, int64));
+ MOCK_METHOD2(RenderUint64, ObjectWriter*(StringPiece, uint64));
+ MOCK_METHOD2(RenderDouble, ObjectWriter*(StringPiece, double));
+ MOCK_METHOD2(RenderFloat, ObjectWriter*(StringPiece, float));
+ MOCK_METHOD2(RenderString, ObjectWriter*(StringPiece, StringPiece));
+ MOCK_METHOD2(RenderBytes, ObjectWriter*(StringPiece, StringPiece));
+ MOCK_METHOD1(RenderNull, ObjectWriter*(StringPiece));
+};
+
+class ExpectingObjectWriter : public ObjectWriter {
+ public:
+ explicit ExpectingObjectWriter(MockObjectWriter* mock) : mock_(mock) {}
+
+ virtual ObjectWriter* StartObject(StringPiece name) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, StartObject(IsEmpty()))
+ : EXPECT_CALL(*mock_, StartObject(StrEq(name.ToString()))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* EndObject() {
+ EXPECT_CALL(*mock_, EndObject())
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* StartList(StringPiece name) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, StartList(IsEmpty()))
+ : EXPECT_CALL(*mock_, StartList(StrEq(name.ToString()))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* EndList() {
+ EXPECT_CALL(*mock_, EndList())
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderBool(StringPiece name, bool value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderBool(IsEmpty(), TypedEq<bool>(value)))
+ : EXPECT_CALL(*mock_, RenderBool(StrEq(name.ToString()),
+ TypedEq<bool>(value))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderInt32(StringPiece name, int32 value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderInt32(IsEmpty(), TypedEq<int32>(value)))
+ : EXPECT_CALL(*mock_, RenderInt32(StrEq(name.ToString()),
+ TypedEq<int32>(value))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderUint32(StringPiece name, uint32 value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderUint32(IsEmpty(), TypedEq<uint32>(value)))
+ : EXPECT_CALL(*mock_, RenderUint32(StrEq(name.ToString()),
+ TypedEq<uint32>(value))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderInt64(StringPiece name, int64 value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderInt64(IsEmpty(), TypedEq<int64>(value)))
+ : EXPECT_CALL(*mock_, RenderInt64(StrEq(name.ToString()),
+ TypedEq<int64>(value))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderUint64(StringPiece name, uint64 value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderUint64(IsEmpty(), TypedEq<uint64>(value)))
+ : EXPECT_CALL(*mock_, RenderUint64(StrEq(name.ToString()),
+ TypedEq<uint64>(value))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderDouble(StringPiece name, double value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderDouble(IsEmpty(),
+ NanSensitiveDoubleEq(value)))
+ : EXPECT_CALL(*mock_, RenderDouble(StrEq(name.ToString()),
+ NanSensitiveDoubleEq(value))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderFloat(StringPiece name, float value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderFloat(IsEmpty(),
+ NanSensitiveFloatEq(value)))
+ : EXPECT_CALL(*mock_, RenderFloat(StrEq(name.ToString()),
+ NanSensitiveFloatEq(value))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderString(StringPiece name, StringPiece value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderString(IsEmpty(),
+ TypedEq<StringPiece>(value.ToString())))
+ : EXPECT_CALL(*mock_, RenderString(StrEq(name.ToString()),
+ TypedEq<StringPiece>(value.ToString()))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+ virtual ObjectWriter* RenderBytes(StringPiece name, StringPiece value) {
+ (name.empty()
+ ? EXPECT_CALL(*mock_, RenderBytes(IsEmpty(), TypedEq<StringPiece>(
+ value.ToString())))
+ : EXPECT_CALL(*mock_,
+ RenderBytes(StrEq(name.ToString()),
+ TypedEq<StringPiece>(value.ToString()))))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation();
+ return this;
+ }
+
+ virtual ObjectWriter* RenderNull(StringPiece name) {
+ (name.empty() ? EXPECT_CALL(*mock_, RenderNull(IsEmpty()))
+ : EXPECT_CALL(*mock_, RenderNull(StrEq(name.ToString())))
+ .WillOnce(Return(mock_))
+ .RetiresOnSaturation());
+ return this;
+ }
+
+ private:
+ MockObjectWriter* mock_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(ExpectingObjectWriter);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_EXPECTING_OBJECTWRITER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.cc
new file mode 100644
index 0000000000..f0e8fc88a4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.cc
@@ -0,0 +1,225 @@
+// 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.
+
+#include <google/protobuf/util/internal/field_mask_utility.h>
+
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/status_macros.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+namespace {
+inline util::Status CallPathSink(PathSinkCallback path_sink,
+ StringPiece arg) {
+ return path_sink->Run(arg);
+}
+
+util::Status CreatePublicError(util::error::Code code,
+ const string& message) {
+ return util::Status(code, message);
+}
+
+// Appends a FieldMask path segment to a prefix.
+string AppendPathSegmentToPrefix(StringPiece prefix, StringPiece segment) {
+ if (prefix.empty()) {
+ return segment.ToString();
+ }
+ if (segment.empty()) {
+ return prefix.ToString();
+ }
+ // If the segment is a map key, appends it to the prefix without the ".".
+ if (segment.starts_with("[\"")) {
+ return StrCat(prefix, segment);
+ }
+ return StrCat(prefix, ".", segment);
+}
+
+} // namespace
+
+string ConvertFieldMaskPath(const StringPiece path,
+ ConverterCallback converter) {
+ string result;
+ result.reserve(path.size() << 1);
+
+ bool is_quoted = false;
+ bool is_escaping = false;
+ int current_segment_start = 0;
+
+ // Loops until 1 passed the end of the input to make handling the last
+ // segment easier.
+ for (size_t i = 0; i <= path.size(); ++i) {
+ // Outputs quoted string as-is.
+ if (is_quoted) {
+ if (i == path.size()) {
+ break;
+ }
+ result.push_back(path[i]);
+ if (is_escaping) {
+ is_escaping = false;
+ } else if (path[i] == '\\') {
+ is_escaping = true;
+ } else if (path[i] == '\"') {
+ current_segment_start = i + 1;
+ is_quoted = false;
+ }
+ continue;
+ }
+ if (i == path.size() || path[i] == '.' || path[i] == '(' ||
+ path[i] == ')' || path[i] == '\"') {
+ result += converter(
+ path.substr(current_segment_start, i - current_segment_start));
+ if (i < path.size()) {
+ result.push_back(path[i]);
+ }
+ current_segment_start = i + 1;
+ }
+ if (i < path.size() && path[i] == '\"') {
+ is_quoted = true;
+ }
+ }
+ return result;
+}
+
+util::Status DecodeCompactFieldMaskPaths(StringPiece paths,
+ PathSinkCallback path_sink) {
+ stack<string> prefix;
+ int length = paths.length();
+ int previous_position = 0;
+ bool in_map_key = false;
+ bool is_escaping = false;
+ // Loops until 1 passed the end of the input to make the handle of the last
+ // segment easier.
+ for (int i = 0; i <= length; ++i) {
+ if (i != length) {
+ // Skips everything in a map key until we hit the end of it, which is
+ // marked by an un-escaped '"' immediately followed by a ']'.
+ if (in_map_key) {
+ if (is_escaping) {
+ is_escaping = false;
+ continue;
+ }
+ if (paths[i] == '\\') {
+ is_escaping = true;
+ continue;
+ }
+ if (paths[i] != '\"') {
+ continue;
+ }
+ // Un-escaped '"' must be followed with a ']'.
+ if (i >= length - 1 || paths[i + 1] != ']') {
+ return util::Status(
+ util::error::INVALID_ARGUMENT,
+ StrCat("Invalid FieldMask '", paths,
+ "'. Map keys should be represented as [\"some_key\"]."));
+ }
+ // The end of the map key ("\"]") has been found.
+ in_map_key = false;
+ // Skips ']'.
+ i++;
+ // Checks whether the key ends at the end of a path segment.
+ if (i < length - 1 && paths[i + 1] != '.' && paths[i + 1] != ',' &&
+ paths[i + 1] != ')' && paths[i + 1] != '(') {
+ return util::Status(
+ util::error::INVALID_ARGUMENT,
+ StrCat("Invalid FieldMask '", paths,
+ "'. Map keys should be at the end of a path segment."));
+ }
+ is_escaping = false;
+ continue;
+ }
+
+ // We are not in a map key, look for the start of one.
+ if (paths[i] == '[') {
+ if (i >= length - 1 || paths[i + 1] != '\"') {
+ return util::Status(
+ util::error::INVALID_ARGUMENT,
+ StrCat("Invalid FieldMask '", paths,
+ "'. Map keys should be represented as [\"some_key\"]."));
+ }
+ // "[\"" starts a map key.
+ in_map_key = true;
+ i++; // Skips the '\"'.
+ continue;
+ }
+ // If the current character is not a special character (',', '(' or ')'),
+ // continue to the next.
+ if (paths[i] != ',' && paths[i] != ')' && paths[i] != '(') {
+ continue;
+ }
+ }
+ // Gets the current segment - sub-string between previous position (after
+ // '(', ')', ',', or the beginning of the input) and the current position.
+ StringPiece segment =
+ paths.substr(previous_position, i - previous_position);
+ string current_prefix = prefix.empty() ? "" : prefix.top();
+
+ if (i < length && paths[i] == '(') {
+ // Builds a prefix and save it into the stack.
+ prefix.push(AppendPathSegmentToPrefix(current_prefix, segment));
+ } else if (!segment.empty()) {
+ // When the current charactor is ')', ',' or the current position has
+ // passed the end of the input, builds and outputs a new paths by
+ // concatenating the last prefix with the current segment.
+ RETURN_IF_ERROR(CallPathSink(
+ path_sink, AppendPathSegmentToPrefix(current_prefix, segment)));
+ }
+
+ // Removes the last prefix after seeing a ')'.
+ if (i < length && paths[i] == ')') {
+ if (prefix.empty()) {
+ return util::Status(
+ util::error::INVALID_ARGUMENT,
+ StrCat("Invalid FieldMask '", paths,
+ "'. Cannot find matching '(' for all ')'."));
+ }
+ prefix.pop();
+ }
+ previous_position = i + 1;
+ }
+ if (in_map_key) {
+ return util::Status(util::error::INVALID_ARGUMENT,
+ StrCat("Invalid FieldMask '", paths,
+ "'. Cannot find matching ']' for all '['."));
+ }
+ if (!prefix.empty()) {
+ return util::Status(util::error::INVALID_ARGUMENT,
+ StrCat("Invalid FieldMask '", paths,
+ "'. Cannot find matching ')' for all '('."));
+ }
+ return util::Status::OK;
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.h
new file mode 100644
index 0000000000..59f36f756f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/field_mask_utility.h
@@ -0,0 +1,72 @@
+// 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.
+
+// FieldMask related utility methods.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_FIELD_MASK_UTILITY_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_FIELD_MASK_UTILITY_H__
+
+#include <functional>
+#include <stack>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/status.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+typedef string (*ConverterCallback)(StringPiece);
+typedef ResultCallback1<util::Status, StringPiece>* PathSinkCallback;
+
+// Applies a 'converter' to each segment of a FieldMask path and returns the
+// result. Quoted strings in the 'path' are copied to the output as-is without
+// converting their content. Escaping is supported within quoted strings.
+// For example, "ab\"_c" will be returned as "ab\"_c" without any changes.
+string ConvertFieldMaskPath(const StringPiece path,
+ ConverterCallback converter);
+
+// Decodes a compact list of FieldMasks. For example, "a.b,a.c.d,a.c.e" will be
+// decoded into a list of field paths - "a.b", "a.c.d", "a.c.e". And the results
+// will be sent to 'path_sink', i.e. 'path_sink' will be called once per
+// resulting path.
+// Note that we also support Apiary style FieldMask form. The above example in
+// the Apiary style will look like "a.b,a.c(d,e)".
+util::Status DecodeCompactFieldMaskPaths(StringPiece paths,
+ PathSinkCallback path_sink);
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_FIELD_MASK_UTILITY_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.cc
new file mode 100644
index 0000000000..06d2791bf2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.cc
@@ -0,0 +1,404 @@
+// 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.
+
+#include <google/protobuf/util/internal/json_escaping.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+namespace {
+
+// Array of hex characters for conversion to hex.
+static const char kHex[] = "0123456789abcdef";
+
+// Characters 0x00 to 0x9f are very commonly used, so we provide a special
+// table lookup.
+//
+// For unicode code point ch < 0xa0:
+// kCommonEscapes[ch] is the escaped string of ch, if escaping is needed;
+// or an empty string, if escaping is not needed.
+static const char kCommonEscapes[160][7] = {
+ // C0 (ASCII and derivatives) control characters
+ "\\u0000", "\\u0001", "\\u0002", "\\u0003", // 0x00
+ "\\u0004", "\\u0005", "\\u0006", "\\u0007",
+ "\\b", "\\t", "\\n", "\\u000b",
+ "\\f", "\\r", "\\u000e", "\\u000f",
+ "\\u0010", "\\u0011", "\\u0012", "\\u0013", // 0x10
+ "\\u0014", "\\u0015", "\\u0016", "\\u0017",
+ "\\u0018", "\\u0019", "\\u001a", "\\u001b",
+ "\\u001c", "\\u001d", "\\u001e", "\\u001f",
+ // Escaping of " and \ are required by www.json.org string definition.
+ // Escaping of < and > are required for HTML security.
+ "", "", "\\\"", "", "", "", "", "", // 0x20
+ "", "", "", "", "", "", "", "",
+ "", "", "", "", "", "", "", "", // 0x30
+ "", "", "", "", "\\u003c", "", "\\u003e", "",
+ "", "", "", "", "", "", "", "", // 0x40
+ "", "", "", "", "", "", "", "",
+ "", "", "", "", "", "", "", "", // 0x50
+ "", "", "", "", "\\\\", "", "", "",
+ "", "", "", "", "", "", "", "", // 0x60
+ "", "", "", "", "", "", "", "",
+ "", "", "", "", "", "", "", "", // 0x70
+ "", "", "", "", "", "", "", "\\u007f",
+ // C1 (ISO 8859 and Unicode) extended control characters
+ "\\u0080", "\\u0081", "\\u0082", "\\u0083", // 0x80
+ "\\u0084", "\\u0085", "\\u0086", "\\u0087",
+ "\\u0088", "\\u0089", "\\u008a", "\\u008b",
+ "\\u008c", "\\u008d", "\\u008e", "\\u008f",
+ "\\u0090", "\\u0091", "\\u0092", "\\u0093", // 0x90
+ "\\u0094", "\\u0095", "\\u0096", "\\u0097",
+ "\\u0098", "\\u0099", "\\u009a", "\\u009b",
+ "\\u009c", "\\u009d", "\\u009e", "\\u009f"
+};
+
+// Determines if the given char value is a unicode high-surrogate code unit.
+// Such values do not represent characters by themselves, but are used in the
+// representation of supplementary characters in the utf-16 encoding.
+inline bool IsHighSurrogate(uint16 c) {
+ // Optimized form of:
+ // return c >= kMinHighSurrogate && c <= kMaxHighSurrogate;
+ // (Reduced from 3 ALU instructions to 2 ALU instructions)
+ return (c & ~(JsonEscaping::kMaxHighSurrogate -
+ JsonEscaping::kMinHighSurrogate))
+ == JsonEscaping::kMinHighSurrogate;
+}
+
+// Determines if the given char value is a unicode low-surrogate code unit.
+// Such values do not represent characters by themselves, but are used in the
+// representation of supplementary characters in the utf-16 encoding.
+inline bool IsLowSurrogate(uint16 c) {
+ // Optimized form of:
+ // return c >= kMinLowSurrogate && c <= kMaxLowSurrogate;
+ // (Reduced from 3 ALU instructions to 2 ALU instructions)
+ return (c & ~(JsonEscaping::kMaxLowSurrogate -
+ JsonEscaping::kMinLowSurrogate))
+ == JsonEscaping::kMinLowSurrogate;
+}
+
+// Determines if the given char value is a unicode surrogate code unit (either
+// high-surrogate or low-surrogate).
+inline bool IsSurrogate(uint32 c) {
+ // Optimized form of:
+ // return c >= kMinHighSurrogate && c <= kMaxLowSurrogate;
+ // (Reduced from 3 ALU instructions to 2 ALU instructions)
+ return (c & 0xfffff800) == JsonEscaping::kMinHighSurrogate;
+}
+
+// Returns true if the given unicode code point cp is
+// in the supplementary character range.
+inline bool IsSupplementalCodePoint(uint32 cp) {
+ // Optimized form of:
+ // return kMinSupplementaryCodePoint <= cp && cp <= kMaxCodePoint;
+ // (Reduced from 3 ALU instructions to 2 ALU instructions)
+ return (cp & ~(JsonEscaping::kMinSupplementaryCodePoint - 1))
+ < JsonEscaping::kMaxCodePoint;
+}
+
+// Returns true if the given unicode code point cp is a valid
+// unicode code point (i.e. in the range 0 <= cp <= kMaxCodePoint).
+inline bool IsValidCodePoint(uint32 cp) {
+ return cp <= JsonEscaping::kMaxCodePoint;
+}
+
+// Converts the specified surrogate pair to its supplementary code point value.
+// It is the callers' responsibility to validate the specified surrogate pair.
+inline uint32 ToCodePoint(uint16 high, uint16 low) {
+ // Optimized form of:
+ // return ((high - kMinHighSurrogate) << 10)
+ // + (low - kMinLowSurrogate)
+ // + kMinSupplementaryCodePoint;
+ // (Reduced from 5 ALU instructions to 3 ALU instructions)
+ return (high << 10) + low +
+ (JsonEscaping::kMinSupplementaryCodePoint
+ - (static_cast<unsigned>(JsonEscaping::kMinHighSurrogate) << 10)
+ - JsonEscaping::kMinLowSurrogate);
+}
+
+// Returns the low surrogate for the given unicode code point. The result is
+// meaningless if the given code point is not a supplementary character.
+inline uint16 ToLowSurrogate(uint32 cp) {
+ return (cp & (JsonEscaping::kMaxLowSurrogate
+ - JsonEscaping::kMinLowSurrogate))
+ + JsonEscaping::kMinLowSurrogate;
+}
+
+// Returns the high surrogate for the given unicode code point. The result is
+// meaningless if the given code point is not a supplementary character.
+inline uint16 ToHighSurrogate(uint32 cp) {
+ return (cp >> 10) + (JsonEscaping::kMinHighSurrogate -
+ (JsonEscaping::kMinSupplementaryCodePoint >> 10));
+}
+
+// Input str is encoded in UTF-8. A unicode code point could be encoded in
+// UTF-8 using anywhere from 1 to 4 characters, and it could span multiple
+// reads of the ByteSource.
+//
+// This function reads the next unicode code point from the input (str) at
+// the given position (index), taking into account any left-over partial
+// code point from the previous iteration (cp), together with the number
+// of characters left to read to complete this code point (num_left).
+//
+// This function assumes that the input (str) is valid at the given position
+// (index). In order words, at least one character could be read successfully.
+//
+// The code point read (partial or complete) is stored in (cp). Upon return,
+// (num_left) stores the number of characters that has yet to be read in
+// order to complete the current unicode code point. If the read is complete,
+// then (num_left) is 0. Also, (num_read) is the number of characters read.
+//
+// Returns false if we encounter an invalid UTF-8 string. Returns true
+// otherwise, including the case when we reach the end of the input (str)
+// before a complete unicode code point is read.
+bool ReadCodePoint(StringPiece str, int index,
+ uint32 *cp, int* num_left, int *num_read) {
+ if (*num_left == 0) {
+ // Last read was complete. Start reading a new unicode code point.
+ *cp = static_cast<uint8>(str[index++]);
+ *num_read = 1;
+ // The length of the code point is determined from reading the first byte.
+ //
+ // If the first byte is between:
+ // 0..0x7f: that's the value of the code point.
+ // 0x80..0xbf: <invalid>
+ // 0xc0..0xdf: 11-bit code point encoded in 2 bytes.
+ // bit 10-6, bit 5-0
+ // 0xe0..0xef: 16-bit code point encoded in 3 bytes.
+ // bit 15-12, bit 11-6, bit 5-0
+ // 0xf0..0xf7: 21-bit code point encoded in 4 bytes.
+ // bit 20-18, bit 17-12, bit 11-6, bit 5-0
+ // 0xf8..0xff: <invalid>
+ //
+ // Meaning of each bit:
+ // <msb> bit 7: 0 - single byte code point: bits 6-0 are values.
+ // 1 - multibyte code point
+ // bit 6: 0 - subsequent bytes of multibyte code point:
+ // bits 5-0 are values.
+ // 1 - first byte of multibyte code point
+ // bit 5: 0 - first byte of 2-byte code point: bits 4-0 are values.
+ // 1 - first byte of code point with >= 3 bytes.
+ // bit 4: 0 - first byte of 3-byte code point: bits 3-0 are values.
+ // 1 - first byte of code point with >= 4 bytes.
+ // bit 3: 0 - first byte of 4-byte code point: bits 2-0 are values.
+ // 1 - reserved for future expansion.
+ if (*cp <= 0x7f) {
+ return true;
+ } else if (*cp <= 0xbf) {
+ return false;
+ } else if (*cp <= 0xdf) {
+ *cp &= 0x1f;
+ *num_left = 1;
+ } else if (*cp <= 0xef) {
+ *cp &= 0x0f;
+ *num_left = 2;
+ } else if (*cp <= 0xf7) {
+ *cp &= 0x07;
+ *num_left = 3;
+ } else {
+ return false;
+ }
+ } else {
+ // Last read was partial. Initialize num_read to 0 and continue reading
+ // the last unicode code point.
+ *num_read = 0;
+ }
+ while (*num_left > 0 && index < str.size()) {
+ uint32 ch = static_cast<uint8>(str[index++]);
+ --(*num_left);
+ ++(*num_read);
+ *cp = (*cp << 6) | (ch & 0x3f);
+ if (ch < 0x80 || ch > 0xbf) return false;
+ }
+ return *num_left > 0 || (!IsSurrogate(*cp) && IsValidCodePoint(*cp));
+}
+
+// Stores the 16-bit unicode code point as its hexadecimal digits in buffer
+// and returns a StringPiece that points to this buffer. The input buffer needs
+// to be at least 6 bytes long.
+StringPiece ToHex(uint16 cp, char* buffer) {
+ buffer[5] = kHex[cp & 0x0f];
+ cp >>= 4;
+ buffer[4] = kHex[cp & 0x0f];
+ cp >>= 4;
+ buffer[3] = kHex[cp & 0x0f];
+ cp >>= 4;
+ buffer[2] = kHex[cp & 0x0f];
+ return StringPiece(buffer).substr(0, 6);
+}
+
+// Stores the 32-bit unicode code point as its hexadecimal digits in buffer
+// and returns a StringPiece that points to this buffer. The input buffer needs
+// to be at least 12 bytes long.
+StringPiece ToSurrogateHex(uint32 cp, char* buffer) {
+ uint16 low = ToLowSurrogate(cp);
+ uint16 high = ToHighSurrogate(cp);
+
+ buffer[11] = kHex[low & 0x0f];
+ low >>= 4;
+ buffer[10] = kHex[low & 0x0f];
+ low >>= 4;
+ buffer[9] = kHex[low & 0x0f];
+ low >>= 4;
+ buffer[8] = kHex[low & 0x0f];
+
+ buffer[5] = kHex[high & 0x0f];
+ high >>= 4;
+ buffer[4] = kHex[high & 0x0f];
+ high >>= 4;
+ buffer[3] = kHex[high & 0x0f];
+ high >>= 4;
+ buffer[2] = kHex[high & 0x0f];
+
+ return StringPiece(buffer, 12);
+}
+
+// If the given unicode code point needs escaping, then returns the
+// escaped form. The returned StringPiece either points to statically
+// pre-allocated char[] or to the given buffer. The input buffer needs
+// to be at least 12 bytes long.
+//
+// If the given unicode code point does not need escaping, an empty
+// StringPiece is returned.
+StringPiece EscapeCodePoint(uint32 cp, char* buffer) {
+ if (cp < 0xa0) return kCommonEscapes[cp];
+ switch (cp) {
+ // These are not required by json spec
+ // but used to prevent security bugs in javascript.
+ case 0xfeff: // Zero width no-break space
+ case 0xfff9: // Interlinear annotation anchor
+ case 0xfffa: // Interlinear annotation separator
+ case 0xfffb: // Interlinear annotation terminator
+
+ case 0x00ad: // Soft-hyphen
+ case 0x06dd: // Arabic end of ayah
+ case 0x070f: // Syriac abbreviation mark
+ case 0x17b4: // Khmer vowel inherent Aq
+ case 0x17b5: // Khmer vowel inherent Aa
+ return ToHex(cp, buffer);
+
+ default:
+ if ((cp >= 0x0600 && cp <= 0x0603) || // Arabic signs
+ (cp >= 0x200b && cp <= 0x200f) || // Zero width etc.
+ (cp >= 0x2028 && cp <= 0x202e) || // Separators etc.
+ (cp >= 0x2060 && cp <= 0x2064) || // Invisible etc.
+ (cp >= 0x206a && cp <= 0x206f)) { // Shaping etc.
+ return ToHex(cp, buffer);
+ }
+
+ if (cp == 0x000e0001 || // Language tag
+ (cp >= 0x0001d173 && cp <= 0x0001d17a) || // Music formatting
+ (cp >= 0x000e0020 && cp <= 0x000e007f)) { // TAG symbols
+ return ToSurrogateHex(cp, buffer);
+ }
+ }
+ return StringPiece();
+}
+
+// Tries to escape the given code point first. If the given code point
+// does not need to be escaped, but force_output is true, then render
+// the given multi-byte code point in UTF8 in the buffer and returns it.
+StringPiece EscapeCodePoint(uint32 cp, char* buffer, bool force_output) {
+ StringPiece sp = EscapeCodePoint(cp, buffer);
+ if (force_output && sp.empty()) {
+ buffer[5] = (cp & 0x3f) | 0x80;
+ cp >>= 6;
+ if (cp <= 0x1f) {
+ buffer[4] = cp | 0xc0;
+ sp.set(buffer + 4, 2);
+ return sp;
+ }
+ buffer[4] = (cp & 0x3f) | 0x80;
+ cp >>= 6;
+ if (cp <= 0x0f) {
+ buffer[3] = cp | 0xe0;
+ sp.set(buffer + 3, 3);
+ return sp;
+ }
+ buffer[3] = (cp & 0x3f) | 0x80;
+ buffer[2] = ((cp >> 6) & 0x07) | 0xf0;
+ sp.set(buffer + 2, 4);
+ }
+ return sp;
+}
+
+} // namespace
+
+void JsonEscaping::Escape(strings::ByteSource* input,
+ strings::ByteSink* output) {
+ char buffer[12] = "\\udead\\ubee";
+ uint32 cp = 0; // Current unicode code point.
+ int num_left = 0; // Num of chars to read to complete the code point.
+ while (input->Available() > 0) {
+ StringPiece str = input->Peek();
+ StringPiece escaped;
+ int i = 0;
+ int num_read;
+ bool ok;
+ bool cp_was_split = num_left > 0;
+ // Loop until we encounter either
+ // i) a code point that needs to be escaped; or
+ // ii) a split code point is completely read; or
+ // iii) a character that is not a valid utf8; or
+ // iv) end of the StringPiece str is reached.
+ do {
+ ok = ReadCodePoint(str, i, &cp, &num_left, &num_read);
+ if (num_left > 0 || !ok) break; // case iii or iv
+ escaped = EscapeCodePoint(cp, buffer, cp_was_split);
+ if (!escaped.empty()) break; // case i or ii
+ i += num_read;
+ num_read = 0;
+ } while (i < str.length()); // case iv
+ // First copy the un-escaped prefix, if any, to the output ByteSink.
+ if (i > 0) input->CopyTo(output, i);
+ if (num_read > 0) input->Skip(num_read);
+ if (!ok) {
+ // Case iii: Report error.
+ // TODO(wpoon): Add error reporting.
+ num_left = 0;
+ } else if (num_left == 0 && !escaped.empty()) {
+ // Case i or ii: Append the escaped code point to the output ByteSink.
+ output->Append(escaped.data(), escaped.size());
+ }
+ }
+ if (num_left > 0) {
+ // Treat as case iii: report error.
+ // TODO(wpoon): Add error reporting.
+ }
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.h
new file mode 100644
index 0000000000..e3e329fc96
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_escaping.h
@@ -0,0 +1,91 @@
+// 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.
+
+#ifndef NET_PROTO2_UTIL_CONVERTER_STRINGS_JSON_ESCAPING_H_
+#define NET_PROTO2_UTIL_CONVERTER_STRINGS_JSON_ESCAPING_H_
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/bytestream.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class JsonEscaping {
+ public:
+ // The minimum value of a unicode high-surrogate code unit in the utf-16
+ // encoding. A high-surrogate is also known as a leading-surrogate.
+ // See http://www.unicode.org/glossary/#high_surrogate_code_unit
+ static const uint16 kMinHighSurrogate = 0xd800;
+
+ // The maximum value of a unicide high-surrogate code unit in the utf-16
+ // encoding. A high-surrogate is also known as a leading-surrogate.
+ // See http://www.unicode.org/glossary/#high_surrogate_code_unit
+ static const uint16 kMaxHighSurrogate = 0xdbff;
+
+ // The minimum value of a unicode low-surrogate code unit in the utf-16
+ // encoding. A low-surrogate is also known as a trailing-surrogate.
+ // See http://www.unicode.org/glossary/#low_surrogate_code_unit
+ static const uint16 kMinLowSurrogate = 0xdc00;
+
+ // The maximum value of a unicode low-surrogate code unit in the utf-16
+ // encoding. A low-surrogate is also known as a trailing surrogate.
+ // See http://www.unicode.org/glossary/#low_surrogate_code_unit
+ static const uint16 kMaxLowSurrogate = 0xdfff;
+
+ // The minimum value of a unicode supplementary code point.
+ // See http://www.unicode.org/glossary/#supplementary_code_point
+ static const uint32 kMinSupplementaryCodePoint = 0x010000;
+
+ // The minimum value of a unicode code point.
+ // See http://www.unicode.org/glossary/#code_point
+ static const uint32 kMinCodePoint = 0x000000;
+
+ // The maximum value of a unicode code point.
+ // See http://www.unicode.org/glossary/#code_point
+ static const uint32 kMaxCodePoint = 0x10ffff;
+
+ JsonEscaping() {}
+ virtual ~JsonEscaping() {}
+
+ // Escape the given ByteSource to the given ByteSink.
+ static void Escape(strings::ByteSource* input, strings::ByteSink* output);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(JsonEscaping);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+#endif // NET_PROTO2_UTIL_CONVERTER_STRINGS_JSON_ESCAPING_H_
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.cc
new file mode 100644
index 0000000000..b84210c10b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.cc
@@ -0,0 +1,183 @@
+// 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.
+
+#include <google/protobuf/util/internal/json_objectwriter.h>
+
+#include <math.h>
+
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/util/internal/json_escaping.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/mathlimits.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using strings::ArrayByteSource;
+;
+
+JsonObjectWriter::~JsonObjectWriter() {
+ if (!element_->is_root()) {
+ GOOGLE_LOG(WARNING) << "JsonObjectWriter was not fully closed.";
+ }
+}
+
+JsonObjectWriter* JsonObjectWriter::StartObject(StringPiece name) {
+ WritePrefix(name);
+ WriteChar('{');
+ Push();
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::EndObject() {
+ Pop();
+ WriteChar('}');
+ if (element()->is_root()) NewLine();
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::StartList(StringPiece name) {
+ WritePrefix(name);
+ WriteChar('[');
+ Push();
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::EndList() {
+ Pop();
+ WriteChar(']');
+ if (element()->is_root()) NewLine();
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderBool(StringPiece name, bool value) {
+ return RenderSimple(name, value ? "true" : "false");
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderInt32(StringPiece name, int32 value) {
+ return RenderSimple(name, SimpleItoa(value));
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderUint32(StringPiece name,
+ uint32 value) {
+ return RenderSimple(name, SimpleItoa(value));
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderInt64(StringPiece name, int64 value) {
+ WritePrefix(name);
+ WriteChar('"');
+ stream_->WriteString(SimpleItoa(value));
+ WriteChar('"');
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderUint64(StringPiece name,
+ uint64 value) {
+ WritePrefix(name);
+ WriteChar('"');
+ stream_->WriteString(SimpleItoa(value));
+ WriteChar('"');
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderDouble(StringPiece name,
+ double value) {
+ if (MathLimits<double>::IsFinite(value)) {
+ return RenderSimple(name, SimpleDtoa(value));
+ }
+
+ // Render quoted with NaN/Infinity-aware DoubleAsString.
+ return RenderString(name, DoubleAsString(value));
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderFloat(StringPiece name, float value) {
+ if (MathLimits<float>::IsFinite(value)) {
+ return RenderSimple(name, SimpleFtoa(value));
+ }
+
+ // Render quoted with NaN/Infinity-aware FloatAsString.
+ return RenderString(name, FloatAsString(value));
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderString(StringPiece name,
+ StringPiece value) {
+ WritePrefix(name);
+ WriteChar('"');
+ ArrayByteSource source(value);
+ JsonEscaping::Escape(&source, &sink_);
+ WriteChar('"');
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderBytes(StringPiece name,
+ StringPiece value) {
+ WritePrefix(name);
+ string base64;
+
+ if (use_websafe_base64_for_bytes_)
+ WebSafeBase64Escape(value.ToString(), &base64);
+ else
+ Base64Escape(value, &base64);
+
+ WriteChar('"');
+ // TODO(wpoon): Consider a ByteSink solution that writes the base64 bytes
+ // directly to the stream, rather than first putting them
+ // into a string and then writing them to the stream.
+ stream_->WriteRaw(base64.data(), base64.size());
+ WriteChar('"');
+ return this;
+}
+
+JsonObjectWriter* JsonObjectWriter::RenderNull(StringPiece name) {
+ return RenderSimple(name, "null");
+}
+
+void JsonObjectWriter::WritePrefix(StringPiece name) {
+ bool not_first = !element()->is_first();
+ if (not_first) WriteChar(',');
+ if (not_first || !element()->is_root()) NewLine();
+ if (!name.empty()) {
+ WriteChar('"');
+ ArrayByteSource source(name);
+ JsonEscaping::Escape(&source, &sink_);
+ stream_->WriteString("\":");
+ if (!indent_string_.empty()) WriteChar(' ');
+ }
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.h
new file mode 100644
index 0000000000..cb7e2fb30c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter.h
@@ -0,0 +1,215 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_JSON_OBJECTWRITER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_JSON_OBJECTWRITER_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/util/internal/structured_objectwriter.h>
+#include <google/protobuf/stubs/bytestream.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// An ObjectWriter implementation that outputs JSON. This ObjectWriter
+// supports writing a compact form or a pretty printed form.
+//
+// Sample usage:
+// string output;
+// StringOutputStream* str_stream = new StringOutputStream(&output);
+// CodedOutputStream* out_stream = new CodedOutputStream(str_stream);
+// JsonObjectWriter* ow = new JsonObjectWriter(" ", out_stream);
+// ow->StartObject("")
+// ->RenderString("name", "value")
+// ->RenderString("emptystring", string())
+// ->StartObject("nested")
+// ->RenderInt64("light", 299792458);
+// ->RenderDouble("pi", 3.141592653589793);
+// ->EndObject()
+// ->StartList("empty")
+// ->EndList()
+// ->EndObject();
+//
+// And then the output string would become:
+// {
+// "name": "value",
+// "emptystring": "",
+// "nested": {
+// "light": "299792458",
+// "pi": 3.141592653589793
+// },
+// "empty": []
+// }
+//
+// JsonObjectWriter does not validate if calls actually result in valid JSON.
+// For example, passing an empty name when one would be required won't result
+// in an error, just an invalid output.
+//
+// Note that all int64 and uint64 are rendered as strings instead of numbers.
+// This is because JavaScript parses numbers as 64-bit float thus int64 and
+// uint64 would lose precision if rendered as numbers.
+//
+// JsonObjectWriter is thread-unsafe.
+class LIBPROTOBUF_EXPORT JsonObjectWriter : public StructuredObjectWriter {
+ public:
+ JsonObjectWriter(StringPiece indent_string,
+ google::protobuf::io::CodedOutputStream* out)
+ : element_(new Element(NULL)),
+ stream_(out),
+ sink_(out),
+ indent_string_(indent_string.ToString()),
+ use_websafe_base64_for_bytes_(false) {}
+ virtual ~JsonObjectWriter();
+
+ // ObjectWriter methods.
+ virtual JsonObjectWriter* StartObject(StringPiece name);
+ virtual JsonObjectWriter* EndObject();
+ virtual JsonObjectWriter* StartList(StringPiece name);
+ virtual JsonObjectWriter* EndList();
+ virtual JsonObjectWriter* RenderBool(StringPiece name, bool value);
+ virtual JsonObjectWriter* RenderInt32(StringPiece name, int32 value);
+ virtual JsonObjectWriter* RenderUint32(StringPiece name, uint32 value);
+ virtual JsonObjectWriter* RenderInt64(StringPiece name, int64 value);
+ virtual JsonObjectWriter* RenderUint64(StringPiece name, uint64 value);
+ virtual JsonObjectWriter* RenderDouble(StringPiece name, double value);
+ virtual JsonObjectWriter* RenderFloat(StringPiece name, float value);
+ virtual JsonObjectWriter* RenderString(StringPiece name, StringPiece value);
+ virtual JsonObjectWriter* RenderBytes(StringPiece name, StringPiece value);
+ virtual JsonObjectWriter* RenderNull(StringPiece name);
+
+ void set_use_websafe_base64_for_bytes(bool value) {
+ use_websafe_base64_for_bytes_ = value;
+ }
+
+ protected:
+ class LIBPROTOBUF_EXPORT Element : public BaseElement {
+ public:
+ explicit Element(Element* parent) : BaseElement(parent), is_first_(true) {}
+
+ // Called before each field of the Element is to be processed.
+ // Returns true if this is the first call (processing the first field).
+ bool is_first() {
+ if (is_first_) {
+ is_first_ = false;
+ return true;
+ }
+ return false;
+ }
+
+ private:
+ bool is_first_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(Element);
+ };
+
+ virtual Element* element() { return element_.get(); }
+
+ private:
+ class LIBPROTOBUF_EXPORT ByteSinkWrapper : public strings::ByteSink {
+ public:
+ explicit ByteSinkWrapper(google::protobuf::io::CodedOutputStream* stream)
+ : stream_(stream) {}
+ virtual ~ByteSinkWrapper() {}
+
+ // ByteSink methods.
+ virtual void Append(const char* bytes, size_t n) {
+ stream_->WriteRaw(bytes, n);
+ }
+
+ private:
+ google::protobuf::io::CodedOutputStream* stream_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ByteSinkWrapper);
+ };
+
+ // Renders a simple value as a string. By default all non-string Render
+ // methods convert their argument to a string and call this method. This
+ // method can then be used to render the simple value without escaping it.
+ JsonObjectWriter* RenderSimple(StringPiece name, const string& value) {
+ WritePrefix(name);
+ stream_->WriteString(value);
+ return this;
+ }
+
+ // Pushes a new element to the stack.
+ void Push() { element_.reset(new Element(element_.release())); }
+
+ // Pops an element off of the stack and deletes the popped element.
+ void Pop() {
+ bool needs_newline = !element_->is_first();
+ element_.reset(element_->pop<Element>());
+ if (needs_newline) NewLine();
+ }
+
+ // If pretty printing is enabled, this will write a newline to the output,
+ // followed by optional indentation. Otherwise this method is a noop.
+ void NewLine() {
+ if (!indent_string_.empty()) {
+ WriteChar('\n');
+ for (int i = 0; i < element()->level(); i++) {
+ stream_->WriteString(indent_string_);
+ }
+ }
+ }
+
+ // Writes a prefix. This will write out any pretty printing and
+ // commas that are required, followed by the name and a ':' if
+ // the name is not null.
+ void WritePrefix(StringPiece name);
+
+ // Writes an individual character to the output.
+ void WriteChar(const char c) { stream_->WriteRaw(&c, sizeof(c)); }
+
+ google::protobuf::scoped_ptr<Element> element_;
+ google::protobuf::io::CodedOutputStream* stream_;
+ ByteSinkWrapper sink_;
+ const string indent_string_;
+
+ // Whether to use regular or websafe base64 encoding for byte fields. Defaults
+ // to regular base64 encoding.
+ bool use_websafe_base64_for_bytes_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(JsonObjectWriter);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_JSON_OBJECTWRITER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter_test.cc
new file mode 100644
index 0000000000..b87b06ac78
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_objectwriter_test.cc
@@ -0,0 +1,313 @@
+// 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.
+
+#include <google/protobuf/util/internal/json_objectwriter.h>
+
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using google::protobuf::io::CodedOutputStream;
+using google::protobuf::io::StringOutputStream;
+
+class JsonObjectWriterTest : public ::testing::Test {
+ protected:
+ JsonObjectWriterTest()
+ : str_stream_(new StringOutputStream(&output_)),
+ out_stream_(new CodedOutputStream(str_stream_)),
+ ow_(NULL) {}
+
+ virtual ~JsonObjectWriterTest() {
+ delete ow_;
+ delete out_stream_;
+ delete str_stream_;
+ }
+
+ string output_;
+ StringOutputStream* const str_stream_;
+ CodedOutputStream* const out_stream_;
+ JsonObjectWriter* ow_;
+};
+
+TEST_F(JsonObjectWriterTest, EmptyRootObject) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")->EndObject();
+ EXPECT_EQ("{}", output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, EmptyObject) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")
+ ->RenderString("test", "value")
+ ->StartObject("empty")
+ ->EndObject()
+ ->EndObject();
+ EXPECT_EQ("{\"test\":\"value\",\"empty\":{}}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, EmptyRootList) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartList("")->EndList();
+ EXPECT_EQ("[]", output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, EmptyList) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")
+ ->RenderString("test", "value")
+ ->StartList("empty")
+ ->EndList()
+ ->EndObject();
+ EXPECT_EQ("{\"test\":\"value\",\"empty\":[]}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, ObjectInObject) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")
+ ->StartObject("nested")
+ ->RenderString("field", "value")
+ ->EndObject()
+ ->EndObject();
+ EXPECT_EQ("{\"nested\":{\"field\":\"value\"}}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, ListInObject) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")
+ ->StartList("nested")
+ ->RenderString("", "value")
+ ->EndList()
+ ->EndObject();
+ EXPECT_EQ("{\"nested\":[\"value\"]}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, ObjectInList) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartList("")
+ ->StartObject("")
+ ->RenderString("field", "value")
+ ->EndObject()
+ ->EndList();
+ EXPECT_EQ("[{\"field\":\"value\"}]",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, ListInList) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartList("")
+ ->StartList("")
+ ->RenderString("", "value")
+ ->EndList()
+ ->EndList();
+ EXPECT_EQ("[[\"value\"]]", output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, RenderPrimitives) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")
+ ->RenderBool("bool", true)
+ ->RenderDouble("double", std::numeric_limits<double>::max())
+ ->RenderFloat("float", std::numeric_limits<float>::max())
+ ->RenderInt32("int", std::numeric_limits<int32>::min())
+ ->RenderInt64("long", std::numeric_limits<int64>::min())
+ ->RenderBytes("bytes", "abracadabra")
+ ->RenderString("string", "string")
+ ->RenderBytes("emptybytes", "")
+ ->RenderString("emptystring", string())
+ ->EndObject();
+ EXPECT_EQ(
+ "{\"bool\":true,"
+ "\"double\":" +
+ ValueAsString<double>(std::numeric_limits<double>::max()) +
+ ","
+ "\"float\":" +
+ ValueAsString<float>(std::numeric_limits<float>::max()) +
+ ","
+ "\"int\":-2147483648,"
+ "\"long\":\"-9223372036854775808\","
+ "\"bytes\":\"YWJyYWNhZGFicmE=\","
+ "\"string\":\"string\","
+ "\"emptybytes\":\"\","
+ "\"emptystring\":\"\"}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, BytesEncodesAsNonWebSafeBase64) {
+ string s;
+ s.push_back('\377');
+ s.push_back('\357');
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")->RenderBytes("bytes", s)->EndObject();
+ // Non-web-safe would encode this as "/+8="
+ EXPECT_EQ("{\"bytes\":\"/+8=\"}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, PrettyPrintList) {
+ ow_ = new JsonObjectWriter(" ", out_stream_);
+ ow_->StartObject("")
+ ->StartList("items")
+ ->RenderString("", "item1")
+ ->RenderString("", "item2")
+ ->RenderString("", "item3")
+ ->EndList()
+ ->StartList("empty")
+ ->EndList()
+ ->EndObject();
+ EXPECT_EQ(
+ "{\n"
+ " \"items\": [\n"
+ " \"item1\",\n"
+ " \"item2\",\n"
+ " \"item3\"\n"
+ " ],\n"
+ " \"empty\": []\n"
+ "}\n",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, PrettyPrintObject) {
+ ow_ = new JsonObjectWriter(" ", out_stream_);
+ ow_->StartObject("")
+ ->StartObject("items")
+ ->RenderString("key1", "item1")
+ ->RenderString("key2", "item2")
+ ->RenderString("key3", "item3")
+ ->EndObject()
+ ->StartObject("empty")
+ ->EndObject()
+ ->EndObject();
+ EXPECT_EQ(
+ "{\n"
+ " \"items\": {\n"
+ " \"key1\": \"item1\",\n"
+ " \"key2\": \"item2\",\n"
+ " \"key3\": \"item3\"\n"
+ " },\n"
+ " \"empty\": {}\n"
+ "}\n",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, PrettyPrintEmptyObjectInEmptyList) {
+ ow_ = new JsonObjectWriter(" ", out_stream_);
+ ow_->StartObject("")
+ ->StartList("list")
+ ->StartObject("")
+ ->EndObject()
+ ->EndList()
+ ->EndObject();
+ EXPECT_EQ(
+ "{\n"
+ " \"list\": [\n"
+ " {}\n"
+ " ]\n"
+ "}\n",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, PrettyPrintDoubleIndent) {
+ ow_ = new JsonObjectWriter(" ", out_stream_);
+ ow_->StartObject("")
+ ->RenderBool("bool", true)
+ ->RenderInt32("int", 42)
+ ->EndObject();
+ EXPECT_EQ(
+ "{\n"
+ " \"bool\": true,\n"
+ " \"int\": 42\n"
+ "}\n",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, StringsEscapedAndEnclosedInDoubleQuotes) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")->RenderString("string", "'<>&amp;\\\"\r\n")->EndObject();
+ EXPECT_EQ("{\"string\":\"'\\u003c\\u003e&amp;\\\\\\\"\\r\\n\"}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, Stringification) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")
+ ->RenderDouble("double_nan", std::numeric_limits<double>::quiet_NaN())
+ ->RenderFloat("float_nan", std::numeric_limits<float>::quiet_NaN())
+ ->RenderDouble("double_pos", std::numeric_limits<double>::infinity())
+ ->RenderFloat("float_pos", std::numeric_limits<float>::infinity())
+ ->RenderDouble("double_neg", -std::numeric_limits<double>::infinity())
+ ->RenderFloat("float_neg", -std::numeric_limits<float>::infinity())
+ ->EndObject();
+ EXPECT_EQ(
+ "{\"double_nan\":\"NaN\","
+ "\"float_nan\":\"NaN\","
+ "\"double_pos\":\"Infinity\","
+ "\"float_pos\":\"Infinity\","
+ "\"double_neg\":\"-Infinity\","
+ "\"float_neg\":\"-Infinity\"}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, TestRegularByteEncoding) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->StartObject("")
+ ->RenderBytes("bytes", "\x03\xef\xc0")
+ ->EndObject();
+
+ // Test that we get regular (non websafe) base64 encoding on byte fields by
+ // default.
+ EXPECT_EQ("{\"bytes\":\"A+/A\"}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+TEST_F(JsonObjectWriterTest, TestWebsafeByteEncoding) {
+ ow_ = new JsonObjectWriter("", out_stream_);
+ ow_->set_use_websafe_base64_for_bytes(true);
+ ow_->StartObject("")
+ ->RenderBytes("bytes", "\x03\xef\xc0")
+ ->EndObject();
+
+ // Test that we get websafe base64 encoding when explicitly asked.
+ EXPECT_EQ("{\"bytes\":\"A-_A\"}",
+ output_.substr(0, out_stream_->ByteCount()));
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.cc
new file mode 100644
index 0000000000..39be7b0390
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.cc
@@ -0,0 +1,820 @@
+// 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.
+
+#include <google/protobuf/util/internal/json_stream_parser.h>
+
+#include <algorithm>
+#include <cctype>
+#include <cerrno>
+#include <cstdlib>
+#include <cstring>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/util/internal/object_writer.h>
+#include <google/protobuf/util/internal/json_escaping.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+// Allow these symbols to be referenced as util::Status, util::error::* in
+// this file.
+using util::Status;
+namespace error {
+using util::error::INTERNAL;
+using util::error::INVALID_ARGUMENT;
+} // namespace error
+
+namespace converter {
+
+// Number of digits in an escaped UTF-16 code unit ('\\' 'u' X X X X)
+static const int kUnicodeEscapedLength = 6;
+
+// Length of the true, false, and null literals.
+static const int true_len = strlen("true");
+static const int false_len = strlen("false");
+static const int null_len = strlen("null");
+
+inline bool IsLetter(char c) {
+ return ('a' <= c && c <= 'z') || ('A' <= c && c <= 'Z') || (c == '_') ||
+ (c == '$');
+}
+
+inline bool IsAlphanumeric(char c) {
+ return IsLetter(c) || ('0' <= c && c <= '9');
+}
+
+static bool ConsumeKey(StringPiece* input, StringPiece* key) {
+ if (input->empty() || !IsLetter((*input)[0])) return false;
+ int len = 1;
+ for (; len < input->size(); ++len) {
+ if (!IsAlphanumeric((*input)[len])) {
+ break;
+ }
+ }
+ *key = StringPiece(input->data(), len);
+ *input = StringPiece(input->data() + len, input->size() - len);
+ return true;
+}
+
+static bool MatchKey(StringPiece input) {
+ return !input.empty() && IsLetter(input[0]);
+}
+
+JsonStreamParser::JsonStreamParser(ObjectWriter* ow)
+ : ow_(ow),
+ stack_(),
+ leftover_(),
+ json_(),
+ p_(),
+ key_(),
+ key_storage_(),
+ finishing_(false),
+ parsed_(),
+ parsed_storage_(),
+ string_open_(0),
+ chunk_storage_(),
+ coerce_to_utf8_(false) {
+ // Initialize the stack with a single value to be parsed.
+ stack_.push(VALUE);
+}
+
+JsonStreamParser::~JsonStreamParser() {}
+
+
+util::Status JsonStreamParser::Parse(StringPiece json) {
+ StringPiece chunk = json;
+ // If we have leftovers from a previous chunk, append the new chunk to it
+ // and create a new StringPiece pointing at the string's data. This could
+ // be large but we rely on the chunks to be small, assuming they are
+ // fragments of a Cord.
+ if (!leftover_.empty()) {
+ // Don't point chunk to leftover_ because leftover_ will be updated in
+ // ParseChunk(chunk).
+ chunk_storage_.swap(leftover_);
+ json.AppendToString(&chunk_storage_);
+ chunk = StringPiece(chunk_storage_);
+ }
+
+ // Find the structurally valid UTF8 prefix and parse only that.
+ int n = internal::UTF8SpnStructurallyValid(chunk);
+ if (n > 0) {
+ util::Status status = ParseChunk(chunk.substr(0, n));
+
+ // Any leftover characters are stashed in leftover_ for later parsing when
+ // there is more data available.
+ chunk.substr(n).AppendToString(&leftover_);
+ return status;
+ } else {
+ chunk.CopyToString(&leftover_);
+ return util::Status::OK;
+ }
+}
+
+util::Status JsonStreamParser::FinishParse() {
+ // If we do not expect anything and there is nothing left to parse we're all
+ // done.
+ if (stack_.empty() && leftover_.empty()) {
+ return util::Status::OK;
+ }
+
+ // Storage for UTF8-coerced string.
+ google::protobuf::scoped_array<char> utf8;
+ if (coerce_to_utf8_) {
+ utf8.reset(new char[leftover_.size()]);
+ char* coerced = internal::UTF8CoerceToStructurallyValid(leftover_, utf8.get(), ' ');
+ p_ = json_ = StringPiece(coerced, leftover_.size());
+ } else {
+ p_ = json_ = leftover_;
+ if (!internal::IsStructurallyValidUTF8(leftover_)) {
+ return ReportFailure("Encountered non UTF-8 code points.");
+ }
+ }
+
+ // Parse the remainder in finishing mode, which reports errors for things like
+ // unterminated strings or unknown tokens that would normally be retried.
+ finishing_ = true;
+ util::Status result = RunParser();
+ if (result.ok()) {
+ SkipWhitespace();
+ if (!p_.empty()) {
+ result = ReportFailure("Parsing terminated before end of input.");
+ }
+ }
+ return result;
+}
+
+util::Status JsonStreamParser::ParseChunk(StringPiece chunk) {
+ // Do not do any work if the chunk is empty.
+ if (chunk.empty()) return util::Status::OK;
+
+ p_ = json_ = chunk;
+
+ finishing_ = false;
+ util::Status result = RunParser();
+ if (!result.ok()) return result;
+
+ SkipWhitespace();
+ if (p_.empty()) {
+ // If we parsed everything we had, clear the leftover.
+ leftover_.clear();
+ } else {
+ // If we do not expect anything i.e. stack is empty, and we have non-empty
+ // string left to parse, we report an error.
+ if (stack_.empty()) {
+ return ReportFailure("Parsing terminated before end of input.");
+ }
+ // If we expect future data i.e. stack is non-empty, and we have some
+ // unparsed data left, we save it for later parse.
+ leftover_ = p_.ToString();
+ }
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::RunParser() {
+ while (!stack_.empty()) {
+ ParseType type = stack_.top();
+ TokenType t = (string_open_ == 0) ? GetNextTokenType() : BEGIN_STRING;
+ stack_.pop();
+ util::Status result;
+ switch (type) {
+ case VALUE:
+ result = ParseValue(t);
+ break;
+
+ case OBJ_MID:
+ result = ParseObjectMid(t);
+ break;
+
+ case ENTRY:
+ result = ParseEntry(t);
+ break;
+
+ case ENTRY_MID:
+ result = ParseEntryMid(t);
+ break;
+
+ case ARRAY_VALUE:
+ result = ParseArrayValue(t);
+ break;
+
+ case ARRAY_MID:
+ result = ParseArrayMid(t);
+ break;
+
+ default:
+ result = util::Status(util::error::INTERNAL,
+ StrCat("Unknown parse type: ", type));
+ break;
+ }
+ if (!result.ok()) {
+ // If we were cancelled, save our state and try again later.
+ if (!finishing_ && result == util::Status::CANCELLED) {
+ stack_.push(type);
+ // If we have a key we still need to render, make sure to save off the
+ // contents in our own storage.
+ if (!key_.empty() && key_storage_.empty()) {
+ key_.AppendToString(&key_storage_);
+ key_ = StringPiece(key_storage_);
+ }
+ result = util::Status::OK;
+ }
+ return result;
+ }
+ }
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::ParseValue(TokenType type) {
+ switch (type) {
+ case BEGIN_OBJECT:
+ return HandleBeginObject();
+ case BEGIN_ARRAY:
+ return HandleBeginArray();
+ case BEGIN_STRING:
+ return ParseString();
+ case BEGIN_NUMBER:
+ return ParseNumber();
+ case BEGIN_TRUE:
+ return ParseTrue();
+ case BEGIN_FALSE:
+ return ParseFalse();
+ case BEGIN_NULL:
+ return ParseNull();
+ case UNKNOWN:
+ return ReportUnknown("Expected a value.");
+ default: {
+ // Special case for having been cut off while parsing, wait for more data.
+ // This handles things like 'fals' being at the end of the string, we
+ // don't know if the next char would be e, completing it, or something
+ // else, making it invalid.
+ if (!finishing_ && p_.length() < false_len) {
+ return util::Status::CANCELLED;
+ }
+ return ReportFailure("Unexpected token.");
+ }
+ }
+}
+
+util::Status JsonStreamParser::ParseString() {
+ util::Status result = ParseStringHelper();
+ if (result.ok()) {
+ ow_->RenderString(key_, parsed_);
+ key_.clear();
+ parsed_.clear();
+ parsed_storage_.clear();
+ }
+ return result;
+}
+
+util::Status JsonStreamParser::ParseStringHelper() {
+ // If we haven't seen the start quote, grab it and remember it for later.
+ if (string_open_ == 0) {
+ string_open_ = *p_.data();
+ GOOGLE_DCHECK(string_open_ == '\"' || string_open_ == '\'');
+ Advance();
+ }
+ // Track where we last copied data from so we can minimize copying.
+ const char* last = p_.data();
+ while (!p_.empty()) {
+ const char* data = p_.data();
+ if (*data == '\\') {
+ // We're about to handle an escape, copy all bytes from last to data.
+ if (last < data) {
+ parsed_storage_.append(last, data - last);
+ last = data;
+ }
+ // If we ran out of string after the \, cancel or report an error
+ // depending on if we expect more data later.
+ if (p_.length() == 1) {
+ if (!finishing_) {
+ return util::Status::CANCELLED;
+ }
+ return ReportFailure("Closing quote expected in string.");
+ }
+ // Parse a unicode escape if we found \u in the string.
+ if (data[1] == 'u') {
+ util::Status result = ParseUnicodeEscape();
+ if (!result.ok()) {
+ return result;
+ }
+ // Move last pointer past the unicode escape and continue.
+ last = p_.data();
+ continue;
+ }
+ // Handle the standard set of backslash-escaped characters.
+ switch (data[1]) {
+ case 'b':
+ parsed_storage_.push_back('\b');
+ break;
+ case 'f':
+ parsed_storage_.push_back('\f');
+ break;
+ case 'n':
+ parsed_storage_.push_back('\n');
+ break;
+ case 'r':
+ parsed_storage_.push_back('\r');
+ break;
+ case 't':
+ parsed_storage_.push_back('\t');
+ break;
+ case 'v':
+ parsed_storage_.push_back('\v');
+ break;
+ default:
+ parsed_storage_.push_back(data[1]);
+ }
+ // We handled two characters, so advance past them and continue.
+ p_.remove_prefix(2);
+ last = p_.data();
+ continue;
+ }
+ // If we found the closing quote note it, advance past it, and return.
+ if (*data == string_open_) {
+ // If we didn't copy anything, reuse the input buffer.
+ if (parsed_storage_.empty()) {
+ parsed_ = StringPiece(last, data - last);
+ } else {
+ if (last < data) {
+ parsed_storage_.append(last, data - last);
+ last = data;
+ }
+ parsed_ = StringPiece(parsed_storage_);
+ }
+ // Clear the quote char so next time we try to parse a string we'll
+ // start fresh.
+ string_open_ = 0;
+ Advance();
+ return util::Status::OK;
+ }
+ // Normal character, just advance past it.
+ Advance();
+ }
+ // If we ran out of characters, copy over what we have so far.
+ if (last < p_.data()) {
+ parsed_storage_.append(last, p_.data() - last);
+ }
+ // If we didn't find the closing quote but we expect more data, cancel for now
+ if (!finishing_) {
+ return util::Status::CANCELLED;
+ }
+ // End of string reached without a closing quote, report an error.
+ string_open_ = 0;
+ return ReportFailure("Closing quote expected in string.");
+}
+
+// Converts a unicode escaped character to a decimal value stored in a char32
+// for use in UTF8 encoding utility. We assume that str begins with \uhhhh and
+// convert that from the hex number to a decimal value.
+//
+// There are some security exploits with UTF-8 that we should be careful of:
+// - http://www.unicode.org/reports/tr36/#UTF-8_Exploit
+// - http://sites/intl-eng/design-guide/core-application
+util::Status JsonStreamParser::ParseUnicodeEscape() {
+ if (p_.length() < kUnicodeEscapedLength) {
+ if (!finishing_) {
+ return util::Status::CANCELLED;
+ }
+ return ReportFailure("Illegal hex string.");
+ }
+ GOOGLE_DCHECK_EQ('\\', p_.data()[0]);
+ GOOGLE_DCHECK_EQ('u', p_.data()[1]);
+ uint32 code = 0;
+ for (int i = 2; i < kUnicodeEscapedLength; ++i) {
+ if (!isxdigit(p_.data()[i])) {
+ return ReportFailure("Invalid escape sequence.");
+ }
+ code = (code << 4) + hex_digit_to_int(p_.data()[i]);
+ }
+ if (code >= JsonEscaping::kMinHighSurrogate &&
+ code <= JsonEscaping::kMaxHighSurrogate) {
+ if (p_.length() < 2 * kUnicodeEscapedLength) {
+ if (!finishing_) {
+ return util::Status::CANCELLED;
+ }
+ if (!coerce_to_utf8_) {
+ return ReportFailure("Missing low surrogate.");
+ }
+ } else if (p_.data()[kUnicodeEscapedLength] == '\\' &&
+ p_.data()[kUnicodeEscapedLength + 1] == 'u') {
+ uint32 low_code = 0;
+ for (int i = kUnicodeEscapedLength + 2; i < 2 * kUnicodeEscapedLength;
+ ++i) {
+ if (!isxdigit(p_.data()[i])) {
+ return ReportFailure("Invalid escape sequence.");
+ }
+ low_code = (low_code << 4) + hex_digit_to_int(p_.data()[i]);
+ }
+ if (low_code >= JsonEscaping::kMinLowSurrogate &&
+ low_code <= JsonEscaping::kMaxLowSurrogate) {
+ // Convert UTF-16 surrogate pair to 21-bit Unicode codepoint.
+ code = (((code & 0x3FF) << 10) | (low_code & 0x3FF)) +
+ JsonEscaping::kMinSupplementaryCodePoint;
+ // Advance past the first code unit escape.
+ p_.remove_prefix(kUnicodeEscapedLength);
+ } else if (!coerce_to_utf8_) {
+ return ReportFailure("Invalid low surrogate.");
+ }
+ } else if (!coerce_to_utf8_) {
+ return ReportFailure("Missing low surrogate.");
+ }
+ }
+ if (!coerce_to_utf8_ && !IsValidCodePoint(code)) {
+ return ReportFailure("Invalid unicode code point.");
+ }
+ char buf[UTFmax];
+ int len = EncodeAsUTF8Char(code, buf);
+ // Advance past the [final] code unit escape.
+ p_.remove_prefix(kUnicodeEscapedLength);
+ parsed_storage_.append(buf, len);
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::ParseNumber() {
+ NumberResult number;
+ util::Status result = ParseNumberHelper(&number);
+ if (result.ok()) {
+ switch (number.type) {
+ case NumberResult::DOUBLE:
+ ow_->RenderDouble(key_, number.double_val);
+ key_.clear();
+ break;
+
+ case NumberResult::INT:
+ ow_->RenderInt64(key_, number.int_val);
+ key_.clear();
+ break;
+
+ case NumberResult::UINT:
+ ow_->RenderUint64(key_, number.uint_val);
+ key_.clear();
+ break;
+
+ default:
+ return ReportFailure("Unable to parse number.");
+ }
+ }
+ return result;
+}
+
+util::Status JsonStreamParser::ParseNumberHelper(NumberResult* result) {
+ const char* data = p_.data();
+ int length = p_.length();
+
+ // Look for the first non-numeric character, or the end of the string.
+ int index = 0;
+ bool floating = false;
+ bool negative = data[index] == '-';
+ // Find the first character that cannot be part of the number. Along the way
+ // detect if the number needs to be parsed as a double.
+ // Note that this restricts numbers to the JSON specification, so for example
+ // we do not support hex or octal notations.
+ for (; index < length; ++index) {
+ char c = data[index];
+ if (isdigit(c)) continue;
+ if (c == '.' || c == 'e' || c == 'E') {
+ floating = true;
+ continue;
+ }
+ if (c == '+' || c == '-' || c == 'x') continue;
+ // Not a valid number character, break out.
+ break;
+ }
+
+ // If the entire input is a valid number, and we may have more content in the
+ // future, we abort for now and resume when we know more.
+ if (index == length && !finishing_) {
+ return util::Status::CANCELLED;
+ }
+
+ // Create a string containing just the number, so we can use safe_strtoX
+ string number = p_.substr(0, index).ToString();
+
+ // Floating point number, parse as a double.
+ if (floating) {
+ if (!safe_strtod(number, &result->double_val)) {
+ return ReportFailure("Unable to parse number.");
+ }
+ result->type = NumberResult::DOUBLE;
+ p_.remove_prefix(index);
+ return util::Status::OK;
+ }
+
+ // Positive non-floating point number, parse as a uint64.
+ if (!negative) {
+ // Octal/Hex numbers are not valid JSON values.
+ if (number.length() >= 2 && number[0] == '0') {
+ return ReportFailure("Octal/hex numbers are not valid JSON values.");
+ }
+ if (!safe_strtou64(number, &result->uint_val)) {
+ return ReportFailure("Unable to parse number.");
+ }
+ result->type = NumberResult::UINT;
+ p_.remove_prefix(index);
+ return util::Status::OK;
+ }
+
+ // Octal/Hex numbers are not valid JSON values.
+ if (number.length() >= 3 && number[1] == '0') {
+ return ReportFailure("Octal/hex numbers are not valid JSON values.");
+ }
+ // Negative non-floating point number, parse as an int64.
+ if (!safe_strto64(number, &result->int_val)) {
+ return ReportFailure("Unable to parse number.");
+ }
+ result->type = NumberResult::INT;
+ p_.remove_prefix(index);
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::HandleBeginObject() {
+ GOOGLE_DCHECK_EQ('{', *p_.data());
+ Advance();
+ ow_->StartObject(key_);
+ key_.clear();
+ stack_.push(ENTRY);
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::ParseObjectMid(TokenType type) {
+ if (type == UNKNOWN) {
+ return ReportUnknown("Expected , or } after key:value pair.");
+ }
+
+ // Object is complete, advance past the comma and render the EndObject.
+ if (type == END_OBJECT) {
+ Advance();
+ ow_->EndObject();
+ return util::Status::OK;
+ }
+ // Found a comma, advance past it and get ready for an entry.
+ if (type == VALUE_SEPARATOR) {
+ Advance();
+ stack_.push(ENTRY);
+ return util::Status::OK;
+ }
+ // Illegal token after key:value pair.
+ return ReportFailure("Expected , or } after key:value pair.");
+}
+
+util::Status JsonStreamParser::ParseEntry(TokenType type) {
+ if (type == UNKNOWN) {
+ return ReportUnknown("Expected an object key or }.");
+ }
+
+ // Close the object and return. This allows for trailing commas.
+ if (type == END_OBJECT) {
+ ow_->EndObject();
+ Advance();
+ return util::Status::OK;
+ }
+
+ util::Status result;
+ if (type == BEGIN_STRING) {
+ // Key is a string (standard JSON), parse it and store the string.
+ result = ParseStringHelper();
+ if (result.ok()) {
+ key_storage_.clear();
+ if (!parsed_storage_.empty()) {
+ parsed_storage_.swap(key_storage_);
+ key_ = StringPiece(key_storage_);
+ } else {
+ key_ = parsed_;
+ }
+ parsed_.clear();
+ }
+ } else if (type == BEGIN_KEY) {
+ // Key is a bare key (back compat), create a StringPiece pointing to it.
+ result = ParseKey();
+ } else {
+ // Unknown key type, report an error.
+ result = ReportFailure("Expected an object key or }.");
+ }
+ // On success we next expect an entry mid ':' then an object mid ',' or '}'
+ if (result.ok()) {
+ stack_.push(OBJ_MID);
+ stack_.push(ENTRY_MID);
+ }
+ return result;
+}
+
+util::Status JsonStreamParser::ParseEntryMid(TokenType type) {
+ if (type == UNKNOWN) {
+ return ReportUnknown("Expected : between key:value pair.");
+ }
+ if (type == ENTRY_SEPARATOR) {
+ Advance();
+ stack_.push(VALUE);
+ return util::Status::OK;
+ }
+ return ReportFailure("Expected : between key:value pair.");
+}
+
+util::Status JsonStreamParser::HandleBeginArray() {
+ GOOGLE_DCHECK_EQ('[', *p_.data());
+ Advance();
+ ow_->StartList(key_);
+ key_.clear();
+ stack_.push(ARRAY_VALUE);
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::ParseArrayValue(TokenType type) {
+ if (type == UNKNOWN) {
+ return ReportUnknown("Expected a value or ] within an array.");
+ }
+
+ if (type == END_ARRAY) {
+ ow_->EndList();
+ Advance();
+ return util::Status::OK;
+ }
+
+ // The ParseValue call may push something onto the stack so we need to make
+ // sure an ARRAY_MID is after it, so we push it on now.
+ stack_.push(ARRAY_MID);
+ util::Status result = ParseValue(type);
+ if (result == util::Status::CANCELLED) {
+ // If we were cancelled, pop back off the ARRAY_MID so we don't try to
+ // push it on again when we try over.
+ stack_.pop();
+ }
+ return result;
+}
+
+util::Status JsonStreamParser::ParseArrayMid(TokenType type) {
+ if (type == UNKNOWN) {
+ return ReportUnknown("Expected , or ] after array value.");
+ }
+
+ if (type == END_ARRAY) {
+ ow_->EndList();
+ Advance();
+ return util::Status::OK;
+ }
+
+ // Found a comma, advance past it and expect an array value next.
+ if (type == VALUE_SEPARATOR) {
+ Advance();
+ stack_.push(ARRAY_VALUE);
+ return util::Status::OK;
+ }
+ // Illegal token after array value.
+ return ReportFailure("Expected , or ] after array value.");
+}
+
+util::Status JsonStreamParser::ParseTrue() {
+ ow_->RenderBool(key_, true);
+ key_.clear();
+ p_.remove_prefix(true_len);
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::ParseFalse() {
+ ow_->RenderBool(key_, false);
+ key_.clear();
+ p_.remove_prefix(false_len);
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::ParseNull() {
+ ow_->RenderNull(key_);
+ key_.clear();
+ p_.remove_prefix(null_len);
+ return util::Status::OK;
+}
+
+util::Status JsonStreamParser::ReportFailure(StringPiece message) {
+ static const int kContextLength = 20;
+ const char* p_start = p_.data();
+ const char* json_start = json_.data();
+ const char* begin = std::max(p_start - kContextLength, json_start);
+ const char* end =
+ std::min(p_start + kContextLength, json_start + json_.size());
+ StringPiece segment(begin, end - begin);
+ string location(p_start - begin, ' ');
+ location.push_back('^');
+ return util::Status(util::error::INVALID_ARGUMENT,
+ StrCat(message, "\n", segment, "\n", location));
+}
+
+util::Status JsonStreamParser::ReportUnknown(StringPiece message) {
+ // If we aren't finishing the parse, cancel parsing and try later.
+ if (!finishing_) {
+ return util::Status::CANCELLED;
+ }
+ if (p_.empty()) {
+ return ReportFailure(StrCat("Unexpected end of string. ", message));
+ }
+ return ReportFailure(message);
+}
+
+void JsonStreamParser::SkipWhitespace() {
+ while (!p_.empty() && ascii_isspace(*p_.data())) {
+ Advance();
+ }
+}
+
+void JsonStreamParser::Advance() {
+ // Advance by moving one UTF8 character while making sure we don't go beyond
+ // the length of StringPiece.
+ p_.remove_prefix(std::min<int>(
+ p_.length(), UTF8FirstLetterNumBytes(p_.data(), p_.length())));
+}
+
+util::Status JsonStreamParser::ParseKey() {
+ StringPiece original = p_;
+ if (!ConsumeKey(&p_, &key_)) {
+ return ReportFailure("Invalid key or variable name.");
+ }
+ // If we consumed everything but expect more data, reset p_ and cancel since
+ // we can't know if the key was complete or not.
+ if (!finishing_ && p_.empty()) {
+ p_ = original;
+ return util::Status::CANCELLED;
+ }
+ // Since we aren't using the key storage, clear it out.
+ key_storage_.clear();
+ return util::Status::OK;
+}
+
+JsonStreamParser::TokenType JsonStreamParser::GetNextTokenType() {
+ SkipWhitespace();
+
+ int size = p_.size();
+ if (size == 0) {
+ // If we ran out of data, report unknown and we'll place the previous parse
+ // type onto the stack and try again when we have more data.
+ return UNKNOWN;
+ }
+ // TODO(sven): Split this method based on context since different contexts
+ // support different tokens. Would slightly speed up processing?
+ const char* data = p_.data();
+ if (*data == '\"' || *data == '\'') return BEGIN_STRING;
+ if (*data == '-' || ('0' <= *data && *data <= '9')) {
+ return BEGIN_NUMBER;
+ }
+ if (size >= true_len && !strncmp(data, "true", true_len)) {
+ return BEGIN_TRUE;
+ }
+ if (size >= false_len && !strncmp(data, "false", false_len)) {
+ return BEGIN_FALSE;
+ }
+ if (size >= null_len && !strncmp(data, "null", null_len)) {
+ return BEGIN_NULL;
+ }
+ if (*data == '{') return BEGIN_OBJECT;
+ if (*data == '}') return END_OBJECT;
+ if (*data == '[') return BEGIN_ARRAY;
+ if (*data == ']') return END_ARRAY;
+ if (*data == ':') return ENTRY_SEPARATOR;
+ if (*data == ',') return VALUE_SEPARATOR;
+ if (MatchKey(p_)) {
+ return BEGIN_KEY;
+ }
+
+ // We don't know that we necessarily have an invalid token here, just that we
+ // can't parse what we have so far. So we don't report an error and just
+ // return UNKNOWN so we can try again later when we have more data, or if we
+ // finish and we have leftovers.
+ return UNKNOWN;
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.h
new file mode 100644
index 0000000000..0278c28fbc
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser.h
@@ -0,0 +1,258 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_JSON_STREAM_PARSER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_JSON_STREAM_PARSER_H__
+
+#include <stack>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/status.h>
+
+namespace google {
+namespace util {
+class Status;
+} // namespace util
+
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class ObjectWriter;
+
+// A JSON parser that can parse a stream of JSON chunks rather than needing the
+// entire JSON string up front. It is a modified version of the parser in
+// //net/proto/json/json-parser.h that has been changed in the following ways:
+// - Changed from recursion to an explicit stack to allow resumption
+// - Added support for int64 and uint64 numbers
+// - Removed support for octal and decimal escapes
+// - Removed support for numeric keys
+// - Removed support for functions (javascript)
+// - Removed some lax-comma support (but kept trailing comma support)
+// - Writes directly to an ObjectWriter rather than using subclassing
+//
+// Here is an example usage:
+// JsonStreamParser parser(ow_.get());
+// util::Status result = parser.Parse(chunk1);
+// result.Update(parser.Parse(chunk2));
+// result.Update(parser.FinishParse());
+// GOOGLE_DCHECK(result.ok()) << "Failed to parse JSON";
+//
+// This parser is thread-compatible as long as only one thread is calling a
+// Parse() method at a time.
+class LIBPROTOBUF_EXPORT JsonStreamParser {
+ public:
+ // Creates a JsonStreamParser that will write to the given ObjectWriter.
+ explicit JsonStreamParser(ObjectWriter* ow);
+ virtual ~JsonStreamParser();
+
+ // Parses a UTF-8 encoded JSON string from a StringPiece.
+ util::Status Parse(StringPiece json);
+
+
+ // Finish parsing the JSON string.
+ util::Status FinishParse();
+
+
+ private:
+ enum TokenType {
+ BEGIN_STRING, // " or '
+ BEGIN_NUMBER, // - or digit
+ BEGIN_TRUE, // true
+ BEGIN_FALSE, // false
+ BEGIN_NULL, // null
+ BEGIN_OBJECT, // {
+ END_OBJECT, // }
+ BEGIN_ARRAY, // [
+ END_ARRAY, // ]
+ ENTRY_SEPARATOR, // :
+ VALUE_SEPARATOR, // ,
+ BEGIN_KEY, // letter, _, $ or digit. Must begin with non-digit
+ UNKNOWN // Unknown token or we ran out of the stream.
+ };
+
+ enum ParseType {
+ VALUE, // Expects a {, [, true, false, null, string or number
+ OBJ_MID, // Expects a ',' or }
+ ENTRY, // Expects a key or }
+ ENTRY_MID, // Expects a :
+ ARRAY_VALUE, // Expects a value or ]
+ ARRAY_MID // Expects a ',' or ]
+ };
+
+ // Holds the result of parsing a number
+ struct NumberResult {
+ enum Type { DOUBLE, INT, UINT };
+ Type type;
+ union {
+ double double_val;
+ int64 int_val;
+ uint64 uint_val;
+ };
+ };
+
+ // Parses a single chunk of JSON, returning an error if the JSON was invalid.
+ util::Status ParseChunk(StringPiece json);
+
+ // Runs the parser based on stack_ and p_, until the stack is empty or p_ runs
+ // out of data. If we unexpectedly run out of p_ we push the latest back onto
+ // the stack and return.
+ util::Status RunParser();
+
+ // Parses a value from p_ and writes it to ow_.
+ // A value may be an object, array, true, false, null, string or number.
+ util::Status ParseValue(TokenType type);
+
+ // Parses a string and writes it out to the ow_.
+ util::Status ParseString();
+
+ // Parses a string, storing the result in parsed_.
+ util::Status ParseStringHelper();
+
+ // This function parses unicode escape sequences in strings. It returns an
+ // error when there's a parsing error, either the size is not the expected
+ // size or a character is not a hex digit. When it returns str will contain
+ // what has been successfully parsed so far.
+ util::Status ParseUnicodeEscape();
+
+ // Expects p_ to point to a JSON number, writes the number to the writer using
+ // the appropriate Render method based on the type of number.
+ util::Status ParseNumber();
+
+ // Parse a number into a NumberResult, reporting an error if no number could
+ // be parsed. This method will try to parse into a uint64, int64, or double
+ // based on whether the number was positive or negative or had a decimal
+ // component.
+ util::Status ParseNumberHelper(NumberResult* result);
+
+ // Handles a { during parsing of a value.
+ util::Status HandleBeginObject();
+
+ // Parses from the ENTRY state.
+ util::Status ParseEntry(TokenType type);
+
+ // Parses from the ENTRY_MID state.
+ util::Status ParseEntryMid(TokenType type);
+
+ // Parses from the OBJ_MID state.
+ util::Status ParseObjectMid(TokenType type);
+
+ // Handles a [ during parsing of a value.
+ util::Status HandleBeginArray();
+
+ // Parses from the ARRAY_VALUE state.
+ util::Status ParseArrayValue(TokenType type);
+
+ // Parses from the ARRAY_MID state.
+ util::Status ParseArrayMid(TokenType type);
+
+ // Expects p_ to point to an unquoted literal
+ util::Status ParseTrue();
+ util::Status ParseFalse();
+ util::Status ParseNull();
+
+ // Report a failure as a util::Status.
+ util::Status ReportFailure(StringPiece message);
+
+ // Report a failure due to an UNKNOWN token type. We check if we hit the
+ // end of the stream and if we're finishing or not to detect what type of
+ // status to return in this case.
+ util::Status ReportUnknown(StringPiece message);
+
+ // Advance p_ past all whitespace or until the end of the string.
+ void SkipWhitespace();
+
+ // Advance p_ one UTF-8 character
+ void Advance();
+
+ // Expects p_ to point to the beginning of a key.
+ util::Status ParseKey();
+
+ // Return the type of the next token at p_.
+ TokenType GetNextTokenType();
+
+ // The object writer to write parse events to.
+ ObjectWriter* ow_;
+
+ // The stack of parsing we still need to do. When the stack runs empty we will
+ // have parsed a single value from the root (e.g. an object or list).
+ std::stack<ParseType> stack_;
+
+ // Contains any leftover text from a previous chunk that we weren't able to
+ // fully parse, for example the start of a key or number.
+ string leftover_;
+
+ // The current chunk of JSON being parsed. Primarily used for providing
+ // context during error reporting.
+ StringPiece json_;
+
+ // A pointer within the current JSON being parsed, used to track location.
+ StringPiece p_;
+
+ // Stores the last key read, as we separate parsing of keys and values.
+ StringPiece key_;
+
+ // Storage for key_ if we need to keep ownership, for example between chunks
+ // or if the key was unescaped from a JSON string.
+ string key_storage_;
+
+ // True during the FinishParse() call, so we know that any errors are fatal.
+ // For example an unterminated string will normally result in cancelling and
+ // trying during the next chunk, but during FinishParse() it is an error.
+ bool finishing_;
+
+ // String we parsed during a call to ParseStringHelper().
+ StringPiece parsed_;
+
+ // Storage for the string we parsed. This may be empty if the string was able
+ // to be parsed directly from the input.
+ string parsed_storage_;
+
+ // The character that opened the string, either ' or ".
+ // A value of 0 indicates that string parsing is not in process.
+ char string_open_;
+
+ // Storage for the chunk that are being parsed in ParseChunk().
+ string chunk_storage_;
+
+ // Whether to allow non UTF-8 encoded input and replace invalid code points.
+ bool coerce_to_utf8_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(JsonStreamParser);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_JSON_STREAM_PARSER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser_test.cc
new file mode 100644
index 0000000000..059ea6d86a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/json_stream_parser_test.cc
@@ -0,0 +1,819 @@
+// 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.
+
+#include <google/protobuf/util/internal/json_stream_parser.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/time.h>
+#include <google/protobuf/util/internal/expecting_objectwriter.h>
+#include <google/protobuf/util/internal/object_writer.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/status.h>
+
+
+namespace google {
+namespace protobuf {
+namespace util {
+using util::Status;
+namespace error {
+using util::error::INVALID_ARGUMENT;
+} // namespace error
+namespace converter {
+
+using util::Status;
+
+// Tests for the JSON Stream Parser. These tests are intended to be
+// comprehensive and cover the following:
+//
+// Positive tests:
+// - true, false, null
+// - empty object or array.
+// - negative and positive double and int, unsigned int
+// - single and double quoted strings
+// - string key, unquoted key, numeric key
+// - array containing array, object, value
+// - object containing array, object, value
+// - unicode handling in strings
+// - ascii escaping (\b, \f, \n, \r, \t, \v)
+// - trailing commas
+//
+// Negative tests:
+// - illegal literals
+// - mismatched quotes failure on strings
+// - unterminated string failure
+// - unexpected end of string failure
+// - mismatched object and array closing
+// - Failure to close array or object
+// - numbers too large
+// - invalid unicode escapes.
+// - invalid unicode sequences.
+// - numbers as keys
+//
+// For each test we split the input string on every possible character to ensure
+// the parser is able to handle arbitrarily split input for all cases. We also
+// do a final test of the entire test case one character at a time.
+class JsonStreamParserTest : public ::testing::Test {
+ protected:
+ JsonStreamParserTest() : mock_(), ow_(&mock_) {}
+ virtual ~JsonStreamParserTest() {}
+
+ util::Status RunTest(StringPiece json, int split, bool coerce_utf8 = false) {
+ JsonStreamParser parser(&mock_);
+
+ // Special case for split == length, test parsing one character at a time.
+ if (split == json.length()) {
+ GOOGLE_LOG(INFO) << "Testing split every char: " << json;
+ for (int i = 0; i < json.length(); ++i) {
+ StringPiece single = json.substr(i, 1);
+ util::Status result = parser.Parse(single);
+ if (!result.ok()) {
+ return result;
+ }
+ }
+ return parser.FinishParse();
+ }
+
+ // Normal case, split at the split point and parse two substrings.
+ StringPiece first = json.substr(0, split);
+ StringPiece rest = json.substr(split);
+ GOOGLE_LOG(INFO) << "Testing split: " << first << "><" << rest;
+ util::Status result = parser.Parse(first);
+ if (result.ok()) {
+ result = parser.Parse(rest);
+ if (result.ok()) {
+ result = parser.FinishParse();
+ }
+ }
+ return result;
+ }
+
+ void DoTest(StringPiece json, int split, bool coerce_utf8 = false) {
+ util::Status result = RunTest(json, split, coerce_utf8);
+ if (!result.ok()) {
+ GOOGLE_LOG(WARNING) << result;
+ }
+ EXPECT_OK(result);
+ }
+
+ void DoErrorTest(StringPiece json, int split, StringPiece error_prefix,
+ bool coerce_utf8 = false) {
+ util::Status result = RunTest(json, split, coerce_utf8);
+ EXPECT_EQ(util::error::INVALID_ARGUMENT, result.error_code());
+ StringPiece error_message(result.error_message());
+ EXPECT_EQ(error_prefix, error_message.substr(0, error_prefix.size()));
+ }
+
+
+ MockObjectWriter mock_;
+ ExpectingObjectWriter ow_;
+};
+
+
+// Positive tests
+
+// - true, false, null
+TEST_F(JsonStreamParserTest, SimpleTrue) {
+ StringPiece str = "true";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderBool("", true);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleFalse) {
+ StringPiece str = "false";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderBool("", false);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleNull) {
+ StringPiece str = "null";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderNull("");
+ DoTest(str, i);
+ }
+}
+
+// - empty object and array.
+TEST_F(JsonStreamParserTest, EmptyObject) {
+ StringPiece str = "{}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")->EndObject();
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, EmptyList) {
+ StringPiece str = "[]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")->EndList();
+ DoTest(str, i);
+ }
+}
+
+// - negative and positive double and int, unsigned int
+TEST_F(JsonStreamParserTest, SimpleDouble) {
+ StringPiece str = "42.5";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderDouble("", 42.5);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, ScientificDouble) {
+ StringPiece str = "1.2345e-10";
+ for (int i = 0; i < str.length(); ++i) {
+ ow_.RenderDouble("", 1.2345e-10);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleNegativeDouble) {
+ StringPiece str = "-1045.235";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderDouble("", -1045.235);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleInt) {
+ StringPiece str = "123456";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderUint64("", 123456);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleNegativeInt) {
+ StringPiece str = "-79497823553162765";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderInt64("", -79497823553162765LL);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleUnsignedInt) {
+ StringPiece str = "11779497823553162765";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderUint64("", 11779497823553162765ULL);
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, OctalNumberIsInvalid) {
+ StringPiece str = "01234";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Octal/hex numbers are not valid JSON values.");
+ }
+ str = "-01234";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Octal/hex numbers are not valid JSON values.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, HexNumberIsInvalid) {
+ StringPiece str = "0x1234";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Octal/hex numbers are not valid JSON values.");
+ }
+ str = "-0x1234";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Octal/hex numbers are not valid JSON values.");
+ }
+ str = "12x34";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Unable to parse number.");
+ }
+}
+
+// - single and double quoted strings
+TEST_F(JsonStreamParserTest, EmptyDoubleQuotedString) {
+ StringPiece str = "\"\"";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderString("", "");
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, EmptySingleQuotedString) {
+ StringPiece str = "''";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderString("", "");
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleDoubleQuotedString) {
+ StringPiece str = "\"Some String\"";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderString("", "Some String");
+ DoTest(str, i);
+ }
+}
+
+TEST_F(JsonStreamParserTest, SimpleSingleQuotedString) {
+ StringPiece str = "'Another String'";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderString("", "Another String");
+ DoTest(str, i);
+ }
+}
+
+// - string key, unquoted key, numeric key
+TEST_F(JsonStreamParserTest, ObjectKeyTypes) {
+ StringPiece str =
+ "{'s': true, \"d\": false, key: null, snake_key: [], camelKey: {}}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")
+ ->RenderBool("s", true)
+ ->RenderBool("d", false)
+ ->RenderNull("key")
+ ->StartList("snake_key")
+ ->EndList()
+ ->StartObject("camelKey")
+ ->EndObject()
+ ->EndObject();
+ DoTest(str, i);
+ }
+}
+
+// - array containing array, object, values (true, false, null, num, string)
+TEST_F(JsonStreamParserTest, ArrayValues) {
+ StringPiece str =
+ "[true, false, null, 'a string', \"another string\", [22, -127, 45.3, "
+ "-1056.4, 11779497823553162765], {'key': true}]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")
+ ->RenderBool("", true)
+ ->RenderBool("", false)
+ ->RenderNull("")
+ ->RenderString("", "a string")
+ ->RenderString("", "another string")
+ ->StartList("")
+ ->RenderUint64("", 22)
+ ->RenderInt64("", -127)
+ ->RenderDouble("", 45.3)
+ ->RenderDouble("", -1056.4)
+ ->RenderUint64("", 11779497823553162765ULL)
+ ->EndList()
+ ->StartObject("")
+ ->RenderBool("key", true)
+ ->EndObject()
+ ->EndList();
+ DoTest(str, i);
+ }
+}
+
+// - object containing array, object, value (true, false, null, num, string)
+TEST_F(JsonStreamParserTest, ObjectValues) {
+ StringPiece str =
+ "{t: true, f: false, n: null, s: 'a string', d: \"another string\", pi: "
+ "22, ni: -127, pd: 45.3, nd: -1056.4, pl: 11779497823553162765, l: [[]], "
+ "o: {'key': true}}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")
+ ->RenderBool("t", true)
+ ->RenderBool("f", false)
+ ->RenderNull("n")
+ ->RenderString("s", "a string")
+ ->RenderString("d", "another string")
+ ->RenderUint64("pi", 22)
+ ->RenderInt64("ni", -127)
+ ->RenderDouble("pd", 45.3)
+ ->RenderDouble("nd", -1056.4)
+ ->RenderUint64("pl", 11779497823553162765ULL)
+ ->StartList("l")
+ ->StartList("")
+ ->EndList()
+ ->EndList()
+ ->StartObject("o")
+ ->RenderBool("key", true)
+ ->EndObject()
+ ->EndObject();
+ DoTest(str, i);
+ }
+}
+
+
+TEST_F(JsonStreamParserTest, RejectNonUtf8WhenNotCoerced) {
+ StringPiece json = "{\"address\":\xFF\"חרושת 23, רעננה, ישר×ל\"}";
+ for (int i = 0; i <= json.length(); ++i) {
+ DoErrorTest(json, i, "Encountered non UTF-8 code points.");
+ }
+ json = "{\"address\": \"חרושת 23,\xFFרעננה, ישר×ל\"}";
+ for (int i = 0; i <= json.length(); ++i) {
+ DoErrorTest(json, i, "Encountered non UTF-8 code points.");
+ }
+ DoErrorTest("\xFF{}", 0, "Encountered non UTF-8 code points.");
+}
+
+// - unicode handling in strings
+TEST_F(JsonStreamParserTest, UnicodeEscaping) {
+ StringPiece str = "[\"\\u0639\\u0631\\u0628\\u0649\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")
+ ->RenderString("", "\xD8\xB9\xD8\xB1\xD8\xA8\xD9\x89")
+ ->EndList();
+ DoTest(str, i);
+ }
+}
+
+// - unicode UTF-16 surrogate pair handling in strings
+TEST_F(JsonStreamParserTest, UnicodeSurrogatePairEscaping) {
+ StringPiece str =
+ "[\"\\u0bee\\ud800\\uddf1\\uD80C\\uDDA4\\uD83d\\udC1D\\uD83C\\uDF6F\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")
+ ->RenderString("",
+ "\xE0\xAF\xAE\xF0\x90\x87\xB1\xF0\x93\x86\xA4\xF0"
+ "\x9F\x90\x9D\xF0\x9F\x8D\xAF")
+ ->EndList();
+ DoTest(str, i);
+ }
+}
+
+
+TEST_F(JsonStreamParserTest, UnicodeEscapingInvalidCodePointWhenNotCoerced) {
+ // A low surrogate alone.
+ StringPiece str = "[\"\\ude36\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Invalid unicode code point.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, UnicodeEscapingMissingLowSurrogateWhenNotCoerced) {
+ // A high surrogate alone.
+ StringPiece str = "[\"\\ud83d\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Missing low surrogate.");
+ }
+ // A high surrogate with some trailing characters.
+ str = "[\"\\ud83d|ude36\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Missing low surrogate.");
+ }
+ // A high surrogate with half a low surrogate.
+ str = "[\"\\ud83d\\ude--\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Invalid escape sequence.");
+ }
+ // Two high surrogates.
+ str = "[\"\\ud83d\\ud83d\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Invalid low surrogate.");
+ }
+}
+
+// - ascii escaping (\b, \f, \n, \r, \t, \v)
+TEST_F(JsonStreamParserTest, AsciiEscaping) {
+ StringPiece str =
+ "[\"\\b\", \"\\ning\", \"test\\f\", \"\\r\\t\", \"test\\\\\\ving\"]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")
+ ->RenderString("", "\b")
+ ->RenderString("", "\ning")
+ ->RenderString("", "test\f")
+ ->RenderString("", "\r\t")
+ ->RenderString("", "test\\\ving")
+ ->EndList();
+ DoTest(str, i);
+ }
+}
+
+// - trailing commas, we support a single trailing comma but no internal commas.
+TEST_F(JsonStreamParserTest, TrailingCommas) {
+ StringPiece str = "[['a',true,], {b: null,},]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")
+ ->StartList("")
+ ->RenderString("", "a")
+ ->RenderBool("", true)
+ ->EndList()
+ ->StartObject("")
+ ->RenderNull("b")
+ ->EndObject()
+ ->EndList();
+ DoTest(str, i);
+ }
+}
+
+// Negative tests
+
+// illegal literals
+TEST_F(JsonStreamParserTest, ExtraTextAfterTrue) {
+ StringPiece str = "truee";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderBool("", true);
+ DoErrorTest(str, i, "Parsing terminated before end of input.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidNumberDashOnly) {
+ StringPiece str = "-";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Unable to parse number.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidNumberDashName) {
+ StringPiece str = "-foo";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Unable to parse number.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidLiteralInArray) {
+ StringPiece str = "[nule]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("");
+ DoErrorTest(str, i, "Unexpected token.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidLiteralInObject) {
+ StringPiece str = "{123false}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected an object key or }.");
+ }
+}
+
+// mismatched quotes failure on strings
+TEST_F(JsonStreamParserTest, MismatchedSingleQuotedLiteral) {
+ StringPiece str = "'Some str\"";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Closing quote expected in string.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, MismatchedDoubleQuotedLiteral) {
+ StringPiece str = "\"Another string that ends poorly!'";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Closing quote expected in string.");
+ }
+}
+
+// unterminated strings
+TEST_F(JsonStreamParserTest, UnterminatedLiteralString) {
+ StringPiece str = "\"Forgot the rest of i";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Closing quote expected in string.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, UnterminatedStringEscape) {
+ StringPiece str = "\"Forgot the rest of \\";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Closing quote expected in string.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, UnterminatedStringInArray) {
+ StringPiece str = "[\"Forgot to close the string]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("");
+ DoErrorTest(str, i, "Closing quote expected in string.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, UnterminatedStringInObject) {
+ StringPiece str = "{f: \"Forgot to close the string}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Closing quote expected in string.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, UnterminatedObject) {
+ StringPiece str = "{";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Unexpected end of string.");
+ }
+}
+
+
+// mismatched object and array closing
+TEST_F(JsonStreamParserTest, MismatchedCloseObject) {
+ StringPiece str = "{'key': true]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")->RenderBool("key", true);
+ DoErrorTest(str, i, "Expected , or } after key:value pair.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, MismatchedCloseArray) {
+ StringPiece str = "[true, null}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")->RenderBool("", true)->RenderNull("");
+ DoErrorTest(str, i, "Expected , or ] after array value.");
+ }
+}
+
+// Invalid object keys.
+TEST_F(JsonStreamParserTest, InvalidNumericObjectKey) {
+ StringPiece str = "{42: true}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected an object key or }.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidLiteralObjectInObject) {
+ StringPiece str = "{{bob: true}}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected an object key or }.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidLiteralArrayInObject) {
+ StringPiece str = "{[null]}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected an object key or }.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidLiteralValueInObject) {
+ StringPiece str = "{false}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected an object key or }.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, MissingColonAfterStringInObject) {
+ StringPiece str = "{\"key\"}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected : between key:value pair.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, MissingColonAfterKeyInObject) {
+ StringPiece str = "{key}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected : between key:value pair.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, EndOfTextAfterKeyInObject) {
+ StringPiece str = "{key";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Unexpected end of string.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, MissingValueAfterColonInObject) {
+ StringPiece str = "{key:}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Unexpected token.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, MissingCommaBetweenObjectEntries) {
+ StringPiece str = "{key:20 'hello': true}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")->RenderUint64("key", 20);
+ DoErrorTest(str, i, "Expected , or } after key:value pair.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, InvalidLiteralAsObjectKey) {
+ StringPiece str = "{false: 20}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected an object key or }.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, ExtraCharactersAfterObject) {
+ StringPiece str = "{}}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")->EndObject();
+ DoErrorTest(str, i, "Parsing terminated before end of input.");
+ }
+}
+
+// numbers too large
+TEST_F(JsonStreamParserTest, PositiveNumberTooBig) {
+ StringPiece str = "[18446744073709551616]"; // 2^64
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("");
+ DoErrorTest(str, i, "Unable to parse number.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, NegativeNumberTooBig) {
+ StringPiece str = "[-18446744073709551616]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("");
+ DoErrorTest(str, i, "Unable to parse number.");
+ }
+}
+
+/*
+TODO(sven): Fail parsing when parsing a double that is too large.
+
+TEST_F(JsonStreamParserTest, DoubleTooBig) {
+ StringPiece str = "[184464073709551232321616.45]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("");
+ DoErrorTest(str, i, "Unable to parse number");
+ }
+}
+*/
+
+// invalid bare backslash.
+TEST_F(JsonStreamParserTest, UnfinishedEscape) {
+ StringPiece str = "\"\\";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Closing quote expected in string.");
+ }
+}
+
+// invalid bare backslash u.
+TEST_F(JsonStreamParserTest, UnfinishedUnicodeEscape) {
+ StringPiece str = "\"\\u";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Illegal hex string.");
+ }
+}
+
+// invalid unicode sequence.
+TEST_F(JsonStreamParserTest, UnicodeEscapeCutOff) {
+ StringPiece str = "\"\\u12";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Illegal hex string.");
+ }
+}
+
+// invalid unicode sequence (valid in modern EcmaScript but not in JSON).
+TEST_F(JsonStreamParserTest, BracketedUnicodeEscape) {
+ StringPiece str = "\"\\u{1f36f}\"";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Invalid escape sequence.");
+ }
+}
+
+
+TEST_F(JsonStreamParserTest, UnicodeEscapeInvalidCharacters) {
+ StringPiece str = "\"\\u12$4hello";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Invalid escape sequence.");
+ }
+}
+
+// invalid unicode sequence in low half surrogate: g is not a hex digit.
+TEST_F(JsonStreamParserTest, UnicodeEscapeLowHalfSurrogateInvalidCharacters) {
+ StringPiece str = "\"\\ud800\\udcfg\"";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Invalid escape sequence.");
+ }
+}
+
+// Extra commas with an object or array.
+TEST_F(JsonStreamParserTest, ExtraCommaInObject) {
+ StringPiece str = "{'k1': true,,'k2': false}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")->RenderBool("k1", true);
+ DoErrorTest(str, i, "Expected an object key or }.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, ExtraCommaInArray) {
+ StringPiece str = "[true,,false}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")->RenderBool("", true);
+ DoErrorTest(str, i, "Unexpected token.");
+ }
+}
+
+// Extra text beyond end of value.
+TEST_F(JsonStreamParserTest, ExtraTextAfterLiteral) {
+ StringPiece str = "'hello', 'world'";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.RenderString("", "hello");
+ DoErrorTest(str, i, "Parsing terminated before end of input.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, ExtraTextAfterObject) {
+ StringPiece str = "{'key': true} 'oops'";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("")->RenderBool("key", true)->EndObject();
+ DoErrorTest(str, i, "Parsing terminated before end of input.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, ExtraTextAfterArray) {
+ StringPiece str = "[null] 'oops'";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("")->RenderNull("")->EndList();
+ DoErrorTest(str, i, "Parsing terminated before end of input.");
+ }
+}
+
+// Random unknown text in the value.
+TEST_F(JsonStreamParserTest, UnknownCharactersAsValue) {
+ StringPiece str = "*&#25";
+ for (int i = 0; i <= str.length(); ++i) {
+ DoErrorTest(str, i, "Expected a value.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, UnknownCharactersInArray) {
+ StringPiece str = "[*&#25]";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartList("");
+ DoErrorTest(str, i, "Expected a value or ] within an array.");
+ }
+}
+
+TEST_F(JsonStreamParserTest, UnknownCharactersInObject) {
+ StringPiece str = "{'key': *&#25}";
+ for (int i = 0; i <= str.length(); ++i) {
+ ow_.StartObject("");
+ DoErrorTest(str, i, "Expected a value.");
+ }
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/location_tracker.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/location_tracker.h
new file mode 100644
index 0000000000..0864b05737
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/location_tracker.h
@@ -0,0 +1,65 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_LOCATION_TRACKER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_LOCATION_TRACKER_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// LocationTrackerInterface is an interface for classes that track
+// the location information for the purpose of error reporting.
+class LIBPROTOBUF_EXPORT LocationTrackerInterface {
+ public:
+ virtual ~LocationTrackerInterface() {}
+
+ // Returns the object location as human readable string.
+ virtual string ToString() const = 0;
+
+ protected:
+ LocationTrackerInterface() {}
+
+ private:
+ // Please do not add any data members to this class.
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(LocationTrackerInterface);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_LOCATION_TRACKER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/mock_error_listener.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/mock_error_listener.h
new file mode 100644
index 0000000000..591c35dbbb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/mock_error_listener.h
@@ -0,0 +1,63 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_MOCK_ERROR_LISTENER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_MOCK_ERROR_LISTENER_H__
+
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/util/internal/error_listener.h>
+#include <google/protobuf/util/internal/location_tracker.h>
+#include <gmock/gmock.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class MockErrorListener : public ErrorListener {
+ public:
+ MockErrorListener() {}
+ virtual ~MockErrorListener() {}
+
+ MOCK_METHOD3(InvalidName, void(const LocationTrackerInterface& loc,
+ StringPiece unknown_name,
+ StringPiece message));
+ MOCK_METHOD3(InvalidValue, void(const LocationTrackerInterface& loc,
+ StringPiece type_name, StringPiece value));
+ MOCK_METHOD2(MissingField, void(const LocationTrackerInterface& loc,
+ StringPiece missing_name));
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_MOCK_ERROR_LISTENER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_location_tracker.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_location_tracker.h
new file mode 100644
index 0000000000..8586cecc91
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_location_tracker.h
@@ -0,0 +1,64 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_LOCATION_TRACKER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_LOCATION_TRACKER_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/util/internal/location_tracker.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// An empty concrete implementation of LocationTrackerInterface.
+class ObjectLocationTracker : public LocationTrackerInterface {
+ public:
+ // Creates an empty location tracker.
+ ObjectLocationTracker() {}
+
+ virtual ~ObjectLocationTracker() {}
+
+ // Returns empty because nothing is tracked.
+ virtual string ToString() const { return ""; }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ObjectLocationTracker);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_LOCATION_TRACKER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_source.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_source.h
new file mode 100644
index 0000000000..2c31cfb09e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_source.h
@@ -0,0 +1,79 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_SOURCE_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_SOURCE_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/status.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class ObjectWriter;
+
+// An ObjectSource is anything that can write to an ObjectWriter.
+// Implementation of this interface typically provide constructors or
+// factory methods to create an instance based on some source data, for
+// example, a character stream, or protobuf.
+//
+// Derived classes could be thread-unsafe.
+class LIBPROTOBUF_EXPORT ObjectSource {
+ public:
+ virtual ~ObjectSource() {}
+
+ // Writes to the ObjectWriter
+ virtual util::Status WriteTo(ObjectWriter* ow) const {
+ return NamedWriteTo("", ow);
+ }
+
+ // Writes to the ObjectWriter with a custom name for the message.
+ // This is useful when you chain ObjectSource together by embedding one
+ // within another.
+ virtual util::Status NamedWriteTo(StringPiece name,
+ ObjectWriter* ow) const = 0;
+
+ protected:
+ ObjectSource() {}
+
+ private:
+ // Do not add any data members to this class.
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ObjectSource);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_SOURCE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.cc
new file mode 100644
index 0000000000..57cc08a1d7
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.cc
@@ -0,0 +1,92 @@
+// 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.
+
+#include <google/protobuf/util/internal/object_writer.h>
+
+#include <google/protobuf/util/internal/datapiece.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// static
+void ObjectWriter::RenderDataPieceTo(const DataPiece& data, StringPiece name,
+ ObjectWriter* ow) {
+ switch (data.type()) {
+ case DataPiece::TYPE_INT32: {
+ ow->RenderInt32(name, data.ToInt32().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_INT64: {
+ ow->RenderInt64(name, data.ToInt64().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_UINT32: {
+ ow->RenderUint32(name, data.ToUint32().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_UINT64: {
+ ow->RenderUint64(name, data.ToUint64().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_DOUBLE: {
+ ow->RenderDouble(name, data.ToDouble().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_FLOAT: {
+ ow->RenderFloat(name, data.ToFloat().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_BOOL: {
+ ow->RenderBool(name, data.ToBool().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_STRING: {
+ ow->RenderString(name, data.ToString().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_BYTES: {
+ ow->RenderBytes(name, data.ToBytes().ValueOrDie());
+ break;
+ }
+ case DataPiece::TYPE_NULL: {
+ ow->RenderNull(name);
+ break;
+ }
+ default:
+ break;
+ }
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.h
new file mode 100644
index 0000000000..5781aa1e21
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/object_writer.h
@@ -0,0 +1,139 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_WRITER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_WRITER_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringpiece.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class DataPiece;
+
+// An ObjectWriter is an interface for writing a stream of events
+// representing objects and collections. Implementation of this
+// interface can be used to write an object stream to an in-memory
+// structure, protobufs, JSON, XML, or any other output format
+// desired. The ObjectSource interface is typically used as the
+// source of an object stream.
+//
+// See JsonObjectWriter for a sample implementation of ObjectWriter
+// and its use.
+//
+// Derived classes could be thread-unsafe.
+//
+// TODO(xinb): seems like a prime candidate to apply the RAII paradigm
+// and get rid the need to call EndXXX().
+class LIBPROTOBUF_EXPORT ObjectWriter {
+ public:
+ virtual ~ObjectWriter() {}
+
+ // Starts an object. If the name is empty, the object will not be named.
+ virtual ObjectWriter* StartObject(StringPiece name) = 0;
+
+ // Ends an object.
+ virtual ObjectWriter* EndObject() = 0;
+
+ // Starts a list. If the name is empty, the list will not be named.
+ virtual ObjectWriter* StartList(StringPiece name) = 0;
+
+ // Ends a list.
+ virtual ObjectWriter* EndList() = 0;
+
+ // Renders a boolean value.
+ virtual ObjectWriter* RenderBool(StringPiece name, bool value) = 0;
+
+ // Renders an 32-bit integer value.
+ virtual ObjectWriter* RenderInt32(StringPiece name, int32 value) = 0;
+
+ // Renders an 32-bit unsigned integer value.
+ virtual ObjectWriter* RenderUint32(StringPiece name, uint32 value) = 0;
+
+ // Renders a 64-bit integer value.
+ virtual ObjectWriter* RenderInt64(StringPiece name, int64 value) = 0;
+
+ // Renders an 64-bit unsigned integer value.
+ virtual ObjectWriter* RenderUint64(StringPiece name, uint64 value) = 0;
+
+ // Renders a double value.
+ virtual ObjectWriter* RenderDouble(StringPiece name, double value) = 0;
+
+ // Renders a float value.
+ virtual ObjectWriter* RenderFloat(StringPiece name, float value) = 0;
+
+ // Renders a StringPiece value. This is for rendering strings.
+ virtual ObjectWriter* RenderString(StringPiece name, StringPiece value) = 0;
+
+ // Renders a bytes value.
+ virtual ObjectWriter* RenderBytes(StringPiece name, StringPiece value) = 0;
+
+ // Renders a Null value.
+ virtual ObjectWriter* RenderNull(StringPiece name) = 0;
+
+
+ // Renders a DataPiece object to a ObjectWriter.
+ static void RenderDataPieceTo(const DataPiece& data, StringPiece name,
+ ObjectWriter* ow);
+
+ // Indicates whether this ObjectWriter has completed writing the root message,
+ // usually this means writing of one complete object. Subclasses must override
+ // this behavior appropriately.
+ virtual bool done() { return false; }
+
+ void set_use_strict_base64_decoding(bool value) {
+ use_strict_base64_decoding_ = value;
+ }
+
+ bool use_strict_base64_decoding() const {
+ return use_strict_base64_decoding_;
+ }
+
+ protected:
+ ObjectWriter() : use_strict_base64_decoding_(true) {}
+
+ private:
+ // If set to true, we use the stricter version of base64 decoding for byte
+ // fields by making sure decoded version encodes back to the original string.
+ bool use_strict_base64_decoding_;
+
+ // Do not add any data members to this class.
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ObjectWriter);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_OBJECT_WRITER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.cc
new file mode 100644
index 0000000000..0c38aeb900
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.cc
@@ -0,0 +1,796 @@
+// 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.
+
+#include <google/protobuf/util/internal/proto_writer.h>
+
+#include <functional>
+#include <stack>
+
+#include <google/protobuf/stubs/once.h>
+#include <google/protobuf/stubs/time.h>
+#include <google/protobuf/wire_format_lite.h>
+#include <google/protobuf/util/internal/field_mask_utility.h>
+#include <google/protobuf/util/internal/object_location_tracker.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/statusor.h>
+
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using google::protobuf::internal::WireFormatLite;
+using google::protobuf::io::CodedOutputStream;
+using util::error::INVALID_ARGUMENT;
+using util::Status;
+using util::StatusOr;
+
+
+ProtoWriter::ProtoWriter(TypeResolver* type_resolver,
+ const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener)
+ : master_type_(type),
+ typeinfo_(TypeInfo::NewTypeInfo(type_resolver)),
+ own_typeinfo_(true),
+ done_(false),
+ ignore_unknown_fields_(false),
+ element_(NULL),
+ size_insert_(),
+ output_(output),
+ buffer_(),
+ adapter_(&buffer_),
+ stream_(new CodedOutputStream(&adapter_)),
+ listener_(listener),
+ invalid_depth_(0),
+ tracker_(new ObjectLocationTracker()) {}
+
+ProtoWriter::ProtoWriter(const TypeInfo* typeinfo,
+ const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener)
+ : master_type_(type),
+ typeinfo_(typeinfo),
+ own_typeinfo_(false),
+ done_(false),
+ ignore_unknown_fields_(false),
+ element_(NULL),
+ size_insert_(),
+ output_(output),
+ buffer_(),
+ adapter_(&buffer_),
+ stream_(new CodedOutputStream(&adapter_)),
+ listener_(listener),
+ invalid_depth_(0),
+ tracker_(new ObjectLocationTracker()) {}
+
+ProtoWriter::~ProtoWriter() {
+ if (own_typeinfo_) {
+ delete typeinfo_;
+ }
+ if (element_ == NULL) return;
+ // Cleanup explicitly in order to avoid destructor stack overflow when input
+ // is deeply nested.
+ // Cast to BaseElement to avoid doing additional checks (like missing fields)
+ // during pop().
+ google::protobuf::scoped_ptr<BaseElement> element(
+ static_cast<BaseElement*>(element_.get())->pop<BaseElement>());
+ while (element != NULL) {
+ element.reset(element->pop<BaseElement>());
+ }
+}
+
+namespace {
+
+// Writes an INT32 field, including tag to the stream.
+inline Status WriteInt32(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<int32> i32 = data.ToInt32();
+ if (i32.ok()) {
+ WireFormatLite::WriteInt32(field_number, i32.ValueOrDie(), stream);
+ }
+ return i32.status();
+}
+
+// writes an SFIXED32 field, including tag, to the stream.
+inline Status WriteSFixed32(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<int32> i32 = data.ToInt32();
+ if (i32.ok()) {
+ WireFormatLite::WriteSFixed32(field_number, i32.ValueOrDie(), stream);
+ }
+ return i32.status();
+}
+
+// Writes an SINT32 field, including tag, to the stream.
+inline Status WriteSInt32(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<int32> i32 = data.ToInt32();
+ if (i32.ok()) {
+ WireFormatLite::WriteSInt32(field_number, i32.ValueOrDie(), stream);
+ }
+ return i32.status();
+}
+
+// Writes a FIXED32 field, including tag, to the stream.
+inline Status WriteFixed32(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<uint32> u32 = data.ToUint32();
+ if (u32.ok()) {
+ WireFormatLite::WriteFixed32(field_number, u32.ValueOrDie(), stream);
+ }
+ return u32.status();
+}
+
+// Writes a UINT32 field, including tag, to the stream.
+inline Status WriteUInt32(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<uint32> u32 = data.ToUint32();
+ if (u32.ok()) {
+ WireFormatLite::WriteUInt32(field_number, u32.ValueOrDie(), stream);
+ }
+ return u32.status();
+}
+
+// Writes an INT64 field, including tag, to the stream.
+inline Status WriteInt64(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<int64> i64 = data.ToInt64();
+ if (i64.ok()) {
+ WireFormatLite::WriteInt64(field_number, i64.ValueOrDie(), stream);
+ }
+ return i64.status();
+}
+
+// Writes an SFIXED64 field, including tag, to the stream.
+inline Status WriteSFixed64(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<int64> i64 = data.ToInt64();
+ if (i64.ok()) {
+ WireFormatLite::WriteSFixed64(field_number, i64.ValueOrDie(), stream);
+ }
+ return i64.status();
+}
+
+// Writes an SINT64 field, including tag, to the stream.
+inline Status WriteSInt64(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<int64> i64 = data.ToInt64();
+ if (i64.ok()) {
+ WireFormatLite::WriteSInt64(field_number, i64.ValueOrDie(), stream);
+ }
+ return i64.status();
+}
+
+// Writes a FIXED64 field, including tag, to the stream.
+inline Status WriteFixed64(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<uint64> u64 = data.ToUint64();
+ if (u64.ok()) {
+ WireFormatLite::WriteFixed64(field_number, u64.ValueOrDie(), stream);
+ }
+ return u64.status();
+}
+
+// Writes a UINT64 field, including tag, to the stream.
+inline Status WriteUInt64(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<uint64> u64 = data.ToUint64();
+ if (u64.ok()) {
+ WireFormatLite::WriteUInt64(field_number, u64.ValueOrDie(), stream);
+ }
+ return u64.status();
+}
+
+// Writes a DOUBLE field, including tag, to the stream.
+inline Status WriteDouble(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<double> d = data.ToDouble();
+ if (d.ok()) {
+ WireFormatLite::WriteDouble(field_number, d.ValueOrDie(), stream);
+ }
+ return d.status();
+}
+
+// Writes a FLOAT field, including tag, to the stream.
+inline Status WriteFloat(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<float> f = data.ToFloat();
+ if (f.ok()) {
+ WireFormatLite::WriteFloat(field_number, f.ValueOrDie(), stream);
+ }
+ return f.status();
+}
+
+// Writes a BOOL field, including tag, to the stream.
+inline Status WriteBool(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<bool> b = data.ToBool();
+ if (b.ok()) {
+ WireFormatLite::WriteBool(field_number, b.ValueOrDie(), stream);
+ }
+ return b.status();
+}
+
+// Writes a BYTES field, including tag, to the stream.
+inline Status WriteBytes(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<string> c = data.ToBytes();
+ if (c.ok()) {
+ WireFormatLite::WriteBytes(field_number, c.ValueOrDie(), stream);
+ }
+ return c.status();
+}
+
+// Writes a STRING field, including tag, to the stream.
+inline Status WriteString(int field_number, const DataPiece& data,
+ CodedOutputStream* stream) {
+ StatusOr<string> s = data.ToString();
+ if (s.ok()) {
+ WireFormatLite::WriteString(field_number, s.ValueOrDie(), stream);
+ }
+ return s.status();
+}
+
+// Writes an ENUM field, including tag, to the stream.
+inline Status WriteEnum(int field_number, const DataPiece& data,
+ const google::protobuf::Enum* enum_type,
+ CodedOutputStream* stream) {
+ StatusOr<int> e = data.ToEnum(enum_type);
+ if (e.ok()) {
+ WireFormatLite::WriteEnum(field_number, e.ValueOrDie(), stream);
+ }
+ return e.status();
+}
+
+// Given a google::protobuf::Type, returns the set of all required fields.
+std::set<const google::protobuf::Field*> GetRequiredFields(
+ const google::protobuf::Type& type) {
+ std::set<const google::protobuf::Field*> required;
+ for (int i = 0; i < type.fields_size(); i++) {
+ const google::protobuf::Field& field = type.fields(i);
+ if (field.cardinality() ==
+ google::protobuf::Field_Cardinality_CARDINALITY_REQUIRED) {
+ required.insert(&field);
+ }
+ }
+ return required;
+}
+
+} // namespace
+
+ProtoWriter::ProtoElement::ProtoElement(const TypeInfo* typeinfo,
+ const google::protobuf::Type& type,
+ ProtoWriter* enclosing)
+ : BaseElement(NULL),
+ ow_(enclosing),
+ parent_field_(NULL),
+ typeinfo_(typeinfo),
+ proto3_(type.syntax() == google::protobuf::SYNTAX_PROTO3),
+ type_(type),
+ size_index_(-1),
+ array_index_(-1),
+ // oneof_indices_ values are 1-indexed (0 means not present).
+ oneof_indices_(type.oneofs_size() + 1) {
+ if (!proto3_) {
+ required_fields_ = GetRequiredFields(type_);
+ }
+}
+
+ProtoWriter::ProtoElement::ProtoElement(ProtoWriter::ProtoElement* parent,
+ const google::protobuf::Field* field,
+ const google::protobuf::Type& type,
+ bool is_list)
+ : BaseElement(parent),
+ ow_(this->parent()->ow_),
+ parent_field_(field),
+ typeinfo_(this->parent()->typeinfo_),
+ proto3_(type.syntax() == google::protobuf::SYNTAX_PROTO3),
+ type_(type),
+ size_index_(
+ !is_list && field->kind() == google::protobuf::Field_Kind_TYPE_MESSAGE
+ ? ow_->size_insert_.size()
+ : -1),
+ array_index_(is_list ? 0 : -1),
+ // oneof_indices_ values are 1-indexed (0 means not present).
+ oneof_indices_(type_.oneofs_size() + 1) {
+ if (!is_list) {
+ if (ow_->IsRepeated(*field)) {
+ // Update array_index_ if it is an explicit list.
+ if (this->parent()->array_index_ >= 0) this->parent()->array_index_++;
+ } else if (!proto3_) {
+ // For required fields tracking.
+ this->parent()->RegisterField(field);
+ }
+
+ if (field->kind() == google::protobuf::Field_Kind_TYPE_MESSAGE) {
+ if (!proto3_) {
+ required_fields_ = GetRequiredFields(type_);
+ }
+ int start_pos = ow_->stream_->ByteCount();
+ // length of serialized message is the final buffer position minus
+ // starting buffer position, plus length adjustments for size fields
+ // of any nested messages. We start with -start_pos here, so we only
+ // need to add the final buffer position to it at the end.
+ SizeInfo info = {start_pos, -start_pos};
+ ow_->size_insert_.push_back(info);
+ }
+ }
+}
+
+ProtoWriter::ProtoElement* ProtoWriter::ProtoElement::pop() {
+ if (!proto3_) {
+ // Calls the registered error listener for any required field(s) not yet
+ // seen.
+ for (set<const google::protobuf::Field*>::iterator it =
+ required_fields_.begin();
+ it != required_fields_.end(); ++it) {
+ ow_->MissingField((*it)->name());
+ }
+ }
+ // Computes the total number of proto bytes used by a message, also adjusts
+ // the size of all parent messages by the length of this size field.
+ // If size_index_ < 0, this is not a message, so no size field is added.
+ if (size_index_ >= 0) {
+ // Add the final buffer position to compute the total length of this
+ // serialized message. The stored value (before this addition) already
+ // contains the total length of the size fields of all nested messages
+ // minus the initial buffer position.
+ ow_->size_insert_[size_index_].size += ow_->stream_->ByteCount();
+ // Calculate the length required to serialize the size field of the
+ // message, and propagate this additional size information upward to
+ // all enclosing messages.
+ int size = ow_->size_insert_[size_index_].size;
+ int length = CodedOutputStream::VarintSize32(size);
+ for (ProtoElement* e = parent(); e != NULL; e = e->parent()) {
+ // Only nested messages have size field, lists do not have size field.
+ if (e->size_index_ >= 0) {
+ ow_->size_insert_[e->size_index_].size += length;
+ }
+ }
+ }
+ return BaseElement::pop<ProtoElement>();
+}
+
+void ProtoWriter::ProtoElement::RegisterField(
+ const google::protobuf::Field* field) {
+ if (!required_fields_.empty() &&
+ field->cardinality() ==
+ google::protobuf::Field_Cardinality_CARDINALITY_REQUIRED) {
+ required_fields_.erase(field);
+ }
+}
+
+string ProtoWriter::ProtoElement::ToString() const {
+ if (parent() == NULL) return "";
+ string loc = parent()->ToString();
+ if (!ow_->IsRepeated(*parent_field_) ||
+ parent()->parent_field_ != parent_field_) {
+ string name = parent_field_->name();
+ int i = 0;
+ while (i < name.size() && (ascii_isalnum(name[i]) || name[i] == '_')) ++i;
+ if (i > 0 && i == name.size()) { // safe field name
+ if (loc.empty()) {
+ loc = name;
+ } else {
+ StrAppend(&loc, ".", name);
+ }
+ } else {
+ StrAppend(&loc, "[\"", CEscape(name), "\"]");
+ }
+ }
+ if (ow_->IsRepeated(*parent_field_) && array_index_ > 0) {
+ StrAppend(&loc, "[", array_index_ - 1, "]");
+ }
+ return loc.empty() ? "." : loc;
+}
+
+bool ProtoWriter::ProtoElement::IsOneofIndexTaken(int32 index) {
+ return oneof_indices_[index];
+}
+
+void ProtoWriter::ProtoElement::TakeOneofIndex(int32 index) {
+ oneof_indices_[index] = true;
+}
+
+void ProtoWriter::InvalidName(StringPiece unknown_name, StringPiece message) {
+ listener_->InvalidName(location(), ToSnakeCase(unknown_name), message);
+}
+
+void ProtoWriter::InvalidValue(StringPiece type_name, StringPiece value) {
+ listener_->InvalidValue(location(), type_name, value);
+}
+
+void ProtoWriter::MissingField(StringPiece missing_name) {
+ listener_->MissingField(location(), missing_name);
+}
+
+ProtoWriter* ProtoWriter::StartObject(StringPiece name) {
+ // Starting the root message. Create the root ProtoElement and return.
+ if (element_ == NULL) {
+ if (!name.empty()) {
+ InvalidName(name, "Root element should not be named.");
+ }
+ element_.reset(new ProtoElement(typeinfo_, master_type_, this));
+ return this;
+ }
+
+ const google::protobuf::Field* field = NULL;
+ field = BeginNamed(name, false);
+ if (field == NULL) return this;
+
+ // Check to see if this field is a oneof and that no oneof in that group has
+ // already been set.
+ if (!ValidOneof(*field, name)) {
+ ++invalid_depth_;
+ return this;
+ }
+
+ const google::protobuf::Type* type = LookupType(field);
+ if (type == NULL) {
+ ++invalid_depth_;
+ InvalidName(name,
+ StrCat("Missing descriptor for field: ", field->type_url()));
+ return this;
+ }
+
+ return StartObjectField(*field, *type);
+}
+
+ProtoWriter* ProtoWriter::EndObject() {
+ if (invalid_depth_ > 0) {
+ --invalid_depth_;
+ return this;
+ }
+
+ if (element_ != NULL) {
+ element_.reset(element_->pop());
+ }
+
+
+ // If ending the root element,
+ // then serialize the full message with calculated sizes.
+ if (element_ == NULL) {
+ WriteRootMessage();
+ }
+ return this;
+}
+
+ProtoWriter* ProtoWriter::StartList(StringPiece name) {
+ const google::protobuf::Field* field = BeginNamed(name, true);
+ if (field == NULL) return this;
+
+ if (!ValidOneof(*field, name)) {
+ ++invalid_depth_;
+ return this;
+ }
+
+ const google::protobuf::Type* type = LookupType(field);
+ if (type == NULL) {
+ ++invalid_depth_;
+ InvalidName(name,
+ StrCat("Missing descriptor for field: ", field->type_url()));
+ return this;
+ }
+
+ return StartListField(*field, *type);
+}
+
+ProtoWriter* ProtoWriter::EndList() {
+ if (invalid_depth_ > 0) {
+ --invalid_depth_;
+ } else if (element_ != NULL) {
+ element_.reset(element_->pop());
+ }
+ return this;
+}
+
+ProtoWriter* ProtoWriter::RenderDataPiece(StringPiece name,
+ const DataPiece& data) {
+ Status status;
+ if (invalid_depth_ > 0) return this;
+
+ const google::protobuf::Field* field = Lookup(name);
+ if (field == NULL) return this;
+
+ if (!ValidOneof(*field, name)) return this;
+
+ const google::protobuf::Type* type = LookupType(field);
+ if (type == NULL) {
+ InvalidName(name,
+ StrCat("Missing descriptor for field: ", field->type_url()));
+ return this;
+ }
+
+ return RenderPrimitiveField(*field, *type, data);
+}
+
+bool ProtoWriter::ValidOneof(const google::protobuf::Field& field,
+ StringPiece unnormalized_name) {
+ if (element_ == NULL) return true;
+
+ if (field.oneof_index() > 0) {
+ if (element_->IsOneofIndexTaken(field.oneof_index())) {
+ InvalidValue(
+ "oneof",
+ StrCat("oneof field '",
+ element_->type().oneofs(field.oneof_index() - 1),
+ "' is already set. Cannot set '", unnormalized_name, "'"));
+ return false;
+ }
+ element_->TakeOneofIndex(field.oneof_index());
+ }
+ return true;
+}
+
+bool ProtoWriter::IsRepeated(const google::protobuf::Field& field) {
+ return field.cardinality() ==
+ google::protobuf::Field_Cardinality_CARDINALITY_REPEATED;
+}
+
+ProtoWriter* ProtoWriter::StartObjectField(const google::protobuf::Field& field,
+ const google::protobuf::Type& type) {
+ WriteTag(field);
+ element_.reset(new ProtoElement(element_.release(), &field, type, false));
+ return this;
+}
+
+ProtoWriter* ProtoWriter::StartListField(const google::protobuf::Field& field,
+ const google::protobuf::Type& type) {
+ element_.reset(new ProtoElement(element_.release(), &field, type, true));
+ return this;
+}
+
+ProtoWriter* ProtoWriter::RenderPrimitiveField(
+ const google::protobuf::Field& field, const google::protobuf::Type& type,
+ const DataPiece& data) {
+ Status status;
+
+ // Pushing a ProtoElement and then pop it off at the end for 2 purposes:
+ // error location reporting and required field accounting.
+ //
+ // For proto3, since there is no required field tracking, we only need to push
+ // ProtoElement for error cases.
+ if (!element_->proto3()) {
+ element_.reset(new ProtoElement(element_.release(), &field, type, false));
+ }
+
+ if (field.kind() == google::protobuf::Field_Kind_TYPE_UNKNOWN ||
+ field.kind() == google::protobuf::Field_Kind_TYPE_MESSAGE) {
+ // Push a ProtoElement for location reporting purposes.
+ if (element_->proto3()) {
+ element_.reset(new ProtoElement(element_.release(), &field, type, false));
+ }
+ InvalidValue(field.type_url().empty()
+ ? google::protobuf::Field_Kind_Name(field.kind())
+ : field.type_url(),
+ data.ValueAsStringOrDefault(""));
+ element_.reset(element()->pop());
+ return this;
+ }
+
+ switch (field.kind()) {
+ case google::protobuf::Field_Kind_TYPE_INT32: {
+ status = WriteInt32(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SFIXED32: {
+ status = WriteSFixed32(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SINT32: {
+ status = WriteSInt32(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FIXED32: {
+ status = WriteFixed32(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT32: {
+ status = WriteUInt32(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_INT64: {
+ status = WriteInt64(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SFIXED64: {
+ status = WriteSFixed64(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SINT64: {
+ status = WriteSInt64(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FIXED64: {
+ status = WriteFixed64(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT64: {
+ status = WriteUInt64(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_DOUBLE: {
+ status = WriteDouble(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FLOAT: {
+ status = WriteFloat(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_BOOL: {
+ status = WriteBool(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_BYTES: {
+ status = WriteBytes(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_STRING: {
+ status = WriteString(field.number(), data, stream_.get());
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_ENUM: {
+ status = WriteEnum(field.number(), data,
+ typeinfo_->GetEnumByTypeUrl(field.type_url()),
+ stream_.get());
+ break;
+ }
+ default: // TYPE_GROUP or TYPE_MESSAGE
+ status = Status(INVALID_ARGUMENT, data.ToString().ValueOrDie());
+ }
+
+ if (!status.ok()) {
+ // Push a ProtoElement for location reporting purposes.
+ if (element_->proto3()) {
+ element_.reset(new ProtoElement(element_.release(), &field, type, false));
+ }
+ InvalidValue(google::protobuf::Field_Kind_Name(field.kind()),
+ status.error_message());
+ element_.reset(element()->pop());
+ return this;
+ }
+
+ if (!element_->proto3()) element_.reset(element()->pop());
+
+ return this;
+}
+
+const google::protobuf::Field* ProtoWriter::BeginNamed(StringPiece name,
+ bool is_list) {
+ if (invalid_depth_ > 0) {
+ ++invalid_depth_;
+ return NULL;
+ }
+ const google::protobuf::Field* field = Lookup(name);
+ if (field == NULL) {
+ ++invalid_depth_;
+ // InvalidName() already called in Lookup().
+ return NULL;
+ }
+ if (is_list && !IsRepeated(*field)) {
+ ++invalid_depth_;
+ InvalidName(name, "Proto field is not repeating, cannot start list.");
+ return NULL;
+ }
+ return field;
+}
+
+const google::protobuf::Field* ProtoWriter::Lookup(
+ StringPiece unnormalized_name) {
+ ProtoElement* e = element();
+ if (e == NULL) {
+ InvalidName(unnormalized_name, "Root element must be a message.");
+ return NULL;
+ }
+ if (unnormalized_name.empty()) {
+ // Objects in repeated field inherit the same field descriptor.
+ if (e->parent_field() == NULL) {
+ InvalidName(unnormalized_name, "Proto fields must have a name.");
+ } else if (!IsRepeated(*e->parent_field())) {
+ InvalidName(unnormalized_name, "Proto fields must have a name.");
+ return NULL;
+ }
+ return e->parent_field();
+ }
+ const google::protobuf::Field* field =
+ typeinfo_->FindField(&e->type(), unnormalized_name);
+ if (field == NULL && !ignore_unknown_fields_) {
+ InvalidName(unnormalized_name, "Cannot find field.");
+ }
+ return field;
+}
+
+const google::protobuf::Type* ProtoWriter::LookupType(
+ const google::protobuf::Field* field) {
+ return ((field->kind() == google::protobuf::Field_Kind_TYPE_MESSAGE ||
+ field->kind() == google::protobuf::Field_Kind_TYPE_GROUP)
+ ? typeinfo_->GetTypeByTypeUrl(field->type_url())
+ : &element_->type());
+}
+
+void ProtoWriter::WriteRootMessage() {
+ GOOGLE_DCHECK(!done_);
+ int curr_pos = 0;
+ // Calls the destructor of CodedOutputStream to remove any uninitialized
+ // memory from the Cord before we read it.
+ stream_.reset(NULL);
+ const void* data;
+ int length;
+ google::protobuf::io::ArrayInputStream input_stream(buffer_.data(), buffer_.size());
+ while (input_stream.Next(&data, &length)) {
+ if (length == 0) continue;
+ int num_bytes = length;
+ // Write up to where we need to insert the size field.
+ // The number of bytes we may write is the smaller of:
+ // - the current fragment size
+ // - the distance to the next position where a size field needs to be
+ // inserted.
+ if (!size_insert_.empty() &&
+ size_insert_.front().pos - curr_pos < num_bytes) {
+ num_bytes = size_insert_.front().pos - curr_pos;
+ }
+ output_->Append(static_cast<const char*>(data), num_bytes);
+ if (num_bytes < length) {
+ input_stream.BackUp(length - num_bytes);
+ }
+ curr_pos += num_bytes;
+ // Insert the size field.
+ // size_insert_.front(): the next <index, size> pair to be written.
+ // size_insert_.front().pos: position of the size field.
+ // size_insert_.front().size: the size (integer) to be inserted.
+ if (!size_insert_.empty() && curr_pos == size_insert_.front().pos) {
+ // Varint32 occupies at most 10 bytes.
+ uint8 insert_buffer[10];
+ uint8* insert_buffer_pos = CodedOutputStream::WriteVarint32ToArray(
+ size_insert_.front().size, insert_buffer);
+ output_->Append(reinterpret_cast<const char*>(insert_buffer),
+ insert_buffer_pos - insert_buffer);
+ size_insert_.pop_front();
+ }
+ }
+ output_->Flush();
+ stream_.reset(new CodedOutputStream(&adapter_));
+ done_ = true;
+}
+
+void ProtoWriter::WriteTag(const google::protobuf::Field& field) {
+ WireFormatLite::WireType wire_type = WireFormatLite::WireTypeForFieldType(
+ static_cast<WireFormatLite::FieldType>(field.kind()));
+ stream_->WriteTag(WireFormatLite::MakeTag(field.number(), wire_type));
+}
+
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.h
new file mode 100644
index 0000000000..7f1108abfe
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/proto_writer.h
@@ -0,0 +1,345 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTO_WRITER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTO_WRITER_H__
+
+#include <deque>
+#include <string>
+#include <vector>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/type_info.h>
+#include <google/protobuf/util/internal/datapiece.h>
+#include <google/protobuf/util/internal/error_listener.h>
+#include <google/protobuf/util/internal/structured_objectwriter.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/stubs/bytestream.h>
+#include <google/protobuf/stubs/hash.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+class CodedOutputStream;
+} // namespace io
+} // namespace protobuf
+
+
+namespace protobuf {
+class Type;
+class Field;
+} // namespace protobuf
+
+
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class ObjectLocationTracker;
+
+// An ObjectWriter that can write protobuf bytes directly from writer events.
+// This class does not support special types like Struct or Map. However, since
+// this class supports raw protobuf, it can be used to provide support for
+// special types by inheriting from it or by wrapping it.
+//
+// It also supports streaming.
+class LIBPROTOBUF_EXPORT ProtoWriter : public StructuredObjectWriter {
+ public:
+// Constructor. Does not take ownership of any parameter passed in.
+ ProtoWriter(TypeResolver* type_resolver, const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener);
+ virtual ~ProtoWriter();
+
+ // ObjectWriter methods.
+ virtual ProtoWriter* StartObject(StringPiece name);
+ virtual ProtoWriter* EndObject();
+ virtual ProtoWriter* StartList(StringPiece name);
+ virtual ProtoWriter* EndList();
+ virtual ProtoWriter* RenderBool(StringPiece name, bool value) {
+ return RenderDataPiece(name, DataPiece(value));
+ }
+ virtual ProtoWriter* RenderInt32(StringPiece name, int32 value) {
+ return RenderDataPiece(name, DataPiece(value));
+ }
+ virtual ProtoWriter* RenderUint32(StringPiece name, uint32 value) {
+ return RenderDataPiece(name, DataPiece(value));
+ }
+ virtual ProtoWriter* RenderInt64(StringPiece name, int64 value) {
+ return RenderDataPiece(name, DataPiece(value));
+ }
+ virtual ProtoWriter* RenderUint64(StringPiece name, uint64 value) {
+ return RenderDataPiece(name, DataPiece(value));
+ }
+ virtual ProtoWriter* RenderDouble(StringPiece name, double value) {
+ return RenderDataPiece(name, DataPiece(value));
+ }
+ virtual ProtoWriter* RenderFloat(StringPiece name, float value) {
+ return RenderDataPiece(name, DataPiece(value));
+ }
+ virtual ProtoWriter* RenderString(StringPiece name, StringPiece value) {
+ return RenderDataPiece(name,
+ DataPiece(value, use_strict_base64_decoding()));
+ }
+ virtual ProtoWriter* RenderBytes(StringPiece name, StringPiece value) {
+ return RenderDataPiece(
+ name, DataPiece(value, false, use_strict_base64_decoding()));
+ }
+ virtual ProtoWriter* RenderNull(StringPiece name) {
+ return RenderDataPiece(name, DataPiece::NullData());
+ }
+
+
+ // Renders a DataPiece 'value' into a field whose wire type is determined
+ // from the given field 'name'.
+ virtual ProtoWriter* RenderDataPiece(StringPiece name,
+ const DataPiece& value);
+
+ // Returns the location tracker to use for tracking locations for errors.
+ const LocationTrackerInterface& location() {
+ return element_ != NULL ? *element_ : *tracker_;
+ }
+
+ // When true, we finished writing to output a complete message.
+ bool done() { return done_; }
+
+ // Returns the proto stream object.
+ google::protobuf::io::CodedOutputStream* stream() { return stream_.get(); }
+
+ // Getters and mutators of invalid_depth_.
+ void IncrementInvalidDepth() { ++invalid_depth_; }
+ void DecrementInvalidDepth() { --invalid_depth_; }
+ int invalid_depth() { return invalid_depth_; }
+
+ ErrorListener* listener() { return listener_; }
+
+ const TypeInfo* typeinfo() { return typeinfo_; }
+
+ void set_ignore_unknown_fields(bool ignore_unknown_fields) {
+ ignore_unknown_fields_ = ignore_unknown_fields;
+ }
+
+ protected:
+ class LIBPROTOBUF_EXPORT ProtoElement : public BaseElement, public LocationTrackerInterface {
+ public:
+ // Constructor for the root element. No parent nor field.
+ ProtoElement(const TypeInfo* typeinfo, const google::protobuf::Type& type,
+ ProtoWriter* enclosing);
+
+ // Constructor for a field of an element.
+ ProtoElement(ProtoElement* parent, const google::protobuf::Field* field,
+ const google::protobuf::Type& type, bool is_list);
+
+ virtual ~ProtoElement() {}
+
+ // Called just before the destructor for clean up:
+ // - reports any missing required fields
+ // - computes the space needed by the size field, and augment the
+ // length of all parent messages by this additional space.
+ // - releases and returns the parent pointer.
+ ProtoElement* pop();
+
+ // Accessors
+ // parent_field() may be NULL if we are at root.
+ const google::protobuf::Field* parent_field() const {
+ return parent_field_;
+ }
+ const google::protobuf::Type& type() const { return type_; }
+
+ // Registers field for accounting required fields.
+ void RegisterField(const google::protobuf::Field* field);
+
+ // To report location on error messages.
+ virtual string ToString() const;
+
+ virtual ProtoElement* parent() const {
+ return static_cast<ProtoElement*>(BaseElement::parent());
+ }
+
+ // Returns true if the index is already taken by a preceding oneof input.
+ bool IsOneofIndexTaken(int32 index);
+
+ // Marks the oneof 'index' as taken. Future inputs to this oneof will
+ // generate an error.
+ void TakeOneofIndex(int32 index);
+
+ bool proto3() { return proto3_; }
+
+ private:
+ // Used for access to variables of the enclosing instance of
+ // ProtoWriter.
+ ProtoWriter* ow_;
+
+ // Describes the element as a field in the parent message.
+ // parent_field_ is NULL if and only if this element is the root element.
+ const google::protobuf::Field* parent_field_;
+
+ // TypeInfo to lookup types.
+ const TypeInfo* typeinfo_;
+
+ // Whether the type_ is proto3 or not.
+ bool proto3_;
+
+ // Additional variables if this element is a message:
+ // (Root element is always a message).
+ // type_ : the type of this element.
+ // required_fields_ : set of required fields.
+ // size_index_ : index into ProtoWriter::size_insert_
+ // for later insertion of serialized message length.
+ const google::protobuf::Type& type_;
+ std::set<const google::protobuf::Field*> required_fields_;
+ const int size_index_;
+
+ // Tracks position in repeated fields, needed for LocationTrackerInterface.
+ int array_index_;
+
+ // Set of oneof indices already seen for the type_. Used to validate
+ // incoming messages so no more than one oneof is set.
+ std::vector<bool> oneof_indices_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(ProtoElement);
+ };
+
+ // Container for inserting 'size' information at the 'pos' position.
+ struct SizeInfo {
+ const int pos;
+ int size;
+ };
+
+ ProtoWriter(const TypeInfo* typeinfo, const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener);
+
+ virtual ProtoElement* element() { return element_.get(); }
+
+ // Helper methods for calling ErrorListener. See error_listener.h.
+ void InvalidName(StringPiece unknown_name, StringPiece message);
+ void InvalidValue(StringPiece type_name, StringPiece value);
+ void MissingField(StringPiece missing_name);
+
+ // Common code for BeginObject() and BeginList() that does invalid_depth_
+ // bookkeeping associated with name lookup.
+ const google::protobuf::Field* BeginNamed(StringPiece name, bool is_list);
+
+ // Lookup the field in the current element. Looks in the base descriptor
+ // and in any extension. This will report an error if the field cannot be
+ // found when ignore_unknown_names_ is false or if multiple matching
+ // extensions are found.
+ const google::protobuf::Field* Lookup(StringPiece name);
+
+ // Lookup the field type in the type descriptor. Returns NULL if the type
+ // is not known.
+ const google::protobuf::Type* LookupType(
+ const google::protobuf::Field* field);
+
+ // Write serialized output to the final output ByteSink, inserting all
+ // the size information for nested messages that are missing from the
+ // intermediate Cord buffer.
+ void WriteRootMessage();
+
+ // Helper method to write proto tags based on the given field.
+ void WriteTag(const google::protobuf::Field& field);
+
+
+ // Returns true if the field for type_ can be set as a oneof. If field is not
+ // a oneof type, this function does nothing and returns true.
+ // If another field for this oneof is already set, this function returns
+ // false. It also calls the appropriate error callback.
+ // unnormalized_name is used for error string.
+ bool ValidOneof(const google::protobuf::Field& field,
+ StringPiece unnormalized_name);
+
+ // Returns true if the field is repeated.
+ bool IsRepeated(const google::protobuf::Field& field);
+
+ // Starts an object given the field and the enclosing type.
+ ProtoWriter* StartObjectField(const google::protobuf::Field& field,
+ const google::protobuf::Type& type);
+
+ // Starts a list given the field and the enclosing type.
+ ProtoWriter* StartListField(const google::protobuf::Field& field,
+ const google::protobuf::Type& type);
+
+ // Renders a primitve field given the field and the enclosing type.
+ ProtoWriter* RenderPrimitiveField(const google::protobuf::Field& field,
+ const google::protobuf::Type& type,
+ const DataPiece& value);
+
+ private:
+ // Variables for describing the structure of the input tree:
+ // master_type_: descriptor for the whole protobuf message.
+ // typeinfo_ : the TypeInfo object to lookup types.
+ const google::protobuf::Type& master_type_;
+ const TypeInfo* typeinfo_;
+ // Whether we own the typeinfo_ object.
+ bool own_typeinfo_;
+
+ // Indicates whether we finished writing root message completely.
+ bool done_;
+
+ // If true, don't report unknown field names to the listener.
+ bool ignore_unknown_fields_;
+
+ // Variable for internal state processing:
+ // element_ : the current element.
+ // size_insert_: sizes of nested messages.
+ // pos - position to insert the size field.
+ // size - size value to be inserted.
+ google::protobuf::scoped_ptr<ProtoElement> element_;
+ std::deque<SizeInfo> size_insert_;
+
+ // Variables for output generation:
+ // output_ : pointer to an external ByteSink for final user-visible output.
+ // buffer_ : buffer holding partial message before being ready for output_.
+ // adapter_ : internal adapter between CodedOutputStream and buffer_.
+ // stream_ : wrapper for writing tags and other encodings in wire format.
+ strings::ByteSink* output_;
+ string buffer_;
+ google::protobuf::io::StringOutputStream adapter_;
+ google::protobuf::scoped_ptr<google::protobuf::io::CodedOutputStream> stream_;
+
+ // Variables for error tracking and reporting:
+ // listener_ : a place to report any errors found.
+ // invalid_depth_: number of enclosing invalid nested messages.
+ // tracker_ : the root location tracker interface.
+ ErrorListener* listener_;
+ int invalid_depth_;
+ google::protobuf::scoped_ptr<LocationTrackerInterface> tracker_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(ProtoWriter);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTO_WRITER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.cc
new file mode 100644
index 0000000000..0048d75b58
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.cc
@@ -0,0 +1,1114 @@
+// 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.
+
+#include <google/protobuf/util/internal/protostream_objectsource.h>
+
+#include <utility>
+
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/stubs/time.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/wire_format_lite.h>
+#include <google/protobuf/util/internal/field_mask_utility.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/status_macros.h>
+
+
+namespace google {
+namespace protobuf {
+namespace util {
+using util::Status;
+using util::StatusOr;
+namespace error {
+using util::error::Code;
+using util::error::INTERNAL;
+}
+namespace converter {
+
+using google::protobuf::Descriptor;
+using google::protobuf::EnumValueDescriptor;
+using google::protobuf::FieldDescriptor;
+using google::protobuf::internal::WireFormat;
+using google::protobuf::internal::WireFormatLite;
+using util::Status;
+using util::StatusOr;
+
+namespace {
+
+static int kDefaultMaxRecursionDepth = 64;
+
+// Finds a field with the given number. NULL if none found.
+const google::protobuf::Field* FindFieldByNumber(
+ const google::protobuf::Type& type, int number);
+
+// Returns true if the field is packable.
+bool IsPackable(const google::protobuf::Field& field);
+
+// Finds an enum value with the given number. NULL if none found.
+const google::protobuf::EnumValue* FindEnumValueByNumber(
+ const google::protobuf::Enum& tech_enum, int number);
+
+// Utility function to format nanos.
+const string FormatNanos(uint32 nanos);
+
+StatusOr<string> MapKeyDefaultValueAsString(
+ const google::protobuf::Field& field) {
+ switch (field.kind()) {
+ case google::protobuf::Field_Kind_TYPE_BOOL:
+ return string("false");
+ case google::protobuf::Field_Kind_TYPE_INT32:
+ case google::protobuf::Field_Kind_TYPE_INT64:
+ case google::protobuf::Field_Kind_TYPE_UINT32:
+ case google::protobuf::Field_Kind_TYPE_UINT64:
+ case google::protobuf::Field_Kind_TYPE_SINT32:
+ case google::protobuf::Field_Kind_TYPE_SINT64:
+ case google::protobuf::Field_Kind_TYPE_SFIXED32:
+ case google::protobuf::Field_Kind_TYPE_SFIXED64:
+ case google::protobuf::Field_Kind_TYPE_FIXED32:
+ case google::protobuf::Field_Kind_TYPE_FIXED64:
+ return string("0");
+ case google::protobuf::Field_Kind_TYPE_STRING:
+ return string();
+ default:
+ return Status(util::error::INTERNAL, "Invalid map key type.");
+ }
+}
+} // namespace
+
+
+ProtoStreamObjectSource::ProtoStreamObjectSource(
+ google::protobuf::io::CodedInputStream* stream, TypeResolver* type_resolver,
+ const google::protobuf::Type& type)
+ : stream_(stream),
+ typeinfo_(TypeInfo::NewTypeInfo(type_resolver)),
+ own_typeinfo_(true),
+ type_(type),
+ use_lower_camel_for_enums_(false),
+ recursion_depth_(0),
+ max_recursion_depth_(kDefaultMaxRecursionDepth),
+ render_unknown_fields_(false) {
+ GOOGLE_LOG_IF(DFATAL, stream == NULL) << "Input stream is NULL.";
+}
+
+ProtoStreamObjectSource::ProtoStreamObjectSource(
+ google::protobuf::io::CodedInputStream* stream, const TypeInfo* typeinfo,
+ const google::protobuf::Type& type)
+ : stream_(stream),
+ typeinfo_(typeinfo),
+ own_typeinfo_(false),
+ type_(type),
+ use_lower_camel_for_enums_(false),
+ recursion_depth_(0),
+ max_recursion_depth_(kDefaultMaxRecursionDepth),
+ render_unknown_fields_(false) {
+ GOOGLE_LOG_IF(DFATAL, stream == NULL) << "Input stream is NULL.";
+}
+
+ProtoStreamObjectSource::~ProtoStreamObjectSource() {
+ if (own_typeinfo_) {
+ delete typeinfo_;
+ }
+}
+
+Status ProtoStreamObjectSource::NamedWriteTo(StringPiece name,
+ ObjectWriter* ow) const {
+ return WriteMessage(type_, name, 0, true, ow);
+}
+
+const google::protobuf::Field* ProtoStreamObjectSource::FindAndVerifyField(
+ const google::protobuf::Type& type, uint32 tag) const {
+ // Lookup the new field in the type by tag number.
+ const google::protobuf::Field* field = FindFieldByNumber(type, tag >> 3);
+ // Verify if the field corresponds to the wire type in tag.
+ // If there is any discrepancy, mark the field as not found.
+ if (field != NULL) {
+ WireFormatLite::WireType expected_type =
+ WireFormatLite::WireTypeForFieldType(
+ static_cast<WireFormatLite::FieldType>(field->kind()));
+ WireFormatLite::WireType actual_type = WireFormatLite::GetTagWireType(tag);
+ if (actual_type != expected_type &&
+ (!IsPackable(*field) ||
+ actual_type != WireFormatLite::WIRETYPE_LENGTH_DELIMITED)) {
+ field = NULL;
+ }
+ }
+ return field;
+}
+
+Status ProtoStreamObjectSource::WriteMessage(const google::protobuf::Type& type,
+ StringPiece name,
+ const uint32 end_tag,
+ bool include_start_and_end,
+ ObjectWriter* ow) const {
+
+ const TypeRenderer* type_renderer = FindTypeRenderer(type.name());
+ if (type_renderer != NULL) {
+ return (*type_renderer)(this, type, name, ow);
+ }
+
+ const google::protobuf::Field* field = NULL;
+ string field_name;
+ // last_tag set to dummy value that is different from tag.
+ uint32 tag = stream_->ReadTag(), last_tag = tag + 1;
+ google::protobuf::UnknownFieldSet unknown_fields;
+
+ if (include_start_and_end) {
+ ow->StartObject(name);
+ }
+ while (tag != end_tag) {
+ if (tag != last_tag) { // Update field only if tag is changed.
+ last_tag = tag;
+ field = FindAndVerifyField(type, tag);
+ if (field != NULL) {
+ field_name = field->json_name();
+ }
+ }
+ if (field == NULL) {
+ // If we didn't find a field, skip this unknown tag.
+ // TODO(wpoon): Check return boolean value.
+ WireFormat::SkipField(stream_, tag,
+ render_unknown_fields_ ? &unknown_fields : NULL);
+ tag = stream_->ReadTag();
+ continue;
+ }
+
+ if (field->cardinality() ==
+ google::protobuf::Field_Cardinality_CARDINALITY_REPEATED) {
+ bool check_maps = true;
+
+ if (check_maps && IsMap(*field)) {
+ ow->StartObject(field_name);
+ ASSIGN_OR_RETURN(tag, RenderMap(field, field_name, tag, ow));
+ ow->EndObject();
+ } else {
+ ASSIGN_OR_RETURN(tag, RenderList(field, field_name, tag, ow));
+ }
+ } else {
+ // Render the field.
+ RETURN_IF_ERROR(RenderField(field, field_name, ow));
+ tag = stream_->ReadTag();
+ }
+ }
+
+
+ if (include_start_and_end) {
+ ow->EndObject();
+ }
+ return Status::OK;
+}
+
+StatusOr<uint32> ProtoStreamObjectSource::RenderList(
+ const google::protobuf::Field* field, StringPiece name, uint32 list_tag,
+ ObjectWriter* ow) const {
+ uint32 tag_to_return = 0;
+ ow->StartList(name);
+ if (IsPackable(*field) &&
+ list_tag ==
+ WireFormatLite::MakeTag(field->number(),
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED)) {
+ RETURN_IF_ERROR(RenderPacked(field, ow));
+ // Since packed fields have a single tag, read another tag from stream to
+ // return.
+ tag_to_return = stream_->ReadTag();
+ } else {
+ do {
+ RETURN_IF_ERROR(RenderField(field, "", ow));
+ } while ((tag_to_return = stream_->ReadTag()) == list_tag);
+ }
+ ow->EndList();
+ return tag_to_return;
+}
+
+StatusOr<uint32> ProtoStreamObjectSource::RenderMap(
+ const google::protobuf::Field* field, StringPiece name, uint32 list_tag,
+ ObjectWriter* ow) const {
+ const google::protobuf::Type* field_type =
+ typeinfo_->GetTypeByTypeUrl(field->type_url());
+ uint32 tag_to_return = 0;
+ do {
+ // Render map entry message type.
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32); // message length
+ int old_limit = stream_->PushLimit(buffer32);
+ string map_key;
+ for (uint32 tag = stream_->ReadTag(); tag != 0; tag = stream_->ReadTag()) {
+ const google::protobuf::Field* field =
+ FindAndVerifyField(*field_type, tag);
+ if (field == NULL) {
+ WireFormat::SkipField(stream_, tag, NULL);
+ continue;
+ }
+ // Map field numbers are key = 1 and value = 2
+ if (field->number() == 1) {
+ map_key = ReadFieldValueAsString(*field);
+ } else if (field->number() == 2) {
+ if (map_key.empty()) {
+ // An absent map key is treated as the default.
+ const google::protobuf::Field* key_field =
+ FindFieldByNumber(*field_type, 1);
+ if (key_field == NULL) {
+ // The Type info for this map entry is incorrect. It should always
+ // have a field named "key" and with field number 1.
+ return Status(util::error::INTERNAL, "Invalid map entry.");
+ }
+ ASSIGN_OR_RETURN(map_key, MapKeyDefaultValueAsString(*key_field));
+ }
+ RETURN_IF_ERROR(RenderField(field, map_key, ow));
+ } else {
+ // The Type info for this map entry is incorrect. It should contain
+ // exactly two fields with field number 1 and 2.
+ return Status(util::error::INTERNAL, "Invalid map entry.");
+ }
+ }
+ stream_->PopLimit(old_limit);
+ } while ((tag_to_return = stream_->ReadTag()) == list_tag);
+ return tag_to_return;
+}
+
+Status ProtoStreamObjectSource::RenderPacked(
+ const google::protobuf::Field* field, ObjectWriter* ow) const {
+ uint32 length;
+ stream_->ReadVarint32(&length);
+ int old_limit = stream_->PushLimit(length);
+ while (stream_->BytesUntilLimit() > 0) {
+ RETURN_IF_ERROR(RenderField(field, StringPiece(), ow));
+ }
+ stream_->PopLimit(old_limit);
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderTimestamp(
+ const ProtoStreamObjectSource* os, const google::protobuf::Type& type,
+ StringPiece field_name, ObjectWriter* ow) {
+ pair<int64, int32> p = os->ReadSecondsAndNanos(type);
+ int64 seconds = p.first;
+ int32 nanos = p.second;
+ if (seconds > kTimestampMaxSeconds || seconds < kTimestampMinSeconds) {
+ return Status(
+ util::error::INTERNAL,
+ StrCat("Timestamp seconds exceeds limit for field: ", field_name));
+ }
+
+ if (nanos < 0 || nanos >= kNanosPerSecond) {
+ return Status(
+ util::error::INTERNAL,
+ StrCat("Timestamp nanos exceeds limit for field: ", field_name));
+ }
+
+ ow->RenderString(field_name,
+ ::google::protobuf::internal::FormatTime(seconds, nanos));
+
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderDuration(
+ const ProtoStreamObjectSource* os, const google::protobuf::Type& type,
+ StringPiece field_name, ObjectWriter* ow) {
+ pair<int64, int32> p = os->ReadSecondsAndNanos(type);
+ int64 seconds = p.first;
+ int32 nanos = p.second;
+ if (seconds > kDurationMaxSeconds || seconds < kDurationMinSeconds) {
+ return Status(
+ util::error::INTERNAL,
+ StrCat("Duration seconds exceeds limit for field: ", field_name));
+ }
+
+ if (nanos <= -kNanosPerSecond || nanos >= kNanosPerSecond) {
+ return Status(
+ util::error::INTERNAL,
+ StrCat("Duration nanos exceeds limit for field: ", field_name));
+ }
+
+ string sign = "";
+ if (seconds < 0) {
+ if (nanos > 0) {
+ return Status(util::error::INTERNAL,
+ StrCat("Duration nanos is non-negative, but seconds is "
+ "negative for field: ",
+ field_name));
+ }
+ sign = "-";
+ seconds = -seconds;
+ nanos = -nanos;
+ } else if (seconds == 0 && nanos < 0) {
+ sign = "-";
+ nanos = -nanos;
+ }
+ string formatted_duration = StringPrintf("%s%lld%ss", sign.c_str(), seconds,
+ FormatNanos(nanos).c_str());
+ ow->RenderString(field_name, formatted_duration);
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderDouble(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint64 buffer64 = 0; // default value of Double wrapper value
+ if (tag != 0) {
+ os->stream_->ReadLittleEndian64(&buffer64);
+ os->stream_->ReadTag();
+ }
+ ow->RenderDouble(field_name, bit_cast<double>(buffer64));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderFloat(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint32 buffer32 = 0; // default value of Float wrapper value
+ if (tag != 0) {
+ os->stream_->ReadLittleEndian32(&buffer32);
+ os->stream_->ReadTag();
+ }
+ ow->RenderFloat(field_name, bit_cast<float>(buffer32));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderInt64(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint64 buffer64 = 0; // default value of Int64 wrapper value
+ if (tag != 0) {
+ os->stream_->ReadVarint64(&buffer64);
+ os->stream_->ReadTag();
+ }
+ ow->RenderInt64(field_name, bit_cast<int64>(buffer64));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderUInt64(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint64 buffer64 = 0; // default value of UInt64 wrapper value
+ if (tag != 0) {
+ os->stream_->ReadVarint64(&buffer64);
+ os->stream_->ReadTag();
+ }
+ ow->RenderUint64(field_name, bit_cast<uint64>(buffer64));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderInt32(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint32 buffer32 = 0; // default value of Int32 wrapper value
+ if (tag != 0) {
+ os->stream_->ReadVarint32(&buffer32);
+ os->stream_->ReadTag();
+ }
+ ow->RenderInt32(field_name, bit_cast<int32>(buffer32));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderUInt32(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint32 buffer32 = 0; // default value of UInt32 wrapper value
+ if (tag != 0) {
+ os->stream_->ReadVarint32(&buffer32);
+ os->stream_->ReadTag();
+ }
+ ow->RenderUint32(field_name, bit_cast<uint32>(buffer32));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderBool(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint64 buffer64 = 0; // results in 'false' value as default, which is the
+ // default value of Bool wrapper
+ if (tag != 0) {
+ os->stream_->ReadVarint64(&buffer64);
+ os->stream_->ReadTag();
+ }
+ ow->RenderBool(field_name, buffer64 != 0);
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderString(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint32 buffer32;
+ string str; // default value of empty for String wrapper
+ if (tag != 0) {
+ os->stream_->ReadVarint32(&buffer32); // string size.
+ os->stream_->ReadString(&str, buffer32);
+ os->stream_->ReadTag();
+ }
+ ow->RenderString(field_name, str);
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderBytes(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+ uint32 buffer32;
+ string str;
+ if (tag != 0) {
+ os->stream_->ReadVarint32(&buffer32);
+ os->stream_->ReadString(&str, buffer32);
+ os->stream_->ReadTag();
+ }
+ ow->RenderBytes(field_name, str);
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderStruct(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ const google::protobuf::Field* field = NULL;
+ uint32 tag = os->stream_->ReadTag();
+ ow->StartObject(field_name);
+ while (tag != 0) {
+ field = os->FindAndVerifyField(type, tag);
+ // google.protobuf.Struct has only one field that is a map. Hence we use
+ // RenderMap to render that field.
+ if (os->IsMap(*field)) {
+ ASSIGN_OR_RETURN(tag, os->RenderMap(field, field_name, tag, ow));
+ }
+ }
+ ow->EndObject();
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderStructValue(
+ const ProtoStreamObjectSource* os, const google::protobuf::Type& type,
+ StringPiece field_name, ObjectWriter* ow) {
+ const google::protobuf::Field* field = NULL;
+ for (uint32 tag = os->stream_->ReadTag(); tag != 0;
+ tag = os->stream_->ReadTag()) {
+ field = os->FindAndVerifyField(type, tag);
+ if (field == NULL) {
+ WireFormat::SkipField(os->stream_, tag, NULL);
+ continue;
+ }
+ RETURN_IF_ERROR(os->RenderField(field, field_name, ow));
+ }
+ return Status::OK;
+}
+
+// TODO(skarvaje): Avoid code duplication of for loops and SkipField logic.
+Status ProtoStreamObjectSource::RenderStructListValue(
+ const ProtoStreamObjectSource* os, const google::protobuf::Type& type,
+ StringPiece field_name, ObjectWriter* ow) {
+ uint32 tag = os->stream_->ReadTag();
+
+ // Render empty list when we find empty ListValue message.
+ if (tag == 0) {
+ ow->StartList(field_name);
+ ow->EndList();
+ return Status::OK;
+ }
+
+ while (tag != 0) {
+ const google::protobuf::Field* field = os->FindAndVerifyField(type, tag);
+ if (field == NULL) {
+ WireFormat::SkipField(os->stream_, tag, NULL);
+ tag = os->stream_->ReadTag();
+ continue;
+ }
+ ASSIGN_OR_RETURN(tag, os->RenderList(field, field_name, tag, ow));
+ }
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderAny(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece field_name,
+ ObjectWriter* ow) {
+ // An Any is of the form { string type_url = 1; bytes value = 2; }
+ uint32 tag;
+ string type_url;
+ string value;
+
+ // First read out the type_url and value from the proto stream
+ for (tag = os->stream_->ReadTag(); tag != 0; tag = os->stream_->ReadTag()) {
+ const google::protobuf::Field* field = os->FindAndVerifyField(type, tag);
+ if (field == NULL) {
+ WireFormat::SkipField(os->stream_, tag, NULL);
+ continue;
+ }
+ // 'type_url' has field number of 1 and 'value' has field number 2
+ // //google/protobuf/any.proto
+ if (field->number() == 1) {
+ // read type_url
+ uint32 type_url_size;
+ os->stream_->ReadVarint32(&type_url_size);
+ os->stream_->ReadString(&type_url, type_url_size);
+ } else if (field->number() == 2) {
+ // read value
+ uint32 value_size;
+ os->stream_->ReadVarint32(&value_size);
+ os->stream_->ReadString(&value, value_size);
+ }
+ }
+
+ // If there is no value, we don't lookup the type, we just output it (if
+ // present). If both type and value are empty we output an empty object.
+ if (value.empty()) {
+ ow->StartObject(field_name);
+ if (!type_url.empty()) {
+ ow->RenderString("@type", type_url);
+ }
+ ow->EndObject();
+ return util::Status::OK;
+ }
+
+ // If there is a value but no type, we cannot render it, so report an error.
+ if (type_url.empty()) {
+ // TODO(sven): Add an external message once those are ready.
+ return util::Status(util::error::INTERNAL,
+ "Invalid Any, the type_url is missing.");
+ }
+
+ util::StatusOr<const google::protobuf::Type*> resolved_type =
+ os->typeinfo_->ResolveTypeUrl(type_url);
+
+ if (!resolved_type.ok()) {
+ // Convert into an internal error, since this means the backend gave us
+ // an invalid response (missing or invalid type information).
+ return util::Status(util::error::INTERNAL,
+ resolved_type.status().error_message());
+ }
+ // nested_type cannot be null at this time.
+ const google::protobuf::Type* nested_type = resolved_type.ValueOrDie();
+
+ google::protobuf::io::ArrayInputStream zero_copy_stream(value.data(), value.size());
+ google::protobuf::io::CodedInputStream in_stream(&zero_copy_stream);
+ // We know the type so we can render it. Recursively parse the nested stream
+ // using a nested ProtoStreamObjectSource using our nested type information.
+ ProtoStreamObjectSource nested_os(&in_stream, os->typeinfo_, *nested_type);
+
+ // We manually call start and end object here so we can inject the @type.
+ ow->StartObject(field_name);
+ ow->RenderString("@type", type_url);
+ util::Status result =
+ nested_os.WriteMessage(nested_os.type_, "value", 0, false, ow);
+ ow->EndObject();
+ return result;
+}
+
+Status ProtoStreamObjectSource::RenderFieldMask(
+ const ProtoStreamObjectSource* os, const google::protobuf::Type& type,
+ StringPiece field_name, ObjectWriter* ow) {
+ string combined;
+ uint32 buffer32;
+ uint32 paths_field_tag = 0;
+ for (uint32 tag = os->stream_->ReadTag(); tag != 0;
+ tag = os->stream_->ReadTag()) {
+ if (paths_field_tag == 0) {
+ const google::protobuf::Field* field = os->FindAndVerifyField(type, tag);
+ if (field != NULL && field->number() == 1 &&
+ field->name() == "paths") {
+ paths_field_tag = tag;
+ }
+ }
+ if (paths_field_tag != tag) {
+ return util::Status(util::error::INTERNAL,
+ "Invalid FieldMask, unexpected field.");
+ }
+ string str;
+ os->stream_->ReadVarint32(&buffer32); // string size.
+ os->stream_->ReadString(&str, buffer32);
+ if (!combined.empty()) {
+ combined.append(",");
+ }
+ combined.append(ConvertFieldMaskPath(str, &ToCamelCase));
+ }
+ ow->RenderString(field_name, combined);
+ return Status::OK;
+}
+
+
+hash_map<string, ProtoStreamObjectSource::TypeRenderer>*
+ ProtoStreamObjectSource::renderers_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(source_renderers_init_);
+
+void ProtoStreamObjectSource::InitRendererMap() {
+ renderers_ = new hash_map<string, ProtoStreamObjectSource::TypeRenderer>();
+ (*renderers_)["google.protobuf.Timestamp"] =
+ &ProtoStreamObjectSource::RenderTimestamp;
+ (*renderers_)["google.protobuf.Duration"] =
+ &ProtoStreamObjectSource::RenderDuration;
+ (*renderers_)["google.protobuf.DoubleValue"] =
+ &ProtoStreamObjectSource::RenderDouble;
+ (*renderers_)["google.protobuf.FloatValue"] =
+ &ProtoStreamObjectSource::RenderFloat;
+ (*renderers_)["google.protobuf.Int64Value"] =
+ &ProtoStreamObjectSource::RenderInt64;
+ (*renderers_)["google.protobuf.UInt64Value"] =
+ &ProtoStreamObjectSource::RenderUInt64;
+ (*renderers_)["google.protobuf.Int32Value"] =
+ &ProtoStreamObjectSource::RenderInt32;
+ (*renderers_)["google.protobuf.UInt32Value"] =
+ &ProtoStreamObjectSource::RenderUInt32;
+ (*renderers_)["google.protobuf.BoolValue"] =
+ &ProtoStreamObjectSource::RenderBool;
+ (*renderers_)["google.protobuf.StringValue"] =
+ &ProtoStreamObjectSource::RenderString;
+ (*renderers_)["google.protobuf.BytesValue"] =
+ &ProtoStreamObjectSource::RenderBytes;
+ (*renderers_)["google.protobuf.Any"] = &ProtoStreamObjectSource::RenderAny;
+ (*renderers_)["google.protobuf.Struct"] =
+ &ProtoStreamObjectSource::RenderStruct;
+ (*renderers_)["google.protobuf.Value"] =
+ &ProtoStreamObjectSource::RenderStructValue;
+ (*renderers_)["google.protobuf.ListValue"] =
+ &ProtoStreamObjectSource::RenderStructListValue;
+ (*renderers_)["google.protobuf.FieldMask"] =
+ &ProtoStreamObjectSource::RenderFieldMask;
+ ::google::protobuf::internal::OnShutdown(&DeleteRendererMap);
+}
+
+void ProtoStreamObjectSource::DeleteRendererMap() {
+ delete ProtoStreamObjectSource::renderers_;
+ renderers_ = NULL;
+}
+
+// static
+ProtoStreamObjectSource::TypeRenderer*
+ProtoStreamObjectSource::FindTypeRenderer(const string& type_url) {
+ ::google::protobuf::GoogleOnceInit(&source_renderers_init_, &InitRendererMap);
+ return FindOrNull(*renderers_, type_url);
+}
+
+Status ProtoStreamObjectSource::RenderField(
+ const google::protobuf::Field* field, StringPiece field_name,
+ ObjectWriter* ow) const {
+ // Short-circuit message types as it tends to call WriteMessage recursively
+ // and ends up using a lot of stack space. Keep the stack usage of this
+ // message small in order to preserve stack space and not crash.
+ if (field->kind() == google::protobuf::Field_Kind_TYPE_MESSAGE) {
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32); // message length
+ int old_limit = stream_->PushLimit(buffer32);
+ // Get the nested message type for this field.
+ const google::protobuf::Type* type =
+ typeinfo_->GetTypeByTypeUrl(field->type_url());
+ if (type == NULL) {
+ return Status(util::error::INTERNAL,
+ StrCat("Invalid configuration. Could not find the type: ",
+ field->type_url()));
+ }
+
+ // Short-circuit any special type rendering to save call-stack space.
+ const TypeRenderer* type_renderer = FindTypeRenderer(type->name());
+
+ bool use_type_renderer = type_renderer != NULL;
+
+ if (use_type_renderer) {
+ RETURN_IF_ERROR((*type_renderer)(this, *type, field_name, ow));
+ } else {
+ RETURN_IF_ERROR(IncrementRecursionDepth(type->name(), field_name));
+ RETURN_IF_ERROR(WriteMessage(*type, field_name, 0, true, ow));
+ --recursion_depth_;
+ }
+ if (!stream_->ConsumedEntireMessage()) {
+ return Status(util::error::INVALID_ARGUMENT,
+ "Nested protocol message not parsed in its entirety.");
+ }
+ stream_->PopLimit(old_limit);
+ } else {
+ // Render all other non-message types.
+ return RenderNonMessageField(field, field_name, ow);
+ }
+ return Status::OK;
+}
+
+Status ProtoStreamObjectSource::RenderNonMessageField(
+ const google::protobuf::Field* field, StringPiece field_name,
+ ObjectWriter* ow) const {
+ // Temporary buffers of different types.
+ uint32 buffer32;
+ uint64 buffer64;
+ string strbuffer;
+ switch (field->kind()) {
+ case google::protobuf::Field_Kind_TYPE_BOOL: {
+ stream_->ReadVarint64(&buffer64);
+ ow->RenderBool(field_name, buffer64 != 0);
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_INT32: {
+ stream_->ReadVarint32(&buffer32);
+ ow->RenderInt32(field_name, bit_cast<int32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_INT64: {
+ stream_->ReadVarint64(&buffer64);
+ ow->RenderInt64(field_name, bit_cast<int64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT32: {
+ stream_->ReadVarint32(&buffer32);
+ ow->RenderUint32(field_name, bit_cast<uint32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT64: {
+ stream_->ReadVarint64(&buffer64);
+ ow->RenderUint64(field_name, bit_cast<uint64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SINT32: {
+ stream_->ReadVarint32(&buffer32);
+ ow->RenderInt32(field_name, WireFormatLite::ZigZagDecode32(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SINT64: {
+ stream_->ReadVarint64(&buffer64);
+ ow->RenderInt64(field_name, WireFormatLite::ZigZagDecode64(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SFIXED32: {
+ stream_->ReadLittleEndian32(&buffer32);
+ ow->RenderInt32(field_name, bit_cast<int32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SFIXED64: {
+ stream_->ReadLittleEndian64(&buffer64);
+ ow->RenderInt64(field_name, bit_cast<int64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FIXED32: {
+ stream_->ReadLittleEndian32(&buffer32);
+ ow->RenderUint32(field_name, bit_cast<uint32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FIXED64: {
+ stream_->ReadLittleEndian64(&buffer64);
+ ow->RenderUint64(field_name, bit_cast<uint64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FLOAT: {
+ stream_->ReadLittleEndian32(&buffer32);
+ ow->RenderFloat(field_name, bit_cast<float>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_DOUBLE: {
+ stream_->ReadLittleEndian64(&buffer64);
+ ow->RenderDouble(field_name, bit_cast<double>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_ENUM: {
+ stream_->ReadVarint32(&buffer32);
+
+ // If the field represents an explicit NULL value, render null.
+ if (field->type_url() == kStructNullValueTypeUrl) {
+ ow->RenderNull(field_name);
+ break;
+ }
+
+ // Get the nested enum type for this field.
+ // TODO(skarvaje): Avoid string manipulation. Find ways to speed this
+ // up.
+ const google::protobuf::Enum* en =
+ typeinfo_->GetEnumByTypeUrl(field->type_url());
+ // Lookup the name of the enum, and render that. Skips unknown enums.
+ if (en != NULL) {
+ const google::protobuf::EnumValue* enum_value =
+ FindEnumValueByNumber(*en, buffer32);
+ if (enum_value != NULL) {
+ if (use_lower_camel_for_enums_)
+ ow->RenderString(field_name, ToCamelCase(enum_value->name()));
+ else
+ ow->RenderString(field_name, enum_value->name());
+ }
+ } else {
+ GOOGLE_LOG(INFO) << "Unknown enum skipped: " << field->type_url();
+ }
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_STRING: {
+ stream_->ReadVarint32(&buffer32); // string size.
+ stream_->ReadString(&strbuffer, buffer32);
+ ow->RenderString(field_name, strbuffer);
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_BYTES: {
+ stream_->ReadVarint32(&buffer32); // bytes size.
+ stream_->ReadString(&strbuffer, buffer32);
+ ow->RenderBytes(field_name, strbuffer);
+ break;
+ }
+ default:
+ break;
+ }
+ return Status::OK;
+}
+
+// TODO(skarvaje): Fix this to avoid code duplication.
+const string ProtoStreamObjectSource::ReadFieldValueAsString(
+ const google::protobuf::Field& field) const {
+ string result;
+ switch (field.kind()) {
+ case google::protobuf::Field_Kind_TYPE_BOOL: {
+ uint64 buffer64;
+ stream_->ReadVarint64(&buffer64);
+ result = buffer64 != 0 ? "true" : "false";
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_INT32: {
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32);
+ result = SimpleItoa(bit_cast<int32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_INT64: {
+ uint64 buffer64;
+ stream_->ReadVarint64(&buffer64);
+ result = SimpleItoa(bit_cast<int64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT32: {
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32);
+ result = SimpleItoa(bit_cast<uint32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_UINT64: {
+ uint64 buffer64;
+ stream_->ReadVarint64(&buffer64);
+ result = SimpleItoa(bit_cast<uint64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SINT32: {
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32);
+ result = SimpleItoa(WireFormatLite::ZigZagDecode32(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SINT64: {
+ uint64 buffer64;
+ stream_->ReadVarint64(&buffer64);
+ result = SimpleItoa(WireFormatLite::ZigZagDecode64(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SFIXED32: {
+ uint32 buffer32;
+ stream_->ReadLittleEndian32(&buffer32);
+ result = SimpleItoa(bit_cast<int32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_SFIXED64: {
+ uint64 buffer64;
+ stream_->ReadLittleEndian64(&buffer64);
+ result = SimpleItoa(bit_cast<int64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FIXED32: {
+ uint32 buffer32;
+ stream_->ReadLittleEndian32(&buffer32);
+ result = SimpleItoa(bit_cast<uint32>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FIXED64: {
+ uint64 buffer64;
+ stream_->ReadLittleEndian64(&buffer64);
+ result = SimpleItoa(bit_cast<uint64>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_FLOAT: {
+ uint32 buffer32;
+ stream_->ReadLittleEndian32(&buffer32);
+ result = SimpleFtoa(bit_cast<float>(buffer32));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_DOUBLE: {
+ uint64 buffer64;
+ stream_->ReadLittleEndian64(&buffer64);
+ result = SimpleDtoa(bit_cast<double>(buffer64));
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_ENUM: {
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32);
+ // Get the nested enum type for this field.
+ // TODO(skarvaje): Avoid string manipulation. Find ways to speed this
+ // up.
+ const google::protobuf::Enum* en =
+ typeinfo_->GetEnumByTypeUrl(field.type_url());
+ // Lookup the name of the enum, and render that. Skips unknown enums.
+ if (en != NULL) {
+ const google::protobuf::EnumValue* enum_value =
+ FindEnumValueByNumber(*en, buffer32);
+ if (enum_value != NULL) {
+ result = enum_value->name();
+ }
+ }
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_STRING: {
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32); // string size.
+ stream_->ReadString(&result, buffer32);
+ break;
+ }
+ case google::protobuf::Field_Kind_TYPE_BYTES: {
+ uint32 buffer32;
+ stream_->ReadVarint32(&buffer32); // bytes size.
+ stream_->ReadString(&result, buffer32);
+ break;
+ }
+ default:
+ break;
+ }
+ return result;
+}
+
+// Field is a map if it is a repeated message and it has an option "map_type".
+// TODO(skarvaje): Consider pre-computing the IsMap() into Field directly.
+bool ProtoStreamObjectSource::IsMap(
+ const google::protobuf::Field& field) const {
+ const google::protobuf::Type* field_type =
+ typeinfo_->GetTypeByTypeUrl(field.type_url());
+
+ // TODO(xiaofeng): Unify option names.
+ return field.kind() == google::protobuf::Field_Kind_TYPE_MESSAGE &&
+ (GetBoolOptionOrDefault(field_type->options(),
+ "google.protobuf.MessageOptions.map_entry", false) ||
+ GetBoolOptionOrDefault(field_type->options(), "map_entry", false));
+}
+
+std::pair<int64, int32> ProtoStreamObjectSource::ReadSecondsAndNanos(
+ const google::protobuf::Type& type) const {
+ uint64 seconds = 0;
+ uint32 nanos = 0;
+ uint32 tag = 0;
+ int64 signed_seconds = 0;
+ int32 signed_nanos = 0;
+
+ for (tag = stream_->ReadTag(); tag != 0; tag = stream_->ReadTag()) {
+ const google::protobuf::Field* field = FindAndVerifyField(type, tag);
+ if (field == NULL) {
+ WireFormat::SkipField(stream_, tag, NULL);
+ continue;
+ }
+ // 'seconds' has field number of 1 and 'nanos' has field number 2
+ // //google/protobuf/timestamp.proto & duration.proto
+ if (field->number() == 1) {
+ // read seconds
+ stream_->ReadVarint64(&seconds);
+ signed_seconds = bit_cast<int64>(seconds);
+ } else if (field->number() == 2) {
+ // read nanos
+ stream_->ReadVarint32(&nanos);
+ signed_nanos = bit_cast<int32>(nanos);
+ }
+ }
+ return std::pair<int64, int32>(signed_seconds, signed_nanos);
+}
+
+Status ProtoStreamObjectSource::IncrementRecursionDepth(
+ StringPiece type_name, StringPiece field_name) const {
+ if (++recursion_depth_ > max_recursion_depth_) {
+ return Status(
+ util::error::INVALID_ARGUMENT,
+ StrCat("Message too deep. Max recursion depth reached for type '",
+ type_name, "', field '", field_name, "'"));
+ }
+ return Status::OK;
+}
+
+namespace {
+// TODO(skarvaje): Speed this up by not doing a linear scan.
+const google::protobuf::Field* FindFieldByNumber(
+ const google::protobuf::Type& type, int number) {
+ for (int i = 0; i < type.fields_size(); ++i) {
+ if (type.fields(i).number() == number) {
+ return &type.fields(i);
+ }
+ }
+ return NULL;
+}
+
+// TODO(skarvaje): Replace FieldDescriptor by implementing IsTypePackable()
+// using tech Field.
+bool IsPackable(const google::protobuf::Field& field) {
+ return field.cardinality() ==
+ google::protobuf::Field_Cardinality_CARDINALITY_REPEATED &&
+ google::protobuf::FieldDescriptor::IsTypePackable(
+ static_cast<google::protobuf::FieldDescriptor::Type>(field.kind()));
+}
+
+// TODO(skarvaje): Speed this up by not doing a linear scan.
+const google::protobuf::EnumValue* FindEnumValueByNumber(
+ const google::protobuf::Enum& tech_enum, int number) {
+ for (int i = 0; i < tech_enum.enumvalue_size(); ++i) {
+ const google::protobuf::EnumValue& ev = tech_enum.enumvalue(i);
+ if (ev.number() == number) {
+ return &ev;
+ }
+ }
+ return NULL;
+}
+
+// TODO(skarvaje): Look into optimizing this by not doing computation on
+// double.
+const string FormatNanos(uint32 nanos) {
+ const char* format =
+ (nanos % 1000 != 0) ? "%.9f" : (nanos % 1000000 != 0) ? "%.6f" : "%.3f";
+ string formatted =
+ StringPrintf(format, static_cast<double>(nanos) / kNanosPerSecond);
+ // remove the leading 0 before decimal.
+ return formatted.substr(1);
+}
+} // namespace
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.h
new file mode 100644
index 0000000000..243f85b2db
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource.h
@@ -0,0 +1,302 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTOSTREAM_OBJECTSOURCE_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTOSTREAM_OBJECTSOURCE_H__
+
+#include <functional>
+#include <google/protobuf/stubs/hash.h>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/type.pb.h>
+#include <google/protobuf/util/internal/object_source.h>
+#include <google/protobuf/util/internal/object_writer.h>
+#include <google/protobuf/util/internal/type_info.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/status.h>
+#include <google/protobuf/stubs/statusor.h>
+
+
+namespace google {
+namespace protobuf {
+class Field;
+class Type;
+} // namespace protobuf
+
+
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class TypeInfo;
+
+// An ObjectSource that can parse a stream of bytes as a protocol buffer.
+// Its WriteTo() method can be given an ObjectWriter.
+// This implementation uses a google.protobuf.Type for tag and name lookup.
+// The field names are converted into lower camel-case when writing to the
+// ObjectWriter.
+//
+// Sample usage: (suppose input is: string proto)
+// ArrayInputStream arr_stream(proto.data(), proto.size());
+// CodedInputStream in_stream(&arr_stream);
+// ProtoStreamObjectSource os(&in_stream, /*ServiceTypeInfo*/ typeinfo,
+// <your message google::protobuf::Type>);
+//
+// Status status = os.WriteTo(<some ObjectWriter>);
+class LIBPROTOBUF_EXPORT ProtoStreamObjectSource : public ObjectSource {
+ public:
+ ProtoStreamObjectSource(google::protobuf::io::CodedInputStream* stream,
+ TypeResolver* type_resolver,
+ const google::protobuf::Type& type);
+
+ virtual ~ProtoStreamObjectSource();
+
+ virtual util::Status NamedWriteTo(StringPiece name, ObjectWriter* ow) const;
+
+ // Sets whether or not to use lowerCamelCase casing for enum values. If set to
+ // false, enum values are output without any case conversions.
+ //
+ // For example, if we have an enum:
+ // enum Type {
+ // ACTION_AND_ADVENTURE = 1;
+ // }
+ // Type type = 20;
+ //
+ // And this option is set to true. Then the rendered "type" field will have
+ // the string "actionAndAdventure".
+ // {
+ // ...
+ // "type": "actionAndAdventure",
+ // ...
+ // }
+ //
+ // If set to false, the rendered "type" field will have the string
+ // "ACTION_AND_ADVENTURE".
+ // {
+ // ...
+ // "type": "ACTION_AND_ADVENTURE",
+ // ...
+ // }
+ void set_use_lower_camel_for_enums(bool value) {
+ use_lower_camel_for_enums_ = value;
+ }
+
+ // Sets the max recursion depth of proto message to be deserialized. Proto
+ // messages over this depth will fail to be deserialized.
+ // Default value is 64.
+ void set_max_recursion_depth(int max_depth) {
+ max_recursion_depth_ = max_depth;
+ }
+
+
+ protected:
+ // Writes a proto2 Message to the ObjectWriter. When the given end_tag is
+ // found this method will complete, allowing it to be used for parsing both
+ // nested messages (end with 0) and nested groups (end with group end tag).
+ // The include_start_and_end parameter allows this method to be called when
+ // already inside of an object, and skip calling StartObject and EndObject.
+ virtual util::Status WriteMessage(const google::protobuf::Type& descriptor,
+ StringPiece name, const uint32 end_tag,
+ bool include_start_and_end,
+ ObjectWriter* ow) const;
+
+ private:
+ ProtoStreamObjectSource(google::protobuf::io::CodedInputStream* stream,
+ const TypeInfo* typeinfo,
+ const google::protobuf::Type& type);
+ // Function that renders a well known type with a modified behavior.
+ typedef util::Status (*TypeRenderer)(const ProtoStreamObjectSource*,
+ const google::protobuf::Type&,
+ StringPiece, ObjectWriter*);
+
+ // Looks up a field and verify its consistency with wire type in tag.
+ const google::protobuf::Field* FindAndVerifyField(
+ const google::protobuf::Type& type, uint32 tag) const;
+
+ // TODO(skarvaje): Mark these methods as non-const as they modify internal
+ // state (stream_).
+ //
+ // Renders a repeating field (packed or unpacked).
+ // Returns the next tag after reading all sequential repeating elements. The
+ // caller should use this tag before reading more tags from the stream.
+ util::StatusOr<uint32> RenderList(const google::protobuf::Field* field,
+ StringPiece name, uint32 list_tag,
+ ObjectWriter* ow) const;
+ // Renders a NWP map.
+ // Returns the next tag after reading all map entries. The caller should use
+ // this tag before reading more tags from the stream.
+ util::StatusOr<uint32> RenderMap(const google::protobuf::Field* field,
+ StringPiece name, uint32 list_tag,
+ ObjectWriter* ow) const;
+
+ // Renders a packed repeating field. A packed field is stored as:
+ // {tag length item1 item2 item3} instead of the less efficient
+ // {tag item1 tag item2 tag item3}.
+ util::Status RenderPacked(const google::protobuf::Field* field,
+ ObjectWriter* ow) const;
+
+ // Renders a google.protobuf.Timestamp value to ObjectWriter
+ static util::Status RenderTimestamp(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ // Renders a google.protobuf.Duration value to ObjectWriter
+ static util::Status RenderDuration(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ // Following RenderTYPE functions render well known types in
+ // google/protobuf/wrappers.proto corresponding to TYPE.
+ static util::Status RenderDouble(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderFloat(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderInt64(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderUInt64(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderInt32(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderUInt32(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderBool(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderString(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+ static util::Status RenderBytes(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ // Renders a google.protobuf.Struct to ObjectWriter.
+ static util::Status RenderStruct(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ // Helper to render google.protobuf.Struct's Value fields to ObjectWriter.
+ static util::Status RenderStructValue(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ // Helper to render google.protobuf.Struct's ListValue fields to ObjectWriter.
+ static util::Status RenderStructListValue(
+ const ProtoStreamObjectSource* os, const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ // Render the "Any" type.
+ static util::Status RenderAny(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ // Render the "FieldMask" type.
+ static util::Status RenderFieldMask(const ProtoStreamObjectSource* os,
+ const google::protobuf::Type& type,
+ StringPiece name, ObjectWriter* ow);
+
+ static hash_map<string, TypeRenderer>* renderers_;
+ static void InitRendererMap();
+ static void DeleteRendererMap();
+ static TypeRenderer* FindTypeRenderer(const string& type_url);
+
+ // Renders a field value to the ObjectWriter.
+ util::Status RenderField(const google::protobuf::Field* field,
+ StringPiece field_name, ObjectWriter* ow) const;
+
+ // Same as above but renders all non-message field types. Callers don't call
+ // this function directly. They just use RenderField.
+ util::Status RenderNonMessageField(const google::protobuf::Field* field,
+ StringPiece field_name,
+ ObjectWriter* ow) const;
+
+
+ // Reads field value according to Field spec in 'field' and returns the read
+ // value as string. This only works for primitive datatypes (no message
+ // types).
+ const string ReadFieldValueAsString(
+ const google::protobuf::Field& field) const;
+
+ // Utility function to detect proto maps. The 'field' MUST be repeated.
+ bool IsMap(const google::protobuf::Field& field) const;
+
+ // Utility to read int64 and int32 values from a message type in stream_.
+ // Used for reading google.protobuf.Timestamp and Duration messages.
+ std::pair<int64, int32> ReadSecondsAndNanos(
+ const google::protobuf::Type& type) const;
+
+ // Helper function to check recursion depth and increment it. It will return
+ // Status::OK if the current depth is allowed. Otherwise an error is returned.
+ // type_name and field_name are used for error reporting.
+ util::Status IncrementRecursionDepth(StringPiece type_name,
+ StringPiece field_name) const;
+
+ // Input stream to read from. Ownership rests with the caller.
+ google::protobuf::io::CodedInputStream* stream_;
+
+ // Type information for all the types used in the descriptor. Used to find
+ // google::protobuf::Type of nested messages/enums.
+ const TypeInfo* typeinfo_;
+ // Whether this class owns the typeinfo_ object. If true the typeinfo_ object
+ // should be deleted in the destructor.
+ bool own_typeinfo_;
+
+ // google::protobuf::Type of the message source.
+ const google::protobuf::Type& type_;
+
+
+ // Whether to render enums using lowerCamelCase. Defaults to false.
+ bool use_lower_camel_for_enums_;
+
+ // Tracks current recursion depth.
+ mutable int recursion_depth_;
+
+ // Maximum allowed recursion depth.
+ int max_recursion_depth_;
+
+ // Whether to render unknown fields.
+ bool render_unknown_fields_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(ProtoStreamObjectSource);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTOSTREAM_OBJECTSOURCE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource_test.cc
new file mode 100644
index 0000000000..3f6fdf973f
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectsource_test.cc
@@ -0,0 +1,1007 @@
+// 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.
+
+#include <google/protobuf/util/internal/protostream_objectsource.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <sstream>
+
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/any.pb.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/expecting_objectwriter.h>
+#include <google/protobuf/util/internal/testdata/books.pb.h>
+#include <google/protobuf/util/internal/testdata/field_mask.pb.h>
+#include <google/protobuf/util/internal/type_info_test_helper.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/util/internal/testdata/anys.pb.h>
+#include <google/protobuf/util/internal/testdata/maps.pb.h>
+#include <google/protobuf/util/internal/testdata/struct.pb.h>
+#include <google/protobuf/util/internal/testdata/timestamp_duration.pb.h>
+#include <gtest/gtest.h>
+
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using google::protobuf::Descriptor;
+using google::protobuf::DescriptorPool;
+using google::protobuf::FileDescriptorProto;
+using google::protobuf::Message;
+using google::protobuf::io::ArrayInputStream;
+using google::protobuf::io::CodedInputStream;
+using util::Status;
+using google::protobuf::testing::Author;
+using google::protobuf::testing::BadAuthor;
+using google::protobuf::testing::BadNestedBook;
+using google::protobuf::testing::Book;
+using google::protobuf::testing::Cyclic;
+using google::protobuf::testing::Book_Label;
+using google::protobuf::testing::NestedBook;
+using google::protobuf::testing::PackedPrimitive;
+using google::protobuf::testing::Primitive;
+using google::protobuf::testing::more_author;
+using google::protobuf::testing::maps::MapOut;
+using google::protobuf::testing::maps::MapOutWireFormat;
+using google::protobuf::testing::timestampduration::TimestampDuration;
+using google::protobuf::testing::anys::AnyOut;
+using google::protobuf::testing::anys::AnyM;
+using google::protobuf::testing::FieldMaskTest;
+using google::protobuf::testing::NestedFieldMask;
+using google::protobuf::testing::structs::StructType;
+using ::testing::_;
+
+
+namespace {
+string GetTypeUrl(const Descriptor* descriptor) {
+ return string(kTypeServiceBaseUrl) + "/" + descriptor->full_name();
+}
+} // namespace
+
+class ProtostreamObjectSourceTest
+ : public ::testing::TestWithParam<testing::TypeInfoSource> {
+ protected:
+ ProtostreamObjectSourceTest()
+ : helper_(GetParam()),
+ mock_(),
+ ow_(&mock_),
+ use_lower_camel_for_enums_(false) {
+ helper_.ResetTypeInfo(Book::descriptor());
+ }
+
+ virtual ~ProtostreamObjectSourceTest() {}
+
+ void DoTest(const Message& msg, const Descriptor* descriptor) {
+ Status status = ExecuteTest(msg, descriptor);
+ EXPECT_EQ(Status::OK, status);
+ }
+
+ Status ExecuteTest(const Message& msg, const Descriptor* descriptor) {
+ ostringstream oss;
+ msg.SerializePartialToOstream(&oss);
+ string proto = oss.str();
+ ArrayInputStream arr_stream(proto.data(), proto.size());
+ CodedInputStream in_stream(&arr_stream);
+
+ google::protobuf::scoped_ptr<ProtoStreamObjectSource> os(
+ helper_.NewProtoSource(&in_stream, GetTypeUrl(descriptor)));
+ if (use_lower_camel_for_enums_) os->set_use_lower_camel_for_enums(true);
+ os->set_max_recursion_depth(64);
+ return os->WriteTo(&mock_);
+ }
+
+ void PrepareExpectingObjectWriterForRepeatedPrimitive() {
+ ow_.StartObject("")
+ ->StartList("repFix32")
+ ->RenderUint32("", bit_cast<uint32>(3201))
+ ->RenderUint32("", bit_cast<uint32>(0))
+ ->RenderUint32("", bit_cast<uint32>(3202))
+ ->EndList()
+ ->StartList("repU32")
+ ->RenderUint32("", bit_cast<uint32>(3203))
+ ->RenderUint32("", bit_cast<uint32>(0))
+ ->EndList()
+ ->StartList("repI32")
+ ->RenderInt32("", 0)
+ ->RenderInt32("", 3204)
+ ->RenderInt32("", 3205)
+ ->EndList()
+ ->StartList("repSf32")
+ ->RenderInt32("", 3206)
+ ->RenderInt32("", 0)
+ ->EndList()
+ ->StartList("repS32")
+ ->RenderInt32("", 0)
+ ->RenderInt32("", 3207)
+ ->RenderInt32("", 3208)
+ ->EndList()
+ ->StartList("repFix64")
+ ->RenderUint64("", bit_cast<uint64>(6401LL))
+ ->RenderUint64("", bit_cast<uint64>(0LL))
+ ->EndList()
+ ->StartList("repU64")
+ ->RenderUint64("", bit_cast<uint64>(0LL))
+ ->RenderUint64("", bit_cast<uint64>(6402LL))
+ ->RenderUint64("", bit_cast<uint64>(6403LL))
+ ->EndList()
+ ->StartList("repI64")
+ ->RenderInt64("", 6404L)
+ ->RenderInt64("", 0L)
+ ->EndList()
+ ->StartList("repSf64")
+ ->RenderInt64("", 0L)
+ ->RenderInt64("", 6405L)
+ ->RenderInt64("", 6406L)
+ ->EndList()
+ ->StartList("repS64")
+ ->RenderInt64("", 6407L)
+ ->RenderInt64("", 0L)
+ ->EndList()
+ ->StartList("repFloat")
+ ->RenderFloat("", 0.0f)
+ ->RenderFloat("", 32.1f)
+ ->RenderFloat("", 32.2f)
+ ->EndList()
+ ->StartList("repDouble")
+ ->RenderDouble("", 64.1L)
+ ->RenderDouble("", 0.0L)
+ ->EndList()
+ ->StartList("repBool")
+ ->RenderBool("", true)
+ ->RenderBool("", false)
+ ->EndList()
+ ->EndObject();
+ }
+
+ Primitive PrepareRepeatedPrimitive() {
+ Primitive primitive;
+ primitive.add_rep_fix32(3201);
+ primitive.add_rep_fix32(0);
+ primitive.add_rep_fix32(3202);
+ primitive.add_rep_u32(3203);
+ primitive.add_rep_u32(0);
+ primitive.add_rep_i32(0);
+ primitive.add_rep_i32(3204);
+ primitive.add_rep_i32(3205);
+ primitive.add_rep_sf32(3206);
+ primitive.add_rep_sf32(0);
+ primitive.add_rep_s32(0);
+ primitive.add_rep_s32(3207);
+ primitive.add_rep_s32(3208);
+ primitive.add_rep_fix64(6401L);
+ primitive.add_rep_fix64(0L);
+ primitive.add_rep_u64(0L);
+ primitive.add_rep_u64(6402L);
+ primitive.add_rep_u64(6403L);
+ primitive.add_rep_i64(6404L);
+ primitive.add_rep_i64(0L);
+ primitive.add_rep_sf64(0L);
+ primitive.add_rep_sf64(6405L);
+ primitive.add_rep_sf64(6406L);
+ primitive.add_rep_s64(6407L);
+ primitive.add_rep_s64(0L);
+ primitive.add_rep_float(0.0f);
+ primitive.add_rep_float(32.1f);
+ primitive.add_rep_float(32.2f);
+ primitive.add_rep_double(64.1L);
+ primitive.add_rep_double(0.0);
+ primitive.add_rep_bool(true);
+ primitive.add_rep_bool(false);
+
+ PrepareExpectingObjectWriterForRepeatedPrimitive();
+ return primitive;
+ }
+
+ PackedPrimitive PreparePackedPrimitive() {
+ PackedPrimitive primitive;
+ primitive.add_rep_fix32(3201);
+ primitive.add_rep_fix32(0);
+ primitive.add_rep_fix32(3202);
+ primitive.add_rep_u32(3203);
+ primitive.add_rep_u32(0);
+ primitive.add_rep_i32(0);
+ primitive.add_rep_i32(3204);
+ primitive.add_rep_i32(3205);
+ primitive.add_rep_sf32(3206);
+ primitive.add_rep_sf32(0);
+ primitive.add_rep_s32(0);
+ primitive.add_rep_s32(3207);
+ primitive.add_rep_s32(3208);
+ primitive.add_rep_fix64(6401L);
+ primitive.add_rep_fix64(0L);
+ primitive.add_rep_u64(0L);
+ primitive.add_rep_u64(6402L);
+ primitive.add_rep_u64(6403L);
+ primitive.add_rep_i64(6404L);
+ primitive.add_rep_i64(0L);
+ primitive.add_rep_sf64(0L);
+ primitive.add_rep_sf64(6405L);
+ primitive.add_rep_sf64(6406L);
+ primitive.add_rep_s64(6407L);
+ primitive.add_rep_s64(0L);
+ primitive.add_rep_float(0.0f);
+ primitive.add_rep_float(32.1f);
+ primitive.add_rep_float(32.2f);
+ primitive.add_rep_double(64.1L);
+ primitive.add_rep_double(0.0);
+ primitive.add_rep_bool(true);
+ primitive.add_rep_bool(false);
+
+ PrepareExpectingObjectWriterForRepeatedPrimitive();
+ return primitive;
+ }
+
+ void UseLowerCamelForEnums() { use_lower_camel_for_enums_ = true; }
+
+ testing::TypeInfoTestHelper helper_;
+
+ ::testing::NiceMock<MockObjectWriter> mock_;
+ ExpectingObjectWriter ow_;
+ bool use_lower_camel_for_enums_;
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtostreamObjectSourceTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtostreamObjectSourceTest, EmptyMessage) {
+ Book empty;
+ ow_.StartObject("")->EndObject();
+ DoTest(empty, Book::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, Primitives) {
+ Primitive primitive;
+ primitive.set_fix32(3201);
+ primitive.set_u32(3202);
+ primitive.set_i32(3203);
+ primitive.set_sf32(3204);
+ primitive.set_s32(3205);
+ primitive.set_fix64(6401L);
+ primitive.set_u64(6402L);
+ primitive.set_i64(6403L);
+ primitive.set_sf64(6404L);
+ primitive.set_s64(6405L);
+ primitive.set_str("String Value");
+ primitive.set_bytes("Some Bytes");
+ primitive.set_float_(32.1f);
+ primitive.set_double_(64.1L);
+ primitive.set_bool_(true);
+
+ ow_.StartObject("")
+ ->RenderUint32("fix32", bit_cast<uint32>(3201))
+ ->RenderUint32("u32", bit_cast<uint32>(3202))
+ ->RenderInt32("i32", 3203)
+ ->RenderInt32("sf32", 3204)
+ ->RenderInt32("s32", 3205)
+ ->RenderUint64("fix64", bit_cast<uint64>(6401LL))
+ ->RenderUint64("u64", bit_cast<uint64>(6402LL))
+ ->RenderInt64("i64", 6403L)
+ ->RenderInt64("sf64", 6404L)
+ ->RenderInt64("s64", 6405L)
+ ->RenderString("str", "String Value")
+ ->RenderBytes("bytes", "Some Bytes")
+ ->RenderFloat("float", 32.1f)
+ ->RenderDouble("double", 64.1L)
+ ->RenderBool("bool", true)
+ ->EndObject();
+ DoTest(primitive, Primitive::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, RepeatingPrimitives) {
+ Primitive primitive = PrepareRepeatedPrimitive();
+ primitive.add_rep_str("String One");
+ primitive.add_rep_str("String Two");
+ primitive.add_rep_bytes("Some Bytes");
+
+ ow_.StartList("repStr")
+ ->RenderString("", "String One")
+ ->RenderString("", "String Two")
+ ->EndList()
+ ->StartList("repBytes")
+ ->RenderBytes("", "Some Bytes")
+ ->EndList();
+ DoTest(primitive, Primitive::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, CustomJsonName) {
+ Author author;
+ author.set_id(12345);
+
+ ow_.StartObject("")->RenderUint64("@id", 12345)->EndObject();
+ DoTest(author, Author::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, NestedMessage) {
+ Author* author = new Author();
+ author->set_name("Tolstoy");
+ Book book;
+ book.set_title("My Book");
+ book.set_allocated_author(author);
+
+ ow_.StartObject("")
+ ->RenderString("title", "My Book")
+ ->StartObject("author")
+ ->RenderString("name", "Tolstoy")
+ ->EndObject()
+ ->EndObject();
+ DoTest(book, Book::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, RepeatingField) {
+ Author author;
+ author.set_alive(false);
+ author.set_name("john");
+ author.add_pseudonym("phil");
+ author.add_pseudonym("bob");
+
+ ow_.StartObject("")
+ ->RenderBool("alive", false)
+ ->RenderString("name", "john")
+ ->StartList("pseudonym")
+ ->RenderString("", "phil")
+ ->RenderString("", "bob")
+ ->EndList()
+ ->EndObject();
+ DoTest(author, Author::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, PackedRepeatingFields) {
+ DoTest(PreparePackedPrimitive(), PackedPrimitive::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, NonPackedPackableFieldsActuallyPacked) {
+ // Protostream is packed, but parse with non-packed Primitive.
+ DoTest(PreparePackedPrimitive(), Primitive::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, PackedPackableFieldNotActuallyPacked) {
+ // Protostream is not packed, but parse with PackedPrimitive.
+ DoTest(PrepareRepeatedPrimitive(), PackedPrimitive::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, BadAuthor) {
+ Author author;
+ author.set_alive(false);
+ author.set_name("john");
+ author.set_id(1234L);
+ author.add_pseudonym("phil");
+ author.add_pseudonym("bob");
+
+ ow_.StartObject("")
+ ->StartList("alive")
+ ->RenderBool("", false)
+ ->EndList()
+ ->StartList("name")
+ ->RenderUint64("", static_cast<uint64>('j'))
+ ->RenderUint64("", static_cast<uint64>('o'))
+ ->RenderUint64("", static_cast<uint64>('h'))
+ ->RenderUint64("", static_cast<uint64>('n'))
+ ->EndList()
+ ->RenderString("pseudonym", "phil")
+ ->RenderString("pseudonym", "bob")
+ ->EndObject();
+ // Protostream created with Author, but parsed with BadAuthor.
+ DoTest(author, BadAuthor::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, NestedBookToBadNestedBook) {
+ Book* book = new Book();
+ book->set_length(250);
+ book->set_published(2014L);
+ NestedBook nested;
+ nested.set_allocated_book(book);
+
+ ow_.StartObject("")
+ ->StartList("book")
+ ->RenderUint32("", 24) // tag for field length (3 << 3)
+ ->RenderUint32("", 250)
+ ->RenderUint32("", 32) // tag for field published (4 << 3)
+ ->RenderUint32("", 2014)
+ ->EndList()
+ ->EndObject();
+ // Protostream created with NestedBook, but parsed with BadNestedBook.
+ DoTest(nested, BadNestedBook::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, BadNestedBookToNestedBook) {
+ BadNestedBook nested;
+ nested.add_book(1);
+ nested.add_book(2);
+ nested.add_book(3);
+ nested.add_book(4);
+ nested.add_book(5);
+ nested.add_book(6);
+ nested.add_book(7);
+
+ ow_.StartObject("")->StartObject("book")->EndObject()->EndObject();
+ // Protostream created with BadNestedBook, but parsed with NestedBook.
+ DoTest(nested, NestedBook::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest,
+ LongRepeatedListDoesNotBreakIntoMultipleJsonLists) {
+ Book book;
+
+ int repeat = 10000;
+ for (int i = 0; i < repeat; ++i) {
+ Book_Label* label = book.add_labels();
+ label->set_key(StrCat("i", i));
+ label->set_value(StrCat("v", i));
+ }
+
+ // Make sure StartList and EndList are called exactly once (see b/18227499 for
+ // problems when this doesn't happen)
+ EXPECT_CALL(mock_, StartList(_)).Times(1);
+ EXPECT_CALL(mock_, EndList()).Times(1);
+
+ DoTest(book, Book::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, LowerCamelEnumOutputTest) {
+ Book book;
+ book.set_type(Book::ACTION_AND_ADVENTURE);
+
+ UseLowerCamelForEnums();
+
+ ow_.StartObject("")->RenderString("type", "actionAndAdventure")->EndObject();
+ DoTest(book, Book::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, EnumCaseIsUnchangedByDefault) {
+ Book book;
+ book.set_type(Book::ACTION_AND_ADVENTURE);
+ ow_.StartObject("")
+ ->RenderString("type", "ACTION_AND_ADVENTURE")
+ ->EndObject();
+ DoTest(book, Book::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceTest, CyclicMessageDepthTest) {
+ Cyclic cyclic;
+ cyclic.set_m_int(123);
+
+ Book* book = cyclic.mutable_m_book();
+ book->set_title("book title");
+ Cyclic* current = cyclic.mutable_m_cyclic();
+ Author* current_author = cyclic.add_m_author();
+ for (int i = 0; i < 63; ++i) {
+ Author* next = current_author->add_friend_();
+ next->set_id(i);
+ next->set_name(StrCat("author_name_", i));
+ next->set_alive(true);
+ current_author = next;
+ }
+
+ // Recursive message with depth (65) > max (max is 64).
+ for (int i = 0; i < 64; ++i) {
+ Cyclic* next = current->mutable_m_cyclic();
+ next->set_m_str(StrCat("count_", i));
+ current = next;
+ }
+
+ Status status = ExecuteTest(cyclic, Cyclic::descriptor());
+ EXPECT_EQ(util::error::INVALID_ARGUMENT, status.error_code());
+}
+
+class ProtostreamObjectSourceMapsTest : public ProtostreamObjectSourceTest {
+ protected:
+ ProtostreamObjectSourceMapsTest() {
+ helper_.ResetTypeInfo(MapOut::descriptor());
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtostreamObjectSourceMapsTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+// Tests JSON map.
+//
+// This is the example expected output.
+// {
+// "map1": {
+// "key1": {
+// "foo": "foovalue"
+// },
+// "key2": {
+// "foo": "barvalue"
+// }
+// },
+// "map2": {
+// "nestedself": {
+// "map1": {
+// "nested_key1": {
+// "foo": "nested_foo"
+// }
+// },
+// "bar": "nested_bar_string"
+// }
+// },
+// "map3": {
+// "111": "one one one"
+// },
+// "bar": "top bar"
+// }
+TEST_P(ProtostreamObjectSourceMapsTest, MapsTest) {
+ MapOut out;
+ (*out.mutable_map1())["key1"].set_foo("foovalue");
+ (*out.mutable_map1())["key2"].set_foo("barvalue");
+
+ MapOut* nested_value = &(*out.mutable_map2())["nestedself"];
+ (*nested_value->mutable_map1())["nested_key1"].set_foo("nested_foo");
+ nested_value->set_bar("nested_bar_string");
+
+ (*out.mutable_map3())[111] = "one one one";
+
+ out.set_bar("top bar");
+
+ ow_.StartObject("")
+ ->StartObject("map1")
+ ->StartObject("key1")
+ ->RenderString("foo", "foovalue")
+ ->EndObject()
+ ->StartObject("key2")
+ ->RenderString("foo", "barvalue")
+ ->EndObject()
+ ->StartObject("map2")
+ ->StartObject("nestedself")
+ ->StartObject("map1")
+ ->StartObject("nested_key1")
+ ->RenderString("foo", "nested_foo")
+ ->EndObject()
+ ->EndObject()
+ ->RenderString("bar", "nested_bar_string")
+ ->EndObject()
+ ->EndObject()
+ ->StartObject("map3")
+ ->RenderString("111", "one one one")
+ ->EndObject()
+ ->EndObject()
+ ->RenderString("bar", "top bar")
+ ->EndObject();
+
+ DoTest(out, MapOut::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceMapsTest, MissingKeysTest) {
+ // MapOutWireFormat has the same wire representation with MapOut but uses
+ // repeated message fields to represent map fields so we can intentionally
+ // leave out the key field or the value field of a map entry.
+ MapOutWireFormat out;
+ // Create some map entries without keys. They will be rendered with the
+ // default values ("" for strings, "0" for integers, etc.).
+ // {
+ // "map1": {
+ // "": {
+ // "foo": "foovalue"
+ // }
+ // },
+ // "map2": {
+ // "": {
+ // "map1": {
+ // "nested_key1": {
+ // "foo": "nested_foo"
+ // }
+ // }
+ // }
+ // },
+ // "map3": {
+ // "0": "one one one"
+ // },
+ // "map4": {
+ // "false": "bool"
+ // }
+ // }
+ out.add_map1()->mutable_value()->set_foo("foovalue");
+ MapOut* nested = out.add_map2()->mutable_value();
+ (*nested->mutable_map1())["nested_key1"].set_foo("nested_foo");
+ out.add_map3()->set_value("one one one");
+ out.add_map4()->set_value("bool");
+
+ ow_.StartObject("")
+ ->StartObject("map1")
+ ->StartObject("")
+ ->RenderString("foo", "foovalue")
+ ->EndObject()
+ ->EndObject()
+ ->StartObject("map2")
+ ->StartObject("")
+ ->StartObject("map1")
+ ->StartObject("nested_key1")
+ ->RenderString("foo", "nested_foo")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject()
+ ->EndObject()
+ ->StartObject("map3")
+ ->RenderString("0", "one one one")
+ ->EndObject()
+ ->StartObject("map4")
+ ->RenderString("false", "bool")
+ ->EndObject()
+ ->EndObject();
+
+ DoTest(out, MapOut::descriptor());
+}
+
+class ProtostreamObjectSourceAnysTest : public ProtostreamObjectSourceTest {
+ protected:
+ ProtostreamObjectSourceAnysTest() {
+ helper_.ResetTypeInfo(AnyOut::descriptor(),
+ google::protobuf::Any::descriptor());
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtostreamObjectSourceAnysTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+// Tests JSON any support.
+//
+// This is the example expected output.
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.testing.anys.AnyM"
+// "foo": "foovalue"
+// }
+// }
+TEST_P(ProtostreamObjectSourceAnysTest, BasicAny) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+
+ AnyM m;
+ m.set_foo("foovalue");
+ any->PackFrom(m);
+
+ ow_.StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type",
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM")
+ ->RenderString("foo", "foovalue")
+ ->EndObject()
+ ->EndObject();
+
+ DoTest(out, AnyOut::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceAnysTest, RecursiveAny) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+ any->set_type_url("type.googleapis.com/google.protobuf.Any");
+
+ ::google::protobuf::Any nested_any;
+ nested_any.set_type_url(
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM");
+
+ AnyM m;
+ m.set_foo("foovalue");
+ nested_any.set_value(m.SerializeAsString());
+
+ any->set_value(nested_any.SerializeAsString());
+
+ ow_.StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Any")
+ ->StartObject("value")
+ ->RenderString("@type",
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM")
+ ->RenderString("foo", "foovalue")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+
+ DoTest(out, AnyOut::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceAnysTest, DoubleRecursiveAny) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+ any->set_type_url("type.googleapis.com/google.protobuf.Any");
+
+ ::google::protobuf::Any nested_any;
+ nested_any.set_type_url("type.googleapis.com/google.protobuf.Any");
+
+ ::google::protobuf::Any second_nested_any;
+ second_nested_any.set_type_url(
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM");
+
+ AnyM m;
+ m.set_foo("foovalue");
+ second_nested_any.set_value(m.SerializeAsString());
+ nested_any.set_value(second_nested_any.SerializeAsString());
+ any->set_value(nested_any.SerializeAsString());
+
+ ow_.StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Any")
+ ->StartObject("value")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Any")
+ ->StartObject("value")
+ ->RenderString("@type",
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM")
+ ->RenderString("foo", "foovalue")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+
+ DoTest(out, AnyOut::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceAnysTest, EmptyAnyOutputsEmptyObject) {
+ AnyOut out;
+ out.mutable_any();
+
+ ow_.StartObject("")->StartObject("any")->EndObject()->EndObject();
+
+ DoTest(out, AnyOut::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceAnysTest, EmptyWithTypeAndNoValueOutputsType) {
+ AnyOut out;
+ out.mutable_any()->set_type_url("foo.googleapis.com/my.Type");
+
+ ow_.StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "foo.googleapis.com/my.Type")
+ ->EndObject()
+ ->EndObject();
+
+ DoTest(out, AnyOut::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceAnysTest, MissingTypeUrlError) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+
+ AnyM m;
+ m.set_foo("foovalue");
+ any->set_value(m.SerializeAsString());
+
+ // We start the "AnyOut" part and then fail when we hit the Any object.
+ ow_.StartObject("");
+
+ Status status = ExecuteTest(out, AnyOut::descriptor());
+ EXPECT_EQ(util::error::INTERNAL, status.error_code());
+}
+
+TEST_P(ProtostreamObjectSourceAnysTest, UnknownTypeServiceError) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+ any->set_type_url("foo.googleapis.com/my.own.Type");
+
+ AnyM m;
+ m.set_foo("foovalue");
+ any->set_value(m.SerializeAsString());
+
+ // We start the "AnyOut" part and then fail when we hit the Any object.
+ ow_.StartObject("");
+
+ Status status = ExecuteTest(out, AnyOut::descriptor());
+ EXPECT_EQ(util::error::INTERNAL, status.error_code());
+}
+
+TEST_P(ProtostreamObjectSourceAnysTest, UnknownTypeError) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+ any->set_type_url("type.googleapis.com/unknown.Type");
+
+ AnyM m;
+ m.set_foo("foovalue");
+ any->set_value(m.SerializeAsString());
+
+ // We start the "AnyOut" part and then fail when we hit the Any object.
+ ow_.StartObject("");
+
+ Status status = ExecuteTest(out, AnyOut::descriptor());
+ EXPECT_EQ(util::error::INTERNAL, status.error_code());
+}
+
+class ProtostreamObjectSourceStructTest : public ProtostreamObjectSourceTest {
+ protected:
+ ProtostreamObjectSourceStructTest() {
+ helper_.ResetTypeInfo(StructType::descriptor(),
+ google::protobuf::Struct::descriptor());
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtostreamObjectSourceStructTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+// Tests struct
+//
+// "object": {
+// "k1": 123,
+// "k2": true
+// }
+TEST_P(ProtostreamObjectSourceStructTest, StructRenderSuccess) {
+ StructType out;
+ google::protobuf::Struct* s = out.mutable_object();
+ s->mutable_fields()->operator[]("k1").set_number_value(123);
+ s->mutable_fields()->operator[]("k2").set_bool_value(true);
+
+ ow_.StartObject("")
+ ->StartObject("object")
+ ->RenderDouble("k1", 123)
+ ->RenderBool("k2", true)
+ ->EndObject()
+ ->EndObject();
+
+ DoTest(out, StructType::descriptor());
+}
+
+TEST_P(ProtostreamObjectSourceStructTest, MissingValueSkipsField) {
+ StructType out;
+ google::protobuf::Struct* s = out.mutable_object();
+ s->mutable_fields()->operator[]("k1");
+
+ ow_.StartObject("")->StartObject("object")->EndObject()->EndObject();
+
+ DoTest(out, StructType::descriptor());
+}
+
+class ProtostreamObjectSourceFieldMaskTest
+ : public ProtostreamObjectSourceTest {
+ protected:
+ ProtostreamObjectSourceFieldMaskTest() {
+ helper_.ResetTypeInfo(FieldMaskTest::descriptor(),
+ google::protobuf::FieldMask::descriptor());
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtostreamObjectSourceFieldMaskTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtostreamObjectSourceFieldMaskTest, FieldMaskRenderSuccess) {
+ FieldMaskTest out;
+ out.set_id("1");
+ out.mutable_single_mask()->add_paths("path1");
+ out.mutable_single_mask()->add_paths("snake_case_path2");
+ ::google::protobuf::FieldMask* mask = out.add_repeated_mask();
+ mask->add_paths("path3");
+ mask = out.add_repeated_mask();
+ mask->add_paths("snake_case_path4");
+ mask->add_paths("path5");
+ NestedFieldMask* nested = out.add_nested_mask();
+ nested->set_data("data");
+ nested->mutable_single_mask()->add_paths("nested.path1");
+ nested->mutable_single_mask()->add_paths("nested_field.snake_case_path2");
+ mask = nested->add_repeated_mask();
+ mask->add_paths("nested_field.path3");
+ mask->add_paths("nested.snake_case_path4");
+ mask = nested->add_repeated_mask();
+ mask->add_paths("nested.path5");
+ mask = nested->add_repeated_mask();
+ mask->add_paths(
+ "snake_case.map_field[\"map_key_should_be_ignored\"].nested_snake_case."
+ "map_field[\"map_key_sho\\\"uld_be_ignored\"]");
+
+ ow_.StartObject("")
+ ->RenderString("id", "1")
+ ->RenderString("singleMask", "path1,snakeCasePath2")
+ ->StartList("repeatedMask")
+ ->RenderString("", "path3")
+ ->RenderString("", "snakeCasePath4,path5")
+ ->EndList()
+ ->StartList("nestedMask")
+ ->StartObject("")
+ ->RenderString("data", "data")
+ ->RenderString("singleMask", "nested.path1,nestedField.snakeCasePath2")
+ ->StartList("repeatedMask")
+ ->RenderString("", "nestedField.path3,nested.snakeCasePath4")
+ ->RenderString("", "nested.path5")
+ ->RenderString("",
+ "snakeCase.mapField[\"map_key_should_be_ignored\"]."
+ "nestedSnakeCase.mapField[\"map_key_sho\\\"uld_be_"
+ "ignored\"]")
+ ->EndList()
+ ->EndObject()
+ ->EndList()
+ ->EndObject();
+
+ DoTest(out, FieldMaskTest::descriptor());
+}
+
+class ProtostreamObjectSourceTimestampTest
+ : public ProtostreamObjectSourceTest {
+ protected:
+ ProtostreamObjectSourceTimestampTest() {
+ helper_.ResetTypeInfo(TimestampDuration::descriptor());
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtostreamObjectSourceTimestampTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtostreamObjectSourceTimestampTest, InvalidTimestampBelowMinTest) {
+ TimestampDuration out;
+ google::protobuf::Timestamp* ts = out.mutable_ts();
+ // Min allowed seconds - 1
+ ts->set_seconds(kTimestampMinSeconds - 1);
+ ow_.StartObject("");
+
+ Status status = ExecuteTest(out, TimestampDuration::descriptor());
+ EXPECT_EQ(util::error::INTERNAL, status.error_code());
+}
+
+TEST_P(ProtostreamObjectSourceTimestampTest, InvalidTimestampAboveMaxTest) {
+ TimestampDuration out;
+ google::protobuf::Timestamp* ts = out.mutable_ts();
+ // Max allowed seconds + 1
+ ts->set_seconds(kTimestampMaxSeconds + 1);
+ ow_.StartObject("");
+
+ Status status = ExecuteTest(out, TimestampDuration::descriptor());
+ EXPECT_EQ(util::error::INTERNAL, status.error_code());
+}
+
+TEST_P(ProtostreamObjectSourceTimestampTest, InvalidDurationBelowMinTest) {
+ TimestampDuration out;
+ google::protobuf::Duration* dur = out.mutable_dur();
+ // Min allowed seconds - 1
+ dur->set_seconds(kDurationMinSeconds - 1);
+ ow_.StartObject("");
+
+ Status status = ExecuteTest(out, TimestampDuration::descriptor());
+ EXPECT_EQ(util::error::INTERNAL, status.error_code());
+}
+
+TEST_P(ProtostreamObjectSourceTimestampTest, InvalidDurationAboveMaxTest) {
+ TimestampDuration out;
+ google::protobuf::Duration* dur = out.mutable_dur();
+ // Min allowed seconds + 1
+ dur->set_seconds(kDurationMaxSeconds + 1);
+ ow_.StartObject("");
+
+ Status status = ExecuteTest(out, TimestampDuration::descriptor());
+ EXPECT_EQ(util::error::INTERNAL, status.error_code());
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.cc
new file mode 100644
index 0000000000..1825f5569e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.cc
@@ -0,0 +1,1215 @@
+// 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.
+
+#include <google/protobuf/util/internal/protostream_objectwriter.h>
+
+#include <functional>
+#include <stack>
+
+#include <google/protobuf/stubs/once.h>
+#include <google/protobuf/stubs/time.h>
+#include <google/protobuf/wire_format_lite.h>
+#include <google/protobuf/util/internal/field_mask_utility.h>
+#include <google/protobuf/util/internal/object_location_tracker.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/statusor.h>
+
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using google::protobuf::internal::WireFormatLite;
+using util::error::INVALID_ARGUMENT;
+using util::Status;
+using util::StatusOr;
+
+
+ProtoStreamObjectWriter::ProtoStreamObjectWriter(
+ TypeResolver* type_resolver, const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener,
+ const ProtoStreamObjectWriter::Options& options)
+ : ProtoWriter(type_resolver, type, output, listener),
+ master_type_(type),
+ current_(NULL),
+ options_(options) {
+ set_ignore_unknown_fields(options_.ignore_unknown_fields);
+}
+
+ProtoStreamObjectWriter::ProtoStreamObjectWriter(
+ const TypeInfo* typeinfo, const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener)
+ : ProtoWriter(typeinfo, type, output, listener),
+ master_type_(type),
+ current_(NULL),
+ options_(ProtoStreamObjectWriter::Options::Defaults()) {}
+
+ProtoStreamObjectWriter::~ProtoStreamObjectWriter() {
+ if (current_ == NULL) return;
+ // Cleanup explicitly in order to avoid destructor stack overflow when input
+ // is deeply nested.
+ // Cast to BaseElement to avoid doing additional checks (like missing fields)
+ // during pop().
+ google::protobuf::scoped_ptr<BaseElement> element(
+ static_cast<BaseElement*>(current_.get())->pop<BaseElement>());
+ while (element != NULL) {
+ element.reset(element->pop<BaseElement>());
+ }
+}
+
+namespace {
+// Utility method to split a string representation of Timestamp or Duration and
+// return the parts.
+void SplitSecondsAndNanos(StringPiece input, StringPiece* seconds,
+ StringPiece* nanos) {
+ size_t idx = input.rfind('.');
+ if (idx != string::npos) {
+ *seconds = input.substr(0, idx);
+ *nanos = input.substr(idx + 1);
+ } else {
+ *seconds = input;
+ *nanos = StringPiece();
+ }
+}
+
+Status GetNanosFromStringPiece(StringPiece s_nanos,
+ const char* parse_failure_message,
+ const char* exceeded_limit_message,
+ int32* nanos) {
+ *nanos = 0;
+
+ // Count the number of leading 0s and consume them.
+ int num_leading_zeros = 0;
+ while (s_nanos.Consume("0")) {
+ num_leading_zeros++;
+ }
+ int32 i_nanos = 0;
+ // 's_nanos' contains fractional seconds -- i.e. 'nanos' is equal to
+ // "0." + s_nanos.ToString() seconds. An int32 is used for the
+ // conversion to 'nanos', rather than a double, so that there is no
+ // loss of precision.
+ if (!s_nanos.empty() && !safe_strto32(s_nanos.ToString(), &i_nanos)) {
+ return Status(INVALID_ARGUMENT, parse_failure_message);
+ }
+ if (i_nanos > kNanosPerSecond || i_nanos < 0) {
+ return Status(INVALID_ARGUMENT, exceeded_limit_message);
+ }
+ // s_nanos should only have digits. No whitespace.
+ if (s_nanos.find_first_not_of("0123456789") != StringPiece::npos) {
+ return Status(INVALID_ARGUMENT, parse_failure_message);
+ }
+
+ if (i_nanos > 0) {
+ // 'scale' is the number of digits to the right of the decimal
+ // point in "0." + s_nanos.ToString()
+ int32 scale = num_leading_zeros + s_nanos.size();
+ // 'conversion' converts i_nanos into nanoseconds.
+ // conversion = kNanosPerSecond / static_cast<int32>(std::pow(10, scale))
+ // For efficiency, we precompute the conversion factor.
+ int32 conversion = 0;
+ switch (scale) {
+ case 1:
+ conversion = 100000000;
+ break;
+ case 2:
+ conversion = 10000000;
+ break;
+ case 3:
+ conversion = 1000000;
+ break;
+ case 4:
+ conversion = 100000;
+ break;
+ case 5:
+ conversion = 10000;
+ break;
+ case 6:
+ conversion = 1000;
+ break;
+ case 7:
+ conversion = 100;
+ break;
+ case 8:
+ conversion = 10;
+ break;
+ case 9:
+ conversion = 1;
+ break;
+ default:
+ return Status(INVALID_ARGUMENT, exceeded_limit_message);
+ }
+ *nanos = i_nanos * conversion;
+ }
+
+ return Status::OK;
+}
+
+} // namespace
+
+ProtoStreamObjectWriter::AnyWriter::AnyWriter(ProtoStreamObjectWriter* parent)
+ : parent_(parent),
+ ow_(),
+ invalid_(false),
+ data_(),
+ output_(&data_),
+ depth_(0),
+ is_well_known_type_(false),
+ well_known_type_render_(NULL) {}
+
+ProtoStreamObjectWriter::AnyWriter::~AnyWriter() {}
+
+void ProtoStreamObjectWriter::AnyWriter::StartObject(StringPiece name) {
+ ++depth_;
+ // If an object writer is absent, that means we have not called StartAny()
+ // before reaching here. This is an invalid state. StartAny() gets called
+ // whenever we see an "@type" being rendered (see AnyWriter::RenderDataPiece).
+ if (ow_ == NULL) {
+ // Make sure we are not already in an invalid state. This avoids making
+ // multiple unnecessary InvalidValue calls.
+ if (!invalid_) {
+ parent_->InvalidValue("Any",
+ StrCat("Missing or invalid @type for any field in ",
+ parent_->master_type_.name()));
+ invalid_ = true;
+ }
+ } else if (is_well_known_type_ && depth_ == 1) {
+ // For well-known types, the only other field besides "@type" should be a
+ // "value" field.
+ if (name != "value" && !invalid_) {
+ parent_->InvalidValue("Any",
+ "Expect a \"value\" field for well-known types.");
+ invalid_ = true;
+ }
+ ow_->StartObject("");
+ } else {
+ // Forward the call to the child writer if:
+ // 1. the type is not a well-known type.
+ // 2. or, we are in a nested Any, Struct, or Value object.
+ ow_->StartObject(name);
+ }
+}
+
+bool ProtoStreamObjectWriter::AnyWriter::EndObject() {
+ --depth_;
+ // As long as depth_ >= 0, we know we haven't reached the end of Any.
+ // Propagate these EndObject() calls to the contained ow_. For regular
+ // message types, we propagate the end of Any as well.
+ if (ow_ != NULL && (depth_ >= 0 || !is_well_known_type_)) {
+ ow_->EndObject();
+ }
+ // A negative depth_ implies that we have reached the end of Any
+ // object. Now we write out its contents.
+ if (depth_ < 0) {
+ WriteAny();
+ return false;
+ }
+ return true;
+}
+
+void ProtoStreamObjectWriter::AnyWriter::StartList(StringPiece name) {
+ ++depth_;
+ // We expect ow_ to be present as this call only makes sense inside an Any.
+ if (ow_ == NULL) {
+ if (!invalid_) {
+ parent_->InvalidValue("Any",
+ StrCat("Missing or invalid @type for any field in ",
+ parent_->master_type_.name()));
+ invalid_ = true;
+ }
+ } else if (is_well_known_type_ && depth_ == 1) {
+ if (name != "value" && !invalid_) {
+ parent_->InvalidValue("Any",
+ "Expect a \"value\" field for well-known types.");
+ invalid_ = true;
+ }
+ ow_->StartList("");
+ } else {
+ ow_->StartList(name);
+ }
+}
+
+void ProtoStreamObjectWriter::AnyWriter::EndList() {
+ --depth_;
+ if (depth_ < 0) {
+ GOOGLE_LOG(DFATAL) << "Mismatched EndList found, should not be possible";
+ depth_ = 0;
+ }
+ // We don't write an error on the close, only on the open
+ if (ow_ != NULL) {
+ ow_->EndList();
+ }
+}
+
+void ProtoStreamObjectWriter::AnyWriter::RenderDataPiece(
+ StringPiece name, const DataPiece& value) {
+ // Start an Any only at depth_ 0. Other RenderDataPiece calls with "@type"
+ // should go to the contained ow_ as they indicate nested Anys.
+ if (depth_ == 0 && ow_ == NULL && name == "@type") {
+ StartAny(value);
+ } else if (ow_ == NULL) {
+ if (!invalid_) {
+ parent_->InvalidValue("Any",
+ StrCat("Missing or invalid @type for any field in ",
+ parent_->master_type_.name()));
+ invalid_ = true;
+ }
+ } else if (depth_ == 0 && is_well_known_type_) {
+ if (name != "value" && !invalid_) {
+ parent_->InvalidValue("Any",
+ "Expect a \"value\" field for well-known types.");
+ invalid_ = true;
+ }
+ if (well_known_type_render_ == NULL) {
+ // Only Any and Struct don't have a special type render but both of
+ // them expect a JSON object (i.e., a StartObject() call).
+ if (!invalid_) {
+ parent_->InvalidValue("Any", "Expect a JSON object.");
+ invalid_ = true;
+ }
+ } else {
+ ow_->ProtoWriter::StartObject("");
+ Status status = (*well_known_type_render_)(ow_.get(), value);
+ if (!status.ok()) ow_->InvalidValue("Any", status.error_message());
+ ow_->ProtoWriter::EndObject();
+ }
+ } else {
+ ow_->RenderDataPiece(name, value);
+ }
+}
+
+void ProtoStreamObjectWriter::AnyWriter::StartAny(const DataPiece& value) {
+ // Figure out the type url. This is a copy-paste from WriteString but we also
+ // need the value, so we can't just call through to that.
+ if (value.type() == DataPiece::TYPE_STRING) {
+ type_url_ = value.str().ToString();
+ } else {
+ StatusOr<string> s = value.ToString();
+ if (!s.ok()) {
+ parent_->InvalidValue("String", s.status().error_message());
+ invalid_ = true;
+ return;
+ }
+ type_url_ = s.ValueOrDie();
+ }
+ // Resolve the type url, and report an error if we failed to resolve it.
+ StatusOr<const google::protobuf::Type*> resolved_type =
+ parent_->typeinfo()->ResolveTypeUrl(type_url_);
+ if (!resolved_type.ok()) {
+ parent_->InvalidValue("Any", resolved_type.status().error_message());
+ invalid_ = true;
+ return;
+ }
+ // At this point, type is never null.
+ const google::protobuf::Type* type = resolved_type.ValueOrDie();
+
+ well_known_type_render_ = FindTypeRenderer(type_url_);
+ if (well_known_type_render_ != NULL ||
+ // Explicitly list Any and Struct here because they don't have a
+ // custom renderer.
+ type->name() == kAnyType || type->name() == kStructType) {
+ is_well_known_type_ = true;
+ }
+
+ // Create our object writer and initialize it with the first StartObject
+ // call.
+ ow_.reset(new ProtoStreamObjectWriter(parent_->typeinfo(), *type, &output_,
+ parent_->listener()));
+
+ // Don't call StartObject() for well-known types yet. Depending on the
+ // type of actual data, we may not need to call StartObject(). For
+ // example:
+ // {
+ // "@type": "type.googleapis.com/google.protobuf.Value",
+ // "value": [1, 2, 3],
+ // }
+ // With the above JSON representation, we will only call StartList() on the
+ // contained ow_.
+ if (!is_well_known_type_) {
+ ow_->StartObject("");
+ }
+}
+
+void ProtoStreamObjectWriter::AnyWriter::WriteAny() {
+ if (ow_ == NULL) {
+ // If we had no object writer, we never got any content, so just return
+ // immediately, which is equivalent to writing an empty Any.
+ return;
+ }
+ // Render the type_url and value fields directly to the stream.
+ // type_url has tag 1 and value has tag 2.
+ WireFormatLite::WriteString(1, type_url_, parent_->stream());
+ if (!data_.empty()) {
+ WireFormatLite::WriteBytes(2, data_, parent_->stream());
+ }
+}
+
+ProtoStreamObjectWriter::Item::Item(ProtoStreamObjectWriter* enclosing,
+ ItemType item_type, bool is_placeholder,
+ bool is_list)
+ : BaseElement(NULL),
+ ow_(enclosing),
+ any_(),
+ item_type_(item_type),
+ is_placeholder_(is_placeholder),
+ is_list_(is_list) {
+ if (item_type_ == ANY) {
+ any_.reset(new AnyWriter(ow_));
+ }
+ if (item_type == MAP) {
+ map_keys_.reset(new hash_set<string>);
+ }
+}
+
+ProtoStreamObjectWriter::Item::Item(ProtoStreamObjectWriter::Item* parent,
+ ItemType item_type, bool is_placeholder,
+ bool is_list)
+ : BaseElement(parent),
+ ow_(this->parent()->ow_),
+ any_(),
+ item_type_(item_type),
+ is_placeholder_(is_placeholder),
+ is_list_(is_list) {
+ if (item_type == ANY) {
+ any_.reset(new AnyWriter(ow_));
+ }
+ if (item_type == MAP) {
+ map_keys_.reset(new hash_set<string>);
+ }
+}
+
+bool ProtoStreamObjectWriter::Item::InsertMapKeyIfNotPresent(
+ StringPiece map_key) {
+ return InsertIfNotPresent(map_keys_.get(), map_key.ToString());
+}
+
+ProtoStreamObjectWriter* ProtoStreamObjectWriter::StartObject(
+ StringPiece name) {
+ if (invalid_depth() > 0) {
+ IncrementInvalidDepth();
+ return this;
+ }
+
+ // Starting the root message. Create the root Item and return.
+ // ANY message type does not need special handling, just set the ItemType
+ // to ANY.
+ if (current_ == NULL) {
+ ProtoWriter::StartObject(name);
+ current_.reset(new Item(
+ this, master_type_.name() == kAnyType ? Item::ANY : Item::MESSAGE,
+ false, false));
+
+ // If master type is a special type that needs extra values to be written to
+ // stream, we write those values.
+ if (master_type_.name() == kStructType) {
+ // Struct has a map<string, Value> field called "fields".
+ // https://github.com/google/protobuf/blob/master/src/google/protobuf/struct.proto
+ // "fields": [
+ Push("fields", Item::MAP, true, true);
+ return this;
+ }
+
+ if (master_type_.name() == kStructValueType) {
+ // We got a StartObject call with google.protobuf.Value field. The only
+ // object within that type is a struct type. So start a struct.
+ //
+ // The struct field in Value type is named "struct_value"
+ // https://github.com/google/protobuf/blob/master/src/google/protobuf/struct.proto
+ // Also start the map field "fields" within the struct.
+ // "struct_value": {
+ // "fields": [
+ Push("struct_value", Item::MESSAGE, true, false);
+ Push("fields", Item::MAP, true, true);
+ return this;
+ }
+
+ if (master_type_.name() == kStructListValueType) {
+ InvalidValue(kStructListValueType,
+ "Cannot start root message with ListValue.");
+ }
+
+ return this;
+ }
+
+ // Send all ANY events to AnyWriter.
+ if (current_->IsAny()) {
+ current_->any()->StartObject(name);
+ return this;
+ }
+
+ // If we are within a map, we render name as keys and send StartObject to the
+ // value field.
+ if (current_->IsMap()) {
+ if (!ValidMapKey(name)) {
+ IncrementInvalidDepth();
+ return this;
+ }
+
+ // Map is a repeated field of message type with a "key" and a "value" field.
+ // https://developers.google.com/protocol-buffers/docs/proto3?hl=en#maps
+ // message MapFieldEntry {
+ // key_type key = 1;
+ // value_type value = 2;
+ // }
+ //
+ // repeated MapFieldEntry map_field = N;
+ //
+ // That means, we render the following element within a list (hence no
+ // name):
+ // { "key": "<name>", "value": {
+ Push("", Item::MESSAGE, false, false);
+ ProtoWriter::RenderDataPiece("key",
+ DataPiece(name, use_strict_base64_decoding()));
+ Push("value", Item::MESSAGE, true, false);
+
+ // Make sure we are valid so far after starting map fields.
+ if (invalid_depth() > 0) return this;
+
+ // If top of stack is g.p.Struct type, start the struct the map field within
+ // it.
+ if (element() != NULL && IsStruct(*element()->parent_field())) {
+ // Render "fields": [
+ Push("fields", Item::MAP, true, true);
+ return this;
+ }
+
+ // If top of stack is g.p.Value type, start the Struct within it.
+ if (element() != NULL && IsStructValue(*element()->parent_field())) {
+ // Render
+ // "struct_value": {
+ // "fields": [
+ Push("struct_value", Item::MESSAGE, true, false);
+ Push("fields", Item::MAP, true, true);
+ }
+ return this;
+ }
+
+ const google::protobuf::Field* field = BeginNamed(name, false);
+ if (field == NULL) return this;
+
+ if (IsStruct(*field)) {
+ // Start a struct object.
+ // Render
+ // "<name>": {
+ // "fields": {
+ Push(name, Item::MESSAGE, false, false);
+ Push("fields", Item::MAP, true, true);
+ return this;
+ }
+
+ if (IsStructValue(*field)) {
+ // We got a StartObject call with google.protobuf.Value field. The only
+ // object within that type is a struct type. So start a struct.
+ // Render
+ // "<name>": {
+ // "struct_value": {
+ // "fields": {
+ Push(name, Item::MESSAGE, false, false);
+ Push("struct_value", Item::MESSAGE, true, false);
+ Push("fields", Item::MAP, true, true);
+ return this;
+ }
+
+ if (IsMap(*field)) {
+ // Begin a map. A map is triggered by a StartObject() call if the current
+ // field has a map type.
+ // A map type is always repeated, hence set is_list to true.
+ // Render
+ // "<name>": [
+ Push(name, Item::MAP, false, true);
+ return this;
+ }
+
+ // A regular message type. Pass it directly to ProtoWriter.
+ // Render
+ // "<name>": {
+ Push(name, IsAny(*field) ? Item::ANY : Item::MESSAGE, false, false);
+ return this;
+}
+
+ProtoStreamObjectWriter* ProtoStreamObjectWriter::EndObject() {
+ if (invalid_depth() > 0) {
+ DecrementInvalidDepth();
+ return this;
+ }
+
+ if (current_ == NULL) return this;
+
+ if (current_->IsAny()) {
+ if (current_->any()->EndObject()) return this;
+ }
+
+ Pop();
+
+ return this;
+}
+
+ProtoStreamObjectWriter* ProtoStreamObjectWriter::StartList(StringPiece name) {
+ if (invalid_depth() > 0) {
+ IncrementInvalidDepth();
+ return this;
+ }
+
+ // Since we cannot have a top-level repeated item in protobuf, the only way
+ // this is valid is if we start a special type google.protobuf.ListValue or
+ // google.protobuf.Value.
+ if (current_ == NULL) {
+ if (!name.empty()) {
+ InvalidName(name, "Root element should not be named.");
+ IncrementInvalidDepth();
+ return this;
+ }
+
+ // If master type is a special type that needs extra values to be written to
+ // stream, we write those values.
+ if (master_type_.name() == kStructValueType) {
+ // We got a StartList with google.protobuf.Value master type. This means
+ // we have to start the "list_value" within google.protobuf.Value.
+ //
+ // See
+ // https://github.com/google/protobuf/blob/master/src/google/protobuf/struct.proto
+ //
+ // Render
+ // "<name>": {
+ // "list_value": {
+ // "values": [ // Start this list.
+ ProtoWriter::StartObject(name);
+ current_.reset(new Item(this, Item::MESSAGE, false, false));
+ Push("list_value", Item::MESSAGE, true, false);
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+
+ if (master_type_.name() == kStructListValueType) {
+ // We got a StartList with google.protobuf.ListValue master type. This
+ // means we have to start the "values" within google.protobuf.ListValue.
+ //
+ // Render
+ // "<name>": {
+ // "values": [ // Start this list.
+ ProtoWriter::StartObject(name);
+ current_.reset(new Item(this, Item::MESSAGE, false, false));
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+
+ // Send the event to ProtoWriter so proper errors can be reported.
+ //
+ // Render a regular list:
+ // "<name>": [
+ ProtoWriter::StartList(name);
+ current_.reset(new Item(this, Item::MESSAGE, false, true));
+ return this;
+ }
+
+ if (current_->IsAny()) {
+ current_->any()->StartList(name);
+ return this;
+ }
+
+ // If the top of stack is a map, we are starting a list value within a map.
+ // Since map does not allow repeated values, this can only happen when the map
+ // value is of a special type that renders a list in JSON. These can be one
+ // of 3 cases:
+ // i. We are rendering a list value within google.protobuf.Struct
+ // ii. We are rendering a list value within google.protobuf.Value
+ // iii. We are rendering a list value with type google.protobuf.ListValue.
+ if (current_->IsMap()) {
+ if (!ValidMapKey(name)) {
+ IncrementInvalidDepth();
+ return this;
+ }
+
+ // Start the repeated map entry object.
+ // Render
+ // { "key": "<name>", "value": {
+ Push("", Item::MESSAGE, false, false);
+ ProtoWriter::RenderDataPiece("key",
+ DataPiece(name, use_strict_base64_decoding()));
+ Push("value", Item::MESSAGE, true, false);
+
+ // Make sure we are valid after pushing all above items.
+ if (invalid_depth() > 0) return this;
+
+ // case i and ii above. Start "list_value" field within g.p.Value
+ if (element() != NULL && element()->parent_field() != NULL) {
+ // Render
+ // "list_value": {
+ // "values": [ // Start this list
+ if (IsStructValue(*element()->parent_field())) {
+ Push("list_value", Item::MESSAGE, true, false);
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+
+ // Render
+ // "values": [
+ if (IsStructListValue(*element()->parent_field())) {
+ // case iii above. Bind directly to g.p.ListValue
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+ }
+
+ // Report an error.
+ InvalidValue("Map", StrCat("Cannot have repeated items ('", name,
+ "') within a map."));
+ return this;
+ }
+
+ // When name is empty and stack is not empty, we are rendering an item within
+ // a list.
+ if (name.empty()) {
+ if (element() != NULL && element()->parent_field() != NULL) {
+ if (IsStructValue(*element()->parent_field())) {
+ // Since it is g.p.Value, we bind directly to the list_value.
+ // Render
+ // { // g.p.Value item within the list
+ // "list_value": {
+ // "values": [
+ Push("", Item::MESSAGE, false, false);
+ Push("list_value", Item::MESSAGE, true, false);
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+
+ if (IsStructListValue(*element()->parent_field())) {
+ // Since it is g.p.ListValue, we bind to it directly.
+ // Render
+ // { // g.p.ListValue item within the list
+ // "values": [
+ Push("", Item::MESSAGE, false, false);
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+ }
+
+ // Pass the event to underlying ProtoWriter.
+ Push(name, Item::MESSAGE, false, true);
+ return this;
+ }
+
+ // name is not empty
+ const google::protobuf::Field* field = Lookup(name);
+ if (field == NULL) {
+ IncrementInvalidDepth();
+ return this;
+ }
+
+ if (IsStructValue(*field)) {
+ // If g.p.Value is repeated, start that list. Otherwise, start the
+ // "list_value" within it.
+ if (IsRepeated(*field)) {
+ // Render it just like a regular repeated field.
+ // "<name>": [
+ Push(name, Item::MESSAGE, false, true);
+ return this;
+ }
+
+ // Start the "list_value" field.
+ // Render
+ // "<name>": {
+ // "list_value": {
+ // "values": [
+ Push(name, Item::MESSAGE, false, false);
+ Push("list_value", Item::MESSAGE, true, false);
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+
+ if (IsStructListValue(*field)) {
+ // If g.p.ListValue is repeated, start that list. Otherwise, start the
+ // "values" within it.
+ if (IsRepeated(*field)) {
+ // Render it just like a regular repeated field.
+ // "<name>": [
+ Push(name, Item::MESSAGE, false, true);
+ return this;
+ }
+
+ // Start the "values" field within g.p.ListValue.
+ // Render
+ // "<name>": {
+ // "values": [
+ Push(name, Item::MESSAGE, false, false);
+ Push("values", Item::MESSAGE, true, true);
+ return this;
+ }
+
+ // If we are here, the field should be repeated. Report an error otherwise.
+ if (!IsRepeated(*field)) {
+ IncrementInvalidDepth();
+ InvalidName(name, "Proto field is not repeating, cannot start list.");
+ return this;
+ }
+
+ if (IsMap(*field)) {
+ InvalidValue("Map",
+ StrCat("Cannot bind a list to map for field '", name, "'."));
+ IncrementInvalidDepth();
+ return this;
+ }
+
+ // Pass the event to ProtoWriter.
+ // Render
+ // "<name>": [
+ Push(name, Item::MESSAGE, false, true);
+ return this;
+}
+
+ProtoStreamObjectWriter* ProtoStreamObjectWriter::EndList() {
+ if (invalid_depth() > 0) {
+ DecrementInvalidDepth();
+ return this;
+ }
+
+ if (current_ == NULL) return this;
+
+ if (current_->IsAny()) {
+ current_->any()->EndList();
+ return this;
+ }
+
+ Pop();
+ return this;
+}
+
+Status ProtoStreamObjectWriter::RenderStructValue(ProtoStreamObjectWriter* ow,
+ const DataPiece& data) {
+ string struct_field_name;
+ switch (data.type()) {
+ // Our JSON parser parses numbers as either int64, uint64, or double.
+ case DataPiece::TYPE_INT64: {
+ // If the option to treat integers as strings is set, then render them as
+ // strings. Otherwise, fallback to rendering them as double.
+ if (ow->options_.struct_integers_as_strings) {
+ StatusOr<int64> int_value = data.ToInt64();
+ if (int_value.ok()) {
+ ow->ProtoWriter::RenderDataPiece(
+ "string_value",
+ DataPiece(SimpleItoa(int_value.ValueOrDie()), true));
+ return Status::OK;
+ }
+ }
+ struct_field_name = "number_value";
+ break;
+ }
+ case DataPiece::TYPE_UINT64: {
+ // If the option to treat integers as strings is set, then render them as
+ // strings. Otherwise, fallback to rendering them as double.
+ if (ow->options_.struct_integers_as_strings) {
+ StatusOr<uint64> int_value = data.ToUint64();
+ if (int_value.ok()) {
+ ow->ProtoWriter::RenderDataPiece(
+ "string_value",
+ DataPiece(SimpleItoa(int_value.ValueOrDie()), true));
+ return Status::OK;
+ }
+ }
+ struct_field_name = "number_value";
+ break;
+ }
+ case DataPiece::TYPE_DOUBLE: {
+ struct_field_name = "number_value";
+ break;
+ }
+ case DataPiece::TYPE_STRING: {
+ struct_field_name = "string_value";
+ break;
+ }
+ case DataPiece::TYPE_BOOL: {
+ struct_field_name = "bool_value";
+ break;
+ }
+ case DataPiece::TYPE_NULL: {
+ struct_field_name = "null_value";
+ break;
+ }
+ default: {
+ return Status(INVALID_ARGUMENT,
+ "Invalid struct data type. Only number, string, boolean or "
+ "null values are supported.");
+ }
+ }
+ ow->ProtoWriter::RenderDataPiece(struct_field_name, data);
+ return Status::OK;
+}
+
+Status ProtoStreamObjectWriter::RenderTimestamp(ProtoStreamObjectWriter* ow,
+ const DataPiece& data) {
+ if (data.type() != DataPiece::TYPE_STRING) {
+ return Status(INVALID_ARGUMENT,
+ StrCat("Invalid data type for timestamp, value is ",
+ data.ValueAsStringOrDefault("")));
+ }
+
+ StringPiece value(data.str());
+
+ int64 seconds;
+ int32 nanos;
+ if (!::google::protobuf::internal::ParseTime(value.ToString(), &seconds,
+ &nanos)) {
+ return Status(INVALID_ARGUMENT, StrCat("Invalid time format: ", value));
+ }
+
+
+ ow->ProtoWriter::RenderDataPiece("seconds", DataPiece(seconds));
+ ow->ProtoWriter::RenderDataPiece("nanos", DataPiece(nanos));
+ return Status::OK;
+}
+
+static inline util::Status RenderOneFieldPath(ProtoStreamObjectWriter* ow,
+ StringPiece path) {
+ ow->ProtoWriter::RenderDataPiece(
+ "paths", DataPiece(ConvertFieldMaskPath(path, &ToSnakeCase), true));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectWriter::RenderFieldMask(ProtoStreamObjectWriter* ow,
+ const DataPiece& data) {
+ if (data.type() != DataPiece::TYPE_STRING) {
+ return Status(INVALID_ARGUMENT,
+ StrCat("Invalid data type for field mask, value is ",
+ data.ValueAsStringOrDefault("")));
+ }
+
+// TODO(tsun): figure out how to do proto descriptor based snake case
+// conversions as much as possible. Because ToSnakeCase sometimes returns the
+// wrong value.
+ google::protobuf::scoped_ptr<ResultCallback1<util::Status, StringPiece> > callback(
+ ::google::protobuf::internal::NewPermanentCallback(&RenderOneFieldPath, ow));
+ return DecodeCompactFieldMaskPaths(data.str(), callback.get());
+}
+
+Status ProtoStreamObjectWriter::RenderDuration(ProtoStreamObjectWriter* ow,
+ const DataPiece& data) {
+ if (data.type() != DataPiece::TYPE_STRING) {
+ return Status(INVALID_ARGUMENT,
+ StrCat("Invalid data type for duration, value is ",
+ data.ValueAsStringOrDefault("")));
+ }
+
+ StringPiece value(data.str());
+
+ if (!value.ends_with("s")) {
+ return Status(INVALID_ARGUMENT,
+ "Illegal duration format; duration must end with 's'");
+ }
+ value = value.substr(0, value.size() - 1);
+ int sign = 1;
+ if (value.starts_with("-")) {
+ sign = -1;
+ value = value.substr(1);
+ }
+
+ StringPiece s_secs, s_nanos;
+ SplitSecondsAndNanos(value, &s_secs, &s_nanos);
+ uint64 unsigned_seconds;
+ if (!safe_strtou64(s_secs, &unsigned_seconds)) {
+ return Status(INVALID_ARGUMENT,
+ "Invalid duration format, failed to parse seconds");
+ }
+
+ int32 nanos = 0;
+ Status nanos_status = GetNanosFromStringPiece(
+ s_nanos, "Invalid duration format, failed to parse nano seconds",
+ "Duration value exceeds limits", &nanos);
+ if (!nanos_status.ok()) {
+ return nanos_status;
+ }
+ nanos = sign * nanos;
+
+ int64 seconds = sign * unsigned_seconds;
+ if (seconds > kDurationMaxSeconds || seconds < kDurationMinSeconds ||
+ nanos <= -kNanosPerSecond || nanos >= kNanosPerSecond) {
+ return Status(INVALID_ARGUMENT, "Duration value exceeds limits");
+ }
+
+ ow->ProtoWriter::RenderDataPiece("seconds", DataPiece(seconds));
+ ow->ProtoWriter::RenderDataPiece("nanos", DataPiece(nanos));
+ return Status::OK;
+}
+
+Status ProtoStreamObjectWriter::RenderWrapperType(ProtoStreamObjectWriter* ow,
+ const DataPiece& data) {
+ ow->ProtoWriter::RenderDataPiece("value", data);
+ return Status::OK;
+}
+
+ProtoStreamObjectWriter* ProtoStreamObjectWriter::RenderDataPiece(
+ StringPiece name, const DataPiece& data) {
+ Status status;
+ if (invalid_depth() > 0) return this;
+
+ if (current_ == NULL) {
+ const TypeRenderer* type_renderer =
+ FindTypeRenderer(GetFullTypeWithUrl(master_type_.name()));
+ if (type_renderer == NULL) {
+ InvalidName(name, "Root element must be a message.");
+ return this;
+ }
+ // Render the special type.
+ // "<name>": {
+ // ... Render special type ...
+ // }
+ ProtoWriter::StartObject(name);
+ status = (*type_renderer)(this, data);
+ if (!status.ok()) {
+ InvalidValue(master_type_.name(),
+ StrCat("Field '", name, "', ", status.error_message()));
+ }
+ ProtoWriter::EndObject();
+ return this;
+ }
+
+ if (current_->IsAny()) {
+ current_->any()->RenderDataPiece(name, data);
+ return this;
+ }
+
+ const google::protobuf::Field* field = NULL;
+ if (current_->IsMap()) {
+ if (!ValidMapKey(name)) return this;
+
+ // Render an item in repeated map list.
+ // { "key": "<name>", "value":
+ Push("", Item::MESSAGE, false, false);
+ ProtoWriter::RenderDataPiece("key",
+ DataPiece(name, use_strict_base64_decoding()));
+ field = Lookup("value");
+ if (field == NULL) {
+ Pop();
+ GOOGLE_LOG(DFATAL) << "Map does not have a value field.";
+ return this;
+ }
+
+ const TypeRenderer* type_renderer = FindTypeRenderer(field->type_url());
+ if (type_renderer != NULL) {
+ // Map's value type is a special type. Render it like a message:
+ // "value": {
+ // ... Render special type ...
+ // }
+ Push("value", Item::MESSAGE, true, false);
+ status = (*type_renderer)(this, data);
+ if (!status.ok()) {
+ InvalidValue(field->type_url(),
+ StrCat("Field '", name, "', ", status.error_message()));
+ }
+ Pop();
+ return this;
+ }
+
+ // If we are rendering explicit null values and the backend proto field is
+ // not of the google.protobuf.NullType type, we do nothing.
+ if (data.type() == DataPiece::TYPE_NULL &&
+ field->type_url() != kStructNullValueTypeUrl) {
+ Pop();
+ return this;
+ }
+
+ // Render the map value as a primitive type.
+ ProtoWriter::RenderDataPiece("value", data);
+ Pop();
+ return this;
+ }
+
+ field = Lookup(name);
+ if (field == NULL) return this;
+
+ // Check if the field is of special type. Render it accordingly if so.
+ const TypeRenderer* type_renderer = FindTypeRenderer(field->type_url());
+ if (type_renderer != NULL) {
+ Push(name, Item::MESSAGE, false, false);
+ status = (*type_renderer)(this, data);
+ if (!status.ok()) {
+ InvalidValue(field->type_url(),
+ StrCat("Field '", name, "', ", status.error_message()));
+ }
+ Pop();
+ return this;
+ }
+
+ // If we are rendering explicit null values and the backend proto field is
+ // not of the google.protobuf.NullType type, we do nothing.
+ if (data.type() == DataPiece::TYPE_NULL &&
+ field->type_url() != kStructNullValueTypeUrl) {
+ return this;
+ }
+
+ ProtoWriter::RenderDataPiece(name, data);
+ return this;
+}
+
+// Map of functions that are responsible for rendering well known type
+// represented by the key.
+hash_map<string, ProtoStreamObjectWriter::TypeRenderer>*
+ ProtoStreamObjectWriter::renderers_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(writer_renderers_init_);
+
+void ProtoStreamObjectWriter::InitRendererMap() {
+ renderers_ = new hash_map<string, ProtoStreamObjectWriter::TypeRenderer>();
+ (*renderers_)["type.googleapis.com/google.protobuf.Timestamp"] =
+ &ProtoStreamObjectWriter::RenderTimestamp;
+ (*renderers_)["type.googleapis.com/google.protobuf.Duration"] =
+ &ProtoStreamObjectWriter::RenderDuration;
+ (*renderers_)["type.googleapis.com/google.protobuf.FieldMask"] =
+ &ProtoStreamObjectWriter::RenderFieldMask;
+ (*renderers_)["type.googleapis.com/google.protobuf.Double"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Float"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Int64"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.UInt64"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Int32"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.UInt32"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Bool"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.String"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Bytes"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.DoubleValue"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.FloatValue"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Int64Value"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.UInt64Value"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Int32Value"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.UInt32Value"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.BoolValue"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.StringValue"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.BytesValue"] =
+ &ProtoStreamObjectWriter::RenderWrapperType;
+ (*renderers_)["type.googleapis.com/google.protobuf.Value"] =
+ &ProtoStreamObjectWriter::RenderStructValue;
+ ::google::protobuf::internal::OnShutdown(&DeleteRendererMap);
+}
+
+void ProtoStreamObjectWriter::DeleteRendererMap() {
+ delete ProtoStreamObjectWriter::renderers_;
+ renderers_ = NULL;
+}
+
+ProtoStreamObjectWriter::TypeRenderer*
+ProtoStreamObjectWriter::FindTypeRenderer(const string& type_url) {
+ ::google::protobuf::GoogleOnceInit(&writer_renderers_init_, &InitRendererMap);
+ return FindOrNull(*renderers_, type_url);
+}
+
+bool ProtoStreamObjectWriter::ValidMapKey(StringPiece unnormalized_name) {
+ if (current_ == NULL) return true;
+
+ if (!current_->InsertMapKeyIfNotPresent(unnormalized_name)) {
+ listener()->InvalidName(
+ location(), unnormalized_name,
+ StrCat("Repeated map key: '", unnormalized_name, "' is already set."));
+ return false;
+ }
+
+ return true;
+}
+
+void ProtoStreamObjectWriter::Push(StringPiece name, Item::ItemType item_type,
+ bool is_placeholder, bool is_list) {
+ is_list ? ProtoWriter::StartList(name) : ProtoWriter::StartObject(name);
+
+ // invalid_depth == 0 means it is a successful StartObject or StartList.
+ if (invalid_depth() == 0)
+ current_.reset(
+ new Item(current_.release(), item_type, is_placeholder, is_list));
+}
+
+void ProtoStreamObjectWriter::Pop() {
+ // Pop all placeholder items sending StartObject or StartList events to
+ // ProtoWriter according to is_list value.
+ while (current_ != NULL && current_->is_placeholder()) {
+ PopOneElement();
+ }
+ if (current_ != NULL) {
+ PopOneElement();
+ }
+}
+
+void ProtoStreamObjectWriter::PopOneElement() {
+ current_->is_list() ? ProtoWriter::EndList() : ProtoWriter::EndObject();
+ current_.reset(current_->pop<Item>());
+}
+
+bool ProtoStreamObjectWriter::IsMap(const google::protobuf::Field& field) {
+ if (field.type_url().empty() ||
+ field.kind() != google::protobuf::Field_Kind_TYPE_MESSAGE ||
+ field.cardinality() !=
+ google::protobuf::Field_Cardinality_CARDINALITY_REPEATED) {
+ return false;
+ }
+ const google::protobuf::Type* field_type =
+ typeinfo()->GetTypeByTypeUrl(field.type_url());
+
+ // TODO(xiaofeng): Unify option names.
+ return GetBoolOptionOrDefault(field_type->options(),
+ "google.protobuf.MessageOptions.map_entry", false) ||
+ GetBoolOptionOrDefault(field_type->options(), "map_entry", false);
+}
+
+bool ProtoStreamObjectWriter::IsAny(const google::protobuf::Field& field) {
+ return GetTypeWithoutUrl(field.type_url()) == kAnyType;
+}
+
+bool ProtoStreamObjectWriter::IsStruct(const google::protobuf::Field& field) {
+ return GetTypeWithoutUrl(field.type_url()) == kStructType;
+}
+
+bool ProtoStreamObjectWriter::IsStructValue(
+ const google::protobuf::Field& field) {
+ return GetTypeWithoutUrl(field.type_url()) == kStructValueType;
+}
+
+bool ProtoStreamObjectWriter::IsStructListValue(
+ const google::protobuf::Field& field) {
+ return GetTypeWithoutUrl(field.type_url()) == kStructListValueType;
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.h
new file mode 100644
index 0000000000..2e4d14d143
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter.h
@@ -0,0 +1,345 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTOSTREAM_OBJECTWRITER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTOSTREAM_OBJECTWRITER_H__
+
+#include <deque>
+#include <google/protobuf/stubs/hash.h>
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/type_info.h>
+#include <google/protobuf/util/internal/datapiece.h>
+#include <google/protobuf/util/internal/error_listener.h>
+#include <google/protobuf/util/internal/proto_writer.h>
+#include <google/protobuf/util/internal/structured_objectwriter.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/stubs/bytestream.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+class CodedOutputStream;
+} // namespace io
+} // namespace protobuf
+
+
+namespace protobuf {
+class Type;
+class Field;
+} // namespace protobuf
+
+
+namespace protobuf {
+namespace util {
+namespace converter {
+
+class ObjectLocationTracker;
+
+// An ObjectWriter that can write protobuf bytes directly from writer events.
+// This class supports all special types like Struct and Map. It uses
+// the ProtoWriter class to write raw proto bytes.
+//
+// It also supports streaming.
+class LIBPROTOBUF_EXPORT ProtoStreamObjectWriter : public ProtoWriter {
+ public:
+ // Options that control ProtoStreamObjectWriter class's behavior.
+ struct Options {
+ // Treats integer inputs in google.protobuf.Struct as strings. Normally,
+ // integer values are returned in double field "number_value" of
+ // google.protobuf.Struct. However, this can cause precision loss for
+ // int64/uint64 inputs. This option is provided for cases that want to
+ // preserve integer precision.
+ bool struct_integers_as_strings;
+
+ // Not treat unknown fields as an error. If there is an unknown fields,
+ // just ignore it and continue to process the rest.
+ bool ignore_unknown_fields;
+
+ Options()
+ : struct_integers_as_strings(false), ignore_unknown_fields(false) {}
+
+ // Default instance of Options with all options set to defaults.
+ static const Options& Defaults() {
+ static Options defaults;
+ return defaults;
+ }
+ };
+
+// Constructor. Does not take ownership of any parameter passed in.
+ ProtoStreamObjectWriter(TypeResolver* type_resolver,
+ const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener,
+ const ProtoStreamObjectWriter::Options& options =
+ ProtoStreamObjectWriter::Options::Defaults());
+ virtual ~ProtoStreamObjectWriter();
+
+ // ObjectWriter methods.
+ virtual ProtoStreamObjectWriter* StartObject(StringPiece name);
+ virtual ProtoStreamObjectWriter* EndObject();
+ virtual ProtoStreamObjectWriter* StartList(StringPiece name);
+ virtual ProtoStreamObjectWriter* EndList();
+
+ // Renders a DataPiece 'value' into a field whose wire type is determined
+ // from the given field 'name'.
+ virtual ProtoStreamObjectWriter* RenderDataPiece(StringPiece name,
+ const DataPiece& value);
+
+ protected:
+ // Function that renders a well known type with modified behavior.
+ typedef util::Status (*TypeRenderer)(ProtoStreamObjectWriter*,
+ const DataPiece&);
+
+ // Handles writing Anys out using nested object writers and the like.
+ class LIBPROTOBUF_EXPORT AnyWriter {
+ public:
+ explicit AnyWriter(ProtoStreamObjectWriter* parent);
+ ~AnyWriter();
+
+ // Passes a StartObject call through to the Any writer.
+ void StartObject(StringPiece name);
+
+ // Passes an EndObject call through to the Any. Returns true if the any
+ // handled the EndObject call, false if the Any is now all done and is no
+ // longer needed.
+ bool EndObject();
+
+ // Passes a StartList call through to the Any writer.
+ void StartList(StringPiece name);
+
+ // Passes an EndList call through to the Any writer.
+ void EndList();
+
+ // Renders a data piece on the any.
+ void RenderDataPiece(StringPiece name, const DataPiece& value);
+
+ private:
+ // Handles starting up the any once we have a type.
+ void StartAny(const DataPiece& value);
+
+ // Writes the Any out to the parent writer in its serialized form.
+ void WriteAny();
+
+ // The parent of this writer, needed for various bits such as type info and
+ // the listeners.
+ ProtoStreamObjectWriter* parent_;
+
+ // The nested object writer, used to write events.
+ google::protobuf::scoped_ptr<ProtoStreamObjectWriter> ow_;
+
+ // The type_url_ that this Any represents.
+ string type_url_;
+
+ // Whether this any is invalid. This allows us to only report an invalid
+ // Any message a single time rather than every time we get a nested field.
+ bool invalid_;
+
+ // The output data and wrapping ByteSink.
+ string data_;
+ strings::StringByteSink output_;
+
+ // The depth within the Any, so we can track when we're done.
+ int depth_;
+
+ // True if the type is a well-known type. Well-known types in Any
+ // has a special formating:
+ // {
+ // "@type": "type.googleapis.com/google.protobuf.XXX",
+ // "value": <JSON representation of the type>,
+ // }
+ bool is_well_known_type_;
+ TypeRenderer* well_known_type_render_;
+ };
+
+ // Represents an item in a stack of items used to keep state between
+ // ObjectWrier events.
+ class LIBPROTOBUF_EXPORT Item : public BaseElement {
+ public:
+ // Indicates the type of item.
+ enum ItemType {
+ MESSAGE, // Simple message
+ MAP, // Proto3 map type
+ ANY, // Proto3 Any type
+ };
+
+ // Constructor for the root item.
+ Item(ProtoStreamObjectWriter* enclosing, ItemType item_type,
+ bool is_placeholder, bool is_list);
+
+ // Constructor for a field of a message.
+ Item(Item* parent, ItemType item_type, bool is_placeholder, bool is_list);
+
+ virtual ~Item() {}
+
+ // These functions return true if the element type is corresponding to the
+ // type in function name.
+ bool IsMap() { return item_type_ == MAP; }
+ bool IsAny() { return item_type_ == ANY; }
+
+ AnyWriter* any() const { return any_.get(); }
+
+ virtual Item* parent() const {
+ return static_cast<Item*>(BaseElement::parent());
+ }
+
+ // Inserts map key into hash set if and only if the key did NOT already
+ // exist in hash set.
+ // The hash set (map_keys_) is ONLY used to keep track of map keys.
+ // Return true if insert successfully; returns false if the map key was
+ // already present.
+ bool InsertMapKeyIfNotPresent(StringPiece map_key);
+
+ bool is_placeholder() const { return is_placeholder_; }
+ bool is_list() const { return is_list_; }
+
+ private:
+ // Used for access to variables of the enclosing instance of
+ // ProtoStreamObjectWriter.
+ ProtoStreamObjectWriter* ow_;
+
+ // A writer for Any objects, handles all Any-related nonsense.
+ google::protobuf::scoped_ptr<AnyWriter> any_;
+
+ // The type of this element, see enum for permissible types.
+ ItemType item_type_;
+
+ // Set of map keys already seen for the type_. Used to validate incoming
+ // messages so no map key appears more than once.
+ google::protobuf::scoped_ptr<hash_set<string> > map_keys_;
+
+ // Conveys whether this Item is a placeholder or not. Placeholder items are
+ // pushed to stack to account for special types.
+ bool is_placeholder_;
+
+ // Conveys whether this Item is a list or not. This is used to send
+ // StartList or EndList calls to underlying ObjectWriter.
+ bool is_list_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(Item);
+ };
+
+ ProtoStreamObjectWriter(const TypeInfo* typeinfo,
+ const google::protobuf::Type& type,
+ strings::ByteSink* output, ErrorListener* listener);
+
+ // Returns true if the field is a map.
+ inline bool IsMap(const google::protobuf::Field& field);
+
+ // Returns true if the field is an any.
+ inline bool IsAny(const google::protobuf::Field& field);
+
+ // Returns true if the field is google.protobuf.Struct.
+ inline bool IsStruct(const google::protobuf::Field& field);
+
+ // Returns true if the field is google.protobuf.Value.
+ inline bool IsStructValue(const google::protobuf::Field& field);
+
+ // Returns true if the field is google.protobuf.ListValue.
+ inline bool IsStructListValue(const google::protobuf::Field& field);
+
+ // Renders google.protobuf.Value in struct.proto. It picks the right oneof
+ // type based on value's type.
+ static util::Status RenderStructValue(ProtoStreamObjectWriter* ow,
+ const DataPiece& value);
+
+ // Renders google.protobuf.Timestamp value.
+ static util::Status RenderTimestamp(ProtoStreamObjectWriter* ow,
+ const DataPiece& value);
+
+ // Renders google.protobuf.FieldMask value.
+ static util::Status RenderFieldMask(ProtoStreamObjectWriter* ow,
+ const DataPiece& value);
+
+ // Renders google.protobuf.Duration value.
+ static util::Status RenderDuration(ProtoStreamObjectWriter* ow,
+ const DataPiece& value);
+
+ // Renders wrapper message types for primitive types in
+ // google/protobuf/wrappers.proto.
+ static util::Status RenderWrapperType(ProtoStreamObjectWriter* ow,
+ const DataPiece& value);
+
+ static void InitRendererMap();
+ static void DeleteRendererMap();
+ static TypeRenderer* FindTypeRenderer(const string& type_url);
+
+ // Returns true if the map key for type_ is not duplicated key.
+ // If map key is duplicated key, this function returns false.
+ // Note that caller should make sure that the current proto element (current_)
+ // is of element type MAP or STRUCT_MAP.
+ // It also calls the appropriate error callback and unnormalzied_name is used
+ // for error string.
+ bool ValidMapKey(StringPiece unnormalized_name);
+
+ // Pushes an item on to the stack. Also calls either StartObject or StartList
+ // on the underlying ObjectWriter depending on whether is_list is false or
+ // not.
+ // is_placeholder conveys whether the item is a placeholder item or not.
+ // Placeholder items are pushed when adding auxillary types' StartObject or
+ // StartList calls.
+ void Push(StringPiece name, Item::ItemType item_type, bool is_placeholder,
+ bool is_list);
+
+ // Pops items from the stack. All placeholder items are popped until a
+ // non-placeholder item is found.
+ void Pop();
+
+ // Pops one element from the stack. Calls EndObject() or EndList() on the
+ // underlying ObjectWriter depending on the value of is_list_.
+ void PopOneElement();
+
+ private:
+ // Helper functions to create the map and find functions responsible for
+ // rendering well known types, keyed by type URL.
+ static hash_map<string, TypeRenderer>* renderers_;
+
+ // Variables for describing the structure of the input tree:
+ // master_type_: descriptor for the whole protobuf message.
+ const google::protobuf::Type& master_type_;
+
+ // The current element, variable for internal state processing.
+ google::protobuf::scoped_ptr<Item> current_;
+
+ // Reference to the options that control this class's behavior.
+ const ProtoStreamObjectWriter::Options options_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(ProtoStreamObjectWriter);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_PROTOSTREAM_OBJECTWRITER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter_test.cc
new file mode 100644
index 0000000000..30e58e6279
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/protostream_objectwriter_test.cc
@@ -0,0 +1,2394 @@
+// 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.
+
+#include <google/protobuf/util/internal/protostream_objectwriter.h>
+
+#include <stddef.h> // For size_t
+
+#include <google/protobuf/field_mask.pb.h>
+#include <google/protobuf/timestamp.pb.h>
+#include <google/protobuf/wrappers.pb.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/util/internal/mock_error_listener.h>
+#include <google/protobuf/util/internal/testdata/books.pb.h>
+#include <google/protobuf/util/internal/testdata/field_mask.pb.h>
+#include <google/protobuf/util/internal/type_info_test_helper.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/util/message_differencer.h>
+#include <google/protobuf/stubs/bytestream.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/util/internal/testdata/anys.pb.h>
+#include <google/protobuf/util/internal/testdata/maps.pb.h>
+#include <google/protobuf/util/internal/testdata/oneofs.pb.h>
+#include <google/protobuf/util/internal/testdata/struct.pb.h>
+#include <google/protobuf/util/internal/testdata/timestamp_duration.pb.h>
+#include <gtest/gtest.h>
+
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+using google::protobuf::testing::Author;
+using google::protobuf::testing::Book;
+using google::protobuf::testing::Book_Data;
+using google::protobuf::testing::Primitive;
+using google::protobuf::testing::Publisher;
+using google::protobuf::Descriptor;
+using google::protobuf::DescriptorPool;
+using google::protobuf::DynamicMessageFactory;
+using google::protobuf::FileDescriptorProto;
+using google::protobuf::Message;
+using google::protobuf::io::ArrayInputStream;
+using strings::GrowingArrayByteSink;
+using ::testing::_;
+using ::testing::Args;
+using google::protobuf::testing::anys::AnyM;
+using google::protobuf::testing::anys::AnyOut;
+using google::protobuf::testing::oneofs::OneOfsRequest;
+using google::protobuf::testing::FieldMaskTest;
+using google::protobuf::testing::maps::MapIn;
+using google::protobuf::testing::structs::StructType;
+using google::protobuf::testing::timestampduration::TimestampDuration;
+
+
+namespace {
+string GetTypeUrl(const Descriptor* descriptor) {
+ return string(kTypeServiceBaseUrl) + "/" + descriptor->full_name();
+}
+} // namespace
+
+#if __cplusplus >= 201103L
+ using std::get;
+#else
+ using std::tr1::get;
+#endif
+
+class BaseProtoStreamObjectWriterTest
+ : public ::testing::TestWithParam<testing::TypeInfoSource> {
+ protected:
+ BaseProtoStreamObjectWriterTest()
+ : helper_(GetParam()),
+ listener_(),
+ output_(new GrowingArrayByteSink(1000)),
+ ow_() {}
+
+ explicit BaseProtoStreamObjectWriterTest(const Descriptor* descriptor)
+ : helper_(GetParam()),
+ listener_(),
+ output_(new GrowingArrayByteSink(1000)),
+ ow_() {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(descriptor);
+ ResetTypeInfo(descriptors);
+ }
+
+ explicit BaseProtoStreamObjectWriterTest(
+ vector<const Descriptor*> descriptors)
+ : helper_(GetParam()),
+ listener_(),
+ output_(new GrowingArrayByteSink(1000)),
+ ow_() {
+ ResetTypeInfo(descriptors);
+ }
+
+ void ResetTypeInfo(vector<const Descriptor*> descriptors) {
+ GOOGLE_CHECK(!descriptors.empty()) << "Must have at least one descriptor!";
+ helper_.ResetTypeInfo(descriptors);
+ ow_.reset(helper_.NewProtoWriter(GetTypeUrl(descriptors[0]), output_.get(),
+ &listener_, options_));
+ }
+
+ void ResetTypeInfo(const Descriptor* descriptor) {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(descriptor);
+ ResetTypeInfo(descriptors);
+ }
+
+ virtual ~BaseProtoStreamObjectWriterTest() {}
+
+ void CheckOutput(const Message& expected, int expected_length) {
+ size_t nbytes;
+ google::protobuf::scoped_array<char> buffer(output_->GetBuffer(&nbytes));
+ if (expected_length >= 0) {
+ EXPECT_EQ(expected_length, nbytes);
+ }
+ string str(buffer.get(), nbytes);
+
+ std::stringbuf str_buf(str, std::ios_base::in);
+ std::istream istream(&str_buf);
+ google::protobuf::scoped_ptr<Message> message(expected.New());
+ message->ParsePartialFromIstream(&istream);
+
+ if (!MessageDifferencer::Equivalent(expected, *message)) {
+ EXPECT_EQ(expected.DebugString(), message->DebugString());
+ }
+ }
+
+ void CheckOutput(const Message& expected) { CheckOutput(expected, -1); }
+
+ const google::protobuf::Type* GetType(const Descriptor* descriptor) {
+ return helper_.GetTypeInfo()->GetTypeByTypeUrl(GetTypeUrl(descriptor));
+ }
+
+ testing::TypeInfoTestHelper helper_;
+ MockErrorListener listener_;
+ google::protobuf::scoped_ptr<GrowingArrayByteSink> output_;
+ google::protobuf::scoped_ptr<ProtoStreamObjectWriter> ow_;
+ ProtoStreamObjectWriter::Options options_;
+};
+
+MATCHER_P(HasObjectLocation, expected,
+ "Verifies the expected object location") {
+ string actual = get<0>(arg).ToString();
+ if (actual.compare(expected) == 0) return true;
+ *result_listener << "actual location is: " << actual;
+ return false;
+}
+
+class ProtoStreamObjectWriterTest : public BaseProtoStreamObjectWriterTest {
+ protected:
+ ProtoStreamObjectWriterTest()
+ : BaseProtoStreamObjectWriterTest(Book::descriptor()) {}
+
+ void ResetProtoWriter() {
+ ResetTypeInfo(Book::descriptor());
+ }
+
+ virtual ~ProtoStreamObjectWriterTest() {}
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtoStreamObjectWriterTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtoStreamObjectWriterTest, EmptyObject) {
+ Book empty;
+ ow_->StartObject("")->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, SimpleObject) {
+ string content("My content");
+
+ Book book;
+ book.set_title("My Title");
+ book.set_length(222);
+ book.set_content(content);
+
+ ow_->StartObject("")
+ ->RenderString("title", "My Title")
+ ->RenderInt32("length", 222)
+ ->RenderBytes("content", content)
+ ->EndObject();
+ CheckOutput(book);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, SimpleMessage) {
+ Book book;
+ book.set_title("Some Book");
+ book.set_length(102);
+ Publisher* publisher = book.mutable_publisher();
+ publisher->set_name("My Publisher");
+ Author* robert = book.mutable_author();
+ robert->set_alive(true);
+ robert->set_name("robert");
+ robert->add_pseudonym("bob");
+ robert->add_pseudonym("bobby");
+ robert->add_friend_()->set_name("john");
+
+ ow_->StartObject("")
+ ->RenderString("title", "Some Book")
+ ->RenderInt32("length", 102)
+ ->StartObject("publisher")
+ ->RenderString("name", "My Publisher")
+ ->EndObject()
+ ->StartObject("author")
+ ->RenderBool("alive", true)
+ ->RenderString("name", "robert")
+ ->StartList("pseudonym")
+ ->RenderString("", "bob")
+ ->RenderString("", "bobby")
+ ->EndList()
+ ->StartList("friend")
+ ->StartObject("")
+ ->RenderString("name", "john")
+ ->EndObject()
+ ->EndList()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(book);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, CustomJsonName) {
+ Book book;
+ Author* robert = book.mutable_author();
+ robert->set_id(12345);
+ robert->set_name("robert");
+
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderUint64("@id", 12345)
+ ->RenderString("name", "robert")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(book);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, PrimitiveFromStringConversion) {
+ Primitive full;
+ full.set_fix32(101);
+ full.set_u32(102);
+ full.set_i32(-103);
+ full.set_sf32(-104);
+ full.set_s32(-105);
+ full.set_fix64(40000000001L);
+ full.set_u64(40000000002L);
+ full.set_i64(-40000000003L);
+ full.set_sf64(-40000000004L);
+ full.set_s64(-40000000005L);
+ full.set_str("string1");
+ full.set_bytes("Some Bytes");
+ full.set_float_(3.14f);
+ full.set_double_(-4.05L);
+ full.set_bool_(true);
+ full.add_rep_fix32(201);
+ full.add_rep_u32(202);
+ full.add_rep_i32(-203);
+ full.add_rep_sf32(-204);
+ full.add_rep_s32(-205);
+ full.add_rep_fix64(80000000001L);
+ full.add_rep_u64(80000000002L);
+ full.add_rep_i64(-80000000003L);
+ full.add_rep_sf64(-80000000004L);
+ full.add_rep_s64(-80000000005L);
+ full.add_rep_str("string2");
+ full.add_rep_bytes("More Bytes");
+ full.add_rep_float(6.14f);
+ full.add_rep_double(-8.05L);
+ full.add_rep_bool(false);
+
+ ResetTypeInfo(Primitive::descriptor());
+
+ ow_->StartObject("")
+ ->RenderString("fix32", "101")
+ ->RenderString("u32", "102")
+ ->RenderString("i32", "-103")
+ ->RenderString("sf32", "-104")
+ ->RenderString("s32", "-105")
+ ->RenderString("fix64", "40000000001")
+ ->RenderString("u64", "40000000002")
+ ->RenderString("i64", "-40000000003")
+ ->RenderString("sf64", "-40000000004")
+ ->RenderString("s64", "-40000000005")
+ ->RenderString("str", "string1")
+ ->RenderString("bytes", "U29tZSBCeXRlcw==") // "Some Bytes"
+ ->RenderString("float", "3.14")
+ ->RenderString("double", "-4.05")
+ ->RenderString("bool", "true")
+ ->StartList("rep_fix32")
+ ->RenderString("", "201")
+ ->EndList()
+ ->StartList("rep_u32")
+ ->RenderString("", "202")
+ ->EndList()
+ ->StartList("rep_i32")
+ ->RenderString("", "-203")
+ ->EndList()
+ ->StartList("rep_sf32")
+ ->RenderString("", "-204")
+ ->EndList()
+ ->StartList("rep_s32")
+ ->RenderString("", "-205")
+ ->EndList()
+ ->StartList("rep_fix64")
+ ->RenderString("", "80000000001")
+ ->EndList()
+ ->StartList("rep_u64")
+ ->RenderString("", "80000000002")
+ ->EndList()
+ ->StartList("rep_i64")
+ ->RenderString("", "-80000000003")
+ ->EndList()
+ ->StartList("rep_sf64")
+ ->RenderString("", "-80000000004")
+ ->EndList()
+ ->StartList("rep_s64")
+ ->RenderString("", "-80000000005")
+ ->EndList()
+ ->StartList("rep_str")
+ ->RenderString("", "string2")
+ ->EndList()
+ ->StartList("rep_bytes")
+ ->RenderString("", "TW9yZSBCeXRlcw==") // "More Bytes"
+ ->EndList()
+ ->StartList("rep_float")
+ ->RenderString("", "6.14")
+ ->EndList()
+ ->StartList("rep_double")
+ ->RenderString("", "-8.05")
+ ->EndList()
+ ->StartList("rep_bool")
+ ->RenderString("", "false")
+ ->EndList()
+ ->EndObject();
+ CheckOutput(full);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, InfinityInputTest) {
+ Primitive full;
+ full.set_double_(std::numeric_limits<double>::infinity());
+ full.set_float_(std::numeric_limits<float>::infinity());
+ full.set_str("-Infinity");
+
+ ResetTypeInfo(Primitive::descriptor());
+
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_INT32"),
+ StringPiece("\"Infinity\"")))
+ .With(Args<0>(HasObjectLocation("i32")));
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_UINT32"),
+ StringPiece("\"Infinity\"")))
+ .With(Args<0>(HasObjectLocation("u32")));
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_SFIXED64"),
+ StringPiece("\"-Infinity\"")))
+ .With(Args<0>(HasObjectLocation("sf64")));
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_BOOL"),
+ StringPiece("\"Infinity\"")))
+ .With(Args<0>(HasObjectLocation("bool")));
+
+ ow_->StartObject("")
+ ->RenderString("double", "Infinity")
+ ->RenderString("float", "Infinity")
+ ->RenderString("i32", "Infinity")
+ ->RenderString("u32", "Infinity")
+ ->RenderString("sf64", "-Infinity")
+ ->RenderString("str", "-Infinity")
+ ->RenderString("bool", "Infinity")
+ ->EndObject();
+ CheckOutput(full);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, NaNInputTest) {
+ Primitive full;
+ full.set_double_(std::numeric_limits<double>::quiet_NaN());
+ full.set_float_(std::numeric_limits<float>::quiet_NaN());
+ full.set_str("NaN");
+
+ ResetTypeInfo(Primitive::descriptor());
+
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_INT32"),
+ StringPiece("\"NaN\"")))
+ .With(Args<0>(HasObjectLocation("i32")));
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_UINT32"),
+ StringPiece("\"NaN\"")))
+ .With(Args<0>(HasObjectLocation("u32")));
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_SFIXED64"),
+ StringPiece("\"NaN\"")))
+ .With(Args<0>(HasObjectLocation("sf64")));
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("TYPE_BOOL"), StringPiece("\"NaN\"")))
+ .With(Args<0>(HasObjectLocation("bool")));
+
+ ow_->StartObject("")
+ ->RenderString("double", "NaN")
+ ->RenderString("float", "NaN")
+ ->RenderString("i32", "NaN")
+ ->RenderString("u32", "NaN")
+ ->RenderString("sf64", "NaN")
+ ->RenderString("str", "NaN")
+ ->RenderString("bool", "NaN")
+ ->EndObject();
+
+ CheckOutput(full);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, ImplicitPrimitiveList) {
+ Book expected;
+ Author* author = expected.mutable_author();
+ author->set_name("The Author");
+ author->add_pseudonym("first");
+ author->add_pseudonym("second");
+
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "The Author")
+ ->RenderString("pseudonym", "first")
+ ->RenderString("pseudonym", "second")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest,
+ LastWriteWinsOnNonRepeatedPrimitiveFieldWithDuplicates) {
+ Book expected;
+ Author* author = expected.mutable_author();
+ author->set_name("second");
+
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "first")
+ ->RenderString("name", "second")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, ExplicitPrimitiveList) {
+ Book expected;
+ Author* author = expected.mutable_author();
+ author->set_name("The Author");
+ author->add_pseudonym("first");
+ author->add_pseudonym("second");
+
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "The Author")
+ ->StartList("pseudonym")
+ ->RenderString("", "first")
+ ->RenderString("", "second")
+ ->EndList()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, NonRepeatedExplicitPrimitiveList) {
+ Book expected;
+ expected.set_allocated_author(new Author());
+
+ EXPECT_CALL(
+ listener_,
+ InvalidName(
+ _, StringPiece("name"),
+ StringPiece("Proto field is not repeating, cannot start list.")))
+ .With(Args<0>(HasObjectLocation("author")));
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->StartList("name")
+ ->RenderString("", "first")
+ ->RenderString("", "second")
+ ->EndList()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, ImplicitMessageList) {
+ Book expected;
+ Author* outer = expected.mutable_author();
+ outer->set_name("outer");
+ outer->set_alive(true);
+ Author* first = outer->add_friend_();
+ first->set_name("first");
+ Author* second = outer->add_friend_();
+ second->set_name("second");
+
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "outer")
+ ->RenderBool("alive", true)
+ ->StartObject("friend")
+ ->RenderString("name", "first")
+ ->EndObject()
+ ->StartObject("friend")
+ ->RenderString("name", "second")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest,
+ LastWriteWinsOnNonRepeatedMessageFieldWithDuplicates) {
+ Book expected;
+ Author* author = expected.mutable_author();
+ author->set_name("The Author");
+ Publisher* publisher = expected.mutable_publisher();
+ publisher->set_name("second");
+
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "The Author")
+ ->EndObject()
+ ->StartObject("publisher")
+ ->RenderString("name", "first")
+ ->EndObject()
+ ->StartObject("publisher")
+ ->RenderString("name", "second")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, ExplicitMessageList) {
+ Book expected;
+ Author* outer = expected.mutable_author();
+ outer->set_name("outer");
+ outer->set_alive(true);
+ Author* first = outer->add_friend_();
+ first->set_name("first");
+ Author* second = outer->add_friend_();
+ second->set_name("second");
+
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "outer")
+ ->RenderBool("alive", true)
+ ->StartList("friend")
+ ->StartObject("")
+ ->RenderString("name", "first")
+ ->EndObject()
+ ->StartObject("")
+ ->RenderString("name", "second")
+ ->EndObject()
+ ->EndList()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, NonRepeatedExplicitMessageList) {
+ Book expected;
+ Author* author = expected.mutable_author();
+ author->set_name("The Author");
+
+ EXPECT_CALL(
+ listener_,
+ InvalidName(
+ _, StringPiece("publisher"),
+ StringPiece("Proto field is not repeating, cannot start list.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "The Author")
+ ->EndObject()
+ ->StartList("publisher")
+ ->StartObject("")
+ ->RenderString("name", "first")
+ ->EndObject()
+ ->StartObject("")
+ ->RenderString("name", "second")
+ ->EndObject()
+ ->EndList()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnknownFieldAtRoot) {
+ Book empty;
+
+ EXPECT_CALL(listener_, InvalidName(_, StringPiece("unknown"),
+ StringPiece("Cannot find field.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("")->RenderString("unknown", "Nope!")->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnknownFieldAtAuthorFriend) {
+ Book expected;
+ Author* paul = expected.mutable_author();
+ paul->set_name("Paul");
+ Author* mark = paul->add_friend_();
+ mark->set_name("Mark");
+ Author* john = paul->add_friend_();
+ john->set_name("John");
+ Author* luke = paul->add_friend_();
+ luke->set_name("Luke");
+
+ EXPECT_CALL(listener_, InvalidName(_, StringPiece("address"),
+ StringPiece("Cannot find field.")))
+ .With(Args<0>(HasObjectLocation("author.friend[1]")));
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "Paul")
+ ->StartList("friend")
+ ->StartObject("")
+ ->RenderString("name", "Mark")
+ ->EndObject()
+ ->StartObject("")
+ ->RenderString("name", "John")
+ ->RenderString("address", "Patmos")
+ ->EndObject()
+ ->StartObject("")
+ ->RenderString("name", "Luke")
+ ->EndObject()
+ ->EndList()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnknownObjectAtRoot) {
+ Book empty;
+
+ EXPECT_CALL(listener_, InvalidName(_, StringPiece("unknown"),
+ StringPiece("Cannot find field.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("")->StartObject("unknown")->EndObject()->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnknownObjectAtAuthor) {
+ Book expected;
+ Author* author = expected.mutable_author();
+ author->set_name("William");
+ author->add_pseudonym("Bill");
+
+ EXPECT_CALL(listener_, InvalidName(_, StringPiece("wife"),
+ StringPiece("Cannot find field.")))
+ .With(Args<0>(HasObjectLocation("author")));
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "William")
+ ->StartObject("wife")
+ ->RenderString("name", "Hilary")
+ ->EndObject()
+ ->RenderString("pseudonym", "Bill")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnknownListAtRoot) {
+ Book empty;
+
+ EXPECT_CALL(listener_, InvalidName(_, StringPiece("unknown"),
+ StringPiece("Cannot find field.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("")->StartList("unknown")->EndList()->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnknownListAtPublisher) {
+ Book expected;
+ expected.set_title("Brainwashing");
+ Publisher* publisher = expected.mutable_publisher();
+ publisher->set_name("propaganda");
+
+ EXPECT_CALL(listener_, InvalidName(_, StringPiece("alliance"),
+ StringPiece("Cannot find field.")))
+ .With(Args<0>(HasObjectLocation("publisher")));
+ ow_->StartObject("")
+ ->StartObject("publisher")
+ ->RenderString("name", "propaganda")
+ ->StartList("alliance")
+ ->EndList()
+ ->EndObject()
+ ->RenderString("title", "Brainwashing")
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, IgnoreUnknownFieldAtRoot) {
+ Book empty;
+
+ options_.ignore_unknown_fields = true;
+ ResetProtoWriter();
+
+ EXPECT_CALL(listener_, InvalidName(_, _, _)).Times(0);
+ ow_->StartObject("")->RenderString("unknown", "Nope!")->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, IgnoreUnknownFieldAtAuthorFriend) {
+ Book expected;
+ Author* paul = expected.mutable_author();
+ paul->set_name("Paul");
+ Author* mark = paul->add_friend_();
+ mark->set_name("Mark");
+ Author* john = paul->add_friend_();
+ john->set_name("John");
+ Author* luke = paul->add_friend_();
+ luke->set_name("Luke");
+
+ options_.ignore_unknown_fields = true;
+ ResetProtoWriter();
+
+ EXPECT_CALL(listener_, InvalidName(_, _, _)).Times(0);
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "Paul")
+ ->StartList("friend")
+ ->StartObject("")
+ ->RenderString("name", "Mark")
+ ->EndObject()
+ ->StartObject("")
+ ->RenderString("name", "John")
+ ->RenderString("address", "Patmos")
+ ->EndObject()
+ ->StartObject("")
+ ->RenderString("name", "Luke")
+ ->EndObject()
+ ->EndList()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, IgnoreUnknownObjectAtRoot) {
+ Book empty;
+
+ options_.ignore_unknown_fields = true;
+ ResetProtoWriter();
+
+ EXPECT_CALL(listener_, InvalidName(_, StringPiece("unknown"),
+ StringPiece("Cannot find field.")))
+ .Times(0);
+ ow_->StartObject("")->StartObject("unknown")->EndObject()->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, IgnoreUnknownObjectAtAuthor) {
+ Book expected;
+ Author* author = expected.mutable_author();
+ author->set_name("William");
+ author->add_pseudonym("Bill");
+
+ options_.ignore_unknown_fields = true;
+ ResetProtoWriter();
+
+ EXPECT_CALL(listener_, InvalidName(_, _, _)).Times(0);
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderString("name", "William")
+ ->StartObject("wife")
+ ->RenderString("name", "Hilary")
+ ->EndObject()
+ ->RenderString("pseudonym", "Bill")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, IgnoreUnknownListAtRoot) {
+ Book empty;
+
+ options_.ignore_unknown_fields = true;
+ ResetProtoWriter();
+
+ EXPECT_CALL(listener_, InvalidName(_, _, _)).Times(0);
+ ow_->StartObject("")->StartList("unknown")->EndList()->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, IgnoreUnknownListAtPublisher) {
+ Book expected;
+ expected.set_title("Brainwashing");
+ Publisher* publisher = expected.mutable_publisher();
+ publisher->set_name("propaganda");
+
+ options_.ignore_unknown_fields = true;
+ ResetProtoWriter();
+
+ EXPECT_CALL(listener_, InvalidName(_, _, _)).Times(0);
+ ow_->StartObject("")
+ ->StartObject("publisher")
+ ->RenderString("name", "propaganda")
+ ->StartList("alliance")
+ ->EndList()
+ ->EndObject()
+ ->RenderString("title", "Brainwashing")
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, MissingRequiredField) {
+ Book expected;
+ expected.set_title("My Title");
+ expected.set_allocated_publisher(new Publisher());
+
+ EXPECT_CALL(listener_, MissingField(_, StringPiece("name")))
+ .With(Args<0>(HasObjectLocation("publisher")));
+ ow_->StartObject("")
+ ->StartObject("publisher")
+ ->EndObject()
+ ->RenderString("title", "My Title")
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, InvalidFieldValueAtRoot) {
+ Book empty;
+
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_UINT32"),
+ StringPiece("\"garbage\"")))
+ .With(Args<0>(HasObjectLocation("length")));
+ ow_->StartObject("")->RenderString("length", "garbage")->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, MultipleInvalidFieldValues) {
+ Book expected;
+ expected.set_title("My Title");
+
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_UINT32"),
+ StringPiece("\"-400\"")))
+ .With(Args<0>(HasObjectLocation("length")));
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("TYPE_INT64"),
+ StringPiece("\"3.14\"")))
+ .With(Args<0>(HasObjectLocation("published")));
+ ow_->StartObject("")
+ ->RenderString("length", "-400")
+ ->RenderString("published", "3.14")
+ ->RenderString("title", "My Title")
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnnamedFieldAtRoot) {
+ Book empty;
+
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece(""),
+ StringPiece("Proto fields must have a name.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("")->RenderFloat("", 3.14)->EndObject();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnnamedFieldAtAuthor) {
+ Book expected;
+ expected.set_title("noname");
+ expected.set_allocated_author(new Author());
+
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece(""),
+ StringPiece("Proto fields must have a name.")))
+ .With(Args<0>(HasObjectLocation("author")));
+ ow_->StartObject("")
+ ->StartObject("author")
+ ->RenderInt32("", 123)
+ ->EndObject()
+ ->RenderString("title", "noname")
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, UnnamedListAtRoot) {
+ Book expected;
+ expected.set_title("noname");
+
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece(""),
+ StringPiece("Proto fields must have a name.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("")
+ ->StartList("")
+ ->EndList()
+ ->RenderString("title", "noname")
+ ->EndObject();
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, RootNamedObject) {
+ Book expected;
+ expected.set_title("Annie");
+
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece("oops"),
+ StringPiece("Root element should not be named.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("oops")->RenderString("title", "Annie")->EndObject();
+ CheckOutput(expected, 7);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, RootNamedList) {
+ Book empty;
+
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece("oops"),
+ StringPiece("Root element should not be named.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartList("oops")->RenderString("", "item")->EndList();
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, RootUnnamedField) {
+ Book empty;
+
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece(""),
+ StringPiece("Root element must be a message.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->RenderBool("", true);
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, RootNamedField) {
+ Book empty;
+
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece("oops"),
+ StringPiece("Root element must be a message.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->RenderBool("oops", true);
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, NullValue) {
+ Book empty;
+
+ ow_->RenderNull("");
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, NullValueForMessageField) {
+ Book empty;
+
+ ow_->RenderNull("author");
+ CheckOutput(empty, 0);
+}
+
+TEST_P(ProtoStreamObjectWriterTest, NullValueForPrimitiveField) {
+ Book empty;
+
+ ow_->RenderNull("length");
+ CheckOutput(empty, 0);
+}
+
+class ProtoStreamObjectWriterTimestampDurationTest
+ : public BaseProtoStreamObjectWriterTest {
+ protected:
+ ProtoStreamObjectWriterTimestampDurationTest() {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(TimestampDuration::descriptor());
+ descriptors.push_back(google::protobuf::Timestamp::descriptor());
+ descriptors.push_back(google::protobuf::Duration::descriptor());
+ ResetTypeInfo(descriptors);
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtoStreamObjectWriterTimestampDurationTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, ParseTimestamp) {
+ TimestampDuration timestamp;
+ google::protobuf::Timestamp* ts = timestamp.mutable_ts();
+ ts->set_seconds(1448249855);
+ ts->set_nanos(33155000);
+
+ ow_->StartObject("")
+ ->RenderString("ts", "2015-11-23T03:37:35.033155Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ ParseTimestampYearNotZeroPadded) {
+ TimestampDuration timestamp;
+ google::protobuf::Timestamp* ts = timestamp.mutable_ts();
+ ts->set_seconds(-61665654145);
+ ts->set_nanos(33155000);
+
+ ow_->StartObject("")
+ ->RenderString("ts", "15-11-23T03:37:35.033155Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ ParseTimestampYearZeroPadded) {
+ TimestampDuration timestamp;
+ google::protobuf::Timestamp* ts = timestamp.mutable_ts();
+ ts->set_seconds(-61665654145);
+ ts->set_nanos(33155000);
+
+ ow_->StartObject("")
+ ->RenderString("ts", "0015-11-23T03:37:35.033155Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ ParseTimestampWithPositiveOffset) {
+ TimestampDuration timestamp;
+ google::protobuf::Timestamp* ts = timestamp.mutable_ts();
+ ts->set_seconds(1448249855);
+ ts->set_nanos(33155000);
+
+ ow_->StartObject("")
+ ->RenderString("ts", "2015-11-23T11:47:35.033155+08:10")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ ParseTimestampWithNegativeOffset) {
+ TimestampDuration timestamp;
+ google::protobuf::Timestamp* ts = timestamp.mutable_ts();
+ ts->set_seconds(1448249855);
+ ts->set_nanos(33155000);
+
+ ow_->StartObject("")
+ ->RenderString("ts", "2015-11-22T19:47:35.033155-07:50")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ TimestampWithInvalidOffset1) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "2016-03-07T15:14:23+")));
+
+ ow_->StartObject("")->RenderString("ts", "2016-03-07T15:14:23+")->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ TimestampWithInvalidOffset2) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "2016-03-07T15:14:23+08-10")));
+
+ ow_->StartObject("")
+ ->RenderString("ts", "2016-03-07T15:14:23+08-10")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ TimestampWithInvalidOffset3) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "2016-03-07T15:14:23+24:10")));
+
+ ow_->StartObject("")
+ ->RenderString("ts", "2016-03-07T15:14:23+24:10")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ TimestampWithInvalidOffset4) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "2016-03-07T15:14:23+04:60")));
+
+ ow_->StartObject("")
+ ->RenderString("ts", "2016-03-07T15:14:23+04:60")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError1) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: ")));
+
+ ow_->StartObject("")->RenderString("ts", "")->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError2) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: Z")));
+
+ ow_->StartObject("")->RenderString("ts", "Z")->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError3) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "1970-01-01T00:00:00.ABZ")));
+
+ ow_->StartObject("")
+ ->RenderString("ts", "1970-01-01T00:00:00.ABZ")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError4) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "-8031-10-18T00:00:00.000Z")));
+
+ ow_->StartObject("")
+ ->RenderString("ts", "-8031-10-18T00:00:00.000Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError5) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "2015-11-23T03:37:35.033155 Z")));
+
+ ow_->StartObject("")
+ // Whitespace in the Timestamp nanos is not allowed.
+ ->RenderString("ts", "2015-11-23T03:37:35.033155 Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError6) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "2015-11-23T03:37:35.033155 1234Z")));
+
+ ow_->StartObject("")
+ // Whitespace in the Timestamp nanos is not allowed.
+ ->RenderString("ts", "2015-11-23T03:37:35.033155 1234Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError7) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "2015-11-23T03:37:35.033abc155Z")));
+
+ ow_->StartObject("")
+ // Non-numeric characters in the Timestamp nanos is not allowed.
+ ->RenderString("ts", "2015-11-23T03:37:35.033abc155Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidTimestampError8) {
+ TimestampDuration timestamp;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece("Field 'ts', Invalid time format: "
+ "0-12-31T23:59:59.000Z")));
+
+ ow_->StartObject("")
+ ->RenderString("ts", "0-12-31T23:59:59.000Z")
+ ->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, ParseDuration) {
+ TimestampDuration duration;
+ google::protobuf::Duration* dur = duration.mutable_dur();
+ dur->set_seconds(1448216930);
+ dur->set_nanos(132262000);
+
+ ow_->StartObject("")->RenderString("dur", "1448216930.132262s")->EndObject();
+ CheckOutput(duration);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidDurationError1) {
+ TimestampDuration duration;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.Duration"),
+ StringPiece("Field 'dur', Illegal duration format; duration must "
+ "end with 's'")));
+
+ ow_->StartObject("")->RenderString("dur", "")->EndObject();
+ CheckOutput(duration);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidDurationError2) {
+ TimestampDuration duration;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.Duration"),
+ StringPiece("Field 'dur', Invalid duration format, failed to parse "
+ "seconds")));
+
+ ow_->StartObject("")->RenderString("dur", "s")->EndObject();
+ CheckOutput(duration);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidDurationError3) {
+ TimestampDuration duration;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.Duration"),
+ StringPiece("Field 'dur', Invalid duration format, failed to "
+ "parse nano seconds")));
+
+ ow_->StartObject("")->RenderString("dur", "123.DEFs")->EndObject();
+ CheckOutput(duration);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidDurationError4) {
+ TimestampDuration duration;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Duration"),
+ StringPiece("Field 'dur', Duration value exceeds limits")));
+
+ ow_->StartObject("")->RenderString("dur", "315576000002s")->EndObject();
+ CheckOutput(duration);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest, InvalidDurationError5) {
+ TimestampDuration duration;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.Duration"),
+ StringPiece("Field 'dur', Duration value exceeds limits")));
+
+ ow_->StartObject("")->RenderString("dur", "0.1000000001s")->EndObject();
+ CheckOutput(duration);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ MismatchedTimestampTypeInput) {
+ TimestampDuration timestamp;
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.Timestamp"),
+ StringPiece(
+ "Field 'ts', Invalid data type for timestamp, value is null")))
+ .With(Args<0>(HasObjectLocation("ts")));
+ ow_->StartObject("")->RenderNull("ts")->EndObject();
+ CheckOutput(timestamp);
+}
+
+TEST_P(ProtoStreamObjectWriterTimestampDurationTest,
+ MismatchedDurationTypeInput) {
+ TimestampDuration duration;
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.Duration"),
+ StringPiece(
+ "Field 'dur', Invalid data type for duration, value is null")))
+ .With(Args<0>(HasObjectLocation("dur")));
+ ow_->StartObject("")->RenderNull("dur")->EndObject();
+ CheckOutput(duration);
+}
+
+class ProtoStreamObjectWriterStructTest
+ : public BaseProtoStreamObjectWriterTest {
+ protected:
+ ProtoStreamObjectWriterStructTest() { ResetProtoWriter(); }
+
+ // Resets ProtoWriter with current set of options and other state.
+ void ResetProtoWriter() {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(StructType::descriptor());
+ descriptors.push_back(google::protobuf::Struct::descriptor());
+ ResetTypeInfo(descriptors);
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtoStreamObjectWriterStructTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+// TODO(skarvaje): Write tests for failure cases.
+TEST_P(ProtoStreamObjectWriterStructTest, StructRenderSuccess) {
+ StructType struct_type;
+ google::protobuf::Struct* s = struct_type.mutable_object();
+ s->mutable_fields()->operator[]("k1").set_number_value(123);
+ s->mutable_fields()->operator[]("k2").set_bool_value(true);
+
+ ow_->StartObject("")
+ ->StartObject("object")
+ ->RenderDouble("k1", 123)
+ ->RenderBool("k2", true)
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(struct_type);
+}
+
+TEST_P(ProtoStreamObjectWriterStructTest, StructNullInputSuccess) {
+ StructType struct_type;
+ EXPECT_CALL(listener_,
+ InvalidName(_, StringPiece(""),
+ StringPiece("Proto fields must have a name.")))
+ .With(Args<0>(HasObjectLocation("")));
+ ow_->StartObject("")->RenderNull("")->EndObject();
+ CheckOutput(struct_type);
+}
+
+TEST_P(ProtoStreamObjectWriterStructTest, StructInvalidInputFailure) {
+ StructType struct_type;
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_, StringPiece("type.googleapis.com/google.protobuf.Struct"),
+ StringPiece("true")))
+ .With(Args<0>(HasObjectLocation("object")));
+
+ ow_->StartObject("")->RenderBool("object", true)->EndObject();
+ CheckOutput(struct_type);
+}
+
+TEST_P(ProtoStreamObjectWriterStructTest, SimpleRepeatedStructMapKeyTest) {
+ EXPECT_CALL(
+ listener_,
+ InvalidName(_, StringPiece("gBike"),
+ StringPiece("Repeated map key: 'gBike' is already set.")));
+ ow_->StartObject("")
+ ->StartObject("object")
+ ->RenderString("gBike", "v1")
+ ->RenderString("gBike", "v2")
+ ->EndObject()
+ ->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterStructTest, RepeatedStructMapListKeyTest) {
+ EXPECT_CALL(
+ listener_,
+ InvalidName(_, StringPiece("k1"),
+ StringPiece("Repeated map key: 'k1' is already set.")));
+ ow_->StartObject("")
+ ->StartObject("object")
+ ->RenderString("k1", "v1")
+ ->StartList("k1")
+ ->RenderString("", "v2")
+ ->EndList()
+ ->EndObject()
+ ->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterStructTest, RepeatedStructMapObjectKeyTest) {
+ EXPECT_CALL(
+ listener_,
+ InvalidName(_, StringPiece("k1"),
+ StringPiece("Repeated map key: 'k1' is already set.")));
+ ow_->StartObject("")
+ ->StartObject("object")
+ ->StartObject("k1")
+ ->RenderString("sub_k1", "v1")
+ ->EndObject()
+ ->StartObject("k1")
+ ->RenderString("sub_k2", "v2")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterStructTest, OptionStructIntAsStringsTest) {
+ StructType struct_type;
+ google::protobuf::Struct* s = struct_type.mutable_object();
+ s->mutable_fields()->operator[]("k1").set_number_value(123);
+ s->mutable_fields()->operator[]("k2").set_bool_value(true);
+ s->mutable_fields()->operator[]("k3").set_string_value("-222222222");
+ s->mutable_fields()->operator[]("k4").set_string_value("33333333");
+
+ options_.struct_integers_as_strings = true;
+ ResetProtoWriter();
+
+ ow_->StartObject("")
+ ->StartObject("object")
+ ->RenderDouble("k1", 123)
+ ->RenderBool("k2", true)
+ ->RenderInt64("k3", -222222222)
+ ->RenderUint64("k4", 33333333)
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(struct_type);
+}
+
+class ProtoStreamObjectWriterMapTest : public BaseProtoStreamObjectWriterTest {
+ protected:
+ ProtoStreamObjectWriterMapTest()
+ : BaseProtoStreamObjectWriterTest(MapIn::descriptor()) {}
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtoStreamObjectWriterMapTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtoStreamObjectWriterMapTest, MapShouldNotAcceptList) {
+ MapIn mm;
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("Map"),
+ StringPiece("Cannot bind a list to map for field 'map_input'.")));
+ ow_->StartObject("")
+ ->StartList("map_input")
+ ->RenderString("a", "b")
+ ->EndList()
+ ->EndObject();
+ CheckOutput(mm);
+}
+
+TEST_P(ProtoStreamObjectWriterMapTest, RepeatedMapKeyTest) {
+ EXPECT_CALL(
+ listener_,
+ InvalidName(_, StringPiece("k1"),
+ StringPiece("Repeated map key: 'k1' is already set.")));
+ ow_->StartObject("")
+ ->RenderString("other", "test")
+ ->StartObject("map_input")
+ ->RenderString("k1", "v1")
+ ->RenderString("k1", "v2")
+ ->EndObject()
+ ->EndObject();
+}
+
+class ProtoStreamObjectWriterAnyTest : public BaseProtoStreamObjectWriterTest {
+ protected:
+ ProtoStreamObjectWriterAnyTest() {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(AnyOut::descriptor());
+ descriptors.push_back(google::protobuf::DoubleValue::descriptor());
+ descriptors.push_back(google::protobuf::Timestamp::descriptor());
+ descriptors.push_back(google::protobuf::Any::descriptor());
+ descriptors.push_back(google::protobuf::Value::descriptor());
+ descriptors.push_back(google::protobuf::Struct::descriptor());
+ ResetTypeInfo(descriptors);
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtoStreamObjectWriterAnyTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyRenderSuccess) {
+ AnyOut any;
+ google::protobuf::Any* any_type = any.mutable_any();
+ any_type->set_type_url("type.googleapis.com/google.protobuf.DoubleValue");
+ google::protobuf::DoubleValue d;
+ d.set_value(40.2);
+ any_type->set_value(d.SerializeAsString());
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.DoubleValue")
+ ->RenderDouble("value", 40.2)
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, RecursiveAny) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+ any->set_type_url("type.googleapis.com/google.protobuf.Any");
+
+ ::google::protobuf::Any nested_any;
+ nested_any.set_type_url(
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM");
+
+ AnyM m;
+ m.set_foo("foovalue");
+ nested_any.set_value(m.SerializeAsString());
+
+ any->set_value(nested_any.SerializeAsString());
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Any")
+ ->StartObject("value")
+ ->RenderString("@type",
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM")
+ ->RenderString("foo", "foovalue")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, DoubleRecursiveAny) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+ any->set_type_url("type.googleapis.com/google.protobuf.Any");
+
+ ::google::protobuf::Any nested_any;
+ nested_any.set_type_url("type.googleapis.com/google.protobuf.Any");
+
+ ::google::protobuf::Any second_nested_any;
+ second_nested_any.set_type_url(
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM");
+
+ AnyM m;
+ m.set_foo("foovalue");
+ second_nested_any.set_value(m.SerializeAsString());
+
+ nested_any.set_value(second_nested_any.SerializeAsString());
+ any->set_value(nested_any.SerializeAsString());
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Any")
+ ->StartObject("value")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Any")
+ ->StartObject("value")
+ ->RenderString("@type",
+ "type.googleapis.com/google.protobuf.testing.anys.AnyM")
+ ->RenderString("foo", "foovalue")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, EmptyAnyFromEmptyObject) {
+ AnyOut out;
+ out.mutable_any();
+
+ ow_->StartObject("")->StartObject("any")->EndObject()->EndObject();
+
+ CheckOutput(out, 2);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithoutTypeUrlFails1) {
+ AnyOut any;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_, StringPiece("Any"),
+ StringPiece("Missing or invalid @type for any field in "
+ "google.protobuf.testing.anys.AnyOut")));
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->StartObject("another")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithoutTypeUrlFails2) {
+ AnyOut any;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_, StringPiece("Any"),
+ StringPiece("Missing or invalid @type for any field in "
+ "google.protobuf.testing.anys.AnyOut")));
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->StartList("another")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithoutTypeUrlFails3) {
+ AnyOut any;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_, StringPiece("Any"),
+ StringPiece("Missing or invalid @type for any field in "
+ "google.protobuf.testing.anys.AnyOut")));
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("value", "somevalue")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithInvalidTypeUrlFails) {
+ AnyOut any;
+
+ EXPECT_CALL(listener_,
+ InvalidValue(
+ _, StringPiece("Any"),
+ StringPiece("Invalid type URL, type URLs must be of the form "
+ "'type.googleapis.com/<typename>', got: "
+ "type.other.com/some.Type")));
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.other.com/some.Type")
+ ->RenderDouble("value", 40.2)
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithUnknownTypeFails) {
+ AnyOut any;
+
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_, StringPiece("Any"),
+ StringPiece("Invalid type URL, unknown type: some.Type")));
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/some.Type")
+ ->RenderDouble("value", 40.2)
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyNullInputFails) {
+ AnyOut any;
+
+ ow_->StartObject("")->RenderNull("any")->EndObject();
+ CheckOutput(any);
+}
+
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWellKnownTypeErrorTest) {
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("Any"),
+ StringPiece("Invalid time format: ")));
+
+ AnyOut any;
+ google::protobuf::Any* any_type = any.mutable_any();
+ any_type->set_type_url("type.googleapis.com/google.protobuf.Timestamp");
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Timestamp")
+ ->RenderString("value", "")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Value",
+// "value": "abc"
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithNestedPrimitiveValue) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+
+ ::google::protobuf::Value value;
+ value.set_string_value("abc");
+ any->PackFrom(value);
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Value")
+ ->RenderString("value", "abc")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(out);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Value",
+// "value": {
+// "foo": "abc"
+// }
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithNestedObjectValue) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+
+ ::google::protobuf::Value value;
+ (*value.mutable_struct_value()->mutable_fields())["foo"].set_string_value(
+ "abc");
+ any->PackFrom(value);
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Value")
+ ->StartObject("value")
+ ->RenderString("foo", "abc")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(out);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Value",
+// "value": ["hello"],
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWithNestedArrayValue) {
+ AnyOut out;
+ ::google::protobuf::Any* any = out.mutable_any();
+
+ ::google::protobuf::Value value;
+ value.mutable_list_value()->add_values()->set_string_value("hello");
+ any->PackFrom(value);
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Value")
+ ->StartList("value")
+ ->RenderString("", "hello")
+ ->EndList()
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(out);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Value",
+// "not_value": ""
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest,
+ AnyWellKnownTypesNoValueFieldForPrimitive) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("Any"),
+ StringPiece("Expect a \"value\" field for well-known types.")));
+ AnyOut any;
+ google::protobuf::Any* any_type = any.mutable_any();
+ any_type->set_type_url("type.googleapis.com/google.protobuf.Value");
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Value")
+ ->RenderString("not_value", "")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Value",
+// "not_value": {}
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWellKnownTypesNoValueFieldForObject) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("Any"),
+ StringPiece("Expect a \"value\" field for well-known types.")));
+ AnyOut any;
+ google::protobuf::Any* any_type = any.mutable_any();
+ any_type->set_type_url("type.googleapis.com/google.protobuf.Value");
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Value")
+ ->StartObject("not_value")
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Value",
+// "not_value": [],
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWellKnownTypesNoValueFieldForArray) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("Any"),
+ StringPiece("Expect a \"value\" field for well-known types.")));
+ AnyOut any;
+ google::protobuf::Any* any_type = any.mutable_any();
+ any_type->set_type_url("type.googleapis.com/google.protobuf.Value");
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Value")
+ ->StartList("not_value")
+ ->EndList()
+ ->EndObject()
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Struct",
+// "value": "",
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWellKnownTypesExpectObjectForStruct) {
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("Any"),
+ StringPiece("Expect a JSON object.")));
+ AnyOut any;
+ google::protobuf::Any* any_type = any.mutable_any();
+ any_type->set_type_url("type.googleapis.com/google.protobuf.Struct");
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Struct")
+ ->RenderString("value", "")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+// Test the following case:
+//
+// {
+// "any": {
+// "@type": "type.googleapis.com/google.protobuf.Any",
+// "value": "",
+// }
+// }
+TEST_P(ProtoStreamObjectWriterAnyTest, AnyWellKnownTypesExpectObjectForAny) {
+ EXPECT_CALL(listener_, InvalidValue(_, StringPiece("Any"),
+ StringPiece("Expect a JSON object.")));
+ AnyOut any;
+ google::protobuf::Any* any_type = any.mutable_any();
+ any_type->set_type_url("type.googleapis.com/google.protobuf.Any");
+
+ ow_->StartObject("")
+ ->StartObject("any")
+ ->RenderString("@type", "type.googleapis.com/google.protobuf.Any")
+ ->RenderString("value", "")
+ ->EndObject()
+ ->EndObject();
+ CheckOutput(any);
+}
+
+class ProtoStreamObjectWriterFieldMaskTest
+ : public BaseProtoStreamObjectWriterTest {
+ protected:
+ ProtoStreamObjectWriterFieldMaskTest() {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(FieldMaskTest::descriptor());
+ descriptors.push_back(google::protobuf::FieldMask::descriptor());
+ ResetTypeInfo(descriptors);
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtoStreamObjectWriterFieldMaskTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, SimpleFieldMaskTest) {
+ FieldMaskTest expected;
+ expected.set_id("1");
+ expected.mutable_single_mask()->add_paths("path1");
+
+ ow_->StartObject("");
+ ow_->RenderString("id", "1");
+ ow_->RenderString("single_mask", "path1");
+ ow_->EndObject();
+
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, MutipleMasksInCompactForm) {
+ FieldMaskTest expected;
+ expected.set_id("1");
+ expected.mutable_single_mask()->add_paths("camel_case1");
+ expected.mutable_single_mask()->add_paths("camel_case2");
+ expected.mutable_single_mask()->add_paths("camel_case3");
+
+ ow_->StartObject("");
+ ow_->RenderString("id", "1");
+ ow_->RenderString("single_mask", "camelCase1,camelCase2,camelCase3");
+ ow_->EndObject();
+
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, RepeatedFieldMaskTest) {
+ FieldMaskTest expected;
+ expected.set_id("1");
+ google::protobuf::FieldMask* mask = expected.add_repeated_mask();
+ mask->add_paths("field1");
+ mask->add_paths("field2");
+ expected.add_repeated_mask()->add_paths("field3");
+
+ ow_->StartObject("");
+ ow_->RenderString("id", "1");
+ ow_->StartList("repeated_mask");
+ ow_->RenderString("", "field1,field2");
+ ow_->RenderString("", "field3");
+ ow_->EndList();
+ ow_->EndObject();
+
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, EmptyFieldMaskTest) {
+ FieldMaskTest expected;
+ expected.set_id("1");
+
+ ow_->StartObject("");
+ ow_->RenderString("id", "1");
+ ow_->RenderString("single_mask", "");
+ ow_->EndObject();
+
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, MaskUsingApiaryStyleShouldWork) {
+ FieldMaskTest expected;
+ expected.set_id("1");
+
+ ow_->StartObject("");
+ ow_->RenderString("id", "1");
+ // Case1
+ ow_->RenderString("single_mask",
+ "outerField(camelCase1,camelCase2,camelCase3)");
+ expected.mutable_single_mask()->add_paths("outer_field.camel_case1");
+ expected.mutable_single_mask()->add_paths("outer_field.camel_case2");
+ expected.mutable_single_mask()->add_paths("outer_field.camel_case3");
+
+ ow_->StartList("repeated_mask");
+
+ ow_->RenderString("", "a(field1,field2)");
+ google::protobuf::FieldMask* mask = expected.add_repeated_mask();
+ mask->add_paths("a.field1");
+ mask->add_paths("a.field2");
+
+ ow_->RenderString("", "a(field3)");
+ mask = expected.add_repeated_mask();
+ mask->add_paths("a.field3");
+
+ ow_->RenderString("", "a()");
+ expected.add_repeated_mask();
+
+ ow_->RenderString("", "a(,)");
+ expected.add_repeated_mask();
+
+ ow_->RenderString("", "a(field1(field2(field3)))");
+ mask = expected.add_repeated_mask();
+ mask->add_paths("a.field1.field2.field3");
+
+ ow_->RenderString("", "a(field1(field2(field3,field4),field5),field6)");
+ mask = expected.add_repeated_mask();
+ mask->add_paths("a.field1.field2.field3");
+ mask->add_paths("a.field1.field2.field4");
+ mask->add_paths("a.field1.field5");
+ mask->add_paths("a.field6");
+
+ ow_->RenderString("", "a(id,field1(id,field2(field3,field4),field5),field6)");
+ mask = expected.add_repeated_mask();
+ mask->add_paths("a.id");
+ mask->add_paths("a.field1.id");
+ mask->add_paths("a.field1.field2.field3");
+ mask->add_paths("a.field1.field2.field4");
+ mask->add_paths("a.field1.field5");
+ mask->add_paths("a.field6");
+
+ ow_->RenderString("", "a(((field3,field4)))");
+ mask = expected.add_repeated_mask();
+ mask->add_paths("a.field3");
+ mask->add_paths("a.field4");
+
+ ow_->EndList();
+ ow_->EndObject();
+
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, MoreCloseThanOpenParentheses) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.FieldMask"),
+ StringPiece("Field 'single_mask', Invalid FieldMask 'a(b,c))'. "
+ "Cannot find matching '(' for all ')'.")));
+
+ ow_->StartObject("");
+ ow_->RenderString("id", "1");
+ ow_->RenderString("single_mask", "a(b,c))");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, MoreOpenThanCloseParentheses) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.FieldMask"),
+ StringPiece(
+ "Field 'single_mask', Invalid FieldMask 'a(((b,c)'. Cannot "
+ "find matching ')' for all '('.")));
+
+ ow_->StartObject("");
+ ow_->RenderString("id", "1");
+ ow_->RenderString("single_mask", "a(((b,c)");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, PathWithMapKeyShouldWork) {
+ FieldMaskTest expected;
+ expected.mutable_single_mask()->add_paths("path.to.map[\"key1\"]");
+ expected.mutable_single_mask()->add_paths(
+ "path.to.map[\"e\\\"[]][scape\\\"\"]");
+ expected.mutable_single_mask()->add_paths("path.to.map[\"key2\"]");
+
+ ow_->StartObject("");
+ ow_->RenderString("single_mask",
+ "path.to.map[\"key1\"],path.to.map[\"e\\\"[]][scape\\\"\"],"
+ "path.to.map[\"key2\"]");
+ ow_->EndObject();
+
+ CheckOutput(expected);
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest,
+ MapKeyMustBeAtTheEndOfAPathSegment) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("type.googleapis.com/google.protobuf.FieldMask"),
+ StringPiece("Field 'single_mask', Invalid FieldMask "
+ "'path.to.map[\"key1\"]a,path.to.map[\"key2\"]'. "
+ "Map keys should be at the end of a path segment.")));
+
+ ow_->StartObject("");
+ ow_->RenderString("single_mask",
+ "path.to.map[\"key1\"]a,path.to.map[\"key2\"]");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, MapKeyMustEnd) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.FieldMask"),
+ StringPiece("Field 'single_mask', Invalid FieldMask "
+ "'path.to.map[\"key1\"'. Map keys should be "
+ "represented as [\"some_key\"].")));
+
+ ow_->StartObject("");
+ ow_->RenderString("single_mask", "path.to.map[\"key1\"");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, MapKeyMustBeEscapedCorrectly) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(_,
+ StringPiece("type.googleapis.com/google.protobuf.FieldMask"),
+ StringPiece("Field 'single_mask', Invalid FieldMask "
+ "'path.to.map[\"ke\"y1\"]'. Map keys should be "
+ "represented as [\"some_key\"].")));
+
+ ow_->StartObject("");
+ ow_->RenderString("single_mask", "path.to.map[\"ke\"y1\"]");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterFieldMaskTest, MapKeyCanContainAnyChars) {
+ FieldMaskTest expected;
+ expected.mutable_single_mask()->add_paths(
+ // \xE5\xAD\x99 is the UTF-8 byte sequence for chinese character å­™.
+ // We cannot embed non-ASCII characters in the code directly because
+ // some windows compilers will try to interpret them using the system's
+ // current encoding and end up with invalid UTF-8 byte sequence.
+ "path.to.map[\"(),[],\\\"'!@#$%^&*123_|War\xE5\xAD\x99,./?><\\\\\"]");
+ expected.mutable_single_mask()->add_paths("path.to.map[\"key2\"]");
+
+ ow_->StartObject("");
+ ow_->RenderString(
+ "single_mask",
+ "path.to.map[\"(),[],\\\"'!@#$%^&*123_|War\xE5\xAD\x99,./?><\\\\\"],"
+ "path.to.map[\"key2\"]");
+ ow_->EndObject();
+
+ CheckOutput(expected);
+}
+
+class ProtoStreamObjectWriterOneOfsTest
+ : public BaseProtoStreamObjectWriterTest {
+ protected:
+ ProtoStreamObjectWriterOneOfsTest() {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(OneOfsRequest::descriptor());
+ descriptors.push_back(google::protobuf::Struct::descriptor());
+ ResetTypeInfo(descriptors);
+ }
+};
+
+INSTANTIATE_TEST_CASE_P(DifferentTypeInfoSourceTest,
+ ProtoStreamObjectWriterOneOfsTest,
+ ::testing::Values(
+ testing::USE_TYPE_RESOLVER));
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForPrimitiveTypesTest) {
+ EXPECT_CALL(
+ listener_,
+ InvalidValue(
+ _, StringPiece("oneof"),
+ StringPiece(
+ "oneof field 'data' is already set. Cannot set 'intData'")));
+
+ ow_->StartObject("");
+ ow_->RenderString("strData", "blah");
+ ow_->RenderString("intData", "123");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForMessageTypesPrimitiveFirstTest) {
+ // Test for setting primitive oneof field first and then message field.
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'messageData'")));
+
+ // JSON: { "strData": "blah", "messageData": { "dataValue": 123 } }
+ ow_->StartObject("");
+ ow_->RenderString("strData", "blah");
+ ow_->StartObject("messageData");
+ ow_->RenderInt32("dataValue", 123);
+ ow_->EndObject();
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForMessageTypesMessageFirstTest) {
+ // Test for setting message oneof field first and then primitive field.
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'strData'")));
+
+ // JSON: { "messageData": { "dataValue": 123 }, "strData": "blah" }
+ ow_->StartObject("");
+ ow_->StartObject("messageData");
+ ow_->RenderInt32("dataValue", 123);
+ ow_->EndObject();
+ ow_->RenderString("strData", "blah");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForStructTypesPrimitiveFirstTest) {
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'structData'")));
+
+ // JSON: { "strData": "blah", "structData": { "a": "b" } }
+ ow_->StartObject("");
+ ow_->RenderString("strData", "blah");
+ ow_->StartObject("structData");
+ ow_->RenderString("a", "b");
+ ow_->EndObject();
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForStructTypesStructFirstTest) {
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'strData'")));
+
+ // JSON: { "structData": { "a": "b" }, "strData": "blah" }
+ ow_->StartObject("");
+ ow_->StartObject("structData");
+ ow_->RenderString("a", "b");
+ ow_->EndObject();
+ ow_->RenderString("strData", "blah");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForStructValueTypesTest) {
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'valueData'")));
+
+ // JSON: { "messageData": { "dataValue": 123 }, "valueData": { "a": "b" } }
+ ow_->StartObject("");
+ ow_->StartObject("messageData");
+ ow_->RenderInt32("dataValue", 123);
+ ow_->EndObject();
+ ow_->StartObject("valueData");
+ ow_->RenderString("a", "b");
+ ow_->EndObject();
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForWellKnownTypesPrimitiveFirstTest) {
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'tsData'")));
+
+ // JSON: { "intData": 123, "tsData": "1970-01-02T01:00:00.000Z" }
+ ow_->StartObject("");
+ ow_->RenderInt32("intData", 123);
+ ow_->RenderString("tsData", "1970-01-02T01:00:00.000Z");
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForWellKnownTypesWktFirstTest) {
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'intData'")));
+
+ // JSON: { "tsData": "1970-01-02T01:00:00.000Z", "intData": 123 }
+ ow_->StartObject("");
+ ow_->RenderString("tsData", "1970-01-02T01:00:00.000Z");
+ ow_->RenderInt32("intData", 123);
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForWellKnownTypesAndMessageTest) {
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'messageData'")));
+
+ // JSON: { "tsData": "1970-01-02T01:00:00.000Z",
+ // "messageData": { "dataValue": 123 } }
+ ow_->StartObject("");
+ ow_->RenderString("tsData", "1970-01-02T01:00:00.000Z");
+ ow_->StartObject("messageData");
+ ow_->RenderInt32("dataValue", 123);
+ ow_->EndObject();
+ ow_->EndObject();
+}
+
+TEST_P(ProtoStreamObjectWriterOneOfsTest,
+ MultipleOneofsFailForOneofWithinAnyTest) {
+ EXPECT_CALL(listener_,
+ InvalidValue(_, StringPiece("oneof"),
+ StringPiece("oneof field 'data' is already set. "
+ "Cannot set 'intData'")));
+
+ using google::protobuf::testing::oneofs::OneOfsRequest;
+ // JSON:
+ // { "anyData":
+ // { "@type":
+ // "type.googleapis.com/google.protobuf.testing.oneofs.OneOfsRequest",
+ // "strData": "blah",
+ // "intData": 123
+ // }
+ // }
+ ow_->StartObject("");
+ ow_->StartObject("anyData");
+ ow_->RenderString(
+ "@type",
+ "type.googleapis.com/google.protobuf.testing.oneofs.OneOfsRequest");
+ ow_->RenderString("strData", "blah");
+ ow_->RenderInt32("intData", 123);
+ ow_->EndObject();
+ ow_->EndObject();
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/structured_objectwriter.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/structured_objectwriter.h
new file mode 100644
index 0000000000..3f065d6b1c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/structured_objectwriter.h
@@ -0,0 +1,118 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_STRUCTURED_OBJECTWRITER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_STRUCTURED_OBJECTWRITER_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+
+#include <google/protobuf/stubs/casts.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/util/internal/object_writer.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// An StructuredObjectWriter is an ObjectWriter for writing
+// tree-structured data in a stream of events representing objects
+// and collections. Implementation of this interface can be used to
+// write an object stream to an in-memory structure, protobufs,
+// JSON, XML, or any other output format desired. The ObjectSource
+// interface is typically used as the source of an object stream.
+//
+// See JsonObjectWriter for a sample implementation of
+// StructuredObjectWriter and its use.
+//
+// Derived classes could be thread-unsafe.
+class LIBPROTOBUF_EXPORT StructuredObjectWriter : public ObjectWriter {
+ public:
+ virtual ~StructuredObjectWriter() {}
+
+ protected:
+ // A base element class for subclasses to extend, makes tracking state easier.
+ //
+ // StructuredObjectWriter behaves as a visitor. BaseElement represents a node
+ // in the input tree. Implementation of StructuredObjectWriter should also
+ // extend BaseElement to keep track of the location in the input tree.
+ class LIBPROTOBUF_EXPORT BaseElement {
+ public:
+ // Takes ownership of the parent Element.
+ explicit BaseElement(BaseElement* parent)
+ : parent_(parent), level_(parent == NULL ? 0 : parent->level() + 1) {}
+ virtual ~BaseElement() {}
+
+ // Releases ownership of the parent and returns a pointer to it.
+ template <typename ElementType>
+ ElementType* pop() {
+ return down_cast<ElementType*>(parent_.release());
+ }
+
+ // Returns true if this element is the root.
+ bool is_root() const { return parent_ == NULL; }
+
+ // Returns the number of hops from this element to the root element.
+ int level() const { return level_; }
+
+ protected:
+ // Returns pointer to parent element without releasing ownership.
+ virtual BaseElement* parent() const { return parent_.get(); }
+
+ private:
+ // Pointer to the parent Element.
+ google::protobuf::scoped_ptr<BaseElement> parent_;
+
+ // Number of hops to the root Element.
+ // The root Element has NULL parent_ and a level_ of 0.
+ const int level_;
+
+ GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(BaseElement);
+ };
+
+ StructuredObjectWriter() {}
+
+ // Returns the current element. Used for indentation and name overrides.
+ virtual BaseElement* element() = 0;
+
+ private:
+ // Do not add any data members to this class.
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StructuredObjectWriter);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_STRUCTURED_OBJECTWRITER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/anys.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/anys.proto
new file mode 100644
index 0000000000..18c59cbb96
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/anys.proto
@@ -0,0 +1,53 @@
+// 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.
+
+// Proto to test Proto3 Any serialization.
+syntax = "proto3";
+
+package google.protobuf.testing.anys;
+option java_package = "com.google.protobuf.testing.anys";
+
+import "google/protobuf/any.proto";
+
+message AnyIn {
+ string something = 1;
+}
+
+message AnyOut {
+ google.protobuf.Any any = 1;
+}
+
+message AnyM {
+ string foo = 1;
+}
+
+service TestService {
+ rpc Call(AnyIn) returns (AnyOut);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/books.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/books.proto
new file mode 100644
index 0000000000..1cbbba4781
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/books.proto
@@ -0,0 +1,187 @@
+// 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: sven@google.com (Sven Mawson)
+//
+// Sample protos for testing.
+syntax = "proto2";
+
+package google.protobuf.testing;
+
+// A book
+message Book {
+ optional string title = 1;
+ optional Author author = 2;
+ optional uint32 length = 3;
+ optional int64 published = 4;
+ optional bytes content = 5;
+
+ optional group Data = 6 {
+ optional uint32 year = 7;
+ optional string copyright = 8;
+ }
+
+ message Label {
+ optional string key = 1;
+ optional string value = 2;
+ }
+
+ optional Publisher publisher = 9;
+ repeated Label labels = 10;
+
+ enum Type {
+ FICTION = 1;
+ KIDS = 2;
+ ACTION_AND_ADVENTURE = 3;
+ }
+ optional Type type = 11;
+
+ extensions 200 to 499;
+}
+
+// A publisher of a book, tests required fields.
+message Publisher {
+ required string name = 1;
+}
+
+// An author of a book
+message Author {
+ optional uint64 id = 1 [json_name = "@id"];
+ optional string name = 2;
+ repeated string pseudonym = 3;
+ optional bool alive = 4;
+ repeated Author friend = 5;
+}
+
+// For testing resiliency of our protostream parser.
+// Field numbers of Author are reused for something else.
+message BadAuthor {
+ optional string id = 1; // non-length-delimited to length-delimited.
+ repeated uint64 name = 2; // string to repeated (both length-delimited).
+ optional string pseudonym = 3; // Repeated to optional.
+ repeated bool alive = 4 [packed=true]; // Optional to repeated.
+}
+
+// All primitive types
+message Primitive {
+ // 32 bit numbers:
+ optional fixed32 fix32 = 1;
+ optional uint32 u32 = 2;
+ optional int32 i32 = 3;
+ optional sfixed32 sf32 = 4;
+ optional sint32 s32 = 5;
+
+ // 64 bit numbers:
+ optional fixed64 fix64 = 6;
+ optional uint64 u64 = 7;
+ optional int64 i64 = 8;
+ optional sfixed64 sf64 = 9;
+ optional sint64 s64 = 10;
+
+ // The other stuff.
+ optional string str = 11;
+ optional bytes bytes = 12;
+ optional float float = 13;
+ optional double double = 14;
+ optional bool bool = 15;
+
+ // repeated 32 bit numbers:
+ repeated fixed32 rep_fix32 = 16;
+ repeated uint32 rep_u32 = 17;
+ repeated int32 rep_i32 = 18;
+ repeated sfixed32 rep_sf32 = 19;
+ repeated sint32 rep_s32 = 20;
+
+ // repeated 64 bit numbers:
+ repeated fixed64 rep_fix64 = 21;
+ repeated uint64 rep_u64 = 22;
+ repeated int64 rep_i64 = 23;
+ repeated sfixed64 rep_sf64 = 24;
+ repeated sint64 rep_s64 = 25;
+
+ // repeated other stuff:
+ repeated string rep_str = 26;
+ repeated bytes rep_bytes = 27;
+ repeated float rep_float = 28;
+ repeated double rep_double = 29;
+ repeated bool rep_bool = 30;
+}
+
+// Test packed versions of all repeated primitives.
+// The field numbers should match their non-packed version in Primitive message.
+message PackedPrimitive {
+ // repeated 32 bit numbers:
+ repeated fixed32 rep_fix32 = 16 [packed=true];
+ repeated uint32 rep_u32 = 17 [packed=true];
+ repeated int32 rep_i32 = 18 [packed=true];
+ repeated sfixed32 rep_sf32 = 19 [packed=true];
+ repeated sint32 rep_s32 = 20 [packed=true];
+
+ // repeated 64 bit numbers:
+ repeated fixed64 rep_fix64 = 21 [packed=true];
+ repeated uint64 rep_u64 = 22 [packed=true];
+ repeated int64 rep_i64 = 23 [packed=true];
+ repeated sfixed64 rep_sf64 = 24 [packed=true];
+ repeated sint64 rep_s64 = 25 [packed=true];
+
+ // repeated other stuff:
+ repeated float rep_float = 28 [packed=true];
+ repeated double rep_double = 29 [packed=true];
+ repeated bool rep_bool = 30 [packed=true];
+}
+
+// Test extensions.
+extend Book {
+ repeated Author more_author = 201;
+}
+
+// Test nested extensions.
+message NestedBook {
+ extend Book {
+ optional NestedBook another_book = 301;
+ }
+ // Recurse
+ optional Book book = 1;
+}
+
+// For testing resiliency of our protostream parser.
+// Field number of NestedBook is reused for something else.
+message BadNestedBook {
+ repeated uint32 book = 1 [packed=true]; // Packed to optional message.
+}
+
+// A recursively defined message.
+message Cyclic {
+ optional int32 m_int = 1;
+ optional string m_str = 2;
+ optional Book m_book = 3;
+ repeated Author m_author = 5;
+ optional Cyclic m_cyclic = 4;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value.proto
new file mode 100644
index 0000000000..cccc741c2d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value.proto
@@ -0,0 +1,170 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf.testing;
+
+import "google/protobuf/any.proto";
+import "google/protobuf/struct.proto";
+import "google/protobuf/wrappers.proto";
+
+message DefaultValueTestCases {
+ DoubleMessage empty_double = 1;
+ DoubleMessage double_with_default_value = 2;
+ DoubleMessage double_with_nondefault_value = 3;
+ DoubleMessage repeated_double = 4;
+ DoubleMessage nested_message = 5;
+ DoubleMessage repeated_nested_message = 6;
+ DoubleMessage double_message_with_oneof = 7;
+ StructMessage empty_struct = 201;
+ StructMessage empty_struct2 = 202;
+ StructMessage struct_with_null_value = 203;
+ StructMessage struct_with_values = 204;
+ StructMessage struct_with_nested_struct = 205;
+ StructMessage struct_with_nested_list = 206;
+ StructMessage struct_with_list_of_nulls = 207;
+ StructMessage struct_with_list_of_lists = 208;
+ StructMessage struct_with_list_of_structs = 209;
+ google.protobuf.Struct top_level_struct = 210;
+ ValueMessage value_wrapper_simple = 212;
+ ValueMessage value_wrapper_with_struct = 213;
+ ValueMessage value_wrapper_with_list = 214;
+ ListValueMessage list_value_wrapper = 215;
+ google.protobuf.Value top_level_value_simple = 216;
+ google.protobuf.Value top_level_value_with_struct = 217;
+ google.protobuf.Value top_level_value_with_list = 218;
+ google.protobuf.ListValue top_level_listvalue = 219;
+ AnyMessage empty_any = 301;
+ AnyMessage type_only_any = 302;
+ AnyMessage recursive_any = 303;
+ AnyMessage any_with_message_value = 304;
+ AnyMessage any_with_nested_message = 305;
+ AnyMessage any_with_message_containing_map = 306;
+ AnyMessage any_with_message_containing_struct = 307;
+ google.protobuf.Any top_level_any = 308;
+ StringtoIntMap empty_map = 401;
+ StringtoIntMap string_to_int = 402;
+ IntToStringMap int_to_string = 403;
+ MixedMap mixed1 = 404;
+ MixedMap2 mixed2 = 405;
+ MixedMap2 empty_mixed2 = 406;
+ MessageMap map_of_objects = 407;
+ MixedMap mixed_empty = 408;
+ MessageMap message_map_empty = 409;
+ DoubleValueMessage double_value = 501;
+ DoubleValueMessage double_value_default = 502;
+}
+
+message DoubleMessage {
+ double double_value = 1;
+ repeated double repeated_double = 2;
+ DoubleMessage nested_message = 3;
+ repeated DoubleMessage repeated_nested_message = 4;
+ google.protobuf.DoubleValue double_wrapper = 100;
+ oneof value {
+ string str_value = 112;
+ int64 num_value = 113;
+ }
+}
+
+message StructMessage {
+ google.protobuf.Struct struct = 1;
+}
+
+message ValueMessage {
+ google.protobuf.Value value = 1;
+}
+
+message ListValueMessage {
+ google.protobuf.ListValue shopping_list = 1;
+}
+message RequestMessage {
+ string content = 1;
+}
+
+// A test service.
+service DefaultValueTestService {
+ // A test method.
+ rpc Call(RequestMessage) returns (DefaultValueTestCases);
+}
+
+message AnyMessage {
+ google.protobuf.Any any = 1;
+ AnyData data = 2;
+}
+
+message AnyData {
+ int32 attr = 1;
+ string str = 2;
+ repeated string msgs = 3;
+ AnyData nested_data = 4;
+ map<string, string> map_data = 7;
+ google.protobuf.Struct struct_data = 8;
+ repeated AnyData repeated_data = 9;
+}
+
+message StringtoIntMap {
+ map<string, int32> map = 1;
+}
+
+message IntToStringMap {
+ map<int32, string> map = 1;
+}
+
+message MixedMap {
+ string msg = 1;
+ map<string, float> map = 2;
+ int32 int_value = 3;
+}
+
+message MixedMap2 {
+ enum E {
+ E0 = 0;
+ E1 = 1;
+ E2 = 2;
+ E3 = 3;
+ }
+ map<int32, bool> map = 1;
+ E ee = 2;
+ string msg = 4;
+}
+
+message MessageMap {
+ message M {
+ int32 inner_int = 1;
+ string inner_text = 2;
+ }
+ map<string, M> map = 1;
+}
+
+message DoubleValueMessage {
+ google.protobuf.DoubleValue double = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value_test.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value_test.proto
new file mode 100644
index 0000000000..932883410e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/default_value_test.proto
@@ -0,0 +1,53 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf.testing;
+
+message DefaultValueTest {
+ double double_value = 1;
+ repeated double repeated_double = 2;
+ float float_value = 3;
+ int64 int64_value = 5;
+ uint64 uint64_value = 7;
+ int32 int32_value = 9;
+ uint32 uint32_value = 11;
+ bool bool_value = 13;
+ string string_value = 15;
+ bytes bytes_value = 17 [ctype = CORD];
+
+ enum EnumDefault {
+ ENUM_FIRST = 0;
+ ENUM_SECOND = 1;
+ ENUM_THIRD = 2;
+ }
+ EnumDefault enum_value = 18;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/field_mask.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/field_mask.proto
new file mode 100644
index 0000000000..e8b2bc5f2e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/field_mask.proto
@@ -0,0 +1,71 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf.testing;
+
+import "google/protobuf/field_mask.proto";
+
+message NestedFieldMask {
+ string data = 1;
+ google.protobuf.FieldMask single_mask = 2;
+ repeated google.protobuf.FieldMask repeated_mask = 3;
+}
+
+message FieldMaskTest {
+ string id = 1;
+ google.protobuf.FieldMask single_mask = 2;
+ repeated google.protobuf.FieldMask repeated_mask = 3;
+ repeated NestedFieldMask nested_mask = 4;
+}
+
+message FieldMaskTestCases {
+ FieldMaskWrapper single_mask = 1;
+ FieldMaskWrapper multiple_mask = 2;
+ FieldMaskWrapper snake_camel = 3;
+ FieldMaskWrapper empty_field = 4;
+ FieldMaskWrapper apiary_format1 = 5;
+ FieldMaskWrapper apiary_format2 = 6;
+ FieldMaskWrapper apiary_format3 = 7;
+ FieldMaskWrapper map_key1 = 8;
+ FieldMaskWrapper map_key2 = 9;
+ FieldMaskWrapper map_key3 = 10;
+ FieldMaskWrapper map_key4 = 11;
+ FieldMaskWrapper map_key5 = 12;
+}
+
+message FieldMaskWrapper {
+ google.protobuf.FieldMask mask = 1;
+}
+
+service FieldMaskTestService {
+ rpc Call(FieldMaskTestCases) returns (FieldMaskTestCases);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/maps.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/maps.proto
new file mode 100644
index 0000000000..6475ecddc2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/maps.proto
@@ -0,0 +1,86 @@
+// 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.
+
+// Proto to test proto3 maps.
+syntax = "proto3";
+
+package google.protobuf.testing.maps;
+option java_package = "com.google.protobuf.testing.maps";
+
+message MapIn {
+ string other = 1;
+ repeated string things = 2;
+ map<string, string> map_input = 3;
+}
+
+message MapOut {
+ map<string, MapM> map1 = 1;
+ map<string, MapOut> map2 = 2;
+ map<int32, string> map3 = 3;
+ map<bool, string> map4 = 5;
+ string bar = 4;
+}
+
+// A message with exactly the same wire representation as MapOut, but using
+// repeated message fields instead of map fields. We use this message to test
+// the wire-format compatibility of the JSON transcoder (e.g., whether it
+// handles missing keys correctly).
+message MapOutWireFormat {
+ message Map1Entry {
+ string key = 1;
+ MapM value = 2;
+ }
+ repeated Map1Entry map1 = 1;
+ message Map2Entry {
+ string key = 1;
+ MapOut value = 2;
+ }
+ repeated Map2Entry map2 = 2;
+ message Map3Entry {
+ int32 key = 1;
+ string value = 2;
+ }
+ repeated Map3Entry map3 = 3;
+ message Map4Entry {
+ bool key = 1;
+ string value = 2;
+ }
+ repeated Map4Entry map4 = 5;
+ string bar = 4;
+}
+
+message MapM {
+ string foo = 1;
+}
+
+service TestService {
+ rpc Call1(MapIn) returns (MapOut);
+ rpc Call2(MapIn) returns (MapOut);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/oneofs.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/oneofs.proto
new file mode 100644
index 0000000000..5bc9fa084d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/oneofs.proto
@@ -0,0 +1,68 @@
+// 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.
+
+// Proto to test oneofs.
+syntax = "proto3";
+
+import "google/protobuf/any.proto";
+import "google/protobuf/struct.proto";
+import "google/protobuf/timestamp.proto";
+
+package google.protobuf.testing.oneofs;
+option java_package = "com.google.protobuf.testing.oneofs";
+
+message OneOfsRequest {
+ string value = 1;
+ oneof data {
+ string str_data = 2;
+ int32 int_data = 3;
+ // Simple message
+ Data message_data = 4;
+ // Well known types
+ google.protobuf.Struct struct_data = 5;
+ google.protobuf.Value value_data = 6;
+ google.protobuf.ListValue list_value_data = 7;
+ google.protobuf.Timestamp ts_data = 8;
+ }
+ google.protobuf.Any any_data = 19;
+}
+
+message Data {
+ int32 data_value = 1;
+}
+
+message Response {
+ string value = 1;
+}
+
+service TestService {
+ // Test call.
+ rpc Call(OneOfsRequest) returns (Response);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/struct.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/struct.proto
new file mode 100644
index 0000000000..c15aba0d6d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/struct.proto
@@ -0,0 +1,45 @@
+// 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.
+
+// Proto to test proto3 struct.
+syntax = "proto3";
+
+package google.protobuf.testing.structs;
+option java_package = "com.google.protobuf.testing.structs";
+
+import "google/protobuf/struct.proto";
+
+message StructType {
+ google.protobuf.Struct object = 1;
+}
+
+service TestService {
+ rpc Call(StructType) returns (StructType);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/timestamp_duration.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/timestamp_duration.proto
new file mode 100644
index 0000000000..56351f168c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/timestamp_duration.proto
@@ -0,0 +1,47 @@
+// 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.
+
+// Proto to test proto3 Timestamp and Duration.
+syntax = "proto3";
+
+package google.protobuf.testing.timestampduration;
+option java_package = "com.google.protobuf.testing.timestampduration";
+
+import "google/protobuf/timestamp.proto";
+import "google/protobuf/duration.proto";
+
+message TimestampDuration {
+ google.protobuf.Timestamp ts = 1;
+ google.protobuf.Duration dur = 2;
+}
+
+service TestService {
+ rpc Call(TimestampDuration) returns (TimestampDuration);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/wrappers.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/wrappers.proto
new file mode 100644
index 0000000000..eabc99f245
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/testdata/wrappers.proto
@@ -0,0 +1,100 @@
+// 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.
+
+syntax = "proto3";
+
+package google.protobuf.testing;
+
+import "google/protobuf/wrappers.proto";
+
+// Top-level test cases proto used by MarshallingTest. See description
+// at the top of the class MarshallingTest for details on how to write
+// test cases.
+message WrappersTestCases {
+ DoubleWrapper double_wrapper = 1;
+ FloatWrapper float_wrapper = 2;
+ Int64Wrapper int64_wrapper = 3;
+ UInt64Wrapper uint64_wrapper = 4;
+ Int32Wrapper int32_wrapper = 5;
+ UInt32Wrapper uint32_wrapper = 6;
+ BoolWrapper bool_wrapper = 7;
+ StringWrapper string_wrapper = 8;
+ BytesWrapper bytes_wrapper = 9;
+
+ DoubleWrapper double_wrapper_default = 10;
+ FloatWrapper float_wrapper_default = 11;
+ Int64Wrapper int64_wrapper_default = 12;
+ UInt64Wrapper uint64_wrapper_default = 13;
+ Int32Wrapper int32_wrapper_default = 14;
+ UInt32Wrapper uint32_wrapper_default = 15;
+ BoolWrapper bool_wrapper_default = 16;
+ StringWrapper string_wrapper_default = 17;
+ BytesWrapper bytes_wrapper_default = 18;
+}
+
+message DoubleWrapper {
+ google.protobuf.DoubleValue double = 1;
+}
+
+message FloatWrapper {
+ google.protobuf.FloatValue float = 1;
+}
+
+message Int64Wrapper {
+ google.protobuf.Int64Value int64 = 1;
+}
+
+message UInt64Wrapper {
+ google.protobuf.UInt64Value uint64 = 1;
+}
+
+message Int32Wrapper {
+ google.protobuf.Int32Value int32 = 1;
+}
+
+message UInt32Wrapper {
+ google.protobuf.UInt32Value uint32 = 1;
+}
+
+message BoolWrapper {
+ google.protobuf.BoolValue bool = 1;
+}
+
+message StringWrapper {
+ google.protobuf.StringValue string = 1;
+}
+
+message BytesWrapper {
+ google.protobuf.BytesValue bytes = 1;
+}
+
+service WrappersTestService {
+ rpc Call(WrappersTestCases) returns (WrappersTestCases);
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.cc
new file mode 100644
index 0000000000..00a8ee7a2a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.cc
@@ -0,0 +1,171 @@
+// 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.
+
+#include <google/protobuf/util/internal/type_info.h>
+
+#include <map>
+#include <set>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/type.pb.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/status.h>
+#include <google/protobuf/stubs/statusor.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+namespace {
+// A TypeInfo that looks up information provided by a TypeResolver.
+class TypeInfoForTypeResolver : public TypeInfo {
+ public:
+ explicit TypeInfoForTypeResolver(TypeResolver* type_resolver)
+ : type_resolver_(type_resolver) {}
+
+ virtual ~TypeInfoForTypeResolver() {
+ DeleteCachedTypes(&cached_types_);
+ DeleteCachedTypes(&cached_enums_);
+ }
+
+ virtual util::StatusOr<const google::protobuf::Type*> ResolveTypeUrl(
+ StringPiece type_url) const {
+ map<StringPiece, StatusOrType>::iterator it = cached_types_.find(type_url);
+ if (it != cached_types_.end()) {
+ return it->second;
+ }
+ // Stores the string value so it can be referenced using StringPiece in the
+ // cached_types_ map.
+ const string& string_type_url =
+ *string_storage_.insert(type_url.ToString()).first;
+ google::protobuf::scoped_ptr<google::protobuf::Type> type(new google::protobuf::Type());
+ util::Status status =
+ type_resolver_->ResolveMessageType(string_type_url, type.get());
+ StatusOrType result =
+ status.ok() ? StatusOrType(type.release()) : StatusOrType(status);
+ cached_types_[string_type_url] = result;
+ return result;
+ }
+
+ virtual const google::protobuf::Type* GetTypeByTypeUrl(
+ StringPiece type_url) const {
+ StatusOrType result = ResolveTypeUrl(type_url);
+ return result.ok() ? result.ValueOrDie() : NULL;
+ }
+
+ virtual const google::protobuf::Enum* GetEnumByTypeUrl(
+ StringPiece type_url) const {
+ map<StringPiece, StatusOrEnum>::iterator it = cached_enums_.find(type_url);
+ if (it != cached_enums_.end()) {
+ return it->second.ok() ? it->second.ValueOrDie() : NULL;
+ }
+ // Stores the string value so it can be referenced using StringPiece in the
+ // cached_enums_ map.
+ const string& string_type_url =
+ *string_storage_.insert(type_url.ToString()).first;
+ google::protobuf::scoped_ptr<google::protobuf::Enum> enum_type(
+ new google::protobuf::Enum());
+ util::Status status =
+ type_resolver_->ResolveEnumType(string_type_url, enum_type.get());
+ StatusOrEnum result =
+ status.ok() ? StatusOrEnum(enum_type.release()) : StatusOrEnum(status);
+ cached_enums_[string_type_url] = result;
+ return result.ok() ? result.ValueOrDie() : NULL;
+ }
+
+ virtual const google::protobuf::Field* FindField(
+ const google::protobuf::Type* type, StringPiece camel_case_name) const {
+ if (indexed_types_.find(type) == indexed_types_.end()) {
+ PopulateNameLookupTable(type);
+ indexed_types_.insert(type);
+ }
+ StringPiece name =
+ FindWithDefault(camel_case_name_table_, camel_case_name, StringPiece());
+ if (name.empty()) {
+ // Didn't find a mapping. Use whatever provided.
+ name = camel_case_name;
+ }
+ return FindFieldInTypeOrNull(type, name);
+ }
+
+ private:
+ typedef util::StatusOr<const google::protobuf::Type*> StatusOrType;
+ typedef util::StatusOr<const google::protobuf::Enum*> StatusOrEnum;
+
+ template <typename T>
+ static void DeleteCachedTypes(map<StringPiece, T>* cached_types) {
+ for (typename map<StringPiece, T>::iterator it = cached_types->begin();
+ it != cached_types->end(); ++it) {
+ if (it->second.ok()) {
+ delete it->second.ValueOrDie();
+ }
+ }
+ }
+
+ void PopulateNameLookupTable(const google::protobuf::Type* type) const {
+ for (int i = 0; i < type->fields_size(); ++i) {
+ const google::protobuf::Field& field = type->fields(i);
+ StringPiece name = field.name();
+ StringPiece camel_case_name = field.json_name();
+ const StringPiece* existing = InsertOrReturnExisting(
+ &camel_case_name_table_, camel_case_name, name);
+ if (existing && *existing != name) {
+ GOOGLE_LOG(WARNING) << "Field '" << name << "' and '" << *existing
+ << "' map to the same camel case name '" << camel_case_name
+ << "'.";
+ }
+ }
+ }
+
+ TypeResolver* type_resolver_;
+
+ // Stores string values that will be referenced by StringPieces in
+ // cached_types_, cached_enums_ and camel_case_name_table_.
+ mutable set<string> string_storage_;
+
+ mutable map<StringPiece, StatusOrType> cached_types_;
+ mutable map<StringPiece, StatusOrEnum> cached_enums_;
+
+ mutable set<const google::protobuf::Type*> indexed_types_;
+ mutable map<StringPiece, StringPiece> camel_case_name_table_;
+};
+} // namespace
+
+TypeInfo* TypeInfo::NewTypeInfo(TypeResolver* type_resolver) {
+ return new TypeInfoForTypeResolver(type_resolver);
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.h
new file mode 100644
index 0000000000..d81331763a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info.h
@@ -0,0 +1,92 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_TYPE_INFO_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_TYPE_INFO_H__
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/type.pb.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/status.h>
+#include <google/protobuf/stubs/statusor.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+// Internal helper class for type resolving. Note that this class is not
+// thread-safe and should only be accessed in one thread.
+class LIBPROTOBUF_EXPORT TypeInfo {
+ public:
+ TypeInfo() {}
+ virtual ~TypeInfo() {}
+
+ // Resolves a type url into a Type. If the type url is invalid, returns
+ // INVALID_ARGUMENT error status. If the type url is valid but the
+ // corresponding type cannot be found, returns a NOT_FOUND error status.
+ //
+ // This TypeInfo class retains the ownership of the returned pointer.
+ virtual util::StatusOr<const google::protobuf::Type*> ResolveTypeUrl(
+ StringPiece type_url) const = 0;
+
+ // Resolves a type url into a Type. Like ResolveTypeUrl() but returns
+ // NULL if the type url is invalid or the type cannot be found.
+ //
+ // This TypeInfo class retains the ownership of the returned pointer.
+ virtual const google::protobuf::Type* GetTypeByTypeUrl(
+ StringPiece type_url) const = 0;
+
+ // Resolves a type url for an enum. Returns NULL if the type url is
+ // invalid or the type cannot be found.
+ //
+ // This TypeInfo class retains the ownership of the returned pointer.
+ virtual const google::protobuf::Enum* GetEnumByTypeUrl(
+ StringPiece type_url) const = 0;
+
+ // Looks up a field in the specified type given a CamelCase name.
+ virtual const google::protobuf::Field* FindField(
+ const google::protobuf::Type* type,
+ StringPiece camel_case_name) const = 0;
+
+ // Creates a TypeInfo object that looks up type information from a
+ // TypeResolver. Caller takes ownership of the returned pointer.
+ static TypeInfo* NewTypeInfo(TypeResolver* type_resolver);
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TypeInfo);
+};
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_TYPE_INFO_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.cc
new file mode 100644
index 0000000000..49e18ed0ff
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.cc
@@ -0,0 +1,134 @@
+// 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.
+
+#include <google/protobuf/util/internal/type_info_test_helper.h>
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/default_value_objectwriter.h>
+#include <google/protobuf/util/internal/type_info.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/util/internal/protostream_objectsource.h>
+#include <google/protobuf/util/internal/protostream_objectwriter.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/util/type_resolver_util.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+namespace testing {
+
+
+void TypeInfoTestHelper::ResetTypeInfo(
+ const vector<const Descriptor*>& descriptors) {
+ switch (type_) {
+ case USE_TYPE_RESOLVER: {
+ const DescriptorPool* pool = descriptors[0]->file()->pool();
+ for (int i = 1; i < descriptors.size(); ++i) {
+ GOOGLE_CHECK(pool == descriptors[i]->file()->pool())
+ << "Descriptors from different pools are not supported.";
+ }
+ type_resolver_.reset(
+ NewTypeResolverForDescriptorPool(kTypeServiceBaseUrl, pool));
+ typeinfo_.reset(TypeInfo::NewTypeInfo(type_resolver_.get()));
+ return;
+ }
+ }
+ GOOGLE_LOG(FATAL) << "Can not reach here.";
+}
+
+void TypeInfoTestHelper::ResetTypeInfo(const Descriptor* descriptor) {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(descriptor);
+ ResetTypeInfo(descriptors);
+}
+
+void TypeInfoTestHelper::ResetTypeInfo(const Descriptor* descriptor1,
+ const Descriptor* descriptor2) {
+ vector<const Descriptor*> descriptors;
+ descriptors.push_back(descriptor1);
+ descriptors.push_back(descriptor2);
+ ResetTypeInfo(descriptors);
+}
+
+TypeInfo* TypeInfoTestHelper::GetTypeInfo() { return typeinfo_.get(); }
+
+ProtoStreamObjectSource* TypeInfoTestHelper::NewProtoSource(
+ io::CodedInputStream* coded_input, const string& type_url) {
+ const google::protobuf::Type* type = typeinfo_->GetTypeByTypeUrl(type_url);
+ switch (type_) {
+ case USE_TYPE_RESOLVER: {
+ return new ProtoStreamObjectSource(coded_input, type_resolver_.get(),
+ *type);
+ }
+ }
+ GOOGLE_LOG(FATAL) << "Can not reach here.";
+ return NULL;
+}
+
+ProtoStreamObjectWriter* TypeInfoTestHelper::NewProtoWriter(
+ const string& type_url, strings::ByteSink* output, ErrorListener* listener,
+ const ProtoStreamObjectWriter::Options& options) {
+ const google::protobuf::Type* type = typeinfo_->GetTypeByTypeUrl(type_url);
+ switch (type_) {
+ case USE_TYPE_RESOLVER: {
+ return new ProtoStreamObjectWriter(type_resolver_.get(), *type, output,
+ listener, options);
+ }
+ }
+ GOOGLE_LOG(FATAL) << "Can not reach here.";
+ return NULL;
+}
+
+DefaultValueObjectWriter* TypeInfoTestHelper::NewDefaultValueWriter(
+ const string& type_url, ObjectWriter* writer) {
+ const google::protobuf::Type* type = typeinfo_->GetTypeByTypeUrl(type_url);
+ switch (type_) {
+ case USE_TYPE_RESOLVER: {
+ return new DefaultValueObjectWriter(type_resolver_.get(), *type, writer);
+ }
+ }
+ GOOGLE_LOG(FATAL) << "Can not reach here.";
+ return NULL;
+}
+
+} // namespace testing
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.h
new file mode 100644
index 0000000000..1a279849ab
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/type_info_test_helper.h
@@ -0,0 +1,98 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_TYPE_INFO_TEST_HELPER_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_TYPE_INFO_TEST_HELPER_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <vector>
+
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/default_value_objectwriter.h>
+#include <google/protobuf/util/internal/type_info.h>
+#include <google/protobuf/util/internal/protostream_objectsource.h>
+#include <google/protobuf/util/internal/protostream_objectwriter.h>
+#include <google/protobuf/util/type_resolver.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+namespace testing {
+
+enum TypeInfoSource {
+ USE_TYPE_RESOLVER,
+};
+
+// In the unit-tests we want to test two scenarios: one with type info from
+// ServiceTypeInfo, the other with type info from TypeResolver. This class
+// wraps the detail of where the type info is from and provides the same
+// interface so the same unit-test code can test both scenarios.
+class TypeInfoTestHelper {
+ public:
+ explicit TypeInfoTestHelper(TypeInfoSource type) : type_(type) {}
+
+ // Creates a TypeInfo object for the given set of descriptors.
+ void ResetTypeInfo(const vector<const Descriptor*>& descriptors);
+
+ // Convinent overloads.
+ void ResetTypeInfo(const Descriptor* descriptor);
+ void ResetTypeInfo(const Descriptor* descriptor1,
+ const Descriptor* descriptor2);
+
+ // Returns the TypeInfo created after ResetTypeInfo.
+ TypeInfo* GetTypeInfo();
+
+ ProtoStreamObjectSource* NewProtoSource(io::CodedInputStream* coded_input,
+ const string& type_url);
+
+ ProtoStreamObjectWriter* NewProtoWriter(
+ const string& type_url, strings::ByteSink* output,
+ ErrorListener* listener, const ProtoStreamObjectWriter::Options& options);
+
+ DefaultValueObjectWriter* NewDefaultValueWriter(const string& type_url,
+ ObjectWriter* writer);
+
+ private:
+ TypeInfoSource type_;
+ google::protobuf::scoped_ptr<TypeInfo> typeinfo_;
+ google::protobuf::scoped_ptr<TypeResolver> type_resolver_;
+};
+} // namespace testing
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_TYPE_INFO_TEST_HELPER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.cc
new file mode 100644
index 0000000000..5f613e77e4
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.cc
@@ -0,0 +1,365 @@
+// 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.
+
+#include <google/protobuf/util/internal/utility.h>
+
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/wrappers.pb.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/constants.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/map_util.h>
+#include <google/protobuf/stubs/mathlimits.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace converter {
+
+namespace {
+const StringPiece SkipWhiteSpace(StringPiece str) {
+ StringPiece::size_type i;
+ for (i = 0; i < str.size() && isspace(str[i]); ++i) {
+ }
+ GOOGLE_DCHECK(i == str.size() || !isspace(str[i]));
+ return str.substr(i);
+}
+} // namespace
+
+bool GetBoolOptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, bool default_value) {
+ const google::protobuf::Option* opt = FindOptionOrNull(options, option_name);
+ if (opt == NULL) {
+ return default_value;
+ }
+ return GetBoolFromAny(opt->value());
+}
+
+int64 GetInt64OptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, int64 default_value) {
+ const google::protobuf::Option* opt = FindOptionOrNull(options, option_name);
+ if (opt == NULL) {
+ return default_value;
+ }
+ return GetInt64FromAny(opt->value());
+}
+
+double GetDoubleOptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, double default_value) {
+ const google::protobuf::Option* opt = FindOptionOrNull(options, option_name);
+ if (opt == NULL) {
+ return default_value;
+ }
+ return GetDoubleFromAny(opt->value());
+}
+
+string GetStringOptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, const string& default_value) {
+ const google::protobuf::Option* opt = FindOptionOrNull(options, option_name);
+ if (opt == NULL) {
+ return default_value;
+ }
+ return GetStringFromAny(opt->value());
+}
+
+template <typename T>
+void ParseFromAny(const string& data, T* result) {
+ result->ParseFromString(data);
+}
+
+// Returns a boolean value contained in Any type.
+// TODO(skarvaje): Add type checking & error messages here.
+bool GetBoolFromAny(const google::protobuf::Any& any) {
+ google::protobuf::BoolValue b;
+ ParseFromAny(any.value(), &b);
+ return b.value();
+}
+
+int64 GetInt64FromAny(const google::protobuf::Any& any) {
+ google::protobuf::Int64Value i;
+ ParseFromAny(any.value(), &i);
+ return i.value();
+}
+
+double GetDoubleFromAny(const google::protobuf::Any& any) {
+ google::protobuf::DoubleValue i;
+ ParseFromAny(any.value(), &i);
+ return i.value();
+}
+
+string GetStringFromAny(const google::protobuf::Any& any) {
+ google::protobuf::StringValue s;
+ ParseFromAny(any.value(), &s);
+ return s.value();
+}
+
+const StringPiece GetTypeWithoutUrl(StringPiece type_url) {
+ if (type_url.size() > kTypeUrlSize && type_url[kTypeUrlSize] == '/') {
+ return type_url.substr(kTypeUrlSize + 1);
+ } else {
+ size_t idx = type_url.rfind('/');
+ return type_url.substr(idx + 1);
+ }
+}
+
+const string GetFullTypeWithUrl(StringPiece simple_type) {
+ return StrCat(kTypeServiceBaseUrl, "/", simple_type);
+}
+
+const google::protobuf::Option* FindOptionOrNull(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name) {
+ for (int i = 0; i < options.size(); ++i) {
+ const google::protobuf::Option& opt = options.Get(i);
+ if (opt.name() == option_name) {
+ return &opt;
+ }
+ }
+ return NULL;
+}
+
+const google::protobuf::Field* FindFieldInTypeOrNull(
+ const google::protobuf::Type* type, StringPiece field_name) {
+ if (type != NULL) {
+ for (int i = 0; i < type->fields_size(); ++i) {
+ const google::protobuf::Field& field = type->fields(i);
+ if (field.name() == field_name) {
+ return &field;
+ }
+ }
+ }
+ return NULL;
+}
+
+const google::protobuf::Field* FindJsonFieldInTypeOrNull(
+ const google::protobuf::Type* type, StringPiece json_name) {
+ if (type != NULL) {
+ for (int i = 0; i < type->fields_size(); ++i) {
+ const google::protobuf::Field& field = type->fields(i);
+ if (field.json_name() == json_name) {
+ return &field;
+ }
+ }
+ }
+ return NULL;
+}
+
+const google::protobuf::EnumValue* FindEnumValueByNameOrNull(
+ const google::protobuf::Enum* enum_type, StringPiece enum_name) {
+ if (enum_type != NULL) {
+ for (int i = 0; i < enum_type->enumvalue_size(); ++i) {
+ const google::protobuf::EnumValue& enum_value = enum_type->enumvalue(i);
+ if (enum_value.name() == enum_name) {
+ return &enum_value;
+ }
+ }
+ }
+ return NULL;
+}
+
+const google::protobuf::EnumValue* FindEnumValueByNumberOrNull(
+ const google::protobuf::Enum* enum_type, int32 value) {
+ if (enum_type != NULL) {
+ for (int i = 0; i < enum_type->enumvalue_size(); ++i) {
+ const google::protobuf::EnumValue& enum_value = enum_type->enumvalue(i);
+ if (enum_value.number() == value) {
+ return &enum_value;
+ }
+ }
+ }
+ return NULL;
+}
+
+string ToCamelCase(const StringPiece input) {
+ bool capitalize_next = false;
+ bool was_cap = true;
+ bool is_cap = false;
+ bool first_word = true;
+ string result;
+ result.reserve(input.size());
+
+ for (size_t i = 0; i < input.size(); ++i, was_cap = is_cap) {
+ is_cap = ascii_isupper(input[i]);
+ if (input[i] == '_') {
+ capitalize_next = true;
+ if (!result.empty()) first_word = false;
+ continue;
+ } else if (first_word) {
+ // Consider when the current character B is capitalized,
+ // first word ends when:
+ // 1) following a lowercase: "...aB..."
+ // 2) followed by a lowercase: "...ABc..."
+ if (!result.empty() && is_cap &&
+ (!was_cap || (i + 1 < input.size() && ascii_islower(input[i + 1])))) {
+ first_word = false;
+ result.push_back(input[i]);
+ } else {
+ result.push_back(ascii_tolower(input[i]));
+ continue;
+ }
+ } else if (capitalize_next) {
+ capitalize_next = false;
+ if (ascii_islower(input[i])) {
+ result.push_back(ascii_toupper(input[i]));
+ continue;
+ } else {
+ result.push_back(input[i]);
+ continue;
+ }
+ } else {
+ result.push_back(ascii_tolower(input[i]));
+ }
+ }
+ return result;
+}
+
+string ToSnakeCase(StringPiece input) {
+ bool was_not_underscore = false; // Initialize to false for case 1 (below)
+ bool was_not_cap = false;
+ string result;
+ result.reserve(input.size() << 1);
+
+ for (size_t i = 0; i < input.size(); ++i) {
+ if (ascii_isupper(input[i])) {
+ // Consider when the current character B is capitalized:
+ // 1) At beginning of input: "B..." => "b..."
+ // (e.g. "Biscuit" => "biscuit")
+ // 2) Following a lowercase: "...aB..." => "...a_b..."
+ // (e.g. "gBike" => "g_bike")
+ // 3) At the end of input: "...AB" => "...ab"
+ // (e.g. "GoogleLAB" => "google_lab")
+ // 4) Followed by a lowercase: "...ABc..." => "...a_bc..."
+ // (e.g. "GBike" => "g_bike")
+ if (was_not_underscore && // case 1 out
+ (was_not_cap || // case 2 in, case 3 out
+ (i + 1 < input.size() && // case 3 out
+ ascii_islower(input[i + 1])))) { // case 4 in
+ // We add an underscore for case 2 and case 4.
+ result.push_back('_');
+ }
+ result.push_back(ascii_tolower(input[i]));
+ was_not_underscore = true;
+ was_not_cap = false;
+ } else {
+ result.push_back(input[i]);
+ was_not_underscore = input[i] != '_';
+ was_not_cap = true;
+ }
+ }
+ return result;
+}
+
+set<string>* well_known_types_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(well_known_types_init_);
+const char* well_known_types_name_array_[] = {
+ "google.protobuf.Timestamp", "google.protobuf.Duration",
+ "google.protobuf.DoubleValue", "google.protobuf.FloatValue",
+ "google.protobuf.Int64Value", "google.protobuf.UInt64Value",
+ "google.protobuf.Int32Value", "google.protobuf.UInt32Value",
+ "google.protobuf.BoolValue", "google.protobuf.StringValue",
+ "google.protobuf.BytesValue", "google.protobuf.FieldMask"};
+
+void DeleteWellKnownTypes() { delete well_known_types_; }
+
+void InitWellKnownTypes() {
+ well_known_types_ = new set<string>;
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(well_known_types_name_array_); ++i) {
+ well_known_types_->insert(well_known_types_name_array_[i]);
+ }
+ google::protobuf::internal::OnShutdown(&DeleteWellKnownTypes);
+}
+
+bool IsWellKnownType(const string& type_name) {
+ InitWellKnownTypes();
+ return ContainsKey(*well_known_types_, type_name);
+}
+
+bool IsValidBoolString(const string& bool_string) {
+ return bool_string == "true" || bool_string == "false" ||
+ bool_string == "1" || bool_string == "0";
+}
+
+bool IsMap(const google::protobuf::Field& field,
+ const google::protobuf::Type& type) {
+ return (field.cardinality() ==
+ google::protobuf::Field_Cardinality_CARDINALITY_REPEATED &&
+ GetBoolOptionOrDefault(type.options(),
+ "google.protobuf.MessageOptions.map_entry", false));
+}
+
+bool IsMessageSetWireFormat(const google::protobuf::Type& type) {
+ return GetBoolOptionOrDefault(
+ type.options(), "google.protobuf.MessageOptions.message_set_wire_format", false);
+}
+
+string DoubleAsString(double value) {
+ if (MathLimits<double>::IsPosInf(value)) return "Infinity";
+ if (MathLimits<double>::IsNegInf(value)) return "-Infinity";
+ if (MathLimits<double>::IsNaN(value)) return "NaN";
+
+ return SimpleDtoa(value);
+}
+
+string FloatAsString(float value) {
+ if (MathLimits<float>::IsFinite(value)) return SimpleFtoa(value);
+ return DoubleAsString(value);
+}
+
+bool SafeStrToFloat(StringPiece str, float* value) {
+ double double_value;
+ if (!safe_strtod(str, &double_value)) {
+ return false;
+ }
+
+ if (MathLimits<double>::IsInf(double_value) ||
+ MathLimits<double>::IsNaN(double_value))
+ return false;
+
+ // Fail if the value is not representable in float.
+ if (double_value > std::numeric_limits<float>::max() ||
+ double_value < -std::numeric_limits<float>::max()) {
+ return false;
+ }
+
+ *value = static_cast<float>(double_value);
+ return true;
+}
+
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.h
new file mode 100644
index 0000000000..26fed4445e
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/internal/utility.h
@@ -0,0 +1,197 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_CONVERTER_UTILITY_H__
+#define GOOGLE_PROTOBUF_UTIL_CONVERTER_UTILITY_H__
+
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <utility>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/type.pb.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/stubs/stringpiece.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/status.h>
+#include <google/protobuf/stubs/statusor.h>
+
+
+namespace google {
+namespace protobuf {
+class Method;
+class Any;
+class Bool;
+class Option;
+class Field;
+class Type;
+class Enum;
+class EnumValue;
+} // namespace protobuf
+
+
+namespace protobuf {
+namespace util {
+namespace converter {
+
+// Size of "type.googleapis.com"
+static const int64 kTypeUrlSize = 19;
+
+// Finds the tech option identified by option_name. Parses the boolean value and
+// returns it.
+// When the option with the given name is not found, default_value is returned.
+LIBPROTOBUF_EXPORT bool GetBoolOptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, bool default_value);
+
+// Returns int64 option value. If the option isn't found, returns the
+// default_value.
+LIBPROTOBUF_EXPORT int64 GetInt64OptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, int64 default_value);
+
+// Returns double option value. If the option isn't found, returns the
+// default_value.
+LIBPROTOBUF_EXPORT double GetDoubleOptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, double default_value);
+
+// Returns string option value. If the option isn't found, returns the
+// default_value.
+LIBPROTOBUF_EXPORT string GetStringOptionOrDefault(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name, const string& default_value);
+
+// Returns a boolean value contained in Any type.
+// TODO(skarvaje): Make these utilities dealing with Any types more generic,
+// add more error checking and move to a more public/sharable location so others
+// can use.
+LIBPROTOBUF_EXPORT bool GetBoolFromAny(const google::protobuf::Any& any);
+
+// Returns int64 value contained in Any type.
+LIBPROTOBUF_EXPORT int64 GetInt64FromAny(const google::protobuf::Any& any);
+
+// Returns double value contained in Any type.
+LIBPROTOBUF_EXPORT double GetDoubleFromAny(const google::protobuf::Any& any);
+
+// Returns string value contained in Any type.
+LIBPROTOBUF_EXPORT string GetStringFromAny(const google::protobuf::Any& any);
+
+// Returns the type string without the url prefix. e.g.: If the passed type is
+// 'type.googleapis.com/tech.type.Bool', the returned value is 'tech.type.Bool'.
+LIBPROTOBUF_EXPORT const StringPiece GetTypeWithoutUrl(StringPiece type_url);
+
+// Returns the simple_type with the base type url (kTypeServiceBaseUrl)
+// prefixed.
+//
+// E.g:
+// GetFullTypeWithUrl("google.protobuf.Timestamp") returns the string
+// "type.googleapis.com/google.protobuf.Timestamp".
+LIBPROTOBUF_EXPORT const string GetFullTypeWithUrl(StringPiece simple_type);
+
+// Finds and returns option identified by name and option_name within the
+// provided map. Returns NULL if none found.
+const google::protobuf::Option* FindOptionOrNull(
+ const google::protobuf::RepeatedPtrField<google::protobuf::Option>& options,
+ const string& option_name);
+
+// Finds and returns the field identified by field_name in the passed tech Type
+// object. Returns NULL if none found.
+const google::protobuf::Field* FindFieldInTypeOrNull(
+ const google::protobuf::Type* type, StringPiece field_name);
+
+// Similar to FindFieldInTypeOrNull, but this looks up fields with given
+// json_name.
+const google::protobuf::Field* FindJsonFieldInTypeOrNull(
+ const google::protobuf::Type* type, StringPiece json_name);
+
+// Finds and returns the EnumValue identified by enum_name in the passed tech
+// Enum object. Returns NULL if none found.
+const google::protobuf::EnumValue* FindEnumValueByNameOrNull(
+ const google::protobuf::Enum* enum_type, StringPiece enum_name);
+
+// Finds and returns the EnumValue identified by value in the passed tech
+// Enum object. Returns NULL if none found.
+const google::protobuf::EnumValue* FindEnumValueByNumberOrNull(
+ const google::protobuf::Enum* enum_type, int32 value);
+
+// Converts input to camel-case and returns it.
+LIBPROTOBUF_EXPORT string ToCamelCase(const StringPiece input);
+
+// Converts input to snake_case and returns it.
+LIBPROTOBUF_EXPORT string ToSnakeCase(StringPiece input);
+
+// Returns true if type_name represents a well-known type.
+LIBPROTOBUF_EXPORT bool IsWellKnownType(const string& type_name);
+
+// Returns true if 'bool_string' represents a valid boolean value. Only "true",
+// "false", "0" and "1" are allowed.
+LIBPROTOBUF_EXPORT bool IsValidBoolString(const string& bool_string);
+
+// Returns true if "field" is a protobuf map field based on its type.
+LIBPROTOBUF_EXPORT bool IsMap(const google::protobuf::Field& field,
+ const google::protobuf::Type& type);
+
+// Returns true if the given type has special MessageSet wire format.
+bool IsMessageSetWireFormat(const google::protobuf::Type& type);
+
+// Infinity/NaN-aware conversion to string.
+LIBPROTOBUF_EXPORT string DoubleAsString(double value);
+LIBPROTOBUF_EXPORT string FloatAsString(float value);
+
+// Convert from int32, int64, uint32, uint64, double or float to string.
+template <typename T>
+string ValueAsString(T value) {
+ return SimpleItoa(value);
+}
+
+template <>
+inline string ValueAsString(float value) {
+ return FloatAsString(value);
+}
+
+template <>
+inline string ValueAsString(double value) {
+ return DoubleAsString(value);
+}
+
+// Converts a string to float. Unlike safe_strtof, conversion will fail if the
+// value fits into double but not float (e.g., DBL_MAX).
+LIBPROTOBUF_EXPORT bool SafeStrToFloat(StringPiece str, float* value);
+} // namespace converter
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_CONVERTER_UTILITY_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/json_format_proto3.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_format_proto3.proto
new file mode 100644
index 0000000000..3835b30eb9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_format_proto3.proto
@@ -0,0 +1,181 @@
+// 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.
+
+syntax = "proto3";
+
+package proto3;
+
+
+import "google/protobuf/duration.proto";
+import "google/protobuf/timestamp.proto";
+import "google/protobuf/wrappers.proto";
+import "google/protobuf/struct.proto";
+import "google/protobuf/any.proto";
+import "google/protobuf/field_mask.proto";
+import "google/protobuf/unittest.proto";
+
+enum EnumType {
+ FOO = 0;
+ BAR = 1;
+}
+
+message MessageType {
+ int32 value = 1;
+}
+
+message TestMessage {
+ bool bool_value = 1;
+ int32 int32_value = 2;
+ int64 int64_value = 3;
+ uint32 uint32_value = 4;
+ uint64 uint64_value = 5;
+ float float_value = 6;
+ double double_value = 7;
+ string string_value = 8;
+ bytes bytes_value = 9;
+ EnumType enum_value = 10;
+ MessageType message_value = 11;
+
+ repeated bool repeated_bool_value = 21;
+ repeated int32 repeated_int32_value = 22;
+ repeated int64 repeated_int64_value = 23;
+ repeated uint32 repeated_uint32_value = 24;
+ repeated uint64 repeated_uint64_value = 25;
+ repeated float repeated_float_value = 26;
+ repeated double repeated_double_value = 27;
+ repeated string repeated_string_value = 28;
+ repeated bytes repeated_bytes_value = 29;
+ repeated EnumType repeated_enum_value = 30;
+ repeated MessageType repeated_message_value = 31;
+}
+
+message TestOneof {
+ // In JSON format oneof fields behave mostly the same as optional
+ // fields except that:
+ // 1. Oneof fields have field presence information and will be
+ // printed if it's set no matter whether it's the default value.
+ // 2. Multiple oneof fields in the same oneof cannot appear at the
+ // same time in the input.
+ oneof oneof_value {
+ int32 oneof_int32_value = 1;
+ string oneof_string_value = 2;
+ bytes oneof_bytes_value = 3;
+ EnumType oneof_enum_value = 4;
+ MessageType oneof_message_value = 5;
+ }
+}
+
+message TestMap {
+ map<bool, int32> bool_map = 1;
+ map<int32, int32> int32_map = 2;
+ map<int64, int32> int64_map = 3;
+ map<uint32, int32> uint32_map = 4;
+ map<uint64, int32> uint64_map = 5;
+ map<string, int32> string_map = 6;
+}
+
+message TestNestedMap {
+ map<bool, int32> bool_map = 1;
+ map<int32, int32> int32_map = 2;
+ map<int64, int32> int64_map = 3;
+ map<uint32, int32> uint32_map = 4;
+ map<uint64, int32> uint64_map = 5;
+ map<string, int32> string_map = 6;
+ map<string, TestNestedMap> map_map = 7;
+}
+
+message TestWrapper {
+ google.protobuf.BoolValue bool_value = 1;
+ google.protobuf.Int32Value int32_value = 2;
+ google.protobuf.Int64Value int64_value = 3;
+ google.protobuf.UInt32Value uint32_value = 4;
+ google.protobuf.UInt64Value uint64_value = 5;
+ google.protobuf.FloatValue float_value = 6;
+ google.protobuf.DoubleValue double_value = 7;
+ google.protobuf.StringValue string_value = 8;
+ google.protobuf.BytesValue bytes_value = 9;
+
+ repeated google.protobuf.BoolValue repeated_bool_value = 11;
+ repeated google.protobuf.Int32Value repeated_int32_value = 12;
+ repeated google.protobuf.Int64Value repeated_int64_value = 13;
+ repeated google.protobuf.UInt32Value repeated_uint32_value = 14;
+ repeated google.protobuf.UInt64Value repeated_uint64_value = 15;
+ repeated google.protobuf.FloatValue repeated_float_value = 16;
+ repeated google.protobuf.DoubleValue repeated_double_value = 17;
+ repeated google.protobuf.StringValue repeated_string_value = 18;
+ repeated google.protobuf.BytesValue repeated_bytes_value = 19;
+}
+
+message TestTimestamp {
+ google.protobuf.Timestamp value = 1;
+ repeated google.protobuf.Timestamp repeated_value = 2;
+}
+
+message TestDuration {
+ google.protobuf.Duration value = 1;
+ repeated google.protobuf.Duration repeated_value = 2;
+}
+
+message TestFieldMask {
+ google.protobuf.FieldMask value = 1;
+}
+
+message TestStruct {
+ google.protobuf.Struct value = 1;
+ repeated google.protobuf.Struct repeated_value = 2;
+}
+
+message TestAny {
+ google.protobuf.Any value = 1;
+ repeated google.protobuf.Any repeated_value = 2;
+}
+
+message TestValue {
+ google.protobuf.Value value = 1;
+ repeated google.protobuf.Value repeated_value = 2;
+}
+
+message TestListValue {
+ google.protobuf.ListValue value = 1;
+ repeated google.protobuf.ListValue repeated_value = 2;
+}
+
+message TestBoolValue {
+ bool bool_value = 1;
+ map<bool, int32> bool_map = 2;
+}
+
+message TestCustomJsonName {
+ int32 value = 1 [json_name = "@value"];
+}
+
+message TestExtensions {
+ .protobuf_unittest.TestAllExtensions extensions = 1;
+}
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.cc
new file mode 100644
index 0000000000..d7ac2dba66
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.cc
@@ -0,0 +1,242 @@
+// 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.
+
+#include <google/protobuf/util/json_util.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/util/internal/default_value_objectwriter.h>
+#include <google/protobuf/util/internal/error_listener.h>
+#include <google/protobuf/util/internal/json_objectwriter.h>
+#include <google/protobuf/util/internal/json_stream_parser.h>
+#include <google/protobuf/util/internal/protostream_objectsource.h>
+#include <google/protobuf/util/internal/protostream_objectwriter.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/util/type_resolver_util.h>
+#include <google/protobuf/stubs/bytestream.h>
+#include <google/protobuf/stubs/status_macros.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+namespace internal {
+void ZeroCopyStreamByteSink::Append(const char* bytes, size_t len) {
+ while (len > 0) {
+ void* buffer;
+ int length;
+ if (!stream_->Next(&buffer, &length)) {
+ // There isn't a way for ByteSink to report errors.
+ return;
+ }
+ if (len < length) {
+ memcpy(buffer, bytes, len);
+ stream_->BackUp(length - len);
+ break;
+ } else {
+ memcpy(buffer, bytes, length);
+ bytes += length;
+ len -= length;
+ }
+ }
+}
+} // namespace internal
+
+util::Status BinaryToJsonStream(TypeResolver* resolver,
+ const string& type_url,
+ io::ZeroCopyInputStream* binary_input,
+ io::ZeroCopyOutputStream* json_output,
+ const JsonPrintOptions& options) {
+ io::CodedInputStream in_stream(binary_input);
+ google::protobuf::Type type;
+ RETURN_IF_ERROR(resolver->ResolveMessageType(type_url, &type));
+ converter::ProtoStreamObjectSource proto_source(&in_stream, resolver, type);
+ io::CodedOutputStream out_stream(json_output);
+ converter::JsonObjectWriter json_writer(options.add_whitespace ? " " : "",
+ &out_stream);
+ if (options.always_print_primitive_fields) {
+ converter::DefaultValueObjectWriter default_value_writer(
+ resolver, type, &json_writer);
+ return proto_source.WriteTo(&default_value_writer);
+ } else {
+ return proto_source.WriteTo(&json_writer);
+ }
+}
+
+util::Status BinaryToJsonString(TypeResolver* resolver,
+ const string& type_url,
+ const string& binary_input,
+ string* json_output,
+ const JsonPrintOptions& options) {
+ io::ArrayInputStream input_stream(binary_input.data(), binary_input.size());
+ io::StringOutputStream output_stream(json_output);
+ return BinaryToJsonStream(resolver, type_url, &input_stream, &output_stream,
+ options);
+}
+
+namespace {
+class StatusErrorListener : public converter::ErrorListener {
+ public:
+ StatusErrorListener() : status_(util::Status::OK) {}
+ virtual ~StatusErrorListener() {}
+
+ util::Status GetStatus() { return status_; }
+
+ virtual void InvalidName(const converter::LocationTrackerInterface& loc,
+ StringPiece unknown_name, StringPiece message) {
+ status_ = util::Status(util::error::INVALID_ARGUMENT,
+ loc.ToString() + ": " + message.ToString());
+ }
+
+ virtual void InvalidValue(const converter::LocationTrackerInterface& loc,
+ StringPiece type_name, StringPiece value) {
+ status_ =
+ util::Status(util::error::INVALID_ARGUMENT,
+ loc.ToString() + ": invalid value " + value.ToString() +
+ " for type " + type_name.ToString());
+ }
+
+ virtual void MissingField(const converter::LocationTrackerInterface& loc,
+ StringPiece missing_name) {
+ status_ = util::Status(
+ util::error::INVALID_ARGUMENT,
+ loc.ToString() + ": missing field " + missing_name.ToString());
+ }
+
+ private:
+ util::Status status_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StatusErrorListener);
+};
+} // namespace
+
+util::Status JsonToBinaryStream(TypeResolver* resolver,
+ const string& type_url,
+ io::ZeroCopyInputStream* json_input,
+ io::ZeroCopyOutputStream* binary_output,
+ const JsonParseOptions& options) {
+ google::protobuf::Type type;
+ RETURN_IF_ERROR(resolver->ResolveMessageType(type_url, &type));
+ internal::ZeroCopyStreamByteSink sink(binary_output);
+ StatusErrorListener listener;
+ converter::ProtoStreamObjectWriter::Options proto_writer_options;
+ proto_writer_options.ignore_unknown_fields = options.ignore_unknown_fields;
+ converter::ProtoStreamObjectWriter proto_writer(resolver, type, &sink,
+ &listener,
+ proto_writer_options);
+
+ converter::JsonStreamParser parser(&proto_writer);
+ const void* buffer;
+ int length;
+ while (json_input->Next(&buffer, &length)) {
+ if (length == 0) continue;
+ RETURN_IF_ERROR(
+ parser.Parse(StringPiece(static_cast<const char*>(buffer), length)));
+ }
+ RETURN_IF_ERROR(parser.FinishParse());
+
+ return listener.GetStatus();
+}
+
+util::Status JsonToBinaryString(TypeResolver* resolver,
+ const string& type_url,
+ const string& json_input,
+ string* binary_output,
+ const JsonParseOptions& options) {
+ io::ArrayInputStream input_stream(json_input.data(), json_input.size());
+ io::StringOutputStream output_stream(binary_output);
+ return JsonToBinaryStream(
+ resolver, type_url, &input_stream, &output_stream, options);
+}
+
+namespace {
+const char* kTypeUrlPrefix = "type.googleapis.com";
+TypeResolver* generated_type_resolver_ = NULL;
+GOOGLE_PROTOBUF_DECLARE_ONCE(generated_type_resolver_init_);
+
+string GetTypeUrl(const Message& message) {
+ return string(kTypeUrlPrefix) + "/" + message.GetDescriptor()->full_name();
+}
+
+void DeleteGeneratedTypeResolver() { delete generated_type_resolver_; }
+
+void InitGeneratedTypeResolver() {
+ generated_type_resolver_ = NewTypeResolverForDescriptorPool(
+ kTypeUrlPrefix, DescriptorPool::generated_pool());
+ ::google::protobuf::internal::OnShutdown(&DeleteGeneratedTypeResolver);
+}
+
+TypeResolver* GetGeneratedTypeResolver() {
+ ::google::protobuf::GoogleOnceInit(&generated_type_resolver_init_, &InitGeneratedTypeResolver);
+ return generated_type_resolver_;
+}
+} // namespace
+
+util::Status MessageToJsonString(const Message& message, string* output,
+ const JsonOptions& options) {
+ const DescriptorPool* pool = message.GetDescriptor()->file()->pool();
+ TypeResolver* resolver =
+ pool == DescriptorPool::generated_pool()
+ ? GetGeneratedTypeResolver()
+ : NewTypeResolverForDescriptorPool(kTypeUrlPrefix, pool);
+ util::Status result =
+ BinaryToJsonString(resolver, GetTypeUrl(message),
+ message.SerializeAsString(), output, options);
+ if (pool != DescriptorPool::generated_pool()) {
+ delete resolver;
+ }
+ return result;
+}
+
+util::Status JsonStringToMessage(const string& input, Message* message,
+ const JsonParseOptions& options) {
+ const DescriptorPool* pool = message->GetDescriptor()->file()->pool();
+ TypeResolver* resolver =
+ pool == DescriptorPool::generated_pool()
+ ? GetGeneratedTypeResolver()
+ : NewTypeResolverForDescriptorPool(kTypeUrlPrefix, pool);
+ string binary;
+ util::Status result = JsonToBinaryString(
+ resolver, GetTypeUrl(*message), input, &binary, options);
+ if (result.ok() && !message->ParseFromString(binary)) {
+ result =
+ util::Status(util::error::INVALID_ARGUMENT,
+ "JSON transcoder produced invalid protobuf output.");
+ }
+ if (pool != DescriptorPool::generated_pool()) {
+ delete resolver;
+ }
+ return result;
+}
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.h
new file mode 100644
index 0000000000..6d3cee5281
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util.h
@@ -0,0 +1,190 @@
+// 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.
+
+// Utility functions to convert between protobuf binary format and proto3 JSON
+// format.
+#ifndef GOOGLE_PROTOBUF_UTIL_JSON_UTIL_H__
+#define GOOGLE_PROTOBUF_UTIL_JSON_UTIL_H__
+
+#include <google/protobuf/message.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/stubs/bytestream.h>
+
+namespace google {
+namespace protobuf {
+namespace io {
+class ZeroCopyInputStream;
+class ZeroCopyOutputStream;
+} // namespace io
+namespace util {
+
+struct JsonParseOptions {
+ // Whether to ignore unknown JSON fields during parsing
+ bool ignore_unknown_fields;
+
+ JsonParseOptions() : ignore_unknown_fields(false) {}
+};
+
+struct JsonPrintOptions {
+ // Whether to add spaces, line breaks and indentation to make the JSON output
+ // easy to read.
+ bool add_whitespace;
+ // Whether to always print primitive fields. By default primitive fields with
+ // default values will be omitted in JSON joutput. For example, an int32 field
+ // set to 0 will be omitted. Set this flag to true will override the default
+ // behavior and print primitive fields regardless of their values.
+ bool always_print_primitive_fields;
+
+ JsonPrintOptions() : add_whitespace(false),
+ always_print_primitive_fields(false) {
+ }
+};
+
+// DEPRECATED. Use JsonPrintOptions instead.
+typedef JsonPrintOptions JsonOptions;
+
+// Converts from protobuf message to JSON. This is a simple wrapper of
+// BinaryToJsonString(). It will use the DescriptorPool of the passed-in
+// message to resolve Any types.
+LIBPROTOBUF_EXPORT util::Status MessageToJsonString(const Message& message,
+ string* output,
+ const JsonOptions& options);
+
+inline util::Status MessageToJsonString(const Message& message,
+ string* output) {
+ return MessageToJsonString(message, output, JsonOptions());
+}
+
+// Converts from JSON to protobuf message. This is a simple wrapper of
+// JsonStringToBinary(). It will use the DescriptorPool of the passed-in
+// message to resolve Any types.
+LIBPROTOBUF_EXPORT util::Status JsonStringToMessage(const string& input,
+ Message* message,
+ const JsonParseOptions& options);
+
+inline util::Status JsonStringToMessage(const string& input,
+ Message* message) {
+ return JsonStringToMessage(input, message, JsonParseOptions());
+}
+
+// Converts protobuf binary data to JSON.
+// The conversion will fail if:
+// 1. TypeResolver fails to resolve a type.
+// 2. input is not valid protobuf wire format, or conflicts with the type
+// information returned by TypeResolver.
+// Note that unknown fields will be discarded silently.
+LIBPROTOBUF_EXPORT util::Status BinaryToJsonStream(
+ TypeResolver* resolver,
+ const string& type_url,
+ io::ZeroCopyInputStream* binary_input,
+ io::ZeroCopyOutputStream* json_output,
+ const JsonPrintOptions& options);
+
+inline util::Status BinaryToJsonStream(
+ TypeResolver* resolver, const string& type_url,
+ io::ZeroCopyInputStream* binary_input,
+ io::ZeroCopyOutputStream* json_output) {
+ return BinaryToJsonStream(resolver, type_url, binary_input, json_output,
+ JsonPrintOptions());
+}
+
+LIBPROTOBUF_EXPORT util::Status BinaryToJsonString(
+ TypeResolver* resolver,
+ const string& type_url,
+ const string& binary_input,
+ string* json_output,
+ const JsonPrintOptions& options);
+
+inline util::Status BinaryToJsonString(TypeResolver* resolver,
+ const string& type_url,
+ const string& binary_input,
+ string* json_output) {
+ return BinaryToJsonString(resolver, type_url, binary_input, json_output,
+ JsonPrintOptions());
+}
+
+// Converts JSON data to protobuf binary format.
+// The conversion will fail if:
+// 1. TypeResolver fails to resolve a type.
+// 2. input is not valid JSON format, or conflicts with the type
+// information returned by TypeResolver.
+LIBPROTOBUF_EXPORT util::Status JsonToBinaryStream(
+ TypeResolver* resolver,
+ const string& type_url,
+ io::ZeroCopyInputStream* json_input,
+ io::ZeroCopyOutputStream* binary_output,
+ const JsonParseOptions& options);
+
+inline util::Status JsonToBinaryStream(
+ TypeResolver* resolver,
+ const string& type_url,
+ io::ZeroCopyInputStream* json_input,
+ io::ZeroCopyOutputStream* binary_output) {
+ return JsonToBinaryStream(resolver, type_url, json_input, binary_output,
+ JsonParseOptions());
+}
+
+LIBPROTOBUF_EXPORT util::Status JsonToBinaryString(
+ TypeResolver* resolver,
+ const string& type_url,
+ const string& json_input,
+ string* binary_output,
+ const JsonParseOptions& options);
+
+inline util::Status JsonToBinaryString(
+ TypeResolver* resolver,
+ const string& type_url,
+ const string& json_input,
+ string* binary_output) {
+ return JsonToBinaryString(resolver, type_url, json_input, binary_output,
+ JsonParseOptions());
+}
+
+namespace internal {
+// Internal helper class. Put in the header so we can write unit-tests for it.
+class LIBPROTOBUF_EXPORT ZeroCopyStreamByteSink : public strings::ByteSink {
+ public:
+ explicit ZeroCopyStreamByteSink(io::ZeroCopyOutputStream* stream)
+ : stream_(stream) {}
+
+ virtual void Append(const char* bytes, size_t len);
+
+ private:
+ io::ZeroCopyOutputStream* stream_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ZeroCopyStreamByteSink);
+};
+} // namespace internal
+
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_JSON_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util_test.cc
new file mode 100644
index 0000000000..dacac5e01a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/json_util_test.cc
@@ -0,0 +1,354 @@
+// 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.
+
+#include <google/protobuf/util/json_util.h>
+
+#include <list>
+#include <string>
+
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/descriptor_database.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/util/json_format_proto3.pb.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/util/type_resolver_util.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace {
+
+using proto3::FOO;
+using proto3::BAR;
+using proto3::TestMessage;
+using proto3::TestMap;
+
+static const char kTypeUrlPrefix[] = "type.googleapis.com";
+
+static string GetTypeUrl(const Descriptor* message) {
+ return string(kTypeUrlPrefix) + "/" + message->full_name();
+}
+
+// As functions defined in json_util.h are just thin wrappers around the
+// JSON conversion code in //net/proto2/util/converter, in this test we
+// only cover some very basic cases to make sure the wrappers have forwarded
+// parameters to the underlying implementation correctly. More detailed
+// tests are contained in the //net/proto2/util/converter directory.
+class JsonUtilTest : public testing::Test {
+ protected:
+ JsonUtilTest() {
+ }
+
+ string ToJson(const Message& message, const JsonPrintOptions& options) {
+ string result;
+ GOOGLE_CHECK_OK(MessageToJsonString(message, &result, options));
+ return result;
+ }
+
+ bool FromJson(const string& json, Message* message,
+ const JsonParseOptions& options) {
+ return JsonStringToMessage(json, message, options).ok();
+ }
+
+ bool FromJson(const string& json, Message* message) {
+ return FromJson(json, message, JsonParseOptions());
+ }
+
+ google::protobuf::scoped_ptr<TypeResolver> resolver_;
+};
+
+TEST_F(JsonUtilTest, TestWhitespaces) {
+ TestMessage m;
+ m.mutable_message_value();
+
+ JsonPrintOptions options;
+ EXPECT_EQ("{\"messageValue\":{}}", ToJson(m, options));
+ options.add_whitespace = true;
+ EXPECT_EQ(
+ "{\n"
+ " \"messageValue\": {}\n"
+ "}\n",
+ ToJson(m, options));
+}
+
+TEST_F(JsonUtilTest, TestDefaultValues) {
+ TestMessage m;
+ JsonPrintOptions options;
+ EXPECT_EQ("{}", ToJson(m, options));
+ options.always_print_primitive_fields = true;
+ EXPECT_EQ(
+ "{\"boolValue\":false,"
+ "\"int32Value\":0,"
+ "\"int64Value\":\"0\","
+ "\"uint32Value\":0,"
+ "\"uint64Value\":\"0\","
+ "\"floatValue\":0,"
+ "\"doubleValue\":0,"
+ "\"stringValue\":\"\","
+ "\"bytesValue\":\"\","
+ "\"enumValue\":\"FOO\","
+ "\"repeatedBoolValue\":[],"
+ "\"repeatedInt32Value\":[],"
+ "\"repeatedInt64Value\":[],"
+ "\"repeatedUint32Value\":[],"
+ "\"repeatedUint64Value\":[],"
+ "\"repeatedFloatValue\":[],"
+ "\"repeatedDoubleValue\":[],"
+ "\"repeatedStringValue\":[],"
+ "\"repeatedBytesValue\":[],"
+ "\"repeatedEnumValue\":[],"
+ "\"repeatedMessageValue\":[]"
+ "}",
+ ToJson(m, options));
+}
+
+TEST_F(JsonUtilTest, ParseMessage) {
+ // Some random message but good enough to verify that the parsing warpper
+ // functions are working properly.
+ string input =
+ "{\n"
+ " \"int32Value\": 1024,\n"
+ " \"repeatedInt32Value\": [1, 2],\n"
+ " \"messageValue\": {\n"
+ " \"value\": 2048\n"
+ " },\n"
+ " \"repeatedMessageValue\": [\n"
+ " {\"value\": 40}, {\"value\": 96}\n"
+ " ]\n"
+ "}\n";
+ JsonParseOptions options;
+ TestMessage m;
+ ASSERT_TRUE(FromJson(input, &m, options));
+ EXPECT_EQ(1024, m.int32_value());
+ ASSERT_EQ(2, m.repeated_int32_value_size());
+ EXPECT_EQ(1, m.repeated_int32_value(0));
+ EXPECT_EQ(2, m.repeated_int32_value(1));
+ EXPECT_EQ(2048, m.message_value().value());
+ ASSERT_EQ(2, m.repeated_message_value_size());
+ EXPECT_EQ(40, m.repeated_message_value(0).value());
+ EXPECT_EQ(96, m.repeated_message_value(1).value());
+}
+
+TEST_F(JsonUtilTest, ParseMap) {
+ TestMap message;
+ (*message.mutable_string_map())["hello"] = 1234;
+ JsonPrintOptions print_options;
+ JsonParseOptions parse_options;
+ EXPECT_EQ("{\"stringMap\":{\"hello\":1234}}", ToJson(message, print_options));
+ TestMap other;
+ ASSERT_TRUE(FromJson(ToJson(message, print_options), &other, parse_options));
+ EXPECT_EQ(message.DebugString(), other.DebugString());
+}
+
+TEST_F(JsonUtilTest, TestParseIgnoreUnknownFields) {
+ TestMessage m;
+ JsonParseOptions options;
+ options.ignore_unknown_fields = true;
+ EXPECT_TRUE(FromJson("{\"unknownName\":0}", &m, options));
+}
+
+TEST_F(JsonUtilTest, TestParseErrors) {
+ TestMessage m;
+ JsonParseOptions options;
+ // Parsing should fail if the field name can not be recognized.
+ EXPECT_FALSE(FromJson("{\"unknownName\":0}", &m, options));
+ // Parsing should fail if the value is invalid.
+ EXPECT_FALSE(FromJson("{\"int32Value\":2147483648}", &m, options));
+}
+
+TEST_F(JsonUtilTest, TestDynamicMessage) {
+ // Some random message but good enough to test the wrapper functions.
+ string input =
+ "{\n"
+ " \"int32Value\": 1024,\n"
+ " \"repeatedInt32Value\": [1, 2],\n"
+ " \"messageValue\": {\n"
+ " \"value\": 2048\n"
+ " },\n"
+ " \"repeatedMessageValue\": [\n"
+ " {\"value\": 40}, {\"value\": 96}\n"
+ " ]\n"
+ "}\n";
+
+ // Create a new DescriptorPool with the same protos as the generated one.
+ DescriptorPoolDatabase database(*DescriptorPool::generated_pool());
+ DescriptorPool pool(&database);
+ // A dynamic version of the test proto.
+ DynamicMessageFactory factory;
+ google::protobuf::scoped_ptr<Message> message(factory.GetPrototype(
+ pool.FindMessageTypeByName("proto3.TestMessage"))->New());
+ EXPECT_TRUE(FromJson(input, message.get()));
+
+ // Convert to generated message for easy inspection.
+ TestMessage generated;
+ EXPECT_TRUE(generated.ParseFromString(message->SerializeAsString()));
+ EXPECT_EQ(1024, generated.int32_value());
+ ASSERT_EQ(2, generated.repeated_int32_value_size());
+ EXPECT_EQ(1, generated.repeated_int32_value(0));
+ EXPECT_EQ(2, generated.repeated_int32_value(1));
+ EXPECT_EQ(2048, generated.message_value().value());
+ ASSERT_EQ(2, generated.repeated_message_value_size());
+ EXPECT_EQ(40, generated.repeated_message_value(0).value());
+ EXPECT_EQ(96, generated.repeated_message_value(1).value());
+
+ JsonOptions options;
+ EXPECT_EQ(ToJson(generated, options), ToJson(*message, options));
+}
+
+typedef pair<char*, int> Segment;
+// A ZeroCopyOutputStream that writes to multiple buffers.
+class SegmentedZeroCopyOutputStream : public io::ZeroCopyOutputStream {
+ public:
+ explicit SegmentedZeroCopyOutputStream(list<Segment> segments)
+ : segments_(segments), last_segment_(static_cast<char*>(NULL), 0), byte_count_(0) {}
+
+ virtual bool Next(void** buffer, int* length) {
+ if (segments_.empty()) {
+ return false;
+ }
+ last_segment_ = segments_.front();
+ segments_.pop_front();
+ *buffer = last_segment_.first;
+ *length = last_segment_.second;
+ byte_count_ += *length;
+ return true;
+ }
+
+ virtual void BackUp(int length) {
+ GOOGLE_CHECK(length <= last_segment_.second);
+ segments_.push_front(
+ Segment(last_segment_.first + last_segment_.second - length, length));
+ last_segment_ = Segment(last_segment_.first, last_segment_.second - length);
+ byte_count_ -= length;
+ }
+
+ virtual int64 ByteCount() const { return byte_count_; }
+
+ private:
+ list<Segment> segments_;
+ Segment last_segment_;
+ int64 byte_count_;
+};
+
+// This test splits the output buffer and also the input data into multiple
+// segments and checks that the implementation of ZeroCopyStreamByteSink
+// handles all possible cases correctly.
+TEST(ZeroCopyStreamByteSinkTest, TestAllInputOutputPatterns) {
+ static const int kOutputBufferLength = 10;
+ // An exhaustive test takes too long, skip some combinations to make the test
+ // run faster.
+ static const int kSkippedPatternCount = 7;
+
+ char buffer[kOutputBufferLength];
+ for (int split_pattern = 0; split_pattern < (1 << (kOutputBufferLength - 1));
+ split_pattern += kSkippedPatternCount) {
+ // Split the buffer into small segments according to the split_pattern.
+ list<Segment> segments;
+ int segment_start = 0;
+ for (int i = 0; i < kOutputBufferLength - 1; ++i) {
+ if (split_pattern & (1 << i)) {
+ segments.push_back(
+ Segment(buffer + segment_start, i - segment_start + 1));
+ segment_start = i + 1;
+ }
+ }
+ segments.push_back(
+ Segment(buffer + segment_start, kOutputBufferLength - segment_start));
+
+ // Write exactly 10 bytes through the ByteSink.
+ string input_data = "0123456789";
+ for (int input_pattern = 0; input_pattern < (1 << (input_data.size() - 1));
+ input_pattern += kSkippedPatternCount) {
+ memset(buffer, 0, sizeof(buffer));
+ {
+ SegmentedZeroCopyOutputStream output_stream(segments);
+ internal::ZeroCopyStreamByteSink byte_sink(&output_stream);
+ int start = 0;
+ for (int j = 0; j < input_data.length() - 1; ++j) {
+ if (input_pattern & (1 << j)) {
+ byte_sink.Append(&input_data[start], j - start + 1);
+ start = j + 1;
+ }
+ }
+ byte_sink.Append(&input_data[start], input_data.length() - start);
+ }
+ EXPECT_EQ(input_data, string(buffer, input_data.length()));
+ }
+
+ // Write only 9 bytes through the ByteSink.
+ input_data = "012345678";
+ for (int input_pattern = 0; input_pattern < (1 << (input_data.size() - 1));
+ input_pattern += kSkippedPatternCount) {
+ memset(buffer, 0, sizeof(buffer));
+ {
+ SegmentedZeroCopyOutputStream output_stream(segments);
+ internal::ZeroCopyStreamByteSink byte_sink(&output_stream);
+ int start = 0;
+ for (int j = 0; j < input_data.length() - 1; ++j) {
+ if (input_pattern & (1 << j)) {
+ byte_sink.Append(&input_data[start], j - start + 1);
+ start = j + 1;
+ }
+ }
+ byte_sink.Append(&input_data[start], input_data.length() - start);
+ }
+ EXPECT_EQ(input_data, string(buffer, input_data.length()));
+ EXPECT_EQ(0, buffer[input_data.length()]);
+ }
+
+ // Write 11 bytes through the ByteSink. The extra byte will just
+ // be ignored.
+ input_data = "0123456789A";
+ for (int input_pattern = 0; input_pattern < (1 << (input_data.size() - 1));
+ input_pattern += kSkippedPatternCount) {
+ memset(buffer, 0, sizeof(buffer));
+ {
+ SegmentedZeroCopyOutputStream output_stream(segments);
+ internal::ZeroCopyStreamByteSink byte_sink(&output_stream);
+ int start = 0;
+ for (int j = 0; j < input_data.length() - 1; ++j) {
+ if (input_pattern & (1 << j)) {
+ byte_sink.Append(&input_data[start], j - start + 1);
+ start = j + 1;
+ }
+ }
+ byte_sink.Append(&input_data[start], input_data.length() - start);
+ }
+ EXPECT_EQ(input_data.substr(0, kOutputBufferLength),
+ string(buffer, kOutputBufferLength));
+ }
+ }
+}
+
+} // namespace
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.cc
new file mode 100644
index 0000000000..a6d0cb0749
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.cc
@@ -0,0 +1,1692 @@
+// 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: jschorr@google.com (Joseph Schorr)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// This file defines static methods and classes for comparing Protocol
+// Messages (see //google/protobuf/util/message_differencer.h for more
+// information).
+
+#include <google/protobuf/util/message_differencer.h>
+
+#include <algorithm>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <utility>
+
+#include <google/protobuf/stubs/callback.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/any.h>
+#include <google/protobuf/io/printer.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/dynamic_message.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/util/field_comparator.h>
+#include <google/protobuf/stubs/strutil.h>
+
+namespace google {
+namespace protobuf {
+
+namespace util {
+
+// When comparing a repeated field as map, MultipleFieldMapKeyComparator can
+// be used to specify multiple fields as key for key comparison.
+// Two elements of a repeated field will be regarded as having the same key
+// iff they have the same value for every specified key field.
+// Note that you can also specify only one field as key.
+class MessageDifferencer::MultipleFieldsMapKeyComparator
+ : public MessageDifferencer::MapKeyComparator {
+ public:
+ MultipleFieldsMapKeyComparator(
+ MessageDifferencer* message_differencer,
+ const vector<vector<const FieldDescriptor*> >& key_field_paths)
+ : message_differencer_(message_differencer),
+ key_field_paths_(key_field_paths) {
+ GOOGLE_CHECK(!key_field_paths_.empty());
+ for (int i = 0; i < key_field_paths_.size(); ++i) {
+ GOOGLE_CHECK(!key_field_paths_[i].empty());
+ }
+ }
+ MultipleFieldsMapKeyComparator(
+ MessageDifferencer* message_differencer,
+ const FieldDescriptor* key)
+ : message_differencer_(message_differencer) {
+ vector<const FieldDescriptor*> key_field_path;
+ key_field_path.push_back(key);
+ key_field_paths_.push_back(key_field_path);
+ }
+ virtual bool IsMatch(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& parent_fields) const {
+ for (int i = 0; i < key_field_paths_.size(); ++i) {
+ if (!IsMatchInternal(message1, message2, parent_fields,
+ key_field_paths_[i], 0)) {
+ return false;
+ }
+ }
+ return true;
+ }
+ private:
+ bool IsMatchInternal(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& parent_fields,
+ const vector<const FieldDescriptor*>& key_field_path,
+ int path_index) const {
+ const FieldDescriptor* field = key_field_path[path_index];
+ vector<SpecificField> current_parent_fields(parent_fields);
+ if (path_index == key_field_path.size() - 1) {
+ if (field->is_repeated()) {
+ if (!message_differencer_->CompareRepeatedField(
+ message1, message2, field, &current_parent_fields)) {
+ return false;
+ }
+ } else {
+ if (!message_differencer_->CompareFieldValueUsingParentFields(
+ message1, message2, field, -1, -1, &current_parent_fields)) {
+ return false;
+ }
+ }
+ return true;
+ } else {
+ const Reflection* reflection1 = message1.GetReflection();
+ const Reflection* reflection2 = message2.GetReflection();
+ bool has_field1 = reflection1->HasField(message1, field);
+ bool has_field2 = reflection2->HasField(message2, field);
+ if (!has_field1 && !has_field2) {
+ return true;
+ }
+ if (has_field1 != has_field2) {
+ return false;
+ }
+ SpecificField specific_field;
+ specific_field.field = field;
+ current_parent_fields.push_back(specific_field);
+ return IsMatchInternal(
+ reflection1->GetMessage(message1, field),
+ reflection2->GetMessage(message2, field),
+ current_parent_fields,
+ key_field_path,
+ path_index + 1);
+ }
+ }
+ MessageDifferencer* message_differencer_;
+ vector<vector<const FieldDescriptor*> > key_field_paths_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MultipleFieldsMapKeyComparator);
+};
+
+bool MessageDifferencer::Equals(const Message& message1,
+ const Message& message2) {
+ MessageDifferencer differencer;
+
+ return differencer.Compare(message1, message2);
+}
+
+bool MessageDifferencer::Equivalent(const Message& message1,
+ const Message& message2) {
+ MessageDifferencer differencer;
+ differencer.set_message_field_comparison(MessageDifferencer::EQUIVALENT);
+
+ return differencer.Compare(message1, message2);
+}
+
+bool MessageDifferencer::ApproximatelyEquals(const Message& message1,
+ const Message& message2) {
+ MessageDifferencer differencer;
+ differencer.set_float_comparison(
+ MessageDifferencer::APPROXIMATE);
+
+ return differencer.Compare(message1, message2);
+}
+
+bool MessageDifferencer::ApproximatelyEquivalent(const Message& message1,
+ const Message& message2) {
+ MessageDifferencer differencer;
+ differencer.set_message_field_comparison(MessageDifferencer::EQUIVALENT);
+ differencer.set_float_comparison(MessageDifferencer::APPROXIMATE);
+
+ return differencer.Compare(message1, message2);
+}
+
+// ===========================================================================
+
+MessageDifferencer::MessageDifferencer()
+ : reporter_(NULL),
+ field_comparator_(NULL),
+ message_field_comparison_(EQUAL),
+ scope_(FULL),
+ repeated_field_comparison_(AS_LIST),
+ report_matches_(false),
+ output_string_(NULL) { }
+
+MessageDifferencer::~MessageDifferencer() {
+ for (int i = 0; i < owned_key_comparators_.size(); ++i) {
+ delete owned_key_comparators_[i];
+ }
+ for (int i = 0; i < ignore_criteria_.size(); ++i) {
+ delete ignore_criteria_[i];
+ }
+}
+
+void MessageDifferencer::set_field_comparator(FieldComparator* comparator) {
+ GOOGLE_CHECK(comparator) << "Field comparator can't be NULL.";
+ field_comparator_ = comparator;
+}
+
+void MessageDifferencer::set_message_field_comparison(
+ MessageFieldComparison comparison) {
+ message_field_comparison_ = comparison;
+}
+
+void MessageDifferencer::set_scope(Scope scope) {
+ scope_ = scope;
+}
+
+MessageDifferencer::Scope MessageDifferencer::scope() {
+ return scope_;
+}
+
+void MessageDifferencer::set_float_comparison(FloatComparison comparison) {
+ default_field_comparator_.set_float_comparison(
+ comparison == EXACT ?
+ DefaultFieldComparator::EXACT : DefaultFieldComparator::APPROXIMATE);
+}
+
+void MessageDifferencer::set_repeated_field_comparison(
+ RepeatedFieldComparison comparison) {
+ repeated_field_comparison_ = comparison;
+}
+
+void MessageDifferencer::TreatAsSet(const FieldDescriptor* field) {
+ GOOGLE_CHECK(field->is_repeated()) << "Field must be repeated: "
+ << field->full_name();
+ const MapKeyComparator* key_comparator = GetMapKeyComparator(field);
+ GOOGLE_CHECK(key_comparator == NULL)
+ << "Cannot treat this repeated field as both Map and Set for"
+ << " comparison. Field name is: " << field->full_name();
+ GOOGLE_CHECK(list_fields_.find(field) == list_fields_.end())
+ << "Cannot treat the same field as both SET and LIST. Field name is: "
+ << field->full_name();
+ set_fields_.insert(field);
+}
+
+void MessageDifferencer::TreatAsList(const FieldDescriptor* field) {
+ GOOGLE_CHECK(field->is_repeated()) << "Field must be repeated: "
+ << field->full_name();
+ const MapKeyComparator* key_comparator = GetMapKeyComparator(field);
+ GOOGLE_CHECK(key_comparator == NULL)
+ << "Cannot treat this repeated field as both Map and Set for"
+ << " comparison. Field name is: " << field->full_name();
+ GOOGLE_CHECK(set_fields_.find(field) == set_fields_.end())
+ << "Cannot treat the same field as both SET and LIST. Field name is: "
+ << field->full_name();
+ list_fields_.insert(field);
+}
+
+void MessageDifferencer::TreatAsMap(const FieldDescriptor* field,
+ const FieldDescriptor* key) {
+ GOOGLE_CHECK(field->is_repeated()) << "Field must be repeated: "
+ << field->full_name();
+ GOOGLE_CHECK_EQ(FieldDescriptor::CPPTYPE_MESSAGE, field->cpp_type())
+ << "Field has to be message type. Field name is: "
+ << field->full_name();
+ GOOGLE_CHECK(key->containing_type() == field->message_type())
+ << key->full_name()
+ << " must be a direct subfield within the repeated field "
+ << field->full_name() << ", not " << key->containing_type()->full_name();
+ GOOGLE_CHECK(set_fields_.find(field) == set_fields_.end())
+ << "Cannot treat this repeated field as both Map and Set for "
+ << "comparison.";
+ GOOGLE_CHECK(list_fields_.find(field) == list_fields_.end())
+ << "Cannot treat this repeated field as both Map and List for "
+ << "comparison.";
+ MapKeyComparator* key_comparator =
+ new MultipleFieldsMapKeyComparator(this, key);
+ owned_key_comparators_.push_back(key_comparator);
+ map_field_key_comparator_[field] = key_comparator;
+}
+
+void MessageDifferencer::TreatAsMapWithMultipleFieldsAsKey(
+ const FieldDescriptor* field,
+ const vector<const FieldDescriptor*>& key_fields) {
+ vector<vector<const FieldDescriptor*> > key_field_paths;
+ for (int i = 0; i < key_fields.size(); ++i) {
+ vector<const FieldDescriptor*> key_field_path;
+ key_field_path.push_back(key_fields[i]);
+ key_field_paths.push_back(key_field_path);
+ }
+ TreatAsMapWithMultipleFieldPathsAsKey(field, key_field_paths);
+}
+
+void MessageDifferencer::TreatAsMapWithMultipleFieldPathsAsKey(
+ const FieldDescriptor* field,
+ const vector<vector<const FieldDescriptor*> >& key_field_paths) {
+ GOOGLE_CHECK(field->is_repeated()) << "Field must be repeated: "
+ << field->full_name();
+ GOOGLE_CHECK_EQ(FieldDescriptor::CPPTYPE_MESSAGE, field->cpp_type())
+ << "Field has to be message type. Field name is: "
+ << field->full_name();
+ for (int i = 0; i < key_field_paths.size(); ++i) {
+ const vector<const FieldDescriptor*>& key_field_path = key_field_paths[i];
+ for (int j = 0; j < key_field_path.size(); ++j) {
+ const FieldDescriptor* parent_field =
+ j == 0 ? field : key_field_path[j - 1];
+ const FieldDescriptor* child_field = key_field_path[j];
+ GOOGLE_CHECK(child_field->containing_type() == parent_field->message_type())
+ << child_field->full_name()
+ << " must be a direct subfield within the field: "
+ << parent_field->full_name();
+ if (j != 0) {
+ GOOGLE_CHECK_EQ(FieldDescriptor::CPPTYPE_MESSAGE, parent_field->cpp_type())
+ << parent_field->full_name() << " has to be of type message.";
+ GOOGLE_CHECK(!parent_field->is_repeated())
+ << parent_field->full_name() << " cannot be a repeated field.";
+ }
+ }
+ }
+ GOOGLE_CHECK(set_fields_.find(field) == set_fields_.end())
+ << "Cannot treat this repeated field as both Map and Set for "
+ << "comparison.";
+ MapKeyComparator* key_comparator =
+ new MultipleFieldsMapKeyComparator(this, key_field_paths);
+ owned_key_comparators_.push_back(key_comparator);
+ map_field_key_comparator_[field] = key_comparator;
+}
+
+void MessageDifferencer::TreatAsMapUsingKeyComparator(
+ const FieldDescriptor* field,
+ const MapKeyComparator* key_comparator) {
+ GOOGLE_CHECK(field->is_repeated()) << "Field must be repeated: "
+ << field->full_name();
+ GOOGLE_CHECK_EQ(FieldDescriptor::CPPTYPE_MESSAGE, field->cpp_type())
+ << "Field has to be message type. Field name is: "
+ << field->full_name();
+ GOOGLE_CHECK(set_fields_.find(field) == set_fields_.end())
+ << "Cannot treat this repeated field as both Map and Set for "
+ << "comparison.";
+ map_field_key_comparator_[field] = key_comparator;
+}
+
+void MessageDifferencer::AddIgnoreCriteria(IgnoreCriteria* ignore_criteria) {
+ ignore_criteria_.push_back(ignore_criteria);
+}
+
+void MessageDifferencer::IgnoreField(const FieldDescriptor* field) {
+ ignored_fields_.insert(field);
+}
+
+void MessageDifferencer::SetFractionAndMargin(const FieldDescriptor* field,
+ double fraction, double margin) {
+ default_field_comparator_.SetFractionAndMargin(field, fraction, margin);
+}
+
+void MessageDifferencer::ReportDifferencesToString(string* output) {
+ GOOGLE_DCHECK(output) << "Specified output string was NULL";
+
+ output_string_ = output;
+ output_string_->clear();
+}
+
+void MessageDifferencer::ReportDifferencesTo(Reporter* reporter) {
+ // If an output string is set, clear it to prevent
+ // it superceding the specified reporter.
+ if (output_string_) {
+ output_string_ = NULL;
+ }
+
+ reporter_ = reporter;
+}
+
+bool MessageDifferencer::FieldBefore(const FieldDescriptor* field1,
+ const FieldDescriptor* field2) {
+ // Handle sentinel values (i.e. make sure NULLs are always ordered
+ // at the end of the list).
+ if (field1 == NULL) {
+ return false;
+ }
+
+ if (field2 == NULL) {
+ return true;
+ }
+
+ // Always order fields by their tag number
+ return (field1->number() < field2->number());
+}
+
+bool MessageDifferencer::Compare(const Message& message1,
+ const Message& message2) {
+ vector<SpecificField> parent_fields;
+
+ bool result = false;
+
+ // Setup the internal reporter if need be.
+ if (output_string_) {
+ io::StringOutputStream output_stream(output_string_);
+ StreamReporter reporter(&output_stream);
+ reporter_ = &reporter;
+ result = Compare(message1, message2, &parent_fields);
+ reporter_ = NULL;
+ } else {
+ result = Compare(message1, message2, &parent_fields);
+ }
+
+ return result;
+}
+
+bool MessageDifferencer::CompareWithFields(
+ const Message& message1,
+ const Message& message2,
+ const vector<const FieldDescriptor*>& message1_fields_arg,
+ const vector<const FieldDescriptor*>& message2_fields_arg) {
+ if (message1.GetDescriptor() != message2.GetDescriptor()) {
+ GOOGLE_LOG(DFATAL) << "Comparison between two messages with different "
+ << "descriptors.";
+ return false;
+ }
+
+ vector<SpecificField> parent_fields;
+
+ bool result = false;
+
+ vector<const FieldDescriptor*> message1_fields(message1_fields_arg);
+ vector<const FieldDescriptor*> message2_fields(message2_fields_arg);
+
+ std::sort(message1_fields.begin(), message1_fields.end(), FieldBefore);
+ std::sort(message2_fields.begin(), message2_fields.end(), FieldBefore);
+ // Append NULL sentinel values.
+ message1_fields.push_back(NULL);
+ message2_fields.push_back(NULL);
+
+ // Setup the internal reporter if need be.
+ if (output_string_) {
+ io::StringOutputStream output_stream(output_string_);
+ StreamReporter reporter(&output_stream);
+ reporter_ = &reporter;
+ result = CompareRequestedFieldsUsingSettings(
+ message1, message2, message1_fields, message2_fields, &parent_fields);
+ reporter_ = NULL;
+ } else {
+ result = CompareRequestedFieldsUsingSettings(
+ message1, message2, message1_fields, message2_fields, &parent_fields);
+ }
+
+ return result;
+}
+
+bool MessageDifferencer::Compare(
+ const Message& message1,
+ const Message& message2,
+ vector<SpecificField>* parent_fields) {
+ const Descriptor* descriptor1 = message1.GetDescriptor();
+ const Descriptor* descriptor2 = message2.GetDescriptor();
+ if (descriptor1 != descriptor2) {
+ GOOGLE_LOG(DFATAL) << "Comparison between two messages with different "
+ << "descriptors. "
+ << descriptor1->full_name() << " vs "
+ << descriptor2->full_name();
+ return false;
+ }
+ // Expand google.protobuf.Any payload if possible.
+ if (descriptor1->full_name() == internal::kAnyFullTypeName) {
+ google::protobuf::scoped_ptr<Message> data1;
+ google::protobuf::scoped_ptr<Message> data2;
+ if (UnpackAny(message1, &data1) && UnpackAny(message2, &data2)) {
+ return Compare(*data1, *data2, parent_fields);
+ }
+ }
+ const Reflection* reflection1 = message1.GetReflection();
+ const Reflection* reflection2 = message2.GetReflection();
+
+ // Retrieve all the set fields, including extensions.
+ vector<const FieldDescriptor*> message1_fields;
+ message1_fields.reserve(1 + message1.GetDescriptor()->field_count());
+
+ vector<const FieldDescriptor*> message2_fields;
+ message2_fields.reserve(1 + message2.GetDescriptor()->field_count());
+
+ reflection1->ListFields(message1, &message1_fields);
+ reflection2->ListFields(message2, &message2_fields);
+
+ // Add sentinel values to deal with the
+ // case where the number of the fields in
+ // each list are different.
+ message1_fields.push_back(NULL);
+ message2_fields.push_back(NULL);
+
+ bool unknown_compare_result = true;
+ // Ignore unknown fields in EQUIVALENT mode
+ if (message_field_comparison_ != EQUIVALENT) {
+ const google::protobuf::UnknownFieldSet* unknown_field_set1 =
+ &reflection1->GetUnknownFields(message1);
+ const google::protobuf::UnknownFieldSet* unknown_field_set2 =
+ &reflection2->GetUnknownFields(message2);
+ if (!CompareUnknownFields(message1, message2,
+ *unknown_field_set1, *unknown_field_set2,
+ parent_fields)) {
+ if (reporter_ == NULL) {
+ return false;
+ };
+ unknown_compare_result = false;
+ }
+ }
+
+ return CompareRequestedFieldsUsingSettings(
+ message1, message2,
+ message1_fields, message2_fields,
+ parent_fields) && unknown_compare_result;
+}
+
+bool MessageDifferencer::CompareRequestedFieldsUsingSettings(
+ const Message& message1,
+ const Message& message2,
+ const vector<const FieldDescriptor*>& message1_fields,
+ const vector<const FieldDescriptor*>& message2_fields,
+ vector<SpecificField>* parent_fields) {
+ if (scope_ == FULL) {
+ if (message_field_comparison_ == EQUIVALENT) {
+ // We need to merge the field lists of both messages (i.e.
+ // we are merely checking for a difference in field values,
+ // rather than the addition or deletion of fields).
+ vector<const FieldDescriptor*> fields_union;
+ CombineFields(message1_fields, FULL, message2_fields, FULL,
+ &fields_union);
+ return CompareWithFieldsInternal(message1, message2, fields_union,
+ fields_union, parent_fields);
+ } else {
+ // Simple equality comparison, use the unaltered field lists.
+ return CompareWithFieldsInternal(message1, message2, message1_fields,
+ message2_fields, parent_fields);
+ }
+ } else {
+ if (message_field_comparison_ == EQUIVALENT) {
+ // We use the list of fields for message1 for both messages when
+ // comparing. This way, extra fields in message2 are ignored,
+ // and missing fields in message2 use their default value.
+ return CompareWithFieldsInternal(message1, message2, message1_fields,
+ message1_fields, parent_fields);
+ } else {
+ // We need to consider the full list of fields for message1
+ // but only the intersection for message2. This way, any fields
+ // only present in message2 will be ignored, but any fields only
+ // present in message1 will be marked as a difference.
+ vector<const FieldDescriptor*> fields_intersection;
+ CombineFields(message1_fields, PARTIAL, message2_fields, PARTIAL,
+ &fields_intersection);
+ return CompareWithFieldsInternal(message1, message2, message1_fields,
+ fields_intersection, parent_fields);
+ }
+ }
+}
+
+void MessageDifferencer::CombineFields(
+ const vector<const FieldDescriptor*>& fields1,
+ Scope fields1_scope,
+ const vector<const FieldDescriptor*>& fields2,
+ Scope fields2_scope,
+ vector<const FieldDescriptor*>* combined_fields) {
+
+ int index1 = 0;
+ int index2 = 0;
+
+ while (index1 < fields1.size() && index2 < fields2.size()) {
+ const FieldDescriptor* field1 = fields1[index1];
+ const FieldDescriptor* field2 = fields2[index2];
+
+ if (FieldBefore(field1, field2)) {
+ if (fields1_scope == FULL) {
+ combined_fields->push_back(fields1[index1]);
+ }
+ ++index1;
+ } else if (FieldBefore(field2, field1)) {
+ if (fields2_scope == FULL) {
+ combined_fields->push_back(fields2[index2]);
+ }
+ ++index2;
+ } else {
+ combined_fields->push_back(fields1[index1]);
+ ++index1;
+ ++index2;
+ }
+ }
+}
+
+bool MessageDifferencer::CompareWithFieldsInternal(
+ const Message& message1,
+ const Message& message2,
+ const vector<const FieldDescriptor*>& message1_fields,
+ const vector<const FieldDescriptor*>& message2_fields,
+ vector<SpecificField>* parent_fields) {
+ bool isDifferent = false;
+ int field_index1 = 0;
+ int field_index2 = 0;
+
+ const Reflection* reflection1 = message1.GetReflection();
+ const Reflection* reflection2 = message2.GetReflection();
+
+ while (true) {
+ const FieldDescriptor* field1 = message1_fields[field_index1];
+ const FieldDescriptor* field2 = message2_fields[field_index2];
+
+ // Once we have reached sentinel values, we are done the comparison.
+ if (field1 == NULL && field2 == NULL) {
+ break;
+ }
+
+ // Check for differences in the field itself.
+ if (FieldBefore(field1, field2)) {
+ // Field 1 is not in the field list for message 2.
+ if (IsIgnored(message1, message2, field1, *parent_fields)) {
+ // We are ignoring field1. Report the ignore and move on to
+ // the next field in message1_fields.
+ if (reporter_ != NULL) {
+ SpecificField specific_field;
+ specific_field.field = field1;
+
+ parent_fields->push_back(specific_field);
+ reporter_->ReportIgnored(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ }
+ ++field_index1;
+ continue;
+ }
+
+ if (reporter_ != NULL) {
+ int count = field1->is_repeated() ?
+ reflection1->FieldSize(message1, field1) : 1;
+
+ for (int i = 0; i < count; ++i) {
+ SpecificField specific_field;
+ specific_field.field = field1;
+ specific_field.index = field1->is_repeated() ? i : -1;
+
+ parent_fields->push_back(specific_field);
+ reporter_->ReportDeleted(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ }
+
+ isDifferent = true;
+ } else {
+ return false;
+ }
+
+ ++field_index1;
+ continue;
+ } else if (FieldBefore(field2, field1)) {
+ // Field 2 is not in the field list for message 1.
+ if (IsIgnored(message1, message2, field2, *parent_fields)) {
+ // We are ignoring field2. Report the ignore and move on to
+ // the next field in message2_fields.
+ if (reporter_ != NULL) {
+ SpecificField specific_field;
+ specific_field.field = field2;
+
+ parent_fields->push_back(specific_field);
+ reporter_->ReportIgnored(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ }
+ ++field_index2;
+ continue;
+ }
+
+ if (reporter_ != NULL) {
+ int count = field2->is_repeated() ?
+ reflection2->FieldSize(message2, field2) : 1;
+
+ for (int i = 0; i < count; ++i) {
+ SpecificField specific_field;
+ specific_field.field = field2;
+ specific_field.index = field2->is_repeated() ? i : -1;
+ specific_field.new_index = specific_field.index;
+
+ parent_fields->push_back(specific_field);
+ reporter_->ReportAdded(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ }
+
+ isDifferent = true;
+ } else {
+ return false;
+ }
+
+ ++field_index2;
+ continue;
+ }
+
+ // By this point, field1 and field2 are guarenteed to point to the same
+ // field, so we can now compare the values.
+ if (IsIgnored(message1, message2, field1, *parent_fields)) {
+ // Ignore this field. Report and move on.
+ if (reporter_ != NULL) {
+ SpecificField specific_field;
+ specific_field.field = field1;
+
+ parent_fields->push_back(specific_field);
+ reporter_->ReportIgnored(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ }
+
+ ++field_index1;
+ ++field_index2;
+ continue;
+ }
+
+ bool fieldDifferent = false;
+ if (field1->is_repeated()) {
+ fieldDifferent = !CompareRepeatedField(message1, message2, field1,
+ parent_fields);
+ if (fieldDifferent) {
+ if (reporter_ == NULL) return false;
+ isDifferent = true;
+ }
+ } else {
+ fieldDifferent = !CompareFieldValueUsingParentFields(
+ message1, message2, field1, -1, -1, parent_fields);
+
+ // If we have found differences, either report them or terminate if
+ // no reporter is present.
+ if (fieldDifferent && reporter_ == NULL) {
+ return false;
+ }
+
+ if (reporter_ != NULL) {
+ SpecificField specific_field;
+ specific_field.field = field1;
+ parent_fields->push_back(specific_field);
+ if (fieldDifferent) {
+ reporter_->ReportModified(message1, message2, *parent_fields);
+ isDifferent = true;
+ } else if (report_matches_) {
+ reporter_->ReportMatched(message1, message2, *parent_fields);
+ }
+ parent_fields->pop_back();
+ }
+ }
+ // Increment the field indicies.
+ ++field_index1;
+ ++field_index2;
+ }
+
+ return !isDifferent;
+}
+
+bool MessageDifferencer::IsMatch(const FieldDescriptor* repeated_field,
+ const MapKeyComparator* key_comparator,
+ const Message* message1,
+ const Message* message2,
+ const vector<SpecificField>& parent_fields,
+ int index1, int index2) {
+ vector<SpecificField> current_parent_fields(parent_fields);
+ if (repeated_field->cpp_type() != FieldDescriptor::CPPTYPE_MESSAGE) {
+ return CompareFieldValueUsingParentFields(
+ *message1, *message2, repeated_field, index1, index2,
+ &current_parent_fields);
+ }
+ // Back up the Reporter and output_string_. They will be reset in the
+ // following code.
+ Reporter* backup_reporter = reporter_;
+ string* output_string = output_string_;
+ reporter_ = NULL;
+ output_string_ = NULL;
+ bool match;
+
+ if (key_comparator == NULL) {
+ match = CompareFieldValueUsingParentFields(
+ *message1, *message2, repeated_field, index1, index2,
+ &current_parent_fields);
+ } else {
+ const Reflection* reflection1 = message1->GetReflection();
+ const Reflection* reflection2 = message2->GetReflection();
+ const Message& m1 =
+ reflection1->GetRepeatedMessage(*message1, repeated_field, index1);
+ const Message& m2 =
+ reflection2->GetRepeatedMessage(*message2, repeated_field, index2);
+ SpecificField specific_field;
+ specific_field.field = repeated_field;
+ current_parent_fields.push_back(specific_field);
+ match = key_comparator->IsMatch(m1, m2, current_parent_fields);
+ }
+
+ reporter_ = backup_reporter;
+ output_string_ = output_string;
+ return match;
+}
+
+bool MessageDifferencer::CompareRepeatedField(
+ const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* repeated_field,
+ vector<SpecificField>* parent_fields) {
+ // the input FieldDescriptor is guaranteed to be repeated field.
+ const Reflection* reflection1 = message1.GetReflection();
+ const Reflection* reflection2 = message2.GetReflection();
+ const int count1 = reflection1->FieldSize(message1, repeated_field);
+ const int count2 = reflection2->FieldSize(message2, repeated_field);
+ const bool treated_as_subset = IsTreatedAsSubset(repeated_field);
+
+ // If the field is not treated as subset and no detailed reports is needed,
+ // we do a quick check on the number of the elements to avoid unnecessary
+ // comparison.
+ if (count1 != count2 && reporter_ == NULL && !treated_as_subset) {
+ return false;
+ }
+ // A match can never be found if message1 has more items than message2.
+ if (count1 > count2 && reporter_ == NULL) {
+ return false;
+ }
+
+ // These two list are used for store the index of the correspondent
+ // element in peer repeated field.
+ vector<int> match_list1;
+ vector<int> match_list2;
+
+ // Try to match indices of the repeated fields. Return false if match fails
+ // and there's no detailed report needed.
+ if (!MatchRepeatedFieldIndices(message1, message2, repeated_field,
+ *parent_fields, &match_list1, &match_list2) &&
+ reporter_ == NULL) {
+ return false;
+ }
+
+ bool fieldDifferent = false;
+ SpecificField specific_field;
+ specific_field.field = repeated_field;
+
+ // At this point, we have already matched pairs of fields (with the reporting
+ // to be done later). Now to check if the paired elements are different.
+ for (int i = 0; i < count1; i++) {
+ if (match_list1[i] == -1) continue;
+ specific_field.index = i;
+ specific_field.new_index = match_list1[i];
+
+ const bool result = CompareFieldValueUsingParentFields(
+ message1, message2, repeated_field, i, specific_field.new_index,
+ parent_fields);
+
+ // If we have found differences, either report them or terminate if
+ // no reporter is present. Note that ReportModified, ReportMoved, and
+ // ReportMatched are all mutually exclusive.
+ if (!result) {
+ if (reporter_ == NULL) return false;
+ parent_fields->push_back(specific_field);
+ reporter_->ReportModified(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ fieldDifferent = true;
+ } else if (reporter_ != NULL &&
+ specific_field.index != specific_field.new_index) {
+ parent_fields->push_back(specific_field);
+ reporter_->ReportMoved(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ } else if (report_matches_ && reporter_ != NULL) {
+ parent_fields->push_back(specific_field);
+ reporter_->ReportMatched(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ }
+ }
+
+ // Report any remaining additions or deletions.
+ for (int i = 0; i < count2; ++i) {
+ if (match_list2[i] != -1) continue;
+ if (!treated_as_subset) {
+ fieldDifferent = true;
+ }
+
+ if (reporter_ == NULL) continue;
+ specific_field.index = i;
+ specific_field.new_index = i;
+ parent_fields->push_back(specific_field);
+ reporter_->ReportAdded(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ }
+
+ for (int i = 0; i < count1; ++i) {
+ if (match_list1[i] != -1) continue;
+ specific_field.index = i;
+ parent_fields->push_back(specific_field);
+ reporter_->ReportDeleted(message1, message2, *parent_fields);
+ parent_fields->pop_back();
+ fieldDifferent = true;
+ }
+ return !fieldDifferent;
+}
+
+bool MessageDifferencer::CompareFieldValue(const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* field,
+ int index1,
+ int index2) {
+ return CompareFieldValueUsingParentFields(message1, message2, field, index1,
+ index2, NULL);
+}
+
+bool MessageDifferencer::CompareFieldValueUsingParentFields(
+ const Message& message1, const Message& message2,
+ const FieldDescriptor* field, int index1, int index2,
+ vector<SpecificField>* parent_fields) {
+ FieldContext field_context(parent_fields);
+ FieldComparator::ComparisonResult result = GetFieldComparisonResult(
+ message1, message2, field, index1, index2, &field_context);
+
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ result == FieldComparator::RECURSE) {
+ // Get the nested messages and compare them using one of the Compare
+ // methods.
+ const Reflection* reflection1 = message1.GetReflection();
+ const Reflection* reflection2 = message2.GetReflection();
+ const Message& m1 = field->is_repeated() ?
+ reflection1->GetRepeatedMessage(message1, field, index1) :
+ reflection1->GetMessage(message1, field);
+ const Message& m2 = field->is_repeated() ?
+ reflection2->GetRepeatedMessage(message2, field, index2) :
+ reflection2->GetMessage(message2, field);
+
+ // parent_fields is used in calls to Reporter methods.
+ if (parent_fields != NULL) {
+ // Append currently compared field to the end of parent_fields.
+ SpecificField specific_field;
+ specific_field.field = field;
+ specific_field.index = index1;
+ specific_field.new_index = index2;
+ parent_fields->push_back(specific_field);
+ const bool compare_result = Compare(m1, m2, parent_fields);
+ parent_fields->pop_back();
+ return compare_result;
+ } else {
+ // Recreates parent_fields as if m1 and m2 had no parents.
+ return Compare(m1, m2);
+ }
+ } else {
+ return (result == FieldComparator::SAME);
+ }
+}
+
+bool MessageDifferencer::CheckPathChanged(
+ const vector<SpecificField>& field_path) {
+ for (int i = 0; i < field_path.size(); ++i) {
+ if (field_path[i].index != field_path[i].new_index) return true;
+ }
+ return false;
+}
+
+bool MessageDifferencer::IsTreatedAsSet(const FieldDescriptor* field) {
+ if (!field->is_repeated()) return false;
+ if (field->is_map()) return true;
+ if (repeated_field_comparison_ == AS_SET)
+ return list_fields_.find(field) == list_fields_.end();
+ return (set_fields_.find(field) != set_fields_.end());
+}
+
+bool MessageDifferencer::IsTreatedAsSubset(const FieldDescriptor* field) {
+ return scope_ == PARTIAL &&
+ (IsTreatedAsSet(field) || GetMapKeyComparator(field) != NULL);
+}
+
+bool MessageDifferencer::IsIgnored(
+ const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* field,
+ const vector<SpecificField>& parent_fields) {
+ if (ignored_fields_.find(field) != ignored_fields_.end()) {
+ return true;
+ }
+ for (int i = 0; i < ignore_criteria_.size(); ++i) {
+ if (ignore_criteria_[i]->IsIgnored(message1, message2, field,
+ parent_fields)) {
+ return true;
+ }
+ }
+ return false;
+}
+
+bool MessageDifferencer::IsUnknownFieldIgnored(
+ const Message& message1, const Message& message2,
+ const SpecificField& field, const vector<SpecificField>& parent_fields) {
+ for (int i = 0; i < ignore_criteria_.size(); ++i) {
+ if (ignore_criteria_[i]->IsUnknownFieldIgnored(message1, message2, field,
+ parent_fields)) {
+ return true;
+ }
+ }
+ return false;
+}
+
+const MessageDifferencer::MapKeyComparator* MessageDifferencer
+ ::GetMapKeyComparator(const FieldDescriptor* field) {
+ if (!field->is_repeated()) return NULL;
+ if (map_field_key_comparator_.find(field) !=
+ map_field_key_comparator_.end()) {
+ return map_field_key_comparator_[field];
+ }
+ return NULL;
+}
+
+namespace {
+
+typedef pair<int, const UnknownField*> IndexUnknownFieldPair;
+
+struct UnknownFieldOrdering {
+ inline bool operator()(const IndexUnknownFieldPair& a,
+ const IndexUnknownFieldPair& b) const {
+ if (a.second->number() < b.second->number()) return true;
+ if (a.second->number() > b.second->number()) return false;
+ return a.second->type() < b.second->type();
+ }
+};
+
+} // namespace
+
+bool MessageDifferencer::UnpackAny(const Message& any,
+ google::protobuf::scoped_ptr<Message>* data) {
+ const Reflection* reflection = any.GetReflection();
+ const FieldDescriptor* type_url_field;
+ const FieldDescriptor* value_field;
+ if (!internal::GetAnyFieldDescriptors(any, &type_url_field, &value_field)) {
+ return false;
+ }
+ const string& type_url = reflection->GetString(any, type_url_field);
+ string full_type_name;
+ if (!internal::ParseAnyTypeUrl(type_url, &full_type_name)) {
+ return false;
+ }
+
+ const google::protobuf::Descriptor* desc =
+ any.GetDescriptor()->file()->pool()->FindMessageTypeByName(
+ full_type_name);
+ if (desc == NULL) {
+ GOOGLE_DLOG(ERROR) << "Proto type '" << full_type_name << "' not found";
+ return false;
+ }
+
+ if (dynamic_message_factory_ == NULL) {
+ dynamic_message_factory_.reset(new DynamicMessageFactory());
+ }
+ data->reset(dynamic_message_factory_->GetPrototype(desc)->New());
+ string serialized_value = reflection->GetString(any, value_field);
+ if (!(*data)->ParseFromString(serialized_value)) {
+ GOOGLE_DLOG(ERROR) << "Failed to parse value for " << full_type_name;
+ return false;
+ }
+ return true;
+}
+
+bool MessageDifferencer::CompareUnknownFields(
+ const Message& message1, const Message& message2,
+ const google::protobuf::UnknownFieldSet& unknown_field_set1,
+ const google::protobuf::UnknownFieldSet& unknown_field_set2,
+ vector<SpecificField>* parent_field) {
+ // Ignore unknown fields in EQUIVALENT mode.
+ if (message_field_comparison_ == EQUIVALENT) return true;
+
+ if (unknown_field_set1.empty() && unknown_field_set2.empty()) {
+ return true;
+ }
+
+ bool is_different = false;
+
+ // We first sort the unknown fields by field number and type (in other words,
+ // in tag order), making sure to preserve ordering of values with the same
+ // tag. This allows us to report only meaningful differences between the
+ // two sets -- that is, differing values for the same tag. We use
+ // IndexUnknownFieldPairs to keep track of the field's original index for
+ // reporting purposes.
+ vector<IndexUnknownFieldPair> fields1; // unknown_field_set1, sorted
+ vector<IndexUnknownFieldPair> fields2; // unknown_field_set2, sorted
+ fields1.reserve(unknown_field_set1.field_count());
+ fields2.reserve(unknown_field_set2.field_count());
+
+ for (int i = 0; i < unknown_field_set1.field_count(); i++) {
+ fields1.push_back(std::make_pair(i, &unknown_field_set1.field(i)));
+ }
+ for (int i = 0; i < unknown_field_set2.field_count(); i++) {
+ fields2.push_back(std::make_pair(i, &unknown_field_set2.field(i)));
+ }
+
+ UnknownFieldOrdering is_before;
+ std::stable_sort(fields1.begin(), fields1.end(), is_before);
+ std::stable_sort(fields2.begin(), fields2.end(), is_before);
+
+ // In order to fill in SpecificField::index, we have to keep track of how
+ // many values we've seen with the same field number and type.
+ // current_repeated points at the first field in this range, and
+ // current_repeated_start{1,2} are the indexes of the first field in the
+ // range within fields1 and fields2.
+ const UnknownField* current_repeated = NULL;
+ int current_repeated_start1 = 0;
+ int current_repeated_start2 = 0;
+
+ // Now that we have two sorted lists, we can detect fields which appear only
+ // in one list or the other by traversing them simultaneously.
+ int index1 = 0;
+ int index2 = 0;
+ while (index1 < fields1.size() || index2 < fields2.size()) {
+ enum { ADDITION, DELETION, MODIFICATION, COMPARE_GROUPS,
+ NO_CHANGE } change_type;
+
+ // focus_field is the field we're currently reporting on. (In the case
+ // of a modification, it's the field on the left side.)
+ const UnknownField* focus_field;
+ bool match = false;
+
+ if (index2 == fields2.size() ||
+ (index1 < fields1.size() &&
+ is_before(fields1[index1], fields2[index2]))) {
+ // fields1[index1] is not present in fields2.
+ change_type = DELETION;
+ focus_field = fields1[index1].second;
+ } else if (index1 == fields1.size() ||
+ is_before(fields2[index2], fields1[index1])) {
+ // fields2[index2] is not present in fields1.
+ if (scope_ == PARTIAL) {
+ // Ignore.
+ ++index2;
+ continue;
+ }
+ change_type = ADDITION;
+ focus_field = fields2[index2].second;
+ } else {
+ // Field type and number are the same. See if the values differ.
+ change_type = MODIFICATION;
+ focus_field = fields1[index1].second;
+
+ switch (focus_field->type()) {
+ case UnknownField::TYPE_VARINT:
+ match = fields1[index1].second->varint() ==
+ fields2[index2].second->varint();
+ break;
+ case UnknownField::TYPE_FIXED32:
+ match = fields1[index1].second->fixed32() ==
+ fields2[index2].second->fixed32();
+ break;
+ case UnknownField::TYPE_FIXED64:
+ match = fields1[index1].second->fixed64() ==
+ fields2[index2].second->fixed64();
+ break;
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ match = fields1[index1].second->length_delimited() ==
+ fields2[index2].second->length_delimited();
+ break;
+ case UnknownField::TYPE_GROUP:
+ // We must deal with this later, after building the SpecificField.
+ change_type = COMPARE_GROUPS;
+ break;
+ }
+ if (match && change_type != COMPARE_GROUPS) {
+ change_type = NO_CHANGE;
+ }
+ }
+
+ if (current_repeated == NULL ||
+ focus_field->number() != current_repeated->number() ||
+ focus_field->type() != current_repeated->type()) {
+ // We've started a new repeated field.
+ current_repeated = focus_field;
+ current_repeated_start1 = index1;
+ current_repeated_start2 = index2;
+ }
+
+ if (change_type == NO_CHANGE && reporter_ == NULL) {
+ // Fields were already compared and matched and we have no reporter.
+ ++index1;
+ ++index2;
+ continue;
+ }
+
+ // Build the SpecificField. This is slightly complicated.
+ SpecificField specific_field;
+ specific_field.unknown_field_number = focus_field->number();
+ specific_field.unknown_field_type = focus_field->type();
+
+ specific_field.unknown_field_set1 = &unknown_field_set1;
+ specific_field.unknown_field_set2 = &unknown_field_set2;
+
+ if (change_type != ADDITION) {
+ specific_field.unknown_field_index1 = fields1[index1].first;
+ }
+ if (change_type != DELETION) {
+ specific_field.unknown_field_index2 = fields2[index2].first;
+ }
+
+ // Calculate the field index.
+ if (change_type == ADDITION) {
+ specific_field.index = index2 - current_repeated_start2;
+ specific_field.new_index = index2 - current_repeated_start2;
+ } else {
+ specific_field.index = index1 - current_repeated_start1;
+ specific_field.new_index = index2 - current_repeated_start2;
+ }
+
+ if (IsUnknownFieldIgnored(message1, message2, specific_field,
+ *parent_field)) {
+ if (reporter_ != NULL) {
+ parent_field->push_back(specific_field);
+ reporter_->ReportUnknownFieldIgnored(message1, message2, *parent_field);
+ parent_field->pop_back();
+ }
+ return true;
+ }
+
+ if (change_type == ADDITION || change_type == DELETION ||
+ change_type == MODIFICATION) {
+ if (reporter_ == NULL) {
+ // We found a difference and we have no reproter.
+ return false;
+ }
+ is_different = true;
+ }
+
+ parent_field->push_back(specific_field);
+
+ switch (change_type) {
+ case ADDITION:
+ reporter_->ReportAdded(message1, message2, *parent_field);
+ ++index2;
+ break;
+ case DELETION:
+ reporter_->ReportDeleted(message1, message2, *parent_field);
+ ++index1;
+ break;
+ case MODIFICATION:
+ reporter_->ReportModified(message1, message2, *parent_field);
+ ++index1;
+ ++index2;
+ break;
+ case COMPARE_GROUPS:
+ if (!CompareUnknownFields(message1, message2,
+ fields1[index1].second->group(),
+ fields2[index2].second->group(),
+ parent_field)) {
+ if (reporter_ == NULL) return false;
+ is_different = true;
+ reporter_->ReportModified(message1, message2, *parent_field);
+ }
+ ++index1;
+ ++index2;
+ break;
+ case NO_CHANGE:
+ ++index1;
+ ++index2;
+ if (report_matches_) {
+ reporter_->ReportMatched(message1, message2, *parent_field);
+ }
+ }
+
+ parent_field->pop_back();
+ }
+
+ return !is_different;
+}
+
+namespace {
+
+// Find maximum bipartite matching using the argumenting path algorithm.
+class MaximumMatcher {
+ public:
+ typedef ResultCallback2<bool, int, int> NodeMatchCallback;
+ // MaximumMatcher takes ownership of the passed in callback and uses it to
+ // determine whether a node on the left side of the bipartial graph matches
+ // a node on the right side. count1 is the number of nodes on the left side
+ // of the graph and count2 to is the number of nodes on the right side.
+ // Every node is referred to using 0-based indices.
+ // If a maximum match is found, the result will be stored in match_list1 and
+ // match_list2. match_list1[i] == j means the i-th node on the left side is
+ // matched to the j-th node on the right side and match_list2[x] == y means
+ // the x-th node on the right side is matched to y-th node on the left side.
+ // match_list1[i] == -1 means the node is not matched. Same with match_list2.
+ MaximumMatcher(int count1, int count2, NodeMatchCallback* callback,
+ vector<int>* match_list1, vector<int>* match_list2);
+ // Find a maximum match and return the number of matched node pairs.
+ // If early_return is true, this method will return 0 immediately when it
+ // finds that not all nodes on the left side can be matched.
+ int FindMaximumMatch(bool early_return);
+ private:
+ // Determines whether the node on the left side of the bipartial graph
+ // matches the one on the right side.
+ bool Match(int left, int right);
+ // Find an argumenting path starting from the node v on the left side. If a
+ // path can be found, update match_list2_ to reflect the path and return
+ // true.
+ bool FindArgumentPathDFS(int v, vector<bool>* visited);
+
+ int count1_;
+ int count2_;
+ google::protobuf::scoped_ptr<NodeMatchCallback> match_callback_;
+ map<pair<int, int>, bool> cached_match_results_;
+ vector<int>* match_list1_;
+ vector<int>* match_list2_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MaximumMatcher);
+};
+
+MaximumMatcher::MaximumMatcher(int count1, int count2,
+ NodeMatchCallback* callback,
+ vector<int>* match_list1,
+ vector<int>* match_list2)
+ : count1_(count1), count2_(count2), match_callback_(callback),
+ match_list1_(match_list1), match_list2_(match_list2) {
+ match_list1_->assign(count1, -1);
+ match_list2_->assign(count2, -1);
+}
+
+int MaximumMatcher::FindMaximumMatch(bool early_return) {
+ int result = 0;
+ for (int i = 0; i < count1_; ++i) {
+ vector<bool> visited(count1_);
+ if (FindArgumentPathDFS(i, &visited)) {
+ ++result;
+ } else if (early_return) {
+ return 0;
+ }
+ }
+ // Backfill match_list1_ as we only filled match_list2_ when finding
+ // argumenting pathes.
+ for (int i = 0; i < count2_; ++i) {
+ if ((*match_list2_)[i] != -1) {
+ (*match_list1_)[(*match_list2_)[i]] = i;
+ }
+ }
+ return result;
+}
+
+bool MaximumMatcher::Match(int left, int right) {
+ pair<int, int> p(left, right);
+ map<pair<int, int>, bool>::iterator it = cached_match_results_.find(p);
+ if (it != cached_match_results_.end()) {
+ return it->second;
+ }
+ cached_match_results_[p] = match_callback_->Run(left, right);
+ return cached_match_results_[p];
+}
+
+bool MaximumMatcher::FindArgumentPathDFS(int v, vector<bool>* visited) {
+ (*visited)[v] = true;
+ // We try to match those un-matched nodes on the right side first. This is
+ // the step that the navie greedy matching algorithm uses. In the best cases
+ // where the greedy algorithm can find a maximum matching, we will always
+ // find a match in this step and the performance will be identical to the
+ // greedy algorithm.
+ for (int i = 0; i < count2_; ++i) {
+ int matched = (*match_list2_)[i];
+ if (matched == -1 && Match(v, i)) {
+ (*match_list2_)[i] = v;
+ return true;
+ }
+ }
+ // Then we try those already matched nodes and see if we can find an
+ // alternaive match for the node matched to them.
+ // The greedy algorithm will stop before this and fail to produce the
+ // correct result.
+ for (int i = 0; i < count2_; ++i) {
+ int matched = (*match_list2_)[i];
+ if (matched != -1 && Match(v, i)) {
+ if (!(*visited)[matched] && FindArgumentPathDFS(matched, visited)) {
+ (*match_list2_)[i] = v;
+ return true;
+ }
+ }
+ }
+ return false;
+}
+
+} // namespace
+
+bool MessageDifferencer::MatchRepeatedFieldIndices(
+ const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* repeated_field,
+ const vector<SpecificField>& parent_fields,
+ vector<int>* match_list1,
+ vector<int>* match_list2) {
+ const int count1 =
+ message1.GetReflection()->FieldSize(message1, repeated_field);
+ const int count2 =
+ message2.GetReflection()->FieldSize(message2, repeated_field);
+ const MapKeyComparator* key_comparator = GetMapKeyComparator(repeated_field);
+
+ match_list1->assign(count1, -1);
+ match_list2->assign(count2, -1);
+
+ SpecificField specific_field;
+ specific_field.field = repeated_field;
+
+ bool success = true;
+ // Find potential match if this is a special repeated field.
+ if (key_comparator != NULL || IsTreatedAsSet(repeated_field)) {
+ if (scope_ == PARTIAL) {
+ // When partial matching is enabled, Compare(a, b) && Compare(a, c)
+ // doesn't necessarily imply Compare(b, c). Therefore a naive greedy
+ // algorithm will fail to find a maximum matching.
+ // Here we use the argumenting path algorithm.
+ MaximumMatcher::NodeMatchCallback* callback =
+ ::google::protobuf::internal::NewPermanentCallback(
+ this, &MessageDifferencer::IsMatch,
+ repeated_field, key_comparator,
+ &message1, &message2, parent_fields);
+ MaximumMatcher matcher(count1, count2, callback, match_list1,
+ match_list2);
+ // If diff info is not needed, we should end the matching process as
+ // soon as possible if not all items can be matched.
+ bool early_return = (reporter_ == NULL);
+ int match_count = matcher.FindMaximumMatch(early_return);
+ if (match_count != count1 && reporter_ == NULL) return false;
+ success = success && (match_count == count1);
+ } else {
+ for (int i = 0; i < count1; ++i) {
+ // Indicates any matched elements for this repeated field.
+ bool match = false;
+
+ specific_field.index = i;
+ specific_field.new_index = i;
+
+ for (int j = 0; j < count2; j++) {
+ if (match_list2->at(j) != -1) continue;
+ specific_field.index = i;
+ specific_field.new_index = j;
+
+ match = IsMatch(repeated_field, key_comparator,
+ &message1, &message2, parent_fields, i, j);
+
+ if (match) {
+ match_list1->at(specific_field.index) = specific_field.new_index;
+ match_list2->at(specific_field.new_index) = specific_field.index;
+ break;
+ }
+ }
+ if (!match && reporter_ == NULL) return false;
+ success = success && match;
+ }
+ }
+ } else {
+ // If this field should be treated as list, just label the match_list.
+ for (int i = 0; i < count1 && i < count2; i++) {
+ match_list1->at(i) = i;
+ match_list2->at(i) = i;
+ }
+ }
+
+ return success;
+}
+
+FieldComparator::ComparisonResult MessageDifferencer::GetFieldComparisonResult(
+ const Message& message1, const Message& message2,
+ const FieldDescriptor* field, int index1, int index2,
+ const FieldContext* field_context) {
+ FieldComparator* comparator = field_comparator_ != NULL ?
+ field_comparator_ : &default_field_comparator_;
+ return comparator->Compare(message1, message2, field,
+ index1, index2, field_context);
+}
+
+// ===========================================================================
+
+MessageDifferencer::Reporter::Reporter() { }
+MessageDifferencer::Reporter::~Reporter() {}
+
+// ===========================================================================
+
+MessageDifferencer::MapKeyComparator::MapKeyComparator() {}
+MessageDifferencer::MapKeyComparator::~MapKeyComparator() {}
+
+// ===========================================================================
+
+MessageDifferencer::IgnoreCriteria::IgnoreCriteria() {}
+MessageDifferencer::IgnoreCriteria::~IgnoreCriteria() {}
+
+// ===========================================================================
+
+// Note that the printer's delimiter is not used, because if we are given a
+// printer, we don't know its delimiter.
+MessageDifferencer::StreamReporter::StreamReporter(
+ io::ZeroCopyOutputStream* output) : printer_(new io::Printer(output, '$')),
+ delete_printer_(true),
+ report_modified_aggregates_(false) { }
+
+MessageDifferencer::StreamReporter::StreamReporter(
+ io::Printer* printer) : printer_(printer),
+ delete_printer_(false),
+ report_modified_aggregates_(false) { }
+
+MessageDifferencer::StreamReporter::~StreamReporter() {
+ if (delete_printer_) delete printer_;
+}
+
+void MessageDifferencer::StreamReporter::PrintPath(
+ const vector<SpecificField>& field_path, bool left_side) {
+ for (int i = 0; i < field_path.size(); ++i) {
+ if (i > 0) {
+ printer_->Print(".");
+ }
+
+ SpecificField specific_field = field_path[i];
+
+ if (specific_field.field != NULL) {
+ if (specific_field.field->is_extension()) {
+ printer_->Print("($name$)", "name",
+ specific_field.field->full_name());
+ } else {
+ printer_->PrintRaw(specific_field.field->name());
+ }
+ } else {
+ printer_->PrintRaw(SimpleItoa(specific_field.unknown_field_number));
+ }
+ if (left_side && specific_field.index >= 0) {
+ printer_->Print("[$name$]", "name", SimpleItoa(specific_field.index));
+ }
+ if (!left_side && specific_field.new_index >= 0) {
+ printer_->Print("[$name$]", "name", SimpleItoa(specific_field.new_index));
+ }
+ }
+}
+
+void MessageDifferencer::
+StreamReporter::PrintValue(const Message& message,
+ const vector<SpecificField>& field_path,
+ bool left_side) {
+ const SpecificField& specific_field = field_path.back();
+ const FieldDescriptor* field = specific_field.field;
+ if (field != NULL) {
+ string output;
+ int index = left_side ? specific_field.index : specific_field.new_index;
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ const Reflection* reflection = message.GetReflection();
+ const Message& field_message = field->is_repeated() ?
+ reflection->GetRepeatedMessage(message, field, index) :
+ reflection->GetMessage(message, field);
+ output = field_message.ShortDebugString();
+ if (output.empty()) {
+ printer_->Print("{ }");
+ } else {
+ printer_->Print("{ $name$ }", "name", output);
+ }
+ } else {
+ TextFormat::PrintFieldValueToString(message, field, index, &output);
+ printer_->PrintRaw(output);
+ }
+ } else {
+ const UnknownFieldSet* unknown_fields =
+ (left_side ?
+ specific_field.unknown_field_set1 :
+ specific_field.unknown_field_set2);
+ const UnknownField* unknown_field = &unknown_fields->field(
+ left_side ?
+ specific_field.unknown_field_index1 :
+ specific_field.unknown_field_index2);
+ PrintUnknownFieldValue(unknown_field);
+ }
+}
+
+void MessageDifferencer::
+StreamReporter::PrintUnknownFieldValue(const UnknownField* unknown_field) {
+ GOOGLE_CHECK(unknown_field != NULL) << " Cannot print NULL unknown_field.";
+
+ string output;
+ switch (unknown_field->type()) {
+ case UnknownField::TYPE_VARINT:
+ output = SimpleItoa(unknown_field->varint());
+ break;
+ case UnknownField::TYPE_FIXED32:
+ output = StrCat("0x", strings::Hex(unknown_field->fixed32(),
+ strings::ZERO_PAD_8));
+ break;
+ case UnknownField::TYPE_FIXED64:
+ output = StrCat("0x", strings::Hex(unknown_field->fixed64(),
+ strings::ZERO_PAD_16));
+ break;
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ output = StringPrintf("\"%s\"",
+ CEscape(unknown_field->length_delimited()).c_str());
+ break;
+ case UnknownField::TYPE_GROUP:
+ // TODO(kenton): Print the contents of the group like we do for
+ // messages. Requires an equivalent of ShortDebugString() for
+ // UnknownFieldSet.
+ output = "{ ... }";
+ break;
+ }
+ printer_->PrintRaw(output);
+}
+
+void MessageDifferencer::StreamReporter::Print(const string& str) {
+ printer_->Print(str.c_str());
+}
+
+void MessageDifferencer::StreamReporter::ReportAdded(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) {
+ printer_->Print("added: ");
+ PrintPath(field_path, false);
+ printer_->Print(": ");
+ PrintValue(message2, field_path, false);
+ printer_->Print("\n"); // Print for newlines.
+}
+
+void MessageDifferencer::StreamReporter::ReportDeleted(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) {
+ printer_->Print("deleted: ");
+ PrintPath(field_path, true);
+ printer_->Print(": ");
+ PrintValue(message1, field_path, true);
+ printer_->Print("\n"); // Print for newlines
+}
+
+void MessageDifferencer::StreamReporter::ReportModified(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) {
+ if (!report_modified_aggregates_ && field_path.back().field == NULL) {
+ if (field_path.back().unknown_field_type == UnknownField::TYPE_GROUP) {
+ // Any changes to the subfields have already been printed.
+ return;
+ }
+ } else if (!report_modified_aggregates_) {
+ if (field_path.back().field->cpp_type() ==
+ FieldDescriptor::CPPTYPE_MESSAGE) {
+ // Any changes to the subfields have already been printed.
+ return;
+ }
+ }
+
+ printer_->Print("modified: ");
+ PrintPath(field_path, true);
+ if (CheckPathChanged(field_path)) {
+ printer_->Print(" -> ");
+ PrintPath(field_path, false);
+ }
+ printer_->Print(": ");
+ PrintValue(message1, field_path, true);
+ printer_->Print(" -> ");
+ PrintValue(message2, field_path, false);
+ printer_->Print("\n"); // Print for newlines.
+}
+
+void MessageDifferencer::StreamReporter::ReportMoved(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) {
+ printer_->Print("moved: ");
+ PrintPath(field_path, true);
+ printer_->Print(" -> ");
+ PrintPath(field_path, false);
+ printer_->Print(" : ");
+ PrintValue(message1, field_path, true);
+ printer_->Print("\n"); // Print for newlines.
+}
+
+void MessageDifferencer::StreamReporter::ReportMatched(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) {
+ printer_->Print("matched: ");
+ PrintPath(field_path, true);
+ if (CheckPathChanged(field_path)) {
+ printer_->Print(" -> ");
+ PrintPath(field_path, false);
+ }
+ printer_->Print(" : ");
+ PrintValue(message1, field_path, true);
+ printer_->Print("\n"); // Print for newlines.
+}
+
+void MessageDifferencer::StreamReporter::ReportIgnored(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) {
+ printer_->Print("ignored: ");
+ PrintPath(field_path, true);
+ if (CheckPathChanged(field_path)) {
+ printer_->Print(" -> ");
+ PrintPath(field_path, false);
+ }
+ printer_->Print("\n"); // Print for newlines.
+}
+
+void MessageDifferencer::StreamReporter::ReportUnknownFieldIgnored(
+ const Message& message1, const Message& message2,
+ const vector<SpecificField>& field_path) {
+ printer_->Print("ignored: ");
+ PrintPath(field_path, true);
+ if (CheckPathChanged(field_path)) {
+ printer_->Print(" -> ");
+ PrintPath(field_path, false);
+ }
+ printer_->Print("\n"); // Print for newlines.
+}
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.h
new file mode 100644
index 0000000000..654d1a67e2
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer.h
@@ -0,0 +1,849 @@
+// 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: jschorr@google.com (Joseph Schorr)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// This file defines static methods and classes for comparing Protocol
+// Messages.
+//
+// Aug. 2008: Added Unknown Fields Comparison for messages.
+// Aug. 2009: Added different options to compare repeated fields.
+// Apr. 2010: Moved field comparison to FieldComparator.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_MESSAGE_DIFFERENCER_H__
+#define GOOGLE_PROTOBUF_UTIL_MESSAGE_DIFFERENCER_H__
+
+#include <map>
+#include <set>
+#include <string>
+#include <vector>
+#include <google/protobuf/descriptor.h> // FieldDescriptor
+#include <google/protobuf/message.h> // Message
+#include <google/protobuf/unknown_field_set.h>
+#include <google/protobuf/util/field_comparator.h>
+
+namespace google {
+namespace protobuf {
+
+class DynamicMessageFactory;
+class FieldDescriptor;
+
+namespace io {
+class ZeroCopyOutputStream;
+class Printer;
+}
+
+namespace util {
+
+class FieldContext; // declared below MessageDifferencer
+
+// A basic differencer that can be used to determine
+// the differences between two specified Protocol Messages. If any differences
+// are found, the Compare method will return false, and any differencer reporter
+// specified via ReportDifferencesTo will have its reporting methods called (see
+// below for implementation of the report). Based off of the original
+// ProtocolDifferencer implementation in //net/proto/protocol-differencer.h
+// (Thanks Todd!).
+//
+// MessageDifferencer REQUIRES that compared messages be the same type, defined
+// as messages that share the same descriptor. If not, the behavior of this
+// class is undefined.
+//
+// People disagree on what MessageDifferencer should do when asked to compare
+// messages with different descriptors. Some people think it should always
+// return false. Others expect it to try to look for similar fields and
+// compare them anyway -- especially if the descriptors happen to be identical.
+// If we chose either of these behaviors, some set of people would find it
+// surprising, and could end up writing code expecting the other behavior
+// without realizing their error. Therefore, we forbid that usage.
+//
+// This class is implemented based on the proto2 reflection. The performance
+// should be good enough for normal usages. However, for places where the
+// performance is extremely sensitive, there are several alternatives:
+// - Comparing serialized string
+// Downside: false negatives (there are messages that are the same but their
+// serialized strings are different).
+// - Equals code generator by compiler plugin (net/proto2/contrib/equals_plugin)
+// Downside: more generated code; maintenance overhead for the additional rule
+// (must be in sync with the original proto_library).
+//
+// Note on handling of google.protobuf.Any: MessageDifferencer automatically
+// unpacks Any::value into a Message and compares its individual fields.
+// Messages encoded in a repeated Any cannot be compared using TreatAsMap.
+//
+//
+// Note on thread-safety: MessageDifferencer is *not* thread-safe. You need to
+// guard it with a lock to use the same MessageDifferencer instance from
+// multiple threads. Note that it's fine to call static comparison methods
+// (like MessageDifferencer::Equals) concurrently.
+class LIBPROTOBUF_EXPORT MessageDifferencer {
+ public:
+ // Determines whether the supplied messages are equal. Equality is defined as
+ // all fields within the two messages being set to the same value. Primitive
+ // fields and strings are compared by value while embedded messages/groups
+ // are compared as if via a recursive call. Use IgnoreField() and Compare()
+ // if some fields should be ignored in the comparison.
+ //
+ // This method REQUIRES that the two messages have the same
+ // Descriptor (message1.GetDescriptor() == message2.GetDescriptor()).
+ static bool Equals(const Message& message1, const Message& message2);
+
+ // Determines whether the supplied messages are equivalent. Equivalency is
+ // defined as all fields within the two messages having the same value. This
+ // differs from the Equals method above in that fields with default values
+ // are considered set to said value automatically. For details on how default
+ // values are defined for each field type, see http://shortn/_x2Gv6XFrWt.
+ // Also, Equivalent() ignores unknown fields. Use IgnoreField() and Compare()
+ // if some fields should be ignored in the comparison.
+ //
+ // This method REQUIRES that the two messages have the same
+ // Descriptor (message1.GetDescriptor() == message2.GetDescriptor()).
+ static bool Equivalent(const Message& message1, const Message& message2);
+
+ // Determines whether the supplied messages are approximately equal.
+ // Approximate equality is defined as all fields within the two messages
+ // being approximately equal. Primitive (non-float) fields and strings are
+ // compared by value, floats are compared using MathUtil::AlmostEquals() and
+ // embedded messages/groups are compared as if via a recursive call. Use
+ // IgnoreField() and Compare() if some fields should be ignored in the
+ // comparison.
+ //
+ // This method REQUIRES that the two messages have the same
+ // Descriptor (message1.GetDescriptor() == message2.GetDescriptor()).
+ static bool ApproximatelyEquals(const Message& message1,
+ const Message& message2);
+
+ // Determines whether the supplied messages are approximately equivalent.
+ // Approximate equivalency is defined as all fields within the two messages
+ // being approximately equivalent. As in
+ // MessageDifferencer::ApproximatelyEquals, primitive (non-float) fields and
+ // strings are compared by value, floats are compared using
+ // MathUtil::AlmostEquals() and embedded messages/groups are compared as if
+ // via a recursive call. However, fields with default values are considered
+ // set to said value, as per MessageDiffencer::Equivalent. Use IgnoreField()
+ // and Compare() if some fields should be ignored in the comparison.
+ //
+ // This method REQUIRES that the two messages have the same
+ // Descriptor (message1.GetDescriptor() == message2.GetDescriptor()).
+ static bool ApproximatelyEquivalent(const Message& message1,
+ const Message& message2);
+
+ // Identifies an individual field in a message instance. Used for field_path,
+ // below.
+ struct SpecificField {
+ // For known fields, "field" is filled in and "unknown_field_number" is -1.
+ // For unknown fields, "field" is NULL, "unknown_field_number" is the field
+ // number, and "unknown_field_type" is its type.
+ const FieldDescriptor* field;
+ int unknown_field_number;
+ UnknownField::Type unknown_field_type;
+
+ // If this a repeated field, "index" is the index within it. For unknown
+ // fields, this is the index of the field among all unknown fields of the
+ // same field number and type.
+ int index;
+
+ // If "field" is a repeated field which is being treated as a map or
+ // a set (see TreatAsMap() and TreatAsSet(), below), new_index indicates
+ // the index the position to which the element has moved. This only
+ // applies to ReportMoved() and (in the case of TreatAsMap())
+ // ReportModified(). In all other cases, "new_index" will have the same
+ // value as "index".
+ int new_index;
+
+ // For unknown fields, these are the pointers to the UnknownFieldSet
+ // containing the unknown fields. In certain cases (e.g. proto1's
+ // MessageSet, or nested groups of unknown fields), these may differ from
+ // the messages' internal UnknownFieldSets.
+ const UnknownFieldSet* unknown_field_set1;
+ const UnknownFieldSet* unknown_field_set2;
+
+ // For unknown fields, these are the index of the field within the
+ // UnknownFieldSets. One or the other will be -1 when
+ // reporting an addition or deletion.
+ int unknown_field_index1;
+ int unknown_field_index2;
+
+ SpecificField()
+ : field(NULL),
+ unknown_field_number(-1),
+ index(-1),
+ new_index(-1),
+ unknown_field_set1(NULL),
+ unknown_field_set2(NULL),
+ unknown_field_index1(-1),
+ unknown_field_index2(-1) {}
+ };
+
+ // Abstract base class from which all MessageDifferencer
+ // reporters derive. The five Report* methods below will be called when
+ // a field has been added, deleted, modified, moved, or matched. The third
+ // argument is a vector of FieldDescriptor pointers which describes the chain
+ // of fields that was taken to find the current field. For example, for a
+ // field found in an embedded message, the vector will contain two
+ // FieldDescriptors. The first will be the field of the embedded message
+ // itself and the second will be the actual field in the embedded message
+ // that was added/deleted/modified.
+ class LIBPROTOBUF_EXPORT Reporter {
+ public:
+ Reporter();
+ virtual ~Reporter();
+
+ // Reports that a field has been added into Message2.
+ virtual void ReportAdded(
+ const Message& message1, const Message& message2,
+ const vector<SpecificField>& field_path) = 0;
+
+ // Reports that a field has been deleted from Message1.
+ virtual void ReportDeleted(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) = 0;
+
+ // Reports that the value of a field has been modified.
+ virtual void ReportModified(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) = 0;
+
+ // Reports that a repeated field has been moved to another location. This
+ // only applies when using TreatAsSet or TreatAsMap() -- see below. Also
+ // note that for any given field, ReportModified and ReportMoved are
+ // mutually exclusive. If a field has been both moved and modified, then
+ // only ReportModified will be called.
+ virtual void ReportMoved(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) { }
+
+ // Reports that two fields match. Useful for doing side-by-side diffs.
+ // This function is mutually exclusive with ReportModified and ReportMoved.
+ // Note that you must call set_report_matches(true) before calling Compare
+ // to make use of this function.
+ virtual void ReportMatched(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) { }
+
+ // Reports that two fields would have been compared, but the
+ // comparison has been skipped because the field was marked as
+ // 'ignored' using IgnoreField(). This function is mutually
+ // exclusive with all the other Report() functions.
+ //
+ // The contract of ReportIgnored is slightly different than the
+ // other Report() functions, in that |field_path.back().index| is
+ // always equal to -1, even if the last field is repeated. This is
+ // because while the other Report() functions indicate where in a
+ // repeated field the action (Addition, Deletion, etc...)
+ // happened, when a repeated field is 'ignored', the differencer
+ // simply calls ReportIgnored on the repeated field as a whole and
+ // moves on without looking at its individual elements.
+ //
+ // Furthermore, ReportIgnored() does not indicate whether the
+ // fields were in fact equal or not, as Compare() does not inspect
+ // these fields at all. It is up to the Reporter to decide whether
+ // the fields are equal or not (perhaps with a second call to
+ // Compare()), if it cares.
+ virtual void ReportIgnored(
+ const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path) { }
+
+ // Report that an unknown field is ignored. (see comment above).
+ // Note this is a different function since the last SpecificField in field
+ // path has a null field. This could break existing Reporter.
+ virtual void ReportUnknownFieldIgnored(
+ const Message& message1, const Message& message2,
+ const vector<SpecificField>& field_path) {}
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(Reporter);
+ };
+
+ // MapKeyComparator is used to determine if two elements have the same key
+ // when comparing elements of a repeated field as a map.
+ class LIBPROTOBUF_EXPORT MapKeyComparator {
+ public:
+ MapKeyComparator();
+ virtual ~MapKeyComparator();
+
+ virtual bool IsMatch(const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& parent_fields) const {
+ GOOGLE_CHECK(false) << "IsMatch() is not implemented.";
+ return false;
+ }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MapKeyComparator);
+ };
+
+ // Abstract base class from which all IgnoreCriteria derive.
+ // By adding IgnoreCriteria more complex ignore logic can be implemented.
+ // IgnoreCriteria are registed with AddIgnoreCriteria. For each compared
+ // field IsIgnored is called on each added IgnoreCriteria until one returns
+ // true or all return false.
+ // IsIgnored is called for fields where at least one side has a value.
+ class LIBPROTOBUF_EXPORT IgnoreCriteria {
+ public:
+ IgnoreCriteria();
+ virtual ~IgnoreCriteria();
+
+ // Returns true if the field should be ignored.
+ virtual bool IsIgnored(
+ const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* field,
+ const vector<SpecificField>& parent_fields) = 0;
+
+ // Returns true if the unknown field should be ignored.
+ // Note: This will be called for unknown fields as well in which case
+ // field.field will be null.
+ virtual bool IsUnknownFieldIgnored(
+ const Message& message1, const Message& message2,
+ const SpecificField& field,
+ const vector<SpecificField>& parent_fields) {
+ return false;
+ }
+ };
+
+ // To add a Reporter, construct default here, then use ReportDifferencesTo or
+ // ReportDifferencesToString.
+ explicit MessageDifferencer();
+
+ ~MessageDifferencer();
+
+ enum MessageFieldComparison {
+ EQUAL, // Fields must be present in both messages
+ // for the messages to be considered the same.
+ EQUIVALENT, // Fields with default values are considered set
+ // for comparison purposes even if not explicitly
+ // set in the messages themselves. Unknown fields
+ // are ignored.
+ };
+
+ enum Scope {
+ FULL, // All fields of both messages are considered in the comparison.
+ PARTIAL // Only fields present in the first message are considered; fields
+ // set only in the second message will be skipped during
+ // comparison.
+ };
+
+ // DEPRECATED. Use FieldComparator::FloatComparison instead.
+ enum FloatComparison {
+ EXACT, // Floats and doubles are compared exactly.
+ APPROXIMATE // Floats and doubles are compared using the
+ // MathUtil::AlmostEquals method.
+ };
+
+ enum RepeatedFieldComparison {
+ AS_LIST, // Repeated fields are compared in order. Differing values at
+ // the same index are reported using ReportModified(). If the
+ // repeated fields have different numbers of elements, the
+ // unpaired elements are reported using ReportAdded() or
+ // ReportDeleted().
+ AS_SET, // Treat all the repeated fields as sets by default.
+ // See TreatAsSet(), as below.
+ };
+
+ // The elements of the given repeated field will be treated as a set for
+ // diffing purposes, so different orderings of the same elements will be
+ // considered equal. Elements which are present on both sides of the
+ // comparison but which have changed position will be reported with
+ // ReportMoved(). Elements which only exist on one side or the other are
+ // reported with ReportAdded() and ReportDeleted() regardless of their
+ // positions. ReportModified() is never used for this repeated field. If
+ // the only differences between the compared messages is that some fields
+ // have been moved, then the comparison returns true.
+ //
+ // If the scope of comparison is set to PARTIAL, then in addition to what's
+ // above, extra values added to repeated fields of the second message will
+ // not cause the comparison to fail.
+ //
+ // Note that set comparison is currently O(k * n^2) (where n is the total
+ // number of elements, and k is the average size of each element). In theory
+ // it could be made O(n * k) with a more complex hashing implementation. Feel
+ // free to contribute one if the current implementation is too slow for you.
+ // If partial matching is also enabled, the time complexity will be O(k * n^2
+ // + n^3) in which n^3 is the time complexity of the maximum matching
+ // algorithm.
+ //
+ // REQUIRES: field->is_repeated() and field not registered with TreatAsList
+ void TreatAsSet(const FieldDescriptor* field);
+
+ // The elements of the given repeated field will be treated as a list for
+ // diffing purposes, so different orderings of the same elements will NOT be
+ // considered equal.
+ //
+ // REQUIRED: field->is_repeated() and field not registered with TreatAsSet
+ void TreatAsList(const FieldDescriptor* field);
+
+ // The elements of the given repeated field will be treated as a map for
+ // diffing purposes, with |key| being the map key. Thus, elements with the
+ // same key will be compared even if they do not appear at the same index.
+ // Differences are reported similarly to TreatAsSet(), except that
+ // ReportModified() is used to report elements with the same key but
+ // different values. Note that if an element is both moved and modified,
+ // only ReportModified() will be called. As with TreatAsSet, if the only
+ // differences between the compared messages is that some fields have been
+ // moved, then the comparison returns true. See TreatAsSet for notes on
+ // performance.
+ //
+ // REQUIRES: field->is_repeated()
+ // REQUIRES: field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE
+ // REQUIRES: key->containing_type() == field->message_type()
+ void TreatAsMap(const FieldDescriptor* field, const FieldDescriptor* key);
+ // Same as TreatAsMap except that this method will use multiple fields as
+ // the key in comparison. All specified fields in 'key_fields' should be
+ // present in the compared elements. Two elements will be treated as having
+ // the same key iff they have the same value for every specified field. There
+ // are two steps in the comparison process. The first one is key matching.
+ // Every element from one message will be compared to every element from
+ // the other message. Only fields in 'key_fields' are compared in this step
+ // to decide if two elements have the same key. The second step is value
+ // comparison. Those pairs of elements with the same key (with equal value
+ // for every field in 'key_fields') will be compared in this step.
+ // Time complexity of the first step is O(s * m * n ^ 2) where s is the
+ // average size of the fields specified in 'key_fields', m is the number of
+ // fields in 'key_fields' and n is the number of elements. If partial
+ // matching is enabled, an extra O(n^3) will be incured by the maximum
+ // matching algorithm. The second step is O(k * n) where k is the average
+ // size of each element.
+ void TreatAsMapWithMultipleFieldsAsKey(
+ const FieldDescriptor* field,
+ const vector<const FieldDescriptor*>& key_fields);
+ // Same as TreatAsMapWithMultipleFieldsAsKey, except that each of the field
+ // do not necessarily need to be a direct subfield. Each element in
+ // key_field_paths indicate a path from the message being compared, listing
+ // successive subfield to reach the key field.
+ //
+ // REQUIRES:
+ // for key_field_path in key_field_paths:
+ // key_field_path[0]->containing_type() == field->message_type()
+ // for i in [0, key_field_path.size() - 1):
+ // key_field_path[i+1]->containing_type() ==
+ // key_field_path[i]->message_type()
+ // key_field_path[i]->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE
+ // !key_field_path[i]->is_repeated()
+ void TreatAsMapWithMultipleFieldPathsAsKey(
+ const FieldDescriptor* field,
+ const vector<vector<const FieldDescriptor*> >& key_field_paths);
+
+ // Uses a custom MapKeyComparator to determine if two elements have the same
+ // key when comparing a repeated field as a map.
+ // The caller is responsible to delete the key_comparator.
+ // This method varies from TreatAsMapWithMultipleFieldsAsKey only in the
+ // first key matching step. Rather than comparing some specified fields, it
+ // will invoke the IsMatch method of the given 'key_comparator' to decide if
+ // two elements have the same key.
+ void TreatAsMapUsingKeyComparator(
+ const FieldDescriptor* field,
+ const MapKeyComparator* key_comparator);
+
+ // Add a custom ignore criteria that is evaluated in addition to the
+ // ignored fields added with IgnoreField.
+ // Takes ownership of ignore_criteria.
+ void AddIgnoreCriteria(IgnoreCriteria* ignore_criteria);
+
+ // Indicates that any field with the given descriptor should be
+ // ignored for the purposes of comparing two messages. This applies
+ // to fields nested in the message structure as well as top level
+ // ones. When the MessageDifferencer encounters an ignored field,
+ // ReportIgnored is called on the reporter, if one is specified.
+ //
+ // The only place where the field's 'ignored' status is not applied is when
+ // it is being used as a key in a field passed to TreatAsMap or is one of
+ // the fields passed to TreatAsMapWithMultipleFieldsAsKey.
+ // In this case it is compared in key matching but after that it's ignored
+ // in value comparison.
+ void IgnoreField(const FieldDescriptor* field);
+
+ // Sets the field comparator used to determine differences between protocol
+ // buffer fields. By default it's set to a DefaultFieldComparator instance.
+ // MessageDifferencer doesn't take ownership over the passed object.
+ // Note that this method must be called before Compare for the comparator to
+ // be used.
+ void set_field_comparator(FieldComparator* comparator);
+
+ // DEPRECATED. Pass a DefaultFieldComparator instance instead.
+ // Sets the fraction and margin for the float comparison of a given field.
+ // Uses MathUtil::WithinFractionOrMargin to compare the values.
+ // NOTE: this method does nothing if differencer's field comparator has been
+ // set to a custom object.
+ //
+ // REQUIRES: field->cpp_type == FieldDescriptor::CPPTYPE_DOUBLE or
+ // field->cpp_type == FieldDescriptor::CPPTYPE_FLOAT
+ // REQUIRES: float_comparison_ == APPROXIMATE
+ void SetFractionAndMargin(const FieldDescriptor* field, double fraction,
+ double margin);
+
+ // Sets the type of comparison (as defined in the MessageFieldComparison
+ // enumeration above) that is used by this differencer when determining how
+ // to compare fields in messages.
+ void set_message_field_comparison(MessageFieldComparison comparison);
+
+ // Tells the differencer whether or not to report matches. This method must
+ // be called before Compare. The default for a new differencer is false.
+ void set_report_matches(bool report_matches) {
+ report_matches_ = report_matches;
+ }
+
+ // Sets the scope of the comparison (as defined in the Scope enumeration
+ // above) that is used by this differencer when determining which fields to
+ // compare between the messages.
+ void set_scope(Scope scope);
+
+ // Returns the current scope used by this differencer.
+ Scope scope();
+
+ // DEPRECATED. Pass a DefaultFieldComparator instance instead.
+ // Sets the type of comparison (as defined in the FloatComparison enumeration
+ // above) that is used by this differencer when comparing float (and double)
+ // fields in messages.
+ // NOTE: this method does nothing if differencer's field comparator has been
+ // set to a custom object.
+ void set_float_comparison(FloatComparison comparison);
+
+ // Sets the type of comparison for repeated field (as defined in the
+ // RepeatedFieldComparison enumeration above) that is used by this
+ // differencer when compare repeated fields in messages.
+ void set_repeated_field_comparison(RepeatedFieldComparison comparison);
+
+ // Compares the two specified messages, returning true if they are the same,
+ // false otherwise. If this method returns false, any changes between the
+ // two messages will be reported if a Reporter was specified via
+ // ReportDifferencesTo (see also ReportDifferencesToString).
+ //
+ // This method REQUIRES that the two messages have the same
+ // Descriptor (message1.GetDescriptor() == message2.GetDescriptor()).
+ bool Compare(const Message& message1, const Message& message2);
+
+ // Same as above, except comparing only the list of fields specified by the
+ // two vectors of FieldDescriptors.
+ bool CompareWithFields(const Message& message1, const Message& message2,
+ const vector<const FieldDescriptor*>& message1_fields,
+ const vector<const FieldDescriptor*>& message2_fields);
+
+ // Automatically creates a reporter that will output the differences
+ // found (if any) to the specified output string pointer. Note that this
+ // method must be called before Compare.
+ void ReportDifferencesToString(string* output);
+
+ // Tells the MessageDifferencer to report differences via the specified
+ // reporter. Note that this method must be called before Compare for
+ // the reporter to be used. It is the responsibility of the caller to delete
+ // this object.
+ // If the provided pointer equals NULL, the MessageDifferencer stops reporting
+ // differences to any previously set reporters or output strings.
+ void ReportDifferencesTo(Reporter* reporter);
+
+ // An implementation of the MessageDifferencer Reporter that outputs
+ // any differences found in human-readable form to the supplied
+ // ZeroCopyOutputStream or Printer. If a printer is used, the delimiter
+ // *must* be '$'.
+ //
+ // WARNING: this reporter does not necessarily flush its output until it is
+ // destroyed. As a result, it is not safe to assume the output is valid or
+ // complete until after you destroy the reporter. For example, if you use a
+ // StreamReporter to write to a StringOutputStream, the target string may
+ // contain uninitialized data until the reporter is destroyed.
+ class LIBPROTOBUF_EXPORT StreamReporter : public Reporter {
+ public:
+ explicit StreamReporter(io::ZeroCopyOutputStream* output);
+ explicit StreamReporter(io::Printer* printer); // delimiter '$'
+ virtual ~StreamReporter();
+
+ // When set to true, the stream reporter will also output aggregates nodes
+ // (i.e. messages and groups) whose subfields have been modified. When
+ // false, will only report the individual subfields. Defaults to false.
+ void set_report_modified_aggregates(bool report) {
+ report_modified_aggregates_ = report;
+ }
+
+ // The following are implementations of the methods described above.
+ virtual void ReportAdded(const Message& message1, const Message& message2,
+ const vector<SpecificField>& field_path);
+
+ virtual void ReportDeleted(const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path);
+
+ virtual void ReportModified(const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path);
+
+ virtual void ReportMoved(const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path);
+
+ virtual void ReportMatched(const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path);
+
+ virtual void ReportIgnored(const Message& message1,
+ const Message& message2,
+ const vector<SpecificField>& field_path);
+
+ virtual void ReportUnknownFieldIgnored(
+ const Message& message1, const Message& message2,
+ const vector<SpecificField>& field_path);
+
+ protected:
+ // Prints the specified path of fields to the buffer.
+ virtual void PrintPath(const vector<SpecificField>& field_path,
+ bool left_side);
+
+ // Prints the value of fields to the buffer. left_side is true if the
+ // given message is from the left side of the comparison, false if it
+ // was the right. This is relevant only to decide whether to follow
+ // unknown_field_index1 or unknown_field_index2 when an unknown field
+ // is encountered in field_path.
+ virtual void PrintValue(const Message& message,
+ const vector<SpecificField>& field_path,
+ bool left_side);
+
+ // Prints the specified path of unknown fields to the buffer.
+ virtual void PrintUnknownFieldValue(const UnknownField* unknown_field);
+
+ // Just print a string
+ void Print(const string& str);
+
+ private:
+ io::Printer* printer_;
+ bool delete_printer_;
+ bool report_modified_aggregates_;
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StreamReporter);
+ };
+
+ private:
+ // A MapKeyComparator to be used in TreatAsMapUsingKeyComparator.
+ // Implementation of this class needs to do field value comparison which
+ // relies on some private methods of MessageDifferencer. That's why this
+ // class is declared as a nested class of MessageDifferencer.
+ class MultipleFieldsMapKeyComparator;
+ // Returns true if field1's number() is less than field2's.
+ static bool FieldBefore(const FieldDescriptor* field1,
+ const FieldDescriptor* field2);
+
+ // Combine the two lists of fields into the combined_fields output vector.
+ // All fields present in both lists will always be included in the combined
+ // list. Fields only present in one of the lists will only appear in the
+ // combined list if the corresponding fields_scope option is set to FULL.
+ void CombineFields(const vector<const FieldDescriptor*>& fields1,
+ Scope fields1_scope,
+ const vector<const FieldDescriptor*>& fields2,
+ Scope fields2_scope,
+ vector<const FieldDescriptor*>* combined_fields);
+
+ // Internal version of the Compare method which performs the actual
+ // comparison. The parent_fields vector is a vector containing field
+ // descriptors of all fields accessed to get to this comparison operation
+ // (i.e. if the current message is an embedded message, the parent_fields
+ // vector will contain the field that has this embedded message).
+ bool Compare(const Message& message1, const Message& message2,
+ vector<SpecificField>* parent_fields);
+
+ // Compares all the unknown fields in two messages.
+ bool CompareUnknownFields(const Message& message1, const Message& message2,
+ const google::protobuf::UnknownFieldSet&,
+ const google::protobuf::UnknownFieldSet&,
+ vector<SpecificField>* parent_fields);
+
+ // Compares the specified messages for the requested field lists. The field
+ // lists are modified depending on comparison settings, and then passed to
+ // CompareWithFieldsInternal.
+ bool CompareRequestedFieldsUsingSettings(
+ const Message& message1, const Message& message2,
+ const vector<const FieldDescriptor*>& message1_fields,
+ const vector<const FieldDescriptor*>& message2_fields,
+ vector<SpecificField>* parent_fields);
+
+ // Compares the specified messages with the specified field lists.
+ bool CompareWithFieldsInternal(
+ const Message& message1, const Message& message2,
+ const vector<const FieldDescriptor*>& message1_fields,
+ const vector<const FieldDescriptor*>& message2_fields,
+ vector<SpecificField>* parent_fields);
+
+ // Compares the repeated fields, and report the error.
+ bool CompareRepeatedField(const Message& message1, const Message& message2,
+ const FieldDescriptor* field,
+ vector<SpecificField>* parent_fields);
+
+ // Shorthand for CompareFieldValueUsingParentFields with NULL parent_fields.
+ bool CompareFieldValue(const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* field,
+ int index1,
+ int index2);
+
+ // Compares the specified field on the two messages, returning
+ // true if they are the same, false otherwise. For repeated fields,
+ // this method only compares the value in the specified index. This method
+ // uses Compare functions to recurse into submessages.
+ // The parent_fields vector is used in calls to a Reporter instance calls.
+ // It can be NULL, in which case the MessageDifferencer will create new
+ // list of parent messages if it needs to recursively compare the given field.
+ // To avoid confusing users you should not set it to NULL unless you modified
+ // Reporter to handle the change of parent_fields correctly.
+ bool CompareFieldValueUsingParentFields(const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* field,
+ int index1,
+ int index2,
+ vector<SpecificField>* parent_fields);
+
+ // Compares the specified field on the two messages, returning comparison
+ // result, as returned by appropriate FieldComparator.
+ FieldComparator::ComparisonResult GetFieldComparisonResult(
+ const Message& message1, const Message& message2,
+ const FieldDescriptor* field, int index1, int index2,
+ const FieldContext* field_context);
+
+ // Check if the two elements in the repeated field are match to each other.
+ // if the key_comprator is NULL, this function returns true when the two
+ // elements are equal.
+ bool IsMatch(const FieldDescriptor* repeated_field,
+ const MapKeyComparator* key_comparator,
+ const Message* message1, const Message* message2,
+ const vector<SpecificField>& parent_fields,
+ int index1, int index2);
+
+ // Returns true when this repeated field has been configured to be treated
+ // as a set.
+ bool IsTreatedAsSet(const FieldDescriptor* field);
+
+ // Returns true when this repeated field is to be compared as a subset, ie.
+ // has been configured to be treated as a set or map and scope is set to
+ // PARTIAL.
+ bool IsTreatedAsSubset(const FieldDescriptor* field);
+
+ // Returns true if this field is to be ignored when this
+ // MessageDifferencer compares messages.
+ bool IsIgnored(
+ const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* field,
+ const vector<SpecificField>& parent_fields);
+
+ // Returns true if this unknown field is to be ignored when this
+ // MessageDifferencer compares messages.
+ bool IsUnknownFieldIgnored(const Message& message1, const Message& message2,
+ const SpecificField& field,
+ const vector<SpecificField>& parent_fields);
+
+ // Returns MapKeyComparator* when this field has been configured to
+ // be treated as a map. If not, returns NULL.
+ const MapKeyComparator* GetMapKeyComparator(const FieldDescriptor* field);
+
+ // Attempts to match indices of a repeated field, so that the contained values
+ // match. Clears output vectors and sets their values to indices of paired
+ // messages, ie. if message1[0] matches message2[1], then match_list1[0] == 1
+ // and match_list2[1] == 0. The unmatched indices are indicated by -1.
+ // This method returns false if the match failed. However, it doesn't mean
+ // that the comparison succeeds when this method returns true (you need to
+ // double-check in this case).
+ bool MatchRepeatedFieldIndices(const Message& message1,
+ const Message& message2,
+ const FieldDescriptor* repeated_field,
+ const vector<SpecificField>& parent_fields,
+ vector<int>* match_list1,
+ vector<int>* match_list2);
+
+ // If "any" is of type google.protobuf.Any, extract its payload using
+ // DynamicMessageFactory and store in "data".
+ bool UnpackAny(const Message& any, google::protobuf::scoped_ptr<Message>* data);
+
+ // Checks if index is equal to new_index in all the specific fields.
+ static bool CheckPathChanged(const vector<SpecificField>& parent_fields);
+
+ // Defines a map between field descriptors and their MapKeyComparators.
+ // Used for repeated fields when they are configured as TreatAsMap.
+ typedef map<const FieldDescriptor*,
+ const MapKeyComparator*> FieldKeyComparatorMap;
+
+ // Defines a set to store field descriptors. Used for repeated fields when
+ // they are configured as TreatAsSet.
+ typedef set<const FieldDescriptor*> FieldSet;
+
+ Reporter* reporter_;
+ DefaultFieldComparator default_field_comparator_;
+ FieldComparator* field_comparator_;
+ MessageFieldComparison message_field_comparison_;
+ Scope scope_;
+ RepeatedFieldComparison repeated_field_comparison_;
+
+ FieldSet set_fields_;
+ FieldSet list_fields_;
+ // Keeps track of MapKeyComparators that are created within
+ // MessageDifferencer. These MapKeyComparators should be deleted
+ // before MessageDifferencer is destroyed.
+ // When TreatAsMap or TreatAsMapWithMultipleFieldsAsKey is called, we don't
+ // store the supplied FieldDescriptors directly. Instead, a new
+ // MapKeyComparator is created for comparison purpose.
+ vector<MapKeyComparator*> owned_key_comparators_;
+ FieldKeyComparatorMap map_field_key_comparator_;
+ vector<IgnoreCriteria*> ignore_criteria_;
+
+ FieldSet ignored_fields_;
+
+ bool compare_unknown_fields_;
+ bool report_matches_;
+
+ string* output_string_;
+
+ google::protobuf::scoped_ptr<DynamicMessageFactory> dynamic_message_factory_;
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageDifferencer);
+};
+
+// This class provides extra information to the FieldComparator::Compare
+// function.
+class LIBPROTOBUF_EXPORT FieldContext {
+ public:
+ explicit FieldContext(
+ vector<MessageDifferencer::SpecificField>* parent_fields)
+ : parent_fields_(parent_fields) {}
+
+ vector<MessageDifferencer::SpecificField>* parent_fields() const {
+ return parent_fields_;
+ }
+
+ private:
+ vector<MessageDifferencer::SpecificField>* parent_fields_;
+};
+
+}
+}
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_MESSAGE_DIFFERENCER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.cc
new file mode 100755
index 0000000000..ed43c512c9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.cc
@@ -0,0 +1,3151 @@
+// 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: jschorr@google.com (Joseph Schorr)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// TODO(ksroka): Move some of these tests to field_comparator_test.cc.
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+
+#include <google/protobuf/util/field_comparator.h>
+#include <google/protobuf/util/message_differencer.h>
+#include <google/protobuf/util/message_differencer_unittest.pb.h>
+#include <google/protobuf/text_format.h>
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/any_test.pb.h>
+#include <google/protobuf/map_unittest.pb.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/map_test_util.h>
+#include <google/protobuf/test_util.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+
+const FieldDescriptor* GetFieldDescriptor(
+ const Message& message, const string& field_name) {
+ vector<string> field_path =
+ Split(field_name, ".", true);
+ const Descriptor* descriptor = message.GetDescriptor();
+ const FieldDescriptor* field = NULL;
+ for (int i = 0; i < field_path.size(); i++) {
+ field = descriptor->FindFieldByName(field_path[i]);
+ descriptor = field->message_type();
+ }
+ return field;
+}
+
+void ExpectEqualsWithDifferencer(util::MessageDifferencer* differencer,
+ const Message& msg1,
+ const Message& msg2) {
+ differencer->set_scope(util::MessageDifferencer::FULL);
+ EXPECT_TRUE(differencer->Compare(msg1, msg2));
+
+ differencer->set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer->Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicEqualityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicInequalityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.set_optional_int32(-1);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldInequalityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.add_repeated_int32(-1);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, MapFieldEqualityTest) {
+ // Create the testing protos
+ unittest::TestMap msg1;
+ unittest::TestMap msg2;
+
+ MapReflectionTester tester(unittest::TestMap::descriptor());
+ tester.SetMapFieldsViaReflection(&msg1);
+ tester.SetMapFieldsViaReflection(&msg2);
+ tester.SwapMapsViaReflection(&msg1);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicPartialEqualityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, PartialEqualityTestExtraField) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.clear_optional_int32();
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, PartialEqualityTestSkipRequiredField) {
+ // Create the testing protos
+ unittest::TestRequired msg1;
+ unittest::TestRequired msg2;
+
+ msg1.set_a(401);
+ msg2.set_a(401);
+ msg2.set_b(402);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicPartialInequalityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.set_optional_int32(-1);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, PartialInequalityMissingFieldTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg2.clear_optional_int32();
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldPartialInequalityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.add_repeated_int32(-1);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicEquivalencyTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::Equivalent(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, EquivalencyNotEqualTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.clear_optional_int32();
+ msg2.set_optional_int32(0);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+ EXPECT_TRUE(util::MessageDifferencer::Equivalent(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicInequivalencyTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.set_optional_int32(-1);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equivalent(msg1, msg2));
+}
+
+
+TEST(MessageDifferencerTest, BasicEquivalencyNonSetTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::Equivalent(msg1, msg2));
+}
+
+
+TEST(MessageDifferencerTest, BasicInequivalencyNonSetTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ msg1.set_optional_int32(-1);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equivalent(msg1, msg2));
+}
+
+
+TEST(MessageDifferencerTest, BasicPartialEquivalencyTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, PartialEquivalencyNotEqualTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.set_optional_int32(0);
+ msg2.clear_optional_int32();
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, PartialEquivalencyTestExtraField) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.clear_optional_int32();
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, PartialEquivalencyTestSkipRequiredField) {
+ // Create the testing protos
+ unittest::TestRequired msg1;
+ unittest::TestRequired msg2;
+
+ msg1.set_a(401);
+ msg2.set_a(401);
+ msg2.set_b(402);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicPartialInequivalencyTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ msg1.set_optional_int32(-1);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicPartialEquivalencyNonSetTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicPartialInequivalencyNonSetTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ msg1.set_optional_int32(-1);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, ApproximateEqualityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::ApproximatelyEquals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, ApproximateModifiedEqualityTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ const float v1 = 2.300005f;
+ const float v2 = 2.300006f;
+ msg1.set_optional_float(v1);
+ msg2.set_optional_float(v2);
+
+ // Compare
+ ASSERT_NE(v1, v2) << "Should not be the same: " << v1 << ", " << v2;
+ ASSERT_FLOAT_EQ(v1, v2) << "Should be approx. equal: " << v1 << ", " << v2;
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+ EXPECT_TRUE(util::MessageDifferencer::ApproximatelyEquals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, ApproximateEquivalencyTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::ApproximatelyEquivalent(msg1,
+ msg2));
+}
+
+TEST(MessageDifferencerTest, ApproximateModifiedEquivalencyTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Modify the approximateness requirement
+ const float v1 = 2.300005f;
+ const float v2 = 2.300006f;
+ msg1.set_optional_float(v1);
+ msg2.set_optional_float(v2);
+
+ // Compare
+ ASSERT_NE(v1, v2) << "Should not be the same: " << v1 << ", " << v2;
+ ASSERT_FLOAT_EQ(v1, v2) << "Should be approx. equal: " << v1 << ", " << v2;
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+ EXPECT_TRUE(util::MessageDifferencer::ApproximatelyEquivalent(msg1,
+ msg2));
+
+ // Modify the equivalency requirement too
+ msg1.clear_optional_int32();
+ msg2.set_optional_int32(0);
+
+ // Compare. Now should only pass on ApproximatelyEquivalent
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+ EXPECT_FALSE(util::MessageDifferencer::Equivalent(msg1, msg2));
+ EXPECT_FALSE(util::MessageDifferencer::ApproximatelyEquals(msg1, msg2));
+ EXPECT_TRUE(util::MessageDifferencer::ApproximatelyEquivalent(msg1,
+ msg2));
+}
+
+TEST(MessageDifferencerTest, ApproximateInequivalencyTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Should fail on equivalency
+ msg1.set_optional_int32(-1);
+ EXPECT_FALSE(util::MessageDifferencer::ApproximatelyEquivalent(msg1,
+ msg2));
+
+ // Make these fields the same again.
+ msg1.set_optional_int32(0);
+ msg2.set_optional_int32(0);
+ EXPECT_TRUE(util::MessageDifferencer::ApproximatelyEquivalent(msg1,
+ msg2));
+
+ // Should fail on approximate equality check
+ const float v1 = 2.3f;
+ const float v2 = 9.3f;
+ msg1.set_optional_float(v1);
+ msg2.set_optional_float(v2);
+ EXPECT_FALSE(util::MessageDifferencer::ApproximatelyEquivalent(msg1,
+ msg2));
+}
+
+TEST(MessageDifferencerTest, WithinFractionOrMarginFloatTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Should fail on approximate equality check
+ const float v1 = 100.0f;
+ const float v2 = 109.9f;
+ msg1.set_optional_float(v1);
+ msg2.set_optional_float(v2);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ const FieldDescriptor* fd =
+ msg1.GetDescriptor()->FindFieldByName("optional_float");
+
+ // Set float comparison to exact, margin and fraction value should not matter.
+ differencer.set_float_comparison(util::MessageDifferencer::EXACT);
+ // Set margin for float comparison.
+ differencer.SetFractionAndMargin(fd, 0.0, 10.0);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Margin and fraction float comparison is activated when float comparison is
+ // set to approximate.
+ differencer.set_float_comparison(util::MessageDifferencer::APPROXIMATE);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Test out float comparison with fraction.
+ differencer.SetFractionAndMargin(fd, 0.2, 0.0);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Should fail since the fraction is smaller than error.
+ differencer.SetFractionAndMargin(fd, 0.01, 0.0);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Should pass if either fraction or margin are satisfied.
+ differencer.SetFractionAndMargin(fd, 0.01, 10.0);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Make sure that the margin and fraction only affects the field that it was
+ // set for.
+ msg1.set_default_float(v1);
+ msg2.set_default_float(v2);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ msg1.set_default_float(v1);
+ msg2.set_default_float(v1);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, WithinFractionOrMarginDoubleTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Should fail on approximate equality check
+ const double v1 = 100.0;
+ const double v2 = 109.9;
+ msg1.set_optional_double(v1);
+ msg2.set_optional_double(v2);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Set comparison to exact, margin and fraction value should not matter.
+ differencer.set_float_comparison(util::MessageDifferencer::EXACT);
+ // Set margin for float comparison.
+ const FieldDescriptor* fd =
+ msg1.GetDescriptor()->FindFieldByName("optional_double");
+ differencer.SetFractionAndMargin(fd, 0.0, 10.0);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Margin and fraction comparison is activated when float comparison is
+ // set to approximate.
+ differencer.set_float_comparison(util::MessageDifferencer::APPROXIMATE);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Test out comparison with fraction.
+ differencer.SetFractionAndMargin(fd, 0.2, 0.0);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Should fail since the fraction is smaller than error.
+ differencer.SetFractionAndMargin(fd, 0.01, 0.0);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Should pass if either fraction or margin are satisfied.
+ differencer.SetFractionAndMargin(fd, 0.01, 10.0);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Make sure that the margin and fraction only affects the field that it was
+ // set for.
+ msg1.set_default_double(v1);
+ msg2.set_default_double(v2);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ msg1.set_default_double(v1);
+ msg2.set_default_double(v1);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, WithinDefaultFractionOrMarginDoubleTest) {
+ // Create the testing protos
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ // Should fail on approximate equality check
+ const double v1 = 100.0;
+ const double v2 = 109.9;
+ msg1.set_optional_double(v1);
+ msg2.set_optional_double(v2);
+
+ util::MessageDifferencer differencer;
+
+ // Compare
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Set up a custom field comparitor, with a default fraction and margin for
+ // float and double comparison.
+ util::DefaultFieldComparator field_comparitor;
+ field_comparitor.SetDefaultFractionAndMargin(0.0, 10.0);
+ differencer.set_field_comparator(&field_comparitor);
+
+ // Set comparison to exact, margin and fraction value should not matter.
+ field_comparitor.set_float_comparison(util::DefaultFieldComparator::EXACT);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Margin and fraction comparison is activated when float comparison is
+ // set to approximate.
+ field_comparitor.set_float_comparison(
+ util::DefaultFieldComparator::APPROXIMATE);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Test out comparison with fraction.
+ field_comparitor.SetDefaultFractionAndMargin(0.2, 0.0);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Should fail since the fraction is smaller than error.
+ field_comparitor.SetDefaultFractionAndMargin(0.01, 0.0);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Should pass if either fraction or margin are satisfied.
+ field_comparitor.SetDefaultFractionAndMargin(0.01, 10.0);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Make sure that the default margin and fraction affects all fields
+ msg1.set_default_double(v1);
+ msg2.set_default_double(v2);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicFieldOrderingsTest) {
+ // Create the testing protos
+ unittest::TestFieldOrderings msg1;
+ unittest::TestFieldOrderings msg2;
+
+ TestUtil::SetAllFieldsAndExtensions(&msg1);
+ TestUtil::SetAllFieldsAndExtensions(&msg2);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+
+TEST(MessageDifferencerTest, BasicFieldOrderingInequalityTest) {
+ // Create the testing protos
+ unittest::TestFieldOrderings msg1;
+ unittest::TestFieldOrderings msg2;
+
+ TestUtil::SetAllFieldsAndExtensions(&msg1);
+ TestUtil::SetAllFieldsAndExtensions(&msg2);
+
+ msg1.set_my_float(15.00);
+ msg2.set_my_float(16.00);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, BasicExtensionTest) {
+ // Create the testing protos
+ unittest::TestAllExtensions msg1;
+ unittest::TestAllExtensions msg2;
+
+ TestUtil::SetAllExtensions(&msg1);
+ TestUtil::SetAllExtensions(&msg2);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+
+TEST(MessageDifferencerTest, BasicExtensionInequalityTest) {
+ // Create the testing protos
+ unittest::TestAllExtensions msg1;
+ unittest::TestAllExtensions msg2;
+
+ TestUtil::SetAllExtensions(&msg1);
+ TestUtil::SetAllExtensions(&msg2);
+
+ msg1.SetExtension(unittest::optional_int32_extension, 101);
+ msg2.SetExtension(unittest::optional_int32_extension, 102);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, OneofTest) {
+ // Create the testing protos
+ unittest::TestOneof2 msg1;
+ unittest::TestOneof2 msg2;
+
+ TestUtil::SetOneof1(&msg1);
+ TestUtil::SetOneof1(&msg2);
+
+ // Compare
+ EXPECT_TRUE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, OneofInequalityTest) {
+ // Create the testing protos
+ unittest::TestOneof2 msg1;
+ unittest::TestOneof2 msg2;
+
+ TestUtil::SetOneof1(&msg1);
+ TestUtil::SetOneof2(&msg2);
+
+ // Compare
+ EXPECT_FALSE(util::MessageDifferencer::Equals(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, UnknownFieldPartialEqualTest) {
+ unittest::TestEmptyMessage empty1;
+ unittest::TestEmptyMessage empty2;
+
+ UnknownFieldSet* unknown1 = empty1.mutable_unknown_fields();
+ UnknownFieldSet* unknown2 = empty2.mutable_unknown_fields();
+
+ unknown1->AddVarint(243, 122);
+ unknown1->AddLengthDelimited(245, "abc");
+ unknown1->AddGroup(246)->AddFixed32(248, 1);
+ unknown1->mutable_field(2)->mutable_group()->AddFixed32(248, 2);
+
+ unknown2->AddVarint(243, 122);
+ unknown2->AddLengthDelimited(245, "abc");
+ unknown2->AddGroup(246)->AddFixed32(248, 1);
+ unknown2->mutable_field(2)->mutable_group()->AddFixed32(248, 2);
+
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(empty1, empty2));
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsEqualityAllTest) {
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ vector<const FieldDescriptor*> fields1;
+ vector<const FieldDescriptor*> fields2;
+ msg1.GetReflection()->ListFields(msg1, &fields1);
+ msg2.GetReflection()->ListFields(msg2, &fields2);
+
+ util::MessageDifferencer differencer;
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2, fields1, fields2));
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsInequalityAllTest) {
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+
+ vector<const FieldDescriptor*> fields1;
+ vector<const FieldDescriptor*> fields2;
+ msg1.GetReflection()->ListFields(msg1, &fields1);
+ msg2.GetReflection()->ListFields(msg2, &fields2);
+
+ util::MessageDifferencer differencer;
+ EXPECT_FALSE(differencer.CompareWithFields(msg1, msg2, fields1, fields2));
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsEmptyListAlwaysSucceeds) {
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+
+ vector<const FieldDescriptor*> empty_fields;
+
+ util::MessageDifferencer differencer;
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2,
+ empty_fields, empty_fields));
+
+ TestUtil::SetAllFields(&msg2);
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2,
+ empty_fields, empty_fields));
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsCompareWithSelf) {
+ unittest::TestAllTypes msg1;
+ TestUtil::SetAllFields(&msg1);
+
+ vector<const FieldDescriptor*> fields;
+ msg1.GetReflection()->ListFields(msg1, &fields);
+
+ util::MessageDifferencer differencer;
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg1, fields, fields));
+
+ {
+ // Compare with a subset of fields.
+ vector<const FieldDescriptor*> compare_fields;
+ for (int i = 0; i < fields.size(); ++i) {
+ if (i % 2 == 0) {
+ compare_fields.push_back(fields[i]);
+ }
+ }
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg1,
+ compare_fields, compare_fields));
+ }
+ {
+ // Specify a different set of fields to compare, even though we're using the
+ // same message. This should fail, since we are explicitly saying that the
+ // set of fields are different.
+ vector<const FieldDescriptor*> compare_fields1;
+ vector<const FieldDescriptor*> compare_fields2;
+ for (int i = 0; i < fields.size(); ++i) {
+ if (i % 2 == 0) {
+ compare_fields1.push_back(fields[i]);
+ } else {
+ compare_fields2.push_back(fields[i]);
+ }
+ }
+ EXPECT_FALSE(differencer.CompareWithFields(
+ msg1, msg1, compare_fields1, compare_fields2));
+ }
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsEqualityAllShuffledTest) {
+ // This is a public function, so make sure there are no assumptions about the
+ // list of fields. Randomly shuffle them to make sure that they are properly
+ // ordered for comparison.
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ vector<const FieldDescriptor*> fields1;
+ vector<const FieldDescriptor*> fields2;
+ msg1.GetReflection()->ListFields(msg1, &fields1);
+ msg2.GetReflection()->ListFields(msg2, &fields2);
+
+ std::random_shuffle(fields1.begin(), fields1.end());
+ std::random_shuffle(fields2.begin(), fields2.end());
+
+ util::MessageDifferencer differencer;
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2, fields1, fields2));
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsSubsetEqualityTest) {
+ // Specify a set of fields to compare. All the fields are equal.
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ vector<const FieldDescriptor*> fields1;
+ msg1.GetReflection()->ListFields(msg1, &fields1);
+
+ vector<const FieldDescriptor*> compare_fields;
+ // Only compare the field descriptors with even indices.
+ for (int i = 0; i < fields1.size(); ++i) {
+ if (i % 2 == 0) {
+ compare_fields.push_back(fields1[i]);
+ }
+ }
+
+ util::MessageDifferencer differencer;
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2,
+ compare_fields, compare_fields));
+}
+
+TEST(MessageDifferencerTest,
+ SpecifiedFieldsSubsetIgnoresOtherFieldDifferencesTest) {
+ // Specify a set of fields to compare, but clear all the other fields in one
+ // of the messages. This should fail a regular compare, but CompareWithFields
+ // should succeed.
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ vector<const FieldDescriptor*> fields1;
+ const Reflection* reflection = msg1.GetReflection();
+ reflection->ListFields(msg1, &fields1);
+
+ vector<const FieldDescriptor*> compare_fields;
+ // Only compare the field descriptors with even indices.
+ for (int i = 0; i < fields1.size(); ++i) {
+ if (i % 2 == 0) {
+ compare_fields.push_back(fields1[i]);
+ } else {
+ reflection->ClearField(&msg2, fields1[i]);
+ }
+ }
+
+ util::MessageDifferencer differencer;
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2,
+ compare_fields, compare_fields));
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsDetectsDifferencesTest) {
+ // Change all of the repeated fields in one of the messages, and use only
+ // those fields for comparison.
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+ TestUtil::ModifyRepeatedFields(&msg2);
+
+ vector<const FieldDescriptor*> fields1;
+ msg1.GetReflection()->ListFields(msg1, &fields1);
+
+ vector<const FieldDescriptor*> compare_fields;
+ // Only compare the repeated field descriptors.
+ for (int i = 0; i < fields1.size(); ++i) {
+ if (fields1[i]->is_repeated()) {
+ compare_fields.push_back(fields1[i]);
+ }
+ }
+
+ util::MessageDifferencer differencer;
+ EXPECT_FALSE(differencer.CompareWithFields(msg1, msg2,
+ compare_fields, compare_fields));
+}
+
+TEST(MessageDifferencerTest, SpecifiedFieldsEquivalenceAllTest) {
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+
+ TestUtil::SetAllFields(&msg1);
+ TestUtil::SetAllFields(&msg2);
+
+ vector<const FieldDescriptor*> fields1;
+ vector<const FieldDescriptor*> fields2;
+ msg1.GetReflection()->ListFields(msg1, &fields1);
+ msg2.GetReflection()->ListFields(msg2, &fields2);
+
+ util::MessageDifferencer differencer;
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2, fields1, fields2));
+}
+
+TEST(MessageDifferencerTest,
+ SpecifiedFieldsEquivalenceIgnoresOtherFieldDifferencesTest) {
+ unittest::TestAllTypes msg1;
+ unittest::TestAllTypes msg2;
+ const Descriptor* desc = msg1.GetDescriptor();
+
+ const FieldDescriptor* optional_int32_desc =
+ desc->FindFieldByName("optional_int32");
+ const FieldDescriptor* optional_int64_desc =
+ desc->FindFieldByName("optional_int64");
+ const FieldDescriptor* default_int64_desc =
+ desc->FindFieldByName("default_int64");
+ ASSERT_TRUE(optional_int32_desc != NULL);
+ ASSERT_TRUE(optional_int64_desc != NULL);
+ ASSERT_TRUE(default_int64_desc != NULL);
+ msg1.set_optional_int32(0);
+ msg2.set_optional_int64(0);
+ msg1.set_default_int64(default_int64_desc->default_value_int64());
+
+ // Set a field to a non-default value so we know that field selection is
+ // actually doing something.
+ msg2.set_optional_uint64(23);
+
+ vector<const FieldDescriptor*> fields1;
+ vector<const FieldDescriptor*> fields2;
+ fields1.push_back(optional_int32_desc);
+ fields1.push_back(default_int64_desc);
+
+ fields2.push_back(optional_int64_desc);
+
+ util::MessageDifferencer differencer;
+ EXPECT_FALSE(differencer.CompareWithFields(msg1, msg2, fields1, fields2));
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2, fields1, fields2));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldSetTest_SetOfSet) {
+ // Create the testing protos
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->add_ra(1); item->add_ra(2); item->add_ra(3);
+ item = msg1.add_item();
+ item->add_ra(5); item->add_ra(6);
+ item = msg1.add_item();
+ item->add_ra(1); item->add_ra(3);
+ item = msg1.add_item();
+ item->add_ra(6); item->add_ra(7); item->add_ra(8);
+
+ item = msg2.add_item();
+ item->add_ra(6); item->add_ra(5);
+ item = msg2.add_item();
+ item->add_ra(6); item->add_ra(8); item->add_ra(7);
+ item = msg2.add_item();
+ item->add_ra(1); item->add_ra(3);
+ item = msg2.add_item();
+ item->add_ra(3); item->add_ra(2); item->add_ra(1);
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.set_repeated_field_comparison(util::MessageDifferencer::AS_SET);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldSetTest_Combination) {
+ // Create the testing protos
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ // Treat "item" as Map, with key = "a"
+ // Treat "item.ra" also as Set
+ // Treat "rv" as Set
+ // Treat "rw" as List
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->set_a(3);
+ item->add_ra(1); item->add_ra(2); item->add_ra(3);
+ item = msg1.add_item();
+ item->set_a(4);
+ item->add_ra(5); item->add_ra(6);
+ item = msg1.add_item();
+ item->set_a(1);
+ item->add_ra(1); item->add_ra(3);
+ item = msg1.add_item();
+ item->set_a(2);
+ item->add_ra(6); item->add_ra(7); item->add_ra(8);
+
+ item = msg2.add_item();
+ item->set_a(4);
+ item->add_ra(6); item->add_ra(5);
+ item = msg2.add_item();
+ item->set_a(2);
+ item->add_ra(6); item->add_ra(8); item->add_ra(7);
+ item = msg2.add_item();
+ item->set_a(1);
+ item->add_ra(1); item->add_ra(3);
+ item = msg2.add_item();
+ item->set_a(3);
+ item->add_ra(3); item->add_ra(2); item->add_ra(1);
+
+ msg1.add_rv(3);
+ msg1.add_rv(4);
+ msg1.add_rv(7);
+ msg1.add_rv(0);
+ msg2.add_rv(4);
+ msg2.add_rv(3);
+ msg2.add_rv(0);
+ msg2.add_rv(7);
+
+ msg1.add_rw("nothing"); msg2.add_rw("nothing");
+ msg1.add_rw("should"); msg2.add_rw("should");
+ msg1.add_rw("change"); msg2.add_rw("change");
+
+ // Compare
+ util::MessageDifferencer differencer1;
+ differencer1.TreatAsMap(msg1.GetDescriptor()->FindFieldByName("item"),
+ item->GetDescriptor()->FindFieldByName("a"));
+ differencer1.TreatAsSet(msg1.GetDescriptor()->FindFieldByName("rv"));
+ differencer1.TreatAsSet(item->GetDescriptor()->FindFieldByName("ra"));
+ EXPECT_TRUE(differencer1.Compare(msg1, msg2));
+
+ util::MessageDifferencer differencer2;
+ differencer2.TreatAsMap(msg1.GetDescriptor()->FindFieldByName("item"),
+ item->GetDescriptor()->FindFieldByName("a"));
+ differencer2.set_repeated_field_comparison(util::MessageDifferencer::AS_SET);
+ differencer2.TreatAsList(msg1.GetDescriptor()->FindFieldByName("rw"));
+ EXPECT_TRUE(differencer2.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldMapTest_Partial) {
+ protobuf_unittest::TestDiffMessage msg1;
+ // message msg1 {
+ // item { a: 1; b: "11" }
+ // }
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->set_a(1);
+ item->set_b("11");
+
+ protobuf_unittest::TestDiffMessage msg2;
+ // message msg2 {
+ // item { a: 2; b: "22" }
+ // item { a: 1; b: "11" }
+ // }
+ item = msg2.add_item();
+ item->set_a(2);
+ item->set_b("22");
+ item = msg2.add_item();
+ item->set_a(1);
+ item->set_b("11");
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.TreatAsMap(GetFieldDescriptor(msg1, "item"),
+ GetFieldDescriptor(msg1, "item.a"));
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldSetTest_Duplicates) {
+ protobuf_unittest::TestDiffMessage a, b, c;
+ // message a: {
+ // rv: 0
+ // rv: 1
+ // rv: 0
+ // }
+ a.add_rv(0);
+ a.add_rv(1);
+ a.add_rv(0);
+ // message b: {
+ // rv: 0
+ // rv: 0
+ // rv: 1
+ // }
+ b.add_rv(0);
+ b.add_rv(0);
+ b.add_rv(1);
+ // message c: {
+ // rv: 0
+ // rv: 1
+ // }
+ c.add_rv(0);
+ c.add_rv(1);
+ util::MessageDifferencer differencer;
+ differencer.TreatAsSet(GetFieldDescriptor(a, "rv"));
+ EXPECT_TRUE(differencer.Compare(b, a));
+ EXPECT_FALSE(differencer.Compare(c, a));
+
+ util::MessageDifferencer differencer1;
+ differencer1.set_repeated_field_comparison(util::MessageDifferencer::AS_SET);
+ EXPECT_TRUE(differencer1.Compare(b, a));
+ EXPECT_FALSE(differencer1.Compare(c, a));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldSetTest_PartialSimple) {
+ protobuf_unittest::TestDiffMessage a, b, c;
+ // message a: {
+ // rm { c: 1 }
+ // rm { c: 0 }
+ // }
+ a.add_rm()->set_c(1);
+ a.add_rm()->set_c(0);
+ // message b: {
+ // rm { c: 1 }
+ // rm {}
+ // }
+ b.add_rm()->set_c(1);
+ b.add_rm();
+ // message c: {
+ // rm {}
+ // rm { c: 1 }
+ // }
+ c.add_rm();
+ c.add_rm()->set_c(1);
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ differencer.TreatAsSet(GetFieldDescriptor(a, "rm"));
+ EXPECT_TRUE(differencer.Compare(b, a));
+ EXPECT_TRUE(differencer.Compare(c, a));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldSetTest_Partial) {
+ protobuf_unittest::TestDiffMessage msg1, msg2;
+ // message msg1: {
+ // rm { a: 1 }
+ // rm { b: 2 }
+ // rm { c: 3 }
+ // }
+ msg1.add_rm()->set_a(1);
+ msg1.add_rm()->set_b(2);
+ msg1.add_rm()->set_c(3);
+ // message msg2: {
+ // rm { a: 1; c: 3 }
+ // rm { b: 2; c: 3 }
+ // rm { b: 2 }
+ // }
+ protobuf_unittest::TestField* field = msg2.add_rm();
+ field->set_a(1);
+ field->set_c(3);
+ field = msg2.add_rm();
+ field->set_b(2);
+ field->set_c(3);
+ field = msg2.add_rm();
+ field->set_b(2);
+
+ util::MessageDifferencer differencer;
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ differencer.TreatAsSet(GetFieldDescriptor(msg1, "rm"));
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldMapTest_MultipleFieldsAsKey) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ // Treat "item" as Map, with key = ("a", "ra")
+ // Treat "item.ra" as Set
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ // key => value: (1, {2, 3}) => "a"
+ item->set_a(1);
+ item->add_ra(2);
+ item->add_ra(3);
+ item->set_b("a");
+ item = msg1.add_item();
+ // key => value: (2, {1, 3}) => "b"
+ item->set_a(2);
+ item->add_ra(1);
+ item->add_ra(3);
+ item->set_b("b");
+ item = msg1.add_item();
+ // key => value: (1, {1, 3}) => "c"
+ item->set_a(1);
+ item->add_ra(1);
+ item->add_ra(3);
+ item->set_b("c");
+
+ item = msg2.add_item();
+ // key => value: (1, {1, 3}) => "c"
+ item->set_a(1);
+ item->add_ra(3);
+ item->add_ra(1);
+ item->set_b("c");
+ item = msg2.add_item();
+ // key => value: (1, {2, 3}) => "a"
+ item->set_a(1);
+ item->add_ra(3);
+ item->add_ra(2);
+ item->set_b("a");
+ item = msg2.add_item();
+ // key => value: (2, {1, 3}) => "b"
+ item->set_a(2);
+ item->add_ra(3);
+ item->add_ra(1);
+ item->set_b("b");
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.TreatAsSet(GetFieldDescriptor(msg1, "item.ra"));
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ vector<const FieldDescriptor*> key_fields;
+ key_fields.push_back(GetFieldDescriptor(msg1, "item.a"));
+ key_fields.push_back(GetFieldDescriptor(msg1, "item.ra"));
+ differencer.TreatAsMapWithMultipleFieldsAsKey(
+ GetFieldDescriptor(msg1, "item"), key_fields);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Introduce some differences.
+ msg1.clear_item();
+ msg2.clear_item();
+ item = msg1.add_item();
+ item->set_a(4);
+ item->add_ra(5);
+ item->add_ra(6);
+ item->set_b("hello");
+ item = msg2.add_item();
+ item->set_a(4);
+ item->add_ra(6);
+ item->add_ra(5);
+ item->set_b("world");
+ string output;
+ differencer.ReportDifferencesToString(&output);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "moved: item[0].ra[0] -> item[0].ra[1] : 5\n"
+ "moved: item[0].ra[1] -> item[0].ra[0] : 6\n"
+ "modified: item[0].b: \"hello\" -> \"world\"\n",
+ output);
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldMapTest_MultipleFieldPathsAsKey) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ // Treat "item" as Map, with key = ("m.a", "m.rc")
+ // Treat "item.m.rc" as Set
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ // key => value: (1, {2, 3}) => "a"
+ item->mutable_m()->set_a(1);
+ item->mutable_m()->add_rc(2);
+ item->mutable_m()->add_rc(3);
+ item->set_b("a");
+ item = msg1.add_item();
+ // key => value: (2, {1, 3}) => "b"
+ item->mutable_m()->set_a(2);
+ item->mutable_m()->add_rc(1);
+ item->mutable_m()->add_rc(3);
+ item->set_b("b");
+ item = msg1.add_item();
+ // key => value: (1, {1, 3}) => "c"
+ item->mutable_m()->set_a(1);
+ item->mutable_m()->add_rc(1);
+ item->mutable_m()->add_rc(3);
+ item->set_b("c");
+
+ item = msg2.add_item();
+ // key => value: (1, {1, 3}) => "c"
+ item->mutable_m()->set_a(1);
+ item->mutable_m()->add_rc(3);
+ item->mutable_m()->add_rc(1);
+ item->set_b("c");
+ item = msg2.add_item();
+ // key => value: (1, {2, 3}) => "a"
+ item->mutable_m()->set_a(1);
+ item->mutable_m()->add_rc(3);
+ item->mutable_m()->add_rc(2);
+ item->set_b("a");
+ item = msg2.add_item();
+ // key => value: (2, {1, 3}) => "b"
+ item->mutable_m()->set_a(2);
+ item->mutable_m()->add_rc(3);
+ item->mutable_m()->add_rc(1);
+ item->set_b("b");
+
+ // Compare
+ util::MessageDifferencer differencer;
+ differencer.TreatAsSet(GetFieldDescriptor(msg1, "item.m.rc"));
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ vector<vector<const FieldDescriptor*> > key_field_paths;
+ vector<const FieldDescriptor*> key_field_path1;
+ key_field_path1.push_back(GetFieldDescriptor(msg1, "item.m"));
+ key_field_path1.push_back(GetFieldDescriptor(msg1, "item.m.a"));
+ vector<const FieldDescriptor*> key_field_path2;
+ key_field_path2.push_back(GetFieldDescriptor(msg1, "item.m"));
+ key_field_path2.push_back(GetFieldDescriptor(msg1, "item.m.rc"));
+ key_field_paths.push_back(key_field_path1);
+ key_field_paths.push_back(key_field_path2);
+ differencer.TreatAsMapWithMultipleFieldPathsAsKey(
+ GetFieldDescriptor(msg1, "item"), key_field_paths);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+
+ // Introduce some differences.
+ msg1.clear_item();
+ msg2.clear_item();
+ item = msg1.add_item();
+ item->mutable_m()->set_a(4);
+ item->mutable_m()->add_rc(5);
+ item->mutable_m()->add_rc(6);
+ item->set_b("hello");
+ item = msg2.add_item();
+ item->mutable_m()->set_a(4);
+ item->mutable_m()->add_rc(6);
+ item->mutable_m()->add_rc(5);
+ item->set_b("world");
+ string output;
+ differencer.ReportDifferencesToString(&output);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "modified: item[0].b: \"hello\" -> \"world\"\n"
+ "moved: item[0].m.rc[0] -> item[0].m.rc[1] : 5\n"
+ "moved: item[0].m.rc[1] -> item[0].m.rc[0] : 6\n",
+ output);
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldMapTest_IgnoredKeyFields) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ // Treat "item" as Map, with key = ("a", "ra")
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->set_a(1);
+ item->add_ra(2);
+ item->set_b("hello");
+ item = msg2.add_item();
+ item->set_a(1);
+ item->add_ra(3);
+ item->set_b("world");
+ // Compare
+ util::MessageDifferencer differencer;
+ vector<const FieldDescriptor*> key_fields;
+ key_fields.push_back(GetFieldDescriptor(msg1, "item.a"));
+ key_fields.push_back(GetFieldDescriptor(msg1, "item.ra"));
+ differencer.TreatAsMapWithMultipleFieldsAsKey(
+ GetFieldDescriptor(msg1, "item"), key_fields);
+ string output;
+ differencer.ReportDifferencesToString(&output);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "added: item[0]: { a: 1 ra: 3 b: \"world\" }\n"
+ "deleted: item[0]: { a: 1 ra: 2 b: \"hello\" }\n",
+ output);
+ // Ignored fields that are listed as parts of the key are still used
+ // in key comparison, but they're not used in value comparison.
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "item.ra"));
+ output.clear();
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "added: item[0]: { a: 1 ra: 3 b: \"world\" }\n"
+ "deleted: item[0]: { a: 1 ra: 2 b: \"hello\" }\n",
+ output);
+ // Ignoring a field in the key is different from treating the left fields
+ // as key. That is:
+ // (key = ("a", "ra") && ignore "ra") != (key = ("a") && ignore "ra")
+ util::MessageDifferencer differencer2;
+ differencer2.TreatAsMap(GetFieldDescriptor(msg1, "item"),
+ GetFieldDescriptor(msg1, "item.a"));
+ differencer2.IgnoreField(GetFieldDescriptor(msg1, "item.ra"));
+ output.clear();
+ differencer2.ReportDifferencesToString(&output);
+ EXPECT_FALSE(differencer2.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "ignored: item[0].ra\n"
+ "modified: item[0].b: \"hello\" -> \"world\"\n",
+ output);
+}
+
+static const char* const kIgnoredFields[] = {"rm.b", "rm.m.b"};
+
+class TestIgnorer : public util::MessageDifferencer::IgnoreCriteria {
+ public:
+ virtual bool IsIgnored(
+ const Message& message1, const Message& message2,
+ const FieldDescriptor* field,
+ const vector<util::MessageDifferencer::SpecificField>& parent_fields) {
+ string name = "";
+ for (int i = 0; i < parent_fields.size(); ++i) {
+ name += parent_fields[i].field->name() + ".";
+ }
+ name += field->name();
+ for (int i = 0; i < GOOGLE_ARRAYSIZE(kIgnoredFields); ++i) {
+ if (name.compare(kIgnoredFields[i]) == 0) {
+ return true;
+ }
+ }
+ return false;
+ }
+};
+
+TEST(MessageDifferencerTest, TreatRepeatedFieldAsSetWithIgnoredFields) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ TextFormat::MergeFromString("rm { a: 11\n b: 12 }", &msg1);
+ TextFormat::MergeFromString("rm { a: 11\n b: 13 }", &msg2);
+ util::MessageDifferencer differ;
+ differ.TreatAsSet(GetFieldDescriptor(msg1, "rm"));
+ differ.AddIgnoreCriteria(new TestIgnorer);
+ EXPECT_TRUE(differ.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, TreatRepeatedFieldAsMapWithIgnoredKeyFields) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ TextFormat::MergeFromString("rm { a: 11\n m { a: 12\n b: 13\n } }", &msg1);
+ TextFormat::MergeFromString("rm { a: 11\n m { a: 12\n b: 14\n } }", &msg2);
+ util::MessageDifferencer differ;
+ differ.TreatAsMap(GetFieldDescriptor(msg1, "rm"),
+ GetFieldDescriptor(msg1, "rm.m"));
+ differ.AddIgnoreCriteria(new TestIgnorer);
+ EXPECT_TRUE(differ.Compare(msg1, msg2));
+}
+
+// Takes the product of all elements of item.ra as the key for key comparison.
+class ValueProductMapKeyComparator
+ : public util::MessageDifferencer::MapKeyComparator {
+ public:
+ typedef util::MessageDifferencer::SpecificField SpecificField;
+ virtual bool IsMatch(
+ const Message &message1, const Message &message2,
+ const vector<SpecificField>& parent_fields) const {
+ const Reflection* reflection1 = message1.GetReflection();
+ const Reflection* reflection2 = message2.GetReflection();
+ // FieldDescriptor for item.ra
+ const FieldDescriptor* ra_field =
+ message1.GetDescriptor()->FindFieldByName("ra");
+ // Get the product of all elements in item.ra
+ int result1 = 1, result2 = 1;
+ for (int i = 0; i < reflection1->FieldSize(message1, ra_field); ++i) {
+ result1 *= reflection1->GetRepeatedInt32(message1, ra_field, i);
+ }
+ for (int i = 0; i < reflection2->FieldSize(message2, ra_field); ++i) {
+ result2 *= reflection2->GetRepeatedInt32(message2, ra_field, i);
+ }
+ return result1 == result2;
+ }
+};
+
+TEST(MessageDifferencerTest, RepeatedFieldMapTest_CustomMapKeyComparator) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ // Treat "item" as Map, using custom key comparator to determine if two
+ // elements have the same key.
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->add_ra(6);
+ item->add_ra(35);
+ item->set_b("hello");
+ item = msg2.add_item();
+ item->add_ra(10);
+ item->add_ra(21);
+ item->set_b("hello");
+ util::MessageDifferencer differencer;
+ ValueProductMapKeyComparator key_comparator;
+ differencer.TreatAsMapUsingKeyComparator(
+ GetFieldDescriptor(msg1, "item"), &key_comparator);
+ string output;
+ differencer.ReportDifferencesToString(&output);
+ // Though the above two messages have different values for item.ra, they
+ // are regarded as having the same key because 6 * 35 == 10 * 21. That's
+ // how the key comparator determines if the two have the same key.
+ // However, in value comparison, all fields of the message are taken into
+ // consideration, so they are different because their item.ra fields have
+ // different values using normal value comparison.
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "modified: item[0].ra[0]: 6 -> 10\n"
+ "modified: item[0].ra[1]: 35 -> 21\n",
+ output);
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "item.ra"));
+ output.clear();
+ // item.ra is ignored in value comparison, so the two messages equal.
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ("ignored: item[0].ra\n", output);
+}
+
+TEST(MessageDifferencerTest, RepeatedFieldSetTest_Subset) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ msg1.add_rv(3);
+ msg1.add_rv(8);
+ msg1.add_rv(2);
+ msg2.add_rv(2);
+ msg2.add_rv(3);
+ msg2.add_rv(5);
+ msg2.add_rv(8);
+
+ util::MessageDifferencer differencer;
+
+ // Fail with only partial scope set.
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ differencer.set_repeated_field_comparison(util::MessageDifferencer::AS_LIST);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Fail with only set-like comparison set.
+ differencer.set_scope(util::MessageDifferencer::FULL);
+ differencer.set_repeated_field_comparison(util::MessageDifferencer::AS_SET);
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ // Succeed with scope and repeated field comparison set properly.
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ differencer.set_repeated_field_comparison(util::MessageDifferencer::AS_SET);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, IgnoreField_Single) {
+ protobuf_unittest::TestField msg1;
+ protobuf_unittest::TestField msg2;
+
+ msg1.set_c(3);
+ msg1.add_rc(1);
+
+ msg2.set_c(5);
+ msg2.add_rc(1);
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "c"));
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_Repeated) {
+ protobuf_unittest::TestField msg1;
+ protobuf_unittest::TestField msg2;
+
+ msg1.set_c(3);
+ msg1.add_rc(1);
+ msg1.add_rc(2);
+
+ msg2.set_c(3);
+ msg2.add_rc(1);
+ msg2.add_rc(3);
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "rc"));
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_Message) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestField* field;
+
+ field = msg1.add_rm();
+ field->set_c(3);
+
+ field = msg2.add_rm();
+ field->set_c(4);
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "rm"));
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_Group) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestDiffMessage::Item* item;
+
+ item = msg1.add_item();
+ item->set_a(3);
+
+ item = msg2.add_item();
+ item->set_a(4);
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "item"));
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_Missing) {
+ protobuf_unittest::TestField msg1;
+ protobuf_unittest::TestField msg2;
+
+ msg1.set_c(3);
+ msg1.add_rc(1);
+
+ msg2.add_rc(1);
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "c"));
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+ ExpectEqualsWithDifferencer(&differencer, msg2, msg1);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_Multiple) {
+ protobuf_unittest::TestField msg1;
+ protobuf_unittest::TestField msg2;
+
+ msg1.set_c(3);
+ msg1.add_rc(1);
+ msg1.add_rc(2);
+
+ msg2.set_c(5);
+ msg2.add_rc(1);
+ msg2.add_rc(3);
+
+ const FieldDescriptor* c = GetFieldDescriptor(msg1, "c");
+ const FieldDescriptor* rc = GetFieldDescriptor(msg1, "rc");
+
+ { // Ignore c
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(c);
+
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ }
+ { // Ignore rc
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(rc);
+
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+ }
+ { // Ignore both
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(c);
+ differencer.IgnoreField(rc);
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+ }
+}
+
+TEST(MessageDifferencerTest, IgnoreField_NestedMessage) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestField* field;
+
+ field = msg1.add_rm();
+ field->set_c(3);
+ field->add_rc(1);
+
+ field = msg2.add_rm();
+ field->set_c(4);
+ field->add_rc(1);
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "rm.c"));
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_NestedGroup) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestDiffMessage::Item* item;
+
+ item = msg1.add_item();
+ item->set_a(3);
+ item->set_b("foo");
+
+ item = msg2.add_item();
+ item->set_a(4);
+ item->set_b("foo");
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(GetFieldDescriptor(msg1, "item.a"));
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_InsideSet) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestDiffMessage::Item* item;
+
+ item = msg1.add_item();
+ item->set_a(1);
+ item->set_b("foo");
+ item->add_ra(1);
+
+ item = msg1.add_item();
+ item->set_a(2);
+ item->set_b("bar");
+ item->add_ra(2);
+
+ item = msg2.add_item();
+ item->set_a(2);
+ item->set_b("bar");
+ item->add_ra(2);
+
+ item = msg2.add_item();
+ item->set_a(1);
+ item->set_b("baz");
+ item->add_ra(1);
+
+ const FieldDescriptor* item_desc = GetFieldDescriptor(msg1, "item");
+ const FieldDescriptor* b = GetFieldDescriptor(msg1, "item.b");
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(b);
+ differencer.TreatAsSet(item_desc);
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_InsideMap) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestDiffMessage::Item* item;
+
+ item = msg1.add_item();
+ item->set_a(1);
+ item->set_b("foo");
+ item->add_ra(1);
+
+ item = msg1.add_item();
+ item->set_a(2);
+ item->set_b("bar");
+ item->add_ra(2);
+
+ item = msg2.add_item();
+ item->set_a(2);
+ item->set_b("bar");
+ item->add_ra(2);
+
+ item = msg2.add_item();
+ item->set_a(1);
+ item->set_b("baz");
+ item->add_ra(1);
+
+ const FieldDescriptor* item_desc = GetFieldDescriptor(msg1, "item");
+ const FieldDescriptor* a = GetFieldDescriptor(msg1, "item.a");
+ const FieldDescriptor* b = GetFieldDescriptor(msg1, "item.b");
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(b);
+ differencer.TreatAsMap(item_desc, a);
+
+ ExpectEqualsWithDifferencer(&differencer, msg1, msg2);
+}
+
+TEST(MessageDifferencerTest, IgnoreField_DoesNotIgnoreKey) {
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestDiffMessage::Item* item;
+
+ item = msg1.add_item();
+ item->set_a(1);
+ item->set_b("foo");
+ item->add_ra(1);
+
+ item = msg2.add_item();
+ item->set_a(2);
+ item->set_b("foo");
+ item->add_ra(1);
+
+ const FieldDescriptor* item_desc = GetFieldDescriptor(msg1, "item");
+ const FieldDescriptor* a = GetFieldDescriptor(msg1, "item.a");
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(a);
+ differencer.TreatAsMap(item_desc, a);
+
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+}
+
+TEST(MessageDifferencerTest, IgnoreField_TrumpsCompareWithFields) {
+ protobuf_unittest::TestField msg1;
+ protobuf_unittest::TestField msg2;
+
+ msg1.set_c(3);
+ msg1.add_rc(1);
+ msg1.add_rc(2);
+
+ msg2.set_c(3);
+ msg2.add_rc(1);
+ msg2.add_rc(3);
+
+ const FieldDescriptor* c = GetFieldDescriptor(msg1, "c");
+ const FieldDescriptor* rc = GetFieldDescriptor(msg1, "rc");
+
+ vector<const FieldDescriptor*> fields;
+ fields.push_back(c);
+ fields.push_back(rc);
+
+ util::MessageDifferencer differencer;
+ differencer.IgnoreField(rc);
+
+ differencer.set_scope(util::MessageDifferencer::FULL);
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2, fields, fields));
+
+ differencer.set_scope(util::MessageDifferencer::PARTIAL);
+ EXPECT_TRUE(differencer.CompareWithFields(msg1, msg2, fields, fields));
+}
+
+
+// Test class to save a copy of the last field_context.parent_fields() vector
+// passed to the comparison function.
+class ParentSavingFieldComparator : public util::FieldComparator {
+ public:
+ ParentSavingFieldComparator() {}
+
+ virtual ComparisonResult Compare(
+ const google::protobuf::Message& message_1,
+ const google::protobuf::Message& message_2,
+ const google::protobuf::FieldDescriptor* field,
+ int index_1, int index_2,
+ const google::protobuf::util::FieldContext* field_context) {
+ if (field_context)
+ parent_fields_ = *(field_context->parent_fields());
+ if (field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE) {
+ return RECURSE;
+ } else {
+ return SAME;
+ }
+ }
+
+ vector<google::protobuf::util::MessageDifferencer::SpecificField> parent_fields() {
+ return parent_fields_;
+ }
+
+ private:
+ vector<google::protobuf::util::MessageDifferencer::SpecificField> parent_fields_;
+};
+
+// Tests if MessageDifferencer sends the parent fields in the FieldContext
+// parameter.
+TEST(MessageDifferencerTest, FieldContextParentFieldsTest) {
+ protobuf_unittest::TestDiffMessage msg1;
+ msg1.add_rm()->set_c(1);
+ protobuf_unittest::TestDiffMessage msg2;
+ msg2.add_rm()->set_c(1);
+
+ ParentSavingFieldComparator field_comparator;
+ util::MessageDifferencer differencer;
+ differencer.set_field_comparator(&field_comparator);
+ differencer.Compare(msg1, msg2);
+
+ // We want only one parent with the name "rm"
+ ASSERT_EQ(1, field_comparator.parent_fields().size());
+ EXPECT_EQ("rm", field_comparator.parent_fields()[0].field->name());
+}
+
+
+class ComparisonTest : public testing::Test {
+ protected:
+ ComparisonTest() : use_equivalency_(false), repeated_field_as_set_(false) {
+ // Setup the test.
+ TestUtil::SetAllFields(&proto1_);
+ TestUtil::SetAllFields(&proto2_);
+
+ TestUtil::SetAllExtensions(&proto1ex_);
+ TestUtil::SetAllExtensions(&proto2ex_);
+
+ TestUtil::SetAllFieldsAndExtensions(&orderings_proto1_);
+ TestUtil::SetAllFieldsAndExtensions(&orderings_proto2_);
+
+ unknown1_ = empty1_.mutable_unknown_fields();
+ unknown2_ = empty2_.mutable_unknown_fields();
+ }
+
+ ~ComparisonTest() { }
+
+ void SetSpecialFieldOption(const Message& message,
+ util::MessageDifferencer* d) {
+ if (!ignored_field_.empty()) {
+ d->IgnoreField(GetFieldDescriptor(message, ignored_field_));
+ }
+
+ if (repeated_field_as_set_) {
+ d->set_repeated_field_comparison(util::MessageDifferencer::AS_SET);
+ }
+
+ if (!set_field_.empty()) {
+ d->TreatAsSet(GetFieldDescriptor(message, set_field_));
+ }
+
+ if (!map_field_.empty() && !map_key_.empty()) {
+ d->TreatAsMap(GetFieldDescriptor(message, map_field_),
+ GetFieldDescriptor(message, map_field_ + "." + map_key_));
+ }
+ }
+
+ string Run(const Message& msg1, const Message& msg2) {
+ string output;
+
+ // Setup the comparison.
+ util::MessageDifferencer differencer;
+ differencer.ReportDifferencesToString(&output);
+
+ if (use_equivalency_) {
+ differencer.set_message_field_comparison(
+ util::MessageDifferencer::EQUIVALENT);
+ }
+
+ SetSpecialFieldOption(msg1, &differencer);
+
+ // Conduct the comparison.
+ EXPECT_FALSE(differencer.Compare(msg1, msg2));
+
+ return output;
+ }
+
+ string Run() {
+ return Run(proto1_, proto2_);
+ }
+
+ string RunOrder() {
+ return Run(orderings_proto1_, orderings_proto2_);
+ }
+
+ string RunEx() {
+ return Run(proto1ex_, proto2ex_);
+ }
+
+ string RunDiff() {
+ return Run(proto1diff_, proto2diff_);
+ }
+
+ string RunUn() {
+ return Run(empty1_, empty2_);
+ }
+
+ void use_equivalency() {
+ use_equivalency_ = true;
+ }
+
+ void repeated_field_as_set() {
+ repeated_field_as_set_ = true;
+ }
+
+ void field_as_set(const string& field) {
+ set_field_ = field;
+ }
+
+ void field_as_map(const string& field, const string& key) {
+ map_field_ = field;
+ map_key_ = key;
+ }
+
+ void ignore_field(const string& field) {
+ ignored_field_ = field;
+ }
+
+ unittest::TestAllTypes proto1_;
+ unittest::TestAllTypes proto2_;
+
+ unittest::TestFieldOrderings orderings_proto1_;
+ unittest::TestFieldOrderings orderings_proto2_;
+
+ unittest::TestAllExtensions proto1ex_;
+ unittest::TestAllExtensions proto2ex_;
+
+ unittest::TestDiffMessage proto1diff_;
+ unittest::TestDiffMessage proto2diff_;
+
+ unittest::TestEmptyMessage empty1_;
+ unittest::TestEmptyMessage empty2_;
+
+ UnknownFieldSet* unknown1_;
+ UnknownFieldSet* unknown2_;
+
+ bool use_equivalency_;
+ bool repeated_field_as_set_;
+
+ string set_field_;
+ string map_field_;
+ string map_key_;
+ string ignored_field_;
+};
+
+// Basic tests.
+TEST_F(ComparisonTest, AdditionTest) {
+ proto1_.clear_optional_int32();
+
+ EXPECT_EQ("added: optional_int32: 101\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, Addition_OrderTest) {
+ orderings_proto1_.clear_my_int();
+
+ EXPECT_EQ("added: my_int: 1\n",
+ RunOrder());
+}
+
+TEST_F(ComparisonTest, DeletionTest) {
+ proto2_.clear_optional_int32();
+
+ EXPECT_EQ("deleted: optional_int32: 101\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, Deletion_OrderTest) {
+ orderings_proto2_.clear_my_string();
+
+ EXPECT_EQ("deleted: my_string: \"foo\"\n",
+ RunOrder());
+}
+
+TEST_F(ComparisonTest, RepeatedDeletionTest) {
+ proto2_.clear_repeated_int32();
+
+ EXPECT_EQ("deleted: repeated_int32[0]: 201\n"
+ "deleted: repeated_int32[1]: 301\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, ModificationTest) {
+ proto1_.set_optional_int32(-1);
+
+ EXPECT_EQ("modified: optional_int32: -1 -> 101\n",
+ Run());
+}
+
+// Basic equivalency tests.
+TEST_F(ComparisonTest, EquivalencyAdditionTest) {
+ use_equivalency();
+
+ proto1_.clear_optional_int32();
+
+ EXPECT_EQ("modified: optional_int32: 0 -> 101\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, EquivalencyDeletionTest) {
+ use_equivalency();
+
+ proto2_.clear_optional_int32();
+
+ EXPECT_EQ("modified: optional_int32: 101 -> 0\n",
+ Run());
+}
+
+// Group tests.
+TEST_F(ComparisonTest, GroupAdditionTest) {
+ proto1_.mutable_optionalgroup()->clear_a();
+
+ EXPECT_EQ("added: optionalgroup.a: 117\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, GroupDeletionTest) {
+ proto2_.mutable_optionalgroup()->clear_a();
+
+ EXPECT_EQ("deleted: optionalgroup.a: 117\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, GroupModificationTest) {
+ proto1_.mutable_optionalgroup()->set_a(2);
+
+ EXPECT_EQ("modified: optionalgroup.a: 2 -> 117\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, GroupFullAdditionTest) {
+ proto1_.clear_optionalgroup();
+
+ // Note the difference in the output between this and GroupAdditionTest.
+ EXPECT_EQ("added: optionalgroup: { a: 117 }\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, GroupFullDeletionTest) {
+ proto2_.clear_optionalgroup();
+
+ EXPECT_EQ("deleted: optionalgroup: { a: 117 }\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, RepeatedSetOptionTest) {
+ repeated_field_as_set();
+
+ proto2_.clear_repeatedgroup();
+ proto1_.clear_repeatedgroup();
+ proto1_.add_repeatedgroup()->set_a(317);
+ proto2_.add_repeatedgroup()->set_a(909);
+ proto2_.add_repeatedgroup()->set_a(907);
+ proto1_.add_repeatedgroup()->set_a(904);
+ proto1_.add_repeatedgroup()->set_a(907);
+ proto1_.add_repeatedgroup()->set_a(909);
+
+ EXPECT_EQ("moved: repeatedgroup[2] -> repeatedgroup[1] : { a: 907 }\n"
+ "moved: repeatedgroup[3] -> repeatedgroup[0] : { a: 909 }\n"
+ "deleted: repeatedgroup[0]: { a: 317 }\n"
+ "deleted: repeatedgroup[1]: { a: 904 }\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, RepeatedSetOptionTest_Ex) {
+ repeated_field_as_set();
+
+ proto1ex_.ClearExtension(protobuf_unittest::repeated_nested_message_extension);
+ proto2ex_.ClearExtension(protobuf_unittest::repeated_nested_message_extension);
+ proto2ex_.AddExtension(protobuf_unittest::repeated_nested_message_extension)
+ ->set_bb(909);
+ proto2ex_.AddExtension(protobuf_unittest::repeated_nested_message_extension)
+ ->set_bb(907);
+ proto1ex_.AddExtension(protobuf_unittest::repeated_nested_message_extension)
+ ->set_bb(904);
+ proto1ex_.AddExtension(protobuf_unittest::repeated_nested_message_extension)
+ ->set_bb(907);
+ proto1ex_.AddExtension(protobuf_unittest::repeated_nested_message_extension)
+ ->set_bb(909);
+
+ EXPECT_EQ("moved: (protobuf_unittest.repeated_nested_message_extension)[2] ->"
+ " (protobuf_unittest.repeated_nested_message_extension)[0] :"
+ " { bb: 909 }\n"
+ "deleted: (protobuf_unittest.repeated_nested_message_extension)[0]:"
+ " { bb: 904 }\n",
+ RunEx());
+}
+
+TEST_F(ComparisonTest, RepeatedMapFieldTest_Group) {
+ field_as_map("repeatedgroup", "a");
+ proto1_.clear_repeatedgroup();
+ proto2_.clear_repeatedgroup();
+
+ proto1_.add_repeatedgroup()->set_a(317); // deleted
+ proto1_.add_repeatedgroup()->set_a(904); // deleted
+ proto1_.add_repeatedgroup()->set_a(907); // moved from
+ proto1_.add_repeatedgroup()->set_a(909); // moved from
+
+ proto2_.add_repeatedgroup()->set_a(909); // moved to
+ proto2_.add_repeatedgroup()->set_a(318); // added
+ proto2_.add_repeatedgroup()->set_a(907); // moved to
+
+ EXPECT_EQ("moved: repeatedgroup[3] -> repeatedgroup[0] : { a: 909 }\n"
+ "added: repeatedgroup[1]: { a: 318 }\n"
+ "deleted: repeatedgroup[0]: { a: 317 }\n"
+ "deleted: repeatedgroup[1]: { a: 904 }\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, RepeatedMapFieldTest_MessageKey) {
+ // Use m as key, but use b as value.
+ field_as_map("item", "m");
+
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+
+ // The following code creates one deletion, one addition and two moved fields
+ // on the messages.
+ item->mutable_m()->set_c(0);
+ item->set_b("first");
+ item = msg1.add_item();
+ item->mutable_m()->set_c(2);
+ item->set_b("second");
+ item = msg1.add_item(); item->set_b("null"); // empty key moved
+ item = msg1.add_item();
+ item->mutable_m()->set_c(3);
+ item->set_b("third"); // deletion
+ item = msg1.add_item();
+ item->mutable_m()->set_c(2);
+ item->set_b("second"); // duplicated key ( deletion )
+ item = msg2.add_item();
+ item->mutable_m()->set_c(2);
+ item->set_b("second"); // modification
+ item = msg2.add_item();
+ item->mutable_m()->set_c(4);
+ item->set_b("fourth"); // addition
+ item = msg2.add_item();
+ item->mutable_m()->set_c(0);
+ item->set_b("fist"); // move with change
+ item = msg2.add_item(); item->set_b("null");
+
+ EXPECT_EQ(
+ "modified: item[0].b -> item[2].b: \"first\" -> \"fist\"\n"
+ "moved: item[1] -> item[0] : { b: \"second\" m { c: 2 } }\n"
+ "moved: item[2] -> item[3] : { b: \"null\" }\n"
+ "added: item[1]: { b: \"fourth\" m { c: 4 } }\n"
+ "deleted: item[3]: { b: \"third\" m { c: 3 } }\n"
+ "deleted: item[4]: { b: \"second\" m { c: 2 } }\n",
+ Run(msg1, msg2));
+}
+
+TEST_F(ComparisonTest, RepeatedFieldSetTest_SetOfSet) {
+ repeated_field_as_set();
+ // Create the testing protos
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->add_ra(1); item->add_ra(2); item->add_ra(3);
+ item = msg1.add_item();
+ item->add_ra(5); item->add_ra(6);
+ item = msg1.add_item();
+ item->add_ra(1); item->add_ra(3);
+ item = msg1.add_item();
+ item->add_ra(6); item->add_ra(7); item->add_ra(8);
+
+ item = msg2.add_item();
+ item->add_ra(6); item->add_ra(5);
+ item = msg2.add_item();
+ item->add_ra(6); item->add_ra(8);
+ item = msg2.add_item();
+ item->add_ra(1); item->add_ra(3);
+ item = msg2.add_item();
+ item->add_ra(3); item->add_ra(2); item->add_ra(1);
+
+ // Compare
+ EXPECT_EQ("moved: item[0].ra[0] -> item[3].ra[2] : 1\n"
+ "moved: item[0].ra[2] -> item[3].ra[0] : 3\n"
+ "moved: item[0] -> item[3] : { ra: 1 ra: 2 ra: 3 }\n"
+ "moved: item[1].ra[0] -> item[0].ra[1] : 5\n"
+ "moved: item[1].ra[1] -> item[0].ra[0] : 6\n"
+ "moved: item[1] -> item[0] : { ra: 5 ra: 6 }\n"
+ "added: item[1]: { ra: 6 ra: 8 }\n"
+ "deleted: item[3]: { ra: 6 ra: 7 ra: 8 }\n",
+ Run(msg1, msg2));
+}
+
+TEST_F(ComparisonTest, RepeatedMapFieldTest_RepeatedKey) {
+ // used rb as a key, but b is the value.
+ repeated_field_as_set();
+ field_as_map("item", "rb");
+
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->add_rb("a");
+ item->add_rb("b");
+ item->set_b("first");
+
+ item = msg2.add_item();
+ item->add_rb("c");
+ item->set_b("second");
+
+ item = msg2.add_item();
+ item->add_rb("b");
+ item->add_rb("a");
+ item->set_b("fist");
+
+
+ EXPECT_EQ("modified: item[0].b -> item[1].b: \"first\" -> \"fist\"\n"
+ "moved: item[0].rb[0] -> item[1].rb[1] : \"a\"\n"
+ "moved: item[0].rb[1] -> item[1].rb[0] : \"b\"\n"
+ "added: item[0]: { b: \"second\" rb: \"c\" }\n",
+ Run(msg1, msg2));
+}
+
+TEST_F(ComparisonTest, RepeatedMapFieldTest_RepeatedMessageKey) {
+ field_as_map("item", "rm");
+
+ protobuf_unittest::TestDiffMessage msg1;
+ protobuf_unittest::TestDiffMessage msg2;
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ protobuf_unittest::TestField* key = item->add_rm();
+ key->set_c(2); key->add_rc(10); key->add_rc(10);
+ item = msg1.add_item(); key = item->add_rm();
+ key->set_c(0); key->add_rc(1); key->add_rc(2);
+ key = item->add_rm();
+ key->set_c(0);
+ item->add_rb("first");
+
+ item = msg2.add_item();
+ item->CopyFrom(msg1.item(1));
+ item->add_rb("second");
+
+ EXPECT_EQ("added: item[0].rb[1]: \"second\"\n"
+ "deleted: item[0]: { rm { c: 2 rc: 10 rc: 10 } }\n",
+ Run(msg1, msg2));
+}
+
+TEST_F(ComparisonTest, RepeatedSetOptionTest_Unknown) {
+ // Currently, as_set option doesn't have affects on unknown field.
+ // If needed, this feature will be added by request.
+ repeated_field_as_set();
+ unknown1_->AddGroup(245)->AddFixed32(248, 1);
+ unknown2_->AddGroup(245)->AddFixed32(248, 3);
+ unknown2_->AddGroup(245)->AddFixed32(248, 1);
+
+ // We expect it behaves the same as normal comparison.
+ EXPECT_EQ("modified: 245[0].248[0]: 0x00000001 -> 0x00000003\n"
+ "added: 245[1]: { ... }\n",
+ RunUn());
+}
+
+TEST_F(ComparisonTest, Matching_Unknown) {
+ unknown1_->AddGroup(245)->AddFixed32(248, 1);
+ unknown2_->AddGroup(245)->AddFixed32(248, 1);
+ unknown1_->AddGroup(245)->AddFixed32(248, 3);
+ unknown2_->AddGroup(245)->AddFixed32(248, 3);
+ unknown2_->AddLengthDelimited(242, "cat");
+ unknown2_->AddGroup(246)->AddFixed32(248, 4);
+
+ // report_match is false so only added/modified fields are expected.
+ EXPECT_EQ("added: 242[0]: \"cat\"\n"
+ "added: 246[0]: { ... }\n",
+ RunUn());
+}
+
+TEST_F(ComparisonTest, RepeatedSetFieldTest) {
+ field_as_set("repeatedgroup");
+
+ proto1_.clear_repeatedgroup();
+ proto2_.clear_repeatedgroup();
+ proto2_.add_repeatedgroup()->set_a(909);
+ proto2_.add_repeatedgroup()->set_a(907);
+ proto1_.add_repeatedgroup()->set_a(317);
+ proto1_.add_repeatedgroup()->set_a(904);
+ proto1_.add_repeatedgroup()->set_a(907);
+ proto1_.add_repeatedgroup()->set_a(909);
+
+ EXPECT_EQ("moved: repeatedgroup[2] -> repeatedgroup[1] : { a: 907 }\n"
+ "moved: repeatedgroup[3] -> repeatedgroup[0] : { a: 909 }\n"
+ "deleted: repeatedgroup[0]: { a: 317 }\n"
+ "deleted: repeatedgroup[1]: { a: 904 }\n",
+ Run());
+}
+
+// Embedded message tests.
+TEST_F(ComparisonTest, EmbeddedAdditionTest) {
+ proto1_.mutable_optional_nested_message()->clear_bb();
+
+ EXPECT_EQ("added: optional_nested_message.bb: 118\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, EmbeddedDeletionTest) {
+ proto2_.mutable_optional_nested_message()->clear_bb();
+
+ EXPECT_EQ("deleted: optional_nested_message.bb: 118\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, EmbeddedModificationTest) {
+ proto1_.mutable_optional_nested_message()->set_bb(2);
+
+ EXPECT_EQ("modified: optional_nested_message.bb: 2 -> 118\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, EmbeddedFullAdditionTest) {
+ proto1_.clear_optional_nested_message();
+
+ EXPECT_EQ("added: optional_nested_message: { bb: 118 }\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, EmbeddedPartialAdditionTest) {
+ proto1_.clear_optional_nested_message();
+ proto2_.mutable_optional_nested_message()->clear_bb();
+
+ EXPECT_EQ("added: optional_nested_message: { }\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, EmbeddedFullDeletionTest) {
+ proto2_.clear_optional_nested_message();
+
+ EXPECT_EQ("deleted: optional_nested_message: { bb: 118 }\n",
+ Run());
+}
+
+// Repeated element tests.
+TEST_F(ComparisonTest, BasicRepeatedTest) {
+ proto1_.clear_repeated_int32();
+ proto2_.clear_repeated_int32();
+
+ proto1_.add_repeated_int32(500);
+ proto1_.add_repeated_int32(501);
+ proto1_.add_repeated_int32(502);
+ proto1_.add_repeated_int32(503);
+ proto1_.add_repeated_int32(500);
+
+ proto2_.add_repeated_int32(500);
+ proto2_.add_repeated_int32(509);
+ proto2_.add_repeated_int32(502);
+ proto2_.add_repeated_int32(504);
+
+ EXPECT_EQ("modified: repeated_int32[1]: 501 -> 509\n"
+ "modified: repeated_int32[3]: 503 -> 504\n"
+ "deleted: repeated_int32[4]: 500\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, BasicRepeatedTest_SetOption) {
+ repeated_field_as_set();
+ proto1_.clear_repeated_int32();
+ proto2_.clear_repeated_int32();
+
+ proto1_.add_repeated_int32(501);
+ proto1_.add_repeated_int32(502);
+ proto1_.add_repeated_int32(503);
+ proto1_.add_repeated_int32(500);
+ proto1_.add_repeated_int32(500);
+
+ proto2_.add_repeated_int32(500);
+ proto2_.add_repeated_int32(509);
+ proto2_.add_repeated_int32(503);
+ proto2_.add_repeated_int32(502);
+ proto2_.add_repeated_int32(504);
+
+ EXPECT_EQ("moved: repeated_int32[1] -> repeated_int32[3] : 502\n"
+ "moved: repeated_int32[3] -> repeated_int32[0] : 500\n"
+ "added: repeated_int32[1]: 509\n"
+ "added: repeated_int32[4]: 504\n"
+ "deleted: repeated_int32[0]: 501\n"
+ "deleted: repeated_int32[4]: 500\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, BasicRepeatedTest_SetField) {
+ field_as_set("repeated_int32");
+ proto1_.clear_repeated_int32();
+ proto2_.clear_repeated_int32();
+
+ proto1_.add_repeated_int32(501);
+ proto1_.add_repeated_int32(502);
+ proto1_.add_repeated_int32(503);
+ proto1_.add_repeated_int32(500);
+ proto1_.add_repeated_int32(500);
+
+ proto2_.add_repeated_int32(500);
+ proto2_.add_repeated_int32(509);
+ proto2_.add_repeated_int32(503);
+ proto2_.add_repeated_int32(502);
+ proto2_.add_repeated_int32(504);
+
+ EXPECT_EQ("moved: repeated_int32[1] -> repeated_int32[3] : 502\n"
+ "moved: repeated_int32[3] -> repeated_int32[0] : 500\n"
+ "added: repeated_int32[1]: 509\n"
+ "added: repeated_int32[4]: 504\n"
+ "deleted: repeated_int32[0]: 501\n"
+ "deleted: repeated_int32[4]: 500\n",
+ Run());
+}
+
+// Multiple action tests.
+TEST_F(ComparisonTest, AddDeleteTest) {
+ proto1_.clear_optional_int32();
+ proto2_.clear_optional_int64();
+
+ EXPECT_EQ("added: optional_int32: 101\n"
+ "deleted: optional_int64: 102\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, AddDelete_FieldOrderingTest) {
+ orderings_proto1_.ClearExtension(unittest::my_extension_string);
+ orderings_proto2_.clear_my_int();
+
+ EXPECT_EQ("deleted: my_int: 1\n"
+ "added: (protobuf_unittest.my_extension_string): \"bar\"\n",
+ RunOrder());
+}
+
+TEST_F(ComparisonTest, AllThreeTest) {
+ proto1_.clear_optional_int32();
+ proto2_.clear_optional_float();
+ proto2_.set_optional_string("hello world!");
+
+ EXPECT_EQ("added: optional_int32: 101\n"
+ "deleted: optional_float: 111\n"
+ "modified: optional_string: \"115\" -> \"hello world!\"\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, SandwhichTest) {
+ proto1_.clear_optional_int64();
+ proto1_.clear_optional_uint32();
+
+ proto2_.clear_optional_uint64();
+
+ EXPECT_EQ("added: optional_int64: 102\n"
+ "added: optional_uint32: 103\n"
+ "deleted: optional_uint64: 104\n",
+ Run());
+}
+
+TEST_F(ComparisonTest, IgnoredNoChangeTest) {
+ proto1diff_.set_v(3);
+ proto2diff_.set_v(3);
+ proto2diff_.set_w("foo");
+
+ ignore_field("v");
+
+ EXPECT_EQ("ignored: v\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredAddTest) {
+ proto2diff_.set_v(3);
+ proto2diff_.set_w("foo");
+
+ ignore_field("v");
+
+ EXPECT_EQ("ignored: v\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredDeleteTest) {
+ proto1diff_.set_v(3);
+ proto2diff_.set_w("foo");
+
+ ignore_field("v");
+
+ EXPECT_EQ("ignored: v\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredModifyTest) {
+ proto1diff_.set_v(3);
+ proto2diff_.set_v(4);
+ proto2diff_.set_w("foo");
+
+ ignore_field("v");
+
+ EXPECT_EQ("ignored: v\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredRepeatedAddTest) {
+ proto1diff_.add_rv(3);
+ proto1diff_.add_rv(4);
+
+ proto2diff_.add_rv(3);
+ proto2diff_.add_rv(4);
+ proto2diff_.add_rv(5);
+
+ proto2diff_.set_w("foo");
+
+ ignore_field("rv");
+
+ EXPECT_EQ("ignored: rv\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredRepeatedDeleteTest) {
+ proto1diff_.add_rv(3);
+ proto1diff_.add_rv(4);
+ proto1diff_.add_rv(5);
+
+ proto2diff_.add_rv(3);
+ proto2diff_.add_rv(4);
+
+ proto2diff_.set_w("foo");
+
+ ignore_field("rv");
+
+ EXPECT_EQ("ignored: rv\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredRepeatedModifyTest) {
+ proto1diff_.add_rv(3);
+ proto1diff_.add_rv(4);
+
+ proto2diff_.add_rv(3);
+ proto2diff_.add_rv(5);
+
+ proto2diff_.set_w("foo");
+
+ ignore_field("rv");
+
+ EXPECT_EQ("ignored: rv\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredWholeNestedMessage) {
+ proto1diff_.mutable_m()->set_c(3);
+ proto2diff_.mutable_m()->set_c(4);
+
+ proto2diff_.set_w("foo");
+
+ ignore_field("m");
+
+ EXPECT_EQ("added: w: \"foo\"\n"
+ "ignored: m\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredNestedField) {
+ proto1diff_.mutable_m()->set_c(3);
+ proto2diff_.mutable_m()->set_c(4);
+
+ proto2diff_.set_w("foo");
+
+ ignore_field("m.c");
+
+ EXPECT_EQ("added: w: \"foo\"\n"
+ "ignored: m.c\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredRepeatedNested) {
+ proto1diff_.add_rm()->set_c(0);
+ proto1diff_.add_rm()->set_c(1);
+ proto2diff_.add_rm()->set_c(2);
+ proto2diff_.add_rm()->set_c(3);
+
+ proto2diff_.set_w("foo");
+
+ ignore_field("rm.c");
+
+ EXPECT_EQ("ignored: rm[0].c\n"
+ "ignored: rm[1].c\n"
+ "added: w: \"foo\"\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, IgnoredNestedRepeated) {
+ proto1diff_.mutable_m()->add_rc(23);
+ proto1diff_.mutable_m()->add_rc(24);
+ proto2diff_.mutable_m()->add_rc(25);
+
+ proto2diff_.set_w("foo");
+
+ ignore_field("m.rc");
+
+ EXPECT_EQ("added: w: \"foo\"\n"
+ "ignored: m.rc\n",
+ RunDiff());
+}
+
+TEST_F(ComparisonTest, ExtensionTest) {
+ proto1ex_.SetExtension(unittest::optional_int32_extension, 401);
+ proto2ex_.SetExtension(unittest::optional_int32_extension, 402);
+
+ proto1ex_.ClearExtension(unittest::optional_int64_extension);
+ proto2ex_.SetExtension(unittest::optional_int64_extension, 403);
+
+ EXPECT_EQ(
+ "modified: (protobuf_unittest.optional_int32_extension): 401 -> 402\n"
+ "added: (protobuf_unittest.optional_int64_extension): 403\n",
+ RunEx());
+}
+
+TEST_F(ComparisonTest, MatchedUnknownFieldTagTest) {
+ unknown1_->AddVarint(240, 122);
+ unknown2_->AddVarint(240, 121);
+ unknown1_->AddFixed32(241, 1);
+ unknown2_->AddFixed64(241, 2);
+ unknown1_->AddLengthDelimited(242, "cat");
+ unknown2_->AddLengthDelimited(242, "dog");
+
+ EXPECT_EQ(
+ "modified: 240[0]: 122 -> 121\n"
+ "deleted: 241[0]: 0x00000001\n"
+ "added: 241[0]: 0x0000000000000002\n"
+ "modified: 242[0]: \"cat\" -> \"dog\"\n",
+ RunUn());
+}
+
+TEST_F(ComparisonTest, UnmatchedUnknownFieldTagTest) {
+ unknown1_->AddFixed32(243, 1);
+ unknown2_->AddVarint(244, 2);
+ unknown2_->AddVarint(244, 4);
+
+ EXPECT_EQ(
+ "deleted: 243[0]: 0x00000001\n"
+ "added: 244[0]: 2\n"
+ "added: 244[1]: 4\n",
+ RunUn());
+}
+
+TEST_F(ComparisonTest, DifferentSizedUnknownFieldTest) {
+ unknown1_->AddVarint(240, 1);
+ unknown1_->AddVarint(240, 3);
+ unknown1_->AddVarint(240, 4);
+ unknown2_->AddVarint(240, 2);
+ unknown2_->AddVarint(240, 3);
+ unknown2_->AddVarint(240, 2);
+ unknown2_->AddVarint(240, 5);
+
+ EXPECT_EQ(
+ "modified: 240[0]: 1 -> 2\n"
+ "modified: 240[2]: 4 -> 2\n"
+ "added: 240[3]: 5\n",
+ RunUn());
+}
+
+TEST_F(ComparisonTest, UnknownFieldsAll) {
+ unknown1_->AddVarint(243, 122);
+ unknown1_->AddFixed64(244, 0x0172356);
+ unknown1_->AddFixed64(244, 0x098);
+ unknown1_->AddGroup(245)->AddFixed32(248, 1);
+ unknown1_->mutable_field(3)->mutable_group()->AddFixed32(248, 2);
+ unknown1_->AddGroup(249)->AddFixed64(250, 1);
+
+ unknown2_->AddVarint(243, 121);
+ unknown2_->AddLengthDelimited(73882, "test 123");
+ unknown2_->AddGroup(245)->AddFixed32(248, 3);
+ unknown2_->AddGroup(247);
+
+ EXPECT_EQ(
+ "modified: 243[0]: 122 -> 121\n"
+ "deleted: 244[0]: 0x0000000000172356\n"
+ "deleted: 244[1]: 0x0000000000000098\n"
+ "modified: 245[0].248[0]: 0x00000001 -> 0x00000003\n"
+ "deleted: 245[0].248[1]: 0x00000002\n"
+ "added: 247[0]: { ... }\n"
+ "deleted: 249[0]: { ... }\n"
+ "added: 73882[0]: \"test 123\"\n",
+ RunUn());
+}
+
+TEST_F(ComparisonTest, EquivalentIgnoresUnknown) {
+ unittest::ForeignMessage message1, message2;
+
+ message1.set_c(5);
+ message1.mutable_unknown_fields()->AddVarint(123, 456);
+ message2.set_c(5);
+ message2.mutable_unknown_fields()->AddVarint(321, 654);
+
+ EXPECT_FALSE(util::MessageDifferencer::Equals(message1, message2));
+ EXPECT_TRUE(util::MessageDifferencer::Equivalent(message1, message2));
+}
+
+class MatchingTest : public testing::Test {
+ public:
+ typedef util::MessageDifferencer MessageDifferencer;
+
+ protected:
+ MatchingTest() {
+ }
+
+ ~MatchingTest() {
+ }
+
+ string RunWithResult(MessageDifferencer* differencer,
+ const Message& msg1, const Message& msg2,
+ bool result) {
+ string output;
+ {
+ // Before we return the "output" string, we must make sure the
+ // StreamReporter is destructored because its destructor will
+ // flush the stream.
+ io::StringOutputStream output_stream(&output);
+ MessageDifferencer::StreamReporter reporter(&output_stream);
+ reporter.set_report_modified_aggregates(true);
+ differencer->set_report_matches(true);
+ differencer->ReportDifferencesTo(&reporter);
+ if (result) {
+ EXPECT_TRUE(differencer->Compare(msg1, msg2));
+ } else {
+ EXPECT_FALSE(differencer->Compare(msg1, msg2));
+ }
+ }
+ return output;
+ }
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MatchingTest);
+};
+
+TEST_F(MatchingTest, StreamReporterMatching) {
+ protobuf_unittest::TestField msg1, msg2;
+ msg1.set_c(72);
+ msg2.set_c(72);
+ msg1.add_rc(13);
+ msg2.add_rc(13);
+ msg1.add_rc(17);
+ msg2.add_rc(17);
+ string output;
+ MessageDifferencer differencer;
+ differencer.set_report_matches(true);
+ differencer.ReportDifferencesToString(&output);
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "matched: c : 72\n"
+ "matched: rc[0] : 13\n"
+ "matched: rc[1] : 17\n",
+ output);
+}
+
+TEST_F(MatchingTest, DontReportMatchedWhenIgnoring) {
+ protobuf_unittest::TestField msg1, msg2;
+ msg1.set_c(72);
+ msg2.set_c(72);
+ msg1.add_rc(13);
+ msg2.add_rc(13);
+ msg1.add_rc(17);
+ msg2.add_rc(17);
+ string output;
+ MessageDifferencer differencer;
+ differencer.set_report_matches(true);
+ differencer.ReportDifferencesToString(&output);
+
+ differencer.IgnoreField(msg1.GetDescriptor()->FindFieldByName("c"));
+
+ EXPECT_TRUE(differencer.Compare(msg1, msg2));
+ EXPECT_EQ(
+ "ignored: c\n"
+ "matched: rc[0] : 13\n"
+ "matched: rc[1] : 17\n",
+ output);
+}
+
+TEST_F(MatchingTest, ReportMatchedForMovedFields) {
+ protobuf_unittest::TestDiffMessage msg1, msg2;
+ protobuf_unittest::TestDiffMessage::Item* item = msg1.add_item();
+ item->set_a(53);
+ item->set_b("hello");
+ item = msg2.add_item();
+ item->set_a(27);
+ item = msg2.add_item();
+ item->set_a(53);
+ item->set_b("hello");
+ item = msg1.add_item();
+ item->set_a(27);
+ MessageDifferencer differencer;
+ const FieldDescriptor* desc;
+ desc = msg1.GetDescriptor()->FindFieldByName("item");
+ differencer.TreatAsSet(desc);
+
+ EXPECT_EQ(
+ "matched: item[0].a -> item[1].a : 53\n"
+ "matched: item[0].b -> item[1].b : \"hello\"\n"
+ "moved: item[0] -> item[1] : { a: 53 b: \"hello\" }\n"
+ "matched: item[1].a -> item[0].a : 27\n"
+ "moved: item[1] -> item[0] : { a: 27 }\n",
+ RunWithResult(&differencer, msg1, msg2, true));
+}
+
+TEST_F(MatchingTest, MatchesAppearInPostTraversalOrderForMovedFields) {
+ protobuf_unittest::TestDiffMessage msg1, msg2;
+ protobuf_unittest::TestDiffMessage::Item* item;
+ protobuf_unittest::TestField* field;
+
+ const FieldDescriptor* desc;
+ const FieldDescriptor* nested_desc;
+ const FieldDescriptor* double_nested_desc;
+ desc = msg1.GetDescriptor()->FindFieldByName("item");
+ nested_desc = desc->message_type()->FindFieldByName("rm");
+ double_nested_desc = nested_desc->message_type()->FindFieldByName("rc");
+ MessageDifferencer differencer;
+ differencer.TreatAsSet(desc);
+ differencer.TreatAsSet(nested_desc);
+ differencer.TreatAsSet(double_nested_desc);
+
+ item = msg1.add_item();
+ field = item->add_rm();
+ field->set_c(1);
+ field->add_rc(2);
+ field->add_rc(3);
+ field = item->add_rm();
+ field->set_c(4);
+ field->add_rc(5);
+ field->add_rc(6);
+ field->add_rc(7);
+ item = msg2.add_item();
+ field = item->add_rm();
+ field->set_c(4);
+ field->add_rc(7);
+ field->add_rc(6);
+ field->add_rc(5);
+ field = item->add_rm();
+ field->set_c(1);
+ field->add_rc(3);
+ field->add_rc(2);
+ item = msg1.add_item();
+ field = item->add_rm();
+ field->set_c(8);
+ field->add_rc(10);
+ field->add_rc(11);
+ field->add_rc(9);
+ item = msg2.add_item();
+ field = item->add_rm();
+ field->set_c(8);
+ field->add_rc(9);
+ field->add_rc(10);
+ field->add_rc(11);
+
+ EXPECT_EQ(
+ "matched: item[0].rm[0].c -> item[0].rm[1].c : 1\n"
+ "moved: item[0].rm[0].rc[0] -> item[0].rm[1].rc[1] : 2\n"
+ "moved: item[0].rm[0].rc[1] -> item[0].rm[1].rc[0] : 3\n"
+ "moved: item[0].rm[0] -> item[0].rm[1] : { c: 1 rc: 2 rc: 3 }\n"
+ "matched: item[0].rm[1].c -> item[0].rm[0].c : 4\n"
+ "moved: item[0].rm[1].rc[0] -> item[0].rm[0].rc[2] : 5\n"
+ "matched: item[0].rm[1].rc[1] -> item[0].rm[0].rc[1] : 6\n"
+ "moved: item[0].rm[1].rc[2] -> item[0].rm[0].rc[0] : 7\n"
+ "moved: item[0].rm[1] -> item[0].rm[0] : { c: 4 rc: 5 rc: 6 rc: 7 }\n"
+ "matched: item[0] : { rm { c: 1 rc: 2 rc: 3 }"
+ " rm { c: 4 rc: 5 rc: 6 rc: 7 } }\n"
+ "matched: item[1].rm[0].c : 8\n"
+ "moved: item[1].rm[0].rc[0] -> item[1].rm[0].rc[1] : 10\n"
+ "moved: item[1].rm[0].rc[1] -> item[1].rm[0].rc[2] : 11\n"
+ "moved: item[1].rm[0].rc[2] -> item[1].rm[0].rc[0] : 9\n"
+ "matched: item[1].rm[0] : { c: 8 rc: 10 rc: 11 rc: 9 }\n"
+ "matched: item[1] : { rm { c: 8 rc: 10 rc: 11 rc: 9 } }\n",
+ RunWithResult(&differencer, msg1, msg2, true));
+}
+
+TEST_F(MatchingTest, MatchAndModifiedInterleaveProperly) {
+ protobuf_unittest::TestDiffMessage msg1, msg2;
+ protobuf_unittest::TestDiffMessage::Item* item;
+ protobuf_unittest::TestField* field;
+
+ const FieldDescriptor* desc;
+ const FieldDescriptor* nested_key;
+ const FieldDescriptor* nested_desc;
+ const FieldDescriptor* double_nested_key;
+ const FieldDescriptor* double_nested_desc;
+ desc = msg1.GetDescriptor()->FindFieldByName("item");
+ nested_key = desc->message_type()->FindFieldByName("a");
+ nested_desc = desc->message_type()->FindFieldByName("rm");
+ double_nested_key = nested_desc->message_type()->FindFieldByName("c");
+ double_nested_desc = nested_desc->message_type()->FindFieldByName("rc");
+
+ MessageDifferencer differencer;
+ differencer.TreatAsMap(desc, nested_key);
+ differencer.TreatAsMap(nested_desc, double_nested_key);
+ differencer.TreatAsSet(double_nested_desc);
+
+ item = msg1.add_item();
+ item->set_a(1);
+ field = item->add_rm();
+ field->set_c(2);
+ field->add_rc(3);
+ field->add_rc(4);
+ field = item->add_rm();
+ field->set_c(5);
+ field->add_rc(6);
+ field->add_rc(7);
+ field->add_rc(8);
+ item = msg1.add_item();
+ item->set_a(9);
+ field = item->add_rm();
+ field->set_c(10);
+ field->add_rc(11);
+ field->add_rc(12);
+ field = item->add_rm();
+ field->set_c(13);
+
+ item = msg2.add_item();
+ item->set_a(1);
+ field = item->add_rm();
+ field->set_c(5);
+ field->add_rc(8);
+ field->add_rc(8);
+ field->add_rc(6);
+ field = item->add_rm();
+ field->set_c(3);
+ field->add_rc(2);
+ field->add_rc(4);
+ item = msg2.add_item();
+ item->set_a(9);
+ field = item->add_rm();
+ field->set_c(10);
+ field->add_rc(12);
+ field->add_rc(11);
+ field = item->add_rm();
+ field->set_c(13);
+
+ EXPECT_EQ(
+ "matched: item[0].a : 1\n"
+ "matched: item[0].rm[1].c -> item[0].rm[0].c : 5\n"
+ "moved: item[0].rm[1].rc[0] -> item[0].rm[0].rc[2] : 6\n"
+ "moved: item[0].rm[1].rc[2] -> item[0].rm[0].rc[0] : 8\n"
+ "added: item[0].rm[0].rc[1]: 8\n"
+ "deleted: item[0].rm[1].rc[1]: 7\n"
+ "modified: item[0].rm[1] -> item[0].rm[0]: { c: 5 rc: 6 rc: 7 rc: 8 } ->"
+ " { c: 5 rc: 8 rc: 8 rc: 6 }\n"
+ "added: item[0].rm[1]: { c: 3 rc: 2 rc: 4 }\n"
+ "deleted: item[0].rm[0]: { c: 2 rc: 3 rc: 4 }\n"
+ "modified: item[0]: { a: 1 rm { c: 2 rc: 3 rc: 4 }"
+ " rm { c: 5 rc: 6 rc: 7 rc: 8 } } ->"
+ " { a: 1 rm { c: 5 rc: 8 rc: 8 rc: 6 }"
+ " rm { c: 3 rc: 2 rc: 4 } }\n"
+ "matched: item[1].a : 9\n"
+ "matched: item[1].rm[0].c : 10\n"
+ "moved: item[1].rm[0].rc[0] -> item[1].rm[0].rc[1] : 11\n"
+ "moved: item[1].rm[0].rc[1] -> item[1].rm[0].rc[0] : 12\n"
+ "matched: item[1].rm[0] : { c: 10 rc: 11 rc: 12 }\n"
+ "matched: item[1].rm[1].c : 13\n"
+ "matched: item[1].rm[1] : { c: 13 }\n"
+ "matched: item[1] : { a: 9 rm { c: 10 rc: 11 rc: 12 } rm { c: 13 } }\n",
+ RunWithResult(&differencer, msg1, msg2, false));
+}
+
+TEST_F(MatchingTest, MatchingWorksWithExtensions) {
+ protobuf_unittest::TestAllExtensions msg1, msg2;
+ protobuf_unittest::TestAllTypes::NestedMessage* nested;
+ using protobuf_unittest::repeated_nested_message_extension;
+
+ const FileDescriptor* descriptor;
+ const FieldDescriptor* desc;
+ const FieldDescriptor* nested_key;
+ descriptor = msg1.GetDescriptor()->file();
+ desc = descriptor->FindExtensionByName("repeated_nested_message_extension");
+ ASSERT_FALSE(desc == NULL);
+ nested_key = desc->message_type()->FindFieldByName("bb");
+
+ MessageDifferencer differencer;
+ differencer.TreatAsMap(desc, nested_key);
+
+ nested = msg1.AddExtension(repeated_nested_message_extension);
+ nested->set_bb(7);
+ nested = msg1.AddExtension(repeated_nested_message_extension);
+ nested->set_bb(13);
+ nested = msg1.AddExtension(repeated_nested_message_extension);
+ nested->set_bb(11);
+ nested = msg2.AddExtension(repeated_nested_message_extension);
+ nested->set_bb(11);
+ nested = msg2.AddExtension(repeated_nested_message_extension);
+ nested->set_bb(13);
+ nested = msg2.AddExtension(repeated_nested_message_extension);
+ nested->set_bb(7);
+
+ EXPECT_EQ(
+ "matched: (protobuf_unittest.repeated_nested_message_extension)[0].bb ->"
+ " (protobuf_unittest.repeated_nested_message_extension)[2].bb : 7\n"
+ "moved: (protobuf_unittest.repeated_nested_message_extension)[0] ->"
+ " (protobuf_unittest.repeated_nested_message_extension)[2] :"
+ " { bb: 7 }\n"
+ "matched: (protobuf_unittest.repeated_nested_message_extension)[1].bb :"
+ " 13\n"
+ "matched: (protobuf_unittest.repeated_nested_message_extension)[1] :"
+ " { bb: 13 }\n"
+ "matched: (protobuf_unittest.repeated_nested_message_extension)[2].bb ->"
+ " (protobuf_unittest.repeated_nested_message_extension)[0].bb :"
+ " 11\n"
+ "moved: (protobuf_unittest.repeated_nested_message_extension)[2] ->"
+ " (protobuf_unittest.repeated_nested_message_extension)[0] :"
+ " { bb: 11 }\n",
+ RunWithResult(&differencer, msg1, msg2, true));
+}
+
+TEST(AnyTest, Simple) {
+ protobuf_unittest::TestField value1, value2;
+ value1.set_a(20);
+ value2.set_a(21);
+
+ protobuf_unittest::TestAny m1, m2;
+ m1.mutable_any_value()->PackFrom(value1);
+ m2.mutable_any_value()->PackFrom(value2);
+ util::MessageDifferencer message_differencer;
+ string difference_string;
+ message_differencer.ReportDifferencesToString(&difference_string);
+ EXPECT_FALSE(message_differencer.Compare(m1, m2));
+ EXPECT_EQ("modified: any_value.a: 20 -> 21\n", difference_string);
+}
+
+TEST(Anytest, TreatAsSet) {
+ protobuf_unittest::TestField value1, value2;
+ value1.set_a(20);
+ value1.set_b(30);
+ value2.set_a(20);
+ value2.set_b(31);
+
+ protobuf_unittest::TestAny m1, m2;
+ m1.add_repeated_any_value()->PackFrom(value1);
+ m1.add_repeated_any_value()->PackFrom(value2);
+ m2.add_repeated_any_value()->PackFrom(value2);
+ m2.add_repeated_any_value()->PackFrom(value1);
+
+ util::MessageDifferencer message_differencer;
+ message_differencer.TreatAsSet(GetFieldDescriptor(m1, "repeated_any_value"));
+ EXPECT_TRUE(message_differencer.Compare(m1, m2));
+}
+
+
+} // namespace
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.proto b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.proto
new file mode 100644
index 0000000000..698775f14c
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/message_differencer_unittest.proto
@@ -0,0 +1,74 @@
+// 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 messages for testing repeated field comparison
+
+syntax = "proto2";
+package protobuf_unittest;
+
+option optimize_for = SPEED;
+
+message TestField {
+ optional int32 a = 3;
+ optional int32 b = 4;
+ optional int32 c = 1;
+ repeated int32 rc = 2;
+ optional TestField m = 5;
+
+ extend TestDiffMessage {
+ optional TestField tf = 100;
+ }
+}
+
+message TestDiffMessage {
+ repeated group Item = 1 {
+ optional int32 a = 2; // Test basic repeated field comparison.
+ optional string b = 4; // Test basic repeated field comparison.
+ repeated int32 ra = 3; // Test SetOfSet Comparison.
+ repeated string rb = 5; // Test TreatAsMap when key is repeated
+ optional TestField m = 6; // Test TreatAsMap when key is a message
+ repeated TestField rm = 7; // Test TreatAsMap when key is a repeated
+ // message
+ }
+
+ optional int32 v = 13 [deprecated = true];
+ optional string w = 14;
+ optional TestField m = 15;
+ repeated int32 rv = 11; // Test for combinations
+ repeated string rw = 10; // Test for combinations
+ repeated TestField rm = 12 [deprecated = true]; // Test for combinations
+
+ extensions 100 to 199;
+}
+
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.cc
new file mode 100644
index 0000000000..031d019ab9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.cc
@@ -0,0 +1,532 @@
+// 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.
+
+#include <google/protobuf/util/time_util.h>
+
+#include <google/protobuf/stubs/time.h>
+#include <google/protobuf/stubs/int128.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/duration.pb.h>
+#include <google/protobuf/timestamp.pb.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+using google::protobuf::Timestamp;
+using google::protobuf::Duration;
+
+namespace {
+static const int kNanosPerSecond = 1000000000;
+static const int kMicrosPerSecond = 1000000;
+static const int kMillisPerSecond = 1000;
+static const int kNanosPerMillisecond = 1000000;
+static const int kMicrosPerMillisecond = 1000;
+static const int kNanosPerMicrosecond = 1000;
+static const int kSecondsPerMinute = 60; // Note that we ignore leap seconds.
+static const int kSecondsPerHour = 3600;
+static const char kTimestampFormat[] = "%E4Y-%m-%dT%H:%M:%S";
+
+template <typename T>
+T CreateNormalized(int64 seconds, int64 nanos);
+
+template <>
+Timestamp CreateNormalized(int64 seconds, int64 nanos) {
+ // Make sure nanos is in the range.
+ if (nanos <= -kNanosPerSecond || nanos >= kNanosPerSecond) {
+ seconds += nanos / kNanosPerSecond;
+ nanos = nanos % kNanosPerSecond;
+ }
+ // For Timestamp nanos should be in the range [0, 999999999]
+ if (nanos < 0) {
+ seconds -= 1;
+ nanos += kNanosPerSecond;
+ }
+ GOOGLE_DCHECK(seconds >= TimeUtil::kTimestampMinSeconds &&
+ seconds <= TimeUtil::kTimestampMaxSeconds);
+ Timestamp result;
+ result.set_seconds(seconds);
+ result.set_nanos(static_cast<int32>(nanos));
+ return result;
+}
+
+template <>
+Duration CreateNormalized(int64 seconds, int64 nanos) {
+ // Make sure nanos is in the range.
+ if (nanos <= -kNanosPerSecond || nanos >= kNanosPerSecond) {
+ seconds += nanos / kNanosPerSecond;
+ nanos = nanos % kNanosPerSecond;
+ }
+ // nanos should have the same sign as seconds.
+ if (seconds < 0 && nanos > 0) {
+ seconds += 1;
+ nanos -= kNanosPerSecond;
+ } else if (seconds > 0 && nanos < 0) {
+ seconds -= 1;
+ nanos += kNanosPerSecond;
+ }
+ GOOGLE_DCHECK(seconds >= TimeUtil::kDurationMinSeconds &&
+ seconds <= TimeUtil::kDurationMaxSeconds);
+ Duration result;
+ result.set_seconds(seconds);
+ result.set_nanos(static_cast<int32>(nanos));
+ return result;
+}
+
+// Format nanoseconds with either 3, 6, or 9 digits depending on the required
+// precision to represent the exact value.
+string FormatNanos(int32 nanos) {
+ if (nanos % kNanosPerMillisecond == 0) {
+ return StringPrintf("%03d", nanos / kNanosPerMillisecond);
+ } else if (nanos % kNanosPerMicrosecond == 0) {
+ return StringPrintf("%06d", nanos / kNanosPerMicrosecond);
+ } else {
+ return StringPrintf("%09d", nanos);
+ }
+}
+
+string FormatTime(int64 seconds, int32 nanos) {
+ return ::google::protobuf::internal::FormatTime(seconds, nanos);
+}
+
+bool ParseTime(const string& value, int64* seconds, int32* nanos) {
+ return ::google::protobuf::internal::ParseTime(value, seconds, nanos);
+}
+
+void CurrentTime(int64* seconds, int32* nanos) {
+ return ::google::protobuf::internal::GetCurrentTime(seconds, nanos);
+}
+
+// Truncates the remainder part after division.
+int64 RoundTowardZero(int64 value, int64 divider) {
+ int64 result = value / divider;
+ int64 remainder = value % divider;
+ // Before C++11, the sign of the remainder is implementation dependent if
+ // any of the operands is negative. Here we try to enforce C++11's "rounded
+ // toward zero" semantics. For example, for (-5) / 2 an implementation may
+ // give -3 as the result with the remainder being 1. This function ensures
+ // we always return -2 (closer to zero) regardless of the implementation.
+ if (result < 0 && remainder > 0) {
+ return result + 1;
+ } else {
+ return result;
+ }
+}
+} // namespace
+
+// Actually define these static const integers. Required by C++ standard (but
+// omitting them may still work with some compilers).
+const int64 TimeUtil::kTimestampMinSeconds;
+const int64 TimeUtil::kTimestampMaxSeconds;
+const int64 TimeUtil::kDurationMaxSeconds;
+const int64 TimeUtil::kDurationMinSeconds;
+
+string TimeUtil::ToString(const Timestamp& timestamp) {
+ return FormatTime(timestamp.seconds(), timestamp.nanos());
+}
+
+bool TimeUtil::FromString(const string& value, Timestamp* timestamp) {
+ int64 seconds;
+ int32 nanos;
+ if (!ParseTime(value, &seconds, &nanos)) {
+ return false;
+ }
+ *timestamp = CreateNormalized<Timestamp>(seconds, nanos);
+ return true;
+}
+
+Timestamp TimeUtil::GetCurrentTime() {
+ int64 seconds;
+ int32 nanos;
+ CurrentTime(&seconds, &nanos);
+ return CreateNormalized<Timestamp>(seconds, nanos);
+}
+
+Timestamp TimeUtil::GetEpoch() { return Timestamp(); }
+
+string TimeUtil::ToString(const Duration& duration) {
+ string result;
+ int64 seconds = duration.seconds();
+ int32 nanos = duration.nanos();
+ if (seconds < 0 || nanos < 0) {
+ result += "-";
+ seconds = -seconds;
+ nanos = -nanos;
+ }
+ result += SimpleItoa(seconds);
+ if (nanos != 0) {
+ result += "." + FormatNanos(nanos);
+ }
+ result += "s";
+ return result;
+}
+
+static int64 Pow(int64 x, int y) {
+ int64 result = 1;
+ for (int i = 0; i < y; ++i) {
+ result *= x;
+ }
+ return result;
+}
+
+bool TimeUtil::FromString(const string& value, Duration* duration) {
+ if (value.length() <= 1 || value[value.length() - 1] != 's') {
+ return false;
+ }
+ bool negative = (value[0] == '-');
+ int sign_length = (negative ? 1 : 0);
+ // Parse the duration value as two integers rather than a float value
+ // to avoid precision loss.
+ string seconds_part, nanos_part;
+ size_t pos = value.find_last_of(".");
+ if (pos == string::npos) {
+ seconds_part = value.substr(sign_length, value.length() - 1 - sign_length);
+ nanos_part = "0";
+ } else {
+ seconds_part = value.substr(sign_length, pos - sign_length);
+ nanos_part = value.substr(pos + 1, value.length() - pos - 2);
+ }
+ char* end;
+ int64 seconds = strto64(seconds_part.c_str(), &end, 10);
+ if (end != seconds_part.c_str() + seconds_part.length()) {
+ return false;
+ }
+ int64 nanos = strto64(nanos_part.c_str(), &end, 10);
+ if (end != nanos_part.c_str() + nanos_part.length()) {
+ return false;
+ }
+ nanos = nanos * Pow(10, 9 - nanos_part.length());
+ if (negative) {
+ // If a Duration is negative, both seconds and nanos should be negative.
+ seconds = -seconds;
+ nanos = -nanos;
+ }
+ duration->set_seconds(seconds);
+ duration->set_nanos(static_cast<int32>(nanos));
+ return true;
+}
+
+Duration TimeUtil::NanosecondsToDuration(int64 nanos) {
+ return CreateNormalized<Duration>(nanos / kNanosPerSecond,
+ nanos % kNanosPerSecond);
+}
+
+Duration TimeUtil::MicrosecondsToDuration(int64 micros) {
+ return CreateNormalized<Duration>(
+ micros / kMicrosPerSecond,
+ (micros % kMicrosPerSecond) * kNanosPerMicrosecond);
+}
+
+Duration TimeUtil::MillisecondsToDuration(int64 millis) {
+ return CreateNormalized<Duration>(
+ millis / kMillisPerSecond,
+ (millis % kMillisPerSecond) * kNanosPerMillisecond);
+}
+
+Duration TimeUtil::SecondsToDuration(int64 seconds) {
+ return CreateNormalized<Duration>(seconds, 0);
+}
+
+Duration TimeUtil::MinutesToDuration(int64 minutes) {
+ return CreateNormalized<Duration>(minutes * kSecondsPerMinute, 0);
+}
+
+Duration TimeUtil::HoursToDuration(int64 hours) {
+ return CreateNormalized<Duration>(hours * kSecondsPerHour, 0);
+}
+
+int64 TimeUtil::DurationToNanoseconds(const Duration& duration) {
+ return duration.seconds() * kNanosPerSecond + duration.nanos();
+}
+
+int64 TimeUtil::DurationToMicroseconds(const Duration& duration) {
+ return duration.seconds() * kMicrosPerSecond +
+ RoundTowardZero(duration.nanos(), kNanosPerMicrosecond);
+}
+
+int64 TimeUtil::DurationToMilliseconds(const Duration& duration) {
+ return duration.seconds() * kMillisPerSecond +
+ RoundTowardZero(duration.nanos(), kNanosPerMillisecond);
+}
+
+int64 TimeUtil::DurationToSeconds(const Duration& duration) {
+ return duration.seconds();
+}
+
+int64 TimeUtil::DurationToMinutes(const Duration& duration) {
+ return RoundTowardZero(duration.seconds(), kSecondsPerMinute);
+}
+
+int64 TimeUtil::DurationToHours(const Duration& duration) {
+ return RoundTowardZero(duration.seconds(), kSecondsPerHour);
+}
+
+Timestamp TimeUtil::NanosecondsToTimestamp(int64 nanos) {
+ return CreateNormalized<Timestamp>(nanos / kNanosPerSecond,
+ nanos % kNanosPerSecond);
+}
+
+Timestamp TimeUtil::MicrosecondsToTimestamp(int64 micros) {
+ return CreateNormalized<Timestamp>(
+ micros / kMicrosPerSecond,
+ micros % kMicrosPerSecond * kNanosPerMicrosecond);
+}
+
+Timestamp TimeUtil::MillisecondsToTimestamp(int64 millis) {
+ return CreateNormalized<Timestamp>(
+ millis / kMillisPerSecond,
+ millis % kMillisPerSecond * kNanosPerMillisecond);
+}
+
+Timestamp TimeUtil::SecondsToTimestamp(int64 seconds) {
+ return CreateNormalized<Timestamp>(seconds, 0);
+}
+
+int64 TimeUtil::TimestampToNanoseconds(const Timestamp& timestamp) {
+ return timestamp.seconds() * kNanosPerSecond + timestamp.nanos();
+}
+
+int64 TimeUtil::TimestampToMicroseconds(const Timestamp& timestamp) {
+ return timestamp.seconds() * kMicrosPerSecond +
+ RoundTowardZero(timestamp.nanos(), kNanosPerMicrosecond);
+}
+
+int64 TimeUtil::TimestampToMilliseconds(const Timestamp& timestamp) {
+ return timestamp.seconds() * kMillisPerSecond +
+ RoundTowardZero(timestamp.nanos(), kNanosPerMillisecond);
+}
+
+int64 TimeUtil::TimestampToSeconds(const Timestamp& timestamp) {
+ return timestamp.seconds();
+}
+
+Timestamp TimeUtil::TimeTToTimestamp(time_t value) {
+ return CreateNormalized<Timestamp>(static_cast<int64>(value), 0);
+}
+
+time_t TimeUtil::TimestampToTimeT(const Timestamp& value) {
+ return static_cast<time_t>(value.seconds());
+}
+
+Timestamp TimeUtil::TimevalToTimestamp(const timeval& value) {
+ return CreateNormalized<Timestamp>(value.tv_sec,
+ value.tv_usec * kNanosPerMicrosecond);
+}
+
+timeval TimeUtil::TimestampToTimeval(const Timestamp& value) {
+ timeval result;
+ result.tv_sec = value.seconds();
+ result.tv_usec = RoundTowardZero(value.nanos(), kNanosPerMicrosecond);
+ return result;
+}
+
+Duration TimeUtil::TimevalToDuration(const timeval& value) {
+ return CreateNormalized<Duration>(value.tv_sec,
+ value.tv_usec * kNanosPerMicrosecond);
+}
+
+timeval TimeUtil::DurationToTimeval(const Duration& value) {
+ timeval result;
+ result.tv_sec = value.seconds();
+ result.tv_usec = RoundTowardZero(value.nanos(), kNanosPerMicrosecond);
+ // timeval.tv_usec's range is [0, 1000000)
+ if (result.tv_usec < 0) {
+ result.tv_sec -= 1;
+ result.tv_usec += kMicrosPerSecond;
+ }
+ return result;
+}
+
+} // namespace util
+} // namespace protobuf
+
+
+namespace protobuf {
+namespace {
+using google::protobuf::util::kNanosPerSecond;
+using google::protobuf::util::CreateNormalized;
+
+// Convert a Timestamp to uint128.
+void ToUint128(const Timestamp& value, uint128* result, bool* negative) {
+ if (value.seconds() < 0) {
+ *negative = true;
+ *result = static_cast<uint64>(-value.seconds());
+ *result = *result * kNanosPerSecond - static_cast<uint32>(value.nanos());
+ } else {
+ *negative = false;
+ *result = static_cast<uint64>(value.seconds());
+ *result = *result * kNanosPerSecond + static_cast<uint32>(value.nanos());
+ }
+}
+
+// Convert a Duration to uint128.
+void ToUint128(const Duration& value, uint128* result, bool* negative) {
+ if (value.seconds() < 0 || value.nanos() < 0) {
+ *negative = true;
+ *result = static_cast<uint64>(-value.seconds());
+ *result = *result * kNanosPerSecond + static_cast<uint32>(-value.nanos());
+ } else {
+ *negative = false;
+ *result = static_cast<uint64>(value.seconds());
+ *result = *result * kNanosPerSecond + static_cast<uint32>(value.nanos());
+ }
+}
+
+void ToTimestamp(const uint128& value, bool negative, Timestamp* timestamp) {
+ int64 seconds = static_cast<int64>(Uint128Low64(value / kNanosPerSecond));
+ int32 nanos = static_cast<int32>(Uint128Low64(value % kNanosPerSecond));
+ if (negative) {
+ seconds = -seconds;
+ nanos = -nanos;
+ if (nanos < 0) {
+ nanos += kNanosPerSecond;
+ seconds -= 1;
+ }
+ }
+ timestamp->set_seconds(seconds);
+ timestamp->set_nanos(nanos);
+}
+
+void ToDuration(const uint128& value, bool negative, Duration* duration) {
+ int64 seconds = static_cast<int64>(Uint128Low64(value / kNanosPerSecond));
+ int32 nanos = static_cast<int32>(Uint128Low64(value % kNanosPerSecond));
+ if (negative) {
+ seconds = -seconds;
+ nanos = -nanos;
+ }
+ duration->set_seconds(seconds);
+ duration->set_nanos(nanos);
+}
+} // namespace
+
+Duration& operator+=(Duration& d1, const Duration& d2) {
+ d1 = CreateNormalized<Duration>(d1.seconds() + d2.seconds(),
+ d1.nanos() + d2.nanos());
+ return d1;
+}
+
+Duration& operator-=(Duration& d1, const Duration& d2) { // NOLINT
+ d1 = CreateNormalized<Duration>(d1.seconds() - d2.seconds(),
+ d1.nanos() - d2.nanos());
+ return d1;
+}
+
+Duration& operator*=(Duration& d, int64 r) { // NOLINT
+ bool negative;
+ uint128 value;
+ ToUint128(d, &value, &negative);
+ if (r > 0) {
+ value *= static_cast<uint64>(r);
+ } else {
+ negative = !negative;
+ value *= static_cast<uint64>(-r);
+ }
+ ToDuration(value, negative, &d);
+ return d;
+}
+
+Duration& operator*=(Duration& d, double r) { // NOLINT
+ double result = (d.seconds() * 1.0 + 1.0 * d.nanos() / kNanosPerSecond) * r;
+ int64 seconds = static_cast<int64>(result);
+ int32 nanos = static_cast<int32>((result - seconds) * kNanosPerSecond);
+ // Note that we normalize here not just because nanos can have a different
+ // sign from seconds but also that nanos can be any arbitrary value when
+ // overflow happens (i.e., the result is a much larger value than what
+ // int64 can represent).
+ d = CreateNormalized<Duration>(seconds, nanos);
+ return d;
+}
+
+Duration& operator/=(Duration& d, int64 r) { // NOLINT
+ bool negative;
+ uint128 value;
+ ToUint128(d, &value, &negative);
+ if (r > 0) {
+ value /= static_cast<uint64>(r);
+ } else {
+ negative = !negative;
+ value /= static_cast<uint64>(-r);
+ }
+ ToDuration(value, negative, &d);
+ return d;
+}
+
+Duration& operator/=(Duration& d, double r) { // NOLINT
+ return d *= 1.0 / r;
+}
+
+Duration& operator%=(Duration& d1, const Duration& d2) { // NOLINT
+ bool negative1, negative2;
+ uint128 value1, value2;
+ ToUint128(d1, &value1, &negative1);
+ ToUint128(d2, &value2, &negative2);
+ uint128 result = value1 % value2;
+ // When negative values are involved in division, we round the division
+ // result towards zero. With this semantics, sign of the remainder is the
+ // same as the dividend. For example:
+ // -5 / 10 = 0, -5 % 10 = -5
+ // -5 / (-10) = 0, -5 % (-10) = -5
+ // 5 / (-10) = 0, 5 % (-10) = 5
+ ToDuration(result, negative1, &d1);
+ return d1;
+}
+
+int64 operator/(const Duration& d1, const Duration& d2) {
+ bool negative1, negative2;
+ uint128 value1, value2;
+ ToUint128(d1, &value1, &negative1);
+ ToUint128(d2, &value2, &negative2);
+ int64 result = Uint128Low64(value1 / value2);
+ if (negative1 != negative2) {
+ result = -result;
+ }
+ return result;
+}
+
+Timestamp& operator+=(Timestamp& t, const Duration& d) { // NOLINT
+ t = CreateNormalized<Timestamp>(t.seconds() + d.seconds(),
+ t.nanos() + d.nanos());
+ return t;
+}
+
+Timestamp& operator-=(Timestamp& t, const Duration& d) { // NOLINT
+ t = CreateNormalized<Timestamp>(t.seconds() - d.seconds(),
+ t.nanos() - d.nanos());
+ return t;
+}
+
+Duration operator-(const Timestamp& t1, const Timestamp& t2) {
+ return CreateNormalized<Duration>(t1.seconds() - t2.seconds(),
+ t1.nanos() - t2.nanos());
+}
+} // namespace protobuf
+
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.h
new file mode 100644
index 0000000000..1bac089707
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util.h
@@ -0,0 +1,293 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_TIME_UTIL_H__
+#define GOOGLE_PROTOBUF_UTIL_TIME_UTIL_H__
+
+#include <ctime>
+#include <ostream>
+#include <string>
+#ifdef _MSC_VER
+#include <winsock2.h>
+#else
+#include <sys/time.h>
+#endif
+
+#include <google/protobuf/duration.pb.h>
+#include <google/protobuf/timestamp.pb.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+class LIBPROTOBUF_EXPORT TimeUtil {
+ typedef google::protobuf::Timestamp Timestamp;
+ typedef google::protobuf::Duration Duration;
+
+ public:
+ // The min/max Timestamp/Duration values we support.
+ //
+ // For "0001-01-01T00:00:00Z".
+ static const int64 kTimestampMinSeconds = -62135596800LL;
+ // For "9999-12-31T23:59:59.999999999Z".
+ static const int64 kTimestampMaxSeconds = 253402300799LL;
+ static const int64 kDurationMinSeconds = -315576000000LL;
+ static const int64 kDurationMaxSeconds = 315576000000LL;
+
+ // Converts Timestamp to/from RFC 3339 date string format.
+ // Generated output will always be Z-normalized and uses 3, 6 or 9
+ // fractional digits as required to represent the exact time. When
+ // parsing, any fractional digits (or none) and any offset are
+ // accepted as long as they fit into nano-seconds precision.
+ // Note that Timestamp can only represent time from
+ // 0001-01-01T00:00:00Z to 9999-12-31T23:59:59.999999999Z. Converting
+ // a Timestamp outside of this range is undefined behavior.
+ // See https://www.ietf.org/rfc/rfc3339.txt
+ //
+ // Example of generated format:
+ // "1972-01-01T10:00:20.021Z"
+ //
+ // Example of accepted format:
+ // "1972-01-01T10:00:20.021-05:00"
+ static string ToString(const Timestamp& timestamp);
+ static bool FromString(const string& value, Timestamp* timestamp);
+
+ // Converts Duration to/from string format. The string format will contains
+ // 3, 6, or 9 fractional digits depending on the precision required to
+ // represent the exact Duration value. For example:
+ // "1s", "1.010s", "1.000000100s", "-3.100s"
+ // The range that can be represented by Duration is from -315,576,000,000
+ // to +315,576,000,000 inclusive (in seconds).
+ static string ToString(const Duration& duration);
+ static bool FromString(const string& value, Duration* timestamp);
+
+#ifdef GetCurrentTime
+#undef GetCurrentTime // Visual Studio has macro GetCurrentTime
+#endif
+ // Gets the current UTC time.
+ static Timestamp GetCurrentTime();
+ // Returns the Time representing "1970-01-01 00:00:00".
+ static Timestamp GetEpoch();
+
+ // Converts between Duration and integer types. The behavior is undefined if
+ // the input value is not in the valid range of Duration.
+ static Duration NanosecondsToDuration(int64 nanos);
+ static Duration MicrosecondsToDuration(int64 micros);
+ static Duration MillisecondsToDuration(int64 millis);
+ static Duration SecondsToDuration(int64 seconds);
+ static Duration MinutesToDuration(int64 minutes);
+ static Duration HoursToDuration(int64 hours);
+ // Result will be truncated towards zero. For example, "-1.5s" will be
+ // truncated to "-1s", and "1.5s" to "1s" when converting to seconds.
+ // It's undefined behavior if the input duration is not valid or the result
+ // exceeds the range of int64. A duration is not valid if it's not in the
+ // valid range of Duration, or have an invalid nanos value (i.e., larger
+ // than 999999999, less than -999999999, or have a different sign from the
+ // seconds part).
+ static int64 DurationToNanoseconds(const Duration& duration);
+ static int64 DurationToMicroseconds(const Duration& duration);
+ static int64 DurationToMilliseconds(const Duration& duration);
+ static int64 DurationToSeconds(const Duration& duration);
+ static int64 DurationToMinutes(const Duration& duration);
+ static int64 DurationToHours(const Duration& duration);
+ // Creates Timestamp from integer types. The integer value indicates the
+ // time elapsed from Epoch time. The behavior is undefined if the input
+ // value is not in the valid range of Timestamp.
+ static Timestamp NanosecondsToTimestamp(int64 nanos);
+ static Timestamp MicrosecondsToTimestamp(int64 micros);
+ static Timestamp MillisecondsToTimestamp(int64 millis);
+ static Timestamp SecondsToTimestamp(int64 seconds);
+ // Result will be truncated down to the nearest integer value. For example,
+ // with "1969-12-31T23:59:59.9Z", TimestampToMilliseconds() returns -100
+ // and TimestampToSeconds() returns -1. It's undefined behavior if the input
+ // Timestamp is not valid (i.e., its seconds part or nanos part does not fall
+ // in the valid range) or the return value doesn't fit into int64.
+ static int64 TimestampToNanoseconds(const Timestamp& timestamp);
+ static int64 TimestampToMicroseconds(const Timestamp& timestamp);
+ static int64 TimestampToMilliseconds(const Timestamp& timestamp);
+ static int64 TimestampToSeconds(const Timestamp& timestamp);
+
+ // Conversion to/from other time/date types. Note that these types may
+ // have a different precision and time range from Timestamp/Duration.
+ // When converting to a lower precision type, the value will be truncated
+ // to the nearest value that can be represented. If the value is
+ // out of the range of the result type, the return value is undefined.
+ //
+ // Conversion to/from time_t
+ static Timestamp TimeTToTimestamp(time_t value);
+ static time_t TimestampToTimeT(const Timestamp& value);
+
+ // Conversion to/from timeval
+ static Timestamp TimevalToTimestamp(const timeval& value);
+ static timeval TimestampToTimeval(const Timestamp& value);
+ static Duration TimevalToDuration(const timeval& value);
+ static timeval DurationToTimeval(const Duration& value);
+};
+
+} // namespace util
+} // namespace protobuf
+
+
+namespace protobuf {
+// Overloaded operators for Duration.
+//
+// Assignment operators.
+LIBPROTOBUF_EXPORT Duration& operator+=(Duration& d1, const Duration& d2); // NOLINT
+LIBPROTOBUF_EXPORT Duration& operator-=(Duration& d1, const Duration& d2); // NOLINT
+LIBPROTOBUF_EXPORT Duration& operator*=(Duration& d, int64 r); // NOLINT
+LIBPROTOBUF_EXPORT Duration& operator*=(Duration& d, double r); // NOLINT
+LIBPROTOBUF_EXPORT Duration& operator/=(Duration& d, int64 r); // NOLINT
+LIBPROTOBUF_EXPORT Duration& operator/=(Duration& d, double r); // NOLINT
+// Overload for other integer types.
+template <typename T>
+Duration& operator*=(Duration& d, T r) { // NOLINT
+ int64 x = r;
+ return d *= x;
+}
+template <typename T>
+Duration& operator/=(Duration& d, T r) { // NOLINT
+ int64 x = r;
+ return d /= x;
+}
+LIBPROTOBUF_EXPORT Duration& operator%=(Duration& d1, const Duration& d2); // NOLINT
+// Relational operators.
+inline bool operator<(const Duration& d1, const Duration& d2) {
+ if (d1.seconds() == d2.seconds()) {
+ return d1.nanos() < d2.nanos();
+ }
+ return d1.seconds() < d2.seconds();
+}
+inline bool operator>(const Duration& d1, const Duration& d2) {
+ return d2 < d1;
+}
+inline bool operator>=(const Duration& d1, const Duration& d2) {
+ return !(d1 < d2);
+}
+inline bool operator<=(const Duration& d1, const Duration& d2) {
+ return !(d2 < d1);
+}
+inline bool operator==(const Duration& d1, const Duration& d2) {
+ return d1.seconds() == d2.seconds() && d1.nanos() == d2.nanos();
+}
+inline bool operator!=(const Duration& d1, const Duration& d2) {
+ return !(d1 == d2);
+}
+// Additive operators
+inline Duration operator-(const Duration& d) {
+ Duration result;
+ result.set_seconds(-d.seconds());
+ result.set_nanos(-d.nanos());
+ return result;
+}
+inline Duration operator+(const Duration& d1, const Duration& d2) {
+ Duration result = d1;
+ return result += d2;
+}
+inline Duration operator-(const Duration& d1, const Duration& d2) {
+ Duration result = d1;
+ return result -= d2;
+}
+// Multiplicative operators
+template<typename T>
+inline Duration operator*(Duration d, T r) {
+ return d *= r;
+}
+template<typename T>
+inline Duration operator*(T r, Duration d) {
+ return d *= r;
+}
+template<typename T>
+inline Duration operator/(Duration d, T r) {
+ return d /= r;
+}
+LIBPROTOBUF_EXPORT int64 operator/(const Duration& d1, const Duration& d2);
+
+inline Duration operator%(const Duration& d1, const Duration& d2) {
+ Duration result = d1;
+ return result %= d2;
+}
+
+inline ostream& operator<<(ostream& out, const Duration& d) {
+ out << google::protobuf::util::TimeUtil::ToString(d);
+ return out;
+}
+
+// Overloaded operators for Timestamp
+//
+// Assignement operators.
+LIBPROTOBUF_EXPORT Timestamp& operator+=(Timestamp& t, const Duration& d); // NOLINT
+LIBPROTOBUF_EXPORT Timestamp& operator-=(Timestamp& t, const Duration& d); // NOLINT
+// Relational operators.
+inline bool operator<(const Timestamp& t1, const Timestamp& t2) {
+ if (t1.seconds() == t2.seconds()) {
+ return t1.nanos() < t2.nanos();
+ }
+ return t1.seconds() < t2.seconds();
+}
+inline bool operator>(const Timestamp& t1, const Timestamp& t2) {
+ return t2 < t1;
+}
+inline bool operator>=(const Timestamp& t1, const Timestamp& t2) {
+ return !(t1 < t2);
+}
+inline bool operator<=(const Timestamp& t1, const Timestamp& t2) {
+ return !(t2 < t1);
+}
+inline bool operator==(const Timestamp& t1, const Timestamp& t2) {
+ return t1.seconds() == t2.seconds() && t1.nanos() == t2.nanos();
+}
+inline bool operator!=(const Timestamp& t1, const Timestamp& t2) {
+ return !(t1 == t2);
+}
+// Additive operators.
+inline Timestamp operator+(const Timestamp& t, const Duration& d) {
+ Timestamp result = t;
+ return result += d;
+}
+inline Timestamp operator+(const Duration& d, const Timestamp& t) {
+ Timestamp result = t;
+ return result += d;
+}
+inline Timestamp operator-(const Timestamp& t, const Duration& d) {
+ Timestamp result = t;
+ return result -= d;
+}
+LIBPROTOBUF_EXPORT Duration operator-(const Timestamp& t1, const Timestamp& t2);
+
+inline ostream& operator<<(ostream& out, const Timestamp& t) {
+ out << google::protobuf::util::TimeUtil::ToString(t);
+ return out;
+}
+
+} // namespace protobuf
+
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_TIME_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util_test.cc
new file mode 100644
index 0000000000..285740abe1
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/time_util_test.cc
@@ -0,0 +1,380 @@
+// 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.
+
+#include <google/protobuf/util/time_util.h>
+
+#include <ctime>
+
+#include <google/protobuf/timestamp.pb.h>
+#include <google/protobuf/duration.pb.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+
+using google::protobuf::Timestamp;
+using google::protobuf::Duration;
+
+namespace {
+
+TEST(TimeUtilTest, TimestampStringFormat) {
+ Timestamp begin, end;
+ EXPECT_TRUE(TimeUtil::FromString("0001-01-01T00:00:00Z", &begin));
+ EXPECT_EQ(TimeUtil::kTimestampMinSeconds, begin.seconds());
+ EXPECT_EQ(0, begin.nanos());
+ EXPECT_TRUE(TimeUtil::FromString("9999-12-31T23:59:59.999999999Z", &end));
+ EXPECT_EQ(TimeUtil::kTimestampMaxSeconds, end.seconds());
+ EXPECT_EQ(999999999, end.nanos());
+ EXPECT_EQ("0001-01-01T00:00:00Z", TimeUtil::ToString(begin));
+ EXPECT_EQ("9999-12-31T23:59:59.999999999Z", TimeUtil::ToString(end));
+
+ // Test negative timestamps.
+ Timestamp time = TimeUtil::NanosecondsToTimestamp(-1);
+ EXPECT_EQ(-1, time.seconds());
+ // Timestamp's nano part is always non-negative.
+ EXPECT_EQ(999999999, time.nanos());
+ EXPECT_EQ("1969-12-31T23:59:59.999999999Z", TimeUtil::ToString(time));
+
+ // Generated output should contain 3, 6, or 9 fractional digits.
+ EXPECT_EQ("1970-01-01T00:00:00Z",
+ TimeUtil::ToString(TimeUtil::NanosecondsToTimestamp(0)));
+ EXPECT_EQ("1970-01-01T00:00:00.010Z",
+ TimeUtil::ToString(TimeUtil::NanosecondsToTimestamp(10000000)));
+ EXPECT_EQ("1970-01-01T00:00:00.000010Z",
+ TimeUtil::ToString(TimeUtil::NanosecondsToTimestamp(10000)));
+ EXPECT_EQ("1970-01-01T00:00:00.000000010Z",
+ TimeUtil::ToString(TimeUtil::NanosecondsToTimestamp(10)));
+
+ // Parsing accepts an fractional digits as long as they fit into nano
+ // precision.
+ EXPECT_TRUE(TimeUtil::FromString("1970-01-01T00:00:00.1Z", &time));
+ EXPECT_EQ(100000000, TimeUtil::TimestampToNanoseconds(time));
+ EXPECT_TRUE(TimeUtil::FromString("1970-01-01T00:00:00.0001Z", &time));
+ EXPECT_EQ(100000, TimeUtil::TimestampToNanoseconds(time));
+ EXPECT_TRUE(TimeUtil::FromString("1970-01-01T00:00:00.0000001Z", &time));
+ EXPECT_EQ(100, TimeUtil::TimestampToNanoseconds(time));
+
+ // Also accpets offsets.
+ EXPECT_TRUE(TimeUtil::FromString("1970-01-01T00:00:00-08:00", &time));
+ EXPECT_EQ(8 * 3600, TimeUtil::TimestampToSeconds(time));
+}
+
+TEST(TimeUtilTest, DurationStringFormat) {
+ Timestamp begin, end;
+ EXPECT_TRUE(TimeUtil::FromString("0001-01-01T00:00:00Z", &begin));
+ EXPECT_TRUE(TimeUtil::FromString("9999-12-31T23:59:59.999999999Z", &end));
+
+ EXPECT_EQ("315537897599.999999999s", TimeUtil::ToString(end - begin));
+ EXPECT_EQ(999999999, (end - begin).nanos());
+ EXPECT_EQ("-315537897599.999999999s", TimeUtil::ToString(begin - end));
+ EXPECT_EQ(-999999999, (begin - end).nanos());
+
+ // Generated output should contain 3, 6, or 9 fractional digits.
+ EXPECT_EQ("1s", TimeUtil::ToString(TimeUtil::SecondsToDuration(1)));
+ EXPECT_EQ("0.010s", TimeUtil::ToString(TimeUtil::MillisecondsToDuration(10)));
+ EXPECT_EQ("0.000010s",
+ TimeUtil::ToString(TimeUtil::MicrosecondsToDuration(10)));
+ EXPECT_EQ("0.000000010s",
+ TimeUtil::ToString(TimeUtil::NanosecondsToDuration(10)));
+
+ // Parsing accepts an fractional digits as long as they fit into nano
+ // precision.
+ Duration d;
+ EXPECT_TRUE(TimeUtil::FromString("0.1s", &d));
+ EXPECT_EQ(100, TimeUtil::DurationToMilliseconds(d));
+ EXPECT_TRUE(TimeUtil::FromString("0.0001s", &d));
+ EXPECT_EQ(100, TimeUtil::DurationToMicroseconds(d));
+ EXPECT_TRUE(TimeUtil::FromString("0.0000001s", &d));
+ EXPECT_EQ(100, TimeUtil::DurationToNanoseconds(d));
+
+ // Duration must support range from -315,576,000,000s to +315576000000s
+ // which includes negative values.
+ EXPECT_TRUE(TimeUtil::FromString("315576000000.999999999s", &d));
+ EXPECT_EQ(315576000000LL, d.seconds());
+ EXPECT_EQ(999999999, d.nanos());
+ EXPECT_TRUE(TimeUtil::FromString("-315576000000.999999999s", &d));
+ EXPECT_EQ(-315576000000LL, d.seconds());
+ EXPECT_EQ(-999999999, d.nanos());
+}
+
+TEST(TimeUtilTest, GetEpoch) {
+ EXPECT_EQ(0, TimeUtil::TimestampToNanoseconds(TimeUtil::GetEpoch()));
+}
+
+TEST(TimeUtilTest, DurationIntegerConversion) {
+ EXPECT_EQ("0.000000001s",
+ TimeUtil::ToString(TimeUtil::NanosecondsToDuration(1)));
+ EXPECT_EQ("-0.000000001s",
+ TimeUtil::ToString(TimeUtil::NanosecondsToDuration(-1)));
+ EXPECT_EQ("0.000001s",
+ TimeUtil::ToString(TimeUtil::MicrosecondsToDuration(1)));
+ EXPECT_EQ("-0.000001s",
+ TimeUtil::ToString(TimeUtil::MicrosecondsToDuration(-1)));
+ EXPECT_EQ("0.001s", TimeUtil::ToString(TimeUtil::MillisecondsToDuration(1)));
+ EXPECT_EQ("-0.001s",
+ TimeUtil::ToString(TimeUtil::MillisecondsToDuration(-1)));
+ EXPECT_EQ("1s", TimeUtil::ToString(TimeUtil::SecondsToDuration(1)));
+ EXPECT_EQ("-1s", TimeUtil::ToString(TimeUtil::SecondsToDuration(-1)));
+ EXPECT_EQ("60s", TimeUtil::ToString(TimeUtil::MinutesToDuration(1)));
+ EXPECT_EQ("-60s", TimeUtil::ToString(TimeUtil::MinutesToDuration(-1)));
+ EXPECT_EQ("3600s", TimeUtil::ToString(TimeUtil::HoursToDuration(1)));
+ EXPECT_EQ("-3600s", TimeUtil::ToString(TimeUtil::HoursToDuration(-1)));
+
+ EXPECT_EQ(
+ 1, TimeUtil::DurationToNanoseconds(TimeUtil::NanosecondsToDuration(1)));
+ EXPECT_EQ(
+ -1, TimeUtil::DurationToNanoseconds(TimeUtil::NanosecondsToDuration(-1)));
+ EXPECT_EQ(
+ 1, TimeUtil::DurationToMicroseconds(TimeUtil::MicrosecondsToDuration(1)));
+ EXPECT_EQ(-1, TimeUtil::DurationToMicroseconds(
+ TimeUtil::MicrosecondsToDuration(-1)));
+ EXPECT_EQ(
+ 1, TimeUtil::DurationToMilliseconds(TimeUtil::MillisecondsToDuration(1)));
+ EXPECT_EQ(-1, TimeUtil::DurationToMilliseconds(
+ TimeUtil::MillisecondsToDuration(-1)));
+ EXPECT_EQ(1, TimeUtil::DurationToSeconds(TimeUtil::SecondsToDuration(1)));
+ EXPECT_EQ(-1, TimeUtil::DurationToSeconds(TimeUtil::SecondsToDuration(-1)));
+ EXPECT_EQ(1, TimeUtil::DurationToMinutes(TimeUtil::MinutesToDuration(1)));
+ EXPECT_EQ(-1, TimeUtil::DurationToMinutes(TimeUtil::MinutesToDuration(-1)));
+ EXPECT_EQ(1, TimeUtil::DurationToHours(TimeUtil::HoursToDuration(1)));
+ EXPECT_EQ(-1, TimeUtil::DurationToHours(TimeUtil::HoursToDuration(-1)));
+
+ // Test truncation behavior.
+ EXPECT_EQ(1, TimeUtil::DurationToMicroseconds(
+ TimeUtil::NanosecondsToDuration(1999)));
+ // For negative values, Duration will be rounded towards 0.
+ EXPECT_EQ(-1, TimeUtil::DurationToMicroseconds(
+ TimeUtil::NanosecondsToDuration(-1999)));
+}
+
+TEST(TestUtilTest, TimestampIntegerConversion) {
+ EXPECT_EQ("1970-01-01T00:00:00.000000001Z",
+ TimeUtil::ToString(TimeUtil::NanosecondsToTimestamp(1)));
+ EXPECT_EQ("1969-12-31T23:59:59.999999999Z",
+ TimeUtil::ToString(TimeUtil::NanosecondsToTimestamp(-1)));
+ EXPECT_EQ("1970-01-01T00:00:00.000001Z",
+ TimeUtil::ToString(TimeUtil::MicrosecondsToTimestamp(1)));
+ EXPECT_EQ("1969-12-31T23:59:59.999999Z",
+ TimeUtil::ToString(TimeUtil::MicrosecondsToTimestamp(-1)));
+ EXPECT_EQ("1970-01-01T00:00:00.001Z",
+ TimeUtil::ToString(TimeUtil::MillisecondsToTimestamp(1)));
+ EXPECT_EQ("1969-12-31T23:59:59.999Z",
+ TimeUtil::ToString(TimeUtil::MillisecondsToTimestamp(-1)));
+ EXPECT_EQ("1970-01-01T00:00:01Z",
+ TimeUtil::ToString(TimeUtil::SecondsToTimestamp(1)));
+ EXPECT_EQ("1969-12-31T23:59:59Z",
+ TimeUtil::ToString(TimeUtil::SecondsToTimestamp(-1)));
+
+ EXPECT_EQ(
+ 1, TimeUtil::TimestampToNanoseconds(TimeUtil::NanosecondsToTimestamp(1)));
+ EXPECT_EQ(-1, TimeUtil::TimestampToNanoseconds(
+ TimeUtil::NanosecondsToTimestamp(-1)));
+ EXPECT_EQ(1, TimeUtil::TimestampToMicroseconds(
+ TimeUtil::MicrosecondsToTimestamp(1)));
+ EXPECT_EQ(-1, TimeUtil::TimestampToMicroseconds(
+ TimeUtil::MicrosecondsToTimestamp(-1)));
+ EXPECT_EQ(1, TimeUtil::TimestampToMilliseconds(
+ TimeUtil::MillisecondsToTimestamp(1)));
+ EXPECT_EQ(-1, TimeUtil::TimestampToMilliseconds(
+ TimeUtil::MillisecondsToTimestamp(-1)));
+ EXPECT_EQ(1, TimeUtil::TimestampToSeconds(TimeUtil::SecondsToTimestamp(1)));
+ EXPECT_EQ(-1, TimeUtil::TimestampToSeconds(TimeUtil::SecondsToTimestamp(-1)));
+
+ // Test truncation behavior.
+ EXPECT_EQ(1, TimeUtil::TimestampToMicroseconds(
+ TimeUtil::NanosecondsToTimestamp(1999)));
+ // For negative values, Timestamp will be rounded down.
+ // For example, "1969-12-31T23:59:59.5Z" (i.e., -0.5s) rounded to seconds
+ // will be "1969-12-31T23:59:59Z" (i.e., -1s) rather than
+ // "1970-01-01T00:00:00Z" (i.e., 0s).
+ EXPECT_EQ(-2, TimeUtil::TimestampToMicroseconds(
+ TimeUtil::NanosecondsToTimestamp(-1999)));
+}
+
+TEST(TimeUtilTest, TimeTConversion) {
+ time_t value = time(NULL);
+ EXPECT_EQ(value,
+ TimeUtil::TimestampToTimeT(TimeUtil::TimeTToTimestamp(value)));
+ EXPECT_EQ(
+ 1, TimeUtil::TimestampToTimeT(TimeUtil::MillisecondsToTimestamp(1999)));
+}
+
+TEST(TimeUtilTest, TimevalConversion) {
+ timeval value = TimeUtil::TimestampToTimeval(
+ TimeUtil::NanosecondsToTimestamp(1999999999));
+ EXPECT_EQ(1, value.tv_sec);
+ EXPECT_EQ(999999, value.tv_usec);
+ value = TimeUtil::TimestampToTimeval(
+ TimeUtil::NanosecondsToTimestamp(-1999999999));
+ EXPECT_EQ(-2, value.tv_sec);
+ EXPECT_EQ(0, value.tv_usec);
+
+ value =
+ TimeUtil::DurationToTimeval(TimeUtil::NanosecondsToDuration(1999999999));
+ EXPECT_EQ(1, value.tv_sec);
+ EXPECT_EQ(999999, value.tv_usec);
+ value =
+ TimeUtil::DurationToTimeval(TimeUtil::NanosecondsToDuration(-1999999999));
+ EXPECT_EQ(-2, value.tv_sec);
+ EXPECT_EQ(1, value.tv_usec);
+}
+
+TEST(TimeUtilTest, DurationOperators) {
+ Duration one_second = TimeUtil::SecondsToDuration(1);
+ Duration one_nano = TimeUtil::NanosecondsToDuration(1);
+
+ // Test +/-
+ Duration a = one_second;
+ a += one_second;
+ a -= one_nano;
+ EXPECT_EQ("1.999999999s", TimeUtil::ToString(a));
+ Duration b = -a;
+ EXPECT_EQ("-1.999999999s", TimeUtil::ToString(b));
+ EXPECT_EQ("3.999999998s", TimeUtil::ToString(a + a));
+ EXPECT_EQ("0s", TimeUtil::ToString(a + b));
+ EXPECT_EQ("0s", TimeUtil::ToString(b + a));
+ EXPECT_EQ("-3.999999998s", TimeUtil::ToString(b + b));
+ EXPECT_EQ("3.999999998s", TimeUtil::ToString(a - b));
+ EXPECT_EQ("0s", TimeUtil::ToString(a - a));
+ EXPECT_EQ("0s", TimeUtil::ToString(b - b));
+ EXPECT_EQ("-3.999999998s", TimeUtil::ToString(b - a));
+
+ // Test *
+ EXPECT_EQ(a + a, a * 2);
+ EXPECT_EQ(b + b, a * (-2));
+ EXPECT_EQ(b + b, b * 2);
+ EXPECT_EQ(a + a, b * (-2));
+ EXPECT_EQ("0.999999999s", TimeUtil::ToString(a * 0.5));
+ EXPECT_EQ("-0.999999999s", TimeUtil::ToString(b * 0.5));
+ // Multiplication should not overflow if the result fits into the supported
+ // range of Duration (intermediate result may be larger than int64).
+ EXPECT_EQ("315575999684.424s",
+ TimeUtil::ToString((one_second - one_nano) * 315576000000LL));
+ EXPECT_EQ("-315575999684.424s",
+ TimeUtil::ToString((one_nano - one_second) * 315576000000LL));
+ EXPECT_EQ("-315575999684.424s",
+ TimeUtil::ToString((one_second - one_nano) * (-315576000000LL)));
+
+ // Test / and %
+ EXPECT_EQ("0.999999999s", TimeUtil::ToString(a / 2));
+ EXPECT_EQ("-0.999999999s", TimeUtil::ToString(b / 2));
+ Duration large = TimeUtil::SecondsToDuration(315576000000LL) - one_nano;
+ // We have to handle division with values beyond 64 bits.
+ EXPECT_EQ("0.999999999s", TimeUtil::ToString(large / 315576000000LL));
+ EXPECT_EQ("-0.999999999s", TimeUtil::ToString((-large) / 315576000000LL));
+ EXPECT_EQ("-0.999999999s", TimeUtil::ToString(large / (-315576000000LL)));
+ Duration large2 = large + one_nano;
+ EXPECT_EQ(large, large % large2);
+ EXPECT_EQ(-large, (-large) % large2);
+ EXPECT_EQ(large, large % (-large2));
+ EXPECT_EQ(one_nano, large2 % large);
+ EXPECT_EQ(-one_nano, (-large2) % large);
+ EXPECT_EQ(one_nano, large2 % (-large));
+ // Some corner cases about negative values.
+ //
+ // (-5) / 2 = -2, remainder = -1
+ // (-5) / (-2) = 2, remainder = -1
+ a = TimeUtil::NanosecondsToDuration(-5);
+ EXPECT_EQ(TimeUtil::NanosecondsToDuration(-2), a / 2);
+ EXPECT_EQ(TimeUtil::NanosecondsToDuration(2), a / (-2));
+ b = TimeUtil::NanosecondsToDuration(2);
+ EXPECT_EQ(-2, a / b);
+ EXPECT_EQ(TimeUtil::NanosecondsToDuration(-1), a % b);
+ EXPECT_EQ(2, a / (-b));
+ EXPECT_EQ(TimeUtil::NanosecondsToDuration(-1), a % (-b));
+
+ // Test relational operators.
+ EXPECT_TRUE(one_nano < one_second);
+ EXPECT_FALSE(one_second < one_second);
+ EXPECT_FALSE(one_second < one_nano);
+ EXPECT_FALSE(-one_nano < -one_second);
+ EXPECT_FALSE(-one_second < -one_second);
+ EXPECT_TRUE(-one_second < -one_nano);
+ EXPECT_TRUE(-one_nano < one_nano);
+ EXPECT_FALSE(one_nano < -one_nano);
+
+ EXPECT_FALSE(one_nano > one_second);
+ EXPECT_FALSE(one_nano > one_nano);
+ EXPECT_TRUE(one_second > one_nano);
+
+ EXPECT_FALSE(one_nano >= one_second);
+ EXPECT_TRUE(one_nano >= one_nano);
+ EXPECT_TRUE(one_second >= one_nano);
+
+ EXPECT_TRUE(one_nano <= one_second);
+ EXPECT_TRUE(one_nano <= one_nano);
+ EXPECT_FALSE(one_second <= one_nano);
+
+ EXPECT_TRUE(one_nano == one_nano);
+ EXPECT_FALSE(one_nano == one_second);
+
+ EXPECT_FALSE(one_nano != one_nano);
+ EXPECT_TRUE(one_nano != one_second);
+}
+
+TEST(TimeUtilTest, TimestampOperators) {
+ Timestamp begin, end;
+ EXPECT_TRUE(TimeUtil::FromString("0001-01-01T00:00:00Z", &begin));
+ EXPECT_TRUE(TimeUtil::FromString("9999-12-31T23:59:59.999999999Z", &end));
+ Duration d = end - begin;
+ EXPECT_TRUE(end == begin + d);
+ EXPECT_TRUE(end == d + begin);
+ EXPECT_TRUE(begin == end - d);
+
+ // Test relational operators
+ Timestamp t1 = begin + d / 4;
+ Timestamp t2 = end - d / 4;
+ EXPECT_TRUE(t1 < t2);
+ EXPECT_FALSE(t1 < t1);
+ EXPECT_FALSE(t2 < t1);
+ EXPECT_FALSE(t1 > t2);
+ EXPECT_FALSE(t1 > t1);
+ EXPECT_TRUE(t2 > t1);
+ EXPECT_FALSE(t1 >= t2);
+ EXPECT_TRUE(t1 >= t1);
+ EXPECT_TRUE(t2 >= t1);
+ EXPECT_TRUE(t1 <= t2);
+ EXPECT_TRUE(t1 <= t1);
+ EXPECT_FALSE(t2 <= t1);
+
+ EXPECT_FALSE(t1 == t2);
+ EXPECT_TRUE(t1 == t1);
+ EXPECT_FALSE(t2 == t1);
+ EXPECT_TRUE(t1 != t2);
+ EXPECT_FALSE(t1 != t1);
+ EXPECT_TRUE(t2 != t1);
+}
+
+} // namespace
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver.h
new file mode 100644
index 0000000000..77d4416a71
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver.h
@@ -0,0 +1,75 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_TYPE_RESOLVER_H__
+#define GOOGLE_PROTOBUF_UTIL_TYPE_RESOLVER_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/status.h>
+
+
+namespace google {
+namespace protobuf {
+class Type;
+class Enum;
+} // namespace protobuf
+
+
+namespace protobuf {
+class DescriptorPool;
+namespace util {
+
+// Abstract interface for a type resovler.
+//
+// Implementations of this interface must be thread-safe.
+class LIBPROTOBUF_EXPORT TypeResolver {
+ public:
+ TypeResolver() {}
+ virtual ~TypeResolver() {}
+
+ // Resolves a type url for a message type.
+ virtual util::Status ResolveMessageType(
+ const string& type_url, google::protobuf::Type* message_type) = 0;
+
+ // Resolves a type url for an enum type.
+ virtual util::Status ResolveEnumType(const string& type_url,
+ google::protobuf::Enum* enum_type) = 0;
+
+ private:
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TypeResolver);
+};
+
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_TYPE_RESOLVER_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.cc
new file mode 100644
index 0000000000..963939032a
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.cc
@@ -0,0 +1,259 @@
+// 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.
+
+#include <google/protobuf/util/type_resolver_util.h>
+
+#include <google/protobuf/type.pb.h>
+#include <google/protobuf/wrappers.pb.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/util/internal/utility.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/stubs/strutil.h>
+#include <google/protobuf/stubs/status.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace {
+using google::protobuf::BoolValue;
+using google::protobuf::Enum;
+using google::protobuf::EnumValue;
+using google::protobuf::Field;
+using google::protobuf::Option;
+using google::protobuf::Type;
+
+using util::Status;
+using util::error::INVALID_ARGUMENT;
+using util::error::NOT_FOUND;
+
+bool SplitTypeUrl(const string& type_url, string* url_prefix,
+ string* message_name) {
+ size_t pos = type_url.find_last_of("/");
+ if (pos == string::npos) {
+ return false;
+ }
+ *url_prefix = type_url.substr(0, pos);
+ *message_name = type_url.substr(pos + 1);
+ return true;
+}
+
+class DescriptorPoolTypeResolver : public TypeResolver {
+ public:
+ DescriptorPoolTypeResolver(const string& url_prefix,
+ const DescriptorPool* pool)
+ : url_prefix_(url_prefix), pool_(pool) {}
+
+ Status ResolveMessageType(const string& type_url, Type* type) {
+ string url_prefix, message_name;
+ if (!SplitTypeUrl(type_url, &url_prefix, &message_name) ||
+ url_prefix != url_prefix_) {
+ return Status(INVALID_ARGUMENT,
+ StrCat("Invalid type URL, type URLs must be of the form '",
+ url_prefix_, "/<typename>', got: ", type_url));
+ }
+ if (url_prefix != url_prefix_) {
+ return Status(INVALID_ARGUMENT,
+ "Cannot resolve types from URL: " + url_prefix);
+ }
+ const Descriptor* descriptor = pool_->FindMessageTypeByName(message_name);
+ if (descriptor == NULL) {
+ return Status(NOT_FOUND,
+ "Invalid type URL, unknown type: " + message_name);
+ }
+ ConvertDescriptor(descriptor, type);
+ return Status();
+ }
+
+ Status ResolveEnumType(const string& type_url, Enum* enum_type) {
+ string url_prefix, type_name;
+ if (!SplitTypeUrl(type_url, &url_prefix, &type_name) ||
+ url_prefix != url_prefix_) {
+ return Status(INVALID_ARGUMENT,
+ StrCat("Invalid type URL, type URLs must be of the form '",
+ url_prefix_, "/<typename>', got: ", type_url));
+ }
+ if (url_prefix != url_prefix_) {
+ return Status(INVALID_ARGUMENT,
+ "Cannot resolve types from URL: " + url_prefix);
+ }
+ const EnumDescriptor* descriptor = pool_->FindEnumTypeByName(type_name);
+ if (descriptor == NULL) {
+ return Status(NOT_FOUND, "Invalid type URL, unknown type: " + type_name);
+ }
+ ConvertEnumDescriptor(descriptor, enum_type);
+ return Status();
+ }
+
+ private:
+ void ConvertDescriptor(const Descriptor* descriptor, Type* type) {
+ type->Clear();
+ type->set_name(descriptor->full_name());
+ for (int i = 0; i < descriptor->field_count(); ++i) {
+ const FieldDescriptor* field = descriptor->field(i);
+ if (field->type() == FieldDescriptor::TYPE_GROUP) {
+ // Group fields cannot be represented with Type. We discard them.
+ continue;
+ }
+ ConvertFieldDescriptor(descriptor->field(i), type->add_fields());
+ }
+ for (int i = 0; i < descriptor->oneof_decl_count(); ++i) {
+ type->add_oneofs(descriptor->oneof_decl(i)->name());
+ }
+ type->mutable_source_context()->set_file_name(descriptor->file()->name());
+ ConvertMessageOptions(descriptor->options(), type->mutable_options());
+ }
+
+ void ConvertMessageOptions(const MessageOptions& options,
+ RepeatedPtrField<Option>* output) {
+ if (options.map_entry()) {
+ Option* option = output->Add();
+ option->set_name("map_entry");
+ BoolValue value;
+ value.set_value(true);
+ option->mutable_value()->PackFrom(value);
+ }
+
+ // TODO(xiaofeng): Set other "options"?
+ }
+
+ void ConvertFieldDescriptor(const FieldDescriptor* descriptor, Field* field) {
+ field->set_kind(static_cast<Field::Kind>(descriptor->type()));
+ switch (descriptor->label()) {
+ case FieldDescriptor::LABEL_OPTIONAL:
+ field->set_cardinality(Field::CARDINALITY_OPTIONAL);
+ break;
+ case FieldDescriptor::LABEL_REPEATED:
+ field->set_cardinality(Field::CARDINALITY_REPEATED);
+ break;
+ case FieldDescriptor::LABEL_REQUIRED:
+ field->set_cardinality(Field::CARDINALITY_REQUIRED);
+ break;
+ }
+ field->set_number(descriptor->number());
+ field->set_name(descriptor->name());
+ field->set_json_name(descriptor->json_name());
+ if (descriptor->has_default_value()) {
+ field->set_default_value(DefaultValueAsString(descriptor));
+ }
+ if (descriptor->type() == FieldDescriptor::TYPE_MESSAGE) {
+ field->set_type_url(GetTypeUrl(descriptor->message_type()));
+ } else if (descriptor->type() == FieldDescriptor::TYPE_ENUM) {
+ field->set_type_url(GetTypeUrl(descriptor->enum_type()));
+ }
+ if (descriptor->containing_oneof() != NULL) {
+ field->set_oneof_index(descriptor->containing_oneof()->index() + 1);
+ }
+ if (descriptor->is_packed()) {
+ field->set_packed(true);
+ }
+
+ // TODO(xiaofeng): Set other field "options"?
+ }
+
+ void ConvertEnumDescriptor(const EnumDescriptor* descriptor,
+ Enum* enum_type) {
+ enum_type->Clear();
+ enum_type->set_name(descriptor->full_name());
+ enum_type->mutable_source_context()->set_file_name(
+ descriptor->file()->name());
+ for (int i = 0; i < descriptor->value_count(); ++i) {
+ const EnumValueDescriptor* value_descriptor = descriptor->value(i);
+ EnumValue* value = enum_type->mutable_enumvalue()->Add();
+ value->set_name(value_descriptor->name());
+ value->set_number(value_descriptor->number());
+
+ // TODO(xiaofeng): Set EnumValue options.
+ }
+ // TODO(xiaofeng): Set Enum "options".
+ }
+
+ string GetTypeUrl(const Descriptor* descriptor) {
+ return url_prefix_ + "/" + descriptor->full_name();
+ }
+
+ string GetTypeUrl(const EnumDescriptor* descriptor) {
+ return url_prefix_ + "/" + descriptor->full_name();
+ }
+
+ string DefaultValueAsString(const FieldDescriptor* descriptor) {
+ switch (descriptor->cpp_type()) {
+ case FieldDescriptor::CPPTYPE_INT32:
+ return SimpleItoa(descriptor->default_value_int32());
+ break;
+ case FieldDescriptor::CPPTYPE_INT64:
+ return SimpleItoa(descriptor->default_value_int64());
+ break;
+ case FieldDescriptor::CPPTYPE_UINT32:
+ return SimpleItoa(descriptor->default_value_uint32());
+ break;
+ case FieldDescriptor::CPPTYPE_UINT64:
+ return SimpleItoa(descriptor->default_value_uint64());
+ break;
+ case FieldDescriptor::CPPTYPE_FLOAT:
+ return SimpleFtoa(descriptor->default_value_float());
+ break;
+ case FieldDescriptor::CPPTYPE_DOUBLE:
+ return SimpleDtoa(descriptor->default_value_double());
+ break;
+ case FieldDescriptor::CPPTYPE_BOOL:
+ return descriptor->default_value_bool() ? "true" : "false";
+ break;
+ case FieldDescriptor::CPPTYPE_STRING:
+ if (descriptor->type() == FieldDescriptor::TYPE_BYTES) {
+ return CEscape(descriptor->default_value_string());
+ } else {
+ return descriptor->default_value_string();
+ }
+ break;
+ case FieldDescriptor::CPPTYPE_ENUM:
+ return descriptor->default_value_enum()->name();
+ break;
+ case FieldDescriptor::CPPTYPE_MESSAGE:
+ GOOGLE_LOG(DFATAL) << "Messages can't have default values!";
+ break;
+ }
+ return "";
+ }
+
+ string url_prefix_;
+ const DescriptorPool* pool_;
+};
+
+} // namespace
+
+TypeResolver* NewTypeResolverForDescriptorPool(const string& url_prefix,
+ const DescriptorPool* pool) {
+ return new DescriptorPoolTypeResolver(url_prefix, pool);
+}
+
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.h b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.h
new file mode 100644
index 0000000000..c0ef3c1af9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util.h
@@ -0,0 +1,52 @@
+// 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.
+
+#ifndef GOOGLE_PROTOBUF_UTIL_TYPE_RESOLVER_UTIL_H__
+#define GOOGLE_PROTOBUF_UTIL_TYPE_RESOLVER_UTIL_H__
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+namespace google {
+namespace protobuf {
+class DescriptorPool;
+namespace util {
+class TypeResolver;
+
+// Creates a TypeResolver that serves type information in the given descriptor
+// pool. Caller takes ownership of the returned TypeResolver.
+LIBPROTOBUF_EXPORT TypeResolver* NewTypeResolverForDescriptorPool(
+ const string& url_prefix, const DescriptorPool* pool);
+
+} // namespace util
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_UTIL_TYPE_RESOLVER_UTIL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util_test.cc b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util_test.cc
new file mode 100644
index 0000000000..8a0bf65297
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/util/type_resolver_util_test.cc
@@ -0,0 +1,352 @@
+// 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.
+
+#include <google/protobuf/util/type_resolver_util.h>
+
+#include <limits>
+#include <memory>
+#ifndef _SHARED_PTR_H
+#include <google/protobuf/stubs/shared_ptr.h>
+#endif
+#include <string>
+#include <vector>
+
+#include <google/protobuf/type.pb.h>
+#include <google/protobuf/wrappers.pb.h>
+#include <google/protobuf/map_unittest.pb.h>
+#include <google/protobuf/test_util.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/util/json_format_proto3.pb.h>
+#include <google/protobuf/util/type_resolver.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+
+namespace google {
+namespace protobuf {
+namespace util {
+namespace {
+using google::protobuf::Type;
+using google::protobuf::Enum;
+using google::protobuf::Field;
+using google::protobuf::Option;
+using google::protobuf::BoolValue;
+
+static const char kUrlPrefix[] = "type.googleapis.com";
+
+class DescriptorPoolTypeResolverTest : public testing::Test {
+ public:
+ DescriptorPoolTypeResolverTest() {
+ resolver_.reset(NewTypeResolverForDescriptorPool(
+ kUrlPrefix, DescriptorPool::generated_pool()));
+ }
+
+ const Field* FindField(const Type& type, const string& name) {
+ for (int i = 0; i < type.fields_size(); ++i) {
+ const Field& field = type.fields(i);
+ if (field.name() == name) {
+ return &field;
+ }
+ }
+ return NULL;
+ }
+
+ bool HasField(const Type& type, const string& name) {
+ return FindField(type, name) != NULL;
+ }
+
+ bool HasField(const Type& type, Field::Cardinality cardinality,
+ Field::Kind kind, const string& name, int number) {
+ const Field* field = FindField(type, name);
+ if (field == NULL) {
+ return false;
+ }
+ return field->cardinality() == cardinality &&
+ field->kind() == kind && field->number() == number;
+ }
+
+ bool CheckFieldTypeUrl(const Type& type, const string& name,
+ const string& type_url) {
+ const Field* field = FindField(type, name);
+ if (field == NULL) {
+ return false;
+ }
+ return field->type_url() == type_url;
+ }
+
+ bool FieldInOneof(const Type& type, const string& name,
+ const string& oneof_name) {
+ const Field* field = FindField(type, name);
+ if (field == NULL || field->oneof_index() <= 0 ||
+ field->oneof_index() > type.oneofs_size()) {
+ return false;
+ }
+ return type.oneofs(field->oneof_index() - 1) == oneof_name;
+ }
+
+ bool IsPacked(const Type& type, const string& name) {
+ const Field* field = FindField(type, name);
+ if (field == NULL) {
+ return false;
+ }
+ return field->packed();
+ }
+
+ bool EnumHasValue(const Enum& type, const string& name, int number) {
+ for (int i = 0; i < type.enumvalue_size(); ++i) {
+ if (type.enumvalue(i).name() == name &&
+ type.enumvalue(i).number() == number) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ bool HasBoolOption(const RepeatedPtrField<Option>& options,
+ const string& name, bool value) {
+ for (int i = 0; i < options.size(); ++i) {
+ const Option& option = options.Get(i);
+ if (option.name() == name) {
+ BoolValue bool_value;
+ if (option.value().UnpackTo(&bool_value) &&
+ bool_value.value() == value) {
+ return true;
+ }
+ }
+ }
+ return false;
+ }
+
+ string GetTypeUrl(string full_name) {
+ return kUrlPrefix + string("/") + full_name;
+ }
+
+ template<typename T>
+ string GetTypeUrl() {
+ return GetTypeUrl(T::descriptor()->full_name());
+ }
+
+ protected:
+ google::protobuf::scoped_ptr<TypeResolver> resolver_;
+};
+
+TEST_F(DescriptorPoolTypeResolverTest, TestAllTypes) {
+ Type type;
+ ASSERT_TRUE(resolver_->ResolveMessageType(
+ GetTypeUrl<protobuf_unittest::TestAllTypes>(), &type).ok());
+ // Check all optional fields.
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_INT32, "optional_int32", 1));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_INT64, "optional_int64", 2));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_UINT32, "optional_uint32", 3));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_UINT64, "optional_uint64", 4));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_SINT32, "optional_sint32", 5));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_SINT64, "optional_sint64", 6));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_FIXED32, "optional_fixed32", 7));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_FIXED64, "optional_fixed64", 8));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_SFIXED32, "optional_sfixed32", 9));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_SFIXED64, "optional_sfixed64", 10));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_FLOAT, "optional_float", 11));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_DOUBLE, "optional_double", 12));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_BOOL, "optional_bool", 13));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_STRING, "optional_string", 14));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_BYTES, "optional_bytes", 15));
+
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_MESSAGE, "optional_nested_message", 18));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_MESSAGE, "optional_foreign_message", 19));
+
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "optional_nested_message",
+ GetTypeUrl<protobuf_unittest::TestAllTypes::NestedMessage>()));
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "optional_foreign_message",
+ GetTypeUrl<protobuf_unittest::ForeignMessage>()));
+
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_ENUM, "optional_nested_enum", 21));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_ENUM, "optional_foreign_enum", 22));
+
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "optional_nested_enum",
+ GetTypeUrl("protobuf_unittest.TestAllTypes.NestedEnum")));
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "optional_foreign_enum",
+ GetTypeUrl("protobuf_unittest.ForeignEnum")));
+
+ // Check all repeated fields.
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_INT32, "repeated_int32", 31));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_INT64, "repeated_int64", 32));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_UINT32, "repeated_uint32", 33));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_UINT64, "repeated_uint64", 34));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_SINT32, "repeated_sint32", 35));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_SINT64, "repeated_sint64", 36));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_FIXED32, "repeated_fixed32", 37));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_FIXED64, "repeated_fixed64", 38));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_SFIXED32, "repeated_sfixed32", 39));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_SFIXED64, "repeated_sfixed64", 40));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_FLOAT, "repeated_float", 41));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_DOUBLE, "repeated_double", 42));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_BOOL, "repeated_bool", 43));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_STRING, "repeated_string", 44));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_BYTES, "repeated_bytes", 45));
+
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_MESSAGE, "repeated_nested_message", 48));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_MESSAGE, "repeated_foreign_message", 49));
+
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "repeated_nested_message",
+ GetTypeUrl<protobuf_unittest::TestAllTypes::NestedMessage>()));
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "repeated_foreign_message",
+ GetTypeUrl<protobuf_unittest::ForeignMessage>()));
+
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_ENUM, "repeated_nested_enum", 51));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_ENUM, "repeated_foreign_enum", 52));
+
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "repeated_nested_enum",
+ GetTypeUrl("protobuf_unittest.TestAllTypes.NestedEnum")));
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "repeated_foreign_enum",
+ GetTypeUrl("protobuf_unittest.ForeignEnum")));
+
+ // Groups are discarded when converting to Type.
+ const Descriptor* descriptor = protobuf_unittest::TestAllTypes::descriptor();
+ EXPECT_TRUE(descriptor->FindFieldByName("optionalgroup") != NULL);
+ EXPECT_TRUE(descriptor->FindFieldByName("repeatedgroup") != NULL);
+ ASSERT_FALSE(HasField(type, "optionalgroup"));
+ ASSERT_FALSE(HasField(type, "repeatedgroup"));
+}
+
+TEST_F(DescriptorPoolTypeResolverTest, TestPackedField) {
+ Type type;
+ ASSERT_TRUE(resolver_->ResolveMessageType(
+ GetTypeUrl<protobuf_unittest::TestPackedTypes>(), &type).ok());
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_INT32, "packed_int32", 90));
+ EXPECT_TRUE(IsPacked(type, "packed_int32"));
+}
+
+TEST_F(DescriptorPoolTypeResolverTest, TestOneof) {
+ Type type;
+ ASSERT_TRUE(resolver_->ResolveMessageType(
+ GetTypeUrl<protobuf_unittest::TestAllTypes>(), &type).ok());
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_UINT32, "oneof_uint32", 111));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_MESSAGE, "oneof_nested_message", 112));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_STRING, "oneof_string", 113));
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_OPTIONAL,
+ Field::TYPE_BYTES, "oneof_bytes", 114));
+ EXPECT_TRUE(FieldInOneof(type, "oneof_uint32", "oneof_field"));
+ EXPECT_TRUE(FieldInOneof(type, "oneof_nested_message", "oneof_field"));
+ EXPECT_TRUE(FieldInOneof(type, "oneof_string", "oneof_field"));
+ EXPECT_TRUE(FieldInOneof(type, "oneof_bytes", "oneof_field"));
+}
+
+TEST_F(DescriptorPoolTypeResolverTest, TestMap) {
+ Type type;
+ ASSERT_TRUE(resolver_->ResolveMessageType(
+ GetTypeUrl<protobuf_unittest::TestMap>(), &type).ok());
+ EXPECT_TRUE(HasField(type, Field::CARDINALITY_REPEATED,
+ Field::TYPE_MESSAGE, "map_int32_int32", 1));
+ EXPECT_TRUE(CheckFieldTypeUrl(
+ type, "map_int32_int32",
+ GetTypeUrl("protobuf_unittest.TestMap.MapInt32Int32Entry")));
+
+ ASSERT_TRUE(resolver_->ResolveMessageType(
+ GetTypeUrl("protobuf_unittest.TestMap.MapInt32Int32Entry"),
+ &type).ok());
+ EXPECT_TRUE(HasBoolOption(type.options(), "map_entry", true));
+}
+
+TEST_F(DescriptorPoolTypeResolverTest, TestEnum) {
+ Enum type;
+ ASSERT_TRUE(resolver_->ResolveEnumType(
+ GetTypeUrl("protobuf_unittest.TestAllTypes.NestedEnum"), &type).ok());
+ EnumHasValue(type, "FOO", 1);
+ EnumHasValue(type, "BAR", 2);
+ EnumHasValue(type, "BAZ", 3);
+ EnumHasValue(type, "NEG", -1);
+}
+
+TEST_F(DescriptorPoolTypeResolverTest, TestJsonName) {
+ Type type;
+ ASSERT_TRUE(resolver_->ResolveMessageType(
+ GetTypeUrl<protobuf_unittest::TestAllTypes>(), &type)
+ .ok());
+ EXPECT_EQ("optionalInt32", FindField(type, "optional_int32")->json_name());
+
+ ASSERT_TRUE(resolver_->ResolveMessageType(
+ GetTypeUrl<proto3::TestCustomJsonName>(), &type)
+ .ok());
+ EXPECT_EQ("@value", FindField(type, "value")->json_name());
+}
+
+} // namespace
+} // namespace util
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/well_known_types_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/well_known_types_unittest.cc
new file mode 100644
index 0000000000..c9a9aa10ec
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/well_known_types_unittest.cc
@@ -0,0 +1,60 @@
+// 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.
+#include <google/protobuf/unittest_well_known_types.pb.h>
+
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+namespace {
+
+// This test only checks whether well-known types are included in protobuf
+// runtime library. The test passes if it compiles.
+TEST(WellKnownTypesTest, AllKnownTypesAreIncluded) {
+ protobuf_unittest::TestWellKnownTypes message;
+ EXPECT_EQ(0, message.any_field().ByteSize());
+ EXPECT_EQ(0, message.api_field().ByteSize());
+ EXPECT_EQ(0, message.duration_field().ByteSize());
+ EXPECT_EQ(0, message.empty_field().ByteSize());
+ EXPECT_EQ(0, message.field_mask_field().ByteSize());
+ EXPECT_EQ(0, message.source_context_field().ByteSize());
+ EXPECT_EQ(0, message.struct_field().ByteSize());
+ EXPECT_EQ(0, message.timestamp_field().ByteSize());
+ EXPECT_EQ(0, message.type_field().ByteSize());
+ EXPECT_EQ(0, message.int32_field().ByteSize());
+}
+
+} // namespace
+
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wire_format.cc b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format.cc
new file mode 100644
index 0000000000..5ee4e25d49
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format.cc
@@ -0,0 +1,1133 @@
+// 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.
+
+#include <stack>
+#include <string>
+#include <vector>
+
+#include <google/protobuf/wire_format.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/unknown_field_set.h>
+
+
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// ===================================================================
+
+bool UnknownFieldSetFieldSkipper::SkipField(
+ io::CodedInputStream* input, uint32 tag) {
+ return WireFormat::SkipField(input, tag, unknown_fields_);
+}
+
+bool UnknownFieldSetFieldSkipper::SkipMessage(io::CodedInputStream* input) {
+ return WireFormat::SkipMessage(input, unknown_fields_);
+}
+
+void UnknownFieldSetFieldSkipper::SkipUnknownEnum(
+ int field_number, int value) {
+ unknown_fields_->AddVarint(field_number, value);
+}
+
+bool WireFormat::SkipField(io::CodedInputStream* input, uint32 tag,
+ UnknownFieldSet* unknown_fields) {
+ int number = WireFormatLite::GetTagFieldNumber(tag);
+
+ switch (WireFormatLite::GetTagWireType(tag)) {
+ case WireFormatLite::WIRETYPE_VARINT: {
+ uint64 value;
+ if (!input->ReadVarint64(&value)) return false;
+ if (unknown_fields != NULL) unknown_fields->AddVarint(number, value);
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_FIXED64: {
+ uint64 value;
+ if (!input->ReadLittleEndian64(&value)) return false;
+ if (unknown_fields != NULL) unknown_fields->AddFixed64(number, value);
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_LENGTH_DELIMITED: {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ if (unknown_fields == NULL) {
+ if (!input->Skip(length)) return false;
+ } else {
+ if (!input->ReadString(unknown_fields->AddLengthDelimited(number),
+ length)) {
+ return false;
+ }
+ }
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_START_GROUP: {
+ if (!input->IncrementRecursionDepth()) return false;
+ if (!SkipMessage(input, (unknown_fields == NULL) ?
+ NULL : unknown_fields->AddGroup(number))) {
+ return false;
+ }
+ input->DecrementRecursionDepth();
+ // Check that the ending tag matched the starting tag.
+ if (!input->LastTagWas(WireFormatLite::MakeTag(
+ WireFormatLite::GetTagFieldNumber(tag),
+ WireFormatLite::WIRETYPE_END_GROUP))) {
+ return false;
+ }
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_END_GROUP: {
+ return false;
+ }
+ case WireFormatLite::WIRETYPE_FIXED32: {
+ uint32 value;
+ if (!input->ReadLittleEndian32(&value)) return false;
+ if (unknown_fields != NULL) unknown_fields->AddFixed32(number, value);
+ return true;
+ }
+ default: {
+ return false;
+ }
+ }
+}
+
+bool WireFormat::SkipMessage(io::CodedInputStream* input,
+ UnknownFieldSet* unknown_fields) {
+ while (true) {
+ uint32 tag = input->ReadTag();
+ if (tag == 0) {
+ // End of input. This is a valid place to end, so return true.
+ return true;
+ }
+
+ WireFormatLite::WireType wire_type = WireFormatLite::GetTagWireType(tag);
+
+ if (wire_type == WireFormatLite::WIRETYPE_END_GROUP) {
+ // Must be the end of the message.
+ return true;
+ }
+
+ if (!SkipField(input, tag, unknown_fields)) return false;
+ }
+}
+
+bool WireFormat::ReadPackedEnumPreserveUnknowns(io::CodedInputStream* input,
+ uint32 field_number,
+ bool (*is_valid)(int),
+ UnknownFieldSet* unknown_fields,
+ RepeatedField<int>* values) {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ io::CodedInputStream::Limit limit = input->PushLimit(length);
+ while (input->BytesUntilLimit() > 0) {
+ int value;
+ if (!google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, WireFormatLite::TYPE_ENUM>(input, &value)) {
+ return false;
+ }
+ if (is_valid == NULL || is_valid(value)) {
+ values->Add(value);
+ } else {
+ unknown_fields->AddVarint(field_number, value);
+ }
+ }
+ input->PopLimit(limit);
+ return true;
+}
+
+
+void WireFormat::SerializeUnknownFields(const UnknownFieldSet& unknown_fields,
+ io::CodedOutputStream* output) {
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ const UnknownField& field = unknown_fields.field(i);
+ switch (field.type()) {
+ case UnknownField::TYPE_VARINT:
+ output->WriteVarint32(WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_VARINT));
+ output->WriteVarint64(field.varint());
+ break;
+ case UnknownField::TYPE_FIXED32:
+ output->WriteVarint32(WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_FIXED32));
+ output->WriteLittleEndian32(field.fixed32());
+ break;
+ case UnknownField::TYPE_FIXED64:
+ output->WriteVarint32(WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_FIXED64));
+ output->WriteLittleEndian64(field.fixed64());
+ break;
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ output->WriteVarint32(WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED));
+ output->WriteVarint32(field.length_delimited().size());
+ output->WriteRawMaybeAliased(field.length_delimited().data(),
+ field.length_delimited().size());
+ break;
+ case UnknownField::TYPE_GROUP:
+ output->WriteVarint32(WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_START_GROUP));
+ SerializeUnknownFields(field.group(), output);
+ output->WriteVarint32(WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_END_GROUP));
+ break;
+ }
+ }
+}
+
+uint8* WireFormat::SerializeUnknownFieldsToArray(
+ const UnknownFieldSet& unknown_fields,
+ uint8* target) {
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ const UnknownField& field = unknown_fields.field(i);
+
+ switch (field.type()) {
+ case UnknownField::TYPE_VARINT:
+ target = WireFormatLite::WriteInt64ToArray(
+ field.number(), field.varint(), target);
+ break;
+ case UnknownField::TYPE_FIXED32:
+ target = WireFormatLite::WriteFixed32ToArray(
+ field.number(), field.fixed32(), target);
+ break;
+ case UnknownField::TYPE_FIXED64:
+ target = WireFormatLite::WriteFixed64ToArray(
+ field.number(), field.fixed64(), target);
+ break;
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ target = WireFormatLite::WriteBytesToArray(
+ field.number(), field.length_delimited(), target);
+ break;
+ case UnknownField::TYPE_GROUP:
+ target = WireFormatLite::WriteTagToArray(
+ field.number(), WireFormatLite::WIRETYPE_START_GROUP, target);
+ target = SerializeUnknownFieldsToArray(field.group(), target);
+ target = WireFormatLite::WriteTagToArray(
+ field.number(), WireFormatLite::WIRETYPE_END_GROUP, target);
+ break;
+ }
+ }
+ return target;
+}
+
+void WireFormat::SerializeUnknownMessageSetItems(
+ const UnknownFieldSet& unknown_fields,
+ io::CodedOutputStream* output) {
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ const UnknownField& field = unknown_fields.field(i);
+ // The only unknown fields that are allowed to exist in a MessageSet are
+ // messages, which are length-delimited.
+ if (field.type() == UnknownField::TYPE_LENGTH_DELIMITED) {
+ // Start group.
+ output->WriteVarint32(WireFormatLite::kMessageSetItemStartTag);
+
+ // Write type ID.
+ output->WriteVarint32(WireFormatLite::kMessageSetTypeIdTag);
+ output->WriteVarint32(field.number());
+
+ // Write message.
+ output->WriteVarint32(WireFormatLite::kMessageSetMessageTag);
+ field.SerializeLengthDelimitedNoTag(output);
+
+ // End group.
+ output->WriteVarint32(WireFormatLite::kMessageSetItemEndTag);
+ }
+ }
+}
+
+uint8* WireFormat::SerializeUnknownMessageSetItemsToArray(
+ const UnknownFieldSet& unknown_fields,
+ uint8* target) {
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ const UnknownField& field = unknown_fields.field(i);
+
+ // The only unknown fields that are allowed to exist in a MessageSet are
+ // messages, which are length-delimited.
+ if (field.type() == UnknownField::TYPE_LENGTH_DELIMITED) {
+ // Start group.
+ target = io::CodedOutputStream::WriteTagToArray(
+ WireFormatLite::kMessageSetItemStartTag, target);
+
+ // Write type ID.
+ target = io::CodedOutputStream::WriteTagToArray(
+ WireFormatLite::kMessageSetTypeIdTag, target);
+ target = io::CodedOutputStream::WriteVarint32ToArray(
+ field.number(), target);
+
+ // Write message.
+ target = io::CodedOutputStream::WriteTagToArray(
+ WireFormatLite::kMessageSetMessageTag, target);
+ target = field.SerializeLengthDelimitedNoTagToArray(target);
+
+ // End group.
+ target = io::CodedOutputStream::WriteTagToArray(
+ WireFormatLite::kMessageSetItemEndTag, target);
+ }
+ }
+
+ return target;
+}
+
+int WireFormat::ComputeUnknownFieldsSize(
+ const UnknownFieldSet& unknown_fields) {
+ int size = 0;
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ const UnknownField& field = unknown_fields.field(i);
+
+ switch (field.type()) {
+ case UnknownField::TYPE_VARINT:
+ size += io::CodedOutputStream::VarintSize32(
+ WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_VARINT));
+ size += io::CodedOutputStream::VarintSize64(field.varint());
+ break;
+ case UnknownField::TYPE_FIXED32:
+ size += io::CodedOutputStream::VarintSize32(
+ WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_FIXED32));
+ size += sizeof(int32);
+ break;
+ case UnknownField::TYPE_FIXED64:
+ size += io::CodedOutputStream::VarintSize32(
+ WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_FIXED64));
+ size += sizeof(int64);
+ break;
+ case UnknownField::TYPE_LENGTH_DELIMITED:
+ size += io::CodedOutputStream::VarintSize32(
+ WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED));
+ size += io::CodedOutputStream::VarintSize32(
+ field.length_delimited().size());
+ size += field.length_delimited().size();
+ break;
+ case UnknownField::TYPE_GROUP:
+ size += io::CodedOutputStream::VarintSize32(
+ WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_START_GROUP));
+ size += ComputeUnknownFieldsSize(field.group());
+ size += io::CodedOutputStream::VarintSize32(
+ WireFormatLite::MakeTag(field.number(),
+ WireFormatLite::WIRETYPE_END_GROUP));
+ break;
+ }
+ }
+
+ return size;
+}
+
+int WireFormat::ComputeUnknownMessageSetItemsSize(
+ const UnknownFieldSet& unknown_fields) {
+ int size = 0;
+ for (int i = 0; i < unknown_fields.field_count(); i++) {
+ const UnknownField& field = unknown_fields.field(i);
+
+ // The only unknown fields that are allowed to exist in a MessageSet are
+ // messages, which are length-delimited.
+ if (field.type() == UnknownField::TYPE_LENGTH_DELIMITED) {
+ size += WireFormatLite::kMessageSetItemTagsSize;
+ size += io::CodedOutputStream::VarintSize32(field.number());
+
+ int field_size = field.GetLengthDelimitedSize();
+ size += io::CodedOutputStream::VarintSize32(field_size);
+ size += field_size;
+ }
+ }
+
+ return size;
+}
+
+// ===================================================================
+
+bool WireFormat::ParseAndMergePartial(io::CodedInputStream* input,
+ Message* message) {
+ const Descriptor* descriptor = message->GetDescriptor();
+ const Reflection* message_reflection = message->GetReflection();
+
+ while(true) {
+ uint32 tag = input->ReadTag();
+ if (tag == 0) {
+ // End of input. This is a valid place to end, so return true.
+ return true;
+ }
+
+ if (WireFormatLite::GetTagWireType(tag) ==
+ WireFormatLite::WIRETYPE_END_GROUP) {
+ // Must be the end of the message.
+ return true;
+ }
+
+ const FieldDescriptor* field = NULL;
+
+ if (descriptor != NULL) {
+ int field_number = WireFormatLite::GetTagFieldNumber(tag);
+ field = descriptor->FindFieldByNumber(field_number);
+
+ // If that failed, check if the field is an extension.
+ if (field == NULL && descriptor->IsExtensionNumber(field_number)) {
+ if (input->GetExtensionPool() == NULL) {
+ field = message_reflection->FindKnownExtensionByNumber(field_number);
+ } else {
+ field = input->GetExtensionPool()
+ ->FindExtensionByNumber(descriptor, field_number);
+ }
+ }
+
+ // If that failed, but we're a MessageSet, and this is the tag for a
+ // MessageSet item, then parse that.
+ if (field == NULL &&
+ descriptor->options().message_set_wire_format() &&
+ tag == WireFormatLite::kMessageSetItemStartTag) {
+ if (!ParseAndMergeMessageSetItem(input, message)) {
+ return false;
+ }
+ continue; // Skip ParseAndMergeField(); already taken care of.
+ }
+ }
+
+ if (!ParseAndMergeField(tag, field, message, input)) {
+ return false;
+ }
+ }
+}
+
+bool WireFormat::SkipMessageSetField(io::CodedInputStream* input,
+ uint32 field_number,
+ UnknownFieldSet* unknown_fields) {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ return input->ReadString(
+ unknown_fields->AddLengthDelimited(field_number), length);
+}
+
+bool WireFormat::ParseAndMergeMessageSetField(uint32 field_number,
+ const FieldDescriptor* field,
+ Message* message,
+ io::CodedInputStream* input) {
+ const Reflection* message_reflection = message->GetReflection();
+ if (field == NULL) {
+ // We store unknown MessageSet extensions as groups.
+ return SkipMessageSetField(
+ input, field_number, message_reflection->MutableUnknownFields(message));
+ } else if (field->is_repeated() ||
+ field->type() != FieldDescriptor::TYPE_MESSAGE) {
+ // This shouldn't happen as we only allow optional message extensions to
+ // MessageSet.
+ GOOGLE_LOG(ERROR) << "Extensions of MessageSets must be optional messages.";
+ return false;
+ } else {
+ Message* sub_message = message_reflection->MutableMessage(
+ message, field, input->GetExtensionFactory());
+ return WireFormatLite::ReadMessage(input, sub_message);
+ }
+}
+
+static bool StrictUtf8Check(const FieldDescriptor* field) {
+ return field->file()->syntax() == FileDescriptor::SYNTAX_PROTO3;
+}
+
+bool WireFormat::ParseAndMergeField(
+ uint32 tag,
+ const FieldDescriptor* field, // May be NULL for unknown
+ Message* message,
+ io::CodedInputStream* input) {
+ const Reflection* message_reflection = message->GetReflection();
+
+ enum { UNKNOWN, NORMAL_FORMAT, PACKED_FORMAT } value_format;
+
+ if (field == NULL) {
+ value_format = UNKNOWN;
+ } else if (WireFormatLite::GetTagWireType(tag) ==
+ WireTypeForFieldType(field->type())) {
+ value_format = NORMAL_FORMAT;
+ } else if (field->is_packable() &&
+ WireFormatLite::GetTagWireType(tag) ==
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED) {
+ value_format = PACKED_FORMAT;
+ } else {
+ // We don't recognize this field. Either the field number is unknown
+ // or the wire type doesn't match. Put it in our unknown field set.
+ value_format = UNKNOWN;
+ }
+
+ if (value_format == UNKNOWN) {
+ return SkipField(input, tag,
+ message_reflection->MutableUnknownFields(message));
+ } else if (value_format == PACKED_FORMAT) {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ io::CodedInputStream::Limit limit = input->PushLimit(length);
+
+ switch (field->type()) {
+#define HANDLE_PACKED_TYPE(TYPE, CPPTYPE, CPPTYPE_METHOD) \
+ case FieldDescriptor::TYPE_##TYPE: { \
+ while (input->BytesUntilLimit() > 0) { \
+ CPPTYPE value; \
+ if (!WireFormatLite::ReadPrimitive< \
+ CPPTYPE, WireFormatLite::TYPE_##TYPE>(input, &value)) \
+ return false; \
+ message_reflection->Add##CPPTYPE_METHOD(message, field, value); \
+ } \
+ break; \
+ }
+
+ HANDLE_PACKED_TYPE( INT32, int32, Int32)
+ HANDLE_PACKED_TYPE( INT64, int64, Int64)
+ HANDLE_PACKED_TYPE(SINT32, int32, Int32)
+ HANDLE_PACKED_TYPE(SINT64, int64, Int64)
+ HANDLE_PACKED_TYPE(UINT32, uint32, UInt32)
+ HANDLE_PACKED_TYPE(UINT64, uint64, UInt64)
+
+ HANDLE_PACKED_TYPE( FIXED32, uint32, UInt32)
+ HANDLE_PACKED_TYPE( FIXED64, uint64, UInt64)
+ HANDLE_PACKED_TYPE(SFIXED32, int32, Int32)
+ HANDLE_PACKED_TYPE(SFIXED64, int64, Int64)
+
+ HANDLE_PACKED_TYPE(FLOAT , float , Float )
+ HANDLE_PACKED_TYPE(DOUBLE, double, Double)
+
+ HANDLE_PACKED_TYPE(BOOL, bool, Bool)
+#undef HANDLE_PACKED_TYPE
+
+ case FieldDescriptor::TYPE_ENUM: {
+ while (input->BytesUntilLimit() > 0) {
+ int value;
+ if (!WireFormatLite::ReadPrimitive<int, WireFormatLite::TYPE_ENUM>(
+ input, &value)) return false;
+ if (message->GetDescriptor()->file()->syntax() ==
+ FileDescriptor::SYNTAX_PROTO3) {
+ message_reflection->AddEnumValue(message, field, value);
+ } else {
+ const EnumValueDescriptor* enum_value =
+ field->enum_type()->FindValueByNumber(value);
+ if (enum_value != NULL) {
+ message_reflection->AddEnum(message, field, enum_value);
+ } else {
+ // The enum value is not one of the known values. Add it to the
+ // UnknownFieldSet.
+ int64 sign_extended_value = static_cast<int64>(value);
+ message_reflection->MutableUnknownFields(message)
+ ->AddVarint(
+ WireFormatLite::GetTagFieldNumber(tag),
+ sign_extended_value);
+ }
+ }
+ }
+
+ break;
+ }
+
+ case FieldDescriptor::TYPE_STRING:
+ case FieldDescriptor::TYPE_GROUP:
+ case FieldDescriptor::TYPE_MESSAGE:
+ case FieldDescriptor::TYPE_BYTES:
+ // Can't have packed fields of these types: these should be caught by
+ // the protocol compiler.
+ return false;
+ break;
+ }
+
+ input->PopLimit(limit);
+ } else {
+ // Non-packed value (value_format == NORMAL_FORMAT)
+ switch (field->type()) {
+#define HANDLE_TYPE(TYPE, CPPTYPE, CPPTYPE_METHOD) \
+ case FieldDescriptor::TYPE_##TYPE: { \
+ CPPTYPE value; \
+ if (!WireFormatLite::ReadPrimitive< \
+ CPPTYPE, WireFormatLite::TYPE_##TYPE>(input, &value)) \
+ return false; \
+ if (field->is_repeated()) { \
+ message_reflection->Add##CPPTYPE_METHOD(message, field, value); \
+ } else { \
+ message_reflection->Set##CPPTYPE_METHOD(message, field, value); \
+ } \
+ break; \
+ }
+
+ HANDLE_TYPE( INT32, int32, Int32)
+ HANDLE_TYPE( INT64, int64, Int64)
+ HANDLE_TYPE(SINT32, int32, Int32)
+ HANDLE_TYPE(SINT64, int64, Int64)
+ HANDLE_TYPE(UINT32, uint32, UInt32)
+ HANDLE_TYPE(UINT64, uint64, UInt64)
+
+ HANDLE_TYPE( FIXED32, uint32, UInt32)
+ HANDLE_TYPE( FIXED64, uint64, UInt64)
+ HANDLE_TYPE(SFIXED32, int32, Int32)
+ HANDLE_TYPE(SFIXED64, int64, Int64)
+
+ HANDLE_TYPE(FLOAT , float , Float )
+ HANDLE_TYPE(DOUBLE, double, Double)
+
+ HANDLE_TYPE(BOOL, bool, Bool)
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::TYPE_ENUM: {
+ int value;
+ if (!WireFormatLite::ReadPrimitive<int, WireFormatLite::TYPE_ENUM>(
+ input, &value)) return false;
+ if (message->GetDescriptor()->file()->syntax() ==
+ FileDescriptor::SYNTAX_PROTO3) {
+ if (field->is_repeated()) {
+ message_reflection->AddEnumValue(message, field, value);
+ } else {
+ message_reflection->SetEnumValue(message, field, value);
+ }
+ } else {
+ const EnumValueDescriptor* enum_value =
+ field->enum_type()->FindValueByNumber(value);
+ if (enum_value != NULL) {
+ if (field->is_repeated()) {
+ message_reflection->AddEnum(message, field, enum_value);
+ } else {
+ message_reflection->SetEnum(message, field, enum_value);
+ }
+ } else {
+ // The enum value is not one of the known values. Add it to the
+ // UnknownFieldSet.
+ int64 sign_extended_value = static_cast<int64>(value);
+ message_reflection->MutableUnknownFields(message)
+ ->AddVarint(
+ WireFormatLite::GetTagFieldNumber(tag),
+ sign_extended_value);
+ }
+ }
+ break;
+ }
+
+ // Handle strings separately so that we can optimize the ctype=CORD case.
+ case FieldDescriptor::TYPE_STRING: {
+ bool strict_utf8_check = StrictUtf8Check(field);
+ string value;
+ if (!WireFormatLite::ReadString(input, &value)) return false;
+ if (strict_utf8_check) {
+ if (!WireFormatLite::VerifyUtf8String(
+ value.data(), value.length(), WireFormatLite::PARSE,
+ field->full_name().c_str())) {
+ return false;
+ }
+ } else {
+ VerifyUTF8StringNamedField(value.data(), value.length(), PARSE,
+ field->full_name().c_str());
+ }
+ if (field->is_repeated()) {
+ message_reflection->AddString(message, field, value);
+ } else {
+ message_reflection->SetString(message, field, value);
+ }
+ break;
+ }
+
+ case FieldDescriptor::TYPE_BYTES: {
+ string value;
+ if (!WireFormatLite::ReadBytes(input, &value)) return false;
+ if (field->is_repeated()) {
+ message_reflection->AddString(message, field, value);
+ } else {
+ message_reflection->SetString(message, field, value);
+ }
+ break;
+ }
+
+ case FieldDescriptor::TYPE_GROUP: {
+ Message* sub_message;
+ if (field->is_repeated()) {
+ sub_message = message_reflection->AddMessage(
+ message, field, input->GetExtensionFactory());
+ } else {
+ sub_message = message_reflection->MutableMessage(
+ message, field, input->GetExtensionFactory());
+ }
+
+ if (!WireFormatLite::ReadGroup(WireFormatLite::GetTagFieldNumber(tag),
+ input, sub_message))
+ return false;
+ break;
+ }
+
+ case FieldDescriptor::TYPE_MESSAGE: {
+ Message* sub_message;
+ if (field->is_repeated()) {
+ sub_message = message_reflection->AddMessage(
+ message, field, input->GetExtensionFactory());
+ } else {
+ sub_message = message_reflection->MutableMessage(
+ message, field, input->GetExtensionFactory());
+ }
+
+ if (!WireFormatLite::ReadMessage(input, sub_message)) return false;
+ break;
+ }
+ }
+ }
+
+ return true;
+}
+
+bool WireFormat::ParseAndMergeMessageSetItem(
+ io::CodedInputStream* input,
+ Message* message) {
+ const Reflection* message_reflection = message->GetReflection();
+
+ // This method parses a group which should contain two fields:
+ // required int32 type_id = 2;
+ // required data message = 3;
+
+ uint32 last_type_id = 0;
+
+ // Once we see a type_id, we'll look up the FieldDescriptor for the
+ // extension.
+ const FieldDescriptor* field = NULL;
+
+ // If we see message data before the type_id, we'll append it to this so
+ // we can parse it later.
+ string message_data;
+
+ while (true) {
+ uint32 tag = input->ReadTag();
+ if (tag == 0) return false;
+
+ switch (tag) {
+ case WireFormatLite::kMessageSetTypeIdTag: {
+ uint32 type_id;
+ if (!input->ReadVarint32(&type_id)) return false;
+ last_type_id = type_id;
+ field = message_reflection->FindKnownExtensionByNumber(type_id);
+
+ if (!message_data.empty()) {
+ // We saw some message data before the type_id. Have to parse it
+ // now.
+ io::ArrayInputStream raw_input(message_data.data(),
+ message_data.size());
+ io::CodedInputStream sub_input(&raw_input);
+ if (!ParseAndMergeMessageSetField(last_type_id, field, message,
+ &sub_input)) {
+ return false;
+ }
+ message_data.clear();
+ }
+
+ break;
+ }
+
+ case WireFormatLite::kMessageSetMessageTag: {
+ if (last_type_id == 0) {
+ // We haven't seen a type_id yet. Append this data to message_data.
+ string temp;
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ if (!input->ReadString(&temp, length)) return false;
+ io::StringOutputStream output_stream(&message_data);
+ io::CodedOutputStream coded_output(&output_stream);
+ coded_output.WriteVarint32(length);
+ coded_output.WriteString(temp);
+ } else {
+ // Already saw type_id, so we can parse this directly.
+ if (!ParseAndMergeMessageSetField(last_type_id, field, message,
+ input)) {
+ return false;
+ }
+ }
+
+ break;
+ }
+
+ case WireFormatLite::kMessageSetItemEndTag: {
+ return true;
+ }
+
+ default: {
+ if (!SkipField(input, tag, NULL)) return false;
+ }
+ }
+ }
+}
+
+// ===================================================================
+
+void WireFormat::SerializeWithCachedSizes(
+ const Message& message,
+ int size, io::CodedOutputStream* output) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ const Reflection* message_reflection = message.GetReflection();
+ int expected_endpoint = output->ByteCount() + size;
+
+ vector<const FieldDescriptor*> fields;
+ message_reflection->ListFields(message, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ SerializeFieldWithCachedSizes(fields[i], message, output);
+ }
+
+ if (descriptor->options().message_set_wire_format()) {
+ SerializeUnknownMessageSetItems(
+ message_reflection->GetUnknownFields(message), output);
+ } else {
+ SerializeUnknownFields(
+ message_reflection->GetUnknownFields(message), output);
+ }
+
+ GOOGLE_CHECK_EQ(output->ByteCount(), expected_endpoint)
+ << ": Protocol message serialized to a size different from what was "
+ "originally expected. Perhaps it was modified by another thread "
+ "during serialization?";
+}
+
+void WireFormat::SerializeFieldWithCachedSizes(
+ const FieldDescriptor* field,
+ const Message& message,
+ io::CodedOutputStream* output) {
+ const Reflection* message_reflection = message.GetReflection();
+
+ if (field->is_extension() &&
+ field->containing_type()->options().message_set_wire_format() &&
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ !field->is_repeated()) {
+ SerializeMessageSetItemWithCachedSizes(field, message, output);
+ return;
+ }
+
+ int count = 0;
+
+ if (field->is_repeated()) {
+ count = message_reflection->FieldSize(message, field);
+ } else if (message_reflection->HasField(message, field)) {
+ count = 1;
+ }
+
+ const bool is_packed = field->is_packed();
+ if (is_packed && count > 0) {
+ WireFormatLite::WriteTag(field->number(),
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED, output);
+ const int data_size = FieldDataOnlyByteSize(field, message);
+ output->WriteVarint32(data_size);
+ }
+
+ for (int j = 0; j < count; j++) {
+ switch (field->type()) {
+#define HANDLE_PRIMITIVE_TYPE(TYPE, CPPTYPE, TYPE_METHOD, CPPTYPE_METHOD) \
+ case FieldDescriptor::TYPE_##TYPE: { \
+ const CPPTYPE value = field->is_repeated() ? \
+ message_reflection->GetRepeated##CPPTYPE_METHOD( \
+ message, field, j) : \
+ message_reflection->Get##CPPTYPE_METHOD( \
+ message, field); \
+ if (is_packed) { \
+ WireFormatLite::Write##TYPE_METHOD##NoTag(value, output); \
+ } else { \
+ WireFormatLite::Write##TYPE_METHOD(field->number(), value, output); \
+ } \
+ break; \
+ }
+
+ HANDLE_PRIMITIVE_TYPE( INT32, int32, Int32, Int32)
+ HANDLE_PRIMITIVE_TYPE( INT64, int64, Int64, Int64)
+ HANDLE_PRIMITIVE_TYPE(SINT32, int32, SInt32, Int32)
+ HANDLE_PRIMITIVE_TYPE(SINT64, int64, SInt64, Int64)
+ HANDLE_PRIMITIVE_TYPE(UINT32, uint32, UInt32, UInt32)
+ HANDLE_PRIMITIVE_TYPE(UINT64, uint64, UInt64, UInt64)
+
+ HANDLE_PRIMITIVE_TYPE( FIXED32, uint32, Fixed32, UInt32)
+ HANDLE_PRIMITIVE_TYPE( FIXED64, uint64, Fixed64, UInt64)
+ HANDLE_PRIMITIVE_TYPE(SFIXED32, int32, SFixed32, Int32)
+ HANDLE_PRIMITIVE_TYPE(SFIXED64, int64, SFixed64, Int64)
+
+ HANDLE_PRIMITIVE_TYPE(FLOAT , float , Float , Float )
+ HANDLE_PRIMITIVE_TYPE(DOUBLE, double, Double, Double)
+
+ HANDLE_PRIMITIVE_TYPE(BOOL, bool, Bool, Bool)
+#undef HANDLE_PRIMITIVE_TYPE
+
+#define HANDLE_TYPE(TYPE, TYPE_METHOD, CPPTYPE_METHOD) \
+ case FieldDescriptor::TYPE_##TYPE: \
+ WireFormatLite::Write##TYPE_METHOD( \
+ field->number(), \
+ field->is_repeated() ? \
+ message_reflection->GetRepeated##CPPTYPE_METHOD( \
+ message, field, j) : \
+ message_reflection->Get##CPPTYPE_METHOD(message, field), \
+ output); \
+ break;
+
+ HANDLE_TYPE(GROUP , Group , Message)
+ HANDLE_TYPE(MESSAGE, Message, Message)
+#undef HANDLE_TYPE
+
+ case FieldDescriptor::TYPE_ENUM: {
+ const EnumValueDescriptor* value = field->is_repeated() ?
+ message_reflection->GetRepeatedEnum(message, field, j) :
+ message_reflection->GetEnum(message, field);
+ if (is_packed) {
+ WireFormatLite::WriteEnumNoTag(value->number(), output);
+ } else {
+ WireFormatLite::WriteEnum(field->number(), value->number(), output);
+ }
+ break;
+ }
+
+ // Handle strings separately so that we can get string references
+ // instead of copying.
+ case FieldDescriptor::TYPE_STRING: {
+ bool strict_utf8_check = StrictUtf8Check(field);
+ string scratch;
+ const string& value = field->is_repeated() ?
+ message_reflection->GetRepeatedStringReference(
+ message, field, j, &scratch) :
+ message_reflection->GetStringReference(message, field, &scratch);
+ if (strict_utf8_check) {
+ WireFormatLite::VerifyUtf8String(value.data(), value.length(),
+ WireFormatLite::SERIALIZE,
+ field->full_name().c_str());
+ } else {
+ VerifyUTF8StringNamedField(value.data(), value.length(), SERIALIZE,
+ field->full_name().c_str());
+ }
+ WireFormatLite::WriteString(field->number(), value, output);
+ break;
+ }
+
+ case FieldDescriptor::TYPE_BYTES: {
+ string scratch;
+ const string& value = field->is_repeated() ?
+ message_reflection->GetRepeatedStringReference(
+ message, field, j, &scratch) :
+ message_reflection->GetStringReference(message, field, &scratch);
+ WireFormatLite::WriteBytes(field->number(), value, output);
+ break;
+ }
+ }
+ }
+}
+
+void WireFormat::SerializeMessageSetItemWithCachedSizes(
+ const FieldDescriptor* field,
+ const Message& message,
+ io::CodedOutputStream* output) {
+ const Reflection* message_reflection = message.GetReflection();
+
+ // Start group.
+ output->WriteVarint32(WireFormatLite::kMessageSetItemStartTag);
+
+ // Write type ID.
+ output->WriteVarint32(WireFormatLite::kMessageSetTypeIdTag);
+ output->WriteVarint32(field->number());
+
+ // Write message.
+ output->WriteVarint32(WireFormatLite::kMessageSetMessageTag);
+
+ const Message& sub_message = message_reflection->GetMessage(message, field);
+ output->WriteVarint32(sub_message.GetCachedSize());
+ sub_message.SerializeWithCachedSizes(output);
+
+ // End group.
+ output->WriteVarint32(WireFormatLite::kMessageSetItemEndTag);
+}
+
+// ===================================================================
+
+int WireFormat::ByteSize(const Message& message) {
+ const Descriptor* descriptor = message.GetDescriptor();
+ const Reflection* message_reflection = message.GetReflection();
+
+ int our_size = 0;
+
+ vector<const FieldDescriptor*> fields;
+ message_reflection->ListFields(message, &fields);
+ for (int i = 0; i < fields.size(); i++) {
+ our_size += FieldByteSize(fields[i], message);
+ }
+
+ if (descriptor->options().message_set_wire_format()) {
+ our_size += ComputeUnknownMessageSetItemsSize(
+ message_reflection->GetUnknownFields(message));
+ } else {
+ our_size += ComputeUnknownFieldsSize(
+ message_reflection->GetUnknownFields(message));
+ }
+
+ return our_size;
+}
+
+int WireFormat::FieldByteSize(
+ const FieldDescriptor* field,
+ const Message& message) {
+ const Reflection* message_reflection = message.GetReflection();
+
+ if (field->is_extension() &&
+ field->containing_type()->options().message_set_wire_format() &&
+ field->cpp_type() == FieldDescriptor::CPPTYPE_MESSAGE &&
+ !field->is_repeated()) {
+ return MessageSetItemByteSize(field, message);
+ }
+
+ int count = 0;
+ if (field->is_repeated()) {
+ count = message_reflection->FieldSize(message, field);
+ } else if (message_reflection->HasField(message, field)) {
+ count = 1;
+ }
+
+ const int data_size = FieldDataOnlyByteSize(field, message);
+ int our_size = data_size;
+ if (field->is_packed()) {
+ if (data_size > 0) {
+ // Packed fields get serialized like a string, not their native type.
+ // Technically this doesn't really matter; the size only changes if it's
+ // a GROUP
+ our_size += TagSize(field->number(), FieldDescriptor::TYPE_STRING);
+ our_size += io::CodedOutputStream::VarintSize32(data_size);
+ }
+ } else {
+ our_size += count * TagSize(field->number(), field->type());
+ }
+ return our_size;
+}
+
+int WireFormat::FieldDataOnlyByteSize(
+ const FieldDescriptor* field,
+ const Message& message) {
+ const Reflection* message_reflection = message.GetReflection();
+
+ int count = 0;
+ if (field->is_repeated()) {
+ count = message_reflection->FieldSize(message, field);
+ } else if (message_reflection->HasField(message, field)) {
+ count = 1;
+ }
+
+ int data_size = 0;
+ switch (field->type()) {
+#define HANDLE_TYPE(TYPE, TYPE_METHOD, CPPTYPE_METHOD) \
+ case FieldDescriptor::TYPE_##TYPE: \
+ if (field->is_repeated()) { \
+ for (int j = 0; j < count; j++) { \
+ data_size += WireFormatLite::TYPE_METHOD##Size( \
+ message_reflection->GetRepeated##CPPTYPE_METHOD( \
+ message, field, j)); \
+ } \
+ } else { \
+ data_size += WireFormatLite::TYPE_METHOD##Size( \
+ message_reflection->Get##CPPTYPE_METHOD(message, field)); \
+ } \
+ break;
+
+#define HANDLE_FIXED_TYPE(TYPE, TYPE_METHOD) \
+ case FieldDescriptor::TYPE_##TYPE: \
+ data_size += count * WireFormatLite::k##TYPE_METHOD##Size; \
+ break;
+
+ HANDLE_TYPE( INT32, Int32, Int32)
+ HANDLE_TYPE( INT64, Int64, Int64)
+ HANDLE_TYPE(SINT32, SInt32, Int32)
+ HANDLE_TYPE(SINT64, SInt64, Int64)
+ HANDLE_TYPE(UINT32, UInt32, UInt32)
+ HANDLE_TYPE(UINT64, UInt64, UInt64)
+
+ HANDLE_FIXED_TYPE( FIXED32, Fixed32)
+ HANDLE_FIXED_TYPE( FIXED64, Fixed64)
+ HANDLE_FIXED_TYPE(SFIXED32, SFixed32)
+ HANDLE_FIXED_TYPE(SFIXED64, SFixed64)
+
+ HANDLE_FIXED_TYPE(FLOAT , Float )
+ HANDLE_FIXED_TYPE(DOUBLE, Double)
+
+ HANDLE_FIXED_TYPE(BOOL, Bool)
+
+ HANDLE_TYPE(GROUP , Group , Message)
+ HANDLE_TYPE(MESSAGE, Message, Message)
+#undef HANDLE_TYPE
+#undef HANDLE_FIXED_TYPE
+
+ case FieldDescriptor::TYPE_ENUM: {
+ if (field->is_repeated()) {
+ for (int j = 0; j < count; j++) {
+ data_size += WireFormatLite::EnumSize(
+ message_reflection->GetRepeatedEnum(message, field, j)->number());
+ }
+ } else {
+ data_size += WireFormatLite::EnumSize(
+ message_reflection->GetEnum(message, field)->number());
+ }
+ break;
+ }
+
+ // Handle strings separately so that we can get string references
+ // instead of copying.
+ case FieldDescriptor::TYPE_STRING:
+ case FieldDescriptor::TYPE_BYTES: {
+ for (int j = 0; j < count; j++) {
+ string scratch;
+ const string& value = field->is_repeated() ?
+ message_reflection->GetRepeatedStringReference(
+ message, field, j, &scratch) :
+ message_reflection->GetStringReference(message, field, &scratch);
+ data_size += WireFormatLite::StringSize(value);
+ }
+ break;
+ }
+ }
+ return data_size;
+}
+
+int WireFormat::MessageSetItemByteSize(
+ const FieldDescriptor* field,
+ const Message& message) {
+ const Reflection* message_reflection = message.GetReflection();
+
+ int our_size = WireFormatLite::kMessageSetItemTagsSize;
+
+ // type_id
+ our_size += io::CodedOutputStream::VarintSize32(field->number());
+
+ // message
+ const Message& sub_message = message_reflection->GetMessage(message, field);
+ int message_size = sub_message.ByteSize();
+
+ our_size += io::CodedOutputStream::VarintSize32(message_size);
+ our_size += message_size;
+
+ return our_size;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wire_format.h b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format.h
new file mode 100644
index 0000000000..aaee21f02d
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format.h
@@ -0,0 +1,337 @@
+// 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)
+// atenasio@google.com (Chris Atenasio) (ZigZag transform)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// This header is logically internal, but is made public because it is used
+// from protocol-compiler-generated code, which may reside in other components.
+
+#ifndef GOOGLE_PROTOBUF_WIRE_FORMAT_H__
+#define GOOGLE_PROTOBUF_WIRE_FORMAT_H__
+
+#include <string>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/descriptor.pb.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/wire_format_lite.h>
+
+// Do UTF-8 validation on string type in Debug build only
+#ifndef NDEBUG
+#define GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+#endif
+
+namespace google {
+namespace protobuf {
+ namespace io {
+ class CodedInputStream; // coded_stream.h
+ class CodedOutputStream; // coded_stream.h
+ }
+ class UnknownFieldSet; // unknown_field_set.h
+}
+
+namespace protobuf {
+namespace internal {
+
+// This class is for internal use by the protocol buffer library and by
+// protocol-complier-generated message classes. It must not be called
+// directly by clients.
+//
+// This class contains code for implementing the binary protocol buffer
+// wire format via reflection. The WireFormatLite class implements the
+// non-reflection based routines.
+//
+// This class is really a namespace that contains only static methods
+class LIBPROTOBUF_EXPORT WireFormat {
+ public:
+
+ // Given a field return its WireType
+ static inline WireFormatLite::WireType WireTypeForField(
+ const FieldDescriptor* field);
+
+ // Given a FieldDescriptor::Type return its WireType
+ static inline WireFormatLite::WireType WireTypeForFieldType(
+ FieldDescriptor::Type type);
+
+ // Compute the byte size of a tag. For groups, this includes both the start
+ // and end tags.
+ static inline int TagSize(int field_number, FieldDescriptor::Type type);
+
+ // These procedures can be used to implement the methods of Message which
+ // handle parsing and serialization of the protocol buffer wire format
+ // using only the Reflection interface. When you ask the protocol
+ // compiler to optimize for code size rather than speed, it will implement
+ // those methods in terms of these procedures. Of course, these are much
+ // slower than the specialized implementations which the protocol compiler
+ // generates when told to optimize for speed.
+
+ // Read a message in protocol buffer wire format.
+ //
+ // This procedure reads either to the end of the input stream or through
+ // a WIRETYPE_END_GROUP tag ending the message, whichever comes first.
+ // It returns false if the input is invalid.
+ //
+ // Required fields are NOT checked by this method. You must call
+ // IsInitialized() on the resulting message yourself.
+ static bool ParseAndMergePartial(io::CodedInputStream* input,
+ Message* message);
+
+ // Serialize a message in protocol buffer wire format.
+ //
+ // Any embedded messages within the message must have their correct sizes
+ // cached. However, the top-level message need not; its size is passed as
+ // a parameter to this procedure.
+ //
+ // These return false iff the underlying stream returns a write error.
+ static void SerializeWithCachedSizes(
+ const Message& message,
+ int size, io::CodedOutputStream* output);
+
+ // Implements Message::ByteSize() via reflection. WARNING: The result
+ // of this method is *not* cached anywhere. However, all embedded messages
+ // will have their ByteSize() methods called, so their sizes will be cached.
+ // Therefore, calling this method is sufficient to allow you to call
+ // WireFormat::SerializeWithCachedSizes() on the same object.
+ static int ByteSize(const Message& message);
+
+ // -----------------------------------------------------------------
+ // Helpers for dealing with unknown fields
+
+ // Skips a field value of the given WireType. The input should start
+ // positioned immediately after the tag. If unknown_fields is non-NULL,
+ // the contents of the field will be added to it.
+ static bool SkipField(io::CodedInputStream* input, uint32 tag,
+ UnknownFieldSet* unknown_fields);
+
+ // Reads and ignores a message from the input. If unknown_fields is non-NULL,
+ // the contents will be added to it.
+ static bool SkipMessage(io::CodedInputStream* input,
+ UnknownFieldSet* unknown_fields);
+
+ // Read a packed enum field. If the is_valid function is not NULL, values for
+ // which is_valid(value) returns false are appended to unknown_fields_stream.
+ static bool ReadPackedEnumPreserveUnknowns(io::CodedInputStream* input,
+ uint32 field_number,
+ bool (*is_valid)(int),
+ UnknownFieldSet* unknown_fields,
+ RepeatedField<int>* values);
+
+ // Write the contents of an UnknownFieldSet to the output.
+ static void SerializeUnknownFields(const UnknownFieldSet& unknown_fields,
+ io::CodedOutputStream* output);
+ // Same as above, except writing directly to the provided buffer.
+ // Requires that the buffer have sufficient capacity for
+ // ComputeUnknownFieldsSize(unknown_fields).
+ //
+ // Returns a pointer past the last written byte.
+ static uint8* SerializeUnknownFieldsToArray(
+ const UnknownFieldSet& unknown_fields,
+ uint8* target);
+
+ // Same thing except for messages that have the message_set_wire_format
+ // option.
+ static void SerializeUnknownMessageSetItems(
+ const UnknownFieldSet& unknown_fields,
+ io::CodedOutputStream* output);
+ // Same as above, except writing directly to the provided buffer.
+ // Requires that the buffer have sufficient capacity for
+ // ComputeUnknownMessageSetItemsSize(unknown_fields).
+ //
+ // Returns a pointer past the last written byte.
+ static uint8* SerializeUnknownMessageSetItemsToArray(
+ const UnknownFieldSet& unknown_fields,
+ uint8* target);
+
+ // Compute the size of the UnknownFieldSet on the wire.
+ static int ComputeUnknownFieldsSize(const UnknownFieldSet& unknown_fields);
+
+ // Same thing except for messages that have the message_set_wire_format
+ // option.
+ static int ComputeUnknownMessageSetItemsSize(
+ const UnknownFieldSet& unknown_fields);
+
+
+ // Helper functions for encoding and decoding tags. (Inlined below and in
+ // _inl.h)
+ //
+ // This is different from MakeTag(field->number(), field->type()) in the case
+ // of packed repeated fields.
+ static uint32 MakeTag(const FieldDescriptor* field);
+
+ // Parse a single field. The input should start out positioned immediately
+ // after the tag.
+ static bool ParseAndMergeField(
+ uint32 tag,
+ const FieldDescriptor* field, // May be NULL for unknown
+ Message* message,
+ io::CodedInputStream* input);
+
+ // Serialize a single field.
+ static void SerializeFieldWithCachedSizes(
+ const FieldDescriptor* field, // Cannot be NULL
+ const Message& message,
+ io::CodedOutputStream* output);
+
+ // Compute size of a single field. If the field is a message type, this
+ // will call ByteSize() for the embedded message, insuring that it caches
+ // its size.
+ static int FieldByteSize(
+ const FieldDescriptor* field, // Cannot be NULL
+ const Message& message);
+
+ // Parse/serialize a MessageSet::Item group. Used with messages that use
+ // opion message_set_wire_format = true.
+ static bool ParseAndMergeMessageSetItem(
+ io::CodedInputStream* input,
+ Message* message);
+ static void SerializeMessageSetItemWithCachedSizes(
+ const FieldDescriptor* field,
+ const Message& message,
+ io::CodedOutputStream* output);
+ static int MessageSetItemByteSize(
+ const FieldDescriptor* field,
+ const Message& message);
+
+ // Computes the byte size of a field, excluding tags. For packed fields, it
+ // only includes the size of the raw data, and not the size of the total
+ // length, but for other length-delimited types, the size of the length is
+ // included.
+ static int FieldDataOnlyByteSize(
+ const FieldDescriptor* field, // Cannot be NULL
+ const Message& message);
+
+ enum Operation {
+ PARSE = 0,
+ SERIALIZE = 1,
+ };
+
+ // Verifies that a string field is valid UTF8, logging an error if not.
+ // This function will not be called by newly generated protobuf code
+ // but remains present to support existing code.
+ static void VerifyUTF8String(const char* data, int size, Operation op);
+ // The NamedField variant takes a field name in order to produce an
+ // informative error message if verification fails.
+ static void VerifyUTF8StringNamedField(const char* data,
+ int size,
+ Operation op,
+ const char* field_name);
+
+ private:
+ // Skip a MessageSet field.
+ static bool SkipMessageSetField(io::CodedInputStream* input,
+ uint32 field_number,
+ UnknownFieldSet* unknown_fields);
+
+ // Parse a MessageSet field.
+ static bool ParseAndMergeMessageSetField(uint32 field_number,
+ const FieldDescriptor* field,
+ Message* message,
+ io::CodedInputStream* input);
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(WireFormat);
+};
+
+// Subclass of FieldSkipper which saves skipped fields to an UnknownFieldSet.
+class LIBPROTOBUF_EXPORT UnknownFieldSetFieldSkipper : public FieldSkipper {
+ public:
+ UnknownFieldSetFieldSkipper(UnknownFieldSet* unknown_fields)
+ : unknown_fields_(unknown_fields) {}
+ virtual ~UnknownFieldSetFieldSkipper() {}
+
+ // implements FieldSkipper -----------------------------------------
+ virtual bool SkipField(io::CodedInputStream* input, uint32 tag);
+ virtual bool SkipMessage(io::CodedInputStream* input);
+ virtual void SkipUnknownEnum(int field_number, int value);
+
+ protected:
+ UnknownFieldSet* unknown_fields_;
+};
+
+// inline methods ====================================================
+
+inline WireFormatLite::WireType WireFormat::WireTypeForField(
+ const FieldDescriptor* field) {
+ if (field->is_packed()) {
+ return WireFormatLite::WIRETYPE_LENGTH_DELIMITED;
+ } else {
+ return WireTypeForFieldType(field->type());
+ }
+}
+
+inline WireFormatLite::WireType WireFormat::WireTypeForFieldType(
+ FieldDescriptor::Type type) {
+ // Some compilers don't like enum -> enum casts, so we implicit_cast to
+ // int first.
+ return WireFormatLite::WireTypeForFieldType(
+ static_cast<WireFormatLite::FieldType>(
+ implicit_cast<int>(type)));
+}
+
+inline uint32 WireFormat::MakeTag(const FieldDescriptor* field) {
+ return WireFormatLite::MakeTag(field->number(), WireTypeForField(field));
+}
+
+inline int WireFormat::TagSize(int field_number, FieldDescriptor::Type type) {
+ // Some compilers don't like enum -> enum casts, so we implicit_cast to
+ // int first.
+ return WireFormatLite::TagSize(field_number,
+ static_cast<WireFormatLite::FieldType>(
+ implicit_cast<int>(type)));
+}
+
+inline void WireFormat::VerifyUTF8String(const char* data, int size,
+ WireFormat::Operation op) {
+#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+ WireFormatLite::VerifyUtf8String(
+ data, size, static_cast<WireFormatLite::Operation>(op), NULL);
+#else
+ // Avoid the compiler warning about unused variables.
+ (void)data; (void)size; (void)op;
+#endif
+}
+
+inline void WireFormat::VerifyUTF8StringNamedField(
+ const char* data, int size, WireFormat::Operation op,
+ const char* field_name) {
+#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+ WireFormatLite::VerifyUtf8String(
+ data, size, static_cast<WireFormatLite::Operation>(op), field_name);
+#endif
+}
+
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_WIRE_FORMAT_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.cc b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.cc
new file mode 100644
index 0000000000..05cc0854cb
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.cc
@@ -0,0 +1,545 @@
+// 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.
+
+#include <google/protobuf/wire_format_lite_inl.h>
+
+#include <stack>
+#include <string>
+#include <vector>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/stringprintf.h>
+#include <google/protobuf/io/coded_stream_inl.h>
+#include <google/protobuf/io/zero_copy_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl_lite.h>
+
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+// Old version of MSVC doesn't like definitions of inline constants, GCC
+// requires them.
+const int WireFormatLite::kMessageSetItemStartTag;
+const int WireFormatLite::kMessageSetItemEndTag;
+const int WireFormatLite::kMessageSetTypeIdTag;
+const int WireFormatLite::kMessageSetMessageTag;
+
+#endif
+
+// IBM xlC requires prefixing constants with WireFormatLite::
+const int WireFormatLite::kMessageSetItemTagsSize =
+ io::CodedOutputStream::StaticVarintSize32<
+ WireFormatLite::kMessageSetItemStartTag>::value +
+ io::CodedOutputStream::StaticVarintSize32<
+ WireFormatLite::kMessageSetItemEndTag>::value +
+ io::CodedOutputStream::StaticVarintSize32<
+ WireFormatLite::kMessageSetTypeIdTag>::value +
+ io::CodedOutputStream::StaticVarintSize32<
+ WireFormatLite::kMessageSetMessageTag>::value;
+
+const WireFormatLite::CppType
+WireFormatLite::kFieldTypeToCppTypeMap[MAX_FIELD_TYPE + 1] = {
+ static_cast<CppType>(0), // 0 is reserved for errors
+
+ CPPTYPE_DOUBLE, // TYPE_DOUBLE
+ CPPTYPE_FLOAT, // TYPE_FLOAT
+ CPPTYPE_INT64, // TYPE_INT64
+ CPPTYPE_UINT64, // TYPE_UINT64
+ CPPTYPE_INT32, // TYPE_INT32
+ CPPTYPE_UINT64, // TYPE_FIXED64
+ CPPTYPE_UINT32, // TYPE_FIXED32
+ CPPTYPE_BOOL, // TYPE_BOOL
+ CPPTYPE_STRING, // TYPE_STRING
+ CPPTYPE_MESSAGE, // TYPE_GROUP
+ CPPTYPE_MESSAGE, // TYPE_MESSAGE
+ CPPTYPE_STRING, // TYPE_BYTES
+ CPPTYPE_UINT32, // TYPE_UINT32
+ CPPTYPE_ENUM, // TYPE_ENUM
+ CPPTYPE_INT32, // TYPE_SFIXED32
+ CPPTYPE_INT64, // TYPE_SFIXED64
+ CPPTYPE_INT32, // TYPE_SINT32
+ CPPTYPE_INT64, // TYPE_SINT64
+};
+
+const WireFormatLite::WireType
+WireFormatLite::kWireTypeForFieldType[MAX_FIELD_TYPE + 1] = {
+ static_cast<WireFormatLite::WireType>(-1), // invalid
+ WireFormatLite::WIRETYPE_FIXED64, // TYPE_DOUBLE
+ WireFormatLite::WIRETYPE_FIXED32, // TYPE_FLOAT
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_INT64
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_UINT64
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_INT32
+ WireFormatLite::WIRETYPE_FIXED64, // TYPE_FIXED64
+ WireFormatLite::WIRETYPE_FIXED32, // TYPE_FIXED32
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_BOOL
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED, // TYPE_STRING
+ WireFormatLite::WIRETYPE_START_GROUP, // TYPE_GROUP
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED, // TYPE_MESSAGE
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED, // TYPE_BYTES
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_UINT32
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_ENUM
+ WireFormatLite::WIRETYPE_FIXED32, // TYPE_SFIXED32
+ WireFormatLite::WIRETYPE_FIXED64, // TYPE_SFIXED64
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_SINT32
+ WireFormatLite::WIRETYPE_VARINT, // TYPE_SINT64
+};
+
+bool WireFormatLite::SkipField(
+ io::CodedInputStream* input, uint32 tag) {
+ switch (WireFormatLite::GetTagWireType(tag)) {
+ case WireFormatLite::WIRETYPE_VARINT: {
+ uint64 value;
+ if (!input->ReadVarint64(&value)) return false;
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_FIXED64: {
+ uint64 value;
+ if (!input->ReadLittleEndian64(&value)) return false;
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_LENGTH_DELIMITED: {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ if (!input->Skip(length)) return false;
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_START_GROUP: {
+ if (!input->IncrementRecursionDepth()) return false;
+ if (!SkipMessage(input)) return false;
+ input->DecrementRecursionDepth();
+ // Check that the ending tag matched the starting tag.
+ if (!input->LastTagWas(WireFormatLite::MakeTag(
+ WireFormatLite::GetTagFieldNumber(tag),
+ WireFormatLite::WIRETYPE_END_GROUP))) {
+ return false;
+ }
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_END_GROUP: {
+ return false;
+ }
+ case WireFormatLite::WIRETYPE_FIXED32: {
+ uint32 value;
+ if (!input->ReadLittleEndian32(&value)) return false;
+ return true;
+ }
+ default: {
+ return false;
+ }
+ }
+}
+
+bool WireFormatLite::SkipField(
+ io::CodedInputStream* input, uint32 tag, io::CodedOutputStream* output) {
+ switch (WireFormatLite::GetTagWireType(tag)) {
+ case WireFormatLite::WIRETYPE_VARINT: {
+ uint64 value;
+ if (!input->ReadVarint64(&value)) return false;
+ output->WriteVarint32(tag);
+ output->WriteVarint64(value);
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_FIXED64: {
+ uint64 value;
+ if (!input->ReadLittleEndian64(&value)) return false;
+ output->WriteVarint32(tag);
+ output->WriteLittleEndian64(value);
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_LENGTH_DELIMITED: {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ output->WriteVarint32(tag);
+ output->WriteVarint32(length);
+ // TODO(mkilavuz): Provide API to prevent extra string copying.
+ string temp;
+ if (!input->ReadString(&temp, length)) return false;
+ output->WriteString(temp);
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_START_GROUP: {
+ output->WriteVarint32(tag);
+ if (!input->IncrementRecursionDepth()) return false;
+ if (!SkipMessage(input, output)) return false;
+ input->DecrementRecursionDepth();
+ // Check that the ending tag matched the starting tag.
+ if (!input->LastTagWas(WireFormatLite::MakeTag(
+ WireFormatLite::GetTagFieldNumber(tag),
+ WireFormatLite::WIRETYPE_END_GROUP))) {
+ return false;
+ }
+ return true;
+ }
+ case WireFormatLite::WIRETYPE_END_GROUP: {
+ return false;
+ }
+ case WireFormatLite::WIRETYPE_FIXED32: {
+ uint32 value;
+ if (!input->ReadLittleEndian32(&value)) return false;
+ output->WriteVarint32(tag);
+ output->WriteLittleEndian32(value);
+ return true;
+ }
+ default: {
+ return false;
+ }
+ }
+}
+
+bool WireFormatLite::SkipMessage(io::CodedInputStream* input) {
+ while (true) {
+ uint32 tag = input->ReadTag();
+ if (tag == 0) {
+ // End of input. This is a valid place to end, so return true.
+ return true;
+ }
+
+ WireFormatLite::WireType wire_type = WireFormatLite::GetTagWireType(tag);
+
+ if (wire_type == WireFormatLite::WIRETYPE_END_GROUP) {
+ // Must be the end of the message.
+ return true;
+ }
+
+ if (!SkipField(input, tag)) return false;
+ }
+}
+
+bool WireFormatLite::SkipMessage(io::CodedInputStream* input,
+ io::CodedOutputStream* output) {
+ while (true) {
+ uint32 tag = input->ReadTag();
+ if (tag == 0) {
+ // End of input. This is a valid place to end, so return true.
+ return true;
+ }
+
+ WireFormatLite::WireType wire_type = WireFormatLite::GetTagWireType(tag);
+
+ if (wire_type == WireFormatLite::WIRETYPE_END_GROUP) {
+ output->WriteVarint32(tag);
+ // Must be the end of the message.
+ return true;
+ }
+
+ if (!SkipField(input, tag, output)) return false;
+ }
+}
+
+bool FieldSkipper::SkipField(
+ io::CodedInputStream* input, uint32 tag) {
+ return WireFormatLite::SkipField(input, tag);
+}
+
+bool FieldSkipper::SkipMessage(io::CodedInputStream* input) {
+ return WireFormatLite::SkipMessage(input);
+}
+
+void FieldSkipper::SkipUnknownEnum(
+ int /* field_number */, int /* value */) {
+ // Nothing.
+}
+
+bool CodedOutputStreamFieldSkipper::SkipField(
+ io::CodedInputStream* input, uint32 tag) {
+ return WireFormatLite::SkipField(input, tag, unknown_fields_);
+}
+
+bool CodedOutputStreamFieldSkipper::SkipMessage(io::CodedInputStream* input) {
+ return WireFormatLite::SkipMessage(input, unknown_fields_);
+}
+
+void CodedOutputStreamFieldSkipper::SkipUnknownEnum(
+ int field_number, int value) {
+ unknown_fields_->WriteVarint32(field_number);
+ unknown_fields_->WriteVarint64(value);
+}
+
+bool WireFormatLite::ReadPackedEnumNoInline(io::CodedInputStream* input,
+ bool (*is_valid)(int),
+ RepeatedField<int>* values) {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ io::CodedInputStream::Limit limit = input->PushLimit(length);
+ while (input->BytesUntilLimit() > 0) {
+ int value;
+ if (!google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, WireFormatLite::TYPE_ENUM>(input, &value)) {
+ return false;
+ }
+ if (is_valid == NULL || is_valid(value)) {
+ values->Add(value);
+ }
+ }
+ input->PopLimit(limit);
+ return true;
+}
+
+bool WireFormatLite::ReadPackedEnumPreserveUnknowns(
+ io::CodedInputStream* input,
+ int field_number,
+ bool (*is_valid)(int),
+ io::CodedOutputStream* unknown_fields_stream,
+ RepeatedField<int>* values) {
+ uint32 length;
+ if (!input->ReadVarint32(&length)) return false;
+ io::CodedInputStream::Limit limit = input->PushLimit(length);
+ while (input->BytesUntilLimit() > 0) {
+ int value;
+ if (!google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ int, WireFormatLite::TYPE_ENUM>(input, &value)) {
+ return false;
+ }
+ if (is_valid == NULL || is_valid(value)) {
+ values->Add(value);
+ } else {
+ uint32 tag = WireFormatLite::MakeTag(field_number,
+ WireFormatLite::WIRETYPE_VARINT);
+ unknown_fields_stream->WriteVarint32(tag);
+ unknown_fields_stream->WriteVarint32(value);
+ }
+ }
+ input->PopLimit(limit);
+ return true;
+}
+
+void WireFormatLite::WriteInt32(int field_number, int32 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteInt32NoTag(value, output);
+}
+void WireFormatLite::WriteInt64(int field_number, int64 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteInt64NoTag(value, output);
+}
+void WireFormatLite::WriteUInt32(int field_number, uint32 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteUInt32NoTag(value, output);
+}
+void WireFormatLite::WriteUInt64(int field_number, uint64 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteUInt64NoTag(value, output);
+}
+void WireFormatLite::WriteSInt32(int field_number, int32 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteSInt32NoTag(value, output);
+}
+void WireFormatLite::WriteSInt64(int field_number, int64 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteSInt64NoTag(value, output);
+}
+void WireFormatLite::WriteFixed32(int field_number, uint32 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_FIXED32, output);
+ WriteFixed32NoTag(value, output);
+}
+void WireFormatLite::WriteFixed64(int field_number, uint64 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_FIXED64, output);
+ WriteFixed64NoTag(value, output);
+}
+void WireFormatLite::WriteSFixed32(int field_number, int32 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_FIXED32, output);
+ WriteSFixed32NoTag(value, output);
+}
+void WireFormatLite::WriteSFixed64(int field_number, int64 value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_FIXED64, output);
+ WriteSFixed64NoTag(value, output);
+}
+void WireFormatLite::WriteFloat(int field_number, float value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_FIXED32, output);
+ WriteFloatNoTag(value, output);
+}
+void WireFormatLite::WriteDouble(int field_number, double value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_FIXED64, output);
+ WriteDoubleNoTag(value, output);
+}
+void WireFormatLite::WriteBool(int field_number, bool value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteBoolNoTag(value, output);
+}
+void WireFormatLite::WriteEnum(int field_number, int value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_VARINT, output);
+ WriteEnumNoTag(value, output);
+}
+
+void WireFormatLite::WriteString(int field_number, const string& value,
+ io::CodedOutputStream* output) {
+ // String is for UTF-8 text only
+ WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
+ GOOGLE_CHECK_LE(value.size(), kint32max);
+ output->WriteVarint32(value.size());
+ output->WriteString(value);
+}
+void WireFormatLite::WriteStringMaybeAliased(
+ int field_number, const string& value,
+ io::CodedOutputStream* output) {
+ // String is for UTF-8 text only
+ WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
+ GOOGLE_CHECK_LE(value.size(), kint32max);
+ output->WriteVarint32(value.size());
+ output->WriteRawMaybeAliased(value.data(), value.size());
+}
+void WireFormatLite::WriteBytes(int field_number, const string& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
+ GOOGLE_CHECK_LE(value.size(), kint32max);
+ output->WriteVarint32(value.size());
+ output->WriteString(value);
+}
+void WireFormatLite::WriteBytesMaybeAliased(
+ int field_number, const string& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
+ GOOGLE_CHECK_LE(value.size(), kint32max);
+ output->WriteVarint32(value.size());
+ output->WriteRawMaybeAliased(value.data(), value.size());
+}
+
+
+void WireFormatLite::WriteGroup(int field_number,
+ const MessageLite& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_START_GROUP, output);
+ value.SerializeWithCachedSizes(output);
+ WriteTag(field_number, WIRETYPE_END_GROUP, output);
+}
+
+void WireFormatLite::WriteMessage(int field_number,
+ const MessageLite& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
+ const int size = value.GetCachedSize();
+ output->WriteVarint32(size);
+ value.SerializeWithCachedSizes(output);
+}
+
+void WireFormatLite::WriteGroupMaybeToArray(int field_number,
+ const MessageLite& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_START_GROUP, output);
+ const int size = value.GetCachedSize();
+ uint8* target = output->GetDirectBufferForNBytesAndAdvance(size);
+ if (target != NULL) {
+ uint8* end = value.InternalSerializeWithCachedSizesToArray(
+ output->IsSerializationDeterminstic(), target);
+ GOOGLE_DCHECK_EQ(end - target, size);
+ } else {
+ value.SerializeWithCachedSizes(output);
+ }
+ WriteTag(field_number, WIRETYPE_END_GROUP, output);
+}
+
+void WireFormatLite::WriteMessageMaybeToArray(int field_number,
+ const MessageLite& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
+ const int size = value.GetCachedSize();
+ output->WriteVarint32(size);
+ uint8* target = output->GetDirectBufferForNBytesAndAdvance(size);
+ if (target != NULL) {
+ uint8* end = value.InternalSerializeWithCachedSizesToArray(
+ output->IsSerializationDeterminstic(), target);
+ GOOGLE_DCHECK_EQ(end - target, size);
+ } else {
+ value.SerializeWithCachedSizes(output);
+ }
+}
+
+GOOGLE_ATTRIBUTE_ALWAYS_INLINE static bool ReadBytesToString(
+ io::CodedInputStream* input, string* value);
+inline static bool ReadBytesToString(io::CodedInputStream* input,
+ string* value) {
+ uint32 length;
+ return input->ReadVarint32(&length) &&
+ input->InternalReadStringInline(value, length);
+}
+
+bool WireFormatLite::ReadBytes(io::CodedInputStream* input, string* value) {
+ return ReadBytesToString(input, value);
+}
+
+bool WireFormatLite::ReadBytes(io::CodedInputStream* input, string** p) {
+ if (*p == &::google::protobuf::internal::GetEmptyStringAlreadyInited()) {
+ *p = new ::std::string();
+ }
+ return ReadBytesToString(input, *p);
+}
+
+bool WireFormatLite::VerifyUtf8String(const char* data,
+ int size,
+ Operation op,
+ const char* field_name) {
+ if (!IsStructurallyValidUTF8(data, size)) {
+ const char* operation_str = NULL;
+ switch (op) {
+ case PARSE:
+ operation_str = "parsing";
+ break;
+ case SERIALIZE:
+ operation_str = "serializing";
+ break;
+ // no default case: have the compiler warn if a case is not covered.
+ }
+ string quoted_field_name = "";
+ if (field_name != NULL) {
+ quoted_field_name = StringPrintf(" '%s'", field_name);
+ }
+ // no space below to avoid double space when the field name is missing.
+ GOOGLE_LOG(ERROR) << "String field" << quoted_field_name << " contains invalid "
+ << "UTF-8 data when " << operation_str << " a protocol "
+ << "buffer. Use the 'bytes' type if you intend to send raw "
+ << "bytes. ";
+ return false;
+ }
+ return true;
+}
+
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.h b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.h
new file mode 100644
index 0000000000..580d4db03b
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite.h
@@ -0,0 +1,724 @@
+// 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)
+// atenasio@google.com (Chris Atenasio) (ZigZag transform)
+// wink@google.com (Wink Saville) (refactored from wire_format.h)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+//
+// This header is logically internal, but is made public because it is used
+// from protocol-compiler-generated code, which may reside in other components.
+
+#ifndef GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_H__
+#define GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_H__
+
+#include <string>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/message_lite.h>
+#include <google/protobuf/io/coded_stream.h> // for CodedOutputStream::Varint32Size
+
+namespace google {
+
+namespace protobuf {
+ template <typename T> class RepeatedField; // repeated_field.h
+}
+
+namespace protobuf {
+namespace internal {
+
+class StringPieceField;
+
+// This class is for internal use by the protocol buffer library and by
+// protocol-complier-generated message classes. It must not be called
+// directly by clients.
+//
+// This class contains helpers for implementing the binary protocol buffer
+// wire format without the need for reflection. Use WireFormat when using
+// reflection.
+//
+// This class is really a namespace that contains only static methods.
+class LIBPROTOBUF_EXPORT WireFormatLite {
+ public:
+
+ // -----------------------------------------------------------------
+ // Helper constants and functions related to the format. These are
+ // mostly meant for internal and generated code to use.
+
+ // The wire format is composed of a sequence of tag/value pairs, each
+ // of which contains the value of one field (or one element of a repeated
+ // field). Each tag is encoded as a varint. The lower bits of the tag
+ // identify its wire type, which specifies the format of the data to follow.
+ // The rest of the bits contain the field number. Each type of field (as
+ // declared by FieldDescriptor::Type, in descriptor.h) maps to one of
+ // these wire types. Immediately following each tag is the field's value,
+ // encoded in the format specified by the wire type. Because the tag
+ // identifies the encoding of this data, it is possible to skip
+ // unrecognized fields for forwards compatibility.
+
+ enum WireType {
+ WIRETYPE_VARINT = 0,
+ WIRETYPE_FIXED64 = 1,
+ WIRETYPE_LENGTH_DELIMITED = 2,
+ WIRETYPE_START_GROUP = 3,
+ WIRETYPE_END_GROUP = 4,
+ WIRETYPE_FIXED32 = 5,
+ };
+
+ // Lite alternative to FieldDescriptor::Type. Must be kept in sync.
+ enum FieldType {
+ TYPE_DOUBLE = 1,
+ TYPE_FLOAT = 2,
+ TYPE_INT64 = 3,
+ TYPE_UINT64 = 4,
+ TYPE_INT32 = 5,
+ TYPE_FIXED64 = 6,
+ TYPE_FIXED32 = 7,
+ TYPE_BOOL = 8,
+ TYPE_STRING = 9,
+ TYPE_GROUP = 10,
+ TYPE_MESSAGE = 11,
+ TYPE_BYTES = 12,
+ TYPE_UINT32 = 13,
+ TYPE_ENUM = 14,
+ TYPE_SFIXED32 = 15,
+ TYPE_SFIXED64 = 16,
+ TYPE_SINT32 = 17,
+ TYPE_SINT64 = 18,
+ MAX_FIELD_TYPE = 18,
+ };
+
+ // Lite alternative to FieldDescriptor::CppType. Must be kept in sync.
+ enum CppType {
+ CPPTYPE_INT32 = 1,
+ CPPTYPE_INT64 = 2,
+ CPPTYPE_UINT32 = 3,
+ CPPTYPE_UINT64 = 4,
+ CPPTYPE_DOUBLE = 5,
+ CPPTYPE_FLOAT = 6,
+ CPPTYPE_BOOL = 7,
+ CPPTYPE_ENUM = 8,
+ CPPTYPE_STRING = 9,
+ CPPTYPE_MESSAGE = 10,
+ MAX_CPPTYPE = 10,
+ };
+
+ // Helper method to get the CppType for a particular Type.
+ static CppType FieldTypeToCppType(FieldType type);
+
+ // Given a FieldSescriptor::Type return its WireType
+ static inline WireFormatLite::WireType WireTypeForFieldType(
+ WireFormatLite::FieldType type) {
+ return kWireTypeForFieldType[type];
+ }
+
+ // Number of bits in a tag which identify the wire type.
+ static const int kTagTypeBits = 3;
+ // Mask for those bits.
+ static const uint32 kTagTypeMask = (1 << kTagTypeBits) - 1;
+
+ // Helper functions for encoding and decoding tags. (Inlined below and in
+ // _inl.h)
+ //
+ // This is different from MakeTag(field->number(), field->type()) in the case
+ // of packed repeated fields.
+ static uint32 MakeTag(int field_number, WireType type);
+ static WireType GetTagWireType(uint32 tag);
+ static int GetTagFieldNumber(uint32 tag);
+
+ // Compute the byte size of a tag. For groups, this includes both the start
+ // and end tags.
+ static inline int TagSize(int field_number, WireFormatLite::FieldType type);
+
+ // Skips a field value with the given tag. The input should start
+ // positioned immediately after the tag. Skipped values are simply discarded,
+ // not recorded anywhere. See WireFormat::SkipField() for a version that
+ // records to an UnknownFieldSet.
+ static bool SkipField(io::CodedInputStream* input, uint32 tag);
+
+ // Skips a field value with the given tag. The input should start
+ // positioned immediately after the tag. Skipped values are recorded to a
+ // CodedOutputStream.
+ static bool SkipField(io::CodedInputStream* input, uint32 tag,
+ io::CodedOutputStream* output);
+
+ // Reads and ignores a message from the input. Skipped values are simply
+ // discarded, not recorded anywhere. See WireFormat::SkipMessage() for a
+ // version that records to an UnknownFieldSet.
+ static bool SkipMessage(io::CodedInputStream* input);
+
+ // Reads and ignores a message from the input. Skipped values are recorded
+ // to a CodedOutputStream.
+ static bool SkipMessage(io::CodedInputStream* input,
+ io::CodedOutputStream* output);
+
+// This macro does the same thing as WireFormatLite::MakeTag(), but the
+// result is usable as a compile-time constant, which makes it usable
+// as a switch case or a template input. WireFormatLite::MakeTag() is more
+// type-safe, though, so prefer it if possible.
+#define GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(FIELD_NUMBER, TYPE) \
+ static_cast<uint32>( \
+ ((FIELD_NUMBER) << ::google::protobuf::internal::WireFormatLite::kTagTypeBits) \
+ | (TYPE))
+
+ // These are the tags for the old MessageSet format, which was defined as:
+ // message MessageSet {
+ // repeated group Item = 1 {
+ // required int32 type_id = 2;
+ // required string message = 3;
+ // }
+ // }
+ static const int kMessageSetItemNumber = 1;
+ static const int kMessageSetTypeIdNumber = 2;
+ static const int kMessageSetMessageNumber = 3;
+ static const int kMessageSetItemStartTag =
+ GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(kMessageSetItemNumber,
+ WireFormatLite::WIRETYPE_START_GROUP);
+ static const int kMessageSetItemEndTag =
+ GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(kMessageSetItemNumber,
+ WireFormatLite::WIRETYPE_END_GROUP);
+ static const int kMessageSetTypeIdTag =
+ GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(kMessageSetTypeIdNumber,
+ WireFormatLite::WIRETYPE_VARINT);
+ static const int kMessageSetMessageTag =
+ GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(kMessageSetMessageNumber,
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED);
+
+ // Byte size of all tags of a MessageSet::Item combined.
+ static const int kMessageSetItemTagsSize;
+
+ // Helper functions for converting between floats/doubles and IEEE-754
+ // uint32s/uint64s so that they can be written. (Assumes your platform
+ // uses IEEE-754 floats.)
+ static uint32 EncodeFloat(float value);
+ static float DecodeFloat(uint32 value);
+ static uint64 EncodeDouble(double value);
+ static double DecodeDouble(uint64 value);
+
+ // Helper functions for mapping signed integers to unsigned integers in
+ // such a way that numbers with small magnitudes will encode to smaller
+ // varints. If you simply static_cast a negative number to an unsigned
+ // number and varint-encode it, it will always take 10 bytes, defeating
+ // the purpose of varint. So, for the "sint32" and "sint64" field types,
+ // we ZigZag-encode the values.
+ static uint32 ZigZagEncode32(int32 n);
+ static int32 ZigZagDecode32(uint32 n);
+ static uint64 ZigZagEncode64(int64 n);
+ static int64 ZigZagDecode64(uint64 n);
+
+ // =================================================================
+ // Methods for reading/writing individual field. The implementations
+ // of these methods are defined in wire_format_lite_inl.h; you must #include
+ // that file to use these.
+
+// Avoid ugly line wrapping
+#define input io::CodedInputStream* input_arg
+#define output io::CodedOutputStream* output_arg
+#define field_number int field_number_arg
+#define INL GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+
+ // Read fields, not including tags. The assumption is that you already
+ // read the tag to determine what field to read.
+
+ // For primitive fields, we just use a templatized routine parameterized by
+ // the represented type and the FieldType. These are specialized with the
+ // appropriate definition for each declared type.
+ template <typename CType, enum FieldType DeclaredType> INL
+ static bool ReadPrimitive(input, CType* value);
+
+ // Reads repeated primitive values, with optimizations for repeats.
+ // tag_size and tag should both be compile-time constants provided by the
+ // protocol compiler.
+ template <typename CType, enum FieldType DeclaredType> INL
+ static bool ReadRepeatedPrimitive(int tag_size,
+ uint32 tag,
+ input,
+ RepeatedField<CType>* value);
+
+ // Identical to ReadRepeatedPrimitive, except will not inline the
+ // implementation.
+ template <typename CType, enum FieldType DeclaredType>
+ static bool ReadRepeatedPrimitiveNoInline(int tag_size,
+ uint32 tag,
+ input,
+ RepeatedField<CType>* value);
+
+ // Reads a primitive value directly from the provided buffer. It returns a
+ // pointer past the segment of data that was read.
+ //
+ // This is only implemented for the types with fixed wire size, e.g.
+ // float, double, and the (s)fixed* types.
+ template <typename CType, enum FieldType DeclaredType> INL
+ static const uint8* ReadPrimitiveFromArray(const uint8* buffer, CType* value);
+
+ // Reads a primitive packed field.
+ //
+ // This is only implemented for packable types.
+ template <typename CType, enum FieldType DeclaredType> INL
+ static bool ReadPackedPrimitive(input, RepeatedField<CType>* value);
+
+ // Identical to ReadPackedPrimitive, except will not inline the
+ // implementation.
+ template <typename CType, enum FieldType DeclaredType>
+ static bool ReadPackedPrimitiveNoInline(input, RepeatedField<CType>* value);
+
+ // Read a packed enum field. If the is_valid function is not NULL, values for
+ // which is_valid(value) returns false are silently dropped.
+ static bool ReadPackedEnumNoInline(input,
+ bool (*is_valid)(int),
+ RepeatedField<int>* values);
+
+ // Read a packed enum field. If the is_valid function is not NULL, values for
+ // which is_valid(value) returns false are appended to unknown_fields_stream.
+ static bool ReadPackedEnumPreserveUnknowns(
+ input,
+ field_number,
+ bool (*is_valid)(int),
+ io::CodedOutputStream* unknown_fields_stream,
+ RepeatedField<int>* values);
+
+ // Read a string. ReadString(..., string* value) requires an existing string.
+ static inline bool ReadString(input, string* value);
+ // ReadString(..., string** p) is internal-only, and should only be called
+ // from generated code. It starts by setting *p to "new string"
+ // if *p == &GetEmptyStringAlreadyInited(). It then invokes
+ // ReadString(input, *p). This is useful for reducing code size.
+ static inline bool ReadString(input, string** p);
+ // Analogous to ReadString().
+ static bool ReadBytes(input, string* value);
+ static bool ReadBytes(input, string** p);
+
+
+ enum Operation {
+ PARSE = 0,
+ SERIALIZE = 1,
+ };
+
+ // Returns true if the data is valid UTF-8.
+ static bool VerifyUtf8String(const char* data, int size,
+ Operation op,
+ const char* field_name);
+
+ static inline bool ReadGroup (field_number, input, MessageLite* value);
+ static inline bool ReadMessage(input, MessageLite* value);
+
+ // Like above, but de-virtualize the call to MergePartialFromCodedStream().
+ // The pointer must point at an instance of MessageType, *not* a subclass (or
+ // the subclass must not override MergePartialFromCodedStream()).
+ template<typename MessageType>
+ static inline bool ReadGroupNoVirtual(field_number, input,
+ MessageType* value);
+ template<typename MessageType>
+ static inline bool ReadMessageNoVirtual(input, MessageType* value);
+
+ // The same, but do not modify input's recursion depth. This is useful
+ // when reading a bunch of groups or messages in a loop, because then the
+ // recursion depth can be incremented before the loop and decremented after.
+ template<typename MessageType>
+ static inline bool ReadGroupNoVirtualNoRecursionDepth(field_number, input,
+ MessageType* value);
+
+ template<typename MessageType>
+ static inline bool ReadMessageNoVirtualNoRecursionDepth(input,
+ MessageType* value);
+
+ // Write a tag. The Write*() functions typically include the tag, so
+ // normally there's no need to call this unless using the Write*NoTag()
+ // variants.
+ INL static void WriteTag(field_number, WireType type, output);
+
+ // Write fields, without tags.
+ INL static void WriteInt32NoTag (int32 value, output);
+ INL static void WriteInt64NoTag (int64 value, output);
+ INL static void WriteUInt32NoTag (uint32 value, output);
+ INL static void WriteUInt64NoTag (uint64 value, output);
+ INL static void WriteSInt32NoTag (int32 value, output);
+ INL static void WriteSInt64NoTag (int64 value, output);
+ INL static void WriteFixed32NoTag (uint32 value, output);
+ INL static void WriteFixed64NoTag (uint64 value, output);
+ INL static void WriteSFixed32NoTag(int32 value, output);
+ INL static void WriteSFixed64NoTag(int64 value, output);
+ INL static void WriteFloatNoTag (float value, output);
+ INL static void WriteDoubleNoTag (double value, output);
+ INL static void WriteBoolNoTag (bool value, output);
+ INL static void WriteEnumNoTag (int value, output);
+
+ // Write fields, including tags.
+ static void WriteInt32 (field_number, int32 value, output);
+ static void WriteInt64 (field_number, int64 value, output);
+ static void WriteUInt32 (field_number, uint32 value, output);
+ static void WriteUInt64 (field_number, uint64 value, output);
+ static void WriteSInt32 (field_number, int32 value, output);
+ static void WriteSInt64 (field_number, int64 value, output);
+ static void WriteFixed32 (field_number, uint32 value, output);
+ static void WriteFixed64 (field_number, uint64 value, output);
+ static void WriteSFixed32(field_number, int32 value, output);
+ static void WriteSFixed64(field_number, int64 value, output);
+ static void WriteFloat (field_number, float value, output);
+ static void WriteDouble (field_number, double value, output);
+ static void WriteBool (field_number, bool value, output);
+ static void WriteEnum (field_number, int value, output);
+
+ static void WriteString(field_number, const string& value, output);
+ static void WriteBytes (field_number, const string& value, output);
+ static void WriteStringMaybeAliased(
+ field_number, const string& value, output);
+ static void WriteBytesMaybeAliased(
+ field_number, const string& value, output);
+
+ static void WriteGroup(
+ field_number, const MessageLite& value, output);
+ static void WriteMessage(
+ field_number, const MessageLite& value, output);
+ // Like above, but these will check if the output stream has enough
+ // space to write directly to a flat array.
+ static void WriteGroupMaybeToArray(
+ field_number, const MessageLite& value, output);
+ static void WriteMessageMaybeToArray(
+ field_number, const MessageLite& value, output);
+
+ // Like above, but de-virtualize the call to SerializeWithCachedSizes(). The
+ // pointer must point at an instance of MessageType, *not* a subclass (or
+ // the subclass must not override SerializeWithCachedSizes()).
+ template<typename MessageType>
+ static inline void WriteGroupNoVirtual(
+ field_number, const MessageType& value, output);
+ template<typename MessageType>
+ static inline void WriteMessageNoVirtual(
+ field_number, const MessageType& value, output);
+
+#undef output
+#define output uint8* target
+
+ // Like above, but use only *ToArray methods of CodedOutputStream.
+ INL static uint8* WriteTagToArray(field_number, WireType type, output);
+
+ // Write fields, without tags.
+ INL static uint8* WriteInt32NoTagToArray (int32 value, output);
+ INL static uint8* WriteInt64NoTagToArray (int64 value, output);
+ INL static uint8* WriteUInt32NoTagToArray (uint32 value, output);
+ INL static uint8* WriteUInt64NoTagToArray (uint64 value, output);
+ INL static uint8* WriteSInt32NoTagToArray (int32 value, output);
+ INL static uint8* WriteSInt64NoTagToArray (int64 value, output);
+ INL static uint8* WriteFixed32NoTagToArray (uint32 value, output);
+ INL static uint8* WriteFixed64NoTagToArray (uint64 value, output);
+ INL static uint8* WriteSFixed32NoTagToArray(int32 value, output);
+ INL static uint8* WriteSFixed64NoTagToArray(int64 value, output);
+ INL static uint8* WriteFloatNoTagToArray (float value, output);
+ INL static uint8* WriteDoubleNoTagToArray (double value, output);
+ INL static uint8* WriteBoolNoTagToArray (bool value, output);
+ INL static uint8* WriteEnumNoTagToArray (int value, output);
+
+ // Write fields, including tags.
+ INL static uint8* WriteInt32ToArray(field_number, int32 value, output);
+ INL static uint8* WriteInt64ToArray(field_number, int64 value, output);
+ INL static uint8* WriteUInt32ToArray(field_number, uint32 value, output);
+ INL static uint8* WriteUInt64ToArray(field_number, uint64 value, output);
+ INL static uint8* WriteSInt32ToArray(field_number, int32 value, output);
+ INL static uint8* WriteSInt64ToArray(field_number, int64 value, output);
+ INL static uint8* WriteFixed32ToArray(field_number, uint32 value, output);
+ INL static uint8* WriteFixed64ToArray(field_number, uint64 value, output);
+ INL static uint8* WriteSFixed32ToArray(field_number, int32 value, output);
+ INL static uint8* WriteSFixed64ToArray(field_number, int64 value, output);
+ INL static uint8* WriteFloatToArray(field_number, float value, output);
+ INL static uint8* WriteDoubleToArray(field_number, double value, output);
+ INL static uint8* WriteBoolToArray(field_number, bool value, output);
+ INL static uint8* WriteEnumToArray(field_number, int value, output);
+
+ INL static uint8* WriteStringToArray(
+ field_number, const string& value, output);
+ INL static uint8* WriteBytesToArray(
+ field_number, const string& value, output);
+
+ // Whether to serialize deterministically (e.g., map keys are
+ // sorted) is a property of a CodedOutputStream, and in the process
+ // of serialization, the "ToArray" variants may be invoked. But they don't
+ // have a CodedOutputStream available, so they get an additional parameter
+ // telling them whether to serialize deterministically.
+ INL static uint8* InternalWriteGroupToArray(
+ field_number, const MessageLite& value, bool deterministic, output);
+ INL static uint8* InternalWriteMessageToArray(
+ field_number, const MessageLite& value, bool deterministic, output);
+
+ // Like above, but de-virtualize the call to SerializeWithCachedSizes(). The
+ // pointer must point at an instance of MessageType, *not* a subclass (or
+ // the subclass must not override SerializeWithCachedSizes()).
+ template<typename MessageType>
+ INL static uint8* InternalWriteGroupNoVirtualToArray(
+ field_number, const MessageType& value, bool deterministic, output);
+ template<typename MessageType>
+ INL static uint8* InternalWriteMessageNoVirtualToArray(
+ field_number, const MessageType& value, bool deterministic, output);
+
+ // For backward-compatibility, the last four methods also have versions
+ // that are non-deterministic always.
+ INL static uint8* WriteGroupToArray(
+ field_number, const MessageLite& value, output) {
+ return InternalWriteGroupToArray(field_number_arg, value, false, target);
+ }
+ INL static uint8* WriteMessageToArray(
+ field_number, const MessageLite& value, output) {
+ return InternalWriteMessageToArray(field_number_arg, value, false, target);
+ }
+ template<typename MessageType>
+ INL static uint8* WriteGroupNoVirtualToArray(
+ field_number, const MessageType& value, output) {
+ return InternalWriteGroupNoVirtualToArray(field_number_arg, value, false,
+ target);
+ }
+ template<typename MessageType>
+ INL static uint8* WriteMessageNoVirtualToArray(
+ field_number, const MessageType& value, output) {
+ return InternalWriteMessageNoVirtualToArray(field_number_arg, value, false,
+ target);
+ }
+
+#undef output
+#undef input
+#undef INL
+
+#undef field_number
+
+ // Compute the byte size of a field. The XxSize() functions do NOT include
+ // the tag, so you must also call TagSize(). (This is because, for repeated
+ // fields, you should only call TagSize() once and multiply it by the element
+ // count, but you may have to call XxSize() for each individual element.)
+ static inline int Int32Size ( int32 value);
+ static inline int Int64Size ( int64 value);
+ static inline int UInt32Size (uint32 value);
+ static inline int UInt64Size (uint64 value);
+ static inline int SInt32Size ( int32 value);
+ static inline int SInt64Size ( int64 value);
+ static inline int EnumSize ( int value);
+
+ // These types always have the same size.
+ static const int kFixed32Size = 4;
+ static const int kFixed64Size = 8;
+ static const int kSFixed32Size = 4;
+ static const int kSFixed64Size = 8;
+ static const int kFloatSize = 4;
+ static const int kDoubleSize = 8;
+ static const int kBoolSize = 1;
+
+ static inline int StringSize(const string& value);
+ static inline int BytesSize (const string& value);
+
+ static inline int GroupSize (const MessageLite& value);
+ static inline int MessageSize(const MessageLite& value);
+
+ // Like above, but de-virtualize the call to ByteSize(). The
+ // pointer must point at an instance of MessageType, *not* a subclass (or
+ // the subclass must not override ByteSize()).
+ template<typename MessageType>
+ static inline int GroupSizeNoVirtual (const MessageType& value);
+ template<typename MessageType>
+ static inline int MessageSizeNoVirtual(const MessageType& value);
+
+ // Given the length of data, calculate the byte size of the data on the
+ // wire if we encode the data as a length delimited field.
+ static inline int LengthDelimitedSize(int length);
+
+ private:
+ // A helper method for the repeated primitive reader. This method has
+ // optimizations for primitive types that have fixed size on the wire, and
+ // can be read using potentially faster paths.
+ template <typename CType, enum FieldType DeclaredType> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static bool ReadRepeatedFixedSizePrimitive(
+ int tag_size,
+ uint32 tag,
+ google::protobuf::io::CodedInputStream* input,
+ RepeatedField<CType>* value);
+
+ // Like ReadRepeatedFixedSizePrimitive but for packed primitive fields.
+ template <typename CType, enum FieldType DeclaredType> GOOGLE_ATTRIBUTE_ALWAYS_INLINE
+ static bool ReadPackedFixedSizePrimitive(google::protobuf::io::CodedInputStream* input,
+ RepeatedField<CType>* value);
+
+ static const CppType kFieldTypeToCppTypeMap[];
+ static const WireFormatLite::WireType kWireTypeForFieldType[];
+
+ GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(WireFormatLite);
+};
+
+// A class which deals with unknown values. The default implementation just
+// discards them. WireFormat defines a subclass which writes to an
+// UnknownFieldSet. This class is used by ExtensionSet::ParseField(), since
+// ExtensionSet is part of the lite library but UnknownFieldSet is not.
+class LIBPROTOBUF_EXPORT FieldSkipper {
+ public:
+ FieldSkipper() {}
+ virtual ~FieldSkipper() {}
+
+ // Skip a field whose tag has already been consumed.
+ virtual bool SkipField(io::CodedInputStream* input, uint32 tag);
+
+ // Skip an entire message or group, up to an end-group tag (which is consumed)
+ // or end-of-stream.
+ virtual bool SkipMessage(io::CodedInputStream* input);
+
+ // Deal with an already-parsed unrecognized enum value. The default
+ // implementation does nothing, but the UnknownFieldSet-based implementation
+ // saves it as an unknown varint.
+ virtual void SkipUnknownEnum(int field_number, int value);
+};
+
+// Subclass of FieldSkipper which saves skipped fields to a CodedOutputStream.
+
+class LIBPROTOBUF_EXPORT CodedOutputStreamFieldSkipper : public FieldSkipper {
+ public:
+ explicit CodedOutputStreamFieldSkipper(io::CodedOutputStream* unknown_fields)
+ : unknown_fields_(unknown_fields) {}
+ virtual ~CodedOutputStreamFieldSkipper() {}
+
+ // implements FieldSkipper -----------------------------------------
+ virtual bool SkipField(io::CodedInputStream* input, uint32 tag);
+ virtual bool SkipMessage(io::CodedInputStream* input);
+ virtual void SkipUnknownEnum(int field_number, int value);
+
+ protected:
+ io::CodedOutputStream* unknown_fields_;
+};
+
+
+// inline methods ====================================================
+
+inline WireFormatLite::CppType
+WireFormatLite::FieldTypeToCppType(FieldType type) {
+ return kFieldTypeToCppTypeMap[type];
+}
+
+inline uint32 WireFormatLite::MakeTag(int field_number, WireType type) {
+ return GOOGLE_PROTOBUF_WIRE_FORMAT_MAKE_TAG(field_number, type);
+}
+
+inline WireFormatLite::WireType WireFormatLite::GetTagWireType(uint32 tag) {
+ return static_cast<WireType>(tag & kTagTypeMask);
+}
+
+inline int WireFormatLite::GetTagFieldNumber(uint32 tag) {
+ return static_cast<int>(tag >> kTagTypeBits);
+}
+
+inline int WireFormatLite::TagSize(int field_number,
+ WireFormatLite::FieldType type) {
+ int result = io::CodedOutputStream::VarintSize32(
+ field_number << kTagTypeBits);
+ if (type == TYPE_GROUP) {
+ // Groups have both a start and an end tag.
+ return result * 2;
+ } else {
+ return result;
+ }
+}
+
+inline uint32 WireFormatLite::EncodeFloat(float value) {
+ union {float f; uint32 i;};
+ f = value;
+ return i;
+}
+
+inline float WireFormatLite::DecodeFloat(uint32 value) {
+ union {float f; uint32 i;};
+ i = value;
+ return f;
+}
+
+inline uint64 WireFormatLite::EncodeDouble(double value) {
+ union {double f; uint64 i;};
+ f = value;
+ return i;
+}
+
+inline double WireFormatLite::DecodeDouble(uint64 value) {
+ union {double f; uint64 i;};
+ i = value;
+ return f;
+}
+
+// ZigZag Transform: Encodes signed integers so that they can be
+// effectively used with varint encoding.
+//
+// varint operates on unsigned integers, encoding smaller numbers into
+// fewer bytes. If you try to use it on a signed integer, it will treat
+// this number as a very large unsigned integer, which means that even
+// small signed numbers like -1 will take the maximum number of bytes
+// (10) to encode. ZigZagEncode() maps signed integers to unsigned
+// in such a way that those with a small absolute value will have smaller
+// encoded values, making them appropriate for encoding using varint.
+//
+// int32 -> uint32
+// -------------------------
+// 0 -> 0
+// -1 -> 1
+// 1 -> 2
+// -2 -> 3
+// ... -> ...
+// 2147483647 -> 4294967294
+// -2147483648 -> 4294967295
+//
+// >> encode >>
+// << decode <<
+
+inline uint32 WireFormatLite::ZigZagEncode32(int32 n) {
+ // Note: the right-shift must be arithmetic
+ return (static_cast<uint32>(n) << 1) ^ (n >> 31);
+}
+
+inline int32 WireFormatLite::ZigZagDecode32(uint32 n) {
+ return (n >> 1) ^ -static_cast<int32>(n & 1);
+}
+
+inline uint64 WireFormatLite::ZigZagEncode64(int64 n) {
+ // Note: the right-shift must be arithmetic
+ return (static_cast<uint64>(n) << 1) ^ (n >> 63);
+}
+
+inline int64 WireFormatLite::ZigZagDecode64(uint64 n) {
+ return (n >> 1) ^ -static_cast<int64>(n & 1);
+}
+
+// String is for UTF-8 text only, but, even so, ReadString() can simply
+// call ReadBytes().
+
+inline bool WireFormatLite::ReadString(io::CodedInputStream* input,
+ string* value) {
+ return ReadBytes(input, value);
+}
+
+inline bool WireFormatLite::ReadString(io::CodedInputStream* input,
+ string** p) {
+ return ReadBytes(input, p);
+}
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite_inl.h b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite_inl.h
new file mode 100644
index 0000000000..93d7c82403
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_lite_inl.h
@@ -0,0 +1,876 @@
+// 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)
+// wink@google.com (Wink Saville) (refactored from wire_format.h)
+// Based on original Protocol Buffers design by
+// Sanjay Ghemawat, Jeff Dean, and others.
+
+#ifndef GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_INL_H__
+#define GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_INL_H__
+
+#ifdef _MSC_VER
+// This is required for min/max on VS2013 only.
+#include <algorithm>
+#endif
+
+#include <string>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/message_lite.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/wire_format_lite.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/arenastring.h>
+
+
+namespace google {
+namespace protobuf {
+namespace internal {
+
+// Implementation details of ReadPrimitive.
+
+template <>
+inline bool WireFormatLite::ReadPrimitive<int32, WireFormatLite::TYPE_INT32>(
+ io::CodedInputStream* input,
+ int32* value) {
+ uint32 temp;
+ if (!input->ReadVarint32(&temp)) return false;
+ *value = static_cast<int32>(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<int64, WireFormatLite::TYPE_INT64>(
+ io::CodedInputStream* input,
+ int64* value) {
+ uint64 temp;
+ if (!input->ReadVarint64(&temp)) return false;
+ *value = static_cast<int64>(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<uint32, WireFormatLite::TYPE_UINT32>(
+ io::CodedInputStream* input,
+ uint32* value) {
+ return input->ReadVarint32(value);
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<uint64, WireFormatLite::TYPE_UINT64>(
+ io::CodedInputStream* input,
+ uint64* value) {
+ return input->ReadVarint64(value);
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<int32, WireFormatLite::TYPE_SINT32>(
+ io::CodedInputStream* input,
+ int32* value) {
+ uint32 temp;
+ if (!input->ReadVarint32(&temp)) return false;
+ *value = ZigZagDecode32(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<int64, WireFormatLite::TYPE_SINT64>(
+ io::CodedInputStream* input,
+ int64* value) {
+ uint64 temp;
+ if (!input->ReadVarint64(&temp)) return false;
+ *value = ZigZagDecode64(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<uint32, WireFormatLite::TYPE_FIXED32>(
+ io::CodedInputStream* input,
+ uint32* value) {
+ return input->ReadLittleEndian32(value);
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<uint64, WireFormatLite::TYPE_FIXED64>(
+ io::CodedInputStream* input,
+ uint64* value) {
+ return input->ReadLittleEndian64(value);
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<int32, WireFormatLite::TYPE_SFIXED32>(
+ io::CodedInputStream* input,
+ int32* value) {
+ uint32 temp;
+ if (!input->ReadLittleEndian32(&temp)) return false;
+ *value = static_cast<int32>(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<int64, WireFormatLite::TYPE_SFIXED64>(
+ io::CodedInputStream* input,
+ int64* value) {
+ uint64 temp;
+ if (!input->ReadLittleEndian64(&temp)) return false;
+ *value = static_cast<int64>(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<float, WireFormatLite::TYPE_FLOAT>(
+ io::CodedInputStream* input,
+ float* value) {
+ uint32 temp;
+ if (!input->ReadLittleEndian32(&temp)) return false;
+ *value = DecodeFloat(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<double, WireFormatLite::TYPE_DOUBLE>(
+ io::CodedInputStream* input,
+ double* value) {
+ uint64 temp;
+ if (!input->ReadLittleEndian64(&temp)) return false;
+ *value = DecodeDouble(temp);
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<bool, WireFormatLite::TYPE_BOOL>(
+ io::CodedInputStream* input,
+ bool* value) {
+ uint64 temp;
+ if (!input->ReadVarint64(&temp)) return false;
+ *value = temp != 0;
+ return true;
+}
+template <>
+inline bool WireFormatLite::ReadPrimitive<int, WireFormatLite::TYPE_ENUM>(
+ io::CodedInputStream* input,
+ int* value) {
+ uint32 temp;
+ if (!input->ReadVarint32(&temp)) return false;
+ *value = static_cast<int>(temp);
+ return true;
+}
+
+template <>
+inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
+ uint32, WireFormatLite::TYPE_FIXED32>(
+ const uint8* buffer,
+ uint32* value) {
+ return io::CodedInputStream::ReadLittleEndian32FromArray(buffer, value);
+}
+template <>
+inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
+ uint64, WireFormatLite::TYPE_FIXED64>(
+ const uint8* buffer,
+ uint64* value) {
+ return io::CodedInputStream::ReadLittleEndian64FromArray(buffer, value);
+}
+template <>
+inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
+ int32, WireFormatLite::TYPE_SFIXED32>(
+ const uint8* buffer,
+ int32* value) {
+ uint32 temp;
+ buffer = io::CodedInputStream::ReadLittleEndian32FromArray(buffer, &temp);
+ *value = static_cast<int32>(temp);
+ return buffer;
+}
+template <>
+inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
+ int64, WireFormatLite::TYPE_SFIXED64>(
+ const uint8* buffer,
+ int64* value) {
+ uint64 temp;
+ buffer = io::CodedInputStream::ReadLittleEndian64FromArray(buffer, &temp);
+ *value = static_cast<int64>(temp);
+ return buffer;
+}
+template <>
+inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
+ float, WireFormatLite::TYPE_FLOAT>(
+ const uint8* buffer,
+ float* value) {
+ uint32 temp;
+ buffer = io::CodedInputStream::ReadLittleEndian32FromArray(buffer, &temp);
+ *value = DecodeFloat(temp);
+ return buffer;
+}
+template <>
+inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
+ double, WireFormatLite::TYPE_DOUBLE>(
+ const uint8* buffer,
+ double* value) {
+ uint64 temp;
+ buffer = io::CodedInputStream::ReadLittleEndian64FromArray(buffer, &temp);
+ *value = DecodeDouble(temp);
+ return buffer;
+}
+
+template <typename CType, enum WireFormatLite::FieldType DeclaredType>
+inline bool WireFormatLite::ReadRepeatedPrimitive(
+ int, // tag_size, unused.
+ uint32 tag,
+ io::CodedInputStream* input,
+ RepeatedField<CType>* values) {
+ CType value;
+ if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
+ values->Add(value);
+ int elements_already_reserved = values->Capacity() - values->size();
+ while (elements_already_reserved > 0 && input->ExpectTag(tag)) {
+ if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
+ values->AddAlreadyReserved(value);
+ elements_already_reserved--;
+ }
+ return true;
+}
+
+template <typename CType, enum WireFormatLite::FieldType DeclaredType>
+inline bool WireFormatLite::ReadRepeatedFixedSizePrimitive(
+ int tag_size,
+ uint32 tag,
+ io::CodedInputStream* input,
+ RepeatedField<CType>* values) {
+ GOOGLE_DCHECK_EQ(UInt32Size(tag), tag_size);
+ CType value;
+ if (!ReadPrimitive<CType, DeclaredType>(input, &value))
+ return false;
+ values->Add(value);
+
+ // For fixed size values, repeated values can be read more quickly by
+ // reading directly from a raw array.
+ //
+ // We can get a tight loop by only reading as many elements as can be
+ // added to the RepeatedField without having to do any resizing. Additionally,
+ // we only try to read as many elements as are available from the current
+ // buffer space. Doing so avoids having to perform boundary checks when
+ // reading the value: the maximum number of elements that can be read is
+ // known outside of the loop.
+ const void* void_pointer;
+ int size;
+ input->GetDirectBufferPointerInline(&void_pointer, &size);
+ if (size > 0) {
+ const uint8* buffer = reinterpret_cast<const uint8*>(void_pointer);
+ // The number of bytes each type occupies on the wire.
+ const int per_value_size = tag_size + sizeof(value);
+
+ int elements_available =
+ std::min(values->Capacity() - values->size(), size / per_value_size);
+ int num_read = 0;
+ while (num_read < elements_available &&
+ (buffer = io::CodedInputStream::ExpectTagFromArray(
+ buffer, tag)) != NULL) {
+ buffer = ReadPrimitiveFromArray<CType, DeclaredType>(buffer, &value);
+ values->AddAlreadyReserved(value);
+ ++num_read;
+ }
+ const int read_bytes = num_read * per_value_size;
+ if (read_bytes > 0) {
+ input->Skip(read_bytes);
+ }
+ }
+ return true;
+}
+
+// Specializations of ReadRepeatedPrimitive for the fixed size types, which use
+// the optimized code path.
+#define READ_REPEATED_FIXED_SIZE_PRIMITIVE(CPPTYPE, DECLARED_TYPE) \
+template <> \
+inline bool WireFormatLite::ReadRepeatedPrimitive< \
+ CPPTYPE, WireFormatLite::DECLARED_TYPE>( \
+ int tag_size, \
+ uint32 tag, \
+ io::CodedInputStream* input, \
+ RepeatedField<CPPTYPE>* values) { \
+ return ReadRepeatedFixedSizePrimitive< \
+ CPPTYPE, WireFormatLite::DECLARED_TYPE>( \
+ tag_size, tag, input, values); \
+}
+
+READ_REPEATED_FIXED_SIZE_PRIMITIVE(uint32, TYPE_FIXED32)
+READ_REPEATED_FIXED_SIZE_PRIMITIVE(uint64, TYPE_FIXED64)
+READ_REPEATED_FIXED_SIZE_PRIMITIVE(int32, TYPE_SFIXED32)
+READ_REPEATED_FIXED_SIZE_PRIMITIVE(int64, TYPE_SFIXED64)
+READ_REPEATED_FIXED_SIZE_PRIMITIVE(float, TYPE_FLOAT)
+READ_REPEATED_FIXED_SIZE_PRIMITIVE(double, TYPE_DOUBLE)
+
+#undef READ_REPEATED_FIXED_SIZE_PRIMITIVE
+
+template <typename CType, enum WireFormatLite::FieldType DeclaredType>
+bool WireFormatLite::ReadRepeatedPrimitiveNoInline(
+ int tag_size,
+ uint32 tag,
+ io::CodedInputStream* input,
+ RepeatedField<CType>* value) {
+ return ReadRepeatedPrimitive<CType, DeclaredType>(
+ tag_size, tag, input, value);
+}
+
+template <typename CType, enum WireFormatLite::FieldType DeclaredType>
+inline bool WireFormatLite::ReadPackedPrimitive(io::CodedInputStream* input,
+ RepeatedField<CType>* values) {
+ int length;
+ if (!input->ReadVarintSizeAsInt(&length)) return false;
+ io::CodedInputStream::Limit limit = input->PushLimit(length);
+ while (input->BytesUntilLimit() > 0) {
+ CType value;
+ if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
+ values->Add(value);
+ }
+ input->PopLimit(limit);
+ return true;
+}
+
+template <typename CType, enum WireFormatLite::FieldType DeclaredType>
+inline bool WireFormatLite::ReadPackedFixedSizePrimitive(
+ io::CodedInputStream* input, RepeatedField<CType>* values) {
+ int length;
+ if (!input->ReadVarintSizeAsInt(&length)) return false;
+ const int old_entries = values->size();
+ const int new_entries = length / sizeof(CType);
+ const int new_bytes = new_entries * sizeof(CType);
+ if (new_bytes != length) return false;
+ // We would *like* to pre-allocate the buffer to write into (for
+ // speed), but *must* avoid performing a very large allocation due
+ // to a malicious user-supplied "length" above. So we have a fast
+ // path that pre-allocates when the "length" is less than a bound.
+ // We determine the bound by calling BytesUntilTotalBytesLimit() and
+ // BytesUntilLimit(). These return -1 to mean "no limit set".
+ // There are four cases:
+ // TotalBytesLimit Limit
+ // -1 -1 Use slow path.
+ // -1 >= 0 Use fast path if length <= Limit.
+ // >= 0 -1 Use slow path.
+ // >= 0 >= 0 Use fast path if length <= min(both limits).
+ int64 bytes_limit = input->BytesUntilTotalBytesLimit();
+ if (bytes_limit == -1) {
+ bytes_limit = input->BytesUntilLimit();
+ } else {
+ bytes_limit =
+ std::min(bytes_limit, static_cast<int64>(input->BytesUntilLimit()));
+ }
+ if (bytes_limit >= new_bytes) {
+ // Fast-path that pre-allocates *values to the final size.
+#if defined(PROTOBUF_LITTLE_ENDIAN)
+ values->Resize(old_entries + new_entries, 0);
+ // values->mutable_data() may change after Resize(), so do this after:
+ void* dest = reinterpret_cast<void*>(values->mutable_data() + old_entries);
+ if (!input->ReadRaw(dest, new_bytes)) {
+ values->Truncate(old_entries);
+ return false;
+ }
+#else
+ values->Reserve(old_entries + new_entries);
+ CType value;
+ for (int i = 0; i < new_entries; ++i) {
+ if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
+ values->AddAlreadyReserved(value);
+ }
+#endif
+ } else {
+ // This is the slow-path case where "length" may be too large to
+ // safely allocate. We read as much as we can into *values
+ // without pre-allocating "length" bytes.
+ CType value;
+ for (int i = 0; i < new_entries; ++i) {
+ if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
+ values->Add(value);
+ }
+ }
+ return true;
+}
+
+// Specializations of ReadPackedPrimitive for the fixed size types, which use
+// an optimized code path.
+#define READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(CPPTYPE, DECLARED_TYPE) \
+template <> \
+inline bool WireFormatLite::ReadPackedPrimitive< \
+ CPPTYPE, WireFormatLite::DECLARED_TYPE>( \
+ io::CodedInputStream* input, \
+ RepeatedField<CPPTYPE>* values) { \
+ return ReadPackedFixedSizePrimitive< \
+ CPPTYPE, WireFormatLite::DECLARED_TYPE>(input, values); \
+}
+
+READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(uint32, TYPE_FIXED32)
+READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(uint64, TYPE_FIXED64)
+READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(int32, TYPE_SFIXED32)
+READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(int64, TYPE_SFIXED64)
+READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(float, TYPE_FLOAT)
+READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(double, TYPE_DOUBLE)
+
+#undef READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE
+
+template <typename CType, enum WireFormatLite::FieldType DeclaredType>
+bool WireFormatLite::ReadPackedPrimitiveNoInline(io::CodedInputStream* input,
+ RepeatedField<CType>* values) {
+ return ReadPackedPrimitive<CType, DeclaredType>(input, values);
+}
+
+
+
+inline bool WireFormatLite::ReadGroup(int field_number,
+ io::CodedInputStream* input,
+ MessageLite* value) {
+ if (!input->IncrementRecursionDepth()) return false;
+ if (!value->MergePartialFromCodedStream(input)) return false;
+ input->DecrementRecursionDepth();
+ // Make sure the last thing read was an end tag for this group.
+ if (!input->LastTagWas(MakeTag(field_number, WIRETYPE_END_GROUP))) {
+ return false;
+ }
+ return true;
+}
+inline bool WireFormatLite::ReadMessage(io::CodedInputStream* input,
+ MessageLite* value) {
+ int length;
+ if (!input->ReadVarintSizeAsInt(&length)) return false;
+ std::pair<io::CodedInputStream::Limit, int> p =
+ input->IncrementRecursionDepthAndPushLimit(length);
+ if (p.second < 0 || !value->MergePartialFromCodedStream(input)) return false;
+ // Make sure that parsing stopped when the limit was hit, not at an endgroup
+ // tag.
+ return input->DecrementRecursionDepthAndPopLimit(p.first);
+}
+
+// We name the template parameter something long and extremely unlikely to occur
+// elsewhere because a *qualified* member access expression designed to avoid
+// virtual dispatch, C++03 [basic.lookup.classref] 3.4.5/4 requires that the
+// name of the qualifying class to be looked up both in the context of the full
+// expression (finding the template parameter) and in the context of the object
+// whose member we are accessing. This could potentially find a nested type
+// within that object. The standard goes on to require these names to refer to
+// the same entity, which this collision would violate. The lack of a safe way
+// to avoid this collision appears to be a defect in the standard, but until it
+// is corrected, we choose the name to avoid accidental collisions.
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline bool WireFormatLite::ReadGroupNoVirtual(
+ int field_number, io::CodedInputStream* input,
+ MessageType_WorkAroundCppLookupDefect* value) {
+ if (!input->IncrementRecursionDepth()) return false;
+ if (!value->
+ MessageType_WorkAroundCppLookupDefect::MergePartialFromCodedStream(input))
+ return false;
+ input->UnsafeDecrementRecursionDepth();
+ // Make sure the last thing read was an end tag for this group.
+ if (!input->LastTagWas(MakeTag(field_number, WIRETYPE_END_GROUP))) {
+ return false;
+ }
+ return true;
+}
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline bool WireFormatLite::ReadGroupNoVirtualNoRecursionDepth(
+ int field_number, io::CodedInputStream* input,
+ MessageType_WorkAroundCppLookupDefect* value) {
+ return value->MessageType_WorkAroundCppLookupDefect::
+ MergePartialFromCodedStream(input) &&
+ input->LastTagWas(MakeTag(field_number, WIRETYPE_END_GROUP));
+}
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline bool WireFormatLite::ReadMessageNoVirtual(
+ io::CodedInputStream* input, MessageType_WorkAroundCppLookupDefect* value) {
+ int length;
+ if (!input->ReadVarintSizeAsInt(&length)) return false;
+ std::pair<io::CodedInputStream::Limit, int> p =
+ input->IncrementRecursionDepthAndPushLimit(length);
+ if (p.second < 0 || !value->
+ MessageType_WorkAroundCppLookupDefect::MergePartialFromCodedStream(input))
+ return false;
+ // Make sure that parsing stopped when the limit was hit, not at an endgroup
+ // tag.
+ return input->DecrementRecursionDepthAndPopLimit(p.first);
+}
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline bool WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+ io::CodedInputStream* input, MessageType_WorkAroundCppLookupDefect* value) {
+ io::CodedInputStream::Limit old_limit = input->ReadLengthAndPushLimit();
+ if (!value->
+ MessageType_WorkAroundCppLookupDefect::MergePartialFromCodedStream(input))
+ return false;
+ // Make sure that parsing stopped when the limit was hit, not at an endgroup
+ // tag.
+ return input->CheckEntireMessageConsumedAndPopLimit(old_limit);
+}
+
+// ===================================================================
+
+inline void WireFormatLite::WriteTag(int field_number, WireType type,
+ io::CodedOutputStream* output) {
+ output->WriteTag(MakeTag(field_number, type));
+}
+
+inline void WireFormatLite::WriteInt32NoTag(int32 value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint32SignExtended(value);
+}
+inline void WireFormatLite::WriteInt64NoTag(int64 value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint64(static_cast<uint64>(value));
+}
+inline void WireFormatLite::WriteUInt32NoTag(uint32 value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint32(value);
+}
+inline void WireFormatLite::WriteUInt64NoTag(uint64 value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint64(value);
+}
+inline void WireFormatLite::WriteSInt32NoTag(int32 value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint32(ZigZagEncode32(value));
+}
+inline void WireFormatLite::WriteSInt64NoTag(int64 value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint64(ZigZagEncode64(value));
+}
+inline void WireFormatLite::WriteFixed32NoTag(uint32 value,
+ io::CodedOutputStream* output) {
+ output->WriteLittleEndian32(value);
+}
+inline void WireFormatLite::WriteFixed64NoTag(uint64 value,
+ io::CodedOutputStream* output) {
+ output->WriteLittleEndian64(value);
+}
+inline void WireFormatLite::WriteSFixed32NoTag(int32 value,
+ io::CodedOutputStream* output) {
+ output->WriteLittleEndian32(static_cast<uint32>(value));
+}
+inline void WireFormatLite::WriteSFixed64NoTag(int64 value,
+ io::CodedOutputStream* output) {
+ output->WriteLittleEndian64(static_cast<uint64>(value));
+}
+inline void WireFormatLite::WriteFloatNoTag(float value,
+ io::CodedOutputStream* output) {
+ output->WriteLittleEndian32(EncodeFloat(value));
+}
+inline void WireFormatLite::WriteDoubleNoTag(double value,
+ io::CodedOutputStream* output) {
+ output->WriteLittleEndian64(EncodeDouble(value));
+}
+inline void WireFormatLite::WriteBoolNoTag(bool value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint32(value ? 1 : 0);
+}
+inline void WireFormatLite::WriteEnumNoTag(int value,
+ io::CodedOutputStream* output) {
+ output->WriteVarint32SignExtended(value);
+}
+
+// See comment on ReadGroupNoVirtual to understand the need for this template
+// parameter name.
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline void WireFormatLite::WriteGroupNoVirtual(
+ int field_number, const MessageType_WorkAroundCppLookupDefect& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_START_GROUP, output);
+ value.MessageType_WorkAroundCppLookupDefect::SerializeWithCachedSizes(output);
+ WriteTag(field_number, WIRETYPE_END_GROUP, output);
+}
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline void WireFormatLite::WriteMessageNoVirtual(
+ int field_number, const MessageType_WorkAroundCppLookupDefect& value,
+ io::CodedOutputStream* output) {
+ WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
+ output->WriteVarint32(
+ value.MessageType_WorkAroundCppLookupDefect::GetCachedSize());
+ value.MessageType_WorkAroundCppLookupDefect::SerializeWithCachedSizes(output);
+}
+
+// ===================================================================
+
+inline uint8* WireFormatLite::WriteTagToArray(int field_number,
+ WireType type,
+ uint8* target) {
+ return io::CodedOutputStream::WriteTagToArray(MakeTag(field_number, type),
+ target);
+}
+
+inline uint8* WireFormatLite::WriteInt32NoTagToArray(int32 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint32SignExtendedToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteInt64NoTagToArray(int64 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint64ToArray(
+ static_cast<uint64>(value), target);
+}
+inline uint8* WireFormatLite::WriteUInt32NoTagToArray(uint32 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint32ToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteUInt64NoTagToArray(uint64 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint64ToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteSInt32NoTagToArray(int32 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint32ToArray(ZigZagEncode32(value),
+ target);
+}
+inline uint8* WireFormatLite::WriteSInt64NoTagToArray(int64 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint64ToArray(ZigZagEncode64(value),
+ target);
+}
+inline uint8* WireFormatLite::WriteFixed32NoTagToArray(uint32 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteLittleEndian32ToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteFixed64NoTagToArray(uint64 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteLittleEndian64ToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteSFixed32NoTagToArray(int32 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteLittleEndian32ToArray(
+ static_cast<uint32>(value), target);
+}
+inline uint8* WireFormatLite::WriteSFixed64NoTagToArray(int64 value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteLittleEndian64ToArray(
+ static_cast<uint64>(value), target);
+}
+inline uint8* WireFormatLite::WriteFloatNoTagToArray(float value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteLittleEndian32ToArray(EncodeFloat(value),
+ target);
+}
+inline uint8* WireFormatLite::WriteDoubleNoTagToArray(double value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteLittleEndian64ToArray(EncodeDouble(value),
+ target);
+}
+inline uint8* WireFormatLite::WriteBoolNoTagToArray(bool value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint32ToArray(value ? 1 : 0, target);
+}
+inline uint8* WireFormatLite::WriteEnumNoTagToArray(int value,
+ uint8* target) {
+ return io::CodedOutputStream::WriteVarint32SignExtendedToArray(value, target);
+}
+
+inline uint8* WireFormatLite::WriteInt32ToArray(int field_number,
+ int32 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteInt32NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteInt64ToArray(int field_number,
+ int64 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteInt64NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteUInt32ToArray(int field_number,
+ uint32 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteUInt32NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteUInt64ToArray(int field_number,
+ uint64 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteUInt64NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteSInt32ToArray(int field_number,
+ int32 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteSInt32NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteSInt64ToArray(int field_number,
+ int64 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteSInt64NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteFixed32ToArray(int field_number,
+ uint32 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_FIXED32, target);
+ return WriteFixed32NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteFixed64ToArray(int field_number,
+ uint64 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_FIXED64, target);
+ return WriteFixed64NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteSFixed32ToArray(int field_number,
+ int32 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_FIXED32, target);
+ return WriteSFixed32NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteSFixed64ToArray(int field_number,
+ int64 value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_FIXED64, target);
+ return WriteSFixed64NoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteFloatToArray(int field_number,
+ float value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_FIXED32, target);
+ return WriteFloatNoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteDoubleToArray(int field_number,
+ double value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_FIXED64, target);
+ return WriteDoubleNoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteBoolToArray(int field_number,
+ bool value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteBoolNoTagToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteEnumToArray(int field_number,
+ int value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
+ return WriteEnumNoTagToArray(value, target);
+}
+
+inline uint8* WireFormatLite::WriteStringToArray(int field_number,
+ const string& value,
+ uint8* target) {
+ // String is for UTF-8 text only
+ // WARNING: In wire_format.cc, both strings and bytes are handled by
+ // WriteString() to avoid code duplication. If the implementations become
+ // different, you will need to update that usage.
+ target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
+ return io::CodedOutputStream::WriteStringWithSizeToArray(value, target);
+}
+inline uint8* WireFormatLite::WriteBytesToArray(int field_number,
+ const string& value,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
+ return io::CodedOutputStream::WriteStringWithSizeToArray(value, target);
+}
+
+
+inline uint8* WireFormatLite::InternalWriteGroupToArray(
+ int field_number, const MessageLite& value, bool deterministic,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_START_GROUP, target);
+ target = value.InternalSerializeWithCachedSizesToArray(deterministic, target);
+ return WriteTagToArray(field_number, WIRETYPE_END_GROUP, target);
+}
+inline uint8* WireFormatLite::InternalWriteMessageToArray(
+ int field_number, const MessageLite& value, bool deterministic,
+ uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
+ target = io::CodedOutputStream::WriteVarint32ToArray(
+ value.GetCachedSize(), target);
+ return value.InternalSerializeWithCachedSizesToArray(deterministic, target);
+}
+
+// See comment on ReadGroupNoVirtual to understand the need for this template
+// parameter name.
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline uint8* WireFormatLite::InternalWriteGroupNoVirtualToArray(
+ int field_number, const MessageType_WorkAroundCppLookupDefect& value,
+ bool deterministic, uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_START_GROUP, target);
+ target = value.InternalSerializeWithCachedSizesToArray(deterministic, target);
+ return WriteTagToArray(field_number, WIRETYPE_END_GROUP, target);
+}
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline uint8* WireFormatLite::InternalWriteMessageNoVirtualToArray(
+ int field_number, const MessageType_WorkAroundCppLookupDefect& value,
+ bool deterministic, uint8* target) {
+ target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
+ target = io::CodedOutputStream::WriteVarint32ToArray(
+ value.MessageType_WorkAroundCppLookupDefect::GetCachedSize(), target);
+ return value.InternalSerializeWithCachedSizesToArray(deterministic, target);
+}
+
+// ===================================================================
+
+inline int WireFormatLite::Int32Size(int32 value) {
+ return io::CodedOutputStream::VarintSize32SignExtended(value);
+}
+inline int WireFormatLite::Int64Size(int64 value) {
+ return io::CodedOutputStream::VarintSize64(static_cast<uint64>(value));
+}
+inline int WireFormatLite::UInt32Size(uint32 value) {
+ return io::CodedOutputStream::VarintSize32(value);
+}
+inline int WireFormatLite::UInt64Size(uint64 value) {
+ return io::CodedOutputStream::VarintSize64(value);
+}
+inline int WireFormatLite::SInt32Size(int32 value) {
+ return io::CodedOutputStream::VarintSize32(ZigZagEncode32(value));
+}
+inline int WireFormatLite::SInt64Size(int64 value) {
+ return io::CodedOutputStream::VarintSize64(ZigZagEncode64(value));
+}
+inline int WireFormatLite::EnumSize(int value) {
+ return io::CodedOutputStream::VarintSize32SignExtended(value);
+}
+
+inline int WireFormatLite::StringSize(const string& value) {
+ return static_cast<int>(
+ io::CodedOutputStream::VarintSize32(static_cast<uint32>(value.size())) +
+ value.size());
+}
+inline int WireFormatLite::BytesSize(const string& value) {
+ return static_cast<int>(
+ io::CodedOutputStream::VarintSize32(static_cast<uint32>(value.size())) +
+ value.size());
+}
+
+
+inline int WireFormatLite::GroupSize(const MessageLite& value) {
+ return value.ByteSize();
+}
+inline int WireFormatLite::MessageSize(const MessageLite& value) {
+ return LengthDelimitedSize(value.ByteSize());
+}
+
+// See comment on ReadGroupNoVirtual to understand the need for this template
+// parameter name.
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline int WireFormatLite::GroupSizeNoVirtual(
+ const MessageType_WorkAroundCppLookupDefect& value) {
+ return value.MessageType_WorkAroundCppLookupDefect::ByteSize();
+}
+template<typename MessageType_WorkAroundCppLookupDefect>
+inline int WireFormatLite::MessageSizeNoVirtual(
+ const MessageType_WorkAroundCppLookupDefect& value) {
+ return LengthDelimitedSize(
+ value.MessageType_WorkAroundCppLookupDefect::ByteSize());
+}
+
+inline int WireFormatLite::LengthDelimitedSize(int length) {
+ return io::CodedOutputStream::VarintSize32(length) + length;
+}
+
+} // namespace internal
+} // namespace protobuf
+
+} // namespace google
+#endif // GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_INL_H__
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_unittest.cc b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_unittest.cc
new file mode 100644
index 0000000000..4e4add66f3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wire_format_unittest.cc
@@ -0,0 +1,1289 @@
+// 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.
+
+#include <google/protobuf/wire_format.h>
+#include <google/protobuf/wire_format_lite_inl.h>
+#include <google/protobuf/descriptor.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
+#include <google/protobuf/io/coded_stream.h>
+#include <google/protobuf/unittest.pb.h>
+#include <google/protobuf/unittest_proto3_arena.pb.h>
+#include <google/protobuf/unittest_mset.pb.h>
+#include <google/protobuf/unittest_mset_wire_format.pb.h>
+#include <google/protobuf/test_util.h>
+
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/stubs/common.h>
+#include <google/protobuf/stubs/logging.h>
+#include <google/protobuf/testing/googletest.h>
+#include <gtest/gtest.h>
+#include <google/protobuf/stubs/stl_util.h>
+
+namespace google {
+namespace protobuf {
+namespace internal {
+namespace {
+
+TEST(WireFormatTest, EnumsInSync) {
+ // Verify that WireFormatLite::FieldType and WireFormatLite::CppType match
+ // FieldDescriptor::Type and FieldDescriptor::CppType.
+
+ EXPECT_EQ(implicit_cast<int>(FieldDescriptor::MAX_TYPE),
+ implicit_cast<int>(WireFormatLite::MAX_FIELD_TYPE));
+ EXPECT_EQ(implicit_cast<int>(FieldDescriptor::MAX_CPPTYPE),
+ implicit_cast<int>(WireFormatLite::MAX_CPPTYPE));
+
+ for (int i = 1; i <= WireFormatLite::MAX_FIELD_TYPE; i++) {
+ EXPECT_EQ(
+ implicit_cast<int>(FieldDescriptor::TypeToCppType(
+ static_cast<FieldDescriptor::Type>(i))),
+ implicit_cast<int>(WireFormatLite::FieldTypeToCppType(
+ static_cast<WireFormatLite::FieldType>(i))));
+ }
+}
+
+TEST(WireFormatTest, MaxFieldNumber) {
+ // Make sure the max field number constant is accurate.
+ EXPECT_EQ((1 << (32 - WireFormatLite::kTagTypeBits)) - 1,
+ FieldDescriptor::kMaxNumber);
+}
+
+TEST(WireFormatTest, Parse) {
+ unittest::TestAllTypes source, dest;
+ string data;
+
+ // Serialize using the generated code.
+ TestUtil::SetAllFields(&source);
+ source.SerializeToString(&data);
+
+ // Parse using WireFormat.
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ TestUtil::ExpectAllFieldsSet(dest);
+}
+
+TEST(WireFormatTest, ParseExtensions) {
+ unittest::TestAllExtensions source, dest;
+ string data;
+
+ // Serialize using the generated code.
+ TestUtil::SetAllExtensions(&source);
+ source.SerializeToString(&data);
+
+ // Parse using WireFormat.
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ TestUtil::ExpectAllExtensionsSet(dest);
+}
+
+TEST(WireFormatTest, ParsePacked) {
+ unittest::TestPackedTypes source, dest;
+ string data;
+
+ // Serialize using the generated code.
+ TestUtil::SetPackedFields(&source);
+ source.SerializeToString(&data);
+
+ // Parse using WireFormat.
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ TestUtil::ExpectPackedFieldsSet(dest);
+}
+
+TEST(WireFormatTest, ParsePackedFromUnpacked) {
+ // Serialize using the generated code.
+ unittest::TestUnpackedTypes source;
+ TestUtil::SetUnpackedFields(&source);
+ string data = source.SerializeAsString();
+
+ // Parse using WireFormat.
+ unittest::TestPackedTypes dest;
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ TestUtil::ExpectPackedFieldsSet(dest);
+}
+
+TEST(WireFormatTest, ParseUnpackedFromPacked) {
+ // Serialize using the generated code.
+ unittest::TestPackedTypes source;
+ TestUtil::SetPackedFields(&source);
+ string data = source.SerializeAsString();
+
+ // Parse using WireFormat.
+ unittest::TestUnpackedTypes dest;
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ TestUtil::ExpectUnpackedFieldsSet(dest);
+}
+
+TEST(WireFormatTest, ParsePackedExtensions) {
+ unittest::TestPackedExtensions source, dest;
+ string data;
+
+ // Serialize using the generated code.
+ TestUtil::SetPackedExtensions(&source);
+ source.SerializeToString(&data);
+
+ // Parse using WireFormat.
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ TestUtil::ExpectPackedExtensionsSet(dest);
+}
+
+TEST(WireFormatTest, ParseOneof) {
+ unittest::TestOneof2 source, dest;
+ string data;
+
+ // Serialize using the generated code.
+ TestUtil::SetOneof1(&source);
+ source.SerializeToString(&data);
+
+ // Parse using WireFormat.
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &dest);
+
+ // Check.
+ TestUtil::ExpectOneofSet1(dest);
+}
+
+TEST(WireFormatTest, OneofOnlySetLast) {
+ unittest::TestOneofBackwardsCompatible source;
+ unittest::TestOneof oneof_dest;
+ string data;
+
+ // Set two fields
+ source.set_foo_int(100);
+ source.set_foo_string("101");
+
+ // Serialize and parse to oneof message.
+ source.SerializeToString(&data);
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ WireFormat::ParseAndMergePartial(&input, &oneof_dest);
+
+ // Only the last field is set.
+ EXPECT_FALSE(oneof_dest.has_foo_int());
+ EXPECT_TRUE(oneof_dest.has_foo_string());
+}
+
+TEST(WireFormatTest, ByteSize) {
+ unittest::TestAllTypes message;
+ TestUtil::SetAllFields(&message);
+
+ EXPECT_EQ(message.ByteSize(), WireFormat::ByteSize(message));
+ message.Clear();
+ EXPECT_EQ(0, message.ByteSize());
+ EXPECT_EQ(0, WireFormat::ByteSize(message));
+}
+
+TEST(WireFormatTest, ByteSizeExtensions) {
+ unittest::TestAllExtensions message;
+ TestUtil::SetAllExtensions(&message);
+
+ EXPECT_EQ(message.ByteSize(),
+ WireFormat::ByteSize(message));
+ message.Clear();
+ EXPECT_EQ(0, message.ByteSize());
+ EXPECT_EQ(0, WireFormat::ByteSize(message));
+}
+
+TEST(WireFormatTest, ByteSizePacked) {
+ unittest::TestPackedTypes message;
+ TestUtil::SetPackedFields(&message);
+
+ EXPECT_EQ(message.ByteSize(), WireFormat::ByteSize(message));
+ message.Clear();
+ EXPECT_EQ(0, message.ByteSize());
+ EXPECT_EQ(0, WireFormat::ByteSize(message));
+}
+
+TEST(WireFormatTest, ByteSizePackedExtensions) {
+ unittest::TestPackedExtensions message;
+ TestUtil::SetPackedExtensions(&message);
+
+ EXPECT_EQ(message.ByteSize(),
+ WireFormat::ByteSize(message));
+ message.Clear();
+ EXPECT_EQ(0, message.ByteSize());
+ EXPECT_EQ(0, WireFormat::ByteSize(message));
+}
+
+TEST(WireFormatTest, ByteSizeOneof) {
+ unittest::TestOneof2 message;
+ TestUtil::SetOneof1(&message);
+
+ EXPECT_EQ(message.ByteSize(),
+ WireFormat::ByteSize(message));
+ message.Clear();
+
+ EXPECT_EQ(0, message.ByteSize());
+ EXPECT_EQ(0, WireFormat::ByteSize(message));
+}
+
+TEST(WireFormatTest, Serialize) {
+ unittest::TestAllTypes message;
+ string generated_data;
+ string dynamic_data;
+
+ TestUtil::SetAllFields(&message);
+ int size = message.ByteSize();
+
+ // Serialize using the generated code.
+ {
+ io::StringOutputStream raw_output(&generated_data);
+ io::CodedOutputStream output(&raw_output);
+ message.SerializeWithCachedSizes(&output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Serialize using WireFormat.
+ {
+ io::StringOutputStream raw_output(&dynamic_data);
+ io::CodedOutputStream output(&raw_output);
+ WireFormat::SerializeWithCachedSizes(message, size, &output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Should be the same.
+ // Don't use EXPECT_EQ here because we're comparing raw binary data and
+ // we really don't want it dumped to stdout on failure.
+ EXPECT_TRUE(dynamic_data == generated_data);
+}
+
+TEST(WireFormatTest, SerializeExtensions) {
+ unittest::TestAllExtensions message;
+ string generated_data;
+ string dynamic_data;
+
+ TestUtil::SetAllExtensions(&message);
+ int size = message.ByteSize();
+
+ // Serialize using the generated code.
+ {
+ io::StringOutputStream raw_output(&generated_data);
+ io::CodedOutputStream output(&raw_output);
+ message.SerializeWithCachedSizes(&output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Serialize using WireFormat.
+ {
+ io::StringOutputStream raw_output(&dynamic_data);
+ io::CodedOutputStream output(&raw_output);
+ WireFormat::SerializeWithCachedSizes(message, size, &output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Should be the same.
+ // Don't use EXPECT_EQ here because we're comparing raw binary data and
+ // we really don't want it dumped to stdout on failure.
+ EXPECT_TRUE(dynamic_data == generated_data);
+}
+
+TEST(WireFormatTest, SerializeFieldsAndExtensions) {
+ unittest::TestFieldOrderings message;
+ string generated_data;
+ string dynamic_data;
+
+ TestUtil::SetAllFieldsAndExtensions(&message);
+ int size = message.ByteSize();
+
+ // Serialize using the generated code.
+ {
+ io::StringOutputStream raw_output(&generated_data);
+ io::CodedOutputStream output(&raw_output);
+ message.SerializeWithCachedSizes(&output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Serialize using WireFormat.
+ {
+ io::StringOutputStream raw_output(&dynamic_data);
+ io::CodedOutputStream output(&raw_output);
+ WireFormat::SerializeWithCachedSizes(message, size, &output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Should be the same.
+ // Don't use EXPECT_EQ here because we're comparing raw binary data and
+ // we really don't want it dumped to stdout on failure.
+ EXPECT_TRUE(dynamic_data == generated_data);
+
+ // Should output in canonical order.
+ TestUtil::ExpectAllFieldsAndExtensionsInOrder(dynamic_data);
+ TestUtil::ExpectAllFieldsAndExtensionsInOrder(generated_data);
+}
+
+TEST(WireFormatTest, SerializeOneof) {
+ unittest::TestOneof2 message;
+ string generated_data;
+ string dynamic_data;
+
+ TestUtil::SetOneof1(&message);
+ int size = message.ByteSize();
+
+ // Serialize using the generated code.
+ {
+ io::StringOutputStream raw_output(&generated_data);
+ io::CodedOutputStream output(&raw_output);
+ message.SerializeWithCachedSizes(&output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Serialize using WireFormat.
+ {
+ io::StringOutputStream raw_output(&dynamic_data);
+ io::CodedOutputStream output(&raw_output);
+ WireFormat::SerializeWithCachedSizes(message, size, &output);
+ ASSERT_FALSE(output.HadError());
+ }
+
+ // Should be the same.
+ // Don't use EXPECT_EQ here because we're comparing raw binary data and
+ // we really don't want it dumped to stdout on failure.
+ EXPECT_TRUE(dynamic_data == generated_data);
+}
+
+TEST(WireFormatTest, ParseMultipleExtensionRanges) {
+ // Make sure we can parse a message that contains multiple extensions ranges.
+ unittest::TestFieldOrderings source;
+ string data;
+
+ TestUtil::SetAllFieldsAndExtensions(&source);
+ source.SerializeToString(&data);
+
+ {
+ unittest::TestFieldOrderings dest;
+ EXPECT_TRUE(dest.ParseFromString(data));
+ EXPECT_EQ(source.DebugString(), dest.DebugString());
+ }
+
+ // Also test using reflection-based parsing.
+ {
+ unittest::TestFieldOrderings dest;
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream coded_input(&raw_input);
+ EXPECT_TRUE(WireFormat::ParseAndMergePartial(&coded_input, &dest));
+ EXPECT_EQ(source.DebugString(), dest.DebugString());
+ }
+}
+
+const int kUnknownTypeId = 1550055;
+
+TEST(WireFormatTest, SerializeMessageSet) {
+ // Set up a TestMessageSet with two known messages and an unknown one.
+ proto2_wireformat_unittest::TestMessageSet message_set;
+ message_set.MutableExtension(
+ unittest::TestMessageSetExtension1::message_set_extension)->set_i(123);
+ message_set.MutableExtension(
+ unittest::TestMessageSetExtension2::message_set_extension)->set_str("foo");
+ message_set.mutable_unknown_fields()->AddLengthDelimited(
+ kUnknownTypeId, "bar");
+
+ string data;
+ ASSERT_TRUE(message_set.SerializeToString(&data));
+
+ // Parse back using RawMessageSet and check the contents.
+ unittest::RawMessageSet raw;
+ ASSERT_TRUE(raw.ParseFromString(data));
+
+ EXPECT_EQ(0, raw.unknown_fields().field_count());
+
+ ASSERT_EQ(3, raw.item_size());
+ EXPECT_EQ(
+ unittest::TestMessageSetExtension1::descriptor()->extension(0)->number(),
+ raw.item(0).type_id());
+ EXPECT_EQ(
+ unittest::TestMessageSetExtension2::descriptor()->extension(0)->number(),
+ raw.item(1).type_id());
+ EXPECT_EQ(kUnknownTypeId, raw.item(2).type_id());
+
+ unittest::TestMessageSetExtension1 message1;
+ EXPECT_TRUE(message1.ParseFromString(raw.item(0).message()));
+ EXPECT_EQ(123, message1.i());
+
+ unittest::TestMessageSetExtension2 message2;
+ EXPECT_TRUE(message2.ParseFromString(raw.item(1).message()));
+ EXPECT_EQ("foo", message2.str());
+
+ EXPECT_EQ("bar", raw.item(2).message());
+}
+
+TEST(WireFormatTest, SerializeMessageSetVariousWaysAreEqual) {
+ // Serialize a MessageSet to a stream and to a flat array using generated
+ // code, and also using WireFormat, and check that the results are equal.
+ // Set up a TestMessageSet with two known messages and an unknown one, as
+ // above.
+
+ proto2_wireformat_unittest::TestMessageSet message_set;
+ message_set.MutableExtension(
+ unittest::TestMessageSetExtension1::message_set_extension)->set_i(123);
+ message_set.MutableExtension(
+ unittest::TestMessageSetExtension2::message_set_extension)->set_str("foo");
+ message_set.mutable_unknown_fields()->AddLengthDelimited(
+ kUnknownTypeId, "bar");
+
+ int size = message_set.ByteSize();
+ EXPECT_EQ(size, message_set.GetCachedSize());
+ ASSERT_EQ(size, WireFormat::ByteSize(message_set));
+
+ string flat_data;
+ string stream_data;
+ string dynamic_data;
+ flat_data.resize(size);
+ stream_data.resize(size);
+
+ // Serialize to flat array
+ {
+ uint8* target = reinterpret_cast<uint8*>(string_as_array(&flat_data));
+ uint8* end = message_set.SerializeWithCachedSizesToArray(target);
+ EXPECT_EQ(size, end - target);
+ }
+
+ // Serialize to buffer
+ {
+ io::ArrayOutputStream array_stream(string_as_array(&stream_data), size, 1);
+ io::CodedOutputStream output_stream(&array_stream);
+ message_set.SerializeWithCachedSizes(&output_stream);
+ ASSERT_FALSE(output_stream.HadError());
+ }
+
+ // Serialize to buffer with WireFormat.
+ {
+ io::StringOutputStream string_stream(&dynamic_data);
+ io::CodedOutputStream output_stream(&string_stream);
+ WireFormat::SerializeWithCachedSizes(message_set, size, &output_stream);
+ ASSERT_FALSE(output_stream.HadError());
+ }
+
+ EXPECT_TRUE(flat_data == stream_data);
+ EXPECT_TRUE(flat_data == dynamic_data);
+}
+
+TEST(WireFormatTest, ParseMessageSet) {
+ // Set up a RawMessageSet with two known messages and an unknown one.
+ unittest::RawMessageSet raw;
+
+ {
+ unittest::RawMessageSet::Item* item = raw.add_item();
+ item->set_type_id(
+ unittest::TestMessageSetExtension1::descriptor()->extension(0)->number());
+ unittest::TestMessageSetExtension1 message;
+ message.set_i(123);
+ message.SerializeToString(item->mutable_message());
+ }
+
+ {
+ unittest::RawMessageSet::Item* item = raw.add_item();
+ item->set_type_id(
+ unittest::TestMessageSetExtension2::descriptor()->extension(0)->number());
+ unittest::TestMessageSetExtension2 message;
+ message.set_str("foo");
+ message.SerializeToString(item->mutable_message());
+ }
+
+ {
+ unittest::RawMessageSet::Item* item = raw.add_item();
+ item->set_type_id(kUnknownTypeId);
+ item->set_message("bar");
+ }
+
+ string data;
+ ASSERT_TRUE(raw.SerializeToString(&data));
+
+ // Parse as a TestMessageSet and check the contents.
+ proto2_wireformat_unittest::TestMessageSet message_set;
+ ASSERT_TRUE(message_set.ParseFromString(data));
+
+ EXPECT_EQ(123, message_set.GetExtension(
+ unittest::TestMessageSetExtension1::message_set_extension).i());
+ EXPECT_EQ("foo", message_set.GetExtension(
+ unittest::TestMessageSetExtension2::message_set_extension).str());
+
+ ASSERT_EQ(1, message_set.unknown_fields().field_count());
+ ASSERT_EQ(UnknownField::TYPE_LENGTH_DELIMITED,
+ message_set.unknown_fields().field(0).type());
+ EXPECT_EQ("bar", message_set.unknown_fields().field(0).length_delimited());
+
+ // Also parse using WireFormat.
+ proto2_wireformat_unittest::TestMessageSet dynamic_message_set;
+ io::CodedInputStream input(reinterpret_cast<const uint8*>(data.data()),
+ data.size());
+ ASSERT_TRUE(WireFormat::ParseAndMergePartial(&input, &dynamic_message_set));
+ EXPECT_EQ(message_set.DebugString(), dynamic_message_set.DebugString());
+}
+
+TEST(WireFormatTest, ParseMessageSetWithReverseTagOrder) {
+ string data;
+ {
+ unittest::TestMessageSetExtension1 message;
+ message.set_i(123);
+ // Build a MessageSet manually with its message content put before its
+ // type_id.
+ io::StringOutputStream output_stream(&data);
+ io::CodedOutputStream coded_output(&output_stream);
+ coded_output.WriteTag(WireFormatLite::kMessageSetItemStartTag);
+ // Write the message content first.
+ WireFormatLite::WriteTag(WireFormatLite::kMessageSetMessageNumber,
+ WireFormatLite::WIRETYPE_LENGTH_DELIMITED,
+ &coded_output);
+ coded_output.WriteVarint32(message.ByteSize());
+ message.SerializeWithCachedSizes(&coded_output);
+ // Write the type id.
+ uint32 type_id = message.GetDescriptor()->extension(0)->number();
+ WireFormatLite::WriteUInt32(WireFormatLite::kMessageSetTypeIdNumber,
+ type_id, &coded_output);
+ coded_output.WriteTag(WireFormatLite::kMessageSetItemEndTag);
+ }
+ {
+ proto2_wireformat_unittest::TestMessageSet message_set;
+ ASSERT_TRUE(message_set.ParseFromString(data));
+
+ EXPECT_EQ(123, message_set.GetExtension(
+ unittest::TestMessageSetExtension1::message_set_extension).i());
+ }
+ {
+ // Test parse the message via Reflection.
+ proto2_wireformat_unittest::TestMessageSet message_set;
+ io::CodedInputStream input(
+ reinterpret_cast<const uint8*>(data.data()), data.size());
+ EXPECT_TRUE(WireFormat::ParseAndMergePartial(&input, &message_set));
+ EXPECT_TRUE(input.ConsumedEntireMessage());
+
+ EXPECT_EQ(123, message_set.GetExtension(
+ unittest::TestMessageSetExtension1::message_set_extension).i());
+ }
+}
+
+TEST(WireFormatTest, ParseBrokenMessageSet) {
+ proto2_wireformat_unittest::TestMessageSet message_set;
+ string input("goodbye"); // Invalid wire format data.
+ EXPECT_FALSE(message_set.ParseFromString(input));
+}
+
+TEST(WireFormatTest, RecursionLimit) {
+ unittest::TestRecursiveMessage message;
+ message.mutable_a()->mutable_a()->mutable_a()->mutable_a()->set_i(1);
+ string data;
+ message.SerializeToString(&data);
+
+ {
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ input.SetRecursionLimit(4);
+ unittest::TestRecursiveMessage message2;
+ EXPECT_TRUE(message2.ParseFromCodedStream(&input));
+ }
+
+ {
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ input.SetRecursionLimit(3);
+ unittest::TestRecursiveMessage message2;
+ EXPECT_FALSE(message2.ParseFromCodedStream(&input));
+ }
+}
+
+TEST(WireFormatTest, UnknownFieldRecursionLimit) {
+ unittest::TestEmptyMessage message;
+ message.mutable_unknown_fields()
+ ->AddGroup(1234)
+ ->AddGroup(1234)
+ ->AddGroup(1234)
+ ->AddGroup(1234)
+ ->AddVarint(1234, 123);
+ string data;
+ message.SerializeToString(&data);
+
+ {
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ input.SetRecursionLimit(4);
+ unittest::TestEmptyMessage message2;
+ EXPECT_TRUE(message2.ParseFromCodedStream(&input));
+ }
+
+ {
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream input(&raw_input);
+ input.SetRecursionLimit(3);
+ unittest::TestEmptyMessage message2;
+ EXPECT_FALSE(message2.ParseFromCodedStream(&input));
+ }
+}
+
+TEST(WireFormatTest, ZigZag) {
+// avoid line-wrapping
+#define LL(x) GOOGLE_LONGLONG(x)
+#define ULL(x) GOOGLE_ULONGLONG(x)
+#define ZigZagEncode32(x) WireFormatLite::ZigZagEncode32(x)
+#define ZigZagDecode32(x) WireFormatLite::ZigZagDecode32(x)
+#define ZigZagEncode64(x) WireFormatLite::ZigZagEncode64(x)
+#define ZigZagDecode64(x) WireFormatLite::ZigZagDecode64(x)
+
+ EXPECT_EQ(0u, ZigZagEncode32( 0));
+ EXPECT_EQ(1u, ZigZagEncode32(-1));
+ EXPECT_EQ(2u, ZigZagEncode32( 1));
+ EXPECT_EQ(3u, ZigZagEncode32(-2));
+ EXPECT_EQ(0x7FFFFFFEu, ZigZagEncode32(0x3FFFFFFF));
+ EXPECT_EQ(0x7FFFFFFFu, ZigZagEncode32(0xC0000000));
+ EXPECT_EQ(0xFFFFFFFEu, ZigZagEncode32(0x7FFFFFFF));
+ EXPECT_EQ(0xFFFFFFFFu, ZigZagEncode32(0x80000000));
+
+ EXPECT_EQ( 0, ZigZagDecode32(0u));
+ EXPECT_EQ(-1, ZigZagDecode32(1u));
+ EXPECT_EQ( 1, ZigZagDecode32(2u));
+ EXPECT_EQ(-2, ZigZagDecode32(3u));
+ EXPECT_EQ(0x3FFFFFFF, ZigZagDecode32(0x7FFFFFFEu));
+ EXPECT_EQ(0xC0000000, ZigZagDecode32(0x7FFFFFFFu));
+ EXPECT_EQ(0x7FFFFFFF, ZigZagDecode32(0xFFFFFFFEu));
+ EXPECT_EQ(0x80000000, ZigZagDecode32(0xFFFFFFFFu));
+
+ EXPECT_EQ(0u, ZigZagEncode64( 0));
+ EXPECT_EQ(1u, ZigZagEncode64(-1));
+ EXPECT_EQ(2u, ZigZagEncode64( 1));
+ EXPECT_EQ(3u, ZigZagEncode64(-2));
+ EXPECT_EQ(ULL(0x000000007FFFFFFE), ZigZagEncode64(LL(0x000000003FFFFFFF)));
+ EXPECT_EQ(ULL(0x000000007FFFFFFF), ZigZagEncode64(LL(0xFFFFFFFFC0000000)));
+ EXPECT_EQ(ULL(0x00000000FFFFFFFE), ZigZagEncode64(LL(0x000000007FFFFFFF)));
+ EXPECT_EQ(ULL(0x00000000FFFFFFFF), ZigZagEncode64(LL(0xFFFFFFFF80000000)));
+ EXPECT_EQ(ULL(0xFFFFFFFFFFFFFFFE), ZigZagEncode64(LL(0x7FFFFFFFFFFFFFFF)));
+ EXPECT_EQ(ULL(0xFFFFFFFFFFFFFFFF), ZigZagEncode64(LL(0x8000000000000000)));
+
+ EXPECT_EQ( 0, ZigZagDecode64(0u));
+ EXPECT_EQ(-1, ZigZagDecode64(1u));
+ EXPECT_EQ( 1, ZigZagDecode64(2u));
+ EXPECT_EQ(-2, ZigZagDecode64(3u));
+ EXPECT_EQ(LL(0x000000003FFFFFFF), ZigZagDecode64(ULL(0x000000007FFFFFFE)));
+ EXPECT_EQ(LL(0xFFFFFFFFC0000000), ZigZagDecode64(ULL(0x000000007FFFFFFF)));
+ EXPECT_EQ(LL(0x000000007FFFFFFF), ZigZagDecode64(ULL(0x00000000FFFFFFFE)));
+ EXPECT_EQ(LL(0xFFFFFFFF80000000), ZigZagDecode64(ULL(0x00000000FFFFFFFF)));
+ EXPECT_EQ(LL(0x7FFFFFFFFFFFFFFF), ZigZagDecode64(ULL(0xFFFFFFFFFFFFFFFE)));
+ EXPECT_EQ(LL(0x8000000000000000), ZigZagDecode64(ULL(0xFFFFFFFFFFFFFFFF)));
+
+ // Some easier-to-verify round-trip tests. The inputs (other than 0, 1, -1)
+ // were chosen semi-randomly via keyboard bashing.
+ EXPECT_EQ( 0, ZigZagDecode32(ZigZagEncode32( 0)));
+ EXPECT_EQ( 1, ZigZagDecode32(ZigZagEncode32( 1)));
+ EXPECT_EQ( -1, ZigZagDecode32(ZigZagEncode32( -1)));
+ EXPECT_EQ(14927, ZigZagDecode32(ZigZagEncode32(14927)));
+ EXPECT_EQ(-3612, ZigZagDecode32(ZigZagEncode32(-3612)));
+
+ EXPECT_EQ( 0, ZigZagDecode64(ZigZagEncode64( 0)));
+ EXPECT_EQ( 1, ZigZagDecode64(ZigZagEncode64( 1)));
+ EXPECT_EQ( -1, ZigZagDecode64(ZigZagEncode64( -1)));
+ EXPECT_EQ(14927, ZigZagDecode64(ZigZagEncode64(14927)));
+ EXPECT_EQ(-3612, ZigZagDecode64(ZigZagEncode64(-3612)));
+
+ EXPECT_EQ(LL(856912304801416), ZigZagDecode64(ZigZagEncode64(
+ LL(856912304801416))));
+ EXPECT_EQ(LL(-75123905439571256), ZigZagDecode64(ZigZagEncode64(
+ LL(-75123905439571256))));
+}
+
+TEST(WireFormatTest, RepeatedScalarsDifferentTagSizes) {
+ // At one point checks would trigger when parsing repeated fixed scalar
+ // fields.
+ protobuf_unittest::TestRepeatedScalarDifferentTagSizes msg1, msg2;
+ for (int i = 0; i < 100; ++i) {
+ msg1.add_repeated_fixed32(i);
+ msg1.add_repeated_int32(i);
+ msg1.add_repeated_fixed64(i);
+ msg1.add_repeated_int64(i);
+ msg1.add_repeated_float(i);
+ msg1.add_repeated_uint64(i);
+ }
+
+ // Make sure that we have a variety of tag sizes.
+ const google::protobuf::Descriptor* desc = msg1.GetDescriptor();
+ const google::protobuf::FieldDescriptor* field;
+ field = desc->FindFieldByName("repeated_fixed32");
+ ASSERT_TRUE(field != NULL);
+ ASSERT_EQ(1, WireFormat::TagSize(field->number(), field->type()));
+ field = desc->FindFieldByName("repeated_int32");
+ ASSERT_TRUE(field != NULL);
+ ASSERT_EQ(1, WireFormat::TagSize(field->number(), field->type()));
+ field = desc->FindFieldByName("repeated_fixed64");
+ ASSERT_TRUE(field != NULL);
+ ASSERT_EQ(2, WireFormat::TagSize(field->number(), field->type()));
+ field = desc->FindFieldByName("repeated_int64");
+ ASSERT_TRUE(field != NULL);
+ ASSERT_EQ(2, WireFormat::TagSize(field->number(), field->type()));
+ field = desc->FindFieldByName("repeated_float");
+ ASSERT_TRUE(field != NULL);
+ ASSERT_EQ(3, WireFormat::TagSize(field->number(), field->type()));
+ field = desc->FindFieldByName("repeated_uint64");
+ ASSERT_TRUE(field != NULL);
+ ASSERT_EQ(3, WireFormat::TagSize(field->number(), field->type()));
+
+ EXPECT_TRUE(msg2.ParseFromString(msg1.SerializeAsString()));
+ EXPECT_EQ(msg1.DebugString(), msg2.DebugString());
+}
+
+TEST(WireFormatTest, CompatibleTypes) {
+ const int64 data = 0x100000000LL;
+ unittest::Int64Message msg1;
+ msg1.set_data(data);
+ string serialized;
+ msg1.SerializeToString(&serialized);
+
+ // Test int64 is compatible with bool
+ unittest::BoolMessage msg2;
+ ASSERT_TRUE(msg2.ParseFromString(serialized));
+ ASSERT_EQ(static_cast<bool>(data), msg2.data());
+
+ // Test int64 is compatible with uint64
+ unittest::Uint64Message msg3;
+ ASSERT_TRUE(msg3.ParseFromString(serialized));
+ ASSERT_EQ(static_cast<uint64>(data), msg3.data());
+
+ // Test int64 is compatible with int32
+ unittest::Int32Message msg4;
+ ASSERT_TRUE(msg4.ParseFromString(serialized));
+ ASSERT_EQ(static_cast<int32>(data), msg4.data());
+
+ // Test int64 is compatible with uint32
+ unittest::Uint32Message msg5;
+ ASSERT_TRUE(msg5.ParseFromString(serialized));
+ ASSERT_EQ(static_cast<uint32>(data), msg5.data());
+}
+
+class Proto3PrimitiveRepeatedWireFormatTest : public ::testing::Test {
+ protected:
+ Proto3PrimitiveRepeatedWireFormatTest()
+ : packedTestAllTypes_(
+ "\xFA\x01\x01\x01"
+ "\x82\x02\x01\x01"
+ "\x8A\x02\x01\x01"
+ "\x92\x02\x01\x01"
+ "\x9A\x02\x01\x02"
+ "\xA2\x02\x01\x02"
+ "\xAA\x02\x04\x01\x00\x00\x00"
+ "\xB2\x02\x08\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\xBA\x02\x04\x01\x00\x00\x00"
+ "\xC2\x02\x08\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\xCA\x02\x04\x00\x00\x80\x3f"
+ "\xD2\x02\x08\x00\x00\x00\x00\x00\x00\xf0\x3f"
+ "\xDA\x02\x01\x01"
+ "\x9A\x03\x01\x01",
+ 86),
+ packedTestUnpackedTypes_(
+ "\x0A\x01\x01"
+ "\x12\x01\x01"
+ "\x1A\x01\x01"
+ "\x22\x01\x01"
+ "\x2A\x01\x02"
+ "\x32\x01\x02"
+ "\x3A\x04\x01\x00\x00\x00"
+ "\x42\x08\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\x4A\x04\x01\x00\x00\x00"
+ "\x52\x08\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\x5A\x04\x00\x00\x80\x3f"
+ "\x62\x08\x00\x00\x00\x00\x00\x00\xf0\x3f"
+ "\x6A\x01\x01"
+ "\x72\x01\x01",
+ 72),
+ unpackedTestAllTypes_(
+ "\xF8\x01\x01"
+ "\x80\x02\x01"
+ "\x88\x02\x01"
+ "\x90\x02\x01"
+ "\x98\x02\x02"
+ "\xA0\x02\x02"
+ "\xAD\x02\x01\x00\x00\x00"
+ "\xB1\x02\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\xBD\x02\x01\x00\x00\x00"
+ "\xC1\x02\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\xCD\x02\x00\x00\x80\x3f"
+ "\xD1\x02\x00\x00\x00\x00\x00\x00\xf0\x3f"
+ "\xD8\x02\x01"
+ "\x98\x03\x01",
+ 72),
+ unpackedTestUnpackedTypes_(
+ "\x08\x01"
+ "\x10\x01"
+ "\x18\x01"
+ "\x20\x01"
+ "\x28\x02"
+ "\x30\x02"
+ "\x3D\x01\x00\x00\x00"
+ "\x41\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\x4D\x01\x00\x00\x00"
+ "\x51\x01\x00\x00\x00\x00\x00\x00\x00"
+ "\x5D\x00\x00\x80\x3f"
+ "\x61\x00\x00\x00\x00\x00\x00\xf0\x3f"
+ "\x68\x01"
+ "\x70\x01",
+ 58) {}
+ template <class Proto>
+ void SetProto3PrimitiveRepeatedFields(Proto* message) {
+ message->add_repeated_int32(1);
+ message->add_repeated_int64(1);
+ message->add_repeated_uint32(1);
+ message->add_repeated_uint64(1);
+ message->add_repeated_sint32(1);
+ message->add_repeated_sint64(1);
+ message->add_repeated_fixed32(1);
+ message->add_repeated_fixed64(1);
+ message->add_repeated_sfixed32(1);
+ message->add_repeated_sfixed64(1);
+ message->add_repeated_float(1.0);
+ message->add_repeated_double(1.0);
+ message->add_repeated_bool(true);
+ message->add_repeated_nested_enum(
+ proto3_arena_unittest::TestAllTypes_NestedEnum_FOO);
+ }
+
+ template <class Proto>
+ void ExpectProto3PrimitiveRepeatedFieldsSet(const Proto& message) {
+ EXPECT_EQ(1, message.repeated_int32(0));
+ EXPECT_EQ(1, message.repeated_int64(0));
+ EXPECT_EQ(1, message.repeated_uint32(0));
+ EXPECT_EQ(1, message.repeated_uint64(0));
+ EXPECT_EQ(1, message.repeated_sint32(0));
+ EXPECT_EQ(1, message.repeated_sint64(0));
+ EXPECT_EQ(1, message.repeated_fixed32(0));
+ EXPECT_EQ(1, message.repeated_fixed64(0));
+ EXPECT_EQ(1, message.repeated_sfixed32(0));
+ EXPECT_EQ(1, message.repeated_sfixed64(0));
+ EXPECT_EQ(1.0, message.repeated_float(0));
+ EXPECT_EQ(1.0, message.repeated_double(0));
+ EXPECT_EQ(true, message.repeated_bool(0));
+ EXPECT_EQ(proto3_arena_unittest::TestAllTypes_NestedEnum_FOO,
+ message.repeated_nested_enum(0));
+ }
+
+ template <class Proto>
+ void TestSerialization(Proto* message, const string& expected) {
+ SetProto3PrimitiveRepeatedFields(message);
+
+ int size = message->ByteSize();
+
+ // Serialize using the generated code.
+ string generated_data;
+ {
+ io::StringOutputStream raw_output(&generated_data);
+ io::CodedOutputStream output(&raw_output);
+ message->SerializeWithCachedSizes(&output);
+ ASSERT_FALSE(output.HadError());
+ }
+ EXPECT_TRUE(expected == generated_data);
+
+ // Serialize using the dynamic code.
+ string dynamic_data;
+ {
+ io::StringOutputStream raw_output(&dynamic_data);
+ io::CodedOutputStream output(&raw_output);
+ WireFormat::SerializeWithCachedSizes(*message, size, &output);
+ ASSERT_FALSE(output.HadError());
+ }
+ EXPECT_TRUE(expected == dynamic_data);
+ }
+
+ template <class Proto>
+ void TestParsing(Proto* message, const string& compatible_data) {
+ message->Clear();
+ message->ParseFromString(compatible_data);
+ ExpectProto3PrimitiveRepeatedFieldsSet(*message);
+
+ message->Clear();
+ io::CodedInputStream input(
+ reinterpret_cast<const uint8*>(compatible_data.data()),
+ compatible_data.size());
+ WireFormat::ParseAndMergePartial(&input, message);
+ ExpectProto3PrimitiveRepeatedFieldsSet(*message);
+ }
+
+ const string packedTestAllTypes_;
+ const string packedTestUnpackedTypes_;
+ const string unpackedTestAllTypes_;
+ const string unpackedTestUnpackedTypes_;
+};
+
+TEST_F(Proto3PrimitiveRepeatedWireFormatTest, Proto3PrimitiveRepeated) {
+ proto3_arena_unittest::TestAllTypes packed_message;
+ proto3_arena_unittest::TestUnpackedTypes unpacked_message;
+ TestSerialization(&packed_message, packedTestAllTypes_);
+ TestParsing(&packed_message, packedTestAllTypes_);
+ TestParsing(&packed_message, unpackedTestAllTypes_);
+ TestSerialization(&unpacked_message, unpackedTestUnpackedTypes_);
+ TestParsing(&unpacked_message, packedTestUnpackedTypes_);
+ TestParsing(&unpacked_message, unpackedTestUnpackedTypes_);
+}
+
+class WireFormatInvalidInputTest : public testing::Test {
+ protected:
+ // Make a serialized TestAllTypes in which the field optional_nested_message
+ // contains exactly the given bytes, which may be invalid.
+ string MakeInvalidEmbeddedMessage(const char* bytes, int size) {
+ const FieldDescriptor* field =
+ unittest::TestAllTypes::descriptor()->FindFieldByName(
+ "optional_nested_message");
+ GOOGLE_CHECK(field != NULL);
+
+ string result;
+
+ {
+ io::StringOutputStream raw_output(&result);
+ io::CodedOutputStream output(&raw_output);
+
+ WireFormatLite::WriteBytes(field->number(), string(bytes, size), &output);
+ }
+
+ return result;
+ }
+
+ // Make a serialized TestAllTypes in which the field optionalgroup
+ // contains exactly the given bytes -- which may be invalid -- and
+ // possibly no end tag.
+ string MakeInvalidGroup(const char* bytes, int size, bool include_end_tag) {
+ const FieldDescriptor* field =
+ unittest::TestAllTypes::descriptor()->FindFieldByName(
+ "optionalgroup");
+ GOOGLE_CHECK(field != NULL);
+
+ string result;
+
+ {
+ io::StringOutputStream raw_output(&result);
+ io::CodedOutputStream output(&raw_output);
+
+ output.WriteVarint32(WireFormat::MakeTag(field));
+ output.WriteString(string(bytes, size));
+ if (include_end_tag) {
+ output.WriteVarint32(WireFormatLite::MakeTag(
+ field->number(), WireFormatLite::WIRETYPE_END_GROUP));
+ }
+ }
+
+ return result;
+ }
+};
+
+TEST_F(WireFormatInvalidInputTest, InvalidSubMessage) {
+ unittest::TestAllTypes message;
+
+ // Control case.
+ EXPECT_TRUE(message.ParseFromString(MakeInvalidEmbeddedMessage("", 0)));
+
+ // The byte is a valid varint, but not a valid tag (zero).
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidEmbeddedMessage("\0", 1)));
+
+ // The byte is a malformed varint.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidEmbeddedMessage("\200", 1)));
+
+ // The byte is an endgroup tag, but we aren't parsing a group.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidEmbeddedMessage("\014", 1)));
+
+ // The byte is a valid varint but not a valid tag (bad wire type).
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidEmbeddedMessage("\017", 1)));
+}
+
+TEST_F(WireFormatInvalidInputTest, InvalidGroup) {
+ unittest::TestAllTypes message;
+
+ // Control case.
+ EXPECT_TRUE(message.ParseFromString(MakeInvalidGroup("", 0, true)));
+
+ // Missing end tag. Groups cannot end at EOF.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("", 0, false)));
+
+ // The byte is a valid varint, but not a valid tag (zero).
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\0", 1, false)));
+
+ // The byte is a malformed varint.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\200", 1, false)));
+
+ // The byte is an endgroup tag, but not the right one for this group.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\014", 1, false)));
+
+ // The byte is a valid varint but not a valid tag (bad wire type).
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\017", 1, true)));
+}
+
+TEST_F(WireFormatInvalidInputTest, InvalidUnknownGroup) {
+ // Use TestEmptyMessage so that the group made by MakeInvalidGroup will not
+ // be a known tag number.
+ unittest::TestEmptyMessage message;
+
+ // Control case.
+ EXPECT_TRUE(message.ParseFromString(MakeInvalidGroup("", 0, true)));
+
+ // Missing end tag. Groups cannot end at EOF.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("", 0, false)));
+
+ // The byte is a valid varint, but not a valid tag (zero).
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\0", 1, false)));
+
+ // The byte is a malformed varint.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\200", 1, false)));
+
+ // The byte is an endgroup tag, but not the right one for this group.
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\014", 1, false)));
+
+ // The byte is a valid varint but not a valid tag (bad wire type).
+ EXPECT_FALSE(message.ParseFromString(MakeInvalidGroup("\017", 1, true)));
+}
+
+TEST_F(WireFormatInvalidInputTest, InvalidStringInUnknownGroup) {
+ // Test a bug fix: SkipMessage should fail if the message contains a string
+ // whose length would extend beyond the message end.
+
+ unittest::TestAllTypes message;
+ message.set_optional_string("foo foo foo foo");
+ string data;
+ message.SerializeToString(&data);
+
+ // Chop some bytes off the end.
+ data.resize(data.size() - 4);
+
+ // Try to skip it. Note that the bug was only present when parsing to an
+ // UnknownFieldSet.
+ io::ArrayInputStream raw_input(data.data(), data.size());
+ io::CodedInputStream coded_input(&raw_input);
+ UnknownFieldSet unknown_fields;
+ EXPECT_FALSE(WireFormat::SkipMessage(&coded_input, &unknown_fields));
+}
+
+// Test differences between string and bytes.
+// Value of a string type must be valid UTF-8 string. When UTF-8
+// validation is enabled (GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED):
+// WriteInvalidUTF8String: see error message.
+// ReadInvalidUTF8String: see error message.
+// WriteValidUTF8String: fine.
+// ReadValidUTF8String: fine.
+// WriteAnyBytes: fine.
+// ReadAnyBytes: fine.
+const char * kInvalidUTF8String = "Invalid UTF-8: \xA0\xB0\xC0\xD0";
+// This used to be "Valid UTF-8: \x01\x02\u8C37\u6B4C", but MSVC seems to
+// interpret \u differently from GCC.
+const char * kValidUTF8String = "Valid UTF-8: \x01\x02\350\260\267\346\255\214";
+
+template<typename T>
+bool WriteMessage(const char *value, T *message, string *wire_buffer) {
+ message->set_data(value);
+ wire_buffer->clear();
+ message->AppendToString(wire_buffer);
+ return (wire_buffer->size() > 0);
+}
+
+template<typename T>
+bool ReadMessage(const string &wire_buffer, T *message) {
+ return message->ParseFromArray(wire_buffer.data(), wire_buffer.size());
+}
+
+bool StartsWith(const string& s, const string& prefix) {
+ return s.substr(0, prefix.length()) == prefix;
+}
+
+class Utf8ValidationTest : public ::testing::Test {
+ protected:
+ Utf8ValidationTest() {}
+ virtual ~Utf8ValidationTest() {}
+ virtual void SetUp() {
+ }
+
+};
+
+TEST_F(Utf8ValidationTest, WriteInvalidUTF8String) {
+ string wire_buffer;
+ protobuf_unittest::OneString input;
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ WriteMessage(kInvalidUTF8String, &input, &wire_buffer);
+ errors = log.GetMessages(ERROR);
+ }
+#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+ ASSERT_EQ(1, errors.size());
+ EXPECT_TRUE(StartsWith(errors[0],
+ "String field 'protobuf_unittest.OneString.data' "
+ "contains invalid UTF-8 data when "
+ "serializing a protocol buffer. Use the "
+ "'bytes' type if you intend to send raw bytes."));
+#else
+ ASSERT_EQ(0, errors.size());
+#endif // GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+}
+
+
+TEST_F(Utf8ValidationTest, ReadInvalidUTF8String) {
+ string wire_buffer;
+ protobuf_unittest::OneString input;
+ WriteMessage(kInvalidUTF8String, &input, &wire_buffer);
+ protobuf_unittest::OneString output;
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ ReadMessage(wire_buffer, &output);
+ errors = log.GetMessages(ERROR);
+ }
+#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+ ASSERT_EQ(1, errors.size());
+ EXPECT_TRUE(StartsWith(errors[0],
+ "String field 'protobuf_unittest.OneString.data' "
+ "contains invalid UTF-8 data when "
+ "parsing a protocol buffer. Use the "
+ "'bytes' type if you intend to send raw bytes."));
+
+#else
+ ASSERT_EQ(0, errors.size());
+#endif // GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+}
+
+
+TEST_F(Utf8ValidationTest, WriteValidUTF8String) {
+ string wire_buffer;
+ protobuf_unittest::OneString input;
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ WriteMessage(kValidUTF8String, &input, &wire_buffer);
+ errors = log.GetMessages(ERROR);
+ }
+ ASSERT_EQ(0, errors.size());
+}
+
+TEST_F(Utf8ValidationTest, ReadValidUTF8String) {
+ string wire_buffer;
+ protobuf_unittest::OneString input;
+ WriteMessage(kValidUTF8String, &input, &wire_buffer);
+ protobuf_unittest::OneString output;
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ ReadMessage(wire_buffer, &output);
+ errors = log.GetMessages(ERROR);
+ }
+ ASSERT_EQ(0, errors.size());
+ EXPECT_EQ(input.data(), output.data());
+}
+
+// Bytes: anything can pass as bytes, use invalid UTF-8 string to test
+TEST_F(Utf8ValidationTest, WriteArbitraryBytes) {
+ string wire_buffer;
+ protobuf_unittest::OneBytes input;
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ WriteMessage(kInvalidUTF8String, &input, &wire_buffer);
+ errors = log.GetMessages(ERROR);
+ }
+ ASSERT_EQ(0, errors.size());
+}
+
+TEST_F(Utf8ValidationTest, ReadArbitraryBytes) {
+ string wire_buffer;
+ protobuf_unittest::OneBytes input;
+ WriteMessage(kInvalidUTF8String, &input, &wire_buffer);
+ protobuf_unittest::OneBytes output;
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ ReadMessage(wire_buffer, &output);
+ errors = log.GetMessages(ERROR);
+ }
+ ASSERT_EQ(0, errors.size());
+ EXPECT_EQ(input.data(), output.data());
+}
+
+TEST_F(Utf8ValidationTest, ParseRepeatedString) {
+ protobuf_unittest::MoreBytes input;
+ input.add_data(kValidUTF8String);
+ input.add_data(kInvalidUTF8String);
+ input.add_data(kInvalidUTF8String);
+ string wire_buffer = input.SerializeAsString();
+
+ protobuf_unittest::MoreString output;
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ ReadMessage(wire_buffer, &output);
+ errors = log.GetMessages(ERROR);
+ }
+#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+ ASSERT_EQ(2, errors.size());
+#else
+ ASSERT_EQ(0, errors.size());
+#endif // GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+ EXPECT_EQ(wire_buffer, output.SerializeAsString());
+}
+
+// Test the old VerifyUTF8String() function, which may still be called by old
+// generated code.
+TEST_F(Utf8ValidationTest, OldVerifyUTF8String) {
+ string data(kInvalidUTF8String);
+
+ vector<string> errors;
+ {
+ ScopedMemoryLog log;
+ WireFormat::VerifyUTF8String(data.data(), data.size(),
+ WireFormat::SERIALIZE);
+ errors = log.GetMessages(ERROR);
+ }
+#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
+ ASSERT_EQ(1, errors.size());
+ EXPECT_TRUE(StartsWith(errors[0],
+ "String field contains invalid UTF-8 data when "
+ "serializing a protocol buffer. Use the "
+ "'bytes' type if you intend to send raw bytes."));
+#else
+ ASSERT_EQ(0, errors.size());
+#endif
+}
+
+
+} // namespace
+} // namespace internal
+} // namespace protobuf
+} // namespace google
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.cc b/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.cc
new file mode 100644
index 0000000000..33a69d3b18
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.cc
@@ -0,0 +1,2801 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/wrappers.proto
+
+#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
+#include <google/protobuf/wrappers.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>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+namespace {
+
+const ::google::protobuf::Descriptor* DoubleValue_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ DoubleValue_reflection_ = NULL;
+const ::google::protobuf::Descriptor* FloatValue_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ FloatValue_reflection_ = NULL;
+const ::google::protobuf::Descriptor* Int64Value_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Int64Value_reflection_ = NULL;
+const ::google::protobuf::Descriptor* UInt64Value_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ UInt64Value_reflection_ = NULL;
+const ::google::protobuf::Descriptor* Int32Value_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ Int32Value_reflection_ = NULL;
+const ::google::protobuf::Descriptor* UInt32Value_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ UInt32Value_reflection_ = NULL;
+const ::google::protobuf::Descriptor* BoolValue_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ BoolValue_reflection_ = NULL;
+const ::google::protobuf::Descriptor* StringValue_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ StringValue_reflection_ = NULL;
+const ::google::protobuf::Descriptor* BytesValue_descriptor_ = NULL;
+const ::google::protobuf::internal::GeneratedMessageReflection*
+ BytesValue_reflection_ = NULL;
+
+} // namespace
+
+
+void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ const ::google::protobuf::FileDescriptor* file =
+ ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
+ "google/protobuf/wrappers.proto");
+ GOOGLE_CHECK(file != NULL);
+ DoubleValue_descriptor_ = file->message_type(0);
+ static const int DoubleValue_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DoubleValue, value_),
+ };
+ DoubleValue_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ DoubleValue_descriptor_,
+ DoubleValue::default_instance_,
+ DoubleValue_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(DoubleValue),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DoubleValue, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(DoubleValue, _is_default_instance_));
+ FloatValue_descriptor_ = file->message_type(1);
+ static const int FloatValue_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FloatValue, value_),
+ };
+ FloatValue_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ FloatValue_descriptor_,
+ FloatValue::default_instance_,
+ FloatValue_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(FloatValue),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FloatValue, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(FloatValue, _is_default_instance_));
+ Int64Value_descriptor_ = file->message_type(2);
+ static const int Int64Value_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Int64Value, value_),
+ };
+ Int64Value_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Int64Value_descriptor_,
+ Int64Value::default_instance_,
+ Int64Value_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Int64Value),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Int64Value, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Int64Value, _is_default_instance_));
+ UInt64Value_descriptor_ = file->message_type(3);
+ static const int UInt64Value_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UInt64Value, value_),
+ };
+ UInt64Value_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ UInt64Value_descriptor_,
+ UInt64Value::default_instance_,
+ UInt64Value_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(UInt64Value),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UInt64Value, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UInt64Value, _is_default_instance_));
+ Int32Value_descriptor_ = file->message_type(4);
+ static const int Int32Value_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Int32Value, value_),
+ };
+ Int32Value_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ Int32Value_descriptor_,
+ Int32Value::default_instance_,
+ Int32Value_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(Int32Value),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Int32Value, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Int32Value, _is_default_instance_));
+ UInt32Value_descriptor_ = file->message_type(5);
+ static const int UInt32Value_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UInt32Value, value_),
+ };
+ UInt32Value_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ UInt32Value_descriptor_,
+ UInt32Value::default_instance_,
+ UInt32Value_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(UInt32Value),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UInt32Value, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(UInt32Value, _is_default_instance_));
+ BoolValue_descriptor_ = file->message_type(6);
+ static const int BoolValue_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(BoolValue, value_),
+ };
+ BoolValue_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ BoolValue_descriptor_,
+ BoolValue::default_instance_,
+ BoolValue_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(BoolValue),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(BoolValue, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(BoolValue, _is_default_instance_));
+ StringValue_descriptor_ = file->message_type(7);
+ static const int StringValue_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(StringValue, value_),
+ };
+ StringValue_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ StringValue_descriptor_,
+ StringValue::default_instance_,
+ StringValue_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(StringValue),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(StringValue, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(StringValue, _is_default_instance_));
+ BytesValue_descriptor_ = file->message_type(8);
+ static const int BytesValue_offsets_[1] = {
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(BytesValue, value_),
+ };
+ BytesValue_reflection_ =
+ ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
+ BytesValue_descriptor_,
+ BytesValue::default_instance_,
+ BytesValue_offsets_,
+ -1,
+ -1,
+ -1,
+ sizeof(BytesValue),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(BytesValue, _internal_metadata_),
+ GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(BytesValue, _is_default_instance_));
+}
+
+namespace {
+
+GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
+inline void protobuf_AssignDescriptorsOnce() {
+ ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
+ &protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ DoubleValue_descriptor_, &DoubleValue::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ FloatValue_descriptor_, &FloatValue::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Int64Value_descriptor_, &Int64Value::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ UInt64Value_descriptor_, &UInt64Value::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ Int32Value_descriptor_, &Int32Value::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ UInt32Value_descriptor_, &UInt32Value::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ BoolValue_descriptor_, &BoolValue::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ StringValue_descriptor_, &StringValue::default_instance());
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
+ BytesValue_descriptor_, &BytesValue::default_instance());
+}
+
+} // namespace
+
+void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto() {
+ delete DoubleValue::default_instance_;
+ delete DoubleValue_reflection_;
+ delete FloatValue::default_instance_;
+ delete FloatValue_reflection_;
+ delete Int64Value::default_instance_;
+ delete Int64Value_reflection_;
+ delete UInt64Value::default_instance_;
+ delete UInt64Value_reflection_;
+ delete Int32Value::default_instance_;
+ delete Int32Value_reflection_;
+ delete UInt32Value::default_instance_;
+ delete UInt32Value_reflection_;
+ delete BoolValue::default_instance_;
+ delete BoolValue_reflection_;
+ delete StringValue::default_instance_;
+ delete StringValue_reflection_;
+ delete BytesValue::default_instance_;
+ delete BytesValue_reflection_;
+}
+
+void protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto() GOOGLE_ATTRIBUTE_COLD;
+void protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto() {
+ static bool already_here = false;
+ if (already_here) return;
+ already_here = true;
+ GOOGLE_PROTOBUF_VERIFY_VERSION;
+
+ ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+ "\n\036google/protobuf/wrappers.proto\022\017google"
+ ".protobuf\"\034\n\013DoubleValue\022\r\n\005value\030\001 \001(\001\""
+ "\033\n\nFloatValue\022\r\n\005value\030\001 \001(\002\"\033\n\nInt64Val"
+ "ue\022\r\n\005value\030\001 \001(\003\"\034\n\013UInt64Value\022\r\n\005valu"
+ "e\030\001 \001(\004\"\033\n\nInt32Value\022\r\n\005value\030\001 \001(\005\"\034\n\013"
+ "UInt32Value\022\r\n\005value\030\001 \001(\r\"\032\n\tBoolValue\022"
+ "\r\n\005value\030\001 \001(\010\"\034\n\013StringValue\022\r\n\005value\030\001"
+ " \001(\t\"\033\n\nBytesValue\022\r\n\005value\030\001 \001(\014B\177\n\023com"
+ ".google.protobufB\rWrappersProtoP\001Z*githu"
+ "b.com/golang/protobuf/ptypes/wrappers\240\001\001"
+ "\370\001\001\242\002\003GPB\252\002\036Google.Protobuf.WellKnownTyp"
+ "esb\006proto3", 450);
+ ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+ "google/protobuf/wrappers.proto", &protobuf_RegisterTypes);
+ DoubleValue::default_instance_ = new DoubleValue();
+ FloatValue::default_instance_ = new FloatValue();
+ Int64Value::default_instance_ = new Int64Value();
+ UInt64Value::default_instance_ = new UInt64Value();
+ Int32Value::default_instance_ = new Int32Value();
+ UInt32Value::default_instance_ = new UInt32Value();
+ BoolValue::default_instance_ = new BoolValue();
+ StringValue::default_instance_ = new StringValue();
+ BytesValue::default_instance_ = new BytesValue();
+ DoubleValue::default_instance_->InitAsDefaultInstance();
+ FloatValue::default_instance_->InitAsDefaultInstance();
+ Int64Value::default_instance_->InitAsDefaultInstance();
+ UInt64Value::default_instance_->InitAsDefaultInstance();
+ Int32Value::default_instance_->InitAsDefaultInstance();
+ UInt32Value::default_instance_->InitAsDefaultInstance();
+ BoolValue::default_instance_->InitAsDefaultInstance();
+ StringValue::default_instance_->InitAsDefaultInstance();
+ BytesValue::default_instance_->InitAsDefaultInstance();
+ ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto);
+}
+
+// Force AddDescriptors() to be called at static initialization time.
+struct StaticDescriptorInitializer_google_2fprotobuf_2fwrappers_2eproto {
+ StaticDescriptorInitializer_google_2fprotobuf_2fwrappers_2eproto() {
+ protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ }
+} static_descriptor_initializer_google_2fprotobuf_2fwrappers_2eproto_;
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int DoubleValue::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+DoubleValue::DoubleValue()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.DoubleValue)
+}
+
+DoubleValue::DoubleValue(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.DoubleValue)
+}
+
+void DoubleValue::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+DoubleValue::DoubleValue(const DoubleValue& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.DoubleValue)
+}
+
+void DoubleValue::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ value_ = 0;
+}
+
+DoubleValue::~DoubleValue() {
+ // @@protoc_insertion_point(destructor:google.protobuf.DoubleValue)
+ SharedDtor();
+}
+
+void DoubleValue::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void DoubleValue::ArenaDtor(void* object) {
+ DoubleValue* _this = reinterpret_cast< DoubleValue* >(object);
+ (void)_this;
+}
+void DoubleValue::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void DoubleValue::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* DoubleValue::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return DoubleValue_descriptor_;
+}
+
+const DoubleValue& DoubleValue::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+DoubleValue* DoubleValue::default_instance_ = NULL;
+
+DoubleValue* DoubleValue::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<DoubleValue>(arena);
+}
+
+void DoubleValue::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.DoubleValue)
+ value_ = 0;
+}
+
+bool DoubleValue::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.DoubleValue)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional double value = 1;
+ case 1: {
+ if (tag == 9) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ double, ::google::protobuf::internal::WireFormatLite::TYPE_DOUBLE>(
+ input, &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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.DoubleValue)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.DoubleValue)
+ return false;
+#undef DO_
+}
+
+void DoubleValue::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.DoubleValue)
+ // optional double value = 1;
+ if (this->value() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteDouble(1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.DoubleValue)
+}
+
+::google::protobuf::uint8* DoubleValue::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.DoubleValue)
+ // optional double value = 1;
+ if (this->value() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteDoubleToArray(1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.DoubleValue)
+ return target;
+}
+
+int DoubleValue::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.DoubleValue)
+ int total_size = 0;
+
+ // optional double value = 1;
+ if (this->value() != 0) {
+ total_size += 1 + 8;
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void DoubleValue::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.DoubleValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const DoubleValue* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const DoubleValue>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.DoubleValue)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.DoubleValue)
+ MergeFrom(*source);
+ }
+}
+
+void DoubleValue::MergeFrom(const DoubleValue& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.DoubleValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value() != 0) {
+ set_value(from.value());
+ }
+}
+
+void DoubleValue::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.DoubleValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void DoubleValue::CopyFrom(const DoubleValue& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.DoubleValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool DoubleValue::IsInitialized() const {
+
+ return true;
+}
+
+void DoubleValue::Swap(DoubleValue* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ DoubleValue temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void DoubleValue::UnsafeArenaSwap(DoubleValue* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void DoubleValue::InternalSwap(DoubleValue* other) {
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata DoubleValue::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = DoubleValue_descriptor_;
+ metadata.reflection = DoubleValue_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// DoubleValue
+
+// optional double value = 1;
+void DoubleValue::clear_value() {
+ value_ = 0;
+}
+ double DoubleValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DoubleValue.value)
+ return value_;
+}
+ void DoubleValue::set_value(double value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DoubleValue.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int FloatValue::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+FloatValue::FloatValue()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.FloatValue)
+}
+
+FloatValue::FloatValue(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.FloatValue)
+}
+
+void FloatValue::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+FloatValue::FloatValue(const FloatValue& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.FloatValue)
+}
+
+void FloatValue::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ value_ = 0;
+}
+
+FloatValue::~FloatValue() {
+ // @@protoc_insertion_point(destructor:google.protobuf.FloatValue)
+ SharedDtor();
+}
+
+void FloatValue::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void FloatValue::ArenaDtor(void* object) {
+ FloatValue* _this = reinterpret_cast< FloatValue* >(object);
+ (void)_this;
+}
+void FloatValue::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void FloatValue::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* FloatValue::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return FloatValue_descriptor_;
+}
+
+const FloatValue& FloatValue::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+FloatValue* FloatValue::default_instance_ = NULL;
+
+FloatValue* FloatValue::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<FloatValue>(arena);
+}
+
+void FloatValue::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.FloatValue)
+ value_ = 0;
+}
+
+bool FloatValue::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.FloatValue)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional float value = 1;
+ case 1: {
+ if (tag == 13) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ float, ::google::protobuf::internal::WireFormatLite::TYPE_FLOAT>(
+ input, &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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.FloatValue)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.FloatValue)
+ return false;
+#undef DO_
+}
+
+void FloatValue::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.FloatValue)
+ // optional float value = 1;
+ if (this->value() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteFloat(1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.FloatValue)
+}
+
+::google::protobuf::uint8* FloatValue::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.FloatValue)
+ // optional float value = 1;
+ if (this->value() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteFloatToArray(1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.FloatValue)
+ return target;
+}
+
+int FloatValue::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.FloatValue)
+ int total_size = 0;
+
+ // optional float value = 1;
+ if (this->value() != 0) {
+ total_size += 1 + 4;
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void FloatValue::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.FloatValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const FloatValue* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const FloatValue>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.FloatValue)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.FloatValue)
+ MergeFrom(*source);
+ }
+}
+
+void FloatValue::MergeFrom(const FloatValue& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.FloatValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value() != 0) {
+ set_value(from.value());
+ }
+}
+
+void FloatValue::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.FloatValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void FloatValue::CopyFrom(const FloatValue& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.FloatValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool FloatValue::IsInitialized() const {
+
+ return true;
+}
+
+void FloatValue::Swap(FloatValue* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ FloatValue temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void FloatValue::UnsafeArenaSwap(FloatValue* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void FloatValue::InternalSwap(FloatValue* other) {
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata FloatValue::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = FloatValue_descriptor_;
+ metadata.reflection = FloatValue_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// FloatValue
+
+// optional float value = 1;
+void FloatValue::clear_value() {
+ value_ = 0;
+}
+ float FloatValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FloatValue.value)
+ return value_;
+}
+ void FloatValue::set_value(float value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FloatValue.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Int64Value::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Int64Value::Int64Value()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Int64Value)
+}
+
+Int64Value::Int64Value(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.Int64Value)
+}
+
+void Int64Value::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Int64Value::Int64Value(const Int64Value& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Int64Value)
+}
+
+void Int64Value::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ value_ = GOOGLE_LONGLONG(0);
+}
+
+Int64Value::~Int64Value() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Int64Value)
+ SharedDtor();
+}
+
+void Int64Value::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void Int64Value::ArenaDtor(void* object) {
+ Int64Value* _this = reinterpret_cast< Int64Value* >(object);
+ (void)_this;
+}
+void Int64Value::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void Int64Value::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Int64Value::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Int64Value_descriptor_;
+}
+
+const Int64Value& Int64Value::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+Int64Value* Int64Value::default_instance_ = NULL;
+
+Int64Value* Int64Value::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<Int64Value>(arena);
+}
+
+void Int64Value::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Int64Value)
+ value_ = GOOGLE_LONGLONG(0);
+}
+
+bool Int64Value::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Int64Value)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional int64 value = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int64, ::google::protobuf::internal::WireFormatLite::TYPE_INT64>(
+ input, &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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Int64Value)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Int64Value)
+ return false;
+#undef DO_
+}
+
+void Int64Value::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Int64Value)
+ // optional int64 value = 1;
+ if (this->value() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt64(1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Int64Value)
+}
+
+::google::protobuf::uint8* Int64Value::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Int64Value)
+ // optional int64 value = 1;
+ if (this->value() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt64ToArray(1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Int64Value)
+ return target;
+}
+
+int Int64Value::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Int64Value)
+ int total_size = 0;
+
+ // optional int64 value = 1;
+ if (this->value() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int64Size(
+ this->value());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Int64Value::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Int64Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Int64Value* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Int64Value>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Int64Value)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Int64Value)
+ MergeFrom(*source);
+ }
+}
+
+void Int64Value::MergeFrom(const Int64Value& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Int64Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value() != 0) {
+ set_value(from.value());
+ }
+}
+
+void Int64Value::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Int64Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Int64Value::CopyFrom(const Int64Value& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Int64Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Int64Value::IsInitialized() const {
+
+ return true;
+}
+
+void Int64Value::Swap(Int64Value* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ Int64Value temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void Int64Value::UnsafeArenaSwap(Int64Value* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void Int64Value::InternalSwap(Int64Value* other) {
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Int64Value::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Int64Value_descriptor_;
+ metadata.reflection = Int64Value_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Int64Value
+
+// optional int64 value = 1;
+void Int64Value::clear_value() {
+ value_ = GOOGLE_LONGLONG(0);
+}
+ ::google::protobuf::int64 Int64Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Int64Value.value)
+ return value_;
+}
+ void Int64Value::set_value(::google::protobuf::int64 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Int64Value.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int UInt64Value::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+UInt64Value::UInt64Value()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.UInt64Value)
+}
+
+UInt64Value::UInt64Value(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.UInt64Value)
+}
+
+void UInt64Value::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+UInt64Value::UInt64Value(const UInt64Value& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.UInt64Value)
+}
+
+void UInt64Value::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ value_ = GOOGLE_ULONGLONG(0);
+}
+
+UInt64Value::~UInt64Value() {
+ // @@protoc_insertion_point(destructor:google.protobuf.UInt64Value)
+ SharedDtor();
+}
+
+void UInt64Value::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void UInt64Value::ArenaDtor(void* object) {
+ UInt64Value* _this = reinterpret_cast< UInt64Value* >(object);
+ (void)_this;
+}
+void UInt64Value::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void UInt64Value::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* UInt64Value::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return UInt64Value_descriptor_;
+}
+
+const UInt64Value& UInt64Value::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+UInt64Value* UInt64Value::default_instance_ = NULL;
+
+UInt64Value* UInt64Value::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<UInt64Value>(arena);
+}
+
+void UInt64Value::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.UInt64Value)
+ value_ = GOOGLE_ULONGLONG(0);
+}
+
+bool UInt64Value::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.UInt64Value)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional uint64 value = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::uint64, ::google::protobuf::internal::WireFormatLite::TYPE_UINT64>(
+ input, &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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.UInt64Value)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.UInt64Value)
+ return false;
+#undef DO_
+}
+
+void UInt64Value::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.UInt64Value)
+ // optional uint64 value = 1;
+ if (this->value() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteUInt64(1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.UInt64Value)
+}
+
+::google::protobuf::uint8* UInt64Value::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.UInt64Value)
+ // optional uint64 value = 1;
+ if (this->value() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteUInt64ToArray(1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.UInt64Value)
+ return target;
+}
+
+int UInt64Value::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.UInt64Value)
+ int total_size = 0;
+
+ // optional uint64 value = 1;
+ if (this->value() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::UInt64Size(
+ this->value());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void UInt64Value::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.UInt64Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const UInt64Value* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const UInt64Value>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.UInt64Value)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.UInt64Value)
+ MergeFrom(*source);
+ }
+}
+
+void UInt64Value::MergeFrom(const UInt64Value& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.UInt64Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value() != 0) {
+ set_value(from.value());
+ }
+}
+
+void UInt64Value::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.UInt64Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void UInt64Value::CopyFrom(const UInt64Value& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.UInt64Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool UInt64Value::IsInitialized() const {
+
+ return true;
+}
+
+void UInt64Value::Swap(UInt64Value* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ UInt64Value temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void UInt64Value::UnsafeArenaSwap(UInt64Value* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void UInt64Value::InternalSwap(UInt64Value* other) {
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata UInt64Value::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = UInt64Value_descriptor_;
+ metadata.reflection = UInt64Value_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// UInt64Value
+
+// optional uint64 value = 1;
+void UInt64Value::clear_value() {
+ value_ = GOOGLE_ULONGLONG(0);
+}
+ ::google::protobuf::uint64 UInt64Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UInt64Value.value)
+ return value_;
+}
+ void UInt64Value::set_value(::google::protobuf::uint64 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UInt64Value.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int Int32Value::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+Int32Value::Int32Value()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.Int32Value)
+}
+
+Int32Value::Int32Value(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.Int32Value)
+}
+
+void Int32Value::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+Int32Value::Int32Value(const Int32Value& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.Int32Value)
+}
+
+void Int32Value::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ value_ = 0;
+}
+
+Int32Value::~Int32Value() {
+ // @@protoc_insertion_point(destructor:google.protobuf.Int32Value)
+ SharedDtor();
+}
+
+void Int32Value::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void Int32Value::ArenaDtor(void* object) {
+ Int32Value* _this = reinterpret_cast< Int32Value* >(object);
+ (void)_this;
+}
+void Int32Value::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void Int32Value::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* Int32Value::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return Int32Value_descriptor_;
+}
+
+const Int32Value& Int32Value::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+Int32Value* Int32Value::default_instance_ = NULL;
+
+Int32Value* Int32Value::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<Int32Value>(arena);
+}
+
+void Int32Value::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Int32Value)
+ value_ = 0;
+}
+
+bool Int32Value::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.Int32Value)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional int32 value = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::int32, ::google::protobuf::internal::WireFormatLite::TYPE_INT32>(
+ input, &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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.Int32Value)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.Int32Value)
+ return false;
+#undef DO_
+}
+
+void Int32Value::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.Int32Value)
+ // optional int32 value = 1;
+ if (this->value() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteInt32(1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.Int32Value)
+}
+
+::google::protobuf::uint8* Int32Value::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Int32Value)
+ // optional int32 value = 1;
+ if (this->value() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteInt32ToArray(1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Int32Value)
+ return target;
+}
+
+int Int32Value::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Int32Value)
+ int total_size = 0;
+
+ // optional int32 value = 1;
+ if (this->value() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::Int32Size(
+ this->value());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void Int32Value::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Int32Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const Int32Value* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const Int32Value>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Int32Value)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Int32Value)
+ MergeFrom(*source);
+ }
+}
+
+void Int32Value::MergeFrom(const Int32Value& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Int32Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value() != 0) {
+ set_value(from.value());
+ }
+}
+
+void Int32Value::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Int32Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void Int32Value::CopyFrom(const Int32Value& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Int32Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool Int32Value::IsInitialized() const {
+
+ return true;
+}
+
+void Int32Value::Swap(Int32Value* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ Int32Value temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void Int32Value::UnsafeArenaSwap(Int32Value* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void Int32Value::InternalSwap(Int32Value* other) {
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata Int32Value::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = Int32Value_descriptor_;
+ metadata.reflection = Int32Value_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// Int32Value
+
+// optional int32 value = 1;
+void Int32Value::clear_value() {
+ value_ = 0;
+}
+ ::google::protobuf::int32 Int32Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Int32Value.value)
+ return value_;
+}
+ void Int32Value::set_value(::google::protobuf::int32 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Int32Value.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int UInt32Value::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+UInt32Value::UInt32Value()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.UInt32Value)
+}
+
+UInt32Value::UInt32Value(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.UInt32Value)
+}
+
+void UInt32Value::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+UInt32Value::UInt32Value(const UInt32Value& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.UInt32Value)
+}
+
+void UInt32Value::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ value_ = 0u;
+}
+
+UInt32Value::~UInt32Value() {
+ // @@protoc_insertion_point(destructor:google.protobuf.UInt32Value)
+ SharedDtor();
+}
+
+void UInt32Value::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void UInt32Value::ArenaDtor(void* object) {
+ UInt32Value* _this = reinterpret_cast< UInt32Value* >(object);
+ (void)_this;
+}
+void UInt32Value::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void UInt32Value::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* UInt32Value::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return UInt32Value_descriptor_;
+}
+
+const UInt32Value& UInt32Value::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+UInt32Value* UInt32Value::default_instance_ = NULL;
+
+UInt32Value* UInt32Value::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<UInt32Value>(arena);
+}
+
+void UInt32Value::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.UInt32Value)
+ value_ = 0u;
+}
+
+bool UInt32Value::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.UInt32Value)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional uint32 value = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ ::google::protobuf::uint32, ::google::protobuf::internal::WireFormatLite::TYPE_UINT32>(
+ input, &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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.UInt32Value)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.UInt32Value)
+ return false;
+#undef DO_
+}
+
+void UInt32Value::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.UInt32Value)
+ // optional uint32 value = 1;
+ if (this->value() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteUInt32(1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.UInt32Value)
+}
+
+::google::protobuf::uint8* UInt32Value::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.UInt32Value)
+ // optional uint32 value = 1;
+ if (this->value() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteUInt32ToArray(1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.UInt32Value)
+ return target;
+}
+
+int UInt32Value::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.UInt32Value)
+ int total_size = 0;
+
+ // optional uint32 value = 1;
+ if (this->value() != 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::UInt32Size(
+ this->value());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void UInt32Value::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.UInt32Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const UInt32Value* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const UInt32Value>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.UInt32Value)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.UInt32Value)
+ MergeFrom(*source);
+ }
+}
+
+void UInt32Value::MergeFrom(const UInt32Value& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.UInt32Value)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value() != 0) {
+ set_value(from.value());
+ }
+}
+
+void UInt32Value::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.UInt32Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void UInt32Value::CopyFrom(const UInt32Value& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.UInt32Value)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool UInt32Value::IsInitialized() const {
+
+ return true;
+}
+
+void UInt32Value::Swap(UInt32Value* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ UInt32Value temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void UInt32Value::UnsafeArenaSwap(UInt32Value* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void UInt32Value::InternalSwap(UInt32Value* other) {
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata UInt32Value::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = UInt32Value_descriptor_;
+ metadata.reflection = UInt32Value_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// UInt32Value
+
+// optional uint32 value = 1;
+void UInt32Value::clear_value() {
+ value_ = 0u;
+}
+ ::google::protobuf::uint32 UInt32Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UInt32Value.value)
+ return value_;
+}
+ void UInt32Value::set_value(::google::protobuf::uint32 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UInt32Value.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int BoolValue::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+BoolValue::BoolValue()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.BoolValue)
+}
+
+BoolValue::BoolValue(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.BoolValue)
+}
+
+void BoolValue::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+BoolValue::BoolValue(const BoolValue& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.BoolValue)
+}
+
+void BoolValue::SharedCtor() {
+ _is_default_instance_ = false;
+ _cached_size_ = 0;
+ value_ = false;
+}
+
+BoolValue::~BoolValue() {
+ // @@protoc_insertion_point(destructor:google.protobuf.BoolValue)
+ SharedDtor();
+}
+
+void BoolValue::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ if (this != default_instance_) {
+ }
+}
+
+void BoolValue::ArenaDtor(void* object) {
+ BoolValue* _this = reinterpret_cast< BoolValue* >(object);
+ (void)_this;
+}
+void BoolValue::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void BoolValue::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* BoolValue::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return BoolValue_descriptor_;
+}
+
+const BoolValue& BoolValue::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+BoolValue* BoolValue::default_instance_ = NULL;
+
+BoolValue* BoolValue::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<BoolValue>(arena);
+}
+
+void BoolValue::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.BoolValue)
+ value_ = false;
+}
+
+bool BoolValue::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.BoolValue)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional bool value = 1;
+ case 1: {
+ if (tag == 8) {
+ DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
+ bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
+ input, &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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.BoolValue)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.BoolValue)
+ return false;
+#undef DO_
+}
+
+void BoolValue::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.BoolValue)
+ // optional bool value = 1;
+ if (this->value() != 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteBool(1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.BoolValue)
+}
+
+::google::protobuf::uint8* BoolValue::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.BoolValue)
+ // optional bool value = 1;
+ if (this->value() != 0) {
+ target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.BoolValue)
+ return target;
+}
+
+int BoolValue::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.BoolValue)
+ int total_size = 0;
+
+ // optional bool value = 1;
+ if (this->value() != 0) {
+ total_size += 1 + 1;
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void BoolValue::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.BoolValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const BoolValue* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const BoolValue>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.BoolValue)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.BoolValue)
+ MergeFrom(*source);
+ }
+}
+
+void BoolValue::MergeFrom(const BoolValue& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.BoolValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value() != 0) {
+ set_value(from.value());
+ }
+}
+
+void BoolValue::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.BoolValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void BoolValue::CopyFrom(const BoolValue& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.BoolValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool BoolValue::IsInitialized() const {
+
+ return true;
+}
+
+void BoolValue::Swap(BoolValue* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ BoolValue temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void BoolValue::UnsafeArenaSwap(BoolValue* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void BoolValue::InternalSwap(BoolValue* other) {
+ std::swap(value_, other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata BoolValue::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = BoolValue_descriptor_;
+ metadata.reflection = BoolValue_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// BoolValue
+
+// optional bool value = 1;
+void BoolValue::clear_value() {
+ value_ = false;
+}
+ bool BoolValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.BoolValue.value)
+ return value_;
+}
+ void BoolValue::set_value(bool value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.BoolValue.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int StringValue::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+StringValue::StringValue()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.StringValue)
+}
+
+StringValue::StringValue(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.StringValue)
+}
+
+void StringValue::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+StringValue::StringValue(const StringValue& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.StringValue)
+}
+
+void StringValue::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+StringValue::~StringValue() {
+ // @@protoc_insertion_point(destructor:google.protobuf.StringValue)
+ SharedDtor();
+}
+
+void StringValue::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ value_.Destroy(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+ if (this != default_instance_) {
+ }
+}
+
+void StringValue::ArenaDtor(void* object) {
+ StringValue* _this = reinterpret_cast< StringValue* >(object);
+ (void)_this;
+}
+void StringValue::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void StringValue::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* StringValue::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return StringValue_descriptor_;
+}
+
+const StringValue& StringValue::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+StringValue* StringValue::default_instance_ = NULL;
+
+StringValue* StringValue::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<StringValue>(arena);
+}
+
+void StringValue::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.StringValue)
+ value_.ClearToEmpty(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+
+bool StringValue::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.StringValue)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional string value = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadString(
+ input, this->mutable_value()));
+ DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->value().data(), this->value().length(),
+ ::google::protobuf::internal::WireFormatLite::PARSE,
+ "google.protobuf.StringValue.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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.StringValue)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.StringValue)
+ return false;
+#undef DO_
+}
+
+void StringValue::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.StringValue)
+ // optional string value = 1;
+ if (this->value().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->value().data(), this->value().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.StringValue.value");
+ ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
+ 1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.StringValue)
+}
+
+::google::protobuf::uint8* StringValue::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.StringValue)
+ // optional string value = 1;
+ if (this->value().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+ this->value().data(), this->value().length(),
+ ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+ "google.protobuf.StringValue.value");
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteStringToArray(
+ 1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.StringValue)
+ return target;
+}
+
+int StringValue::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.StringValue)
+ int total_size = 0;
+
+ // optional string value = 1;
+ if (this->value().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::StringSize(
+ this->value());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void StringValue::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.StringValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const StringValue* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const StringValue>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.StringValue)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.StringValue)
+ MergeFrom(*source);
+ }
+}
+
+void StringValue::MergeFrom(const StringValue& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.StringValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value().size() > 0) {
+ set_value(from.value());
+ }
+}
+
+void StringValue::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.StringValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void StringValue::CopyFrom(const StringValue& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.StringValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool StringValue::IsInitialized() const {
+
+ return true;
+}
+
+void StringValue::Swap(StringValue* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ StringValue temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void StringValue::UnsafeArenaSwap(StringValue* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void StringValue::InternalSwap(StringValue* other) {
+ value_.Swap(&other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata StringValue::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = StringValue_descriptor_;
+ metadata.reflection = StringValue_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// StringValue
+
+// optional string value = 1;
+void StringValue::clear_value() {
+ value_.ClearToEmpty(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+ const ::std::string& StringValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.StringValue.value)
+ return value_.Get(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void StringValue::set_value(const ::std::string& value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set:google.protobuf.StringValue.value)
+}
+ void StringValue::set_value(const char* value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value),
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_char:google.protobuf.StringValue.value)
+}
+ void StringValue::set_value(const char* value,
+ size_t size) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(
+ reinterpret_cast<const char*>(value), size), GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.StringValue.value)
+}
+ ::std::string* StringValue::mutable_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.StringValue.value)
+ return value_.Mutable(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+ ::std::string* StringValue::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.StringValue.value)
+
+ return value_.Release(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+ ::std::string* StringValue::unsafe_arena_release_value() {
+ // @@protoc_insertion_point(field_unsafe_arena_release:google.protobuf.StringValue.value)
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+
+ return value_.UnsafeArenaRelease(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ GetArenaNoVirtual());
+}
+ void StringValue::set_allocated_value(::std::string* value) {
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.SetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value,
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.StringValue.value)
+}
+ void StringValue::unsafe_arena_set_allocated_value(
+ ::std::string* value) {
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.UnsafeArenaSetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_unsafe_arena_set_allocated:google.protobuf.StringValue.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// ===================================================================
+
+#if !defined(_MSC_VER) || _MSC_VER >= 1900
+const int BytesValue::kValueFieldNumber;
+#endif // !defined(_MSC_VER) || _MSC_VER >= 1900
+
+BytesValue::BytesValue()
+ : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+ SharedCtor();
+ // @@protoc_insertion_point(constructor:google.protobuf.BytesValue)
+}
+
+BytesValue::BytesValue(::google::protobuf::Arena* arena)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(arena) {
+ SharedCtor();
+ RegisterArenaDtor(arena);
+ // @@protoc_insertion_point(arena_constructor:google.protobuf.BytesValue)
+}
+
+void BytesValue::InitAsDefaultInstance() {
+ _is_default_instance_ = true;
+}
+
+BytesValue::BytesValue(const BytesValue& from)
+ : ::google::protobuf::Message(),
+ _internal_metadata_(NULL) {
+ SharedCtor();
+ MergeFrom(from);
+ // @@protoc_insertion_point(copy_constructor:google.protobuf.BytesValue)
+}
+
+void BytesValue::SharedCtor() {
+ _is_default_instance_ = false;
+ ::google::protobuf::internal::GetEmptyString();
+ _cached_size_ = 0;
+ value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+
+BytesValue::~BytesValue() {
+ // @@protoc_insertion_point(destructor:google.protobuf.BytesValue)
+ SharedDtor();
+}
+
+void BytesValue::SharedDtor() {
+ if (GetArenaNoVirtual() != NULL) {
+ return;
+ }
+
+ value_.Destroy(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+ if (this != default_instance_) {
+ }
+}
+
+void BytesValue::ArenaDtor(void* object) {
+ BytesValue* _this = reinterpret_cast< BytesValue* >(object);
+ (void)_this;
+}
+void BytesValue::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
+void BytesValue::SetCachedSize(int size) const {
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+}
+const ::google::protobuf::Descriptor* BytesValue::descriptor() {
+ protobuf_AssignDescriptorsOnce();
+ return BytesValue_descriptor_;
+}
+
+const BytesValue& BytesValue::default_instance() {
+ if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ return *default_instance_;
+}
+
+BytesValue* BytesValue::default_instance_ = NULL;
+
+BytesValue* BytesValue::New(::google::protobuf::Arena* arena) const {
+ return ::google::protobuf::Arena::CreateMessage<BytesValue>(arena);
+}
+
+void BytesValue::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.BytesValue)
+ value_.ClearToEmpty(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+
+bool BytesValue::MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input) {
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
+ ::google::protobuf::uint32 tag;
+ // @@protoc_insertion_point(parse_start:google.protobuf.BytesValue)
+ for (;;) {
+ ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+ tag = p.first;
+ if (!p.second) goto handle_unusual;
+ switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
+ // optional bytes value = 1;
+ case 1: {
+ if (tag == 10) {
+ DO_(::google::protobuf::internal::WireFormatLite::ReadBytes(
+ input, this->mutable_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) {
+ goto success;
+ }
+ DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+ break;
+ }
+ }
+ }
+success:
+ // @@protoc_insertion_point(parse_success:google.protobuf.BytesValue)
+ return true;
+failure:
+ // @@protoc_insertion_point(parse_failure:google.protobuf.BytesValue)
+ return false;
+#undef DO_
+}
+
+void BytesValue::SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const {
+ // @@protoc_insertion_point(serialize_start:google.protobuf.BytesValue)
+ // optional bytes value = 1;
+ if (this->value().size() > 0) {
+ ::google::protobuf::internal::WireFormatLite::WriteBytesMaybeAliased(
+ 1, this->value(), output);
+ }
+
+ // @@protoc_insertion_point(serialize_end:google.protobuf.BytesValue)
+}
+
+::google::protobuf::uint8* BytesValue::InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* target) const {
+ // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.BytesValue)
+ // optional bytes value = 1;
+ if (this->value().size() > 0) {
+ target =
+ ::google::protobuf::internal::WireFormatLite::WriteBytesToArray(
+ 1, this->value(), target);
+ }
+
+ // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.BytesValue)
+ return target;
+}
+
+int BytesValue::ByteSize() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.BytesValue)
+ int total_size = 0;
+
+ // optional bytes value = 1;
+ if (this->value().size() > 0) {
+ total_size += 1 +
+ ::google::protobuf::internal::WireFormatLite::BytesSize(
+ this->value());
+ }
+
+ GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
+ _cached_size_ = total_size;
+ GOOGLE_SAFE_CONCURRENT_WRITES_END();
+ return total_size;
+}
+
+void BytesValue::MergeFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.BytesValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ const BytesValue* source =
+ ::google::protobuf::internal::DynamicCastToGenerated<const BytesValue>(
+ &from);
+ if (source == NULL) {
+ // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.BytesValue)
+ ::google::protobuf::internal::ReflectionOps::Merge(from, this);
+ } else {
+ // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.BytesValue)
+ MergeFrom(*source);
+ }
+}
+
+void BytesValue::MergeFrom(const BytesValue& from) {
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.BytesValue)
+ if (GOOGLE_PREDICT_FALSE(&from == this)) {
+ ::google::protobuf::internal::MergeFromFail(__FILE__, __LINE__);
+ }
+ if (from.value().size() > 0) {
+ set_value(from.value());
+ }
+}
+
+void BytesValue::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.BytesValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+void BytesValue::CopyFrom(const BytesValue& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.BytesValue)
+ if (&from == this) return;
+ Clear();
+ MergeFrom(from);
+}
+
+bool BytesValue::IsInitialized() const {
+
+ return true;
+}
+
+void BytesValue::Swap(BytesValue* other) {
+ if (other == this) return;
+ if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+ InternalSwap(other);
+ } else {
+ BytesValue temp;
+ temp.MergeFrom(*this);
+ CopyFrom(*other);
+ other->CopyFrom(temp);
+ }
+}
+void BytesValue::UnsafeArenaSwap(BytesValue* other) {
+ if (other == this) return;
+ GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
+ InternalSwap(other);
+}
+void BytesValue::InternalSwap(BytesValue* other) {
+ value_.Swap(&other->value_);
+ _internal_metadata_.Swap(&other->_internal_metadata_);
+ std::swap(_cached_size_, other->_cached_size_);
+}
+
+::google::protobuf::Metadata BytesValue::GetMetadata() const {
+ protobuf_AssignDescriptorsOnce();
+ ::google::protobuf::Metadata metadata;
+ metadata.descriptor = BytesValue_descriptor_;
+ metadata.reflection = BytesValue_reflection_;
+ return metadata;
+}
+
+#if PROTOBUF_INLINE_NOT_IN_HEADERS
+// BytesValue
+
+// optional bytes value = 1;
+void BytesValue::clear_value() {
+ value_.ClearToEmpty(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+ const ::std::string& BytesValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.BytesValue.value)
+ return value_.Get(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+ void BytesValue::set_value(const ::std::string& value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set:google.protobuf.BytesValue.value)
+}
+ void BytesValue::set_value(const char* value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value),
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_char:google.protobuf.BytesValue.value)
+}
+ void BytesValue::set_value(const void* value,
+ size_t size) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(
+ reinterpret_cast<const char*>(value), size), GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.BytesValue.value)
+}
+ ::std::string* BytesValue::mutable_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.BytesValue.value)
+ return value_.Mutable(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+ ::std::string* BytesValue::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.BytesValue.value)
+
+ return value_.Release(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+ ::std::string* BytesValue::unsafe_arena_release_value() {
+ // @@protoc_insertion_point(field_unsafe_arena_release:google.protobuf.BytesValue.value)
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+
+ return value_.UnsafeArenaRelease(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ GetArenaNoVirtual());
+}
+ void BytesValue::set_allocated_value(::std::string* value) {
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.SetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value,
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.BytesValue.value)
+}
+ void BytesValue::unsafe_arena_set_allocated_value(
+ ::std::string* value) {
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.UnsafeArenaSetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_unsafe_arena_set_allocated:google.protobuf.BytesValue.value)
+}
+
+#endif // PROTOBUF_INLINE_NOT_IN_HEADERS
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.h b/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.h
new file mode 100644
index 0000000000..73f8ff62d3
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.pb.h
@@ -0,0 +1,1216 @@
+// Generated by the protocol buffer compiler. DO NOT EDIT!
+// source: google/protobuf/wrappers.proto
+
+#ifndef PROTOBUF_google_2fprotobuf_2fwrappers_2eproto__INCLUDED
+#define PROTOBUF_google_2fprotobuf_2fwrappers_2eproto__INCLUDED
+
+#include <string>
+
+#include <google/protobuf/stubs/common.h>
+
+#if GOOGLE_PROTOBUF_VERSION < 3000000
+#error This file was generated by a newer version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please update
+#error your headers.
+#endif
+#if 3000000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION
+#error This file was generated by an older version of protoc which is
+#error incompatible with your Protocol Buffer headers. Please
+#error regenerate this file with a newer version of protoc.
+#endif
+
+#include <google/protobuf/arena.h>
+#include <google/protobuf/arenastring.h>
+#include <google/protobuf/generated_message_util.h>
+#include <google/protobuf/metadata.h>
+#include <google/protobuf/message.h>
+#include <google/protobuf/repeated_field.h>
+#include <google/protobuf/extension_set.h>
+#include <google/protobuf/unknown_field_set.h>
+// @@protoc_insertion_point(includes)
+
+namespace google {
+namespace protobuf {
+
+// Internal implementation detail -- do not call these.
+void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+class BoolValue;
+class BytesValue;
+class DoubleValue;
+class FloatValue;
+class Int32Value;
+class Int64Value;
+class StringValue;
+class UInt32Value;
+class UInt64Value;
+
+// ===================================================================
+
+class LIBPROTOBUF_EXPORT DoubleValue : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.DoubleValue) */ {
+ public:
+ DoubleValue();
+ virtual ~DoubleValue();
+
+ DoubleValue(const DoubleValue& from);
+
+ inline DoubleValue& operator=(const DoubleValue& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const DoubleValue& default_instance();
+
+ void UnsafeArenaSwap(DoubleValue* other);
+ void Swap(DoubleValue* other);
+
+ // implements Message ----------------------------------------------
+
+ inline DoubleValue* New() const { return New(NULL); }
+
+ DoubleValue* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const DoubleValue& from);
+ void MergeFrom(const DoubleValue& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(DoubleValue* other);
+ protected:
+ explicit DoubleValue(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional double value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ double value() const;
+ void set_value(double value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.DoubleValue)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ double value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static DoubleValue* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT FloatValue : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.FloatValue) */ {
+ public:
+ FloatValue();
+ virtual ~FloatValue();
+
+ FloatValue(const FloatValue& from);
+
+ inline FloatValue& operator=(const FloatValue& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const FloatValue& default_instance();
+
+ void UnsafeArenaSwap(FloatValue* other);
+ void Swap(FloatValue* other);
+
+ // implements Message ----------------------------------------------
+
+ inline FloatValue* New() const { return New(NULL); }
+
+ FloatValue* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const FloatValue& from);
+ void MergeFrom(const FloatValue& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(FloatValue* other);
+ protected:
+ explicit FloatValue(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional float value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ float value() const;
+ void set_value(float value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.FloatValue)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ float value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static FloatValue* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Int64Value : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Int64Value) */ {
+ public:
+ Int64Value();
+ virtual ~Int64Value();
+
+ Int64Value(const Int64Value& from);
+
+ inline Int64Value& operator=(const Int64Value& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Int64Value& default_instance();
+
+ void UnsafeArenaSwap(Int64Value* other);
+ void Swap(Int64Value* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Int64Value* New() const { return New(NULL); }
+
+ Int64Value* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Int64Value& from);
+ void MergeFrom(const Int64Value& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Int64Value* other);
+ protected:
+ explicit Int64Value(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional int64 value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ ::google::protobuf::int64 value() const;
+ void set_value(::google::protobuf::int64 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Int64Value)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ ::google::protobuf::int64 value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static Int64Value* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT UInt64Value : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.UInt64Value) */ {
+ public:
+ UInt64Value();
+ virtual ~UInt64Value();
+
+ UInt64Value(const UInt64Value& from);
+
+ inline UInt64Value& operator=(const UInt64Value& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const UInt64Value& default_instance();
+
+ void UnsafeArenaSwap(UInt64Value* other);
+ void Swap(UInt64Value* other);
+
+ // implements Message ----------------------------------------------
+
+ inline UInt64Value* New() const { return New(NULL); }
+
+ UInt64Value* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const UInt64Value& from);
+ void MergeFrom(const UInt64Value& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(UInt64Value* other);
+ protected:
+ explicit UInt64Value(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional uint64 value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ ::google::protobuf::uint64 value() const;
+ void set_value(::google::protobuf::uint64 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.UInt64Value)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ ::google::protobuf::uint64 value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static UInt64Value* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT Int32Value : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.Int32Value) */ {
+ public:
+ Int32Value();
+ virtual ~Int32Value();
+
+ Int32Value(const Int32Value& from);
+
+ inline Int32Value& operator=(const Int32Value& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const Int32Value& default_instance();
+
+ void UnsafeArenaSwap(Int32Value* other);
+ void Swap(Int32Value* other);
+
+ // implements Message ----------------------------------------------
+
+ inline Int32Value* New() const { return New(NULL); }
+
+ Int32Value* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const Int32Value& from);
+ void MergeFrom(const Int32Value& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(Int32Value* other);
+ protected:
+ explicit Int32Value(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional int32 value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ ::google::protobuf::int32 value() const;
+ void set_value(::google::protobuf::int32 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.Int32Value)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ ::google::protobuf::int32 value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static Int32Value* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT UInt32Value : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.UInt32Value) */ {
+ public:
+ UInt32Value();
+ virtual ~UInt32Value();
+
+ UInt32Value(const UInt32Value& from);
+
+ inline UInt32Value& operator=(const UInt32Value& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const UInt32Value& default_instance();
+
+ void UnsafeArenaSwap(UInt32Value* other);
+ void Swap(UInt32Value* other);
+
+ // implements Message ----------------------------------------------
+
+ inline UInt32Value* New() const { return New(NULL); }
+
+ UInt32Value* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const UInt32Value& from);
+ void MergeFrom(const UInt32Value& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(UInt32Value* other);
+ protected:
+ explicit UInt32Value(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional uint32 value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ ::google::protobuf::uint32 value() const;
+ void set_value(::google::protobuf::uint32 value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.UInt32Value)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ ::google::protobuf::uint32 value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static UInt32Value* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT BoolValue : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.BoolValue) */ {
+ public:
+ BoolValue();
+ virtual ~BoolValue();
+
+ BoolValue(const BoolValue& from);
+
+ inline BoolValue& operator=(const BoolValue& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const BoolValue& default_instance();
+
+ void UnsafeArenaSwap(BoolValue* other);
+ void Swap(BoolValue* other);
+
+ // implements Message ----------------------------------------------
+
+ inline BoolValue* New() const { return New(NULL); }
+
+ BoolValue* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const BoolValue& from);
+ void MergeFrom(const BoolValue& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(BoolValue* other);
+ protected:
+ explicit BoolValue(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional bool value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ bool value() const;
+ void set_value(bool value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.BoolValue)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ bool value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static BoolValue* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT StringValue : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.StringValue) */ {
+ public:
+ StringValue();
+ virtual ~StringValue();
+
+ StringValue(const StringValue& from);
+
+ inline StringValue& operator=(const StringValue& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const StringValue& default_instance();
+
+ void UnsafeArenaSwap(StringValue* other);
+ void Swap(StringValue* other);
+
+ // implements Message ----------------------------------------------
+
+ inline StringValue* New() const { return New(NULL); }
+
+ StringValue* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const StringValue& from);
+ void MergeFrom(const StringValue& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(StringValue* other);
+ protected:
+ explicit StringValue(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional string value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ const ::std::string& value() const;
+ void set_value(const ::std::string& value);
+ void set_value(const char* value);
+ void set_value(const char* value, size_t size);
+ ::std::string* mutable_value();
+ ::std::string* release_value();
+ void set_allocated_value(::std::string* value);
+ ::std::string* unsafe_arena_release_value();
+ void unsafe_arena_set_allocated_value(
+ ::std::string* value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.StringValue)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static StringValue* default_instance_;
+};
+// -------------------------------------------------------------------
+
+class LIBPROTOBUF_EXPORT BytesValue : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:google.protobuf.BytesValue) */ {
+ public:
+ BytesValue();
+ virtual ~BytesValue();
+
+ BytesValue(const BytesValue& from);
+
+ inline BytesValue& operator=(const BytesValue& from) {
+ CopyFrom(from);
+ return *this;
+ }
+
+ inline ::google::protobuf::Arena* GetArena() const { return GetArenaNoVirtual(); }
+ inline void* GetMaybeArenaPointer() const {
+ return MaybeArenaPtr();
+ }
+ static const ::google::protobuf::Descriptor* descriptor();
+ static const BytesValue& default_instance();
+
+ void UnsafeArenaSwap(BytesValue* other);
+ void Swap(BytesValue* other);
+
+ // implements Message ----------------------------------------------
+
+ inline BytesValue* New() const { return New(NULL); }
+
+ BytesValue* New(::google::protobuf::Arena* arena) const;
+ void CopyFrom(const ::google::protobuf::Message& from);
+ void MergeFrom(const ::google::protobuf::Message& from);
+ void CopyFrom(const BytesValue& from);
+ void MergeFrom(const BytesValue& from);
+ void Clear();
+ bool IsInitialized() const;
+
+ int ByteSize() const;
+ bool MergePartialFromCodedStream(
+ ::google::protobuf::io::CodedInputStream* input);
+ void SerializeWithCachedSizes(
+ ::google::protobuf::io::CodedOutputStream* output) const;
+ ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray(
+ bool deterministic, ::google::protobuf::uint8* output) const;
+ ::google::protobuf::uint8* SerializeWithCachedSizesToArray(::google::protobuf::uint8* output) const {
+ return InternalSerializeWithCachedSizesToArray(false, output);
+ }
+ int GetCachedSize() const { return _cached_size_; }
+ private:
+ void SharedCtor();
+ void SharedDtor();
+ void SetCachedSize(int size) const;
+ void InternalSwap(BytesValue* other);
+ protected:
+ explicit BytesValue(::google::protobuf::Arena* arena);
+ private:
+ static void ArenaDtor(void* object);
+ inline void RegisterArenaDtor(::google::protobuf::Arena* arena);
+ private:
+ inline ::google::protobuf::Arena* GetArenaNoVirtual() const {
+ return _internal_metadata_.arena();
+ }
+ inline void* MaybeArenaPtr() const {
+ return _internal_metadata_.raw_arena_ptr();
+ }
+ public:
+
+ ::google::protobuf::Metadata GetMetadata() const;
+
+ // nested types ----------------------------------------------------
+
+ // accessors -------------------------------------------------------
+
+ // optional bytes value = 1;
+ void clear_value();
+ static const int kValueFieldNumber = 1;
+ const ::std::string& value() const;
+ void set_value(const ::std::string& value);
+ void set_value(const char* value);
+ void set_value(const void* value, size_t size);
+ ::std::string* mutable_value();
+ ::std::string* release_value();
+ void set_allocated_value(::std::string* value);
+ ::std::string* unsafe_arena_release_value();
+ void unsafe_arena_set_allocated_value(
+ ::std::string* value);
+
+ // @@protoc_insertion_point(class_scope:google.protobuf.BytesValue)
+ private:
+
+ ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_;
+ friend class ::google::protobuf::Arena;
+ typedef void InternalArenaConstructable_;
+ typedef void DestructorSkippable_;
+ bool _is_default_instance_;
+ ::google::protobuf::internal::ArenaStringPtr value_;
+ mutable int _cached_size_;
+ friend void LIBPROTOBUF_EXPORT protobuf_AddDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_AssignDesc_google_2fprotobuf_2fwrappers_2eproto();
+ friend void protobuf_ShutdownFile_google_2fprotobuf_2fwrappers_2eproto();
+
+ void InitAsDefaultInstance();
+ static BytesValue* default_instance_;
+};
+// ===================================================================
+
+
+// ===================================================================
+
+#if !PROTOBUF_INLINE_NOT_IN_HEADERS
+// DoubleValue
+
+// optional double value = 1;
+inline void DoubleValue::clear_value() {
+ value_ = 0;
+}
+inline double DoubleValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.DoubleValue.value)
+ return value_;
+}
+inline void DoubleValue::set_value(double value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.DoubleValue.value)
+}
+
+// -------------------------------------------------------------------
+
+// FloatValue
+
+// optional float value = 1;
+inline void FloatValue::clear_value() {
+ value_ = 0;
+}
+inline float FloatValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.FloatValue.value)
+ return value_;
+}
+inline void FloatValue::set_value(float value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.FloatValue.value)
+}
+
+// -------------------------------------------------------------------
+
+// Int64Value
+
+// optional int64 value = 1;
+inline void Int64Value::clear_value() {
+ value_ = GOOGLE_LONGLONG(0);
+}
+inline ::google::protobuf::int64 Int64Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Int64Value.value)
+ return value_;
+}
+inline void Int64Value::set_value(::google::protobuf::int64 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Int64Value.value)
+}
+
+// -------------------------------------------------------------------
+
+// UInt64Value
+
+// optional uint64 value = 1;
+inline void UInt64Value::clear_value() {
+ value_ = GOOGLE_ULONGLONG(0);
+}
+inline ::google::protobuf::uint64 UInt64Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UInt64Value.value)
+ return value_;
+}
+inline void UInt64Value::set_value(::google::protobuf::uint64 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UInt64Value.value)
+}
+
+// -------------------------------------------------------------------
+
+// Int32Value
+
+// optional int32 value = 1;
+inline void Int32Value::clear_value() {
+ value_ = 0;
+}
+inline ::google::protobuf::int32 Int32Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.Int32Value.value)
+ return value_;
+}
+inline void Int32Value::set_value(::google::protobuf::int32 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.Int32Value.value)
+}
+
+// -------------------------------------------------------------------
+
+// UInt32Value
+
+// optional uint32 value = 1;
+inline void UInt32Value::clear_value() {
+ value_ = 0u;
+}
+inline ::google::protobuf::uint32 UInt32Value::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.UInt32Value.value)
+ return value_;
+}
+inline void UInt32Value::set_value(::google::protobuf::uint32 value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.UInt32Value.value)
+}
+
+// -------------------------------------------------------------------
+
+// BoolValue
+
+// optional bool value = 1;
+inline void BoolValue::clear_value() {
+ value_ = false;
+}
+inline bool BoolValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.BoolValue.value)
+ return value_;
+}
+inline void BoolValue::set_value(bool value) {
+
+ value_ = value;
+ // @@protoc_insertion_point(field_set:google.protobuf.BoolValue.value)
+}
+
+// -------------------------------------------------------------------
+
+// StringValue
+
+// optional string value = 1;
+inline void StringValue::clear_value() {
+ value_.ClearToEmpty(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+inline const ::std::string& StringValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.StringValue.value)
+ return value_.Get(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void StringValue::set_value(const ::std::string& value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set:google.protobuf.StringValue.value)
+}
+inline void StringValue::set_value(const char* value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value),
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_char:google.protobuf.StringValue.value)
+}
+inline void StringValue::set_value(const char* value,
+ size_t size) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(
+ reinterpret_cast<const char*>(value), size), GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.StringValue.value)
+}
+inline ::std::string* StringValue::mutable_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.StringValue.value)
+ return value_.Mutable(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+inline ::std::string* StringValue::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.StringValue.value)
+
+ return value_.Release(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+inline ::std::string* StringValue::unsafe_arena_release_value() {
+ // @@protoc_insertion_point(field_unsafe_arena_release:google.protobuf.StringValue.value)
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+
+ return value_.UnsafeArenaRelease(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ GetArenaNoVirtual());
+}
+inline void StringValue::set_allocated_value(::std::string* value) {
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.SetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value,
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.StringValue.value)
+}
+inline void StringValue::unsafe_arena_set_allocated_value(
+ ::std::string* value) {
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.UnsafeArenaSetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_unsafe_arena_set_allocated:google.protobuf.StringValue.value)
+}
+
+// -------------------------------------------------------------------
+
+// BytesValue
+
+// optional bytes value = 1;
+inline void BytesValue::clear_value() {
+ value_.ClearToEmpty(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+inline const ::std::string& BytesValue::value() const {
+ // @@protoc_insertion_point(field_get:google.protobuf.BytesValue.value)
+ return value_.Get(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+}
+inline void BytesValue::set_value(const ::std::string& value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set:google.protobuf.BytesValue.value)
+}
+inline void BytesValue::set_value(const char* value) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(value),
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_char:google.protobuf.BytesValue.value)
+}
+inline void BytesValue::set_value(const void* value,
+ size_t size) {
+
+ value_.Set(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(
+ reinterpret_cast<const char*>(value), size), GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_pointer:google.protobuf.BytesValue.value)
+}
+inline ::std::string* BytesValue::mutable_value() {
+
+ // @@protoc_insertion_point(field_mutable:google.protobuf.BytesValue.value)
+ return value_.Mutable(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+inline ::std::string* BytesValue::release_value() {
+ // @@protoc_insertion_point(field_release:google.protobuf.BytesValue.value)
+
+ return value_.Release(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), GetArenaNoVirtual());
+}
+inline ::std::string* BytesValue::unsafe_arena_release_value() {
+ // @@protoc_insertion_point(field_unsafe_arena_release:google.protobuf.BytesValue.value)
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+
+ return value_.UnsafeArenaRelease(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ GetArenaNoVirtual());
+}
+inline void BytesValue::set_allocated_value(::std::string* value) {
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.SetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value,
+ GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_set_allocated:google.protobuf.BytesValue.value)
+}
+inline void BytesValue::unsafe_arena_set_allocated_value(
+ ::std::string* value) {
+ GOOGLE_DCHECK(GetArenaNoVirtual() != NULL);
+ if (value != NULL) {
+
+ } else {
+
+ }
+ value_.UnsafeArenaSetAllocated(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+ value, GetArenaNoVirtual());
+ // @@protoc_insertion_point(field_unsafe_arena_set_allocated:google.protobuf.BytesValue.value)
+}
+
+#endif // !PROTOBUF_INLINE_NOT_IN_HEADERS
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+// -------------------------------------------------------------------
+
+
+// @@protoc_insertion_point(namespace_scope)
+
+} // namespace protobuf
+} // namespace google
+
+// @@protoc_insertion_point(global_scope)
+
+#endif // PROTOBUF_google_2fprotobuf_2fwrappers_2eproto__INCLUDED
diff --git a/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.proto b/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.proto
new file mode 100644
index 0000000000..4828ad9ae9
--- /dev/null
+++ b/third_party/protobuf/3.0.0/src/google/protobuf/wrappers.proto
@@ -0,0 +1,119 @@
+// 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.
+
+// Wrappers for primitive (non-message) types. These types are useful
+// for embedding primitives in the `google.protobuf.Any` type and for places
+// where we need to distinguish between the absence of a primitive
+// typed field and its default value.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option cc_enable_arenas = true;
+option go_package = "github.com/golang/protobuf/ptypes/wrappers";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "WrappersProto";
+option java_multiple_files = true;
+option java_generate_equals_and_hash = true;
+option objc_class_prefix = "GPB";
+
+// Wrapper message for `double`.
+//
+// The JSON representation for `DoubleValue` is JSON number.
+message DoubleValue {
+ // The double value.
+ double value = 1;
+}
+
+// Wrapper message for `float`.
+//
+// The JSON representation for `FloatValue` is JSON number.
+message FloatValue {
+ // The float value.
+ float value = 1;
+}
+
+// Wrapper message for `int64`.
+//
+// The JSON representation for `Int64Value` is JSON string.
+message Int64Value {
+ // The int64 value.
+ int64 value = 1;
+}
+
+// Wrapper message for `uint64`.
+//
+// The JSON representation for `UInt64Value` is JSON string.
+message UInt64Value {
+ // The uint64 value.
+ uint64 value = 1;
+}
+
+// Wrapper message for `int32`.
+//
+// The JSON representation for `Int32Value` is JSON number.
+message Int32Value {
+ // The int32 value.
+ int32 value = 1;
+}
+
+// Wrapper message for `uint32`.
+//
+// The JSON representation for `UInt32Value` is JSON number.
+message UInt32Value {
+ // The uint32 value.
+ uint32 value = 1;
+}
+
+// Wrapper message for `bool`.
+//
+// The JSON representation for `BoolValue` is JSON `true` and `false`.
+message BoolValue {
+ // The bool value.
+ bool value = 1;
+}
+
+// Wrapper message for `string`.
+//
+// The JSON representation for `StringValue` is JSON string.
+message StringValue {
+ // The string value.
+ string value = 1;
+}
+
+// Wrapper message for `bytes`.
+//
+// The JSON representation for `BytesValue` is JSON string.
+message BytesValue {
+ // The bytes value.
+ bytes value = 1;
+}